不再过多介绍, 依赖hutool库
加解密(hutool)
可通过new RSA()
后获取密钥对(公钥、私钥);定义为常量。rsa.encrypt()
加密得到byte[]
,
⚠:new String(byte[]);
的方式导致输出乱码,致使后续解密ERROR;相关链接
通常通过 base64 对 byte[]
进行编码;
然后通过rsa.decrypt()
对base64/byte[]
解密。
import cn.hutool.core.codec.Base64;
import cn.hutool.crypto.asymmetric.KeyType;
import cn.hutool.crypto.asymmetric.RSA;
public class RsaTest {
private final static String PUBLIC_KEY = "MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQC05MBh04Wgw7S4xPn/PRo2QKFS70G4mkEzn5kibeN81Q/WuG4lJaWE6wW65hsFuz/DxRHvZaCeEO82ebr5LefYRzRXRzq6/a03e2wxiSA3DyFIcqySro+UpKDx824FfVIi+fs54Wc5xATThFKbfVD4UUA3hgAiq5sQpRpqq3CvTQIDAQAB";
private final static String PRIVATE_KEY = "MIICdQIBADANBgkqhkiG9w0BAQEFAASCAl8wggJbAgEAAoGBALTkwGHThaDDtLjE+f89GjZAoVLvQbiaQTOfmSJt43zVD9a4biUlpYTrBbrmGwW7P8PFEe9loJ4Q7zZ5uvkt59hHNFdHOrr9rTd7bDGJIDcPIUhyrJKuj5SkoPHzbgV9UiL5+znhZznEBNOEUpt9UPhRQDeGACKrmxClGmqrcK9NAgMBAAECgYBbfdNb5zsP+8wdI+t5z/LA++FcbAymjMZrkM5IHqJPkgfHx1JWUXstBh3I0Pdb58AxiSwwFAuvxsrml50cyL4YyK4owBXy0ZbQCnw6RXoAQnTsYoF+0kuaEEJ5n+ZP/IBcI0/a0Qlu4rgCtWXKCpCfes4znHOUSkUsrCoNWT5AYQJBAON1lJjX4OB80STbUedgSnrs5wMgi2W8lat0P895uNeGwavzyfD7hwv6CcJor+fd3fcZl4dZFHLhwzDv+zzn4KUCQQDLl2RjGGLLaUarvCf2LWT40B6ehykLSF639LoXqNRWZcbd90OSAr2lYj31CY0MptMeNrt3/2E3SKMptXLL+uuJAkBox8tyNVBEWXtGzTmHqpXk1qj8icttTFhuKRkUDHCX6F3jRmSqfFQTslU4l10hJNWRdNqW4PRIj7OJIaPMxMx5AkAgX3lZ/IWxHJNdOXUNQxicK9PCl3FiVuagz6xLmM/y0Qo3P1siO4dWZfG+Jf+ktF47nq5enWAi/0zak/ymDMcpAkBuEkAZFK2oG80YG0A5BNn1XSpXpJWJWg8TmPLCLBWjyMBD75pdX90MgqUEg4CqMHOIR23CKD/Ql5wjkR30ys/W";
public static void main(String[] args) {
RSA rsa = new RSA(PRIVATE_KEY, PUBLIC_KEY);
byte[] encrypt = rsa.encrypt("username:password", KeyType.PublicKey);
String base64 = Base64.encode(encrypt);
System.out.println("base64 = " + base64);
//new String(byte[]); 的方式导致输出乱码,且在解密时ERROR;
//https://blog.csdn.net/qq_38022877/article/details/88560518
//方式一、byte[] decrypt = rsa.decrypt(encrypt, KeyType.PrivateKey);
//方式二、
byte[] decrypt = rsa.decrypt(base64, KeyType.PrivateKey);
String s1 = new String(decrypt);
System.out.println("s1 = " + s1);
}
}
工具类(生成密钥对到文件)
package utils;
import java.io.File;
import java.io.IOException;
import java.nio.file.Files;
import java.security.*;
import java.security.spec.InvalidKeySpecException;
import java.security.spec.PKCS8EncodedKeySpec;
import java.security.spec.X509EncodedKeySpec;
import java.util.Base64;
public class RsaUtils {
private static final int DEFAULT_KEY_SIZE = 2048;
/**
* 从文件中读取公钥
*
* @param filename 公钥保存路径,相对于classpath
* @return 公钥对象
* @throws Exception
*/
public static PublicKey getPublicKey(String filename) throws Exception {
byte[] bytes = readFile(filename);
return getPublicKey(bytes);
}
/**
* 从文件中读取密钥
*
* @param filename 私钥保存路径,相对于classpath
* @return 私钥对象
* @throws Exception
*/
public static PrivateKey getPrivateKey(String filename) throws Exception {
byte[] bytes = readFile(filename);
return getPrivateKey(bytes);
}
/**
* 获取公钥
*
* @param bytes 公钥的字节形式
* @return
* @throws Exception
*/
private static PublicKey getPublicKey(byte[] bytes) throws Exception {
bytes = Base64.getDecoder().decode(bytes);
X509EncodedKeySpec spec = new X509EncodedKeySpec(bytes);
KeyFactory factory = KeyFactory.getInstance("RSA");
return factory.generatePublic(spec);
}
/**
* 获取密钥
*
* @param bytes 私钥的字节形式
* @return
* @throws Exception
*/
private static PrivateKey getPrivateKey(byte[] bytes) throws NoSuchAlgorithmException, InvalidKeySpecException {
bytes = Base64.getDecoder().decode(bytes);
PKCS8EncodedKeySpec spec = new PKCS8EncodedKeySpec(bytes);
KeyFactory factory = KeyFactory.getInstance("RSA");
return factory.generatePrivate(spec);
}
/**
* 根据密文,生成rsa公钥和私钥,并写入指定文件
*
* @param publicKeyFilename 公钥文件路径
* @param privateKeyFilename 私钥文件路径
* @param secret 生成密钥的密文
*/
public static void generateKey(String publicKeyFilename, String privateKeyFilename, String secret, int keySize) throws Exception {
KeyPairGenerator keyPairGenerator = KeyPairGenerator.getInstance("RSA");
SecureRandom secureRandom = new SecureRandom(secret.getBytes());
keyPairGenerator.initialize(Math.max(keySize, DEFAULT_KEY_SIZE), secureRandom);
KeyPair keyPair = keyPairGenerator.genKeyPair();
// 获取公钥并写出
byte[] publicKeyBytes = keyPair.getPublic().getEncoded();
publicKeyBytes = Base64.getEncoder().encode(publicKeyBytes);
writeFile(publicKeyFilename, publicKeyBytes);
// 获取私钥并写出
byte[] privateKeyBytes = keyPair.getPrivate().getEncoded();
privateKeyBytes = Base64.getEncoder().encode(privateKeyBytes);
writeFile(privateKeyFilename, privateKeyBytes);
}
private static byte[] readFile(String fileName) throws Exception {
return Files.readAllBytes(new File(fileName).toPath());
}
private static void writeFile(String destPath, byte[] bytes) throws IOException {
File dest = new File(destPath);
if (!dest.exists()) {
dest.createNewFile();
}
Files.write(dest.toPath(), bytes);
}
}