在 ASP.NET 應用中,資料保護主要仰賴三類密碼學原語:對稱加密(效能高、適合大量資料)、非對稱加密(金鑰管理彈性、適合金鑰交換與數位簽章)、雜湊函數(單向、驗證完整性)。.NET Framework 在 System.Security.Cryptography 命名空間提供完整實作,本文系統梳理演算法選型、程式碼範例與落地陷阱。
| 類別 | 演算法 | 特性 | 推薦場景 |
|---|---|---|---|
| 對稱加密 | AES (Rijndael) | 區塊 128-bit,金鑰 128/192/256-bit,速度快、安全性高 | 現代應用首選,資料庫欄位加密、API Token 加密 |
| 3DES | 三重 DES,相容舊系統,速度較慢 | 舊系統遷移過渡期 | |
| DES | 56-bit 金鑰,已不安全 | 嚴禁新專案使用 | |
| RC2/RC4 | 串流加密,RC4 已知弱點 | 不推薦 | |
| Blowfish/Twofish | 非標準,需第三方庫 | 特殊相容需求 | |
| 非對稱加密 | RSA | 金鑰 1024~4096-bit,加密慢、簽章驗證快 | 金鑰交換、數位簽章、JWT 簽名 |
| DSA/ECDSA | 僅簽章,ECDSA 金鑰更短效能更好 | 區塊鏈、憑證簽章 | |
| ECC | 橢圓曲線,同等安全性金鑰極短 | 行動裝置、物聯網 | |
| 雜湊/完整性 | SHA-256/384/512 | SHA-2 家族,目前標準 | 密碼雜湊(配合 Salt)、檔案完整性、區塊鏈 |
| HMAC-SHA256 | 帶金鑰雜湊,防範長度擴展攻擊 | API 簽名驗證、Token 完整性 | |
| MD5/SHA1 | 已知碰撞弱點 | 嚴禁安全用途,僅限非安全校驗(如快取 Key) | |
| BCrypt/PBKDF2/Argon2 | 慢速雜湊,專為密碼設計 | 儲存使用者密碼唯一正解 |
AesManaged、TripleDESCryptoServiceProviderRSACryptoServiceProvider、DSACryptoServiceProvider、ECDsaCng (.NET Core 3.0+)SHA256Managed、HMACSHA256、MD5CryptoServiceProvider(僅相容)Rfc2898DeriveBytes (PBKDF2)、ASP.NET Core 內建 IPasswordHasher<TUser> (BCrypt/PBKDF2)RandomNumberGenerator (CSPRNG),嚴禁 使用 System.Randompublic static (byte[] ciphertext, byte[] nonce, byte[] tag) EncryptAesGcm(byte[] plaintext, byte[] key) {
using var aes = new AesGcm(key);
var nonce = RandomNumberGenerator.GetBytes(12); // 96-bit nonce
var tag = new byte[16];
var ciphertext = new byte[plaintext.Length];
aes.Encrypt(nonce, plaintext, ciphertext, tag);
return (ciphertext, nonce, tag);
}
public static byte[] DecryptAesGcm(byte[] ciphertext, byte[] nonce, byte[] tag, byte[] key) {
using var aes = new AesGcm(key);
var plaintext = new byte[ciphertext.Length];
aes.Decrypt(nonce, ciphertext, tag, plaintext);
return plaintext;
}
// 加密(公開金鑰)
public static byte[] RsaEncrypt(byte[] data, RSA publicKey) {
return publicKey.Encrypt(data, RSAEncryptionPadding.OaepSHA256);
}
// 解密(私有金鑰)
public static byte[] RsaDecrypt(byte[] ciphertext, RSA privateKey) {
return privateKey.Decrypt(ciphertext, RSAEncryptionPadding.OaepSHA256);
}
// 簽章/驗簽
public static byte[] RsaSign(byte[] data, RSA privateKey) {
return privateKey.SignData(data, HashAlgorithmName.SHA256, RSASignaturePadding.Pkcs1);
}
public static bool RsaVerify(byte[] data, byte[] signature, RSA publicKey) {
return publicKey.VerifyData(data, signature, HashAlgorithmName.SHA256, RSASignaturePadding.Pkcs1);
}
// PBKDF2 範例(.NET Framework 內建)
public static (string hash, string salt) HashPasswordPbkdf2(string password, int iterations = 100_000) {
var salt = RandomNumberGenerator.GetBytes(16);
using var pbkdf2 = new Rfc2898DeriveBytes(password, salt, iterations, HashAlgorithmName.SHA256);
var hash = pbkdf2.GetBytes(32);
return (Convert.ToBase64String(hash), Convert.ToBase64String(salt));
}
public static bool VerifyPasswordPbkdf2(string password, string hashB64, string saltB64, int iterations = 100_000) {
var hash = Convert.FromBase64String(hashB64);
var salt = Convert.FromBase64String(saltB64);
using var pbkdf2 = new Rfc2898DeriveBytes(password, salt, iterations, HashAlgorithmName.SHA256);
var computed = pbkdf2.GetBytes(32);
return CryptographicOperations.FixedTimeEquals(hash, computed);
}
// ASP.NET Core 專案直接使用內建服務
// services.AddIdentityCore<User>().AddPasswordHasher<PasswordHasher<User>>();
// var hasher = new PasswordHasher<User>();
// var hash = hasher.HashPassword(user, password);
// var result = hasher.VerifyHashedPassword(user, hash, password);
// 加密端
string encrypted = Convert.ToBase64String(Encoding.UTF8.GetBytes("sensitive_id=123"));
string urlSafe = HttpUtility.UrlEncode(encrypted); // 將 + / = 轉義
Response.Redirect($"Target.aspx?token={urlSafe}");
// 解密端
string token = HttpUtility.UrlDecode(Request.QueryString["token"]);
string decrypted = Encoding.UTF8.GetString(Convert.FromBase64String(token));
appsettings.json(生產環境加密)。CryptographicOperations.FixedTimeEquals。FormsAuthentication.HashPasswordForStoringInConfigFile → IPasswordHasher (BCrypt/PBKDF2)DES/3DES/RC2 → AES-GCMMD5/SHA1 → SHA-256/HMAC-SHA256RSACryptoServiceProvider (CAPI) → RSA (CNG) / ECDsaMicrosoft.AspNetCore.DataProtection 統一管理金鑰輪換、用途隔離加密不是買一套庫就能「設定後忘記」的功能,而是包含金鑰生命週期、演算法治理、事件響應的系統工程。建議團隊建立密碼學策略文件,明確各資料類型的保護等級、演算法、金鑰輪換週期與事故處理流程,並納入程式碼審查與滲透測試範圍。安全是成本,但洩露是毀滅性打擊——投資正確的加密架構,永遠划算。