这已被问过几次,但没有一个提供编码测试用例。在这里,我举一个问题的例子:
我没有得到的是,在保存和加载时,我使用 KeyStore.getInstance(“JKS”),但它失败了。欢迎任何建议!
运行时输出:
Creating private keystore at 'private.keystore'. Created keystore, now created signer cert Created signer cert, saving cert Reloading keystore: Failed to load the keystore after creation: Invalid keystore format
测试用例来源:
import java.io.File; import java.io.FileOutputStream; import java.io.IOException; import java.io.InputStream; import java.io.OutputStream; import java.security.InvalidKeyException; import java.security.KeyStore; import java.security.KeyStoreException; import java.security.NoSuchAlgorithmException; import java.security.NoSuchProviderException; import java.security.PrivateKey; import java.security.SignatureException; import java.security.cert.Certificate; import java.security.cert.CertificateException; import java.security.cert.X509Certificate; import sun.security.x509.X500Name; public class KeystoreCreator { private String fPrivateKeyStore; private String fPrivateKeyStorePassword; private String fPrivateKeyStoreKeyPassword; private String fPublicKeyCipherPassword; private String fPrivateKeyAlias; /** * @param args * @throws Exception */ public static void main(String[] args) throws Exception { KeystoreCreator creator = new KeystoreCreator(); creator.setPrivateKeyStore("private.keystore"); creator.setPrivateKeyStorePassword("beer123"); creator.setPrivateKeyAlias("myalias"); creator.setPrivateKeyStoreKeyPassword("beer123"); creator.setPublicKeyCipherPassword("beer123"); creator.initKeyStores(); } public KeystoreCreator() { } public void setPrivateKeyStore(String name) { fPrivateKeyStore=name; } public void setPrivateKeyStorePassword(String pass) { fPrivateKeyStorePassword=pass; } public void setPrivateKeyStoreKeyPassword(String pass) { fPrivateKeyStoreKeyPassword=pass; } public void setPublicKeyCipherPassword(String pass) { fPublicKeyCipherPassword=pass; } public void setPrivateKeyAlias(String alias) { fPrivateKeyAlias=alias; } public void initKeyStores() throws Exception { OutputStream out = null; File f=new File(fPrivateKeyStore); if (f.exists()) { f.delete(); if (f.exists()) { throw new IOException("Want to remove the keystore but can't, still reported as present after removal"); } } try { System.out.println("Creating private keystore at '" + fPrivateKeyStore + "'."); out = new FileOutputStream(fPrivateKeyStore); KeyStore privateKeyStore = KeyStore.getInstance("JKS"); privateKeyStore.load(null, fPrivateKeyStorePassword.toCharArray()); System.out.println("Created keystore, now created signer cert"); X500Name x500name=getCA(); Certificate cert = createCertificate(fPrivateKeyAlias, fPrivateKeyStoreKeyPassword, x500name, privateKeyStore); System.out.println("Created signer cert, saving cert"); privateKeyStore.store(out, fPublicKeyCipherPassword.toCharArray()); out.flush(); out.close(); //try to load it. KeyStore reloadedKeyStore = KeyStore.getInstance("JKS"); try { InputStream reloadedIs=getClass().getClassLoader().getResourceAsStream(fPrivateKeyStore); if (reloadedIs!=null) { System.out.println("Reloading keystore:"); reloadedKeyStore.load(reloadedIs, fPrivateKeyStorePassword.toCharArray()); } } catch (Exception e) { System.err.println("Failed to load the keystore after creation: "+e.getLocalizedMessage()); } } catch (Exception e) { System.err.println("Failed to save the keystore: "+e.getLocalizedMessage()); } } private X500Name getCA() throws IOException { return new sun.security.x509.X500Name("a","b", "c","d","e", "GB"); } public Certificate createCertificate( String alias, String keyPassword, sun.security.x509.X500Name x500Name, KeyStore keyStore ) throws NoSuchAlgorithmException, InvalidKeyException, CertificateException, SignatureException, NoSuchProviderException, KeyStoreException { sun.security.x509.CertAndKeyGen keypair = new sun.security.x509.CertAndKeyGen( "RSA", "MD5WithRSA" ); keypair.generate( 1024 ); PrivateKey privKey = keypair.getPrivateKey(); X509Certificate[] chain = new X509Certificate[1]; chain[0] = keypair.getSelfCertificate( x500Name, 7000 * 24 * 60 * 60 ); keyStore.setKeyEntry( alias, privKey, keyPassword.toCharArray(), chain ); Certificate cert = keyStore.getCertificate( alias ); return cert; } }
答案 0 :(得分:2)
1)您可以通过写入文件在当前工作目录中创建私钥存储:new FileOutputStream(fPrivateKeyStore);
2)稍后,您使用getClass().getClassLoader().getResourceAsStream(fPrivateKeyStore);
我认为你正在阅读错误的文件。而且之前的测试中已经有另一个名为private.keystore
的人。要进行验证,您可能需要打印出两个文件的绝对文件路径,例如: new File(fPrivateKeyStore).getAbsolutePath()
并将其与getClass().getClassLoader().getResource(fPrivateKeyStore).toFileURL();
答案 1 :(得分:0)
我可能遗漏了一些内容,但为什么不使用FileInputStream
重新加载私钥存储?
InputStream reloadedIs = new FileInputStream(fPrivateKeyStore);
(我不确定这可以解决问题,我只是在扫描你的代码时注意到它)