java - Java-使用现有的公钥文件加密字符串

标签 java encryption rsa

我已经在过去4-5个小时内进行了研究,尽管找到了使用从几种方法到整个〜100行类的所有内容的“答案”,但似乎找不到真正有效的答案。我无法想象没有一些简单的功能可以完成如此​​琐碎的事情:P

我有一组预先存在的公用/专用 key (实际上,有两组-一组由ssh-keygen生成,另一组由openssl生成,所以..什么格式都可以用)。

我所需要的只是一个与我在python中编写的代码等效的简单java-

key_object = someModule.KeyObject(nameOfPublicKeyFile)

def encrypt (SomePlainText) :
  return someOtherModule.encrypt(key_object, SomePlainText)

任何帮助都是极好的!

最佳答案

shell 程序中的这些openssl命令创建RSA key 对,并将公用 key 和专用 key 写入 DER 格式的文件。

在这里,私钥文件没有密码保护(-nocrypt),以使事情变得简单。

$ openssl genrsa -out keypair.pem 2048
Generating RSA private key, 2048 bit long modulus
............+++
................................+++
e is 65537 (0x10001)
$ openssl rsa -in keypair.pem -outform DER -pubout -out public.der
writing RSA key
$ openssl pkcs8 -topk8 -nocrypt -in keypair.pem -outform DER -out private.der

现在已经有了DER文件,您可以用Java读取它们并使用 KeySpec KeyFactory 创建 PublicKey PrivateKey 对象。
public byte[] readFileBytes(String filename) throws IOException
{
    Path path = Paths.get(filename);
    return Files.readAllBytes(path);        
}

public PublicKey readPublicKey(String filename) throws IOException, NoSuchAlgorithmException, InvalidKeySpecException
{
    X509EncodedKeySpec publicSpec = new X509EncodedKeySpec(readFileBytes(filename));
    KeyFactory keyFactory = KeyFactory.getInstance("RSA");
    return keyFactory.generatePublic(publicSpec);       
}

public PrivateKey readPrivateKey(String filename) throws IOException, NoSuchAlgorithmException, InvalidKeySpecException
{
    PKCS8EncodedKeySpec keySpec = new PKCS8EncodedKeySpec(readFileBytes(filename));
    KeyFactory keyFactory = KeyFactory.getInstance("RSA");
    return keyFactory.generatePrivate(keySpec);     
}

使用公钥和私钥,您可以加密和解密少量数据(适合您的RSA模数。)我建议使用 OAEP 填充。
public byte[] encrypt(PublicKey key, byte[] plaintext) throws NoSuchAlgorithmException, NoSuchPaddingException, InvalidKeyException, IllegalBlockSizeException, BadPaddingException
{
    Cipher cipher = Cipher.getInstance("RSA/ECB/OAEPWithSHA1AndMGF1Padding");   
    cipher.init(Cipher.ENCRYPT_MODE, key);  
    return cipher.doFinal(plaintext);
}

public byte[] decrypt(PrivateKey key, byte[] ciphertext) throws NoSuchAlgorithmException, NoSuchPaddingException, InvalidKeyException, IllegalBlockSizeException, BadPaddingException
{
    Cipher cipher = Cipher.getInstance("RSA/ECB/OAEPWithSHA1AndMGF1Padding");   
    cipher.init(Cipher.DECRYPT_MODE, key);  
    return cipher.doFinal(ciphertext);
}

在这里,它与简单的加密和解密结合在一起:
public void Hello()
{
    try
    {
        PublicKey publicKey = readPublicKey("public.der");
        PrivateKey privateKey = readPrivateKey("private.der");
        byte[] message = "Hello World".getBytes("UTF8");
        byte[] secret = encrypt(publicKey, message);
        byte[] recovered_message = decrypt(privateKey, secret);
        System.out.println(new String(recovered_message, "UTF8"));
    }
    catch (Exception e)
    {
        e.printStackTrace();
    }
}

关于java - Java-使用现有的公钥文件加密字符串,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/24338108/

相关文章:

c# - VerifyHash 似乎在 Windows 上工作,但在 Linux 上失败

java - JasperReports 中的异常

java - Java 中的视频播放(JMF、Fobs4JMF、Xuggler、FMJ)

c++ - 在 Crypto++ 中使用 RSA 加密对称 AES key

iphone - 使用 C 或 Objective-C 加密不同类型的文件

java - 执行从字符串到键的转换

java - 创建公钥和私钥

java - InvalidKeySpecException : algid parse error, 不是序列

java - 如何订阅 MQTT 主题并在 Eclipse (Java) 上打印收到的消息

java - Lucene在while循环中创建文档越来越慢