使用Java从.p12文件获取PrivateKey对象

正如标题所示,我有谷歌服务帐户api访问所需的.p12文件。 为了获得连接到api的凭证,有一个字段.setServiceAccountPrivateKey(PrivateKey privateKey)。 那么,我能做到这一点最简单的方法是什么? 我有一个资源文件夹,它在我的类路径中,所以如果我在那里添加p12文件,我可以从getClass()获取资源.getResource()作为inputStream或URL。 我已经尝试过URL方法,但它不起作用(我尝试从URL.toURI()创建一个File对象时出现“URI is hierarchical hierarchical”错误)。

您可以使用ClassLoader.getResourceAsStream(String)方法ClassLoader.getResourceAsStream(String) .p12文件,将其ClassLoader.getResourceAsStream(String)到KeyStore,然后从KeyStore获取密钥。

 KeyStore keystore = KeyStore.getInstance("PKCS12"); keystore.load(this.getClass().getClassLoader().getResourceAsStream("keyFile.p12"), p12Password.toCharArray()); PrivateKey key = (PrivateKey)keystore.getKey(keyAlias, p12Password.toCharArray()); 

ClassLoader.getResourceAsStream(String)从任何位置加载资源,只要它们已经在类路径中,就不需要指定文件的路径。

keyAlias是p12文件中与私钥对应的条目的名称。 PKCS12文件可以包含多个条目,因此您需要某种方式来指示要访问的条目。 别名是如何实现的。

如果您不确定私钥的别名是什么,可以使用命令行中的keytool实用程序列出p12文件的内容。 所有JRE和JDK安装都包含此工具。

 keytool -list -keystore keyFile.p12 -storepass password -storetype PKCS12 

产量

 Keystore type: PKCS12 Keystore provider: SunJSSE Your keystore contains 1 entry yourKeyAlias, Sep 4, 2013, PrivateKeyEntry, Certificate fingerprint (MD5): 48:A8:C4:12:8E:4A:8A:AD:58:81:26:90:E7:3D:C8:04 

我认为直接调用Google的SecurityUtils更容易,例如:

 PrivateKey privateKey = SecurityUtils.loadPrivateKeyFromKeyStore(SecurityUtils.getPkcs12KeyStore(), this.getClass().getResourceAsStream("keyFile.p12"), "notasecret", "privatekey", "notasecret") 

它是单行的,您不必担心别名。

如果你从getKey()得到null (例如,你使用BouncyCastle作为提供者),你应该找到最后一个keyAlias元素:

 KeyStore keystore = KeyStore.getInstance("PKCS12", "BC"); keystore.load(this.getClass().getClassLoader().getResourceAsStream("keyFile.p12"), p12Password.toCharArray()); Enumeration aliases = keystore.aliases(); String keyAlias = ""; while (aliases.hasMoreElements()) { keyAlias = (String) aliases.nextElement(); } PrivateKey key = (PrivateKey)keystore.getKey(keyAlias, pass); 

以上建议对我不起作用。 然后我尝试了http://www.java2s.com/Code/Java/Security/RetrievingaKeyPairfromaKeyStore.htm上的那个,它起作用了。 复制粘贴在下面

 import java.io.FileInputStream; import java.security.Key; import java.security.KeyPair; import java.security.KeyStore; import java.security.PrivateKey; import java.security.PublicKey; import java.security.cert.Certificate; public class Main { public static void main(String[] argv) throws Exception { FileInputStream is = new FileInputStream("your.keystore"); KeyStore keystore = KeyStore.getInstance(KeyStore.getDefaultType()); keystore.load(is, "my-keystore-password".toCharArray()); String alias = "myalias"; Key key = keystore.getKey(alias, "password".toCharArray()); if (key instanceof PrivateKey) { // Get certificate of public key Certificate cert = keystore.getCertificate(alias); // Get public key PublicKey publicKey = cert.getPublicKey(); // Return a key pair new KeyPair(publicKey, (PrivateKey) key); } } }