<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	xmlns:georss="http://www.georss.org/georss" xmlns:geo="http://www.w3.org/2003/01/geo/wgs84_pos#" xmlns:media="http://search.yahoo.com/mrss/"
	>

<channel>
	<title>Arran Maclean</title>
	<atom:link href="http://arranmaclean.wordpress.com/feed/" rel="self" type="application/rss+xml" />
	<link>http://arranmaclean.wordpress.com</link>
	<description>.NET, MVC, jQuery, SEO and a little social fun</description>
	<lastBuildDate>Mon, 23 Jan 2012 08:12:36 +0000</lastBuildDate>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
	<generator>http://wordpress.com/</generator>
<cloud domain='arranmaclean.wordpress.com' port='80' path='/?rsscloud=notify' registerProcedure='' protocol='http-post' />
<image>
		<url>http://s2.wp.com/i/buttonw-com.png</url>
		<title>Arran Maclean</title>
		<link>http://arranmaclean.wordpress.com</link>
	</image>
	<atom:link rel="search" type="application/opensearchdescription+xml" href="http://arranmaclean.wordpress.com/osd.xml" title="Arran Maclean" />
	<atom:link rel='hub' href='http://arranmaclean.wordpress.com/?pushpress=hub'/>
		<item>
		<title>Base64 CSS Images for speed MSTASK</title>
		<link>http://arranmaclean.wordpress.com/2012/01/22/base64-css-images-for-speed/</link>
		<comments>http://arranmaclean.wordpress.com/2012/01/22/base64-css-images-for-speed/#comments</comments>
		<pubDate>Sun, 22 Jan 2012 17:24:08 +0000</pubDate>
		<dc:creator>ArranM</dc:creator>
				<category><![CDATA[Code Examples]]></category>
		<category><![CDATA[General rambles]]></category>
		<category><![CDATA[.NET]]></category>
		<category><![CDATA[C#]]></category>
		<category><![CDATA[CSS]]></category>
		<category><![CDATA[MSBUILD]]></category>
		<category><![CDATA[MVC]]></category>
		<category><![CDATA[Speed]]></category>

		<guid isPermaLink="false">http://arranmaclean.wordpress.com/?p=434</guid>
		<description><![CDATA[Hi all, Following on from previous posts and the possible cheap ways to increase your web-site load times. I thought I&#8217;d share a little bit code that helps reduce the number of calls your web pages make when loading images either from CSS or in the HTML itself. The process is straight forwards enough; It&#8217;s [...]<img alt="" border="0" src="http://stats.wordpress.com/b.gif?host=arranmaclean.wordpress.com&amp;blog=7827390&amp;post=434&amp;subd=arranmaclean&amp;ref=&amp;feed=1" width="1" height="1" />]]></description>
			<content:encoded><![CDATA[<p>Hi all,</p>
<p>Following on from previous posts and the possible cheap ways to increase your web-site load times. I thought I&#8217;d share a little bit code that helps reduce the number of calls your web pages make when loading images either from CSS or in the HTML itself.</p>
<p>The process is straight forwards enough; It&#8217;s just a case of where you want to implement it, either during the build process or at runtime.<span id="more-434"></span></p>
<p>I personally like minify during the build process, combining and Base64 files before deploying and then caching. There are a number of solutions that will do all this for you at run time. (Seem comments on previous posts) The choice is yours.</p>
<p>For a recent project I used code similar to the following. There is a little gotcha you have to keep in mind when process to base64 encoding images and that is the limitation of older browsers.</p>
<p>Microsoft Internet Explore version 6 and 7 do not support base64 natively and IE8 has a size limitation of 32Kb. As with most issues around different browsers, building a simple browser sniffer to decide which to version of the CSS to send to the client and cache it, will help resolve the issue.</p>
<p>The downloadable version of the code is wrapped in an MSBUILD task, should you need to wire this up to your CI.</p>
<p>So the following image :</p>
<p><img src="http://arranmaclean.files.wordpress.com/2012/01/screen-shot-2012-01-22-at-17-31-36.png?w=600" alt="Light Box tools" title="Screen Shot 2012-01-22 at 17.31.36"   class="alignnone size-full wp-image-451" /></p>
<p>Would be converted to the following inside the CSS file. Yes your files will get bigger but it&#8217;s still time saving and reduces the number of round trips, but I guess you knew that already else you would not be looking at this as an option.</p>
<p>data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAK8AAAAy etc..</p>
<p>NB: WordPress does like to screw-up inline code, so see the download for a working example.</p>
<p><strong>If you like it and feel the need, please donate and buy me a beer.</strong></p>
<p><pre class="brush: csharp; pad-line-numbers: true;">

        public string ImagePath { get; set; }

private static string MakeImagesBase64(string stylesheet)
        {
            const RegexOptions MyRegexOptions = RegexOptions.None;
            const string RegexPattern = @&quot;(?&lt;=url\(/)(.*)(?=\))&quot;;

            var myRegex = new Regex(RegexPattern, MyRegexOptions);

            var result = myRegex.Replace(stylesheet, this.OnEvaluator).Replace(Environment.NewLine, string.Empty).Replace(&quot;/data&quot;, &quot;data&quot;);
        }

private string OnEvaluator(Match match)
        {
            var uriData = LoadCssImage(this.ImagePath, match.ToString());
            return uriData;
        }

private static string LoadCSSImage(string capturedFilepath)
        {
            string imagePath = HttpContext.Current.Server.MapPath(capturedFilepath);
            int start = capturedFilepath.LastIndexOf('.') + 1;
            int end = capturedFilepath.Length;
            string imageType = capturedFilepath.Substring(start, end - start);
            string result = String.Empty;

            ////Try to load image, if we can't find it put back the original image path
            try
            {
                using(Image image = Image.FromFile(imagePath))
                {
                    System.Drawing.Imaging.ImageFormat format = image.RawFormat;
                    result = ImagetoBase64(image, format, imageType, capturedFilepath);
                }
            }
            catch
            {
                result = capturedFilepath;
            }
            return result;
        }

private static string ImagetoBase64(Image image, System.Drawing.Imaging.ImageFormat format, string imageType, string capturedFilepath)
        {
            using (MemoryStream ms = new MemoryStream())
            {
                string result = String.Empty;
                image.Save(ms, format);
                byte[] imageBytes = ms.ToArray();

                string base64String = Convert.ToBase64String(imageBytes);
                var ie8ByteLimit = 32768;

                if (imageBytes.Length &lt; ie8ByteLimit)
                {
                    result = String.Format(&quot;data:image/{0};base64,{1}&quot;, imageType, base64String);
                }
                else
                {
                    result = capturedFilepath;
                }

                return result;
            }
        }
</pre></p>
<br />  <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gocomments/arranmaclean.wordpress.com/434/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/comments/arranmaclean.wordpress.com/434/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/godelicious/arranmaclean.wordpress.com/434/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/delicious/arranmaclean.wordpress.com/434/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gofacebook/arranmaclean.wordpress.com/434/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/facebook/arranmaclean.wordpress.com/434/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gotwitter/arranmaclean.wordpress.com/434/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/twitter/arranmaclean.wordpress.com/434/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gostumble/arranmaclean.wordpress.com/434/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/stumble/arranmaclean.wordpress.com/434/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/godigg/arranmaclean.wordpress.com/434/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/digg/arranmaclean.wordpress.com/434/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/goreddit/arranmaclean.wordpress.com/434/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/reddit/arranmaclean.wordpress.com/434/" /></a> <img alt="" border="0" src="http://stats.wordpress.com/b.gif?host=arranmaclean.wordpress.com&amp;blog=7827390&amp;post=434&amp;subd=arranmaclean&amp;ref=&amp;feed=1" width="1" height="1" />]]></content:encoded>
			<wfw:commentRss>http://arranmaclean.wordpress.com/2012/01/22/base64-css-images-for-speed/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
	
		<media:content url="http://1.gravatar.com/avatar/be4d11a40f2a59dd3b0a7bb66032149a?s=96&#38;d=identicon&#38;r=G" medium="image">
			<media:title type="html">Arran</media:title>
		</media:content>

		<media:content url="http://arranmaclean.files.wordpress.com/2012/01/screen-shot-2012-01-22-at-17-31-36.png" medium="image">
			<media:title type="html">Screen Shot 2012-01-22 at 17.31.36</media:title>
		</media:content>
	</item>
		<item>
		<title>iPhone Apps built with Monotouch</title>
		<link>http://arranmaclean.wordpress.com/2011/04/27/iphone-app-built-with-monotouch/</link>
		<comments>http://arranmaclean.wordpress.com/2011/04/27/iphone-app-built-with-monotouch/#comments</comments>
		<pubDate>Wed, 27 Apr 2011 11:45:19 +0000</pubDate>
		<dc:creator>ArranM</dc:creator>
				<category><![CDATA[General rambles]]></category>
		<category><![CDATA[C#]]></category>
		<category><![CDATA[iPhone]]></category>
		<category><![CDATA[MonoTouch]]></category>

		<guid isPermaLink="false">http://arranmaclean.wordpress.com/?p=401</guid>
		<description><![CDATA[My MonoTouch iPhone app is live Recently I was very fortunate to work on contract for one of the UK&#8217;s leading nationwide used car sales company, Carcraft. During my time with Carcraft, I worked on number of exciting and fun web projects with a really great bunch of people. One of the more interesting projects was the development of the [...]<img alt="" border="0" src="http://stats.wordpress.com/b.gif?host=arranmaclean.wordpress.com&amp;blog=7827390&amp;post=401&amp;subd=arranmaclean&amp;ref=&amp;feed=1" width="1" height="1" />]]></description>
			<content:encoded><![CDATA[<p><strong>My MonoTouch iPhone app is live</strong></p>
<p><strong></strong>Recently I was very fortunate to work on contract for one of the UK&#8217;s leading nationwide used car sales company, <a title="Used Cars" href="http://www.carcraft.co.uk/?mkid=88888" target="_blank">Carcraft</a>.</p>
<p>During my time with Carcraft, I worked on number of exciting and fun web projects with a really great bunch of people. One of the more interesting projects was the development of the Official <a title="Carcraft iPhone App" href="http://bit.ly/OuriPhoneApp" target="_blank">Carcraft iPhone app</a>. <span id="more-401"></span></p>
<p>After seeing a presentation by <a title="@chrisnt" href="http://twitter.com/chrisntr" target="_blank">@chrisntr</a> at <a title="NxtGenUG" href="http://www.nxtgenug.net" target="_blank">NxtGenUG</a> (managed by <a title="@Grumpydev" href="http://twitter.com/Grumpydev" target="_blank">@Grumpydev</a> and team) about MonoTouch. I decided to stick with a language that complement the rest of the development team skills and develop in C# with MonoTouch.</p>
<p>To find out more and download the app, please visit <a title="iTunes Store" href="http://bit.ly/OuriPhoneApp" target="_blank">iTunes store</a>.</p>
<p><a title="Available on the App Store" href="http://bit.ly/OuriPhoneApp"><img class="size-full wp-image-402 alignnone" title="App_Store_Badge_EN" src="http://arranmaclean.files.wordpress.com/2011/04/app_store_badge_en.png?w=600" alt="Available on the App Store"   /></a></p>
<p><strong>What is MonoTouch?</strong></p>
<p><strong></strong><a title="MonoTouch Website" href="http://monotouch.net/" target="_blank">MonoTouch</a> allows developers to create C# and .NET based applications that run on Apple&#8217;s iPhone, iPad, and iPod Touch devices, while taking advantage of the iPhone APIs and reusing both code and libraries that have been built for .NET, as well as existing skills.  Please visit their web-site and try it for yourself. <a title="MonoTouch" href="http://monotouch.net" target="_blank">MonoTouch</a></p>
<p><strong>How was it?</strong></p>
<p><strong></strong>Once you have the basics under your belt, development for the iPhone was fun and quick, utilising Strongly Typed Models and Web Services, we developed an easy use application, retrieving live stock updates, car galleries and accessing GPS to calculate route maps and distances to your nearest Carcraft showroom. Also unique car industry features like, &#8220;Love this car&#8221; which allows your to enter a registration of any car and search the whole of the Carcraft stock list for something similar car or applying for finance while on the app.</p>
<p>All these features and more where all developed in C#, what more could you ask for?  Android version, we&#8217;ll thanks to <a title="Mono for Android" href="http://mono-android.net/" target="_blank">Mono for Android</a> you can that too, if you wanted it.</p>
<p><strong>Summary</strong></p>
<p><strong></strong>If your interested in getting starting and want to build your own application, I&#8217;d recommend <a href="http://amzn.to/edcmZ7">Professional iPhone Programming with MonoTouch and .NET/C# (Wrox Programmer to Programmer)</a><img style="border:none!important;margin:0!important;" src="http://www.assoc-amazon.co.uk/e/ir?t=websitecoukre-21&amp;l=as2&amp;o=2&amp;a=B003X2870W" alt="" width="1" height="1" border="0" /> as a good starting place.</p>
<p>Also reading the tutorials over at <a title="Monotouch.info resource" href="http://monotouch.info/" target="_blank">monotouch.info</a></p>
<p>I&#8217;ll be blogging about my next iPhone / iPad app, which is going to starting very shortly for mens underwear online store <a title="Calvin Klein Mens Underwear" href="http://www.gounderwear.co.uk/calvin-klein" target="_blank">www.gounderwear.co.uk</a> . So keep following.</p>
<p>If you found this helpful and would like to <strong>buy me a beer</strong> to say thanks, please <a href="https://www.paypal.com/cgi-bin/webscr?cmd=_s-xclick&amp;hosted_button_id=NKKD5YY5DQQK8"><img src="https://www.paypal.com/en_US/i/btn/x-click-but21.gif" alt="" /></a></p>
<p><a title="Follow me on Twitter" href="http://twitter.com/ArranM" target="_blank">@ArranM</a></p>
<br />  <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gocomments/arranmaclean.wordpress.com/401/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/comments/arranmaclean.wordpress.com/401/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/godelicious/arranmaclean.wordpress.com/401/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/delicious/arranmaclean.wordpress.com/401/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gofacebook/arranmaclean.wordpress.com/401/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/facebook/arranmaclean.wordpress.com/401/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gotwitter/arranmaclean.wordpress.com/401/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/twitter/arranmaclean.wordpress.com/401/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gostumble/arranmaclean.wordpress.com/401/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/stumble/arranmaclean.wordpress.com/401/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/godigg/arranmaclean.wordpress.com/401/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/digg/arranmaclean.wordpress.com/401/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/goreddit/arranmaclean.wordpress.com/401/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/reddit/arranmaclean.wordpress.com/401/" /></a> <img alt="" border="0" src="http://stats.wordpress.com/b.gif?host=arranmaclean.wordpress.com&amp;blog=7827390&amp;post=401&amp;subd=arranmaclean&amp;ref=&amp;feed=1" width="1" height="1" />]]></content:encoded>
			<wfw:commentRss>http://arranmaclean.wordpress.com/2011/04/27/iphone-app-built-with-monotouch/feed/</wfw:commentRss>
		<slash:comments>1</slash:comments>
	
		<media:content url="http://1.gravatar.com/avatar/be4d11a40f2a59dd3b0a7bb66032149a?s=96&#38;d=identicon&#38;r=G" medium="image">
			<media:title type="html">Arran</media:title>
		</media:content>

		<media:content url="http://arranmaclean.files.wordpress.com/2011/04/app_store_badge_en.png" medium="image">
			<media:title type="html">App_Store_Badge_EN</media:title>
		</media:content>

		<media:content url="http://www.assoc-amazon.co.uk/e/ir?t=websitecoukre-21&#38;l=as2&#38;o=2&#38;a=B003X2870W" medium="image" />

		<media:content url="https://www.paypal.com/en_US/i/btn/x-click-but21.gif" medium="image" />
	</item>
		<item>
		<title>Twitter Plugin MVC .NET &#8211; Yet another twitter reader</title>
		<link>http://arranmaclean.wordpress.com/2011/04/24/twitter-plugin-mvc-asp/</link>
		<comments>http://arranmaclean.wordpress.com/2011/04/24/twitter-plugin-mvc-asp/#comments</comments>
		<pubDate>Sun, 24 Apr 2011 13:17:15 +0000</pubDate>
		<dc:creator>ArranM</dc:creator>
				<category><![CDATA[Code Examples]]></category>
		<category><![CDATA[.NET]]></category>
		<category><![CDATA[MVC]]></category>
		<category><![CDATA[RSS]]></category>
		<category><![CDATA[Twitter]]></category>

		<guid isPermaLink="false">http://arranmaclean.wordpress.com/?p=339</guid>
		<description><![CDATA[As I have free time this morning, I thought I&#8217;d share a simple twitter feed reader. Yes I know there are hundreds if not thousands out-there, whoever another will not hurt and might just help someone. Left start with the &#8220;File &#62; New Project&#8221; in Visual Studio 2010. First we need to create a basic [...]<img alt="" border="0" src="http://stats.wordpress.com/b.gif?host=arranmaclean.wordpress.com&amp;blog=7827390&amp;post=339&amp;subd=arranmaclean&amp;ref=&amp;feed=1" width="1" height="1" />]]></description>
			<content:encoded><![CDATA[<p>As I have free time this morning, I thought I&#8217;d share a simple twitter feed reader. Yes I know there are hundreds if not thousands out-there, whoever another will not hurt and might just help someone.</p>
<p>Left start with the &#8220;File &gt; New Project&#8221; in Visual Studio 2010.<span id="more-339"></span></p>
<p><a href="http://arranmaclean.files.wordpress.com/2011/04/screen-shot-2011-04-24-at-09-39-561.png"><img class="alignnone size-medium wp-image-347" title="Screen shot 2011-04-24 at 09.39.56" src="http://arranmaclean.files.wordpress.com/2011/04/screen-shot-2011-04-24-at-09-39-561.png?w=300&#038;h=207" alt="File New Project" width="300" height="207" /></a></p>
<p>First we need to create a basic Model for our tweet, which we&#8217;ll call &#8220;TheTweet.cs&#8221;<br />
<a href="http://arranmaclean.files.wordpress.com/2011/04/screen-shot-2011-04-24-at-09-45-15.png"><img class="alignnone size-medium wp-image-341" title="Adding new class model" src="http://arranmaclean.files.wordpress.com/2011/04/screen-shot-2011-04-24-at-09-45-15.png?w=300&#038;h=232" alt="Adding new class" width="300" height="232" /></a></p>
<p>Now we have an empty class, lets add the basics for parts to handle the tweets.</p>
<p><pre class="brush: csharp;">
namespace TwitterFeedReader.Models
{
    public class TheTweet
    {
        public string Title { get; set; }
        public string Date { get; set; }
        public string Photo { get; set; }
    }
}
</pre></p>
<p>Next lets create the main function that we need in order to read our Twitter feed. I was going to do this in a few stages, however time is limited this morning so I&#8217;ll just bulk it all together, and its not that much code so it should easy to understand.</p>
<p>We want to display some tweets on your pages and try and reduce the need for fetching tweets on each view, so we are going to drop the results in to cache memory for 2 minutes. We&#8217;ll also wrap a try/catch around the loading of RSS feed, just encase we can&#8217;t load it.  </p>
<p><pre class="brush: csharp;">
public class TwitterReader
    {

        public IEnumerable GetFeed(int tweetCount)
        {
            //Setup Cache holder
            var TwitterCache = HttpRuntime.Cache;
            //Setup Cache key
            const string key = &quot;twitter&quot;;

            //Initials TheTweet
            IEnumerable Result;

            //Check to see if we already have tweet in memory and has not expired
            if (TwitterCache[key] == null)
            {

                try
                {
                    //Handle XML namespage
                    XNamespace AtomNs = &quot;http://www.w3.org/2005/Atom&quot;;
                    const string url = &quot;http://search.twitter.com/search.atom?q=from%3AArranM&quot;;

                    //Load the twitter feed in.
                    var Element = XElement.Load(url);

                    //Look through the returned twitter feed and grab X tweets in to our Result
                    Result = (from Tweet in Element.Descendants(AtomNs + &quot;entry&quot;).Take(tweetCount)
                              select new TheTweet
                              {
                                  Title = ConvertTwitterLinks((string)Tweet.Element(AtomNs + &quot;title&quot;)),
                                  Date = ConvertTimeDiff(DateTime.Parse((string)Tweet.Element(AtomNs + &quot;published&quot;)))
                              });

                    //Store the tweets in to memory for 2 minutes.
                    TwitterCache.Insert(key, Result, null, DateTime.Now.AddMinutes(2), Cache.NoSlidingExpiration);
                }
                catch
                {
                   //We have an issue, Return a friendly message to the model, so we don't crash. (//log it)
                   Result = new List {new TheTweet {Title = &quot;Unable to load twitter feed.&quot;, Date = &quot;1 second&quot;}};
                }
            }
            else
            {
                //Yes we have tweets in memory, so we'll use those
                Result = (IEnumerable)TwitterCache[key];
            }
            return Result;
        }
    }
</pre></p>
<p>Aren&#8217;t we great, we are now reading tweets! Hold on, what about links in the tweet? Mmm OK, lets create a quick function to process the tweet and convert any WWW, # or @ we find in to useable links. </p>
<p>I converted some <a title="PHP Regex to Make Twitter Links" href="http://www.snipe.net/2009/09/php-twitter-clickable-links/" target="_blank">PHP code</a> I found on the web, which seems simple and easy to use.</p>
<p><pre class="brush: csharp;">
private static String ConvertTwitterLinks(string input)
        {

            const string strWebLinks = @&quot;(^|[\n ])([\w]+?://[\w]+[^ \n\r\t&lt; ]*)&quot;;
            const string strWebLinksWww = @&quot;(^|[\n ])((www|ftp)\.[^ \t\n\r&lt; ]*)&quot;;
            const string strTwitterNames = @&quot;@(\w+)&quot;;
            const string strTwitterTags = @&quot;#(\w+)&quot;;

             input = Regex.Replace(input, strWebLinks, &quot; &lt;a href=\&quot;$2\&quot; rel=\&quot;external nofollow\&quot;&gt;$2&lt;/a&gt;&quot;);

            input = Regex.Replace(input, strWebLinksWww, &quot; &lt;a href=\&quot;http://$2\&quot; rel=\&quot;external nofollow\&quot;&gt;$2&lt;/a&gt;&quot;);

            input = Regex.Replace(input, strTwitterNames, &quot; &lt;a href=\&quot;http://www.twitter.com/$1\&quot; rel=\&quot;external nofollow\&quot;&gt;@$1&lt;/a&gt;&quot;);

            input = Regex.Replace(input, strTwitterTags, &quot; &lt;a href=\&quot;http://search.twitter.com/search?q=$1\&quot; rel=\&quot;external nofollow\&quot;&gt;#$1&lt;/a&gt;&quot;);

            return input;
        }
</pre></p>
<p>Now we have the ability to enable href&#8217;s, @, # tags as links, let go back to GetFeed() function and added it in.</p>
<p><pre class="brush: csharp;">
      Title = ConvertTwitterLinks((string)Tweet.Element(AtomNs + &quot;title&quot;)),
</pre></p>
<p>Cool.. But can we do something with the Date/Time? Well we can, so lets do that.</p>
<p><pre class="brush: csharp;">
private static String ConvertTimeDiff(DateTime tweetTime)
        {
            //Setup our timestamps
            DateTime Dt1 = DateTime.Now;
            DateTime Dt2 = tweetTime;
            TimeSpan Ts = Dt1.Subtract(Dt2);

            string TimeDiff = String.Empty;

            //if it's been more than 24 hours, then returns day/s
            if (Ts.TotalHours &gt; 24)
            {
                TimeDiff = String.Format(Ts.Days &gt;= 2 ? &quot;{0} days, &quot; : &quot;{0} day, &quot;, Ts.Days);
            }

            //if it's been more than 60 minutes, then returns hour/s
            if (Ts.TotalMinutes &gt; 60)
            {
                TimeDiff = Ts.Hours &gt;= 2
                               ? TimeDiff + String.Format(&quot;{0} hrs, &quot;, Ts.Hours)
                               : TimeDiff + String.Format(&quot;{0} hr, &quot;, Ts.Hours);
            }

            //finally return all our string of days/hours/minutes
            return TimeDiff + String.Format(&quot;{0} minutes&quot;, Ts.Minutes);
        }
</pre></p>
<p>Now we just need to parse the date/time from the Twitter feed and return our calculated time in text. We&#8217;ll change a line in the main reader function to this one.</p>
<p><pre class="brush: csharp;">
     Date = ConvertTimeDiff(DateTime.Parse((string)Tweet.Element(AtomNs + &quot;published&quot;)))
</pre></p>
<p>Now that&#8217;s all done! </p>
<p>Let hook up the Controller to use your new excellent Twitter plugin.</p>
<p>Open /Controllers/HomeController.cs and create a new ActionResult to handle the PartialView we will be using, thus allowing us to use the Twitter Plugin on any page.</p>
<p>First add a reference to our &#8220;Models&#8221; where our new function is.</p>
<p><pre class="brush: csharp;">
using TwitterFeedReader.Models;
</pre></p>
<p>Next create a new &#8220;ActionResult&#8221; for the Twitter Feed.</p>
<p><pre class="brush: csharp;">
 public ActionResult TwitterFeed(int tweetCount)
        {
                //could extend to take URL and cache time
                var Twitter = new TwitterReader();
                var Tg = Twitter.GetFeed(tweetCount);
                return PartialView(Tg);
        }
</pre></p>
<p>Great we are almost there. Now lets create our PartialView to handle displaying the Tweets. Right click on &#8220;TwitterFeed&#8221; in the name of the ActionResult definition and select &#8220;Add View&#8221;, you should then be presented with the following dialog box, which we will instruct to be Strongly Typed, and as PartialView..</p>
<p><a href="http://arranmaclean.files.wordpress.com/2011/04/screen-shot-2011-04-24-at-11-15-31.png"><img class="aalignnone size-medium wp-image-347" title="Screen shot 2011-04-24 at 11.15.31" src="http://arranmaclean.files.wordpress.com/2011/04/screen-shot-2011-04-24-at-11-15-31.png?w=300&#038;h=295" alt="New View Dialog Partial View" width="300" height="295" /></a></p>
<p>Let populate the View with a simple HTML definition list element and the always ubiquitous UL LI.</p>
<p><pre class="brush: xml;">
@model IEnumerable&lt;/pre&gt;
&lt;dl&gt;&lt;dt&gt;Twitter Feed&lt;/dt&gt;
&lt;dd&gt;
&lt;ul&gt;
     @foreach (var item in Model)
     {
	&lt;li&gt;@Html.Raw(item.Title) (sent @item.Date ago)&lt;/li&gt;
     }
&lt;/ul&gt;
&lt;/dd&gt;&lt;/dl&gt;
&lt;pre&gt;
</pre></p>
<p>I&#8217;ll let you worry about the styling. Now on to the final part&#8230; Adding the call to the Partial View from our page. Now we can either pop it into the _Layout.cshtml (or Site.Master) or we in the individual view. For the purpose of this quick blog post I will call the Partial View from the /Views/Home/Index.cshtml</p>
<p><pre class="brush: xml;">
      @{Html.RenderAction(&quot;TwitterFeed&quot;, &quot;Home&quot;, new { tweetCount = 5});}
</pre></p>
<p>There we go, All done. So you should have something like this :</p>
<p><a href="http://arranmaclean.files.wordpress.com/2011/04/screen-shot-2011-04-24-at-15-03-57.png"><img src="http://arranmaclean.files.wordpress.com/2011/04/screen-shot-2011-04-24-at-15-03-57.png?w=300&#038;h=148" alt="Example Screen Shot" title="Screen shot 2011-04-24 at 15.03.57" width="300" height="148" class="alignnone size-medium wp-image-398" /></a></p>
<p>Full project code is available for download (See right hand navigation)</p>
<p>If you found this helpful and would like to <strong>buy me a beer</strong> to say thanks, please <a href="https://www.paypal.com/cgi-bin/webscr?cmd=_s-xclick&amp;hosted_button_id=NKKD5YY5DQQK8"><img src="https://www.paypal.com/en_US/i/btn/x-click-but21.gif" alt="" /></a></p>
<p><a title="Follow me on Twitter" href="http://twitter.com/ArranM" target="_blank">@ArranM</a></p>
<br />  <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gocomments/arranmaclean.wordpress.com/339/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/comments/arranmaclean.wordpress.com/339/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/godelicious/arranmaclean.wordpress.com/339/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/delicious/arranmaclean.wordpress.com/339/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gofacebook/arranmaclean.wordpress.com/339/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/facebook/arranmaclean.wordpress.com/339/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gotwitter/arranmaclean.wordpress.com/339/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/twitter/arranmaclean.wordpress.com/339/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gostumble/arranmaclean.wordpress.com/339/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/stumble/arranmaclean.wordpress.com/339/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/godigg/arranmaclean.wordpress.com/339/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/digg/arranmaclean.wordpress.com/339/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/goreddit/arranmaclean.wordpress.com/339/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/reddit/arranmaclean.wordpress.com/339/" /></a> <img alt="" border="0" src="http://stats.wordpress.com/b.gif?host=arranmaclean.wordpress.com&amp;blog=7827390&amp;post=339&amp;subd=arranmaclean&amp;ref=&amp;feed=1" width="1" height="1" />]]></content:encoded>
			<wfw:commentRss>http://arranmaclean.wordpress.com/2011/04/24/twitter-plugin-mvc-asp/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
	
		<media:content url="http://1.gravatar.com/avatar/be4d11a40f2a59dd3b0a7bb66032149a?s=96&#38;d=identicon&#38;r=G" medium="image">
			<media:title type="html">Arran</media:title>
		</media:content>

		<media:content url="http://arranmaclean.files.wordpress.com/2011/04/screen-shot-2011-04-24-at-09-39-561.png?w=300" medium="image">
			<media:title type="html">Screen shot 2011-04-24 at 09.39.56</media:title>
		</media:content>

		<media:content url="http://arranmaclean.files.wordpress.com/2011/04/screen-shot-2011-04-24-at-09-45-15.png?w=300" medium="image">
			<media:title type="html">Adding new class model</media:title>
		</media:content>

		<media:content url="http://arranmaclean.files.wordpress.com/2011/04/screen-shot-2011-04-24-at-11-15-31.png?w=300" medium="image">
			<media:title type="html">Screen shot 2011-04-24 at 11.15.31</media:title>
		</media:content>

		<media:content url="http://arranmaclean.files.wordpress.com/2011/04/screen-shot-2011-04-24-at-15-03-57.png?w=300" medium="image">
			<media:title type="html">Screen shot 2011-04-24 at 15.03.57</media:title>
		</media:content>

		<media:content url="https://www.paypal.com/en_US/i/btn/x-click-but21.gif" medium="image" />
	</item>
		<item>
		<title>2010 in review</title>
		<link>http://arranmaclean.wordpress.com/2011/01/02/2010-in-review/</link>
		<comments>http://arranmaclean.wordpress.com/2011/01/02/2010-in-review/#comments</comments>
		<pubDate>Sun, 02 Jan 2011 15:27:10 +0000</pubDate>
		<dc:creator>ArranM</dc:creator>
				<category><![CDATA[General rambles]]></category>

		<guid isPermaLink="false">http://arranmaclean.wordpress.com/?p=322</guid>
		<description><![CDATA[The stats helper monkeys at WordPress.com mulled over how this blog did in 2010, and here&#8217;s a high level summary of its overall blog health: The Blog-Health-o-Meter™ reads This blog is doing awesome!. Crunchy numbers A Boeing 747-400 passenger jet can hold 416 passengers. This blog was viewed about 2,000 times in 2010. That&#8217;s about [...]<img alt="" border="0" src="http://stats.wordpress.com/b.gif?host=arranmaclean.wordpress.com&amp;blog=7827390&amp;post=322&amp;subd=arranmaclean&amp;ref=&amp;feed=1" width="1" height="1" />]]></description>
			<content:encoded><![CDATA[<p>The stats helper monkeys at WordPress.com mulled over how this blog did in 2010, and here&#8217;s a high level summary of its overall blog health:</p>
<p><img style="border:1px solid #ddd;background:#f5f5f5;padding:20px;" src="http://s0.wp.com/i/annual-recap/meter-healthy2.gif" alt="Healthy blog!" width="250" height="183" /></p>
<p>The <em>Blog-Health-o-Meter™</em> reads This blog is doing awesome!.</p>
<h2>Crunchy numbers</h2>
<p><a href="http://arranmaclean.files.wordpress.com/2010/07/webdeploymentreleasemode_thumb.jpg"><img style="max-height:230px;float:right;border:1px solid #ddd;background:#fff;margin:0 0 1em 1em;padding:6px;" src="http://arranmaclean.files.wordpress.com/2010/07/webdeploymentreleasemode_thumb.jpg?w=288" alt="Featured image" /></a></p>
<p>A Boeing 747-400 passenger jet can hold 416 passengers.  This blog was viewed about <strong>2,000</strong> times in 2010.  That&#8217;s about 5 full 747s.</p>
<p>In 2010, there were <strong>6</strong> new posts, not bad for the first year! There were <strong>47</strong> pictures uploaded, taking up a total of 2mb. That&#8217;s about 4 pictures per month.</p>
<p>The busiest day of the year was November 16th with <strong>54</strong> views. The most popular post that day was <a style="color:#08c;" href="http://arranmaclean.wordpress.com/stag-night/">Stag night</a>.<span id="more-322"></span></p>
<h2>Where did they come from?</h2>
<p>The top referring sites in 2010 were <strong>twitter.com</strong>, <strong>aspdotnetmvc.com</strong>, <strong>Google Reader</strong>, <strong>en.wordpress.com</strong>, and <strong>instapaper.com</strong>.</p>
<p>Some visitors came searching, mostly for <strong>visual studio combine css files</strong>, <strong>visual studio javascript minifier</strong>, <strong>visual studio minify</strong>, <strong>minify html</strong>, and <strong>visual studio 2010 minified script jquery</strong>.</p>
<h2>Attractions in 2010</h2>
<p>These are the posts and pages that got the most views in 2010.</p>
<div style="clear:left;float:left;font-size:24pt;line-height:1em;margin:-5px 10px 20px 0;">1</div>
<p><a style="margin-right:10px;" href="http://arranmaclean.wordpress.com/stag-night/">Stag night</a> <span style="color:#999;font-size:8pt;">November 2010</span></p>
<div style="clear:left;float:left;font-size:24pt;line-height:1em;margin:-5px 10px 20px 0;">2</div>
<p><a style="margin-right:10px;" href="http://arranmaclean.wordpress.com/2010/07/22/minify-combine-css-and-javascript-with-visual-studio/">Minify, Combine CSS and JavaScript with Visual Studio</a> <span style="color:#999;font-size:8pt;">July 2010</span><br />
1 comment</p>
<div style="clear:left;float:left;font-size:24pt;line-height:1em;margin:-5px 10px 20px 0;">3</div>
<p><a style="margin-right:10px;" href="http://arranmaclean.wordpress.com/2010/08/10/minify-html-with-net-mvc-actionfilter/">Minify HTML with .NET MVC ActionFilter</a> <span style="color:#999;font-size:8pt;">August 2010</span><br />
4 comments</p>
<div style="clear:left;float:left;font-size:24pt;line-height:1em;margin:-5px 10px 20px 0;">4</div>
<p><a style="margin-right:10px;" href="http://arranmaclean.wordpress.com/2010/07/20/net-mvc-upload-a-csv-file-to-database-with-bulk-upload/">.NET MVC, Upload a CSV file to Database with Bulk upload</a> <span style="color:#999;font-size:8pt;">July 2010</span></p>
<div style="clear:left;float:left;font-size:24pt;line-height:1em;margin:-5px 10px 20px 0;">5</div>
<p><a style="margin-right:10px;" href="http://arranmaclean.wordpress.com/2010/08/05/cache-for-speed-with-net/">Cache for speed with .Net</a> <span style="color:#999;font-size:8pt;">August 2010</span></p>
<br />  <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gocomments/arranmaclean.wordpress.com/322/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/comments/arranmaclean.wordpress.com/322/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/godelicious/arranmaclean.wordpress.com/322/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/delicious/arranmaclean.wordpress.com/322/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gofacebook/arranmaclean.wordpress.com/322/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/facebook/arranmaclean.wordpress.com/322/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gotwitter/arranmaclean.wordpress.com/322/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/twitter/arranmaclean.wordpress.com/322/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gostumble/arranmaclean.wordpress.com/322/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/stumble/arranmaclean.wordpress.com/322/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/godigg/arranmaclean.wordpress.com/322/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/digg/arranmaclean.wordpress.com/322/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/goreddit/arranmaclean.wordpress.com/322/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/reddit/arranmaclean.wordpress.com/322/" /></a> <img alt="" border="0" src="http://stats.wordpress.com/b.gif?host=arranmaclean.wordpress.com&amp;blog=7827390&amp;post=322&amp;subd=arranmaclean&amp;ref=&amp;feed=1" width="1" height="1" />]]></content:encoded>
			<wfw:commentRss>http://arranmaclean.wordpress.com/2011/01/02/2010-in-review/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
	
		<media:content url="http://1.gravatar.com/avatar/be4d11a40f2a59dd3b0a7bb66032149a?s=96&#38;d=identicon&#38;r=G" medium="image">
			<media:title type="html">Arran</media:title>
		</media:content>

		<media:content url="http://s0.wp.com/i/annual-recap/meter-healthy2.gif" medium="image">
			<media:title type="html">Healthy blog!</media:title>
		</media:content>

		<media:content url="http://arranmaclean.files.wordpress.com/2010/07/webdeploymentreleasemode_thumb.jpg?w=288" medium="image">
			<media:title type="html">Featured image</media:title>
		</media:content>
	</item>
		<item>
		<title>Convert .net MVC Model to KeyPair QueryString</title>
		<link>http://arranmaclean.wordpress.com/2010/11/07/convert-net-mvc-model-to-keypair-querystring/</link>
		<comments>http://arranmaclean.wordpress.com/2010/11/07/convert-net-mvc-model-to-keypair-querystring/#comments</comments>
		<pubDate>Sun, 07 Nov 2010 19:35:19 +0000</pubDate>
		<dc:creator>ArranM</dc:creator>
				<category><![CDATA[Code Examples]]></category>
		<category><![CDATA[.NET]]></category>
		<category><![CDATA[CSV]]></category>
		<category><![CDATA[Model]]></category>
		<category><![CDATA[MVC]]></category>
		<category><![CDATA[Serialise]]></category>

		<guid isPermaLink="false">http://arranmaclean.wordpress.com/?p=262</guid>
		<description><![CDATA[Very quick post today; I had a need today to create a QueryString from a Model (Serialise). There was a good reason why, which I won&#8217;t go into; Lets just say it involves SEO requirements, ever changing model, pagination and price sorting. So lets get to it and see what we can do. We need [...]<img alt="" border="0" src="http://stats.wordpress.com/b.gif?host=arranmaclean.wordpress.com&amp;blog=7827390&amp;post=262&amp;subd=arranmaclean&amp;ref=&amp;feed=1" width="1" height="1" />]]></description>
			<content:encoded><![CDATA[<p>Very quick post today;</p>
<p>I had a need today to create a QueryString from a Model (Serialise). There was a good reason why, which I won&#8217;t go into; Lets just say it involves SEO requirements, ever changing model, pagination and price sorting.</p>
<p>So lets get to it and see what we can do. We need to build a function that will take any Model and strip it to any Key and Value&#8217;s. <span id="more-262"></span></p>
<p>First, we&#8217;ll set-up a basic model class in &#8220;/Models/SearchItems.cs&#8221;.</p>
<p>Model:</p>
<p><pre class="brush: csharp; pad-line-numbers: true;">
using System;

namespace ModelToKeyValuePairs.Models
{
    public class SearchItems
    {
            public SearchItems()
            {
                Makes = &quot;Any&quot;;
                Models = &quot;Any&quot;;
                Colour = &quot;Any&quot;;
                Location = &quot;Any&quot;;
            }
            public string Makes { get; set; }
            public string Models { get; set; }
            public string Price { get; set; }
            public string Colour { get; set; }
            public string Location { get; set; }
    }
}
</pre></p>
<p>As you see, this is a very basic mode with a bunch of default values.<br />
In order to make this a little more reusable, I want to allow any model to be used with the function, so I&#8217;m going to push Gerenic Types.</p>
<p>Now to create a simple static function with all my others &#8220;/Extentions/StaticFunctions.cs&#8221;</p>
<p>Function:</p>
<p><pre class="brush: csharp; pad-line-numbers: true;">
using System;
using System.Linq;
using System.Text;
using System.Web.UI;

namespace ModelToKeyValuePairs.Extenstions
{
    public class StaticFunctions
    {
        public static string ConvertToQueryString&lt;T&gt;(T obj)
        {
            var keyPairs = typeof(T).GetProperties().Select(p =&gt; new Pair(p.Name, p.GetValue(obj, null)));
            StringBuilder sb = new StringBuilder();
            foreach (var item in keyPairs)
            {
                sb.Append(String.Format(&quot;{0}={1}&amp;&quot;, item.First, item.Second));
            }
            return &quot;?&quot; + sb.ToString().Substring(0, sb.Length - 1).ToLower(); //remove last &amp;
        }
    }
}
</pre></p>
<p>We pass in our model to ConvertToQueryString, and use <a title="Find out more about GetProperties" href="http://msdn.microsoft.com/en-us/library/ms554749.aspx" target="_blank">GetProperties() </a>and a little Linq query to retrieve the model attributes for the Key Name and the Key Value.</p>
<p>We then need to loop though the results and use StringBuilder to join all the queries together. I&#8217;m sure this could be refactored to use string.Join and converting it all to an array.</p>
<p>Once we have our output string we just need to chop of the last &amp; to keep it all tidy.</p>
<p>Now lets put the code in to action and drop it in to a simple view.</p>
<p>Usage:<br />
<pre class="brush: csharp; pad-line-numbers: true;">
using System;
using System.Web.Mvc;
using ModelToKeyValuePairs.Models;
using ModelToKeyValuePairs.Extenstions;

namespace ModelToKeyValuePairs.Controllers
{
  [HandleError]
  public class HomeController : Controller
  {
        public ActionResult Index()
        {
            ViewData[&quot;Message&quot;] = &quot;Welcome to ASP.NET MVC!&quot;;

            SearchItems item = new SearchItems();
            var query = StaticFunctions.ConvertToQueryString&lt;SearchItems&gt;(item);

            ViewData[&quot;Query&quot;] = query;

            return View();
        }
   }
}
</pre></p>
<p>Now we are done, left just run the example and see the result<br />
The result :</p>
<p><pre class="brush: csharp;">
?makes=any&amp;models=any&amp;price=&amp;colour=any&amp;location=any
</pre></p>
<p>Sure there are more things you can do with this little snippet for example, create a CVS string. I&#8217;d love to hear about your examples.</p>
<p>I hope this will help someone somewhere, should your have a similar need. You can download the working example code from the right hand menu.</p>
<p>If you found this helpful and would like to <strong>buy me a beer</strong> to say thanks, please <a href="https://www.paypal.com/cgi-bin/webscr?cmd=_s-xclick&amp;hosted_button_id=NKKD5YY5DQQK8"><img src="https://www.paypal.com/en_US/i/btn/x-click-but21.gif" alt="" /></a></p>
<p>@ArranM</p>
<br />  <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gocomments/arranmaclean.wordpress.com/262/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/comments/arranmaclean.wordpress.com/262/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/godelicious/arranmaclean.wordpress.com/262/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/delicious/arranmaclean.wordpress.com/262/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gofacebook/arranmaclean.wordpress.com/262/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/facebook/arranmaclean.wordpress.com/262/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gotwitter/arranmaclean.wordpress.com/262/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/twitter/arranmaclean.wordpress.com/262/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gostumble/arranmaclean.wordpress.com/262/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/stumble/arranmaclean.wordpress.com/262/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/godigg/arranmaclean.wordpress.com/262/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/digg/arranmaclean.wordpress.com/262/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/goreddit/arranmaclean.wordpress.com/262/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/reddit/arranmaclean.wordpress.com/262/" /></a> <img alt="" border="0" src="http://stats.wordpress.com/b.gif?host=arranmaclean.wordpress.com&amp;blog=7827390&amp;post=262&amp;subd=arranmaclean&amp;ref=&amp;feed=1" width="1" height="1" />]]></content:encoded>
			<wfw:commentRss>http://arranmaclean.wordpress.com/2010/11/07/convert-net-mvc-model-to-keypair-querystring/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
	
		<media:content url="http://1.gravatar.com/avatar/be4d11a40f2a59dd3b0a7bb66032149a?s=96&#38;d=identicon&#38;r=G" medium="image">
			<media:title type="html">Arran</media:title>
		</media:content>

		<media:content url="https://www.paypal.com/en_US/i/btn/x-click-but21.gif" medium="image" />
	</item>
		<item>
		<title>Minify HTML with .NET MVC ActionFilter</title>
		<link>http://arranmaclean.wordpress.com/2010/08/10/minify-html-with-net-mvc-actionfilter/</link>
		<comments>http://arranmaclean.wordpress.com/2010/08/10/minify-html-with-net-mvc-actionfilter/#comments</comments>
		<pubDate>Tue, 10 Aug 2010 09:55:22 +0000</pubDate>
		<dc:creator>ArranM</dc:creator>
				<category><![CDATA[Code Examples]]></category>
		<category><![CDATA[.NET]]></category>
		<category><![CDATA[MVC]]></category>
		<category><![CDATA[Speed]]></category>
		<category><![CDATA[Whitespace]]></category>

		<guid isPermaLink="false">https://arranmaclean.wordpress.com/?p=206</guid>
		<description><![CDATA[To make our site a tight as possible, I thought we&#8217;d explore the idea of removing the white space in our generated HTML. I&#8217;ve had this idea for a long time, but after reading @hugoware post about removing white space, I decided to implement it in my own projects. As with any good code, let&#8217;s [...]<img alt="" border="0" src="http://stats.wordpress.com/b.gif?host=arranmaclean.wordpress.com&amp;blog=7827390&amp;post=206&amp;subd=arranmaclean&amp;ref=&amp;feed=1" width="1" height="1" />]]></description>
			<content:encoded><![CDATA[<p>To make our site a tight as possible, I thought we&#8217;d explore the idea of removing the white space in our generated HTML.</p>
<p>I&#8217;ve had this idea for a long time, but after reading <a title="Follow Hugoware" href="http://twitter.com/hugoware" target="_blank">@hugoware</a> <a href="http://somewebguy.wordpress.com/2009/05/09/free-bandwidth-for-all-asp-net-users/" target="_blank">post about removing white space</a>, I decided to implement it in my own projects. As with any good code, let&#8217;s stand on the shoulder of giants and make it fit our needs.</p>
<p>Normally, if we did a &#8220;View Source&#8221; on our web page we would see something like this:</p>
<p><a href="http://arranmaclean.files.wordpress.com/2010/08/beforewhitespacesource.jpg" target="_blank"><img title="Before Whitespace Source" src="http://arranmaclean.files.wordpress.com/2010/08/beforewhitespacesource.jpg?w=270&#038;h=158" alt="MVC Vanilla app, view source." width="270" height="158" /></a></p>
<p>Now a lot of good HTML developers like to leave closing html comments and notes in their code. This helps them track end elements in nested code.  For example:</p>
<p><pre class="brush: xml;">
&lt;div id=&quot;wrap&quot;&gt;
    &lt;div id=&quot;content&quot;&gt;
     content goes here, with more elements of &lt;&gt;
    &lt;/div&gt; &lt;!--end content--&gt;
&lt;/div&gt; &lt;!--end wrap --&gt;
</pre></p>
<p>The issue we may face on larger pages is there can be a lot of notes and end line comments which can add to the overall size of your page, which the user doesn&#8217;t care about but the developer needs for easy editing later.<span id="more-206"></span></p>
<h3>So how do we achieve this?</h3>
<p>We need to minify the generated HTML, thus removing the comments and whitespace as the page is run. Very much the same process we did when <a title="Minify CSS and JavaScript" href="http://arranmaclean.wordpress.com/2010/07/22/minify-combine-css-and-javascript-with-visual-studio/" target="_self">minifying our CSS and JavaScript</a> in an earlier post.</p>
<p>As we are working on an .NET MVC project we will look at building an <a title="Find out more about ActionFilters" href="http://www.asp.net/mvc/tutorials/understanding-action-filters-cs" target="_blank">ActionFilter</a>.</p>
<h3>The tools</h3>
<ul>
<li>Microsoft Visual Studio 2010 or Trail editions (<a title="Download Visual Studio" href="http://www.microsoft.com/express/downloads/" target="_blank">Download via Web platform installer</a>)</li>
<li>A little time to look good.</li>
</ul>
<h3>Creating the ActionFilter</h3>
<p>We will start as always with a standard vanilla <a href="http://en.wikipedia.org/wiki/Model%E2%80%93view%E2%80%93controller" target="_blank">MVC</a> (Model View Controller) .NET application install, good old “File &gt; New Project &gt; ASP.NET MVC Web Application”</p>
<p><a href="http://arranmaclean.files.wordpress.com/2010/07/filenewproject.jpg" target="_blank"><img title="File new project" src="http://arranmaclean.files.wordpress.com/2010/07/filenewproject_thumb.jpg?w=255&#038;h=178&#038;h=178" border="0" alt="File new project" width="255" height="178" /></a> <a href="http://arranmaclean.files.wordpress.com/2010/07/defaultmvcscreen1.jpg" target="_blank"><img title="Default MVC screen" src="http://arranmaclean.files.wordpress.com/2010/07/defaultmvcscreen_thumb1.jpg?w=244&#038;h=178&#038;h=178" border="0" alt="Default MVC screen" width="244" height="178" /></a></p>
<p>Next we will create a folder to hold our ActionFilter, mm what should I call it?</p>
<p> <img class="alignnone size-medium wp-image-218" title="ActionFilter Folder" src="http://arranmaclean.files.wordpress.com/2010/08/addactionfilterfolder.jpg?w=245&#038;h=300" alt="" width="245" height="300" /></p>
<p>Right click on this folder and add a new class called &#8216;RemoveWhiteSpace.cs&#8217; or whatever you thing is best for you. Your class should look something like this.</p>
<p><pre class="brush: csharp;">

using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;

namespace RemoveWhiteSpace.ActionFilters
{
         public class WhiteSpaceFilter
         {

         }
}
</pre></p>
<p>Now to add our Inheritance on the <a title="Find out more about Stream" href="http://msdn.microsoft.com/en-us/library/system.io.stream.aspx">Stream</a> and change our &#8216;Using&#8217; statements to only the ones we need. Thus</p>
<p><pre class="brush: csharp;">
using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;

namespace RemoveWhiteSpace.ActionFilters
{
         public class WhiteSpaceFilter : Stream
         {

         }
}
</pre></p>
<p>The Stream requires we implement inherited abstract members, so let&#8217;s add the basics to our class and alter the constructor to allow for stream input and filter params</p>
<p><pre class="brush: csharp;">
&lt;pre&gt;using System;
using System.IO;
using System.Text;
using System.Web.Mvc;
using System.Text.RegularExpressions;

namespace RemoveWhiteSpace.ActionFilters
{
    public class WhiteSpaceFilter : Stream
    {

        private Stream _shrink;
        private Func&lt;string, string&gt; _filter;

        public WhiteSpaceFilter(Stream shrink, Func&lt;string, string&gt; filter)
        {
            _shrink = shrink;
            _filter = filter;
        }

 
        public override bool CanRead { get { return true; } }
        public override bool CanSeek { get { return true; } }
        public override bool CanWrite { get { return true; } }
        public override void Flush() { _shrink.Flush(); }
        public override long Length { get { return 0; } }
        public override long Position { get; set; }
        public override int Read(byte[] buffer, int offset, int count)
        {
            return _shrink.Read(buffer, offset, count);
        }
        public override long Seek(long offset, SeekOrigin origin)
        {
            return _shrink.Seek(offset, origin);
        }
        public override void SetLength(long value)
        {
            _shrink.SetLength(value);
        }
        public override void Close()
        {
            _shrink.Close();
        }

        public override void Write(byte[] buffer, int offset, int count)
        {
            // capture the data and convert to string 
            byte[] data = new byte[count];
            Buffer.BlockCopy(buffer, offset, data, 0, count);
            string s = Encoding.Default.GetString(buffer);

            // filter the string
            s = _filter(s);

            // write the data to stream 
            byte[] outdata = Encoding.Default.GetBytes(s);
            _shrink.Write(outdata, 0, outdata.GetLength(0));
        }
    }
}
</pre></p>
<p>Next we need to add the ActionFilter Attribute. This allows us to decorate our controller later with our minify filter.</p>
<p><pre class="brush: csharp;">
&lt;pre&gt;public class WhitespaceFilterAttribute : ActionFilterAttribute
    {

        public override void OnActionExecuting(ActionExecutingContext filterContext)
        {

            var request = filterContext.HttpContext.Request;
            var response = filterContext.HttpContext.Response;

            response.Filter = new WhiteSpaceFilter(response.Filter, s =&gt;
                    {
                        s = Regex.Replace(s, @&quot;\s+&quot;, &quot; &quot;);
                        s = Regex.Replace(s, @&quot;\s*\n\s*&quot;, &quot;\n&quot;);
                        s = Regex.Replace(s, @&quot;\s*\&gt;\s*\&lt;\s*&quot;, &quot;&gt;&lt;&quot;);
                        s = Regex.Replace(s, @&quot;&lt;!--(.*?)--&gt;&quot;, &quot;&quot;);   //Remove comments

                        // single-line doctype must be preserved 
                        var firstEndBracketPosition = s.IndexOf(&quot;&gt;&quot;);
                        if (firstEndBracketPosition &gt;= 0)
                        {
                            s = s.Remove(firstEndBracketPosition, 1);
                            s = s.Insert(firstEndBracketPosition, &quot;&gt;&quot;);
                        }
                        return s;
                    });
                   
            }

    }&lt;/pre&gt;
  </pre></p>
<p>We are almost done, we just need to put it all together and decorate our HomeController.cs with the new ActionFilter.   First we need to add another &#8216;Using&#8217; to HomeController</p>
<p><pre class="brush: csharp;">
using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.Mvc;
using RemoveWhiteSpace.ActionFilters;  //Minify HTML Filter
  </pre></p>
<p>Now to minify our HomeController, you can decorate either on the whole controller or just on an &#8216;ActionResult&#8217;</p>
<p><pre class="brush: csharp;">
using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.Mvc;
using RemoveWhiteSpace.ActionFilters; //Minify HTML Filter

namespace RemoveWhiteSpace.Controllers
{
    [HandleError]
    [WhitespaceFilter]
    public class HomeController : Controller
    {
        public ActionResult Index()
        {
            ViewData[&quot;Message&quot;] = &quot;Welcome to ASP.NET MVC!&quot;;

            return View();
        }

        public ActionResult About()
        {
            return View();
        }
    }
}
</pre></p>
<p> With the Filter running we can now see our HTML source code looks a lot different.</p>
<p><a href="http://arranmaclean.files.wordpress.com/2010/08/afterwhitespacesource.jpg"><img class="alignnone size-medium wp-image-220" title="After WhiteSpace Source" src="http://arranmaclean.files.wordpress.com/2010/08/afterwhitespacesource.jpg?w=300&#038;h=175" alt="" width="300" height="175" /></a><br />
This is just a basic page, but comparing the standard HTML page against the minified version we can see we have reduced the download file size even before we add <a title="View post about Gzip/Deflate" href="http://arranmaclean.wordpress.com/2010/07/29/simple-gzip-deflate-in-net/" target="_self">Gzip/Deflate</a><br />
Before:<br />
<a href="http://arranmaclean.files.wordpress.com/2010/08/beforewhitespacestats.jpg?w=300"></a><a href="http://arranmaclean.files.wordpress.com/2010/08/beforewhitespacestats1.jpg" target="_blank"><img class="alignnone size-large wp-image-234" title="Before WhiteSpace Stats" src="http://arranmaclean.files.wordpress.com/2010/08/beforewhitespacestats1.jpg?w=813&#038;h=196" alt="" width="813" height="196" /></a><br />
After:<br />
<a href="http://arranmaclean.files.wordpress.com/2010/08/afterwhitespacestats.jpg?w=300"></a></p>
<h3><a href="http://arranmaclean.files.wordpress.com/2010/08/afterwhitespacestats1.jpg" target="_blank"><img class="alignnone size-large wp-image-235" title="After WhiteSpace Stats" src="http://arranmaclean.files.wordpress.com/2010/08/afterwhitespacestats1.jpg?w=812&#038;h=194" alt="" width="812" height="194" /></a></h3>
<h3>Finally</h3>
<p>In the last few posts we have covered some of the basics of speeding up your web-site. Putting all these together can really make your pages fly. Now it doesn&#8217;t end there, it might be worth you looking at sockets and other alternative options, base64 image in-line to reduce the number http calls. Speed is an ever moving target.</p>
<p>I hope what I shown you over the last few posts helps.</p>
<p>Full project code is available for download (See right hand navigation)</p>
<p>If you found this helpful and would like to <strong>buy me a beer</strong> to say thanks, please <a href="https://www.paypal.com/cgi-bin/webscr?cmd=_s-xclick&amp;hosted_button_id=NKKD5YY5DQQK8"><img src="https://www.paypal.com/en_US/i/btn/x-click-but21.gif" alt="" /></a></p>
<p><a title="Follow me on Twitter" href="http://twitter.com/ArranM" target="_blank">@ArranM</a></p>
<br />  <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gocomments/arranmaclean.wordpress.com/206/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/comments/arranmaclean.wordpress.com/206/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/godelicious/arranmaclean.wordpress.com/206/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/delicious/arranmaclean.wordpress.com/206/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gofacebook/arranmaclean.wordpress.com/206/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/facebook/arranmaclean.wordpress.com/206/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gotwitter/arranmaclean.wordpress.com/206/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/twitter/arranmaclean.wordpress.com/206/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gostumble/arranmaclean.wordpress.com/206/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/stumble/arranmaclean.wordpress.com/206/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/godigg/arranmaclean.wordpress.com/206/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/digg/arranmaclean.wordpress.com/206/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/goreddit/arranmaclean.wordpress.com/206/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/reddit/arranmaclean.wordpress.com/206/" /></a> <img alt="" border="0" src="http://stats.wordpress.com/b.gif?host=arranmaclean.wordpress.com&amp;blog=7827390&amp;post=206&amp;subd=arranmaclean&amp;ref=&amp;feed=1" width="1" height="1" />]]></content:encoded>
			<wfw:commentRss>http://arranmaclean.wordpress.com/2010/08/10/minify-html-with-net-mvc-actionfilter/feed/</wfw:commentRss>
		<slash:comments>5</slash:comments>
	
		<media:content url="http://1.gravatar.com/avatar/be4d11a40f2a59dd3b0a7bb66032149a?s=96&#38;d=identicon&#38;r=G" medium="image">
			<media:title type="html">Arran</media:title>
		</media:content>

		<media:content url="http://arranmaclean.files.wordpress.com/2010/08/beforewhitespacesource.jpg?w=300" medium="image">
			<media:title type="html">Before Whitespace Source</media:title>
		</media:content>

		<media:content url="http://arranmaclean.files.wordpress.com/2010/07/filenewproject_thumb.jpg?w=255&#38;h=178" medium="image">
			<media:title type="html">File new project</media:title>
		</media:content>

		<media:content url="http://arranmaclean.files.wordpress.com/2010/07/defaultmvcscreen_thumb1.jpg?w=244&#38;h=178" medium="image">
			<media:title type="html">Default MVC screen</media:title>
		</media:content>

		<media:content url="http://arranmaclean.files.wordpress.com/2010/08/addactionfilterfolder.jpg?w=245" medium="image">
			<media:title type="html">ActionFilter Folder</media:title>
		</media:content>

		<media:content url="http://arranmaclean.files.wordpress.com/2010/08/afterwhitespacesource.jpg?w=300" medium="image">
			<media:title type="html">After WhiteSpace Source</media:title>
		</media:content>

		<media:content url="http://arranmaclean.files.wordpress.com/2010/08/beforewhitespacestats1.jpg?w=1024" medium="image">
			<media:title type="html">Before WhiteSpace Stats</media:title>
		</media:content>

		<media:content url="http://arranmaclean.files.wordpress.com/2010/08/afterwhitespacestats1.jpg?w=1024" medium="image">
			<media:title type="html">After WhiteSpace Stats</media:title>
		</media:content>

		<media:content url="https://www.paypal.com/en_US/i/btn/x-click-but21.gif" medium="image" />
	</item>
		<item>
		<title>Cache for speed with .Net</title>
		<link>http://arranmaclean.wordpress.com/2010/08/05/cache-for-speed-with-net/</link>
		<comments>http://arranmaclean.wordpress.com/2010/08/05/cache-for-speed-with-net/#comments</comments>
		<pubDate>Thu, 05 Aug 2010 10:18:50 +0000</pubDate>
		<dc:creator>ArranM</dc:creator>
				<category><![CDATA[Code Examples]]></category>
		<category><![CDATA[.NET]]></category>
		<category><![CDATA[CSS]]></category>
		<category><![CDATA[Images]]></category>
		<category><![CDATA[Speed]]></category>

		<guid isPermaLink="false">https://arranmaclean.wordpress.com/?p=179</guid>
		<description><![CDATA[The better you can make your users experience the more they will like to use your site. One aspect is of this experience is speed. Following on from my previous post, we will look at adding simple caching to our project for another quick win, this is just one method of many. Caching really depends on [...]<img alt="" border="0" src="http://stats.wordpress.com/b.gif?host=arranmaclean.wordpress.com&amp;blog=7827390&amp;post=179&amp;subd=arranmaclean&amp;ref=&amp;feed=1" width="1" height="1" />]]></description>
			<content:encoded><![CDATA[<p>The better you can make your users experience the more they will like to use your site. One aspect is of this experience is speed.</p>
<p>Following on from my previous post, we will look at adding simple caching to our project for another quick win, this is just one method of many. Caching really depends on the size and type of your application and hosting environment.<span id="more-179"></span></p>
<h3>The tools</h3>
<ul>
<li>Microsoft Visual Studio 2010 or Trail editions (<a href="http://www.microsoft.com/express/downloads/">Download via Web platform installer</a>)</li>
<li>Mmm thats it!</li>
</ul>
<h3>Lets start</h3>
<p>We need to create a <a title="Find out more about HttpModule" href="http://msdn.microsoft.com/en-us/library/zec9k340(VS.71).aspx" target="_blank">HttpModule</a> to interface and handle our events.</p>
<p>Here we go again. “File &gt; New Project &gt; Windows &gt; Class Library”</p>
<p><a href="http://arranmaclean.files.wordpress.com/2010/08/filenew.jpg" target="_blank"><img class="wlDisabledImage" style="display:inline;border-width:0;" title="FileNew" src="http://arranmaclean.files.wordpress.com/2010/08/filenew_thumb.jpg?w=244&#038;h=170" border="0" alt="FileNew" width="244" height="170" /></a></p>
<p>Create a new class and call it eModule.cs , the name is not really important, it’s just what fits your best.</p>
<p>Now we should have something that look likes this:</p>
<p><pre class="brush: csharp; pad-line-numbers: true;">using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace ExpiresModule
{
    class eModule
    {
    }
}</pre></p>
<p>Lets tidy up our “using”, and add the ones we will need.</p>
<p>Remove :</p>
<p><pre class="brush: csharp; pad-line-numbers: false;">using System.Collections.Generic;
using System.Linq;
using System.Text;</pre></p>
<p>And add :</p>
<p><pre class="brush: csharp; pad-line-numbers: false;">using System.Web;
using System.IO;</pre></p>
<p>Now lets inherit from IHttpModule and set up the basic structure of the HttpModule. First we need to add “<a title="Learn more about System.Web" href="http://msdn.microsoft.com/en-us/library/system.web.aspx" target="_blank">System.Web</a>” to our references so we can work with IHttpModule.</p>
<p><a href="http://arranmaclean.files.wordpress.com/2010/08/addreference.jpg"><img class="wlDisabledImage" style="display:inline;border-width:0;" title="AddReference" src="http://arranmaclean.files.wordpress.com/2010/08/addreference_thumb.jpg?w=216&#038;h=244" border="0" alt="AddReference" width="216" height="244" /></a></p>
<p>Time to set up the basic frame work for our Caching module, We will need to add the Init() and if we want to be nice the Dispose() methods.</p>
<p><pre class="brush: csharp; pad-line-numbers: true;">namespace ExpiresModule
{
    public class eModule : IHttpModule
    {

        public void Dispose()
        {
            // Dispose();
        }

        public void Init(HttpApplication context)
        {

        }

    }
}</pre></p>
<p>Great thats a good start. Now we have to decide which file types we wish to cache. Lets go for static file types.</p>
<p><pre class="brush: csharp; pad-line-numbers: false;">private readonly static string[] CACHCED_STATIC_TYPES = new string[] {&quot;.jpg&quot;, &quot;.gif&quot;, &quot;.png&quot;,&quot;.css&quot;, &quot;.js&quot; };</pre></p>
<p>I think that covers the basics. Now to work with <a title="Find out what it does" href="http://msdn.microsoft.com/en-us/library/system.web.httpcontext.aspx" target="_blank">HttpContext</a> to deal with our item request to out static file types and respond back and set the expire headers for our static types.</p>
<p><pre class="brush: csharp; pad-line-numbers: true;">void context_AcquireRequestState(object sender, EventArgs e)
        {

            HttpContext context = HttpContext.Current;

            if (context != null &amp; context.Response != null)
            {

                string fileExtension = Path.GetExtension(context.Request.PhysicalPath).ToLower();

                if (context.Response.Cache == null || Array.BinarySearch(CACHCED_STATIC_TYPES, fileExtension) &lt; 0)
                    return;

                HttpCachePolicy cache = context.Response.Cache;

                cache.SetExpires(DateTime.Now.AddYears(30));
                cache.SetMaxAge(TimeSpan.FromDays(365.0 * 3.0));

            }

        }</pre></p>
<p>The important thing about caching it setting the cache date far enough in the future, YSlow and Google Page speed do like to be at least a couple of months. You might be thinking, what if I change my CSS file, I want to make sure the user see the latest version? I’ll cover that in a future post.</p>
<p>Time to add our event listener to Init() to trigger our function on request of a page load.</p>
<p><pre class="brush: csharp; pad-line-numbers: true;">public void Init(HttpApplication context)
        {

            context.BeginRequest += context_AcquireRequestState;
        }</pre></p>
<p>Well thats about it for our ExpiresModule. We should now have something like this:</p>
<p><pre class="brush: csharp; pad-line-numbers: true;">using System;
using System.Web;
using System.IO;

namespace ExpiresModule
{
    public class eModule : IHttpModule
    {
        private readonly static string[] CACHCED_STATIC_TYPES = new string[] {&quot;.jpg&quot;, &quot;.gif&quot;, &quot;.png&quot;,&quot;.css&quot;, &quot;.js&quot; };

        public void Dispose()
        {
            // Dispose();
        }

        public void Init(HttpApplication context)
        {

            context.BeginRequest += context_AcquireRequestState;
        }

        void context_AcquireRequestState(object sender, EventArgs e)
        {

            HttpContext context = HttpContext.Current;

            if (context != null &amp; context.Response != null)
            {

                string fileExtension = Path.GetExtension(context.Request.PhysicalPath).ToLower();

                if (context.Response.Cache == null || Array.BinarySearch(CACHCED_STATIC_TYPES, fileExtension) &lt; 0)
                    return;

                HttpCachePolicy cache = context.Response.Cache;

                cache.SetExpires(DateTime.Now.AddYears(30));
                cache.SetMaxAge(TimeSpan.FromDays(365.0 * 3.0));

            }

        }
    }
}</pre></p>
<h3>How do I use it?</h3>
<p>Once you have compile this module, we can add the release DLL as a reference in to any of your other projects.</p>
<p><a href="http://arranmaclean.files.wordpress.com/2010/08/addemodule.jpg" target="_blank"><img class="wlDisabledImage" style="display:inline;border-width:0;" title="AddeModule" src="http://arranmaclean.files.wordpress.com/2010/08/addemodule_thumb.jpg?w=244&#038;h=142" border="0" alt="AddeModule" width="244" height="142" /></a></p>
<p>Followed by a declaration in your web.config to initialise the HttpModule.</p>
<p><pre class="brush: csharp; pad-line-numbers: false;">
&lt;httpModules&gt;
       &lt;add name=&quot;ExpiresModule&quot; type=&quot;ExpiresModule.eModule, ExpiresModule&quot;/&gt;
&lt;/httpModules&gt;
</pre></p>
<h3>Finally</h3>
<p>I hope this might help someone, I’m sure a bit more work could make it better.</p>
<p>If you have access to IIS then the above code could be avoided and caching static types could be configure in IIS. You may also want to investigate “<a title="What is Etag?" href="http://en.wikipedia.org/wiki/HTTP_ETag" target="_blank">ETags</a>” and “<a title="Find out more about clientCache" href="http://msdn.microsoft.com/en-us/library/ms689443(VS.90).aspx" target="_blank">clientCache</a>” in web.config.</p>
<p>If you found this helpful and would like to <strong>buy me a beer</strong> to say thanks, please <a href="https://www.paypal.com/cgi-bin/webscr?cmd=_s-xclick&amp;hosted_button_id=NKKD5YY5DQQK8"><img src="https://www.paypal.com/en_US/i/btn/x-click-but21.gif" alt="" /></a></p>
<p>Full project code is available for download (See right hand navigation)</p>
<p><a title="Follow me on Twitter" href="http://twitter.com/ArranM" target="_blank">@ArranM</a></p>
<br />  <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gocomments/arranmaclean.wordpress.com/179/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/comments/arranmaclean.wordpress.com/179/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/godelicious/arranmaclean.wordpress.com/179/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/delicious/arranmaclean.wordpress.com/179/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gofacebook/arranmaclean.wordpress.com/179/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/facebook/arranmaclean.wordpress.com/179/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gotwitter/arranmaclean.wordpress.com/179/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/twitter/arranmaclean.wordpress.com/179/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gostumble/arranmaclean.wordpress.com/179/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/stumble/arranmaclean.wordpress.com/179/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/godigg/arranmaclean.wordpress.com/179/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/digg/arranmaclean.wordpress.com/179/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/goreddit/arranmaclean.wordpress.com/179/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/reddit/arranmaclean.wordpress.com/179/" /></a> <img alt="" border="0" src="http://stats.wordpress.com/b.gif?host=arranmaclean.wordpress.com&amp;blog=7827390&amp;post=179&amp;subd=arranmaclean&amp;ref=&amp;feed=1" width="1" height="1" />]]></content:encoded>
			<wfw:commentRss>http://arranmaclean.wordpress.com/2010/08/05/cache-for-speed-with-net/feed/</wfw:commentRss>
		<slash:comments>1</slash:comments>
	
		<media:content url="http://1.gravatar.com/avatar/be4d11a40f2a59dd3b0a7bb66032149a?s=96&#38;d=identicon&#38;r=G" medium="image">
			<media:title type="html">Arran</media:title>
		</media:content>

		<media:content url="http://arranmaclean.files.wordpress.com/2010/08/filenew_thumb.jpg" medium="image">
			<media:title type="html">FileNew</media:title>
		</media:content>

		<media:content url="http://arranmaclean.files.wordpress.com/2010/08/addreference_thumb.jpg" medium="image">
			<media:title type="html">AddReference</media:title>
		</media:content>

		<media:content url="http://arranmaclean.files.wordpress.com/2010/08/addemodule_thumb.jpg" medium="image">
			<media:title type="html">AddeModule</media:title>
		</media:content>

		<media:content url="https://www.paypal.com/en_US/i/btn/x-click-but21.gif" medium="image" />
	</item>
		<item>
		<title>Simple Gzip / Deflate in .Net</title>
		<link>http://arranmaclean.wordpress.com/2010/07/29/simple-gzip-deflate-in-net/</link>
		<comments>http://arranmaclean.wordpress.com/2010/07/29/simple-gzip-deflate-in-net/#comments</comments>
		<pubDate>Thu, 29 Jul 2010 09:23:01 +0000</pubDate>
		<dc:creator>ArranM</dc:creator>
				<category><![CDATA[Code Examples]]></category>
		<category><![CDATA[.NET]]></category>
		<category><![CDATA[Deflate]]></category>
		<category><![CDATA[Gzip]]></category>
		<category><![CDATA[Speed]]></category>

		<guid isPermaLink="false">https://arranmaclean.wordpress.com/?p=159</guid>
		<description><![CDATA[As promised this blog post is going to be a really short one. It’s just a quick win to enable your web forms or MVC application to utilise Gzip / Deflate compression and thus speed up the users experience of your web-site.<img alt="" border="0" src="http://stats.wordpress.com/b.gif?host=arranmaclean.wordpress.com&amp;blog=7827390&amp;post=159&amp;subd=arranmaclean&amp;ref=&amp;feed=1" width="1" height="1" />]]></description>
			<content:encoded><![CDATA[<p>As promised this blog post is going to be a really short one. It’s just a quick win to enable your web forms or MVC application to utilise Gzip / Deflate compression and thus speed up the users experience of your web-site.</p>
<h3>Why do this?</h3>
<p>If a page takes a while to download, many visitors will simply click elsewhere.</p>
<p>Some of the advantages of compression:</p>
<ul>
<li>Better experience for the user, better user retention</li>
<li>Reduces your bandwidth and hosting costs</li>
<li>Faster loading for slower connections</li>
</ul>
<p>But as you are reading this post, I’m guessing you already know all this and more so lets get on with the code.<span id="more-159"></span></p>
<h3>The code</h3>
<p>OK, now that is all out of the way lets stand on the shoulders of giants and quickly enable compression for our application.</p>
<p>Add the following section of code to your Global.asax</p>
<p>First we import the namespaces we need, Gzip and Deflate Stream classes as of .net 2.0 are now present in <code>System.IO.Compression</code><br />
<pre class="brush: csharp; pad-line-numbers: true;">
&lt;%@ Import Namespace=&quot;System.IO&quot; %&gt;
&lt;%@ Import Namespace=&quot;System.IO.Compression&quot; %&gt;
</pre></p>
<p>Next we need to declare the handle for the life cycle event in the Global.asax, <code>PreRequestHandlerExecute</code><br />
<pre class="brush: csharp; pad-line-numbers: true;">
void Application_PreRequestHandlerExecute(object sender, EventArgs e)
{

}</pre></p>
<p>Finally drop in the reset of the code and let the magic happen.<br />
<pre class="brush: csharp; pad-line-numbers: true;">
Enable Gzip or Deflate depending on Encoding
void Application_PreRequestHandlerExecute(object sender, EventArgs e)
{
    HttpApplication app = sender as HttpApplication;
    string acceptEncoding = app.Request.Headers[&quot;Accept-Encoding&quot;];
    Stream prevUncompressedStream = app.Response.Filter;

    if (acceptEncoding == null || acceptEncoding.Length == 0)
        return;

    acceptEncoding = acceptEncoding.ToLower();

    if (acceptEncoding.Contains(&quot;deflate&quot;) || acceptEncoding == &quot;*&quot;)
    {
        // defalte
        app.Response.Filter = new DeflateStream(prevUncompressedStream,
            CompressionMode.Compress);
        app.Response.AppendHeader(&quot;Content-Encoding&quot;, &quot;deflate&quot;);

    }
    else if (acceptEncoding.Contains(&quot;gzip&quot;))
    {
        // gzip
        app.Response.Filter = new GZipStream(prevUncompressedStream,
            CompressionMode.Compress);
        app.Response.AppendHeader(&quot;Content-Encoding&quot;, &quot;gzip&quot;);

    }
    app.Response.AppendHeader(&quot;Vary&quot;, &quot;Accept-Encoding&quot;);

}</pre></p>
<p>Now, I would like to claim credit for this, however I can&#8217;t. I found this little gem over at <a title="StarDeveloper.com" href="http://www.stardeveloper.com" target="_blank">www.stardeveloper.com</a> by Faisal Khan.</p>
<p>If you would like to know more about Gzip / Deflate take a look at the following web-sites:</p>
<ul>
<li><a href="http://www.stardeveloper.com/articles/display.html?article=2007110401&amp;page=1" target="_blank">Enabling GZip and Deflate HTTP Compression in ASP.NET pages</a> – Faisal Khan</li>
<li><a href="http://www.stardeveloper.com/articles/display.html?article=2008111201&amp;page=1" target="_blank">Gzip vs Deflate, which is faster HTTP compression method?</a> – Faisal Khan</li>
<li><a href="http://msdn.microsoft.com/en-us/library/system.io.compression.gzipstream.aspx" target="_blank">GZipStream Class</a> – MSDN</li>
<li><a href="http://www.west-wind.com/weblog/posts/10564.aspx" target="_blank">More on GZip compression with ASP.NET</a> – Rick Strahl</li>
</ul>
<h3>Finally</h3>
<p>Using Gzip with minify is now really starting to speed up our pages. Next time we will look at Caching and donut caching your pages for faster users experience. </p>
<p>Achieving at least a 95/100 on Google’s <a title="Google Page Speed" href="http://code.google.com/speed/page-speed/" target="_blank">Page Speed</a> rating and (A /97) on <a title="Yahoo! YSlow" href="http://developer.yahoo.com/yslow/" target="_blank">Yahoo! YSlow</a> rating in V2 mode on a graphically, interactive heavy page is straight forward to obtain even without using a <a title="Content delivery network" href="http://en.wikipedia.org/wiki/Content_delivery_network" target="_blank">CDN</a> (Content delivery network).</p>
<p>I hope you found this helpful, and can progress on it.</p>
<p>If you found this helpful and would like to <strong>buy me a beer</strong> to say thanks, please <a href="https://www.paypal.com/cgi-bin/webscr?cmd=_s-xclick&amp;hosted_button_id=NKKD5YY5DQQK8"><img src="https://www.paypal.com/en_US/i/btn/x-click-but21.gif" alt="" /></a></p>
<p><a href="http://twitter.com/ArranM" target="_blank">@ArranM</a></p>
<br />  <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gocomments/arranmaclean.wordpress.com/159/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/comments/arranmaclean.wordpress.com/159/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/godelicious/arranmaclean.wordpress.com/159/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/delicious/arranmaclean.wordpress.com/159/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gofacebook/arranmaclean.wordpress.com/159/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/facebook/arranmaclean.wordpress.com/159/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gotwitter/arranmaclean.wordpress.com/159/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/twitter/arranmaclean.wordpress.com/159/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gostumble/arranmaclean.wordpress.com/159/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/stumble/arranmaclean.wordpress.com/159/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/godigg/arranmaclean.wordpress.com/159/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/digg/arranmaclean.wordpress.com/159/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/goreddit/arranmaclean.wordpress.com/159/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/reddit/arranmaclean.wordpress.com/159/" /></a> <img alt="" border="0" src="http://stats.wordpress.com/b.gif?host=arranmaclean.wordpress.com&amp;blog=7827390&amp;post=159&amp;subd=arranmaclean&amp;ref=&amp;feed=1" width="1" height="1" />]]></content:encoded>
			<wfw:commentRss>http://arranmaclean.wordpress.com/2010/07/29/simple-gzip-deflate-in-net/feed/</wfw:commentRss>
		<slash:comments>1</slash:comments>
	
		<media:content url="http://1.gravatar.com/avatar/be4d11a40f2a59dd3b0a7bb66032149a?s=96&#38;d=identicon&#38;r=G" medium="image">
			<media:title type="html">Arran</media:title>
		</media:content>

		<media:content url="https://www.paypal.com/en_US/i/btn/x-click-but21.gif" medium="image" />
	</item>
		<item>
		<title>Minify, Combine CSS and JavaScript with Visual Studio</title>
		<link>http://arranmaclean.wordpress.com/2010/07/22/minify-combine-css-and-javascript-with-visual-studio/</link>
		<comments>http://arranmaclean.wordpress.com/2010/07/22/minify-combine-css-and-javascript-with-visual-studio/#comments</comments>
		<pubDate>Thu, 22 Jul 2010 22:07:45 +0000</pubDate>
		<dc:creator>ArranM</dc:creator>
				<category><![CDATA[Code Examples]]></category>
		<category><![CDATA[.NET]]></category>
		<category><![CDATA[combine]]></category>
		<category><![CDATA[CSS]]></category>
		<category><![CDATA[JavaScript]]></category>
		<category><![CDATA[minify]]></category>
		<category><![CDATA[Visual Studio]]></category>

		<guid isPermaLink="false">https://arranmaclean.wordpress.com/?p=107</guid>
		<description><![CDATA[One of my personal favourites and easy to achieve page speed improvements, is to Minify and Combine CSS and JavaScript files upon building the release code. Not everyone has continuous integration (CI) setup and able perform Combine and Minify actions after committing your code to a build agents; so I hope this will help a [...]<img alt="" border="0" src="http://stats.wordpress.com/b.gif?host=arranmaclean.wordpress.com&amp;blog=7827390&amp;post=107&amp;subd=arranmaclean&amp;ref=&amp;feed=1" width="1" height="1" />]]></description>
			<content:encoded><![CDATA[<p>One of my personal favourites and easy to achieve page speed improvements, is to Minify and Combine <a title="Find out more about Cascading Style Sheets" href="http://en.wikipedia.org/wiki/CSS" target="_blank">CSS</a> and <a title="Learn more about JavaScript" href="http://en.wikipedia.org/wiki/JavaScript" target="_blank">JavaScript</a> files upon building the release code.</p>
<p>Not everyone has <a title="Learn more about Continuous integration" href="http://en.wikipedia.org/wiki/Continuous_integration" target="_blank">continuous integration</a> (CI) setup and able perform Combine and Minify actions after committing your code to a build agents; so I hope this will help a few people that are running locally or even with build agents. <span id="more-107"></span></p>
<h3>The tools</h3>
<ul>
<li>Microsoft Visual Studio Express 2010 (<a href="http://www.microsoft.com/express/downloads/">Download via Web platform installer</a>)</li>
<li><a title="Would you like to know more about Microsoft Ajax Minifier?" href="http://aspnet.codeplex.com/releases/view/40584" target="_blank">Microsoft Ajax Minified</a>, <a title="Find out more about YUI Compressor for .Net" href="http://yuicompressor.codeplex.com/" target="_blank">YUI Compressor for .Net</a> or <a title="Learn more about Google Closure Compiler" href="http://code.google.com/closure/compiler/" target="_blank">Google Closure Compiler</a></li>
<li>Large Coffee and a muffin</li>
<li>Example JS, CSS files to work with.</li>
<li><a title="Download Web Deployment Project 2010" href="http://www.microsoft.com/downloads/details.aspx?FamilyID=89f2c4f5-5d3a-49b6-bcad-f776c6edfa63&amp;displaylang=en" target="_blank">Web Deployment Project 2010</a></li>
</ul>
<p>Lets get started by picking which minifier tool we’d like to use. Each of the minifies have their own merits and I would recommend you investigate further which is right for your needs. In this example we are going to be using <a title="Download Microsoft Ajax Minifier" href="http://aspnet.codeplex.com/releases/view/40584" target="_blank">Microsoft Ajax Minified</a> and <a title="Download Web Deployment Project 2010" href="http://www.microsoft.com/downloads/details.aspx?FamilyID=89f2c4f5-5d3a-49b6-bcad-f776c6edfa63&amp;displaylang=en" target="_blank">Web Deployment Project 2010</a>. So download load them and install.</p>
<p><a href="http://arranmaclean.files.wordpress.com/2010/07/ajaxminifyinstall.jpg" target="_blank"><img class="wlDisabledImage" style="display:inline;border-width:0;" title="Ajax Minify Install" src="http://arranmaclean.files.wordpress.com/2010/07/ajaxminifyinstall_thumb.jpg?w=244&#038;h=200" border="0" alt="Ajax Minify Install" width="244" height="200" /></a></p>
<p>That was easy, lets move on to setting up a basic project and creating some  simple CSS and JavaScript files.</p>
<p>We are  going to start with a standard vanilla <a href="http://en.wikipedia.org/wiki/Model%E2%80%93view%E2%80%93controller" target="_blank">MVC</a> (Model View Controller) .NET application install, good old “File &gt; New Project &gt; ASP.NET MVC Web Application”</p>
<p><a href="http://arranmaclean.files.wordpress.com/2010/07/filenewproject.jpg" target="_blank"><img class="wlDisabledImage" style="display:inline;border-width:0;" title="File new project" src="http://arranmaclean.files.wordpress.com/2010/07/filenewproject_thumb.jpg?w=255&#038;h=178" border="0" alt="File new project" width="255" height="178" /></a> <a href="http://arranmaclean.files.wordpress.com/2010/07/defaultmvcscreen1.jpg" target="_blank"><img class="wlDisabledImage" style="display:inline;border-width:0;" title="Default MVC screen" src="http://arranmaclean.files.wordpress.com/2010/07/defaultmvcscreen_thumb1.jpg?w=244&#038;h=178" border="0" alt="Default MVC screen" width="244" height="178" /></a></p>
<h3>Adding Web Deployment Project</h3>
<p>Adding our basic Deployment Project. “Build &gt; Add Web Deployment Project”</p>
<p><a href="http://arranmaclean.files.wordpress.com/2010/07/buildaddwebdeploymentproject.jpg" target="_blank"><img class="wlDisabledImage" style="display:inline;border-width:0;" title="Build, add web deployment project" src="http://arranmaclean.files.wordpress.com/2010/07/buildaddwebdeploymentproject_thumb.jpg?w=262&#038;h=149" border="0" alt="Build, add web deployment project" width="262" height="149" /></a> <a href="http://arranmaclean.files.wordpress.com/2010/07/buildaddwebdeploymentprojectsolution.jpg"><img class="wlDisabledImage" style="display:inline;border-width:0;" title="Build, Add web deployment project solution" src="http://arranmaclean.files.wordpress.com/2010/07/buildaddwebdeploymentprojectsolution_thumb.jpg?w=244&#038;h=148" border="0" alt="Build, Add web deployment project solution" width="244" height="148" /></a></p>
<h3>Release mode</h3>
<p>We need to make sure we configure our new Web Deployment project in to Release mode.</p>
<p>Right click on &#8220;Solution ‘MinifyCombineCssJavaScript’ (2 projects)&#8221; and select &#8220;Properties&#8221;. In the new dialogue popup windows we need to change “MinifyCombineCssJavaScript.csproj_deploy” to release mode.</p>
<p><a href="http://arranmaclean.files.wordpress.com/2010/07/webdeploymentreleasemode.jpg" target="_blank"><img class="wlDisabledImage" style="display:inline;border-width:0;" title="Web deployment release mode" src="http://arranmaclean.files.wordpress.com/2010/07/webdeploymentreleasemode_thumb.jpg?w=244&#038;h=141" border="0" alt="Web deployment release mode" width="244" height="141" /></a></p>
<h3>CSS and JavaScript files</h3>
<p>Lets create a couple of new files in addition to the default ones that come with the vanilla MVC project; Extras.css and Extras.js. These new files really don’t do anything special, but you get the idea.</p>
<p>The beauty of these minify tools, means we can leave comments and formatting in our files and not worry about them still being there in the released code.</p>
<p><strong>Extras.css</strong></p>
<div id="scid:C89E2BDB-ADD3-4f7a-9810-1B7EACF446C1:e3db6261-561a-4d25-a3ac-58171eebcd4d" class="wlWriterEditableSmartContent" style="display:inline;float:none;margin:0;padding:0;"><pre class="brush: css; pad-line-numbers: true;">
/* Style up our h1 */
h1
{
    font-size:2.8em;
    color:ff0000;
}

</pre></p>
</div>
<p><strong>Extras.js</strong></p>
<div id="scid:C89E2BDB-ADD3-4f7a-9810-1B7EACF446C1:378b0666-aee1-4b33-9696-ed8f3c189bb6" class="wlWriterEditableSmartContent" style="display:inline;float:none;margin:0;padding:0;"><pre class="brush: jscript;">
$(document).ready(function () {

    $(&quot;h1&quot;).click(function () {

        alert(&quot;Hello&quot;);

    }); //End h1 click

});   //End of document ready
</pre></p>
</div>
<h4>Time for a break</h4>
<p>Again we have done some great ground work here, Time for a coffee and a muffin.</p>
<p>Done?</p>
<p>Right back to work.</p>
<h3>Adding CSS and JavaScript files to our page</h3>
<p>Lets edit the master page to allow site to use debug files when running locally and minified files when released.</p>
<p>Add this simple little code snippet to the Site.Master page to allow the magic to happen.</p>
<div id="scid:C89E2BDB-ADD3-4f7a-9810-1B7EACF446C1:ebdac160-6fec-4c33-93b6-ab4263bec583" class="wlWriterEditableSmartContent" style="display:inline;float:none;margin:0;padding:0;"><pre class="brush: csharp;">
&lt;%if (HttpContext.Current.IsDebuggingEnabled){%&gt;
        &lt;link href=&quot;../../Content/Site.css&quot; rel=&quot;stylesheet&quot; type=&quot;text/css&quot; /&gt;
&lt;%}
else
{ %&gt;
        &lt;!--release version here--&gt;
&lt;% } %&gt;
</pre></p>
</div>
<p><strong>Site.Master (original)</strong></p>
<div id="scid:C89E2BDB-ADD3-4f7a-9810-1B7EACF446C1:459880c7-9cea-4509-958b-997598a0852f" class="wlWriterEditableSmartContent" style="display:inline;float:none;margin:0;padding:0;"><pre class="brush: csharp;">
&lt;%@ Master Language=&quot;C#&quot; Inherits=&quot;System.Web.Mvc.ViewMasterPage&quot; %&gt;
&lt;!DOCTYPE html PUBLIC &quot;-//W3C//DTD XHTML 1.0 Strict//EN&quot; &quot;http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd&quot;&gt;
&lt;html xmlns=&quot;http://www.w3.org/1999/xhtml&quot;&gt;
&lt;head runat=&quot;server&quot;&gt;
    &lt;title&gt;&lt;asp:ContentPlaceHolder ID=&quot;TitleContent&quot; runat=&quot;server&quot; /&gt;&lt;/title&gt;
&lt;/head&gt;
&lt;body&gt;
&lt;div class=&quot;page&quot;&gt;
&lt;div id=&quot;header&quot;&gt;
&lt;div id=&quot;title&quot;&gt;
&lt;h1&gt;My MVC Application&lt;/h1&gt;
&lt;/div&gt;
&lt;div id=&quot;logindisplay&quot;&gt;
                &lt;!--tml.RenderPartial(&quot;LogOnUserControl&quot;);--&gt;&lt;/div&gt;
&lt;div id=&quot;menucontainer&quot;&gt;
&lt;ul id=&quot;menu&quot;&gt;
	&lt;li&gt;&lt;%= Html.ActionLink(&quot;Home&quot;, &quot;Index&quot;, &quot;Home&quot;)%&gt;&lt;/li&gt;
         &lt;li&gt;&lt;%= Html.ActionLink(&quot;About&quot;, &quot;About&quot;, &quot;Home&quot;)%&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/div&gt;
&lt;/div&gt;
&lt;div id=&quot;main&quot;&gt;
&lt;div id=&quot;footer&quot;&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/div&gt;
</pre></p>
</div>
<p><strong>Site.Master (new)</strong></p>
<div id="scid:C89E2BDB-ADD3-4f7a-9810-1B7EACF446C1:b5cfbf4c-31bc-4a49-ae62-d476ad9bfb42" class="wlWriterEditableSmartContent" style="display:inline;float:none;margin:0;padding:0;"><pre class="brush: csharp;">
&lt;%@ Master Language=&quot;C#&quot; Inherits=&quot;System.Web.Mvc.ViewMasterPage&quot; %&gt;

&lt;!DOCTYPE html PUBLIC &quot;-//W3C//DTD XHTML 1.0 Strict//EN&quot; &quot;http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd&quot;&gt;
&lt;html xmlns=&quot;http://www.w3.org/1999/xhtml&quot;&gt;
&lt;head runat=&quot;server&quot;&gt;
    &lt;title&gt;&lt;asp:ContentPlaceHolder ID=&quot;TitleContent&quot; runat=&quot;server&quot; /&gt;&lt;/title&gt;
    &lt;%if (HttpContext.Current.IsDebuggingEnabled){%&gt;
        &lt;link href=&quot;../../Content/Site.css&quot; rel=&quot;stylesheet&quot; type=&quot;text/css&quot; /&gt;
        &lt;link href=&quot;../../Content/Extras.css&quot; rel=&quot;stylesheet&quot; type=&quot;text/css&quot; /&gt;
    &lt;%}
       else
       { %&gt;
        &lt;link href=&quot;../../Content/all.min.css&quot; rel=&quot;stylesheet&quot; type=&quot;text/css&quot;/&gt;
    &lt;% } %&gt;
&lt;/head&gt;

&lt;body&gt;
    &lt;div class=&quot;page&quot;&gt;

        &lt;div id=&quot;header&quot;&gt;
            &lt;div id=&quot;title&quot;&gt;
                &lt;h1&gt;My MVC Application&lt;/h1&gt;
            &lt;/div&gt;

            &lt;div id=&quot;logindisplay&quot;&gt;
                &lt;% Html.RenderPartial(&quot;LogOnUserControl&quot;); %&gt;
            &lt;/div&gt;

            &lt;div id=&quot;menucontainer&quot;&gt;

                &lt;ul id=&quot;menu&quot;&gt;
                    &lt;li&gt;&lt;%= Html.ActionLink(&quot;Home&quot;, &quot;Index&quot;, &quot;Home&quot;)%&gt;&lt;/li&gt;
                    &lt;li&gt;&lt;%= Html.ActionLink(&quot;About&quot;, &quot;About&quot;, &quot;Home&quot;)%&gt;&lt;/li&gt;
                &lt;/ul&gt;

            &lt;/div&gt;
        &lt;/div&gt;

        &lt;div id=&quot;main&quot;&gt;
            &lt;asp:ContentPlaceHolder ID=&quot;MainContent&quot; runat=&quot;server&quot; /&gt;

            &lt;div id=&quot;footer&quot;&gt;
            &lt;/div&gt;
        &lt;/div&gt;
    &lt;/div&gt;
    &lt;%if (HttpContext.Current.IsDebuggingEnabled){%&gt;
        &lt;script src=&quot;../../Scripts/jquery-1.4.1.js&quot; type=&quot;text/javascript&quot;&gt;&lt;/script&gt;
        &lt;script src=&quot;../../Scripts/Extras.js&quot; type=&quot;text/javascript&quot;&gt;&lt;/script&gt;
    &lt;%}
       else
       { %&gt;
        &lt;script src=&quot;../../Scripts/all.min.js&quot; type=&quot;text/javascript&quot;&gt;&lt;/script&gt;
    &lt;% } %&gt;
&lt;/body&gt;
&lt;/html&gt;
</pre></p>
</div>
<h3>Adding the Minify engine</h3>
<p>Time to start editing the “MinifyCombineCssJavaScript.csproj_deploy” file.</p>
<p>Original “MinifyCombineCssJavaScript.csproj_deploy” file</p>
<div id="scid:C89E2BDB-ADD3-4f7a-9810-1B7EACF446C1:1b098d4f-c83a-44ab-8e2f-8c74fcce8def" class="wlWriterEditableSmartContent" style="display:inline;float:none;margin:0;padding:0;"><pre class="brush: xml; pad-line-numbers: true;">
&lt;?xml version=&quot;1.0&quot; encoding=&quot;utf-8&quot;?&gt;
&lt;!--
  Microsoft Visual Studio 2010 Web Deployment Project
  http://go.microsoft.com/fwlink/?LinkID=104956

--&gt;
&lt;Project ToolsVersion=&quot;4.0&quot; DefaultTargets=&quot;Build&quot; xmlns=&quot;http://schemas.microsoft.com/developer/msbuild/2003&quot;&gt;
  &lt;PropertyGroup&gt;
    &lt;Configuration Condition=&quot; '$(Configuration)' == '' &quot;&gt;Debug&lt;/Configuration&gt;
    &lt;Platform Condition=&quot; '$(Platform)' == '' &quot;&gt;AnyCPU&lt;/Platform&gt;
    &lt;ProductVersion&gt;10.0.30319&lt;/ProductVersion&gt;
    &lt;SchemaVersion&gt;2.0&lt;/SchemaVersion&gt;
    &lt;ProjectGuid&gt;{3740F659-35EC-4DF3-87A3-99FAC0D999F7}&lt;/ProjectGuid&gt;
    &lt;SourceWebPhysicalPath&gt;..\MinifyCombineCssJavaScript&lt;/SourceWebPhysicalPath&gt;
    &lt;SourceWebProject&gt;{B4BFD876-1C24-4A86-AD69-3ACD82E5DE12}|MinifyCombineCssJavaScript\MinifyCombineCssJavaScript.csproj&lt;/SourceWebProject&gt;
    &lt;SourceWebVirtualPath&gt;/MinifyCombineCssJavaScript.csproj&lt;/SourceWebVirtualPath&gt;
    &lt;TargetFrameworkVersion&gt;v3.5&lt;/TargetFrameworkVersion&gt;
  &lt;/PropertyGroup&gt;
  &lt;PropertyGroup Condition=&quot; '$(Configuration)|$(Platform)' == 'Debug|AnyCPU' &quot;&gt;
    &lt;DebugSymbols&gt;true&lt;/DebugSymbols&gt;
    &lt;OutputPath&gt;.\Debug&lt;/OutputPath&gt;
    &lt;EnableUpdateable&gt;true&lt;/EnableUpdateable&gt;
    &lt;UseMerge&gt;true&lt;/UseMerge&gt;
    &lt;SingleAssemblyName&gt;MinifyCombineCssJavaScript.csproj_deploy&lt;/SingleAssemblyName&gt;
  &lt;/PropertyGroup&gt;
  &lt;PropertyGroup Condition=&quot; '$(Configuration)|$(Platform)' == 'Release|AnyCPU' &quot;&gt;
    &lt;DebugSymbols&gt;false&lt;/DebugSymbols&gt;
    &lt;OutputPath&gt;.\Release&lt;/OutputPath&gt;
    &lt;EnableUpdateable&gt;true&lt;/EnableUpdateable&gt;
    &lt;UseMerge&gt;true&lt;/UseMerge&gt;
    &lt;SingleAssemblyName&gt;MinifyCombineCssJavaScript.csproj_deploy&lt;/SingleAssemblyName&gt;
  &lt;/PropertyGroup&gt;
  &lt;ItemGroup&gt;
  &lt;/ItemGroup&gt;
  &lt;Import Project=&quot;$(MSBuildExtensionsPath)\Microsoft\WebDeployment\v10.0\Microsoft.WebDeployment.targets&quot; /&gt;
  &lt;Import Project=&quot;$(MSBuildExtensionsPath)\Microsoft\MicrosoftAjax\ajaxmin.tasks&quot; /&gt;

  &lt;!-- To modify your build process, add your task inside one of the targets below and uncomment it.
       Other similar extension points exist, see Microsoft.WebDeployment.targets.
  &lt;Target Name=&quot;BeforeBuild&quot;&gt;
  &lt;/Target&gt;
  &lt;Target Name=&quot;BeforeMerge&quot;&gt;
  &lt;/Target&gt;
  &lt;Target Name=&quot;AfterMerge&quot;&gt;
  &lt;/Target&gt;
  &lt;Target Name=&quot;AfterBuild&quot;&gt;
  &lt;/Target&gt;
  --&gt;

</pre></p>
</div>
<p>Lets first add the Minify engine. We need to add the following line to just before “&lt;Target Name=&#8221;BeforeBuild&#8221;&gt;&lt;/Target&gt;”</p>
<div id="scid:C89E2BDB-ADD3-4f7a-9810-1B7EACF446C1:afde3898-0888-44c6-ae02-f7a99e4bbc06" class="wlWriterEditableSmartContent" style="display:inline;float:none;margin:0;padding:0;"><pre class="brush: xml;">
&lt;Import Project=&quot;$(MSBuildExtensionsPath)\Microsoft\MicrosoftAjax\ajaxmin.tasks&quot; /&gt;
</pre></p>
</div>
<p>Next we need to create a list group of CSS files which we wish to merge. We can do this in the “Aftermerge” target area.</p>
<div id="scid:C89E2BDB-ADD3-4f7a-9810-1B7EACF446C1:bee701c0-0a44-4619-962b-75fff71e9d40" class="wlWriterEditableSmartContent" style="display:inline;float:none;margin:0;padding:0;"><pre class="brush: xml;">
&lt;Target Name=&quot;AfterMerge&quot;&gt;
    &lt;CssFilesIndex Include=&quot;$(TempBuildDir)\Content\Site.css;$(TempBuildDir)\Content\Extras.css;&quot; /&gt;
  &lt;/Target&gt;
</pre></p>
</div>
<p>Now, we will also do the same for the JavaScript files.</p>
<div id="scid:C89E2BDB-ADD3-4f7a-9810-1B7EACF446C1:bb3772fc-0aac-4019-99df-e1ddd9013466" class="wlWriterEditableSmartContent" style="display:inline;float:none;margin:0;padding:0;"><pre class="brush: xml;">
&lt;JsFiles Include=&quot;$(TempBuildDir)\Scripts\jquery-1.4.1.js;$(TempBuildDir)\Scripts\Extras.js;&quot; /&gt;
</pre></p>
</div>
<p>Time to merge our CSS files in to one file and then for the JavaScript files.</p>
<p><strong>CSS merge to all.css</strong></p>
<div id="scid:C89E2BDB-ADD3-4f7a-9810-1B7EACF446C1:f6751695-8264-494d-a82e-c22b78a0dddd" class="wlWriterEditableSmartContent" style="display:inline;float:none;margin:0;padding:0;"><pre class="brush: xml;">
&lt;ReadLinesFromFile File=&quot;%(CssFiles.Identity)&quot;&gt;
      &lt;Output TaskParameter=&quot;Lines&quot; ItemName=&quot;cssLines&quot; /&gt;
    &lt;/ReadLinesFromFile&gt;
    &lt;WriteLinesToFile File=&quot;$(TempBuildDir)\Content\all.css&quot; Lines=&quot;@(cssLines)&quot; Overwrite=&quot;true&quot; /&gt;</pre></p>
</div>
<p><strong>JavaScript merge to all.js</strong></p>
<div id="scid:C89E2BDB-ADD3-4f7a-9810-1B7EACF446C1:310a607a-b5c8-4add-be31-8ab10797bc3e" class="wlWriterEditableSmartContent" style="display:inline;float:none;margin:0;padding:0;"><pre class="brush: xml;">
&lt;ReadLinesFromFile File=&quot;%(JsFiles.Identity)&quot;&gt;
      &lt;Output TaskParameter=&quot;Lines&quot; ItemName=&quot;jsLines&quot; /&gt;
&lt;/ReadLinesFromFile&gt;
&lt;WriteLinesToFile File=&quot;$(TempBuildDir)\Scripts\all.js&quot; Lines=&quot;@(JsLines)&quot; Overwrite=&quot;true&quot; /&gt;
</pre></p>
</div>
<p>We are on the final stretch.</p>
<p>Lets tell the minifier to compress our new single files. We&#8217;ll do this inside  the “&lt;Target Name=&#8221;AfterBuild&#8221;&gt;&lt;/Target&gt;” and then delete out the single non-minified files, just so we keep things a little tidy.</p>
<div id="scid:C89E2BDB-ADD3-4f7a-9810-1B7EACF446C1:8eb46936-6ca4-4ba4-927a-634156136665" class="wlWriterEditableSmartContent" style="display:inline;float:none;margin:0;padding:0;"><pre class="brush: xml;">
&lt;Target Name=&quot;AfterBuild&quot;&gt;
      &lt;ItemGroup&gt;
        &lt;JS Include=&quot;**\Scripts\all.js;&quot; Exclude=&quot;**\*.min.js&quot; /&gt;
      &lt;/ItemGroup&gt;
      &lt;ItemGroup&gt;
        &lt;CSS Include=&quot;**\Content\all.css;&quot; /&gt;
      &lt;/ItemGroup&gt;
      &lt;AjaxMin JsSourceFiles=&quot;@(JS)&quot; JsSourceExtensionPattern=&quot;\.js$&quot; JsTargetExtension=&quot;.min.js&quot; CssSourceFiles=&quot;@(CSS)&quot; CssSourceExtensionPattern=&quot;\.css$&quot; CssTargetExtension=&quot;.min.css&quot; /&gt;
    &lt;ItemGroup&gt;
      &lt;DeleteAfterBuild Include=&quot;$(OutputPath)Scripts\all.js&quot; /&gt;
      &lt;DeleteAfterBuild Include=&quot;$(OutputPath)Scripts\jquery-1.4.1.js&quot; /&gt;
      &lt;DeleteAfterBuild Include=&quot;$(OutputPath)Scripts\Extras.js&quot; /&gt;
      &lt;DeleteAfterBuild Include=&quot;$(OutputPath)Content\all.css&quot; /&gt;
      &lt;DeleteAfterBuild Include=&quot;$(OutputPath)Content\Site.css&quot; /&gt;
      &lt;DeleteAfterBuild Include=&quot;$(OutputPath)Content\Extras.css&quot; /&gt;
    &lt;/ItemGroup&gt;
  &lt;/Target&gt;
</pre></p>
</div>
<p>That’s it we are done, Hit F5 and watch the magic happen. The release version now knows to use the minified/combine files yet leaving our original files intact while working locally, allowing us to debug.</p>
<h3>Finally</h3>
<p>There is much more you can do with the build script, like excluding files not needed for your live site and deleting all other non live file. We could actually remove one of the steps above, however I thought I&#8217;d leave it in just to keep things in simple blocks.</p>
<p>The same process works for each of the different minifiers, it&#8217;s just a case of swapping them in and out to the one you prefer.</p>
<p>I hope this helps someone out, let me know.</p>
<p>If you found this helpful and would like to <strong>buy me a beer</strong> to say thanks, please <a href="https://www.paypal.com/cgi-bin/webscr?cmd=_s-xclick&amp;hosted_button_id=NKKD5YY5DQQK8"><img src="https://www.paypal.com/en_US/i/btn/x-click-but21.gif" alt="" /></a></p>
<p><a title="Follow me on Twitter" href="http://twitter.com/ArranM" target="_blank">@ArranM</a></p>
<br />  <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gocomments/arranmaclean.wordpress.com/107/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/comments/arranmaclean.wordpress.com/107/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/godelicious/arranmaclean.wordpress.com/107/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/delicious/arranmaclean.wordpress.com/107/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gofacebook/arranmaclean.wordpress.com/107/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/facebook/arranmaclean.wordpress.com/107/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gotwitter/arranmaclean.wordpress.com/107/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/twitter/arranmaclean.wordpress.com/107/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gostumble/arranmaclean.wordpress.com/107/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/stumble/arranmaclean.wordpress.com/107/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/godigg/arranmaclean.wordpress.com/107/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/digg/arranmaclean.wordpress.com/107/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/goreddit/arranmaclean.wordpress.com/107/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/reddit/arranmaclean.wordpress.com/107/" /></a> <img alt="" border="0" src="http://stats.wordpress.com/b.gif?host=arranmaclean.wordpress.com&amp;blog=7827390&amp;post=107&amp;subd=arranmaclean&amp;ref=&amp;feed=1" width="1" height="1" />]]></content:encoded>
			<wfw:commentRss>http://arranmaclean.wordpress.com/2010/07/22/minify-combine-css-and-javascript-with-visual-studio/feed/</wfw:commentRss>
		<slash:comments>5</slash:comments>
	
		<media:content url="http://1.gravatar.com/avatar/be4d11a40f2a59dd3b0a7bb66032149a?s=96&#38;d=identicon&#38;r=G" medium="image">
			<media:title type="html">Arran</media:title>
		</media:content>

		<media:content url="http://arranmaclean.files.wordpress.com/2010/07/ajaxminifyinstall_thumb.jpg" medium="image">
			<media:title type="html">Ajax Minify Install</media:title>
		</media:content>

		<media:content url="http://arranmaclean.files.wordpress.com/2010/07/filenewproject_thumb.jpg" medium="image">
			<media:title type="html">File new project</media:title>
		</media:content>

		<media:content url="http://arranmaclean.files.wordpress.com/2010/07/defaultmvcscreen_thumb1.jpg" medium="image">
			<media:title type="html">Default MVC screen</media:title>
		</media:content>

		<media:content url="http://arranmaclean.files.wordpress.com/2010/07/buildaddwebdeploymentproject_thumb.jpg" medium="image">
			<media:title type="html">Build, add web deployment project</media:title>
		</media:content>

		<media:content url="http://arranmaclean.files.wordpress.com/2010/07/buildaddwebdeploymentprojectsolution_thumb.jpg" medium="image">
			<media:title type="html">Build, Add web deployment project solution</media:title>
		</media:content>

		<media:content url="http://arranmaclean.files.wordpress.com/2010/07/webdeploymentreleasemode_thumb.jpg" medium="image">
			<media:title type="html">Web deployment release mode</media:title>
		</media:content>

		<media:content url="https://www.paypal.com/en_US/i/btn/x-click-but21.gif" medium="image" />
	</item>
		<item>
		<title>.NET MVC, Upload a CSV file to Database with Bulk upload</title>
		<link>http://arranmaclean.wordpress.com/2010/07/20/net-mvc-upload-a-csv-file-to-database-with-bulk-upload/</link>
		<comments>http://arranmaclean.wordpress.com/2010/07/20/net-mvc-upload-a-csv-file-to-database-with-bulk-upload/#comments</comments>
		<pubDate>Tue, 20 Jul 2010 11:01:04 +0000</pubDate>
		<dc:creator>ArranM</dc:creator>
				<category><![CDATA[Code Examples]]></category>
		<category><![CDATA[.NET]]></category>
		<category><![CDATA[Bulk copy]]></category>
		<category><![CDATA[CSV]]></category>
		<category><![CDATA[MVC]]></category>

		<guid isPermaLink="false">https://arranmaclean.wordpress.com/?p=34</guid>
		<description><![CDATA[Simple yet useful tool set to have is dealing with CSV (Comma-separated values), often as not you end having to filter CSV files and then push them in to a database of some kind. I thought I’d give a quick example of taking a CSV file, building a data table in memory and the pushing [...]<img alt="" border="0" src="http://stats.wordpress.com/b.gif?host=arranmaclean.wordpress.com&amp;blog=7827390&amp;post=34&amp;subd=arranmaclean&amp;ref=&amp;feed=1" width="1" height="1" />]]></description>
			<content:encoded><![CDATA[<p>Simple yet useful tool set to have is dealing with <a title="Comma-separated Values WIKI" href="http://en.wikipedia.org/wiki/Comma-separated_values" target="_blank">CSV</a> (Comma-separated values), often as not you end having to filter CSV files and then push them in to a database of some kind.</p>
<p>I thought I’d give a quick example of taking a CSV file, building a data table in memory and the pushing all the data to MS SQL Server in one action.</p>
<p>The following is by no means a finish code or ready for production, but here goes. <span id="more-34"></span></p>
<h3>The tools</h3>
<ul>
<li>Microsoft Visual Studio Express 2010 (<a title="Microsoft Web platform installer (WPI)" href="http://www.microsoft.com/express/downloads/" target="_blank">Download via Web platform installer</a>)</li>
<li>Microsoft SQL Express 2008</li>
<li>Large cup of tea and couple of biscuits</li>
<li>Example CSV file to work with. (CSV example file)</li>
<li>Excel</li>
</ul>
<p>I’m going to start with a standard vanilla <a title="Model View Controller WIKI" href="http://en.wikipedia.org/wiki/Model%E2%80%93view%E2%80%93controller" target="_blank">MVC</a> (Model View Controller) .NET application install, good old “File &gt; New Project &gt; ASP.NET MVC Web Application”</p>
<p><a href="http://arranmaclean.files.wordpress.com/2010/07/filenewprojectmvc.jpg" target="_blank"><img class="wlDisabledImage" style="display:inline;border-width:0;" title="Visual Studio - File  New Project window" src="http://arranmaclean.files.wordpress.com/2010/07/filenewprojectmvc_thumb.jpg?w=264&#038;h=184" border="0" alt="Visual Studio - File  New Project window" width="264" height="184" /></a> <a href="http://arranmaclean.files.wordpress.com/2010/07/defaultmvcscreen.jpg" target="_blank"><img class="wlDisabledImage" style="display:inline;border-width:0;" title="Default .NET MVC Screen" src="http://arranmaclean.files.wordpress.com/2010/07/defaultmvcscreen_thumb.jpg?w=244&#038;h=184" border="0" alt="Default .NET MVC Screen" width="244" height="184" /></a></p>
<p>Now that’s done, lets look at our CSV file and understand what table structure we are going to have to create in the database.</p>
<h3>The CSV file</h3>
<p>The example CSV file contain a simple set of data, First Name (<a title="String - C# Programming language" href="http://msdn.microsoft.com/en-us/library/362314fe(VS.71).aspx" target="_blank">String</a>), Surname (String) and Date of birth (<a title="DateTime - C# Programming language" href="http://msdn.microsoft.com/en-us/library/system.datetime.aspx" target="_blank">DateTime</a>).</p>
<p><a href="http://arranmaclean.files.wordpress.com/2010/07/excelscreenofexampledata1.jpg" target="_blank"><img class="wlDisabledImage" style="display:inline;border-width:0;" title="Excel Screenshot of example data" src="http://arranmaclean.files.wordpress.com/2010/07/excelscreenofexampledata_thumb1.jpg?w=244&#038;h=182" border="0" alt="Excel Screenshot of example data" width="244" height="182" /></a></p>
<p>To make life a little easier for ourselves we will delete the first line which contains the heading. It’s one less thing to deal with. Our CSV should now like this:</p>
<blockquote><p><code>Arran,Maclean,01/12/1980<br />
Rachel,Gorrod,20/12/1985<br />
Simon,Gainham,14/05/1983<br />
Bill,Gates,12/12/1960<br />
Marky,Mark,15/02/1970<br />
</code></p></blockquote>
<p>From this we can now look at creating a table in our database to capture the imported data. Again we will keep this simple, you can refine it later.</p>
<p>Now create your database. I’m keeping this example simple, just asking Visual Studio to create an empty database in the App_Data folder.</p>
<p>We will need 3 columns, “Firstname” <a title="Find out more about nvarchar" href="http://msdn.microsoft.com/en-us/library/ms186939.aspx" target="_blank">nvarchar</a>(50), “Surname” nvarchar(50) and “Dateofbirth” datetime.</p>
<p><a href="http://arranmaclean.files.wordpress.com/2010/07/createtableinthedatabase1.jpg" target="_blank"><img class="wlDisabledImage" style="display:inline;border-width:0;" title="Create a new table in the database" src="http://arranmaclean.files.wordpress.com/2010/07/createtableinthedatabase_thumb1.jpg?w=244&#038;h=152" border="0" alt="Create a new table in the database" width="244" height="152" /></a></p>
<blockquote><p><code>CREATE TABLE BulkImportDetails(<br />
[Firstname] [nvarchar](50) NULL,<br />
[Surname] [nvarchar](50) NULL,<br />
[Dateofbirth] [datetime] NULL<br />
)</code></p></blockquote>
<p>Now to quickly drop in the connection string for the database in the the web.config</p>
<p><pre class="brush: csharp;">
&lt;connectionStrings&gt;
&lt;add name=&quot;DataBaseConnectionString&quot; connectionString=&quot;Data Source=.\SQLEXPRESS;AttachDbFilename=|DataDirectory|\CSVtoBulkUpLoad.mdf;Integrated Security=True;User Instance=True&quot;      providerName=&quot;System.Data.SqlClient&quot; /&gt;
&lt;/connectionStrings&gt;
</pre></p>
<p>OK, now that’s all out of the way, lets get to the fun stuff.</p>
<h3>Upload your CSV file</h3>
<p>As we are utilising MVC; We will create our form in a with a simple <a title="Would you like to know more about Html Helpers?" href="http://msdn.microsoft.com/en-us/library/dd410596.aspx" target="_blank">Html Helper</a>. The important item to remember when uploading a file is <code>enctype=”<a title="What to know more about form-data?" href="http://en.wikipedia.org/wiki/File_select" target="_blank">multipart/form-data</a>”</code> attribute, this deals with the bits and bytes. We will also add a ViewData holder for our feedback to the screen.</p>
<p><pre class="brush: csharp;">
&lt;h2&gt;CSV Bulk Upload&lt;/h2&gt;
&lt;% using (Html.BeginForm(&quot;upload&quot;,&quot;&quot;,FormMethod.Post, new {enctype=&quot;multipart/form-data&quot;})){ %&gt;

&lt;input type=&quot;file&quot; name=&quot;FileUpload&quot; /&gt;
&lt;input type=&quot;submit&quot; name=&quot;Submit&quot; id=&quot;Submit&quot; value=&quot;Upload&quot; /&gt;

&lt;%}    %&gt;

&lt;p&gt;&lt;%= Html.Encode(ViewData[&quot;Feedback&quot;]) %&gt;&lt;/p&gt;
</pre></p>
<p><a href="http://arranmaclean.files.wordpress.com/2010/07/uploadform1.jpg" target="_blank"><img class="wlDisabledImage" style="display:inline;border:0;" title="Example upload form screen" src="http://arranmaclean.files.wordpress.com/2010/07/uploadform_thumb1.jpg?w=244&#038;h=179" border="0" alt="Example upload form screen" width="244" height="179" /></a></p>
<h3>The HomeController</h3>
<p>Now we have the inputs ready, it’s time to build our controller to handle the uploaded file and save it to a set location. Create a new folder in your <strong>App_Data </strong>folder called “uploads”</p>
<p><a href="http://arranmaclean.files.wordpress.com/2010/07/examplelocationofuploadsfolder.jpg" target="_blank"><img class="wlDisabledImage" style="display:inline;border-width:0;" title="location of uploads folder" src="http://arranmaclean.files.wordpress.com/2010/07/examplelocationofuploadsfolder_thumb.jpg?w=244&#038;h=167" border="0" alt="Uploads folder" width="244" height="167" /></a></p>
<p>Lets add the code for to handle the upload process after the user click the upload button. Add the following code to the HomeController. (<a title="Upload load multiple=" href="http://haacked.com/archive/2010/07/16/uploading-files-with-aspnetmvc.aspx" target="_blank">Upload load multiple files?</a>)</p>
<p><pre class="brush: csharp;">
[HttpPost]
public ActionResult Index(HttpPostedFileBase FileUpload)
{
if (FileUpload.ContentLength &gt; 0)
{
           string fileName = Path.GetFileName(FileUpload.FileName);
           string path = Path.Combine(Server.MapPath(&quot;~/App_Data/uploads&quot;), fileName);
           try {
                FileUpload.SaveAs(path);
                ViewData[&quot;Feedback&quot;] = &quot;Upload Complete&quot;;
           }
           catch (Exception ex)
           {
                ViewData[&quot;Feedback&quot;] = ex.Message;
           }
}

       return View(&quot;Index&quot;, ViewData[&quot;Feedback&quot;]);
}
</pre></p>
<h4>Time for a break</h4>
<p>Great work everyone, the upload feature is working. Time for a cup of tea and a biscuit. MMMMmmm.</p>
<p><a href="http://arranmaclean.files.wordpress.com/2010/07/cupofteaandbiscuit.jpg" target="_blank"><img class="wlDisabledImage" style="display:inline;border-width:0;" title="A cup of tea and a biscuit" src="http://arranmaclean.files.wordpress.com/2010/07/cupofteaandbiscuit_thumb.jpg?w=244&#038;h=184" border="0" alt="A cup of tea and a biscuit" width="244" height="184" /></a></p>
<p>Lets crack on and finish.</p>
<h3>Copying CSV to a DataTable</h3>
<p>We are now going to convert our CSV file and return a <a title="Find out more about DataTable" href="http://msdn.microsoft.com/en-us/library/system.data.datatable.aspx" target="_blank">DataTable</a> . Think of this as Excel spread sheet in memory.</p>
<p>Let create our static function; One stumbling block you can come up against when working with CSV data is handling the “ , “ in a sentence.  Thanks to agreed conventions any sentence that contain a “,” should be wrapped in quotes. With this in mind we can use a regular expression to detect the comma’s and which one we need to split on.</p>
<p><pre class="brush: csharp;">
private static DataTable ProcessCSV(string fileName)
{
//Set up our variables
string Feedback = string.Empty;
string line = string.Empty;
string[] strArray;
DataTable dt = new DataTable();
DataRow row;
// work out where we should split on comma, but not in a sentence
   Regex r = new Regex(&quot;,(?=(?:[^\&quot;]*\&quot;[^\&quot;]*\&quot;)*(?![^\&quot;]*\&quot;))&quot;);
            //Set the filename in to our stream
            StreamReader sr = new StreamReader(fileName);

            //Read the first line and split the string at , with our regular expression in to an array
            line = sr.ReadLine();
           strArray = r.Split(line);

           //For each item in the new split array, dynamically builds our Data columns. Save us having to worry about it.
          Array.ForEach(strArray, s =&gt; dt.Columns.Add(new DataColumn()));

           //Read each line in the CVS file until it’s empty
            while ((line = sr.ReadLine()) != null)
           {
                      row = dt.NewRow();

                    //add our current value to our data row
                    row.ItemArray = r.Split(line);
                  dt.Rows.Add(row);
            }

            //Tidy Streameader up
            sr.Dispose();

            //return a the new DataTable
           return dt;

}
</pre></p>
<p>Lets amend our HomeController to now run our new function after upload.</p>
<p><pre class="brush: csharp;">

[HttpPost]
        public ActionResult Index(HttpPostedFileBase FileUpload)
        {
            // Set up DataTable place holder
            DataTable dt = new DataTable();

            //check we have a file
            if (FileUpload.ContentLength &gt; 0)
            {
                //Workout our file path
                string fileName = Path.GetFileName(FileUpload.FileName);
                string path = Path.Combine(Server.MapPath(&quot;~/App_Data/uploads&quot;), fileName);

                //Try and upload
                try
                {
                    FileUpload.SaveAs(path);
                    //Process the CSV file and capture the results to our DataTable place holder
                    dt = ProcessCSV(path);

                }
                catch (Exception ex)
                {
                    //Catch errors
                    ViewData[&quot;Feedback&quot;] = ex.Message;
                }
            }
            else
            {
                //Catch errors
                ViewData[&quot;Feedback&quot;] = &quot;Please select a file&quot;;
            }

            //Tidy up
            dt.Dispose();

            return View(&quot;Index&quot;, ViewData[&quot;Feedback&quot;]);
        }
</pre></p>
<p>Now, if we run our web page and incept the DataTable (dt) we should now see our data in a nice little table.</p>
<p><a href="http://arranmaclean.files.wordpress.com/2010/07/datasetvisualizer.jpg" target="_blank"><img class="wlDisabledImage" style="display:inline;border-width:0;" title="Dataset visualizer" src="http://arranmaclean.files.wordpress.com/2010/07/datasetvisualizer_thumb.jpg?w=244&#038;h=125" border="0" alt="Dataset visualizer" width="244" height="125" /></a></p>
<p>Cool, feeling good so far. Lets move on and do what we really came here for! Bulk copy this table to our database table. The new function will take the DataTable generated above and send it all in one go to our database. You can of course sort, delete etc the data before sending it.</p>
<p><pre class="brush: csharp;">
private static String ProcessBulkCopy(DataTable dt)
        {
            string Feedback = string.Empty;
            string connString = ConfigurationManager.ConnectionStrings[&quot;DataBaseConnectionString&quot;].ConnectionString;

            //make our connection and dispose at the end
            using(  SqlConnection conn = new SqlConnection(connString))
            {
                //make our command and dispose at the end
                using (var copy = new SqlBulkCopy(conn))
                {

                        //Open our connection
                        conn.Open();

                        ///Set target table and tell the number of rows
                        copy.DestinationTableName = &quot;BulkImportDetails&quot;;
                        copy.BatchSize = dt.Rows.Count;
                        try
                        {
                            //Send it to the server
                            copy.WriteToServer(dt);
                            Feedback = &quot;Upload complete&quot;;
                        }
                        catch (Exception ex)
                        {
                            Feedback = ex.Message;
                        }
                }
            }

            return Feedback;
       }
</pre></p>
<p>Also most there, lets amend out HomeController yet again to now run our new bulk copy function.</p>
<p><pre class="brush: csharp;">
[HttpPost]
        public ActionResult Index(HttpPostedFileBase FileUpload)
        {
            // Set up DataTable place holder
            DataTable dt = new DataTable();

            //check we have a file
            if (FileUpload.ContentLength &gt; 0)
            {
                //Workout our file path
                string fileName = Path.GetFileName(FileUpload.FileName);
                string path = Path.Combine(Server.MapPath(&quot;~/App_Data/uploads&quot;), fileName);

                //Try and upload
                try
                {
                    FileUpload.SaveAs(path);
                    //Process the CSV file and capture the results to our DataTable place holder
                    dt = ProcessCSV(path);

                    //Process the DataTable and capture the results to our SQL Bulk copy
                    ViewData[&quot;Feedback&quot;] = ProcessBulkCopy(dt);
                }
                catch (Exception ex)
                {
                    //Catch errors
                    ViewData[&quot;Feedback&quot;] = ex.Message;
                }
            }
            else
            {
                //Catch errors
                ViewData[&quot;Feedback&quot;] = &quot;Please select a file&quot;;
            }

            //Tidy up
            dt.Dispose();

            return View(&quot;Index&quot;, ViewData[&quot;Feedback&quot;]);
        }
</pre></p>
<h3>Finally</h3>
<p>Well that’s it, all working. We have covered a number of topics here. File upload, Reading a CSV file and bulk copying data to a database.</p>
<p>Full project and database is available for download. (See right hand navigation)</p>
<p>If you found this helpful and would like to <strong>buy me a beer</strong> to say thanks, please <a href="https://www.paypal.com/cgi-bin/webscr?cmd=_s-xclick&amp;hosted_button_id=NKKD5YY5DQQK8"><img src="https://www.paypal.com/en_US/i/btn/x-click-but21.gif" alt="" /></a></p>
<p><a title="Follow me on Twitter" href="http://twitter.com/ArranM" target="_blank">@ArranM</a></p>
<br />  <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gocomments/arranmaclean.wordpress.com/34/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/comments/arranmaclean.wordpress.com/34/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/godelicious/arranmaclean.wordpress.com/34/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/delicious/arranmaclean.wordpress.com/34/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gofacebook/arranmaclean.wordpress.com/34/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/facebook/arranmaclean.wordpress.com/34/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gotwitter/arranmaclean.wordpress.com/34/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/twitter/arranmaclean.wordpress.com/34/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gostumble/arranmaclean.wordpress.com/34/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/stumble/arranmaclean.wordpress.com/34/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/godigg/arranmaclean.wordpress.com/34/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/digg/arranmaclean.wordpress.com/34/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/goreddit/arranmaclean.wordpress.com/34/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/reddit/arranmaclean.wordpress.com/34/" /></a> <img alt="" border="0" src="http://stats.wordpress.com/b.gif?host=arranmaclean.wordpress.com&amp;blog=7827390&amp;post=34&amp;subd=arranmaclean&amp;ref=&amp;feed=1" width="1" height="1" />]]></content:encoded>
			<wfw:commentRss>http://arranmaclean.wordpress.com/2010/07/20/net-mvc-upload-a-csv-file-to-database-with-bulk-upload/feed/</wfw:commentRss>
		<slash:comments>8</slash:comments>
	
		<media:content url="http://1.gravatar.com/avatar/be4d11a40f2a59dd3b0a7bb66032149a?s=96&#38;d=identicon&#38;r=G" medium="image">
			<media:title type="html">Arran</media:title>
		</media:content>

		<media:content url="http://arranmaclean.files.wordpress.com/2010/07/filenewprojectmvc_thumb.jpg" medium="image">
			<media:title type="html">Visual Studio - File  New Project window</media:title>
		</media:content>

		<media:content url="http://arranmaclean.files.wordpress.com/2010/07/defaultmvcscreen_thumb.jpg" medium="image">
			<media:title type="html">Default .NET MVC Screen</media:title>
		</media:content>

		<media:content url="http://arranmaclean.files.wordpress.com/2010/07/excelscreenofexampledata_thumb1.jpg" medium="image">
			<media:title type="html">Excel Screenshot of example data</media:title>
		</media:content>

		<media:content url="http://arranmaclean.files.wordpress.com/2010/07/createtableinthedatabase_thumb1.jpg" medium="image">
			<media:title type="html">Create a new table in the database</media:title>
		</media:content>

		<media:content url="http://arranmaclean.files.wordpress.com/2010/07/uploadform_thumb1.jpg" medium="image">
			<media:title type="html">Example upload form screen</media:title>
		</media:content>

		<media:content url="http://arranmaclean.files.wordpress.com/2010/07/examplelocationofuploadsfolder_thumb.jpg" medium="image">
			<media:title type="html">location of uploads folder</media:title>
		</media:content>

		<media:content url="http://arranmaclean.files.wordpress.com/2010/07/cupofteaandbiscuit_thumb.jpg" medium="image">
			<media:title type="html">A cup of tea and a biscuit</media:title>
		</media:content>

		<media:content url="http://arranmaclean.files.wordpress.com/2010/07/datasetvisualizer_thumb.jpg" medium="image">
			<media:title type="html">Dataset visualizer</media:title>
		</media:content>

		<media:content url="https://www.paypal.com/en_US/i/btn/x-click-but21.gif" medium="image" />
	</item>
	</channel>
</rss>
