我在Java中实现了以下AES算法,但问题出现的原因是加密是在设计时执行的,而解密是在运行时执行的,因此解密在运行时失败。
在解密期间,IvParameterSpec和SecretKey为空,因为它们在完全不同的时间被调用。如何在这种情况下实施?
static IvParameterSpec ivspec =null;
static SecretKey secKey=null;
public static SecretKey getSecretEncryptionKey(){
KeyGenerator generator=null;
try {
generator = KeyGenerator.getInstance("AES");
} catch (NoSuchAlgorithmException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
generator.init(128); // The AES key size in number of bits
secKey = generator.generateKey();
return secKey;
}
public static String encrypt(String text) throws GeneralSecurityException {
if (text == null || text.isEmpty()) {
return "";
}
secKey = getSecretEncryptionKey();
byte[] iv = new byte[128/8];
Random randomNumber = new Random();
randomNumber.nextBytes(iv);
ivspec = new IvParameterSpec(iv);
Cipher ci = Cipher.getInstance("AES/CBC/PKCS5Padding");
ci.init(Cipher.ENCRYPT_MODE, secKey, ivspec);
byte[] byteCipherText = ci.doFinal(text.getBytes());
return String.format("{%s}", base64Encode(byteCipherText));
}
public static String decrypt(String text) {
if (text == null || text.isEmpty()) {
return "";
}
if (!text.startsWith("{") || !text.endsWith("}")) {
return text;
}
Cipher ci;
byte[] bytePlainText =null;
try {
ci = Cipher.getInstance("AES/CBC/PKCS5Padding");
ci.init(Cipher.DECRYPT_MODE, secKey,ivspec);
byte[] decryptText=base64Decode(text);
bytePlainText = ci.doFinal(decryptText);
} catch (Exception ex) {
// TODO Auto-generated catch block
ex.printStackTrace();
}
return new String(bytePlainText,StandardCharsets.UTF_8);
}
答案 0 :(得分:0)
我已经实现了如下算法:
获取密钥:
private static SecretKey getKey() {
System.out.println("Key Length " + KEY_LENGTH);
try {
return new SecretKeySpec(SecretKeyFactory.getInstance("PBKDF2WithHmacSHA1")
.generateSecret(new PBEKeySpec(CIPHER_KEY.toCharArray(), CIPHER_KEY.getBytes(), 10000, KEY_LENGTH))
.getEncoded(), "AES");
} catch ( Exception e) {
}
return null;
}
加密方法:
public static String encrypt(String text) throws GeneralSecurityException {
if (text == null || text.isEmpty()) {
return "";
}
Cipher ci = Cipher.getInstance("AES/CBC/PKCS5Padding");
ci.init(Cipher.ENCRYPT_MODE, getKey(), getIvParameterSpec());
return String.format("{%s}", base64Encode(ci.doFinal(text.getBytes())));
}
解密方法:
public static String decrypt(String text) {
if (text == null || text.isEmpty()) {
return "";
}
if (!text.startsWith("{") || !text.endsWith("}")) {
return text;
}
Cipher ci;
byte[] bytePlainText = null;
try {
ci = Cipher.getInstance("AES/CBC/PKCS5Padding");
ci.init(Cipher.DECRYPT_MODE, getKey(), getIvParameterSpec());
bytePlainText = ci.doFinal(base64Decode(text));
} catch (Exception e) {
// TODO Auto-generated catch block
System.out.println(e.toString());
}
return new String(bytePlainText, StandardCharsets.UTF_8);
}