【问题标题】:How do I store and read PGP public keys as strings using Bouncycastle Java?如何使用 Bouncycastle Java 将 PGP 公钥作为字符串存储和读取?
【发布时间】:2014-08-30 17:44:27
【问题描述】:

我一直在尝试创建、编码、存储、检索和解码 Bouncy Castle PGP 公钥。当我尝试重新读取密钥时,我得到了错误的输出和 EOFException。密钥将作为字符串存储在数据库中。

从密钥环中提取原始的RSA加密公钥如下:

@SuppressWarnings("unchecked")
public PGPPublicKey getPublicKey() {
    PGPPublicKey pk = null;
    Iterator<PGPPublicKey> it = publicKeyRing.getPublicKeys();
    while (pk == null && it.hasNext()) {
        PGPPublicKey key = it.next();
        if (key.isEncryptionKey()) {
            pk = key;
        }
    }
    return pk;
}

它被编码,ASCII 铠装,并存储为一个字符串,如下所示:

    PGPPublicKey contactPK = realContact.getPublicKey();
    ByteArrayOutputStream out = new ByteArrayOutputStream();
    ArmoredOutputStream armored = new ArmoredOutputStream(out);
    contactPK.encode(armored);
    armored.close();
    publicKey = new String(out.toByteArray(), Charset.forName("US-ASCII"));

这为我提供了一个 PGP 消息块,我希望在其中获得一个 PGP 公钥块:

----- BEGIN PGP MESSAGE ----- \ n版本:BCPG V1.50 \ n \ nuQINBFO8StkCEACQ4vrDnBTDjEvQkGwrAHuJSBZL8tNLxhZ9B74afhObhLVzW6ZB \ nT3pk / 5XcSPOTvcWd9k1yOKJUabCuF5ixFmMz + niFqUVQTtnl7aqOZ + GrDEzmoYmG \ nNQROP0EiA1TWtm2 + Ja0FqiJauXytt1sIF / Pr5L47FCjtmZKVoXTP8RVFfGLPB0kT \ ndjOz53PaEE3GSValh85w24XIH2 / gczURUnjphCX1bRwTFr14SfA9X / rFWqv9SqWQ \ nV8OiIWrSiwNd5RLJ9q0B + viDzoxrjmnMJZikxhKiuNVKJCu2ccBdMrbW42iBM2w3\n

...(为简洁起见)

\n-----结束 PGP 消息-----

当我尝试读回字符串以重新创建公钥时,我收到 EOFException:

// Import the public key.
ByteArrayInputStream in =
        new ByteArrayInputStream(stored.publicKey.getBytes(
                                                    Charset.forName("US-ASCII")));
// Needed to read ASCII armored keys
InputStream decoded = PGPUtil.getDecoderStream(in);
BCPGInputStream bcpgIn = new BCPGInputStream(decoded);
RSAPublicBCPGKey bcpgKey = new RSAPublicBCPGKey(bcpgIn);
PublicKeyPacket pkPacket = new PublicKeyPacket(PublicKeyAlgorithmTags.RSA_ENCRYPT,
                                                new Date(), bcpgKey);
publicKey = new PGPPublicKey(pkPacket, new BcKeyFingerprintCalculator());

创建 RSAPublicBCPGKey 时发生异常。

我做错了什么,但我不知道是什么。有人可以帮忙吗?

【问题讨论】:

    标签: java bouncycastle public-key pgp


    【解决方案1】:

    假设你已经在 String str 中拥有了你的 pgp 公钥(ascii Armored):

        InputStream in=new ByteArrayInputStream(str.getBytes());
        in = org.bouncycastle.openpgp.PGPUtil.getDecoderStream(in);
    
        JcaPGPPublicKeyRingCollection pgpPub = new JcaPGPPublicKeyRingCollection(in);
        in.close();
    
        PGPPublicKey key = null;
        Iterator<PGPPublicKeyRing> rIt = pgpPub.getKeyRings();
        while (key == null && rIt.hasNext())
        {
            PGPPublicKeyRing kRing = rIt.next();
            Iterator<PGPPublicKey> kIt = kRing.getPublicKeys();
            while (key == null && kIt.hasNext())
            {
                PGPPublicKey k = kIt.next();
    
                if (k.isEncryptionKey())
                {
                    key = k;
                }
            }
        }
        return key;
    

    现在,您的可变密钥将拥有您的 PGPPublicKey。

    【讨论】:

    • 为什么我必须遍历刚刚创建的 PublicKeyRing?它不是只有一个刚刚传递给它的密钥吗?
    【解决方案2】:

    我遇到了这个问题,结果证明公钥环实际上就是公钥本身。当我运行迭代器时,我实际上得到了子密钥(它变成了那个消息块而不是公钥块)。如果我解释得不好,请查看explanation。

    假设realContact 是一个只包含子密钥的公钥环,您实际上不需要通过getPublicKey() 运行它。

    【讨论】:

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