public class RSAUtil { #region 加密 /// <summary> /// 基于BouncyCastle的RSA加密 /// </summary> /// <param name="data">数据源</param> /// <param name="key">密钥</param> /// <param name="isPublicKey">是否为公钥</param> /// <returns>加密结果</returns> public static string EncryptByKey(string data, string key, bool isPublicKey) { byte[] tempData = Encoding.UTF8.GetBytes(data); IAsymmetricBlockCipher engine = new RsaEngine(); byte[] infoByte = Convert.FromBase64String(key); AsymmetricKeyParameter asymmetricKey = null; if (isPublicKey) { asymmetricKey = PublicKeyFactory.CreateKey(infoByte); } else { asymmetricKey = PrivateKeyFactory.CreateKey(infoByte); } engine.Init(true, asymmetricKey);//true 加密 // RSA算法规定,每次加密的字节数,不能超过密钥的长度值减去11,而每次加密得到的密文长度,却恰恰是密钥的长度。 // 所以,如果要加密较长的数据,需要采用数据截取的方法,分段加密。 int maxBlockSize = engine.GetInputBlockSize() / 8 - 11; byte[] buffer = new byte[maxBlockSize]; using (MemoryStream msInput = new MemoryStream(tempData)) { using (MemoryStream msOutput = new MemoryStream()) { int readLen = msInput.Read(buffer, 0, maxBlockSize); while (readLen > 0) { byte[] dataToEnc = new byte[readLen]; Array.Copy(buffer, 0, dataToEnc, 0, readLen); byte[] encData = engine.ProcessBlock(dataToEnc, 0, dataToEnc.Length); msOutput.Write(encData, 0, encData.Length); readLen = msInput.Read(buffer, 0, maxBlockSize); } byte[] result = msOutput.ToArray(); // 得到加密结果 return Convert.ToBase64String(tempData); } } } #endregion #region 解密 /// <summary> /// 基于BouncyCastle的RSA解密 /// </summary> /// <param name="data">数据源</param> /// <param name="key">密钥</param> /// <param name="isPublicKey">是否为公钥</param> /// <returns>解密结果</returns> public static string DecryptByKey(string data, string key, bool isPublicKey) { byte[] tempData = Convert.FromBase64String(data); IAsymmetricBlockCipher engine = new RsaEngine(); byte[] infoByte = Convert.FromBase64String(key); AsymmetricKeyParameter asymmetricKey = null; if (isPublicKey) { asymmetricKey = PublicKeyFactory.CreateKey(infoByte); } else { asymmetricKey = PrivateKeyFactory.CreateKey(infoByte); } engine.Init(false, asymmetricKey);//false 解密 // RSA算法规定,每次加密的字节数,不能超过密钥的长度值减去11,而每次加密得到的密文长度,却恰恰是密钥的长度。 // 所以,如果要加密较长的数据,需要采用数据截取的方法,分段加密。 int maxBlockSize = engine.GetInputBlockSize() / 8 - 11; byte[] buffer = new byte[maxBlockSize]; using (MemoryStream msInput = new MemoryStream(tempData)) { using (MemoryStream msOutput = new MemoryStream()) { int readLen = msInput.Read(buffer, 0, maxBlockSize); while (readLen > 0) { byte[] dataToEnc = new byte[readLen]; Array.Copy(buffer, 0, dataToEnc, 0, readLen); byte[] encData = engine.ProcessBlock(dataToEnc, 0, dataToEnc.Length); msOutput.Write(encData, 0, encData.Length); readLen = msInput.Read(buffer, 0, maxBlockSize); } byte[] result = msOutput.ToArray(); // 得到加密结果 return Encoding.UTF8.GetString(tempData); } } } #endregion #region 生成密钥 /// <summary> /// 基于BouncyCastle的RSA生成密钥 /// </summary> /// <param name="strength">密钥长度</param> /// <param name="encoding">字符编码</param> /// <returns>密钥对</returns> public static RSAKey GetRSAKey(int strength = 3072, string encoding = "UTF-8") { //RSA密钥对的构造器 RsaKeyPairGenerator keyGenerator = new RsaKeyPairGenerator(); //RSA密钥构造器的参数 RsaKeyGenerationParameters param = new RsaKeyGenerationParameters(Org.BouncyCastle.Math.BigInteger.ValueOf(3), new SecureRandom(), strength, 25); //用参数初始化密钥构造器 keyGenerator.Init(param); //产生密钥对 AsymmetricCipherKeyPair keyPair = keyGenerator.GenerateKeyPair(); //获取公钥和密钥 AsymmetricKeyParameter publicKey = keyPair.Public; AsymmetricKeyParameter privateKey = keyPair.Private; SubjectPublicKeyInfo subjectPublicKeyInfo = SubjectPublicKeyInfoFactory.CreateSubjectPublicKeyInfo(publicKey); PrivateKeyInfo privateKeyInfo = PrivateKeyInfoFactory.CreatePrivateKeyInfo(privateKey); Asn1Object asn1ObjectPublic = subjectPublicKeyInfo.ToAsn1Object(); byte[] publicInfoByte = asn1ObjectPublic.GetEncoded(encoding); Asn1Object asn1ObjectPrivate = privateKeyInfo.ToAsn1Object(); byte[] privateInfoByte = asn1ObjectPrivate.GetEncoded(encoding); RSAKey rSAKey = new RSAKey(); rSAKey.PrivateKey = Convert.ToBase64String(privateInfoByte); WriteFile(Path.Combine(AppDomain.CurrentDomain.SetupInformation.ApplicationBase, "private.key"), rSAKey.PrivateKey); rSAKey.PublicKey = Convert.ToBase64String(publicInfoByte); WriteFile(Path.Combine(AppDomain.CurrentDomain.SetupInformation.ApplicationBase, "public.key"), rSAKey.PublicKey); return rSAKey; } #endregion /// <summary> /// 写入文件 /// </summary> /// <param name="filePath"></param> /// <param name="content"></param> public static void WriteFile(string filePath, string content) { if (File.Exists(filePath)) { File.Delete(filePath); } byte[] contents = Encoding.UTF8.GetBytes(content); using (FileStream fileStream = new FileStream(filePath, FileMode.OpenOrCreate)) { fileStream.Write(contents, 0, contents.Length); } } } /// <summary> /// RSA加密的密匙 公钥和私匙 /// </summary> public class RSAKey { public string PublicKey { get; set; } public string PrivateKey { get; set; } }