This article is about to encrypt and decrypt a string value. I have created the following class to encrypt the password and save in database. This class provides 3 methods as bellow:
1. CreateSalt(): This generates a salt key to encrypt the string value.2. Encrypt(string plainText, string saltKey): This method Encrypts the string value with passed saltKey. You can generate a salt key using "CreateSalt()" method.
3. Decrypt(string cipherText, string saltKey): This method Decrypts the encrypted string value with passed saltKey. You have to use the same salKey, that you have used to encrypt the string value.
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Security.Cryptography;
using System.Text;
using System.Web;
namespace YOUR_NAMESPACE
{
public class CryptoUtils
{
private const CipherMode cipherMode = CipherMode.CBC;
private const PaddingMode paddingMode = PaddingMode.ISO10126;
private const string defaultVector = "fdsah123456789";
private const int iterations = 2;
public static string CreateSalt()
{
//Generate a cryptographic random number.
RNGCryptoServiceProvider rng = new RNGCryptoServiceProvider();
byte[] buff = new byte[20];
rng.GetBytes(buff);
// Return a Base64 string representation of the random number.
return Convert.ToBase64String(buff);
}
/// <summary>
/// To encrypt the plain text. This produces the different encrypted text for same string everytime.
/// </summary>
/// <param name="plainText">String value to encrypt</param>
/// <returns></returns>
public static string Encrypt(string plainText, string saltKey)
{
byte[] clearData = Encoding.Unicode.GetBytes(plainText);
byte[] encryptedData;
var crypt = GetCrypto(saltKey);
using (var ms = new MemoryStream())
{
using (var cs = new CryptoStream(ms, crypt.CreateEncryptor(), CryptoStreamMode.Write))
{
cs.Write(clearData, 0, clearData.Length);
//cs.FlushFinalBlock(); //Have tried this active and commented with no change.
}
encryptedData = ms.ToArray();
}
//Changed per Xint0's answer.
return Convert.ToBase64String(encryptedData);
}
public static string Decrypt(string cipherText, string saltKey)
{
//Changed per Xint0's answer.
if (!String.IsNullOrEmpty(cipherText))
{
byte[] encryptedData = Convert.FromBase64String(cipherText);
byte[] clearData;
var crypt = GetCrypto(saltKey);
using (var ms = new MemoryStream())
{
using (var cs = new CryptoStream(ms, crypt.CreateDecryptor(), CryptoStreamMode.Write))
{
cs.Write(encryptedData, 0, encryptedData.Length);
//I have tried adding a cs.FlushFinalBlock(); here as well.
}
clearData = ms.ToArray();
}
return Encoding.Unicode.GetString(clearData);
}
else
{
return null;
}
}
private static Rijndael GetCrypto(string passphrase)
{
var crypt = Rijndael.Create();
crypt.Mode = cipherMode;
crypt.Padding = paddingMode;
crypt.BlockSize = 256;
crypt.KeySize = 256;
crypt.Key = new Rfc2898DeriveBytes(passphrase, Encoding.Unicode.GetBytes(defaultVector), iterations).GetBytes(32);
crypt.IV = new Rfc2898DeriveBytes(passphrase, Encoding.Unicode.GetBytes(defaultVector), iterations).GetBytes(32);
return crypt;
}
}
}
Usage: Use the above class methods as following:
var saltKey = CryptoUtils.CreateSalt();var encryptedData = CryptoUtils.Encrypt("User@12345!@#", saltKey);
var decryptedData = CryptoUtils.Decrypt(encryptedData, saltKey);
Thanks for appreciate. Sure I will try your tool and will recommend to people in such requirements.
ReplyDelete