记录一次项目使用RSA加解密
项目使用Java和Python在开发,RSA加密解密互通代码:
Python代码
# -*- coding: utf-8 -*-
"""
RSA加解密
"""
import base64
from M2Crypto import BIO, RSA
with open("public_key.pem", 'r') as f:
pubkey = f.read()
with open("private_key.pem", 'r') as f:
prikey = f.read()
# 加密
text = "ABCDEF".encode('utf-8') # 明文
pub_bio = BIO.MemoryBuffer(pubkey.encode('utf-8')) # 公钥字符串
pub_rsa = RSA.load_pub_key_bio(pub_bio) # 加载公钥
secret = pub_rsa.public_encrypt(text, RSA.pkcs1_padding) # 公钥加密
sign = base64.b64encode(secret) # 密文base64编码
print(sign)
# 解密
b64_sign = "uhBqhevT0E5+WT++HX+pGzSy7YGskBQODuvoV+hf0k8cSyXG/GuAT4LKYaCiT9qiEGlbWxCIH51Qt1s0y2X56TbNja93AbzXiFWzsC2H6vwo3ZFcoj+YqUBsax+Gad0I6NME9lalpKsPtWqi4W/b3VbG5Mx+WBJ+L17GR7ZvWMo=" # base64密文
cipher = base64.b64decode(b64_sign) # base64解码
pri_bio = BIO.MemoryBuffer(prikey.encode('utf-8')) # 加载私钥
pri_rsa = RSA.load_key_bio(pri_bio)
plain = pri_rsa.private_decrypt(cipher, RSA.pkcs1_padding) # 解密
print(plain.decode('utf-8'))
Java代码
import java.security.Key;
import java.security.KeyFactory;
import java.security.NoSuchAlgorithmException;
import java.security.PrivateKey;
import java.security.PublicKey;
import java.security.spec.InvalidKeySpecException;
import java.security.spec.PKCS8EncodedKeySpec;
import java.security.spec.X509EncodedKeySpec;
import java.util.Base64;
import javax.crypto.Cipher;
public class rsa_demo {
public String encryptoMode ="RSA/ECB/PKCS1Padding";
//public String encryptoMode ="RSA/ECB/NoPadding";
private String priKey="私钥字符串";
private String pubKey="公钥字符串";
public String sign_str = "123456" ;
/***
* 秘钥的来源方式 openssl 生成
*/
/**
* 获得公钥
* @return
* @throws NoSuchAlgorithmException
* @throws InvalidKeySpecException
*/
private PublicKey getPublicKey(String pubKeyString) throws NoSuchAlgorithmException, InvalidKeySpecException {
byte[] pubKeyByte = Base64.getDecoder().decode(pubKey);
X509EncodedKeySpec spec = new X509EncodedKeySpec(pubKeyByte);
KeyFactory keyFactory = KeyFactory.getInstance("RSA");
PublicKey pubkey = keyFactory.generatePublic(spec);
return pubkey;
}
/**
* 获得私钥
* @return
*/
private PrivateKey getPrivateKey(String priKeyString) throws NoSuchAlgorithmException, InvalidKeySpecException {
byte[] priKeyByte = Base64.getDecoder().decode(priKey);
PKCS8EncodedKeySpec spec = new PKCS8EncodedKeySpec(priKeyByte);
KeyFactory keyFactory = KeyFactory.getInstance("RSA");
PrivateKey priKey = keyFactory.generatePrivate(spec);
return priKey;
}
/**
* 公钥加密 (私钥加密)
*/
public String encrypto(String text,Key key) {
try{
Cipher cipher = Cipher.getInstance(encryptoMode);
cipher.init(Cipher.ENCRYPT_MODE, key);
byte tempBytes[] = cipher.doFinal(text.getBytes());
String secretText=Base64.getEncoder().encodeToString(tempBytes);
return secretText;
}catch(Exception e){
throw new RuntimeException("加密字符串[" + text + "]时遇到异常", e);
}
}
/**
* 私钥解密(公钥解密)
* @param secretText
*/
public String decrypto(String secretText,Key key) {
try{
//生成公钥
Cipher cipher = Cipher.getInstance(encryptoMode);
cipher.init(Cipher.DECRYPT_MODE, key);
// 密文解码
byte[] secretText_decode = Base64.getDecoder().decode(secretText.getBytes());
byte tempBytes[] = cipher.doFinal(secretText_decode);
String text=new String( tempBytes);
return text;
}catch(Exception e){
throw new RuntimeException("解密字符串[" + secretText + "]时遇到异常", e);
}
}
/**
* 由于每次公钥 加密出来的结果都不一样,所有python java 每次加密出来的结果都不一样,也就没有可比性。我们只考虑能解密就行
* @param args
*/
public static void main(String[] args) throws Exception {
rsa_demo rsa = new rsa_demo();
System.err.println("明文:"+rsa.sign_str);
PublicKey pubkey = rsa.getPublicKey(rsa.pubKey);
PrivateKey prikey = rsa.getPrivateKey(rsa.priKey);
String secretText = rsa.encrypto(rsa.sign_str,pubkey);//公钥加密,私钥解密
secretText="Lm9PN4oM1dl17d2XFYRIs+hDV6RkGPVYBjgYAglaj020v5RnYzClHUN6lOVBzpeYKyH1MY5JzyOfxuYZHKCupVqhcvY4+zx+jowBH2nbVp1+/OrzuiPkNivfvmEad6ImAZp5/3Y/dVafABm5xZE78j7Ytlv0ak4seXMGTisU39o=";
System.out.println("密文:"+secretText);
String text = rsa.decrypto(secretText,prikey);
System.out.println("明文:"+text);
}
}
note
1 公钥私钥:使用openssl生成pkcs#1格式的公钥私钥pem文件。python直接使用该密钥;Java需要转换为pkcs#8格式公钥私钥,密钥字符串不需要BEGIN/END。
2 python可以将公钥私钥的字符串直接保存使用,避免每次读pem文件。
3 M2Crypto库安装会有环境问题,centOS直接pip安装成功,Ubuntu安装失败。
**粗体** _斜体_ [链接](http://example.com) `代码` - 列表 > 引用
。你还可以使用@
来通知其他用户。