【问题标题】:Store PGP (public) keys in java keystore - Bouncycastle在 Java 密钥库中存储 PGP(公共)密钥 - Bouncycastle
【发布时间】:2012-04-05 13:55:55
【问题描述】:

我在 SSO 的实现中使用 bouncycastle (JAVA) 进行签名、加密、解密和签名验证。 我有原始 PGP 公钥和私钥,我需要将它们存储在 Java 密钥库中。 这些 PGP 公钥没有证书。

我知道对于公钥(根据 Keystore 的 javadoc:http://docs.oracle.com/javase/6/docs/api/java/security/KeyStore.html),我必须创建证书。创建证书后,我可以将其作为 KeyStore.TrustedCertificateEntry 导入密钥库。 但是,我无法为 org.bouncycastle.openpgp.PGPPublicKey 类型创建证书条目。

我在网上搜索过,但找不到任何有效的例子:

  1. Bouncycastle 文档:http://www.bouncycastle.org/wiki/display/JA1/X.509+Public+Key+Certificate+and+Certification+Request+Generation 为 X.509 密钥生成证书 -
  2. Bouncycastle 示例 - org.bouncycastle.openpgp.examples.DirectKeySignature: 将证书(PGPSignature 类型的对象)直接添加到 PGPPublicKey。 总而言之 - 我已经签署(认证)PGPPublicKey,但我无法将这种类型的密钥存储到 java 密钥库中。

    OutputStream out = new ByteArrayOutputStream();
    
    if (armor)
    {
        out = new ArmoredOutputStream(out);
    }
    
    PGPPrivateKey pgpPrivKey = secretKey.extractPrivateKey(secretKeyPass.toCharArray(), "BC");
    
    PGPSignatureGenerator       sGen = new PGPSignatureGenerator(secretKey.getPublicKey().getAlgorithm(), PGPUtil.SHA1, "BC");
    
    sGen.initSign(PGPSignature.DIRECT_KEY, pgpPrivKey);
    
    BCPGOutputStream            bOut = new BCPGOutputStream(out);
    
    sGen.generateOnePassVersion(false).encode(bOut);
    
    PGPSignatureSubpacketGenerator spGen = new PGPSignatureSubpacketGenerator();
    
    boolean isHumanReadable = true;
    
    spGen.setNotationData(true, isHumanReadable, notationName, notationValue);
    
    PGPSignatureSubpacketVector packetVector = spGen.generate();
    sGen.setHashedSubpackets(packetVector);
    
    bOut.flush();
    
    return PGPPublicKey.addCertification(keyToBeSigned, sGen.generate()).getEncoded();
    

我主要对编程解决方案(java 源代码)感兴趣,但使用一些工具的示例也会有所帮助。

谢谢!

【问题讨论】:

    标签: java bouncycastle pgp


    【解决方案1】:

    我认为你应该从你的PGPPublicKey 中提取一个java.security.PublicKey 并使用它来构造一个可以存储在密钥库中的X509Certificate

    JcaPGPKeyConverter c = new JcaPGPKeyConverter();
    PublicKey publicKey = c.getPublicKey(pgpPublicKey);
    // ... Use Bouncy's X509V3CertificateGenerator or X509v3CertificateBuilder
    // ... to construct a self-signed cert
    X509Certificate x509Certificate = // ...
    // ... add cert to KeyStore
    

    要从PublicKey 创建X509Certificate,请参阅:Generate random certificates

    【讨论】:

      【解决方案2】:

      如果您只想保存公钥,为什么不能将密钥内容保存到 Java 密钥库中?然后检索内容并在需要时转换为 PGPPublicKey 对象。

      先创建一个包装类

      public class PgpPublicKeyWrapper implements Key {
          private final String keyContent;
          public PgpPublicKeyWrapper(final String keyContent) {
              this.keyContent = keyContent;
          }
          @Override
          public String getAlgorithm() {
              return "PGP-PublicKey"; // you can call whatever you want
          }
          @Override
          public String getFormat() {
              return "RAW"; // has to be raw format
          }
          @Override
          public byte[] getEncoded() {
              return keyContent.getBytes();
          }
      }
      

      然后你可以这样做来保存它

      keyStore.setKeyEntry("think a name for alias", new PgpPublicKeyWrapper(key), PASSWORD, null);
      

      当你想找回它时

      Key key = this.keyStore.getKey(alias, PASSWORD);
      InputStream is = new ByteArrayInputStream(key.getEncoded());
      PGPPublicKey publicKey = readPublicKey(is); 
      

      对于 readPublicKey(),你可以在网上找到很多关于如何将 InputStream 读取到 PGPPublicKey 对象的示例。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2016-06-25
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2019-06-24
        • 1970-01-01
        相关资源
        最近更新 更多