65.9K
CodeProject is changing. Read more.
Home

Query string encryption for ASP.NET

starIconstarIconstarIcon
emptyStarIcon
starIcon
emptyStarIcon

3.90/5 (28 votes)

Apr 30, 2008

CPOL

2 min read

viewsIcon

252659

downloadIcon

4219

Clear text query strings are a potential security threat for your web application. Thus, query strings should always be encrypted.

Introduction

Using query strings to send data from the browser to the server is a widespread approach. Giving the visitor of a web application the opportunity of modifying query strings by transmitting them in clear text, is certainly a potential security threat.

Thus, I encourage developers to encrypt query strings, even if they do not contain confidential data. However, I am aware that it is still possible to alternate an encrypted query string, but with an appropriate exception handling, this is harmless.

Background

To keep this article simple, I used a contradictable encryption (DES encoding), though any cutting-edge encryption can be easily applied to the samples given.

Using the code

So, let's get down to business. The main part of the presented solution consists of a HttpModule which decrypts the query string and hence provides the page request with the ordinary unencrypted query strings:

 using System; using System.Web; using System.Web.Configuration; namespace HelveticSolutions.QueryStringEncryption { /// <summary> /// Http module that handles encrypted query strings. /// </summary> public class CryptoQueryStringUrlRemapper : IHttpModule { #region IHttpModule Members /// <summary> /// Initialize the http module. /// </summary> /// <param name="application">Application, /// that called this module.</param> public void Init(HttpApplication application) { // Attach the acquire request state event // to catch the encrypted query string application.AcquireRequestState += application_AcquireRequestState; } public void Dispose() {} #endregion /// <summary> /// Event, that is called when the application acquires the request state. /// </summary> /// <param name="sender"></param> /// <param name="e"></param> public void application_AcquireRequestState(object sender, EventArgs e) { // Get http context from the caller. HttpApplication application = (HttpApplication) sender; HttpContext context = application.Context; // Check for encrypted query string string encryptedQueryString = context.Request.QueryString["request"]; if (!string.IsNullOrEmpty(encryptedQueryString)) { // Decrypt query strings string cryptoKey = WebConfigurationManager.AppSettings["CryptoKey"]; string decryptedQueryString = CryptoQueryStringHandler.DecryptQueryStrings(encryptedQueryString, cryptoKey); context.Server.Transfer( context.Request.AppRelativeCurrentExecutionFilePath + "?" + decryptedQueryString); } } } }

As you might have noticed, if there is an encrypted query string for the current request, the module automatically terminates the execution of the current page and internally starts execution of a new request on the server.

The next step is to register the HttpModule in the web.config file:

 <httpModules> <add name="CryptoQueryStringUrlRemapper" type="HelveticSolutions.QueryStringEncryption.CryptoQueryStringUrlRemapper"/> </httpModules>

Last but not least, do not forget to encrypt query strings before sending them back to the server:

 private void PrepareSendButton() { NameValueCollection queryStrings = new NameValueCollection(); queryStrings.Add("param1", "Test1"); queryStrings.Add("param2", "Test2"); queryStrings.Add("param3", "Test3"); // Encrypt query strings string encryptedString = CryptoQueryStringHandler.EncryptQueryStrings( queryStrings, WebConfigurationManager.AppSettings["CryptoKey"]); btnSendParams.PostBackUrl = string.Concat("~/Default.aspx?", encryptedString); }

As outlined earlier in this article, the encryption class can be easily replaced by any other encryption class. A full running sample can be downloaded above.

Important issue

The method DecryptQueryStrings in the CryptoQueryStringHandler contains the following line :

 return Encryption64.Decrypt(encryptedStrings.Replace(" ", "+"), key); 

For unknown reasons, the request replaces every '+' character in the query with an empty character.

History

  • 30.04.2008 - First version (deleted -> was not possible to modify, why ever...).
  • 01.05.2008 - Re-released updated article.
  • 08.05.2008 - BeginRequest event in the HttpModule changed to AcquireRequestState in order to support Session data.
  • 11th November 2014 - Namespace corrected
close