2016-12-16 3 views
2

Скажем, у меня есть созданный ранее закрытый ключ с помощью OpenSSL, но я решил не защищать его с помощью парольной фразы:Как добавить пароль к существующему закрытому ключу в Java

-----BEGIN RSA PRIVATE KEY----- 
BASE64 ENCODED DATA 
-----END RSA PRIVATE KEY----- 

Но потом я понял, что я хочу его защитить.

Я знаю, как защитить его с помощью openssl, но у меня есть требование сделать это на Java. Является ли это возможным ?

ответ

1

Первая загрузка и извлечение незашифрованый ключа PKCS # 1 из файла PEM

String pem = new String(Files.readAllBytes(Paths.get("rsa.key"))); 
String privateKeyPEM = pem.replace(
     "-----BEGIN RSA PRIVATE KEY-----\n", "") 
      .replace("-----END RSA PRIVATE KEY-----", ""); 
byte[] encodedPrivateKey = Base64.getDecoder().decode(privateKeyPEM); 

И затем шифрует ключ, используя вторую часть this code (я включил It)

// We must use a PasswordBasedEncryption algorithm in order to encrypt the private key, you may use any common algorithm supported by openssl, you can check them in the openssl documentation http://www.openssl.org/docs/apps/pkcs8.html 
String MYPBEALG = "PBEWithSHA1AndDESede"; 
String password = "pleaseChangeit!"; 

int count = 20;// hash iteration count 
SecureRandom random = new SecureRandom(); 
byte[] salt = new byte[8]; 
random.nextBytes(salt); 

// Create PBE parameter set 
PBEParameterSpec pbeParamSpec = new PBEParameterSpec(salt, count); 
PBEKeySpec pbeKeySpec = new PBEKeySpec(password.toCharArray()); 
SecretKeyFactory keyFac = SecretKeyFactory.getInstance(MYPBEALG); 
SecretKey pbeKey = keyFac.generateSecret(pbeKeySpec); 

Cipher pbeCipher = Cipher.getInstance(MYPBEALG); 

// Initialize PBE Cipher with key and parameters 
pbeCipher.init(Cipher.ENCRYPT_MODE, pbeKey, pbeParamSpec); 

// Encrypt the encoded Private Key with the PBE key 
byte[] ciphertext = pbeCipher.doFinal(encodedPrivateKey); 

// Now construct PKCS #8 EncryptedPrivateKeyInfo object 
AlgorithmParameters algparms = AlgorithmParameters.getInstance(MYPBEALG); 
algparms.init(pbeParamSpec); 
EncryptedPrivateKeyInfo encinfo = new EncryptedPrivateKeyInfo(algparms, ciphertext); 

// and here we have it! a DER encoded PKCS#8 encrypted key! 
byte[] encryptedPkcs8 = encinfo.getEncoded(); 

Использование следующий код для дешифрования (extrscted from here)

public static PrivateKey getPrivateKey(byte[] encryptedPkcs8, String passwd) throws Exception{ 

     EncryptedPrivateKeyInfo encryptPKInfo = new EncryptedPrivateKeyInfo(encryptedPkcs8); 

     Cipher cipher = Cipher.getInstance(encryptPKInfo.getAlgName()); 
     PBEKeySpec pbeKeySpec = new PBEKeySpec(passwd.toCharArray()); 
     SecretKeyFactory secFac = SecretKeyFactory.getInstance(encryptPKInfo.getAlgName()); 
     Key pbeKey = secFac.generateSecret(pbeKeySpec); 
     AlgorithmParameters algParams = encryptPKInfo.getAlgParameters(); 
     cipher.init(Cipher.DECRYPT_MODE, pbeKey, algParams); 
     KeySpec pkcs8KeySpec = encryptPKInfo.getKeySpec(cipher); 
     KeyFactory kf = KeyFactory.getInstance(ALGORITHM); 
     return kf.generatePrivate(pkcs8KeySpec); 
} 
+0

Спасибо, но делает заголовок ----- BEGIN RSA PRIVATE KEY ----- в формате pkcs8 или pkcs1? – TheByeByeMan

+0

как вы расшифруете свой личный ключ назад? –

+0

@GuenSeven, ответ ответил на ваш вопрос? – pedrofb

Смежные вопросы