首页 > 后端开发 > C++ > 如何使用RijndaelManed和密码学API在C#中加密和解密字符串?

如何使用RijndaelManed和密码学API在C#中加密和解密字符串?

Susan Sarandon
发布: 2025-02-02 16:56:10
原创
238 人浏览过

How to Encrypt and Decrypt Strings in C# Using RijndaelManaged and the Cryptography API?

C# 字符串加密和解密

在 C# 中,字符串加密和解密是数据保护的关键环节。让我们探讨两种常用的方法:

1. 使用 RijndaelManaged 类

RijndaelManaged 类提供了流行的 AES(高级加密标准)算法的强大实现。以下是一个加密和解密字符串的示例:

using System.Security.Cryptography;
using System.Text;

public static class Crypto
{
    // 虽然应用程序特定的盐不是基于密码的加密的最佳实践,
    // 但只要它确实不常见,它可能足够安全。修改此答案还需要做很多工作。
    private static byte[] _salt = { ... };

    public static string Encrypt(string plainText, string sharedSecret)
    {
        // 从共享密钥和盐生成密钥
        Rfc2898DeriveBytes key = new Rfc2898DeriveBytes(sharedSecret, _salt);

        // 创建 RijndaelManaged 对象
        RijndaelManaged aesAlg = new RijndaelManaged();
        aesAlg.Key = key.GetBytes(aesAlg.KeySize / 8);

        // 加密数据
        ICryptoTransform encryptor = aesAlg.CreateEncryptor(aesAlg.Key, aesAlg.IV);
        byte[] cipherText = null;

        using (MemoryStream msEncrypt = new MemoryStream())
        {
            // 添加 IV
            msEncrypt.Write(BitConverter.GetBytes(aesAlg.IV.Length), 0, sizeof(int));
            msEncrypt.Write(aesAlg.IV, 0, aesAlg.IV.Length);

            using (CryptoStream csEncrypt = new CryptoStream(msEncrypt, encryptor, CryptoStreamMode.Write))
            {
                using (StreamWriter swEncrypt = new StreamWriter(csEncrypt))
                {
                    // 将数据写入流
                    swEncrypt.Write(plainText);
                }
            }

            cipherText = msEncrypt.ToArray();
        }

        // 将加密的字节作为 base64 字符串返回
        return Convert.ToBase64String(cipherText);
    }

    public static string Decrypt(string cipherText, string sharedSecret)
    {
        // 从共享密钥和盐生成密钥
        Rfc2898DeriveBytes key = new Rfc2898DeriveBytes(sharedSecret, _salt);

        // 创建 RijndaelManaged 对象
        RijndaelManaged aesAlg = new RijndaelManaged();
        aesAlg.Key = key.GetBytes(aesAlg.KeySize / 8);

        // 解密数据
        ICryptoTransform decryptor = aesAlg.CreateDecryptor(aesAlg.Key, aesAlg.IV);
        byte[] plainText = null;

        using (MemoryStream msDecrypt = new MemoryStream(Convert.FromBase64String(cipherText)))
        {
            // 从加密流中获取初始化向量
            aesAlg.IV = ReadByteArray(msDecrypt);

            using (CryptoStream csDecrypt = new CryptoStream(msDecrypt, decryptor, CryptoStreamMode.Read))
            {
                using (StreamReader srDecrypt = new StreamReader(csDecrypt))
                {
                    // 从解密流中读取解密的字节
                    plainText = Encoding.UTF8.GetBytes(srDecrypt.ReadToEnd());
                }
            }
        }

        // 将解密的文本作为字符串返回
        return Encoding.UTF8.GetString(plainText);
    }

    // 读取流中字节数组的辅助方法
    private static byte[] ReadByteArray(Stream s)
    {
        byte[] rawLength = new byte[sizeof(int)];
        if (s.Read(rawLength, 0, rawLength.Length) != rawLength.Length)
        {
            throw new InvalidOperationException("流不包含正确格式的字节数组");
        }

        byte[] buffer = new byte[BitConverter.ToInt32(rawLength, 0)];
        if (s.Read(buffer, 0, buffer.Length) != buffer.Length)
        {
            throw new InvalidOperationException("未正确读取字节数组");
        }

        return buffer;
    }
}
登录后复制

2. 使用 Cryptography API

C# 中的 Cryptography API 提供了各种用于安全加密操作的类。以下是如何使用此 API 加密和解密字符串的示例:

using System.Security.Cryptography;

public static class Crypto
{
    public static string Encrypt(string plainText, string sharedSecret)
    {
        // 创建对称密钥
        SymmetricAlgorithm algorithm = SymmetricAlgorithm.Create("AES");
        byte[] key = DeriveKey(sharedSecret, algorithm.KeySize);

        // 创建加密器
        ICryptoTransform encryptor = algorithm.CreateEncryptor(key, algorithm.IV);

        // 加密数据
        byte[] cipherText = encryptor.TransformFinalBlock(Encoding.UTF8.GetBytes(plainText), 0, plainText.Length);

        // 将加密的字节作为 base64 字符串返回
        return Convert.ToBase64String(cipherText);
    }

    public static string Decrypt(string cipherText, string sharedSecret)
    {
        // 创建对称密钥
        SymmetricAlgorithm algorithm = SymmetricAlgorithm.Create("AES");
        byte[] key = DeriveKey(sharedSecret, algorithm.KeySize);

        // 创建解密器
        ICryptoTransform decryptor = algorithm.CreateDecryptor(key, algorithm.IV);

        // 解密数据
        byte[] plainText = decryptor.TransformFinalBlock(Convert.FromBase64String(cipherText), 0, cipherText.Length);

        // 将解密的文本作为字符串返回
        return Encoding.UTF8.GetString(plainText);
    }

    // 从共享密钥派生密钥的辅助方法
    private static byte[] DeriveKey(string sharedSecret, int keySize)
    {
        // 使用基于密码的密钥派生函数 (PBKDF2)
        Rfc2898DeriveBytes pbkdf2 = new Rfc2898DeriveBytes(sharedSecret, salt, 10000, HashAlgorithmName.SHA256);
        return pbkdf2.GetBytes(keySize / 8);
    }
}
登录后复制

这两种方法都为保护 C# 中的敏感数据提供了强大的加密和解密机制。RijndaelManaged 类是一种成熟且广泛使用的算法,而 Cryptography API 提供了额外的功能和灵活性。 请注意,代码中省略了salt的定义,实际使用时需要定义一个安全的盐值。 此外,对于生产环境,建议使用更强大的密钥管理和更安全的密钥派生方法。

以上是如何使用RijndaelManed和密码学API在C#中加密和解密字符串?的详细内容。更多信息请关注PHP中文网其他相关文章!

本站声明
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系admin@php.cn
作者最新文章
热门教程
更多>
最新下载
更多>
网站特效
网站源码
网站素材
前端模板