200字范文,内容丰富有趣,生活中的好帮手!
200字范文 > VUE前端RSA+AES加密调用后端接口

VUE前端RSA+AES加密调用后端接口

时间:2022-07-23 22:58:37

相关推荐

VUE前端RSA+AES加密调用后端接口

之前已经将后端的加解密接口都准备好了过后、就可以跟前端进行联调了。这里使用了VUE作为前端开发框架。我们直接上关键代码了。

jsencrypt(RSA)加密

这里使用了jsencrypt作为前端RSA的加解密工具。需要注意的是填充方式要与服务端的保持一致、我们服务端使用的填充方式是RSA/ECB/OAEPWithSHA-1AndMGF1PADDING。那么对应这里也应该是同样的填充方式。我们先npm安装一下

npm install jsencrypt --save

添加加密方法(encryptUtils.js)

import jsrsasign from 'jsrsasign'export default {/* 加密 */rsaPublicData(data,publicKeys) {console.log("进入加密方法"+data);data = encodeURIComponent(data);let ppKey = '-----BEGIN PUBLIC KEY-----';ppKey += publicKeys;ppKey += '-----END PUBLIC KEY-----';const pubKey = jsrsasign.KEYUTIL.getKey(ppKey);let singResult = jsrsasign.KJUR.crypto.Cipher.encrypt(data, pubKey, "RSAOAEP")singResult = jsrsasign.hextob64(singResult);console.log("sign加密结果是"+singResult);return singResult}}

这里需要注意的是,刚刚说的填充方式、jsrsasign.KJUR.crypto.Cipher.encrypt(data, pubKey, "RSAOAEP256")。这里的RSAOAEP256对应的就是RSA/ECB/OAEPWithSHA-1AndMGF1PADDING的方式,具体对应可以看jsrsasign的APIjsrsasign JavaScript API Reference - KJUR.crypto.Cipher

将js引入main.js中,方便调用

import RSAUtils from "./utils/encryptUtils.js";Vue.prototype.RSAUtils=RSAUtils

这样就可以直接在要使用的地方调用

this.RSAUtils.rsaPublicData("要加密的内容","公钥");

AES加密

AES采用的是crypto-js来进行加密。这里需要注意的是、我们采用的是AES的CBC模式、除了密钥之外还有一个向量。这样的加密强度要高很多、AES的普通ECB模式已经不安全了的。大家如果在使用ECB模式的、请尽快替换成CBC模式。这个插件也需要安装

npm install crypto-js --save-dev

添加加解密方法(AES.js)

import CryptoJS from 'crypto-js'export default {//加密encrypt(word,temp_keyStrs,temp_Iv){// cbc加密let key = temp_keyStrs;let iv = temp_Iv;key = CryptoJS.enc.Utf8.parse(key);iv = CryptoJS.enc.Utf8.parse(iv);let srcs = CryptoJS.enc.Utf8.parse(word);// 加密模式为CBClet encrypted = CryptoJS.AES.encrypt(srcs, key, {iv: iv,mode: CryptoJS.mode.CBC,padding: CryptoJS.pad.Pkcs7});//返回base64return CryptoJS.enc.Base64.stringify(encrypted.ciphertext);},//解密decrypt(word,temp_keyStrs,temp_Iv){let key = temp_keyStrs;let iv = temp_Iv;key = CryptoJS.enc.Utf8.parse(key);iv = CryptoJS.enc.Utf8.parse(iv);let base64 = CryptoJS.enc.Base64.parse(word);let src = CryptoJS.enc.Base64.stringify(base64);// 解密模式为CBC,补码方式为PKCS5Padding(也就是PKCS7)let decrypt = CryptoJS.AES.decrypt(src, key, {iv: iv,mode: CryptoJS.mode.CBC,padding: CryptoJS.pad.Pkcs7});let decryptedStr = decrypt.toString(CryptoJS.enc.Utf8);return decryptedStr.toString();}}

然后跟RSA一样,在main.js引入一下

import AES from "./utils/AES.js";Vue.prototype.AES=AES

这样就可以在要使用的地方直接使用了

this.AES.encrypt("要加密的明文","aes密钥","aes向量")this.AES.decrypt("要解密的密文","aes密钥","aes向量")

登录demo

模拟写一个登录功能。我们登录要分几步来走:

1、获取临时Token;

2、根据临时Token去获取RSA公钥(之前提到过、网关需要存储客户端的私钥用于解密就必须要分清楚当前请求到底是哪个客户端的,然后才能使用相应的私钥去解密);

3、本地使用AES生成密钥跟向量;

4、使用RSA公钥对AES密钥跟向量加密——并将结果写入请求头;

5、使用AES密钥跟向量加密请求体内容;

6、发送请求;

vue封装axios请求api.js

import axios from 'axios'import {Message, MessageBox} from 'element-ui'import {getToken} from '@/utils/auth'import store from '../store'// 创建axios实例const service = axios.create({baseURL: process.env.BASE_URL, // api的base_urltimeout: 1999995000 // 请求超时时间2})// request拦截器service.interceptors.request.use(config => {if(localStorage.getItem('token')!=null && localStorage.getItem('token')!=""){config.headers["authorization"] =localStorage.getItem('token'); //把token添加到请求头每次请求接口时候带上}if(localStorage.getItem('AscKey')!=null && localStorage.getItem('AscKey')!=""){config.headers["Requestsecret"] =localStorage.getItem('AscKey'); //把token添加到请求头每次请求接口时候带上}return config}, error => {// Do something with request errorconsole.error(error) // for debugPromise.reject(error)})export default service

完整的登录示例

export default {name: 'login',data() {return {mapSrc: "",loginForm: {userAccount: 'admin',userPass: '123456',imgCode: "ESEXRC",smsCode: "123456"},tokenInfo: {tempKey: "", //临时tokentoken: "" //长期token},raskey: {publicKey: "",privateKey: ""},loginRules: {username: [{required: true, trigger: 'blur', message: "请输入用户名"}],password: [{required: true, trigger: 'blur', message: "请输入密码"}]},aesKey: {key: "",iv: ""},loading: false}},created() {this.aesKey.key = this.createCode(16);this.aesKey.iv = this.createCode(16); //AES 向量this.get_temp_token();},methods: {/*** 获取临时token*/get_temp_token() {console.log("获取临时token");this.api({url: "../临时token",method: "get"}).then(data => {this.tokenInfo.tempKey = data.tempToken;localStorage.setItem('token', 'Bearer ' + data.tempToken);//保存tokenthis.getrsaKey();})},/*** 获取公钥*/getrsaKey() {this.api({url: "../获取公钥",method: "get"}).then(data => {console.log("请求密钥对的结果是" + JSON.toString(data));this.raskey.publicKey = data.publicKey;this.createCode(12);localStorage.setItem('publicKey', data.publicKey);//保存tokenconsole.log("公钥是" + localStorage.getItem('publicKey'));})},/*** 登录*/login(publicKeys) {var ASCKeys = this.aesKey.key + "@" + this.aesKey.iv;console.log("temp_keyStrs=" + this.aesKey.key);console.log("temp_Iv=" + this.aesKey.iv);console.log("加密前的值" + JSON.stringify(this.loginForm));var encrypts = this.AES.encrypt(JSON.stringify(this.loginForm), this.aesKey.key, this.aesKey.iv);console.log("加密后的值=" + encrypts);var decrypts = this.AES.decrypt(encrypts, this.aesKey.key, this.aesKey.iv);console.log("解密后" + decrypts);var jmResult = this.RSAUtils.rsaPublicData(ASCKeys, publicKeys); // 对称加密的keyslocalStorage.setItem('AscKey', jmResult); // 保存tokenvar sendData = {"text": encrypts};this.api({url: "../登录",method: "post",data: sendData}).then(data => {console.log("登录请求得到的Token" + data.token);localStorage.setItem('token', 'Bearer ' + data.token); // 保存token ;this.$router.push({path: '/testmain'})})},/*** 获取图片验证码*/changeImgCode() {this.api({url: "../获取验证码",method: "get",responseType: Blob,}).then(data => {let blob = new Blob([data]); // 返回的文件流数据let url = window.URL.createObjectURL(blob); // 将他转化为路径console.log("图片路径:" + url + "r\n");})},toRegister() {this.$router.push({path: '/register'})},createCode(strLength) {var code = '23456789AaBbCcDdEeFfGgHhJjKkLlMmNnPpOoQqRrSsTtUuVvWwXxYyZz1Ii';var tempCode = "";var tempSize = 0;//设置长度,这里看需求,我这里设置了4var codeLength = strLength;//设置随机字符var random = new Array(0, 1, 2, 3, 4, 5, 6, 7, 8, 9);//循环codeLength 我设置的4就是循环4次for (var i = 0; i < codeLength; i++) {//设置随机数范围,这设置为0 ~ 36var tempSize = Math.floor(this.getRandomArbitrary(0, code.length - 1));tempCode += code.substr(tempSize, 1);}return tempCode;},getRandomArbitrary(min, max) { //生成随机数return Math.random() * (max - min) + min;},handleLogin() {this.$refs.loginForm.validate(valid => {if (valid) {this.loading = trueconsole.log("公钥是" + localStorage.getItem('publicKey'));this.login(localStorage.getItem('publicKey'));} else {return false}})}}}

本内容不代表本网观点和政治立场,如有侵犯你的权益请联系我们处理。
网友评论
网友评论仅供其表达个人看法,并不表明网站立场。