.NET 6+ 应用 RSA.Create(2048) 创建密钥对,用 ExportPkcs8PrivateKey() 和 ExportSubjectPublicKeyInfo() 导出二进制密钥,加密须用 RSAEncryptionPadding.OaepSHA256 且明文≤190 字节,解密需匹配填充并正确 UTF-8 解码。

直接用 RSA.Create(),别碰 RSACryptoServiceProvider —— 它在 .NET 6+ 已过时,Linux/macOS 下会抛 PlatformNotSupportedException,且导出的密钥格式不兼容 OpenSSL。
怎么生成和持久化密钥对(.NET 6+ 推荐路径)
必须用 RSA.Create(2048) 创建新实例,不是 new 旧类。生成后立即导出二进制字节流,而非 XML 或 PEM 字符串:
-
ExportPkcs8PrivateKey()导出私钥(PKCS#8 格式,推荐) -
ExportSubjectPublicKeyInfo()导出公钥(X.509 SPKI 格式) - 导出结果是
byte[],存文件前需 Base64 编码或直接写入二进制文件;若要 PEM,得手动加头尾:"-----BEGIN PRIVATE KEY-----\n{base64}\n-----END PRIVATE KEY-----" - 别调用
ExportParameters(true)—— 返回的RSAParameters是结构体,不带 PEM 封装,也难跨平台复用
公钥加密失败的常见原因和检查点
报 CryptographicException: The parameter is incorrect,90% 是填充或长度问题:
- 必须显式指定
RSAEncryptionPadding.OaepSHA256,不能只写RSAEncryptionPadding.Oaep(默认 SHA1,不安全且可能被拒绝) - 明文长度超限:2048 位密钥下,OAEP-SHA256 最多加密
rsa.KeySize / 8 - 42字节(≈190 字节),超长必须走混合加密(AES + RSA 封装密钥) - 加密时用了私钥、解密时用了公钥 —— 这是签名逻辑,不是加解密流程;确认调用的是
Encrypt()(公钥)和Decrypt()(私钥) - 公钥对象是从
ExportSubjectPublicKeyInfo()加载的,不是从 PEM 解析来的(.NET 原生不解析 PEM,需 BouncyCastle)
为什么解密总返回乱码或空?
解密方拿到的私钥字节流,必须用 ImportPkcs8PrivateKey() 加载,且填充方式必须与加密端完全一致:
- 加载私钥时传错字节数组(比如把公钥字节当私钥传)→ 直接抛异常
- 解密时用了
RSAEncryptionPadding.Pkcs1,但加密端用的是OaepSHA256→ 报 “parameter is incorrect” - 明文是 UTF-8 字节数组加密的,但解密后没用
Encoding.UTF8.GetString()转回字符串 → 得到的是原始字节视图,看起来像乱码 - 密钥长度不匹配:加密用 2048,解密用 3072 实例加载同一私钥 → 失败
最易被忽略的一点:RSA 不是拿来加密业务数据的。它只适合加密 AES 密钥、JWT 加密密钥或 token ID 这类短内容。试图用它加密 JSON 或 HTML,本质上是在给自己埋崩溃点。


















