The encryption and decryption of query string is often encountered in the project. If the query string is processed on the page or page base, it is always a bit uncomfortable.
So I recently tried to use httpmodule. I have seen several articles on the Internet. After combining these articles, I solved the problem of PostBack encrypted URL loss.
Environment Asp.net 2.0
Updated on:
Someone said no downstairs. I tried it. The test may not be complete. If any error is found, please send me the use case code. Thank you!
My testing package code/files/beyondjay/websitehttpmodule.zip
Httpmodule:
# Region using
Using system;
Using system. IO;
Using system. Web;
Using system. text;
Using system. Security. cryptography;
# Endregion
/// <Summary>
/// Summary description for querystringmodule
/// </Summary>
Public class querystringmodule: ihttpmodule
{
# Region ihttpmodule members
Public void dispose ()
{
// Nothing to dispose
}
Public void Init (httpapplication context)
{
Context. beginrequest + = new eventhandler (context_beginrequest );
}
# Endregion
Private const string parameter_name = "ENC = ";
Private const string encryption_key = "key ";
Void context_beginrequest (Object sender, eventargs E)
{
Httpcontext context = httpcontext. Current;
If (context. Request. url. originalstring. Contains ("aspx") & context. Request. rawurl. Contains ("? "))
{
String query = extractquery (context. Request. url. tostring ());
String Path = getvirtualpath ();
If (query. startswith (parameter_name, stringcomparison. ordinalignorecase ))
{
// Decrypts the query string and rewrites the path.
Context. items ["originalurl"] = context. Request. url. tostring ();
String rawquery = query. Replace (parameter_name, String. Empty );
String decryptedquery = decrypt (rawquery );
Context. rewritepath (path, String. Empty, decryptedquery );
}
Else if (context. Request. httpmethod = "get ")
{
// Encrypt the query string and redirects to the encrypted URL.
// Remove if you don't want all query strings to be encrypted automatically.
String encryptedquery = encrypt (query );
Context. items ["originalurl"] = path + encryptedquery;
Context. response. Redirect (path + encryptedquery );
}
}
}
/// <Summary>
/// Parses the current URL and extracts the virtual path without query string.
/// </Summary>
/// <Returns> the virtual path of the current URL. </returns>
Private Static string getvirtualpath ()
{
String Path = httpcontext. Current. Request. rawurl;
Path = path. substring (0, path. indexof ("? "));
Path = path. substring (path. lastindexof ("/") + 1 );
Return path;
}
/// <Summary>
/// Parses a URL and returns the query string.
/// </Summary>
/// <Param name = "url"> the URL to parse. </param>
/// <Returns> the query string without the question mark. </returns>
Private Static string extractquery (string URL)
{
Int Index = URL. indexof ("? ") + 1;
Return URL. substring (INDEX );
}
# Region encryption/Decryption
/// <Summary>
/// The salt value used to strengthen the encryption.
/// </Summary>
Private readonly static byte [] salt = encoding. ASCII. getbytes (encryption_key.length.tostring ());
/// <Summary>
/// Encrypts any string using the Rijndael algorithm.
/// </Summary>
/// <Param name = "inputtext"> the string to encrypt. </param>
/// <Returns> A base64 encrypted string. </returns>
Public static string encrypt (string inputtext)
{
Rijndaelmanaged rijndaelcipher = new rijndaelmanaged ();
Byte [] plaintext = encoding. Unicode. getbytes (inputtext );
Passwordderivebytes secretkey = new passwordderivebytes (encryption_key, salt );
Using (icryptotransform encryptor = rijndaelcipher. createencryptor (secretkey. getbytes (32), secretkey. getbytes (16 )))
{
Using (memorystream = new memorystream ())
{
Using (cryptostream = new cryptostream (memorystream, encryptor, cryptostreammode. Write ))
{
Cryptostream. Write (plaintext, 0, plaintext. Length );
Cryptostream. flushfinalblock ();
Return "? "+ Parameter_name + convert. tobase64string (memorystream. toarray ());
}
}
}
}
/// <Summary>
/// Decrypts A previusly encrypted string.
/// </Summary>
/// <Param name = "inputtext"> the encrypted string to decrypt. </param>
/// <Returns> A decrypted string. </returns>
Public static string decrypt (string inputtext)
{
Rijndaelmanaged rijndaelcipher = new rijndaelmanaged ();
Byte [] encrypteddata = convert. frombase64string (inputtext );
Passwordderivebytes secretkey = new passwordderivebytes (encryption_key, salt );
Using (icryptotransform decryptor = rijndaelcipher. createdecryptor (secretkey. getbytes (32), secretkey. getbytes (16 )))
{
Using (memorystream = new memorystream (encrypteddata ))
{
Using (cryptostream = new cryptostream (memorystream, decryptor, cryptostreammode. Read ))
{
Byte [] plaintext = new byte [encrypteddata. Length];
Int decryptedcount = cryptostream. Read (plaintext, 0, plaintext. Length );
Return encoding. Unicode. getstring (plaintext, 0, decryptedcount );
}
}
}
}
# Endregion
}
Pagebase: You need to inherit this pagebase
Public class pagebase: Page
{
Protected override void onloadcomplete (eventargs E)
{
String originalurl = context. items ["originalurl"] as string;
If (! String. isnullorempty (originalurl) // so this page have been urlrewriten, after the page onloaded, rewrite the URL of this page to original URL
{
String query = string. empty;
Int Pos = originalurl. indexof ('? ');
If (Pos> = 0) // check if has query paramet
Query = originalurl. substring (Pos + 1 );
// Originalurl = originalurl. substring (0, POS );
Context. rewritepath (querystringmodule. getvirtualpath (), String. Empty, query );
}
Base. onloadcomplete (E );
}
}
Reference
Http://msdn.microsoft.com/en-us/library/ms972974.aspx
Http://www.webpronews.com/expertarticles/2007/01/25/aspnet-httpmodule-for-query-string-encryption