对称加密算法-AES实现
依赖POM
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
</dependency>
实现代码:
import com.bruce.tool.common.arithmetic.constant.AesType;
import com.bruce.tool.common.exception.ExceptionUtils;
import com.bruce.tool.common.util.LogUtils;
import lombok.AccessLevel;
import lombok.NoArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import javax.crypto.Cipher;
import javax.crypto.spec.GCMParameterSpec;
import javax.crypto.spec.IvParameterSpec;
import javax.crypto.spec.SecretKeySpec;
@Slf4j
@NoArgsConstructor(access = AccessLevel.PRIVATE)
public class AES {
private static final String KEY_ALGORITHM = "AES";
private static final String CIPHER_ALGORITHM_CBC = "AES/CBC/PKCS5Padding";//算法/模式/补码方式
private static final String CIPHER_ALGORITHM_ECB = "AES/ECB/PKCS5Padding";//算法/模式/补码方式
private static final String CIPHER_ALGORITHM_GCM = "AES/GCM/PKCS5Padding";//算法/模式/补码方式
// CBC
public static String encrypt(AesType type,String content, String secretKey){
if(AesType.CBC.equals(type)){
return executeCBC(content,secretKey,true);
}else if(AesType.ECB.equals(type)){
return executeECB(content,secretKey,true);
}else if(AesType.GCM.equals(type)){
return executeGCM(content,secretKey,true);
}else{
return null;
}
}
// CBC
public static String decrypt(AesType type,String content,String secretKey){
if(AesType.CBC.equals(type)){
return executeCBC(content,secretKey,false);
}else if(AesType.ECB.equals(type)){
return executeECB(content,secretKey,false);
}else if(AesType.GCM.equals(type)){
return executeGCM(content,secretKey,false);
}else{
return null;
}
}
private static String executeCBC(String content, String salt, boolean encode) {
try {
String md5 = MD5.encode(salt);
String key = md5.substring(0, 16);
String ivKey = md5.substring(16);
SecretKeySpec skeySpec = new SecretKeySpec(key.getBytes(), KEY_ALGORITHM);
IvParameterSpec ivSpec = new IvParameterSpec(ivKey.getBytes());
Cipher cipher = Cipher.getInstance(CIPHER_ALGORITHM_CBC);
if( encode ){
cipher.init(Cipher.ENCRYPT_MODE, skeySpec, ivSpec);
byte[] encrypted = cipher.doFinal(content.getBytes());
return Base64.encode(encrypted);
}
cipher.init(Cipher.DECRYPT_MODE, skeySpec, ivSpec);
byte[] original = cipher.doFinal(Base64.decode(content));
return new String(original);
} catch (Exception e) {
LogUtils.error(log,e);
}
return null;
}
private static String executeECB(String content,String secretKey,boolean encode) {
try {
String md5 = MD5.encode(secretKey);
String key = md5.substring(0, 16);
SecretKeySpec secretKey1 = new SecretKeySpec(key.getBytes(), KEY_ALGORITHM);
Cipher cipher = Cipher.getInstance(CIPHER_ALGORITHM_ECB);
if( encode ){
cipher.init(Cipher.ENCRYPT_MODE, secretKey1);
return Base64.encode(cipher.doFinal(content.getBytes()));
}
cipher.init(Cipher.DECRYPT_MODE, secretKey1);
return new String(cipher.doFinal(Base64.decode(content)));
} catch (Exception e) {
ExceptionUtils.printStackTrace(e);
}
return null;
}
private static String executeGCM(String content, String secretKey, boolean encode) {
try {
String md5 = MD5.encode(secretKey);
String key = md5.substring(0, 16);
SecretKeySpec secretKeySpec = new SecretKeySpec(key.getBytes(),"AES");
Cipher cipher= Cipher.getInstance(CIPHER_ALGORITHM_GCM);
cipher.init(Cipher.ENCRYPT_MODE, secretKeySpec);
if( encode ){
byte[] iv = cipher.getIV();
assert iv.length == 12;
byte[] encryptData = cipher.doFinal(content.getBytes());
assert encryptData.length == content.getBytes().length + 16;
byte[] message = new byte[12 + content.getBytes().length + 16];
System.arraycopy(iv, 0, message, 0, 12);
System.arraycopy(encryptData, 0, message, 12, encryptData.length);
return Base64.encode(message);
}
byte[] message = Base64.decode(content);
GCMParameterSpec params = new GCMParameterSpec(128, message, 0, 12);
cipher.init(Cipher.DECRYPT_MODE, secretKeySpec, params);
byte[] decryptData = cipher.doFinal(message, 12, message.length - 12);
return new String(decryptData);
} catch (Exception e) {
ExceptionUtils.printStackTrace(e);
}
return null;
}
}
测试类:
import com.bruce.tool.common.arithmetic.constant.AesType;
import org.junit.Test;
/**
* 功能 :
*
* @author : Bruce(刘正航) 14:52 2019-02-19
*/
public class AESTest {
@Test
public void aes(){
System.out.println(AES.encrypt(AesType.CBC,"123456","123456789"));
System.out.println(AES.decrypt(AesType.CBC,AES.encrypt(AesType.CBC,"123456","123456789"),"123456789"));
System.out.println(AES.encrypt(AesType.ECB,"123456","123456789"));
System.out.println(AES.decrypt(AesType.ECB,AES.encrypt(AesType.ECB,"123456","123456789"),"123456789"));
System.out.println(AES.encrypt(AesType.GCM,"123456","123456789"));
System.out.println(AES.decrypt(AesType.GCM,AES.encrypt(AesType.GCM,"123456","123456789"),"123456789"));
}
}