112 lines
4.4 KiB
Java
112 lines
4.4 KiB
Java
package eu.dnetlib.uoaorcidservice.handlers.utils;
|
|
|
|
import org.apache.logging.log4j.LogManager;
|
|
import org.apache.logging.log4j.Logger;
|
|
import org.springframework.boot.context.properties.ConfigurationProperties;
|
|
|
|
import javax.crypto.Cipher;
|
|
import javax.crypto.IllegalBlockSizeException;
|
|
import javax.crypto.NoSuchPaddingException;
|
|
import javax.crypto.SecretKey;
|
|
import javax.crypto.BadPaddingException;
|
|
import javax.crypto.KeyGenerator;
|
|
import javax.crypto.SecretKeyFactory;
|
|
import javax.crypto.spec.IvParameterSpec;
|
|
import javax.crypto.spec.PBEKeySpec;
|
|
import javax.crypto.spec.SecretKeySpec;
|
|
import java.io.*;
|
|
import java.security.InvalidAlgorithmParameterException;
|
|
import java.security.InvalidKeyException;
|
|
import java.security.NoSuchAlgorithmException;
|
|
import java.security.SecureRandom;
|
|
import java.security.spec.InvalidKeySpecException;
|
|
import java.security.spec.KeySpec;
|
|
import java.util.Arrays;
|
|
import java.util.Base64;
|
|
|
|
@ConfigurationProperties("orcidservice.encryption")
|
|
public class AESUtils {
|
|
private static final Logger log = LogManager.getLogger(AESUtils.class);
|
|
|
|
private static String password;
|
|
public String getPassword() {
|
|
return password;
|
|
}
|
|
|
|
public void setPassword(String password) {
|
|
this.password = password;
|
|
}
|
|
|
|
public static SecretKey generateKey(int n) throws NoSuchAlgorithmException {
|
|
KeyGenerator keyGenerator = KeyGenerator.getInstance("AES");
|
|
keyGenerator.init(n);
|
|
SecretKey key = keyGenerator.generateKey();
|
|
return key;
|
|
}
|
|
|
|
public static SecretKey getKeyFromPassword(String password, String salt)
|
|
throws NoSuchAlgorithmException, InvalidKeySpecException {
|
|
SecretKeyFactory factory = SecretKeyFactory.getInstance("PBKDF2WithHmacSHA256");
|
|
KeySpec spec = new PBEKeySpec(password.toCharArray(), salt.getBytes(), 65536, 256);
|
|
SecretKey secret = new SecretKeySpec(factory.generateSecret(spec)
|
|
.getEncoded(), "AES");
|
|
return secret;
|
|
}
|
|
|
|
public static IvParameterSpec generateIv() {
|
|
byte[] iv = new byte[16];
|
|
new SecureRandom().nextBytes(iv);
|
|
return new IvParameterSpec(iv);
|
|
}
|
|
|
|
public static String encryptPasswordBased(String plainText, String salt)
|
|
throws NoSuchPaddingException, NoSuchAlgorithmException, InvalidAlgorithmParameterException,
|
|
InvalidKeyException, BadPaddingException, IllegalBlockSizeException, IOException, InvalidKeySpecException {
|
|
IvParameterSpec iv = generateIv();
|
|
SecretKey key = AESUtils.getKeyFromPassword(password,salt);
|
|
|
|
Cipher cipher = Cipher.getInstance("AES/CBC/PKCS5Padding");
|
|
cipher.init(Cipher.ENCRYPT_MODE, key, iv);
|
|
|
|
log.debug("password: "+password);
|
|
log.debug("salt: "+salt);
|
|
log.debug("encrypt: "+plainText);
|
|
log.debug("key: "+key);
|
|
log.debug("encrypted: |"+Base64.getEncoder().encodeToString(cipher.doFinal(plainText.getBytes()))+"|");
|
|
|
|
// concatenate salt + iv + ciphertext
|
|
ByteArrayOutputStream outputStream = new ByteArrayOutputStream();
|
|
outputStream.write(iv.getIV());
|
|
outputStream.write(cipher.doFinal(plainText.getBytes()));
|
|
|
|
// properly encode the complete ciphertext
|
|
// return DatatypeConverter.printBase64Binary(outputStream.toByteArray());
|
|
|
|
return Base64.getEncoder().encodeToString(outputStream.toByteArray());
|
|
}
|
|
|
|
public static String decryptPasswordBased(String cipherTextStr, String salt/*, IvParameterSpec iv*/)
|
|
throws NoSuchPaddingException, NoSuchAlgorithmException, InvalidAlgorithmParameterException,
|
|
InvalidKeyException, BadPaddingException, IllegalBlockSizeException, InvalidKeySpecException {
|
|
SecretKey key = getKeyFromPassword(password,salt);
|
|
|
|
byte[] ciphertext = Base64.getDecoder().decode(cipherTextStr);
|
|
// if (ciphertext.length < 48) {
|
|
// return null;
|
|
// }
|
|
// byte[] salt = Arrays.copyOfRange(ciphertext, 0, 16);
|
|
byte[] iv = Arrays.copyOfRange(ciphertext, 0, 16);
|
|
byte[] ct = Arrays.copyOfRange(ciphertext, 16, ciphertext.length);
|
|
|
|
Cipher cipher = Cipher.getInstance("AES/CBC/PKCS5PADDING");
|
|
cipher.init(Cipher.DECRYPT_MODE, key, new IvParameterSpec(iv));
|
|
|
|
log.debug("decrypt: |"+ct+"|");
|
|
log.debug("key: "+key);
|
|
log.debug("decrypted: "+new String(cipher.doFinal(ct)));
|
|
|
|
return new String(cipher.doFinal(ct));
|
|
}
|
|
|
|
}
|