RSA 非對稱加密廣泛用於客戶端-服務端機密通信:客戶端用公鑰加密,服務端用私鑰解密。本文提供完整的密鑰對生成、序列化保存工具類,採用標準 Java Security API,支援 512-2048 位密鑰長度。
import java.io.*;
import java.security.*;
import java.security.spec.*;
public class RsaKeyPairGenerator {
/**
* 生成 RSA 密鑰對並保存到指定目錄
* @param keySize 密鑰長度(512-2048,建議 2048)
* @param outputDir 保存目錄路徑
* @throws Exception 生成或 IO 失敗
*/
public static void generateAndSave(int keySize, String outputDir) throws Exception {
if (keySize < 512 || keySize > 2048) {
throw new IllegalArgumentException("密鑰長度必須在 512-2048 之間");
}
File dir = new File(outputDir);
if (!dir.exists() && !dir.mkdirs()) {
throw new IOException("無法創建輸出目錄: " + outputDir);
}
KeyPairGenerator kpg = KeyPairGenerator.getInstance("RSA");
kpg.initialize(keySize);
KeyPair kp = kpg.generateKeyPair();
PublicKey publicKey = kp.getPublic();
PrivateKey privateKey = kp.getPrivate();
// 保存公鑰 (X.509 格式)
try (FileOutputStream fos = new FileOutputStream(new File(dir, "public_key.der"));
ObjectOutputStream oos = new ObjectOutputStream(fos)) {
oos.writeObject(publicKey);
}
// 保存私鑰 (PKCS#8 格式)
try (FileOutputStream fos = new FileOutputStream(new File(dir, "private_key.der"));
ObjectOutputStream oos = new ObjectOutputStream(fos)) {
oos.writeObject(privateKey);
}
}
/** 從文件加載公鑰 */
public static PublicKey loadPublicKey(String path) throws Exception {
try (FileInputStream fis = new FileInputStream(path);
ObjectInputStream ois = new ObjectInputStream(fis)) {
return (PublicKey) ois.readObject();
}
}
/** 從文件加載私鑰 */
public static PrivateKey loadPrivateKey(String path) throws Exception {
try (FileInputStream fis = new FileInputStream(path);
ObjectInputStream ois = new ObjectInputStream(fis)) {
return (PrivateKey) ois.readObject();
}
}
public static void main(String[] args) {
try {
generateAndSave(2048, "keys/rsa_2048");
System.out.println("密鑰對生成完成,保存至 keys/rsa_2048/");
} catch (Exception e) {
e.printStackTrace();
}
}
}
Base64.getEncoder() 編碼 key.getEncoded() 字節數組。import javax.crypto.Cipher;
public class RsaCrypto {
public static byte[] encrypt(PublicKey publicKey, byte[] data) throws Exception {
Cipher cipher = Cipher.getInstance("RSA/ECB/PKCS1Padding");
cipher.init(Cipher.ENCRYPT_MODE, publicKey);
return cipher.doFinal(data);
}
public static byte[] decrypt(PrivateKey privateKey, byte[] encrypted) throws Exception {
Cipher cipher = Cipher.getInstance("RSA/ECB/PKCS1Padding");
cipher.init(Cipher.DECRYPT_MODE, privateKey);
return cipher.doFinal(encrypted);
}
}
注意:RSA 只能加密小於密鑰長度的數據(2048 位約 245 字節)。大數據應採用混合加密:隨機生成 AES 密鑰加密數據,再用 RSA 加密 AES 密鑰。