怎樣用ASP.NET加密Cookie數(shù)據(jù)?

Cookie確實(shí)在WEB應(yīng)用方面為訪問(wèn)者和編程者都提供了方便,但是也許你并不留意這些數(shù)據(jù),不過(guò)我們可以按下列方法查看Cookie數(shù)據(jù):打開(kāi)IE,選擇“工具”菜單里的“Internet選項(xiàng)”,然后在彈出的對(duì)話框里點(diǎn)擊“設(shè)置”按鈕,在設(shè)置對(duì)話框里點(diǎn)擊“查看”鈕,就會(huì)打開(kāi)一個(gè)窗口顯示瀏覽器放在硬盤里的所有緩存數(shù)據(jù),其中就有大量的Cookie文件。但是還是建議大家重要的數(shù)據(jù)不要保存在這里面,這樣很容易被人看到,有被竊取的可能性。但是我們可以對(duì)這些Cookie數(shù)據(jù)進(jìn)行加密,我們可以利用ASP.NET對(duì)Cookie數(shù)據(jù)進(jìn)行加密。

一、.NET的概要

簡(jiǎn)單講,加密就是將原始字符(字節(jié))串轉(zhuǎn)變?yōu)橥耆煌淖址奶幚磉^(guò)程,達(dá)到原始字符無(wú)法破譯的目的。這個(gè)處理過(guò)程是用另一個(gè)字符串(稱為“密鑰”),采取復(fù)雜的、混合的算法,“搗進(jìn)”原始字符串。有時(shí)還使用一個(gè)稱為“初始向量”的字符串,在密鑰搗進(jìn)之前先打亂目標(biāo)字符串,預(yù)防目標(biāo)字符串中較明顯的內(nèi)容被識(shí)破。加密的功效取決于所用密鑰的大小,密鑰越長(zhǎng),保密性越強(qiáng)。

目前有兩種加密方法:對(duì)稱加密(或稱私有密鑰)和非對(duì)稱加密(或稱公共密鑰)。對(duì)稱加密技術(shù)的數(shù)據(jù)交換兩邊(即加密方和解密方)必須使用一個(gè)保密的私有密鑰。非對(duì)稱加密技術(shù)中,解密方向加密方要求一個(gè)公共密鑰,加密方在建立一個(gè)公共密鑰給解密方后,用公共密鑰創(chuàng)建唯一的私有密鑰。加密方用私有密鑰加密送出的信息,對(duì)方用公共密鑰解密。保護(hù)HTTP傳輸安全的SSL就是使用非對(duì)稱技術(shù)。

我們對(duì)Cookie數(shù)據(jù)的加密采取對(duì)稱加密法。.NET構(gòu)架從基本的SymmetricAlgorithm類擴(kuò)展出來(lái)四種算法:

  • System.Security.Cryptography.DES
  • System.Security.Cryptography.TripleDES
  • System.Security.Cryptography.RC2
  • System.Security.Cryptography.Rijndael

下面將示范DES和TripleDES算法。DES的密鑰大小限制在64位,但用于Cookie的加密是有效的。TripleDES完成了三次加密,并有一個(gè)較大的密鑰位數(shù),所以它更安全。使用那一種算法不僅要考慮加密強(qiáng)度,還要考慮Cookie的大小。因?yàn)榧用芎蟮腃ookie數(shù)據(jù)將變大,并且,密鑰越大,加密后的數(shù)據(jù)就越大,然而Cookie數(shù)據(jù)的大小限制在4KB,這是一個(gè)必須考慮的問(wèn)題。再者,加密的數(shù)據(jù)越多或算法越復(fù)雜,就會(huì)占有更多的服務(wù)器資源,進(jìn)而減慢整個(gè)站點(diǎn)的訪問(wèn)速度。

二、創(chuàng)建一個(gè)簡(jiǎn)單的加密應(yīng)用類

.NET的所有加密和解密通過(guò)CryptoStream類別來(lái)處理,它衍生自System.IO.Stream,將字符串作為以資料流為基礎(chǔ)的模型,供加密轉(zhuǎn)換之用。下面是一個(gè)簡(jiǎn)單的加密應(yīng)用類的代碼:

Imports System.Diagnostics

Imports System.Security.Cryptography

Imports System.Text

Imports System.IO

Public Class CryptoUtil

'隨機(jī)選8個(gè)字節(jié)既為密鑰也為初始向量

Private Shared KEY_64() As Byte = {42, 16, 93, 156, 78, 4, 218, 32}

Private Shared IV_64() As Byte = {55, 103, 246, 79, 36, 99, 167, 3}

'對(duì)TripleDES,采取24字節(jié)或192位的密鑰和初始向量

Private Shared KEY_192() As Byte = {42, 16, 93, 156, 78, 4, 218, 32, _

15, 167, 44, 80, 26, 250, 155, 112, _

2, 94, 11, 204, 119, 35, 184, 197}

Private Shared IV_192() As Byte = {55, 103, 246, 79, 36, 99, 167, 3, _

42, 5, 62, 83, 184, 7, 209, 13, _

145, 23, 200, 58, 173, 10, 121, 222}

'標(biāo)準(zhǔn)的DES加密

Public Shared Function Encrypt(ByVal value As String) As String

If value <> "" Then

Dim cryptoProvider As DESCryptoServiceProvider = _

New DESCryptoServiceProvider()

Dim ms As MemoryStream = New MemoryStream()

Dim cs As CryptoStream = _

New CryptoStream(ms, cryptoProvider.CreateEncryptor(KEY_64, IV_64), _

CryptoStreamMode.Write)

Dim sw As StreamWriter = New StreamWriter(cs)

sw.Write(value)

sw.Flush()

cs.FlushFinalBlock()

ms.Flush()

'再轉(zhuǎn)換為一個(gè)字符串

Return Convert.ToBase64String(ms.GetBuffer(), 0, ms.Length)

End If

End Function

'標(biāo)準(zhǔn)的DES解密

Public Shared Function Decrypt(ByVal value As String) As String

If value <> "" Then

Dim cryptoProvider As DESCryptoServiceProvider = _

New DESCryptoServiceProvider()

'從字符串轉(zhuǎn)換為字節(jié)組

Dim buffer As Byte() = Convert.FromBase64String(value)

Dim ms As MemoryStream = New MemoryStream(buffer)

Dim cs As CryptoStream = _

New CryptoStream(ms, cryptoProvider.CreateDecryptor(KEY_64, IV_64), _

CryptoStreamMode.Read)

Dim sr As StreamReader = New StreamReader(cs)

Return sr.ReadToEnd()

End If

End Function

'TRIPLE DES加密

Public Shared Function EncryptTripleDES(ByVal value As String) As String

If value <> "" Then

Dim cryptoProvider As TripleDESCryptoServiceProvider = _

New TripleDESCryptoServiceProvider()

Dim ms As MemoryStream = New MemoryStream()

Dim cs As CryptoStream = _

New CryptoStream(ms, cryptoProvider.CreateEncryptor(KEY_192, IV_192), _

CryptoStreamMode.Write)

Dim sw As StreamWriter = New StreamWriter(cs)

sw.Write(value)

sw.Flush()

cs.FlushFinalBlock()

ms.Flush()

'再轉(zhuǎn)換為一個(gè)字符串

Return Convert.ToBase64String(ms.GetBuffer(), 0, ms.Length)

End If

End Function

'TRIPLE DES解密

Public Shared Function DecryptTripleDES(ByVal value As String) As String

If value <> "" Then

Dim cryptoProvider As TripleDESCryptoServiceProvider = _

New TripleDESCryptoServiceProvider()

'從字符串轉(zhuǎn)換為字節(jié)組

Dim buffer As Byte() = Convert.FromBase64String(value)

Dim ms As MemoryStream = New MemoryStream(buffer)

Dim cs As CryptoStream = _

New CryptoStream(ms, cryptoProvider.CreateDecryptor(KEY_192, IV_192), _

CryptoStreamMode.Read)

Dim sr As StreamReader = New StreamReader(cs)

Return sr.ReadToEnd()

End If

End Function

End Class

上面我們將一組字節(jié)初始化為密鑰,并且使用的是數(shù)字常量,如果你在實(shí)際應(yīng)用中也這樣做,這些字節(jié)一定要在0和255之間,這是一個(gè)字節(jié)允許的范圍值。

三、創(chuàng)建一個(gè)Cookie的應(yīng)用類

下面我們就創(chuàng)建一個(gè)簡(jiǎn)單的類,來(lái)設(shè)置和獲取Cookies。

Public Class CookieUtil

'設(shè)置COOKIE *****************************************************

'SetTripleDESEncryptedCookie (只針對(duì)密鑰和Cookie數(shù)據(jù))

Public Shared Sub SetTripleDESEncryptedCookie(ByVal key As String, _

ByVal value As String)

key = CryptoUtil.EncryptTripleDES(key)

value = CryptoUtil.EncryptTripleDES(value)

SetCookie(key, value)

End Sub

'SetTripleDESEncryptedCookie (增加了Cookie數(shù)據(jù)的有效期參數(shù))

Public Shared Sub SetTripleDESEncryptedCookie(ByVal key As String, _

ByVal value As String, ByVal expires As Date)

key = CryptoUtil.EncryptTripleDES(key)

value = CryptoUtil.EncryptTripleDES(value)

SetCookie(key, value, expires)

End Sub

'SetEncryptedCookie(只針對(duì)密鑰和Cookie數(shù)據(jù))

Public Shared Sub SetEncryptedCookie(ByVal key As String, _

ByVal value As String)

key = CryptoUtil.Encrypt(key)

value = CryptoUtil.Encrypt(value)

SetCookie(key, value)

End Sub

'SetEncryptedCookie (增加了Cookie數(shù)據(jù)的有效期參數(shù))

Public Shared Sub SetEncryptedCookie(ByVal key As String, _

ByVal value As String, ByVal expires As Date)

key = CryptoUtil.Encrypt(key)

value = CryptoUtil.Encrypt(value)

SetCookie(key, value, expires)

End Sub

'SetCookie (只針對(duì)密鑰和Cookie數(shù)據(jù))

Public Shared Sub SetCookie(ByVal key As String, ByVal value As String)

'編碼部分

key = HttpContext.Current.Server.UrlEncode(key)

value = HttpContext.Current.Server.UrlEncode(value)

Dim cookie As HttpCookie

cookie = New HttpCookie(key, value)

SetCookie(cookie)

End Sub

'SetCookie(增加了Cookie數(shù)據(jù)的有效期參數(shù))

Public Shared Sub SetCookie(ByVal key As String, _

ByVal value As String, ByVal expires As Date)

'編碼部分

key = HttpContext.Current.Server.UrlEncode(key)

value = HttpContext.Current.Server.UrlEncode(value)

Dim cookie As HttpCookie

cookie = New HttpCookie(key, value)

cookie.Expires = expires

SetCookie(cookie)

End Sub

'SetCookie (只針對(duì)HttpCookie)

Public Shared Sub SetCookie(ByVal cookie As HttpCookie)

HttpContext.Current.Response.Cookies.Set(cookie)

End Sub

'獲取COOKIE *****************************************************

Public Shared Function GetTripleDESEncryptedCookieValue(ByVal key As String) _

As String

'只對(duì)密鑰加密

key = CryptoUtil.EncryptTripleDES(key)

'獲取Cookie值

Dim value As String

value = GetCookieValue(key)

'解密Cookie值

value = CryptoUtil.DecryptTripleDES(value)

Return value

End Function

Public Shared Function GetEncryptedCookieValue(ByVal key As String) As String

'只對(duì)密鑰加密

key = CryptoUtil.Encrypt(key)

'獲取Cookie值

Dim value As String

value = GetCookieValue(key)

'解密Cookie值

value = CryptoUtil.Decrypt(value)

Return value

End Function

Public Shared Function GetCookie(ByVal key As String) As HttpCookie

'編碼密鑰

key = HttpContext.Current.Server.UrlEncode(key)

Return HttpContext.Current.Request.Cookies.Get(key)

End Function

Public Shared Function GetCookieValue(ByVal key As String) As String

Try

'編碼在GetCookie里完成

'獲取Cookie值

Dim value As String

value = GetCookie(key).Value

'解碼所存儲(chǔ)的值

value = HttpContext.Current.Server.UrlDecode(value)

Return value

Catch

End Try

End Function

End Class

對(duì)Cookie數(shù)據(jù)進(jìn)行加密后,我們就可以在方便使用的同時(shí)增強(qiáng)文件的安全性!這樣我們也不會(huì)擔(dān)心自己的有關(guān)網(wǎng)頁(yè),密碼和其他用用戶信息被竊取。