对称加密AES
注意:初始向量AES为16bytes字符串,秘钥AES固定格式为16/24/32bytes字符串。
对称加密
/**
* @param 需要加密的字符串
* initialVector 初始向量
* secretKey 秘钥
*/
public static String symmetricEncrypt(String encryptText){
try {
IvParameterSpec parameterSpec = new IvParameterSpec(initialVector.getBytes());
//第一个参数为:秘钥字节数组 ,第二个参数为加密方式AES
SecretKeySpec key = new SecretKeySpec(secretKey.getBytes(),"AES");
Cipher cipher = Cipher.getInstance("AES/CBC/PKCS5Padding");
cipher.init(Cipher.ENCRYPT_MODE, key, parameterSpec);
//加密后的数据
byte[] encryptedData = cipher.doFinal(encryptText.getBytes(StandardCharsets.UTF_8));
return new BASE64Encoder().encode(encryptedData);
} catch (Exception e) {
e.printStackTrace();
}
return null;
}
对称解密
/**
* @param 加密后的的字符串
* initialVector 初始向量
* secretKey 秘钥
*/
public static String symmetricDecrypt(String var0){
try {
byte[] encryptByte = new BASE64Decoder().decodeBuffer(var0);
IvParameterSpec parameterSpec = new IvParameterSpec(initialVector.getBytes());
SecretKeySpec key = new SecretKeySpec(secretKey.getBytes(),"AES");
Cipher cipher = Cipher.getInstance("AES/CBC/PKCS5Padding");
cipher.init(Cipher.DECRYPT_MODE, key,parameterSpec);
byte[] decryptedData = cipher.doFinal(encryptByte);
return new String(decryptedData, StandardCharsets.UTF_8);
} catch (Exception e) {
e.printStackTrace();
}
return null;
}
非对称加密
后端加密生成私钥和公钥,公钥提供给前端用js将字符串加密后的密文给后端进行解密,然后再配对。
生成秘钥
/**
* 生成非对称秘钥对
* @return
*/
public static void asymmetricSecret() {
X9ECParameters sm2ECParameters = GMNamedCurves.getByName("sm2p256v1");
ECDomainParameters domainParameters = new ECDomainParameters(sm2ECParameters.getCurve(), sm2ECParameters.getG(), sm2ECParameters.getN());
ECKeyPairGenerator keyPairGenerator = new ECKeyPairGenerator();
try {
keyPairGenerator.init(new ECKeyGenerationParameters(domainParameters, SecureRandom.getInstance("SHA1PRNG")));
} catch (NoSuchAlgorithmException e) {
e.printStackTrace();
}
AsymmetricCipherKeyPair asymmetricCipherKeyPair = keyPairGenerator.generateKeyPair();
//私钥
BigInteger privateKey = ((ECPrivateKeyParameters) asymmetricCipherKeyPair.getPrivate()).getD();
String privateKeyHex = privateKey.toString(16);
//公钥
ECPoint ecPoint = ((ECPublicKeyParameters) asymmetricCipherKeyPair.getPublic()).getQ();
String publicKeyHex = Hex.toHexString(ecPoint.getEncoded(false));
System.out.println("秘钥:" + privateKeyHex);
System.out.println("公钥:" + publicKeyHex);
}
JS生成密文
//publicKey 公钥,由后端生成给前端写死
var ciphertext = sm2Encrypt(userId, publicKey, 0);
//生成密文给后端
console.log(ciphertext);
非对称解密
/**
* 非对称解密
* @param var0 前端密文
* @return
*/
public static String asymmetricDecrypt(String var0) {
try {
byte[] cipherDataByte = Hex.decode(var0);
String privateKey = "刚生成的私钥";
BigInteger privateKeyD = new BigInteger(privateKey, 16);
X9ECParameters sm2ECParameters = GMNamedCurves.getByName("sm2p256v1");
ECDomainParameters domainParameters = new ECDomainParameters(sm2ECParameters.getCurve(), sm2ECParameters.getG(), sm2ECParameters.getN());
ECPrivateKeyParameters privateKeyParameters = new ECPrivateKeyParameters(privateKeyD, domainParameters);
//用私钥解密
SM2Engine sm2Engine = new SM2Engine();
sm2Engine.init(false, privateKeyParameters);
//processBlock得到Base64格式
byte[] arrayOfBytes = Base64.getDecoder().decode(sm2Engine.processBlock(cipherDataByte, 0, cipherDataByte.length));
//得到明文
return new String(arrayOfBytes);
}catch (Exception e) {
e.getStackTrace();
}
return null;
}
pom
<dependency>
<groupId>org.bouncycastle</groupId>
<artifactId>bcprov-jdk15on</artifactId>
<version>1.65</version>
</dependency>
JS文件
链接: 百度网盘
提取码:c6ed
注:如果是JDK1.7将util.Base64源码复制一份。