如何从作为ByteString复活的Key创建java.security.publicKey - OAEP填充

时间:2017-08-04 11:37:54

标签: java encryption rsa

我有一个用go编写的gRPC服务器,它为用java编写的客户端提供公钥。密钥使用带有sha-256的OAEP填充,并以我认为的PEM格式作为ByteString接收。

我试图读取收到的字节并将它们放入用于解密的PublicKey对象

Go Server Snippet:

plaintext, err := rsa.DecryptOAEP(sha256.New(), rng, d.decKey, ciphertext, label)
if err != nil {
    log.Fatalf("Error from decryption: %s\n", err)
}

// H := H'
return plaintext

RSA密钥

当我执行client.getKey()时,这是打印到控制台的键.toString()

-----BEGIN RSA PUBLIC KEY-----
MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEA5SuTn/IhVfLpcgEtbkty
ip6ajx8tcVNt862lj24cz/zGEqzD3sDaRaS+9l16l63T/mWutPqyCBWekg9oGK6Z
ni313nJyvMETCY1kc9mj7IB9yNd00eXr+jYJNF92qc3k0IlyxDjD6hE/InlKn1cM
njYOMYhZtsMSQQElIeYsiqOD1k55E4905XP8gh3K5YT8jVBHJHboJiXVqBJ0CQPq
LKYufey+WcX3p5wKKUgycKxB1zgS1BAHJ/l9x6fxDTE85CBIeRyfSXijHgiWGAEY
MDOIRIBpA8MT5q0Mghy9+KryIHNkc+659DAgCjghY8pmyFezF5gDzRpEi+jB5OOT
bQIDAQAB
-----END RSA PUBLIC KEY-----

我一直在尝试将其解析为字符串,删除“----- BEGIN RSA PUBLIC KEY -----”和“----- END RSA PUBLIC KEY -----”并转换将剩余的字符串转换为字节数组,然后转换为PublicKey对象

Java代码

String key = client.getPublicKey(nonce).getRSAEncryptionKey().toString();
key = key.replace("-----BEGIN RSA PUBLIC KEY-----\n", "");
key = key.replace("-----END RSA PUBLIC KEY-----", "");
byte[] keyBytes = Base64.getDecoder().decode(key); //bytes of key
Cipher cipher_RSA;
        try {
            cipher_RSA = Cipher.getInstance("RSA");
            X509EncodedKeySpec spec = new X509EncodedKeySpec(keyBytes);
            KeyFactory keyFactory = KeyFactory.getInstance("RSA");
            PublicKey pk = keyFactory.generatePublic( spec);

            cipher_RSA.init(Cipher.ENCRYPT_MODE, pk); 
            return cipher_RSA.doFinal(message);
        }catch(Exception e){}

这会导致“非法base64字符”。我假设这与密钥使用OAEP填充的事实有关。但是,当我将密钥工厂/密码的实例更改为“RSA / ECB / OAEPWITHSHA-256ANDMGF1PADDING”时,我收到此错误:

java.security.NoSuchAlgorithmException: RSA/ECB/OAEPWITHSHA-256ANDMGF1PADDING KeyFactory not available

1 个答案:

答案 0 :(得分:2)

不同的base64解码器在遇到非法base64字符时是否抛出异常或是否只是忽略该字符时有不同的规则。包含换行符的空格不是有效的base64字符。要纠正错误,您必须在base64解码之前从PEM公钥字符串中删除换行符。

key = key.replace("-----BEGIN RSA PUBLIC KEY-----\n", "");
key = key.replace("-----END RSA PUBLIC KEY-----", "");
// add the following line  
key = key.replace("\n", "");

注意:这是过于简单的,因为它假定'\ n'将是行分隔符。您还可以将替换添加到其他公共行分隔符字符序列。确保按长度订购替换件,首先是最长的,最后一个是最短的。