2014-11-03 99 views
9

嗨公钥我想用Java代码从文件中读取密钥仓库

来提取密钥库公钥我创建一个密钥库

keytool -genkey -alias mykeystore -keyalg RSA -keystore mykeystore.jks -keysize 2048 

和出口公众到另一个文件

keytool -export -alias mykeystore -keystore mykeystore.jks -rfc -file publickey.cert 

如何使用Java代码从keystore或publickey.cert文件获取公钥字符串?

谢谢。

UPDATE

public static void main(String[] args) { 

    try { 

     FileInputStream is = new FileInputStream("/home/myuser/my-keystore/mykeystore.jks"); 
     KeyStore keystore = KeyStore.getInstance(KeyStore.getDefaultType()); 
     String password = "myuserpass"; 
     char[] passwd = password.toCharArray(); 
     keystore.load(is, passwd); 
     String alias = "mykeystore"; 
     Key key = keystore.getKey(alias, passwd); 
     if (key instanceof PrivateKey) { 
      // Get certificate of public key 
      Certificate cert = keystore.getCertificate(alias); 
      // Get public key 
      PublicKey publicKey = cert.getPublicKey(); 

      String publicKeyString = Base64.encodeBase64String(publicKey 
        .getEncoded()); 
      System.out.println(publicKeyString); 

     } 

    } catch (Exception e) { 
     e.printStackTrace(); 
    } 
} 

然后它给像

MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAiG2FjSuXrraYuh0TyRNiUvVCyaFlb7VY9AFIMSDdcY0JgNF0c4YVQxYxUCbYzmkLZD/rrYMe/8nxkWV0TMz2Y7GnvichjtWHL1ui58uC0+RtFMkYJ+ftwt9qBy9hvb/rVFTsvT5/b6CQXD8a6bFveMUluQZISLCV7i11XYzp81+w6M7+2fJAwezIJnIrgwv1K9YDjWaToaNXe7hnzzy0s8AdkjTk197+hg8dRfbvkr8XAddNsEMPeUA5iY+5VEpRNI925ZT/dxnaABA0z6i4JbVjeLl8r7ySG9R/2w/j2G+/YSRQc9BmRHPa0tBgH7wvQM+WRwD9WmST+5qeBIfH3QIDAQAB 

当我做cat publickey.cert,它显示了这个

-----BEGIN CERTIFICATE----- 
MIIDgTCCAmmgAwIBAgIEf7XoMDANBgkqhkiG9w0BAQsFADBxMQswCQYDVQQGEwJJTjESMBAGA1UE 
CBMJS2FybmF0YWthMRIwEAYDVQQHEwlCYW5nYWxvcmUxEjAQBgNVBAoTCU5ldHNjaXR1czESMBAG 
A1UECxMJTmV0c2NpdHVzMRIwEAYDVQQDEwlOZXRzY2l0dXMwHhcNMTQxMTAzMDkyNTM3WhcNMTUw 
MjAxMDkyNTM3WjBxMQswCQYDVQQGEwJJTjESMBAGA1UECBMJS2FybmF0YWthMRIwEAYDVQQHEwlC 
YW5nYWxvcmUxEjAQBgNVBAoTCU5ldHNjaXR1czESMBAGA1UECxMJTmV0c2NpdHVzMRIwEAYDVQQD 
EwlOZXRzY2l0dXMwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQCIbYWNK5eutpi6HRPJ 
E2JS9ULJoWVvtVj0AUgxIN1xjQmA0XRzhhVDFjFQJtjOaQtkP+utgx7/yfGRZXRMzPZjsae+JyGO 
1YcvW6Lny4LT5G0UyRgn5+3C32oHL2G9v+tUVOy9Pn9voJBcPxrpsW94xSW5BkhIsJXuLXVdjOnz 
X7Dozv7Z8kDB7MgmciuDC/Ur1gONZpOho1d7uGfPPLSzwB2SNOTX3v6GDx1F9u+SvxcB102wQw95 
QDmJj7lUSlE0j3bllP93GdoAEDTPqLgltWN4uXyvvJIb1H/bD+PYb79hJFBz0GZEc9rS0GAfvC9A 
z5ZHAP1aZJP7mp4Eh8fdAgMBAAGjITAfMB0GA1UdDgQWBBSvgDYtI/NGP8Y0EvsCHASjmr/PmzAN 
BgkqhkiG9w0BAQsFAAOCAQEACefje/dhmzEkBoA6OV934WtGXcBQNcb+9/qBGevUBG1cNJIyJddi 
dea2gFUB1rx/WffTrJyiOCApV8wXG+zmGm6YJenKnGG9sIQtOTibhs3ll7UN4S0n9xsD+1y7YD1c 
DNm9lI/3aFn1WUwPc3T4+RXE6XqkDB3geIvLUXaFUi+Y59XiLPHvk61kcopCGeoweX5yWVZ2Njp/ 
UUJIxQ6Ni3GvfPlxCxWtRe1MDAkhfT6/aAUr37lxtupHibzm9EAJdUEmAFHMhxkNCJiRDsasAiQ8 
7V5uBI3ucdSwh+gPaW8KoWlJpv5SGlAkwzq0lSrxyq2ukkC6ciPeKhUvWtHaPg== 
-----END CERTIFICATE----- 

他们使用不同的密钥,即使是在长度。为什么?

回答

10

您可以通过针对您的问题的googleling找到解决方案。从java2s.com

实施例:

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); 
    } 
    } 
} 

参见:

UPDATE:

有关该问题的其他信息,请参阅注释。

+0

嗨请参阅** **更新的问题 – iCode 2014-11-03 10:24:09

+1

@iProgrammer嗨,在结束回答的问题你的问题:不同的是,publickey.cert是一个完整的证书,而不仅仅是密钥本身。它还包含许多其他信息。见http://en.wikipedia.org/wiki/Public_key_certificate#Contents_of_a_typical_digital_certificate – 2014-11-03 10:26:59

+0

我明白了。但请参阅我从java代码获取的公钥和public.cert文件中的公钥。只要先检查几个字符,就可以了解到两者是不同的。 – iCode 2014-11-03 10:29:25

0

一旦你已经成功出口,可以从密钥存储得到它,

通过KeyPair(publicKey, (PrivateKey) key)

一个例子,

FileInputStream is = new FileInputStream("publickey.cert"); 
    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); 
    } 
    } 

将返回新键,值对。

又看了相似主题,这里Get Private Key from Keystore

+0

请参阅 – iCode 2014-11-03 10:25:27

+0

问题中的**更新**对不起,我不能在你的更新中的第二部分能更清楚 – 2014-11-03 10:27:30

+0

请查看我从Java代码获取的公钥和public.cert文件中的公钥。只要先检查几个字符,就可以了解到两者是不同的。 – iCode 2014-11-03 10:30:05

3

如果它只是公共密钥字符串,你想要的,它更容易获得publickey.cert文件,因为它是一个纯文本文件。假设你有文件的完整路径(如“/home/users/iprogrammer/publickey.cert”或“d:\我的文档\ publickey.cert”),你做这样的事情:

public String getPublicKeyString(Path path) throws IOException { 
    byte[] fileBytes = Files.readAllBytes(Paths.get(path)); 
    return new String(fileBytes, "US-ASCII"); 
} 

这将给你整个文件,包括-----BEGIN CERTIFICATE----------END CERTIFICATE-----

一旦你的整个文件,可以使用BouncyCastle的库中打开它:

PEMParser pemParser = new PEMParser(new StringReader(certPEMData)); 
    Object parsedObj = pemParser.readObject(); 
    System.out.println("PemParser returned: " + parsedObj); 
    if (parsedObj instanceof X509CertificateHolder) 
    { 
     X509CertificateHolder x509CertificateHolder = (X509CertificateHolder) parsedObj; 
     return x509CertificateHolder.getSubjectPublicKeyInfo().getPublicKeyData().getString(); 
    } 
    else 
    { 
     throw new RuntimeException("The parsed object was not an X509CertificateHolder."); 
    } 
+0

然后我可以阅读整个文件。有Java安全功能可以从密钥库中读取公钥。 – iCode 2014-11-03 10:20:53

+0

您要求提供公钥字符串。当然,有些方法可以从密钥存储区读取。但是既然你已经出口了,我给了你阅读它的方式。 – RealSkeptic 2014-11-03 10:22:16

+0

实际上,如果他可以像这样读取证书,那么他可以使用Bouncycastle的'PEMParser'类。 – EpicPandaForce 2014-11-03 11:58:24

0

如果您想采用公钥的字符串版本:

String publicKeyString value = "-----BEGIN PUBLIC KEY-----\n" + new String(Base64.encode(publicKey.getEncoded())) + "\n-----END PUBLIC KEY-----";

0

第一base 64只包含密钥

Base64.encodeBase64String(publicKey.getEncoded()) 

第二基座64包含整个公共证书

Base64.encodeBase64String(cert.getEncoded()) 
0

试试这个:

import java.security.KeyStore; 
import java.security.KeyStoreException; 
import java.security.NoSuchAlgorithmException; 
import java.security.cert.Certificate; 
import java.security.cert.CertificateException; 
import java.io.File; 
import java.io.FileInputStream; 
import java.io.FileNotFoundException; 
import java.io.IOException; 
import java.util.Enumeration; 
import java.security.PublicKey; 
import java.util.Base64; 

//===================== 

try { 
    File file = new File("C:\\Program Files (x86)\\keyStoreFilehere.kstr"); 
    FileInputStream is = new FileInputStream(file); 
    KeyStore keystore = KeyStore.getInstance(KeyStore.getDefaultType()); 
    String password = "password"; 
    keystore.load(is, password.toCharArray()); 
    Enumeration enumeration = keystore.aliases(); 
    while(enumeration.hasMoreElements()) { 
     String alias = (String)enumeration.nextElement(); 
     Certificate certificate = keystore.getCertificate(alias); 
     PublicKey publicKey = keystore.getCertificate(alias).getPublicKey(); 
     byte[] encodedCertKey = certificate.getEncoded(); 
     byte[] encodedPublicKey = publicKey.getEncoded(); 
     String b64PublicKey = Base64.getMimeEncoder().encodeToString(encodedPublicKey); 
     String b64CertKey = Base64.getMimeEncoder().encodeToString(encodedCertKey); 
     String publicKeyString = "-----BEGIN CERTIFICATE-----\n" 
          + b64PublicKey 
          + "\n-----END CERTIFICATE-----"; 

     String certKeyString = "-----BEGIN CERTIFICATE-----\n" 
          + b64CertKey 
          + "\n-----END CERTIFICATE-----"; 
     System.out.println(publicKeyString); 
     System.out.println(certKeyString); 
    } 

} catch (CertificateException | NoSuchAlgorithmException | KeyStoreException | IOException e) { 
      e.printStackTrace(); 
} 
+0

尽管这段代码可能会回答这个问题,但最好包含一些上下文,解释它的工作原理以及何时使用它。从长远来看,仅有代码的答案是没有用的。 – glennsl 2017-09-27 02:11:59