<?xml version='1.0' encoding='UTF-8'?><?xml-stylesheet href="http://www.blogger.com/styles/atom.css" type="text/css"?><feed xmlns='http://www.w3.org/2005/Atom' xmlns:openSearch='http://a9.com/-/spec/opensearchrss/1.0/' xmlns:georss='http://www.georss.org/georss' xmlns:gd='http://schemas.google.com/g/2005' xmlns:thr='http://purl.org/syndication/thread/1.0'><id>tag:blogger.com,1999:blog-8322079459489742719</id><updated>2011-07-08T10:42:12.263-04:00</updated><category term='Code'/><category term='Web Development'/><category term='Tips'/><category term='Security'/><category term='ASP.NET'/><category term='.NET'/><title type='text'>The WebShift Software Blog</title><subtitle type='html'></subtitle><link rel='http://schemas.google.com/g/2005#feed' type='application/atom+xml' href='http://webshiftsoftware.blogspot.com/feeds/posts/default'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/8322079459489742719/posts/default?max-results=100'/><link rel='alternate' type='text/html' href='http://webshiftsoftware.blogspot.com/'/><link rel='hub' href='http://pubsubhubbub.appspot.com/'/><author><name>Jeremy Burman</name><uri>http://www.blogger.com/profile/10664616950976186217</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><generator version='7.00' uri='http://www.blogger.com'>Blogger</generator><openSearch:totalResults>3</openSearch:totalResults><openSearch:startIndex>1</openSearch:startIndex><openSearch:itemsPerPage>100</openSearch:itemsPerPage><entry><id>tag:blogger.com,1999:blog-8322079459489742719.post-3921213345094242085</id><published>2009-11-26T13:59:00.004-05:00</published><updated>2009-11-26T14:36:57.899-05:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='.NET'/><category scheme='http://www.blogger.com/atom/ns#' term='Tips'/><category scheme='http://www.blogger.com/atom/ns#' term='Code'/><title type='text'>Quick Start: Using MSBuild to re-target project output</title><content type='html'>I often find it useful to build many .NET projects from one master build script and then copy their output to a central folder.  It is then easier to perform additional processing on the DLLs.  While the concept is straight forward, I haven't seen many examples for doing this, so I'm posting a complete MSBuild script that demonstrates the technique in action.&lt;div&gt;&lt;div&gt;&lt;br /&gt;&lt;/div&gt;&lt;/div&gt;&lt;br /&gt;&lt;div style="background-color: #efefef;"&gt;&lt;br /&gt;&lt;pre&gt;&lt;br /&gt;&amp;lt;Project ToolsVersion="3.5" DefaultTargets="Build" xmlns="http://schemas.microsoft.com/developer/msbuild/2003" &amp;gt;&lt;br /&gt;    &amp;lt;PropertyGroup&amp;gt;&lt;br /&gt;        &amp;lt;OutputTargetDir&amp;gt;Output&amp;lt;/OutputTargetDir&amp;gt;&lt;br /&gt;    &amp;lt;/PropertyGroup&amp;gt;&lt;br /&gt;    &amp;lt;ItemGroup&amp;gt;&lt;br /&gt;        &amp;lt;ProjectFile Include="PathToProjectA\MyProjA.csproj"/&amp;gt;&lt;br /&gt;        &amp;lt;ProjectFile Include="PathToProjectB\MyProjB.csproj"/&amp;gt;&lt;br /&gt;    &amp;lt;/ItemGroup&amp;gt;&lt;br /&gt;    &amp;lt;Target Name="Build"&amp;gt;&lt;br /&gt;        &amp;lt;Message Text="Building: @(ProjectFile, ', ')" /&amp;gt;&lt;br /&gt;&lt;br /&gt;        &amp;lt;MakeDir Directories="$(OutputTargetDir)" Condition="!Exists($(OutputTargetDir))" /&amp;gt;&lt;br /&gt;&lt;br /&gt;        &amp;lt;!-- Build projects and copy output to target directory --&amp;gt;&lt;br /&gt;        &amp;lt;MSBuild&lt;br /&gt;            Projects="@(ProjectFile)"&lt;br /&gt;            Targets="Build"&amp;gt;&lt;br /&gt;            &amp;lt;Output&lt;br /&gt;                TaskParameter="TargetOutputs"&lt;br /&gt;                ItemName="PrimaryBuildOutput" /&amp;gt;&lt;br /&gt;        &amp;lt;/MSBuild&amp;gt;&lt;br /&gt;        &amp;lt;Copy SourceFiles="@(PrimaryBuildOutput)" DestinationFolder="$(OutputTargetDir)" SkipUnchangedFiles="true" /&amp;gt;&lt;br /&gt;&lt;br /&gt;        &amp;lt;!-- Find built project dependencies and copy to target directory --&amp;gt;&lt;br /&gt;        &amp;lt;ResolveAssemblyReference AssemblyFiles="@(PrimaryBuildOutput)" SearchPaths="{HintPathFromItem}"&amp;gt;&lt;br /&gt;            &amp;lt;Output TaskParameter="ResolvedDependencyFiles"&lt;br /&gt;                ItemName="BuiltProjectDependencies" /&amp;gt;&lt;br /&gt;        &amp;lt;/ResolveAssemblyReference&amp;gt;&lt;br /&gt;        &lt;br /&gt;        &amp;lt;Copy SourceFiles="@(BuiltProjectDependencies)" DestinationFolder="$(OutputTargetDir)" SkipUnchangedFiles="true" /&amp;gt;&lt;br /&gt;    &amp;lt;/Target&amp;gt;&lt;br /&gt;&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;/div&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/8322079459489742719-3921213345094242085?l=webshiftsoftware.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webshiftsoftware.blogspot.com/feeds/3921213345094242085/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=8322079459489742719&amp;postID=3921213345094242085' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/8322079459489742719/posts/default/3921213345094242085'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/8322079459489742719/posts/default/3921213345094242085'/><link rel='alternate' type='text/html' href='http://webshiftsoftware.blogspot.com/2009/11/quick-start-using-msbuild-to-re-target.html' title='Quick Start: Using MSBuild to re-target project output'/><author><name>Jeremy Burman</name><uri>http://www.blogger.com/profile/10664616950976186217</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-8322079459489742719.post-1831370086780209435</id><published>2009-11-23T11:52:00.006-05:00</published><updated>2009-11-23T12:09:39.066-05:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Security'/><category scheme='http://www.blogger.com/atom/ns#' term='Web Development'/><category scheme='http://www.blogger.com/atom/ns#' term='Tips'/><title type='text'>From Users to Developers - Avoiding Web-Based Computer Security Vulnerabilities</title><content type='html'>&lt;p  style="color: rgb(0, 0, 0);font-family:arial;"&gt;&lt;span style="font-size:100%;"&gt;The proliferation of browser platforms and technology available on the web has allowed not only rapid advances in what may be accomplished in web sites but it has also given malicious users new ways to carry out attacks.&lt;span&gt;  &lt;/span&gt;This article covers the most common attacks that are utilized in today's browser platforms and how you can protect yourself from these attacks as both a user of the web and as a web site developer.&lt;/span&gt;&lt;span style="font-size:100%;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;/p&gt;&lt;span style="color: rgb(0, 0, 0);font-family:arial,helvetica,sans-serif;font-size:100%;"  &gt;The vulnerabilities discussed are&lt;/span&gt;&lt;span style="color: rgb(0, 0, 0);font-family:arial;font-size:100%;"  &gt;&lt;br /&gt;&lt;/span&gt; &lt;ul  style="color: rgb(0, 0, 0);font-family:arial;"&gt;&lt;li&gt;&lt;span style="font-size:100%;"&gt;Cross-site scripting (or XSS) attacks&lt;/span&gt;&lt;/li&gt;&lt;span style="font-size:100%;"&gt;&lt;br /&gt;&lt;/span&gt; &lt;li&gt;&lt;span style="font-size:100%;"&gt;Cross-site Request Forgery (CSRF) attacks&lt;/span&gt;&lt;/li&gt;&lt;span style="font-size:100%;"&gt;&lt;br /&gt;&lt;/span&gt; &lt;li&gt;&lt;span style="font-size:100%;"&gt;Clickjacking attacks&lt;/span&gt;&lt;/li&gt;&lt;/ul&gt;&lt;br /&gt;&lt;p  style="color: rgb(0, 0, 0);font-family:arial;"&gt;&lt;span style="font-size:100%;"&gt;&lt;strong&gt;Cross-site Scripting&lt;/strong&gt;&lt;br /&gt;&lt;/span&gt;&lt;/p&gt;&lt;p  style="color: rgb(0, 0, 0);font-family:arial;"&gt;&lt;span style="font-size:100%;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="font-size:100%;"&gt;    Cross-site scripting (XSS) attacks have been by far the most prevalent exploit utilized on the web.&lt;span&gt; &lt;/span&gt;However, in many cases they are also the easiest to avoid from a web site developer stand point. &lt;span&gt; &lt;/span&gt;An XSS attack commonly occurs when a web page displays content either supplied by an end-user or from another site, and it does not perform any HTML encoding of the content.&lt;span&gt;  &lt;/span&gt;The end-user content commonly comes from a form input field, and it essentially allows a user to insert their own HTML or client-site script into a web page.&lt;span&gt; &lt;/span&gt;If that content may viewed by another user (in a message forum, for example) then it could be used to carry out any number of attacks such as:&lt;/span&gt;&lt;/p&gt;&lt;ul  style="color: rgb(0, 0, 0);font-family:arial;"&gt;&lt;li&gt;&lt;span style="font-size:100%;"&gt;Read the content of the user's page and send it to another server.&lt;/span&gt;&lt;/li&gt;&lt;span style="font-size:100%;"&gt;&lt;br /&gt;&lt;/span&gt; &lt;li&gt;&lt;span style="font-size:100%;"&gt;Read the value of a user's cookie and send it to the attacker so that he may assume that user's identity.&lt;/span&gt;&lt;/li&gt;&lt;span style="font-size:100%;"&gt;&lt;br /&gt;&lt;/span&gt; &lt;li&gt;&lt;span style="font-size:100%;"&gt;Send the user to another site.&lt;/span&gt;&lt;/li&gt;&lt;span style="font-size:100%;"&gt;&lt;br /&gt;&lt;/span&gt; &lt;li&gt;&lt;span style="font-size:100%;"&gt;In versions of Internet Explorer prior to IE6 and Windows XP Service Pack 2, a script could target a vulnerable page on a user's local file system and run scripts with full access to that user's system.&lt;/span&gt;&lt;/li&gt;&lt;/ul&gt;&lt;p  style="color: rgb(0, 0, 0);font-family:arial;"&gt;&lt;span style="font-size:100%;"&gt;From a user stand-point, obviously the most severe approach to defeating these attacks is to simply disable client-side scripts from running.&lt;span&gt;  &lt;/span&gt;This would protect you from 99% of the really nasty exploits, although you would still be vulnerable to purely HTML based attacks.&lt;span&gt;  &lt;/span&gt;However, disabling all scripts is somewhat drastic and really hampers your ability to take full advantage of the web.&lt;span&gt;  &lt;/span&gt;A better approach is discussed at the end of this article.&lt;/span&gt;&lt;span style="font-size:100%;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;/p&gt;&lt;p  style="color: rgb(0, 0, 0);font-family:arial;"&gt;&lt;span style="font-size:100%;"&gt;The real onus for defeating XSS attacks lies with web developers.&lt;span&gt;  &lt;/span&gt;The first and most important action that a web developer should take is to not trust any input that could be potentially tainted by an end-user.&lt;span&gt;  &lt;/span&gt;Any data that will be written into a web page needs to be HTML encoded.&lt;span&gt;  &lt;/span&gt;Any data that will be written as a client-script string literal needs to be properly escaped.&lt;span&gt;  &lt;/span&gt;Finally, do not give client scripts access to any cookies unless absolutely necessary.  Instead, mark them as httpOnly so that only your user's browser and your web site have access to them, and nothing else.&lt;/span&gt;&lt;span style="font-size:100%;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;/p&gt;&lt;p  style="color: rgb(0, 0, 0);font-family:arial;"&gt;&lt;span style="font-size:100%;"&gt;&lt;strong&gt;Cross-site Request Forgery&lt;/strong&gt;&lt;br /&gt;&lt;/span&gt;&lt;/p&gt;&lt;p  style="color: rgb(0, 0, 0);font-family:arial;"&gt;&lt;span style="font-size:100%;"&gt;Cross-site Request Forgery (or CSRF) is another attack that is becoming more common.&lt;span&gt;  &lt;/span&gt;It takes advantage of situations where a user remains logged into another site by means of a cookie (httpOnly or otherwise).&lt;span&gt;  &lt;/span&gt;For example, suppose there is a webmail application that a user is logged into.&lt;span&gt;  &lt;/span&gt;As long as an appropriate authentication cookie is sent to the site with a user's request, the site will allow actions to be performed.&lt;span&gt;  &lt;/span&gt;This kind of security is referred to as ambient authority.&lt;span&gt;  &lt;/span&gt;The authentication information is sent with each request to the server; however, the server doesn't really know if the user specifically performed the request with their browser, or if another page tricked the user into performing the request.&lt;span&gt;  &lt;/span&gt;This problem is often called the problem of the &lt;a href="http://www.cap-lore.com/CapTheory/ConfusedDeputy.html"&gt;Confused Deputy&lt;/a&gt;, which refers back to an article written in 1988 by Norm Hardy.&lt;span&gt;  &lt;/span&gt;For example, a malicious third-party site could embed an IFRAME in their own page but the IFRAME's URL points to your web mail server, and sends it a command to delete all of your mail.&lt;span&gt;  &lt;/span&gt;Since you were already logged in to your mail server, the IFRAME request behaves exactly as if you had made that request yourself and sends all of the necessary authentication cookie information.&lt;span&gt;  &lt;/span&gt;These attacks may also be implemented with img tags.&lt;/span&gt;&lt;/p&gt;&lt;p  style="color: rgb(0, 0, 0);font-family:arial;"&gt;&lt;span style="font-size:100%;"&gt;From a user stand-point, there isn't a whole lot that you can do to protect yourself against CSRF attacks other than always logging out of sites when you are done using them.&lt;span&gt;  &lt;/span&gt;You can also protect yourself from attacks via IFRAME based attacks.&lt;span&gt;  &lt;/span&gt;See the last paragraph of this article for more information on that.&lt;/span&gt;&lt;span style="font-size:100%;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;/p&gt;&lt;p  style="color: rgb(0, 0, 0);font-family:arial;"&gt;&lt;span style="font-size:100%;"&gt;From a developer stand-piont, there are a number of ways that you can protect the users of your sites from these attacks.&lt;span&gt;  &lt;/span&gt;Obviously, you could not support persistent authentication via cookies, but most people find it convenient so it would be nice if there were a compromise.&lt;span&gt;  &lt;/span&gt;You could require an additional user confirmation before performing any action that could modify their data.&lt;span&gt;  &lt;/span&gt;However, that would become quickly cumbersome to users.&lt;span&gt; &lt;/span&gt;A more transparent approach is to include a secret value or key that must be sent back in a form or URL.&lt;span&gt;  &lt;/span&gt;If the value is sent back in a cookie or some other means where a browser's same-origin policy applies (i.e. scripts can't access cross-domain data such as what comes back in an IFRAME), then the third-party site cannot successfully construct a valid request.&lt;span&gt;  &lt;/span&gt;Finally, you should also prevent any requests to modify data that are not POST requests.&lt;span&gt;  &lt;/span&gt;The HTTP protocol specifies that GET requests should never change data on the server.&lt;/span&gt;&lt;span style="font-size:100%;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;/p&gt;&lt;span style="color: rgb(0, 0, 0);font-family:arial;font-size:100%;"  &gt;&lt;strong&gt;Clickjacking&lt;/strong&gt;&lt;br /&gt;&lt;/span&gt;&lt;p  style="color: rgb(0, 0, 0);font-family:arial;"&gt;&lt;span style="font-size:100%;"&gt;The final attack that we will examine is also one of the more recent to be classified, and it is called Clickjacking.&lt;span&gt;  &lt;/span&gt;It is also potentially the most dangerous as there isn't a 100% solution for it.&lt;span&gt; &lt;/span&gt;Clickjacking is a derivative of a CSRF attack except that the user is fooled into clicking what appears to be a button on a third-party site, but in between the cursor and the button is a hidden layer positioned over a button on another web site (for example, a delete mail button from our example above).&lt;span&gt;  &lt;/span&gt;This invisible layer can even be made to follow a user's cursor around the page to ensure that the attack will succeed.&lt;span&gt;  &lt;/span&gt;A non-script based approach could simply tile the third-party site's page with these hidden layers.&lt;/span&gt;&lt;span style="font-size:100%;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;/p&gt;&lt;span style="color: rgb(0, 0, 0);font-family:arial;font-size:100%;"  &gt;Considering that this attack forces a user to unknowingly perform an action on a web site in a very real sense, it is indeed very dangerous and hard to detect.&lt;/span&gt;&lt;span style="color: rgb(0, 0, 0);font-family:arial;font-size:100%;"  &gt;  &lt;/span&gt;&lt;span style="color: rgb(0, 0, 0);font-family:arial;font-size:100%;"  &gt;A user's &lt;/span&gt;&lt;span style="color: rgb(0, 0, 0);font-family:arial;font-size:100%;"  &gt;only repercussion is to once again, disable client scripts (which would prevent the majority of these attacks from working), and also logout from any site once finished with it.&lt;/span&gt;&lt;span style="color: rgb(0, 0, 0);font-family:arial;font-size:100%;"  &gt;  &lt;/span&gt;&lt;span style="color: rgb(0, 0, 0);font-family:arial;font-size:100%;"  &gt;A third approach is &lt;/span&gt;&lt;span style="color: rgb(0, 0, 0);font-family:arial,helvetica,sans-serif;font-size:100%;"  &gt;discussed below as well.&lt;/span&gt;&lt;span style="color: rgb(0, 0, 0);font-size:100%;" &gt;&lt;br /&gt;&lt;/span&gt;&lt;p  style="color: rgb(0, 0, 0);font-family:arial;"&gt;&lt;span style="font-size:100%;"&gt;Developers have it much harder for prevent clickjacking attacks.&lt;span&gt;  &lt;/span&gt;A site could be setup to force user confirmation before performing an action, but once again, that becomes cumbersome to users and is not foolproof.&lt;span&gt; &lt;/span&gt;In truth, prevention of these attacks will likely need to come from the browsers.&lt;span&gt;  &lt;/span&gt;A discussion of some of the&lt;br /&gt;possible solutions can be found &lt;a href="http://blog.whatwg.org/this-week-in-html-5-episode-7"&gt;here&lt;/a&gt;.&lt;/span&gt;&lt;span style="font-size:100%;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;/p&gt;&lt;p  style="color: rgb(0, 0, 0);font-family:arial;"&gt;&lt;span style="font-size:100%;"&gt;&lt;strong&gt;Wrapping Things Up&lt;/strong&gt;&lt;br /&gt;&lt;/span&gt;&lt;/p&gt;&lt;p  style="color: rgb(0, 0, 0);font-family:arial;"&gt;&lt;span style="font-size:100%;"&gt;As mentioned several times in this article, an alternative approach exists to dealing with all of these attacks, and that comes in the form of the &lt;a href="http://noscript.net/getit"&gt;NoScript plugin&lt;/a&gt; for Firefox 3+.&lt;span&gt;  &lt;/span&gt;NoScript essentially provides a "white-listing" approach to which sites you allow to execute client-side scripts.&lt;span&gt; &lt;/span&gt;It can also be used to disable IFRAME in un-trusted sites.&lt;span&gt;  &lt;/span&gt;The NoScript plugin is highly recommended, and it can be used to prevent XSS, CSRF, and Clickjacking attacks.&lt;span&gt;  &lt;/span&gt;Simply put, as the technologies used to build the web and enable new applications of the web move forward, so will the number and severity of the exploits available to attackers.&lt;span&gt;  &lt;/span&gt;As both users and developers for the web, we must constantly think about how we can protect ourselves as well as our sites from being attacked.&lt;span&gt;  &lt;/span&gt;The attacks my take a very &lt;a href="http://lists.w3.org/Archives/Public/www-svg/2008Sep/0112.html"&gt;different form&lt;/a&gt; tomorrow.&lt;span&gt;  &lt;/span&gt;While the web opens up many doors of opportunity it will also continue to keep us all&lt;br /&gt;on our toes.&lt;/span&gt;&lt;span style="font-size:100%;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;/p&gt;&lt;span style="color: rgb(0, 0, 0);font-family:arial,helvetica,sans-serif;font-size:100%;"  &gt;&lt;strong&gt;Additional Links of Interest&lt;/strong&gt;&lt;/span&gt;&lt;span style="color: rgb(0, 0, 0);font-family:arial;font-size:100%;"  &gt;&lt;br /&gt;&lt;/span&gt;&lt;ul  style="color: rgb(0, 0, 0);font-family:arial;"&gt;&lt;span style="font-size:100%;"&gt;&lt;/span&gt; &lt;li&gt;&lt;span style="font-size:100%;"&gt;&lt;a href="http://hackademix.net/2008/09/27/clickjacking-and-noscript/"&gt;Discussion of Clickjacking and NoScript&lt;/a&gt;&lt;/span&gt;&lt;/li&gt;&lt;span style="font-size:100%;"&gt;&lt;/span&gt; &lt;li&gt;&lt;span style="font-size:100%;"&gt;&lt;a href="http://en.wikipedia.org/wiki/Cross-site_scripting"&gt;Wikipedia article on XSS&lt;/a&gt;&lt;/span&gt;&lt;/li&gt;&lt;span style="font-size:100%;"&gt;&lt;/span&gt; &lt;li&gt;&lt;span style="font-size:100%;"&gt;&lt;a href="http://en.wikipedia.org/wiki/CSRF"&gt;Wikipedia article on CSRF&lt;/a&gt;&lt;/span&gt;&lt;/li&gt;&lt;li&gt;&lt;span style="font-size:100%;"&gt;&lt;a href="http://ha.ckers.org/xss.html"&gt;XSS Cheat Sheet&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;/span&gt; &lt;/li&gt;&lt;span style="font-size:100%;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;/ul&gt;&lt;span style="color: rgb(0, 0, 0);font-family:arial;font-size:100%;"  &gt;&lt;br /&gt;&lt;/span&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/8322079459489742719-1831370086780209435?l=webshiftsoftware.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webshiftsoftware.blogspot.com/feeds/1831370086780209435/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=8322079459489742719&amp;postID=1831370086780209435' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/8322079459489742719/posts/default/1831370086780209435'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/8322079459489742719/posts/default/1831370086780209435'/><link rel='alternate' type='text/html' href='http://webshiftsoftware.blogspot.com/2009/11/from-users-to-developers-avoiding-web.html' title='From Users to Developers - Avoiding Web-Based Computer Security Vulnerabilities'/><author><name>Jeremy Burman</name><uri>http://www.blogger.com/profile/10664616950976186217</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-8322079459489742719.post-7517828801444755084</id><published>2009-11-23T09:31:00.004-05:00</published><updated>2009-11-23T11:15:11.983-05:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Web Development'/><category scheme='http://www.blogger.com/atom/ns#' term='Tips'/><category scheme='http://www.blogger.com/atom/ns#' term='ASP.NET'/><category scheme='http://www.blogger.com/atom/ns#' term='Code'/><title type='text'>Dynamic Control of ASP.NET Session State Requirement</title><content type='html'>&lt;span style="font-size:90%;"&gt;&lt;span style="text-indent: 12pt;font-family:arial;"&gt;The ASP.NET runtime provides the &lt;a href="http://msdn.microsoft.com/en-us/library/system.web.sessionstate.sessionstatemodule.aspx"&gt;SessionStateModule&lt;/a&gt;, which automatically loads session state for any ASP.NET HTTP Handler implementing the &lt;a href="http://msdn.microsoft.com/en-us/library/system.web.sessionstate.irequiressessionstate.aspx"&gt;IRequiresSessionState &lt;/a&gt;or &lt;a href="http://msdn.microsoft.com/en-us/library/system.web.sessionstate.ireadonlysessionstate.aspx"&gt;IReadOnlySessionState &lt;/a&gt;interfaces. This approach is fine in most circumstances, but consider the case where you may wish to selectively load session state for the same HTTP Handler from one invocation to the next, and you need to make this determination at runtime. In this case, it is unclear what approach should be taken as the IRequiresSessionState and IReadOnlySessionState interfaces are static type information specified at compile time.  When using the interfaces, the HTTP handler is effectively hard-wired to always cause session state to be loaded or to not be loaded. This article examines one approach to dealing with this restriction by implementing a custom HTTP module.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;    First of all, let’s examine what hooks exist in the ASP.NET pipeline for triggering the SessionStateModule to load session state for an HTTP request. Our eventual goal is to load the session state, only when it is needed, into the HttpContext object before the Http Handler’s &lt;span style="font-weight: bold;"&gt;ProcessRequest &lt;/span&gt;method executes. Examining the &lt;a href="http://msdn.microsoft.com/en-us/library/system.web.httpapplication.aspx"&gt;HttpApplication &lt;/a&gt;class, we can see the list of events that are fired by the ASP.NET runtime. The important one is the &lt;span style="font-weight: bold;"&gt;AcquireRequestState &lt;/span&gt;event as it is the event that the SessionStateModule utilizes to determine if session state needs to be loaded. Looking at the event list, we can see that shortly after AcquireRequestState finishes, the HTTP handler itself is invoked. During AcquireRequestState, the SessionStateModule examines the &lt;span style="font-weight: bold;"&gt;Handler &lt;/span&gt;property of the current &lt;span style="font-weight: bold;"&gt;HttpContext &lt;/span&gt;object to see if it implements one of the IRequiresSessionState or IReadOnlySessionState interfaces. If it does, then session state is loaded.&lt;/span&gt;&lt;br /&gt;&lt;div style="background-color:#efefef; padding-left: 8px; font-size:1.0em;"&gt;&lt;br /&gt;&lt;span style="color:Navy;"&gt;&lt;br /&gt;&lt;div style="font-weight: bold; text-decoration: underline; font-family: arial; margin-top: 8px;"&gt;Example:&lt;/div&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;&lt;pre&gt;public void AcquireRequestStateHandler(object sender, EventArgs e)&lt;br /&gt;{&lt;br /&gt;    HttpContext context = ((HttpApplication)sender).Context;&lt;br /&gt;    if (context.Handler is IRequiresSessionState)&lt;br /&gt;    {&lt;br /&gt;        // ...&lt;br /&gt;    }&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;&lt;/span&gt;&lt;/span&gt;&lt;br /&gt;&lt;/div&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;    Conceivably, if we could change the interface of the HTTP handler at runtime before AcquireRequestState runs, then we could control whether the session state is loaded or not. Fortunately, the Handler property is a writable property. Therefore, by creating "wrapper" HTTP handlers we can wrap the current handler at runtime before the AcquireRequestState event runs. Each wrapper type implements an interface corresponding to a type of session state requirement.&lt;/span&gt;&lt;br /&gt;&lt;div   style="background-color:#efefef; padding-left: 8px; font-size:1.0em;"&gt;&lt;br /&gt;&lt;span style="color:Navy;"&gt;&lt;br /&gt;&lt;div style="font-weight: bold; text-decoration: underline; font-family: arial; margin-top: 8px;"&gt;Example wrappers:&lt;/div&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;&lt;pre&gt;/// &lt;summary&gt;&lt;br /&gt;/// Wraps another IHttpHandler and indicates to the SessionStateModule&lt;br /&gt;/// that read-only session state is required for the request.&lt;br /&gt;/// &lt;/summary&gt;&lt;br /&gt;public class ReadStateHandlerWrapper : IHttpHandler, IReadOnlySessionState&lt;br /&gt;{&lt;br /&gt;    private IHttpHandler _wrappedHandler;&lt;br /&gt;&lt;br /&gt;    public ReadStateHandlerWrapper(IHttpHandler wrappedHandler)&lt;br /&gt;    {&lt;br /&gt;        _wrappedHandler = wrappedHandler;&lt;br /&gt;    }&lt;br /&gt;&lt;br /&gt;    public bool IsReusable&lt;br /&gt;    {&lt;br /&gt;        get { return _wrappedHandler.IsReusable; }&lt;br /&gt;    }&lt;br /&gt;&lt;br /&gt;    public void ProcessRequest(HttpContext context)&lt;br /&gt;    {&lt;br /&gt;        _wrappedHandler.ProcessRequest(context);&lt;br /&gt;    }&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;/// &lt;summary&gt;&lt;br /&gt;/// Wraps another IHttpHandler and indicates to the SessionStateModule&lt;br /&gt;/// that read/write session state is required for the request.&lt;br /&gt;/// &lt;/summary&gt;&lt;br /&gt;public class ReadWriteStateHandlerWrapper : IHttpHandler, IRequiresSessionState&lt;br /&gt;{&lt;br /&gt;    private IHttpHandler _wrappedHandler;&lt;br /&gt;&lt;br /&gt;    public ReadWriteStateHandlerWrapper(IHttpHandler wrappedHandler)&lt;br /&gt;    {&lt;br /&gt;        _wrappedHandler = wrappedHandler;&lt;br /&gt;    }&lt;br /&gt;&lt;br /&gt;    public bool IsReusable&lt;br /&gt;    {&lt;br /&gt;        get { return _wrappedHandler.IsReusable; }&lt;br /&gt;    }&lt;br /&gt;&lt;br /&gt;    public void ProcessRequest(HttpContext context)&lt;br /&gt;    {&lt;br /&gt;        _wrappedHandler.ProcessRequest(context);&lt;br /&gt;    }&lt;br /&gt;}&lt;/pre&gt;&lt;/span&gt;&lt;/span&gt;&lt;br /&gt;&lt;/div&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;    Looking again at the HttpApplication events, we can see that an event named &lt;span style="font-weight: bold;"&gt;PostMapRequestHandler &lt;/span&gt;runs before AcquireRequestState executes. All that remains is to create a custom HTTP module that hooks into PostMapRequestHandler, and implements runtime logic to determine if session state is required for the current request or not.&lt;/span&gt;&lt;br /&gt;&lt;div   style="background-color:#efefef; padding-left: 8px; font-size:1.0em;"&gt;&lt;br /&gt;&lt;span style="color:Navy;"&gt;&lt;br /&gt;&lt;div style="font-weight: bold; text-decoration: underline; font-family: arial; margin-top: 8px;"&gt;Example module:&lt;/div&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;&lt;pre&gt;public class StateInitModule : IHttpModule&lt;br /&gt;{&lt;br /&gt;    public void Dispose()&lt;br /&gt;    {&lt;br /&gt;    }&lt;br /&gt;&lt;br /&gt;    public void Init(HttpApplication context)&lt;br /&gt;    {&lt;br /&gt;        context.PostMapRequestHandler += new EventHandler(PostMapRequestHandler);&lt;br /&gt;    }&lt;br /&gt;&lt;br /&gt;    void PostMapRequestHandler(object sender, EventArgs e)&lt;br /&gt;    {&lt;br /&gt;        HttpContext context = ((HttpApplication)sender).Context;&lt;br /&gt;        // Step 1. Determine if a handler is executing that we care about&lt;br /&gt;        // Example: check it by type name&lt;br /&gt;        if (null != context.Handler&lt;br /&gt;            &amp;amp;&amp;amp; "MyHandlerTypeName" == context.Handler.GetType().Name)&lt;br /&gt;        {&lt;br /&gt;            // Step 2. Determine if the handler requires session state or not&lt;br /&gt;            // This will be specific to your particular application.&lt;br /&gt;            // For example, you may examine a query string parameter.&lt;br /&gt;            if(/* ... Logic to determine read-only access requirement */) &lt;br /&gt;            {&lt;br /&gt;                context.Handler = new ReadStateHandlerWrapper(context.Handler);&lt;br /&gt;            } &lt;br /&gt;            else if(/* ... Logic to determine read/write access requirement */) &lt;br /&gt;            {&lt;br /&gt;                context.Handler = new ReadWriteStateHandlerWrapper(context.Handler);&lt;br /&gt;            } // else do not alter the Handler property and state will not be loaded&lt;br /&gt;        }&lt;br /&gt;    }&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;&lt;/span&gt;&lt;/span&gt;&lt;br /&gt;&lt;/div&gt;&lt;span style="color: rgb(102, 102, 102);font-family:arial;font-size:75%;"&gt;(See the &lt;a href="http://msdn.microsoft.com/en-us/library/ms227673.aspx"&gt;Custom Module Walkthrough&lt;/a&gt; if needed, which describes the process of implementing and configuring an ASP.NET HTTP Module.)&lt;/span&gt;&lt;br /&gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;    &lt;span style="font-size:90%;"&gt;Keep in mind that HTTP modules execute in front of all requests so you should try to keep your logic as light and efficient as possible. Obviously each particular application will need to define its own heuristic for determining if a given HTTP handler request requires session state or not, but the above pattern will provide the capability to implement the logic at runtime.&lt;/span&gt;&lt;/span&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/8322079459489742719-7517828801444755084?l=webshiftsoftware.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webshiftsoftware.blogspot.com/feeds/7517828801444755084/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=8322079459489742719&amp;postID=7517828801444755084' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/8322079459489742719/posts/default/7517828801444755084'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/8322079459489742719/posts/default/7517828801444755084'/><link rel='alternate' type='text/html' href='http://webshiftsoftware.blogspot.com/2009/11/dynamic-control-of-aspnet-session-state.html' title='Dynamic Control of ASP.NET Session State Requirement'/><author><name>Jeremy Burman</name><uri>http://www.blogger.com/profile/10664616950976186217</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry></feed>
