闽公网安备 35020302035485号
// 编码
const base64Str = window.btoa('Hello World!');
console.log(base64Str); // SGVsbG8gV29ybGQh
// 解码
const str = window.atob(base64Str);
console.log(str); // Hello World!
当然,我们也可以使用base64插件。pnpm install --save js-base64
<script setup lang="ts">
import { Base64 } from 'js-base64';
// 堆代码 duidaima.com
// 编码
const encode = Base64.encode('Hello World!');
console.log(encode);
// 解码
const decode = Base64.decode(encode);
console.log(decode);
</script>
二.哈希算法import CryptoJS from "crypto-js";
// MD5
const hash = CryptoJS.MD5('Message');
// SHA-1
const hash = CryptoJS.SHA1('Message');
// SHA-256
const hash = CryptoJS.SHA256('Message');
// SHA-512
const hash = CryptoJS.SHA512('Message');
三.对称加密(AES/DES)ECB是一种基础的加密方式,密文被分割成分组长度相等的块(不足补齐),然后单独一个个加密,一个个输出组成密文。CBC是一种循环模式,前一个分组的密文和当前分组的明文异或或操作后再加密,这样做的目的是增强破解难度。
参数Mode为DES/AES的工作方式。参数padding为填充模式,如果加密后密文长度如果达不到指定整数倍(8个字节、16个字节),填充对应字符,padding的赋值固定为CryptoJS.pad.Pkcs7即可。
import CryptoJS from "crypto-js";
//秘钥
const secretKey = CryptoJS.enc.Utf8.parse("12345678ABCDEFGH"); //16位
// iv偏移量
const iv = CryptoJS.enc.Utf8.parse("ABCDEFGH12345678");
// 需要加密的参数,数据类型为bytes
const secretMessage = "Hello World!";
// 加密
const encrypt = CryptoJS.AES.encrypt(secretMessage, secretKey, {
iv: iv,
mode: CryptoJS.mode.CBC,
padding: CryptoJS.pad.Pkcs7
}).tostring();
console.log(encrypt);
//解密
const decrypt = CryptoJS.AES.decrypt(encrypt, secretKey, {
iv: iv,
mode: CryptoJS.mode.CBC,
padding: CryptoJS.pad.Pkcs7
}).toString(CryptoJS.enc.Utf8);
console.log(decrypt);

npm install jsencrypt
import JSEncrypt from 'jsencrypt'
// RSA加密
// 创建加密对象实例
const encryptor = new JSEncrypt();
//之前ssl生成的公钥,复制的时候要小心不要有空格
const pubKey = '-----BEGIN PUBLIC KEY-----MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQC1QQRl0HlrVv6kGqhgonD6A9SU6ZJpnEN+Q0blT/ue6Ndt97WRfxtSAs0QoquTreaDtfC4RRX4o+CU6BTuHLUm+eSvxZS9TzbwoYZq7ObbQAZAY+SYDgAA5PHf1wNN20dGMFFgVS/y0ZWvv1UNa2laEz0I8Vmr5ZlzIn88GkmSiQIDAQAB-----END PUBLIC KEY-----';
//设置公钥
encryptor.setPublicKey(pubKey);
// 对内容进行加密
const encrypted = encryptor.encrypt('要加密的内容')
// RSA解密
//创建解密对象实例
const decrypt = new JSEncrypt();
//之前ssl生成的秘钥
const priKey = '-----BEGIN RSA PRIVATE KEY-----MIICXAIBAAKBgQC1QQRl0HlrVv6kGqhgonD6A9SU6ZJpnEN+Q0blT/ue6Ndt97WRfxtSAs0QoquTreaDtfC4RRX4o+CU6BTuHLUm+eSvxZS9TzbwoYZq7ObbQAZAY+SYDgAA5PHf1wNN20dGMFFgVS/y0ZWvv1UNa2laEz0I8Vmr5ZlzIn88GkmSiQIDAQABAoGBAKYDKP4AFlXkVlMEP5hS8FtuSrUhwgKNJ5xsDnFV8sc3yKlmKp1a6DETc7N66t/Wdb3JVPPSAy+7GaYJc7IsBRZgVqhrjiYiTO3ZvJv3nwAT5snCoZrDqlFzNhR8zvUiyAfGD1pExBKLZKNH826dpfoKD2fYlBVOjz6i6dTKBvCJAkEA/GtL6q1JgGhGLOUenFveqOHJKUydBAk/3jLZksQqIaVxoB+jRQNOZjeSO9er0fxgI2kh0NnfXEvH+v326WxjBwJBALfTRar040v71GJq1m8eFxADIiPDNh5JD2yb71FtYzH9J5/d8SUHI/CUFoROOhxr3DpagmrnTn28H0088vubKe8CQDKMOhOwx/tS5lqvN0YQj7I6JNKEaR0ZzRRuEmv1pIpAW1S5gTScyOJnVn1tXxcZ9xagQwlT2ArfkhiNKxjrf5kCQAwBSDN5+r4jnCMxRv/Kv0bUbY5YWVhw/QjixiZTNn81QTk3jWAVr0su4KmTUkg44xEMiCfjI0Ui3Ah3SocUAxECQAmHCjy8WPjhJN8y0MXSX05OyPTtysrdFzm1pwZNm/tWnhW7GvYQpvE/iAcNrNNb5k17fCImJLH5gbdvJJmCWRk=-----END RSA PRIVATE KEY----';
//设置秘钥
decrypt.setPrivateKey(priKey);
//解密之前拿公钥加密的内容
const uncrypted = decrypt.decrypt(encrypted)
RSA加解密可以应用在用户注册或登录的时候,用公钥对密码进行加密,再去传给后台,后台用私钥对加密的内容进行解密,然后进行密码校验或者保存到数据库。pnpm install js-sha256
import { sha256 } from 'js-sha256'
import { sha256 } from 'js-sha256';
const generateSalt = () => {
const randomBytes = new Uint8Array(16);
crypto.getRandomValues(randomBytes);
return Array.from(randomBytes, (byte) =>
byte.toString(16).padStart(2, '0')
).join('');
};
// 盐值
const salt = generateSalt();
// 假如一个密码
const password = 'admin123456';
// 盐值和密码进行组合
const saltedPassword = salt + password;
// 哈希计算
const hash = sha256(saltedPassword);
console.log(hash);
六.Web Cryptography API // fix safari crypto namespace
if (window.crypto && !window.crypto.subtle && window.crypto.webkitSubtle) {
window.crypto.subtle = window.crypto.webkitSubtle;
}
/**
* Detect Web Cryptography API
* @return {Boolean} true, if success
*/
function isWebCryptoAPISupported() {
return 'crypto' in window && 'subtle' in window.crypto;
}
getRandomValues 同步方法,获取随机数,因为性能要求,这是一个伪随机数生成器(PRNG)。浏览器也通过添加系统级别的种子来提高熵(不确定性的量度),来满足密码学使用要求。const size = 10;
const array = new Uint8Array(size);
window.crypto.getRandomValues(array);
// print values to console
for (let i=0; i!==array.length; ++i) {
console.log(array[i]);
}
SubtleCrypto接口:// 生成公钥和私钥
const keyPair = await window.crypto.subtle.generateKey(
{
name: "RSA-OAEP", // 使用RSA-OAEP算法
modulusLength: 2048, // 密钥长度为2048位
publicExponent: new Uint8Array([1, 0, 1]), // 公共指数为65537
hash: "SHA-256" // 哈希算法为SHA-256
},
true, // 生成可导出的密钥对
["encrypt", "decrypt"] // 可用于加密和解密操作
);
keyPair.then(function(result) {
// 处理生成的密钥对
console.log(result.publicKey); // 打印公钥
console.log(result.privateKey); // 打印私钥
}).catch(function(error) {
// 处理错误
console.error(error);
});
// 加密
async function encryptByRSA(message, publicKey) {
// 将消息编码为Uint8Array格式
const encodedMessage = new TextEncoder().encode(message);
// 使用Web Crypto API的encrypt()方法对消息进行加密
const encrypted = await window.crypto.subtle.encrypt(
{
name: "RSA-OAEP" // 加密算法为RSA-OAEP
},
publicKey, // 使用传入的公钥进行加密
encodedMessage // 要加密的消息
);
// 将加密后的数据转换为Base64编码的字符串
return window.btoa(String.fromCharCode(...new Uint8Array(encrypted)));
}
// 解密 使用RSA私钥对密文进行解密
async function decryptByRSA(ciphertext, privateKey) {
// 将Base64编码的密文解码为Uint8Array格式
const decodedCiphertext = Uint8Array.from(
atob(ciphertext),
c => c.charCodeAt(0)
);
// 使用Web Crypto API的decrypt()方法对密文进行解密
const decrypted = await window.crypto.subtle.decrypt(
{
name: "RSA-OAEP" // 解密算法为RSA-OAEP
},
privateKey, // 使用传入的私钥进行解密
decodedCiphertext // 要解密的密文
);
// 将解密后的数据转换为字符串
return new TextDecoder().decode(decrypted);
}
