<?xml version="1.0" encoding="UTF-8"?>
<?xml-stylesheet type="text/xsl" media="screen" href="/~d/styles/rss2full.xsl"?><?xml-stylesheet type="text/css" media="screen" href="http://feeds.feedburner.com/~d/styles/itemcontent.css"?><rss 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:feedburner="http://rssnamespace.org/feedburner/ext/1.0" version="2.0">

<channel>
	<title>James Broome</title>
	
	<link>http://jamesbroo.me</link>
	<description>"There's sand in my keyboard" - currently developing software in Dubai</description>
	<lastBuildDate>Mon, 21 Feb 2011 12:29:36 +0000</lastBuildDate>
	<generator>http://wordpress.org/?v=2.9.1</generator>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
			<atom10:link xmlns:atom10="http://www.w3.org/2005/Atom" rel="self" type="application/rss+xml" href="http://feeds.feedburner.com/JamesBroome" /><feedburner:info uri="jamesbroome" /><atom10:link xmlns:atom10="http://www.w3.org/2005/Atom" rel="hub" href="http://pubsubhubbub.appspot.com/" /><item>
		<title>Automatically starting the Windows Server AppFabric Caching Service</title>
		<link>http://feedproxy.google.com/~r/JamesBroome/~3/qEGVboq9yvo/</link>
		<comments>http://jamesbroo.me/automatically-starting-the-windows-server-appfabric-caching-service/#comments</comments>
		<pubDate>Mon, 21 Feb 2011 12:22:52 +0000</pubDate>
		<dc:creator>James</dc:creator>
				<category><![CDATA[Uncategorized]]></category>
		<category><![CDATA[.NET]]></category>
		<category><![CDATA[infusion]]></category>
		<category><![CDATA[PowerShell]]></category>

		<guid isPermaLink="false">http://jamesbroo.me/?p=292</guid>
		<description><![CDATA[My current project makes heavy use of the Windows Server AppFabric Caching Service and whilst I think this is great piece of technology, it does have a pretty big hole in functionality. There’s currently no supported, out-the-box way to get a cache host (or the entire cluster) to start automatically, say after a server is [...]]]></description>
			<content:encoded><![CDATA[<p>My current project makes heavy use of the Windows Server AppFabric Caching Service and whilst I think this is great piece of technology, it does have a pretty big hole in functionality. There’s currently no supported, out-the-box way to get a cache host (or the entire cluster) to start automatically, say after a server is rebooted – deliberately or otherwise. This is a bit of a limitation – after you spend time digesting all the configuration options and understood the importance of high availability and set up your cluster perfectly, you still need to be on permanent stand by in case one of your production servers goes down. At the minute, without logging on to one of the hosts in the cluster and manually executing some Powershell commands, your cache host remains permanently “out of the cluster” if something went wrong. Oh dear.</p>
<p>Some trawling around the web throws up some interesting but conflicting discussions  &#8211; on the one hand, <a href="http://social.msdn.microsoft.com/Forums/en-US/velocity/thread/03a6ab4a-1dff-4490-bf63-97c1098519e3#ea13b7fc-ec2f-4501-8ea1-f25ed0ff810a" target="_blank">this functionality is not supported</a>, but on the other, <a href="http://stackoverflow.com/questions/2874786/starting-appfabric-cache-cluster-automatically" target="_blank">it does work by changing the Windows service to start up automatically</a> (although with the caveat <a href="http://social.msdn.microsoft.com/Forums/en/velocity/thread/48676b42-2959-4128-b2c3-d3111d37ae6d" target="_blank">that this could take up to 15 mins to restart</a>), and <a href="http://social.msdn.microsoft.com/Forums/en-US/velocity/thread/03a6ab4a-1dff-4490-bf63-97c1098519e3#ea13b7fc-ec2f-4501-8ea1-f25ed0ff810a" target="_blank">it will never work with an XML based configuration store</a>.</p>
<p>Confusing to say the least. Changing the AppFabric Caching Service to have a startup type of Automatic in the Services control panel resulted in some really unpredictable behaviour. We are using an XML based configuration store, so maybe this was never going to work, but all sorts of errors and crashes started appearing in the Event Log, basically the cache became unusable until this was changed back to Manual.</p>
<p>So, a custom approach was needed…</p>
<h2>Solution</h2>
<p>The custom solution is pretty simple, but there’s a few moving parts so I’ve broken it down piece by piece. It involves a custom Powershell script to start the cache host or cluster that is trigged by a Windows Scheduled Task upon system startup.</p>
<h3>Powershell settings</h3>
<p>By default, Powershell ships in a restricted mode that denies the execution of scripts. This always catches me out, and did so when I migrated this solution from running fine in my development environment onto one of our production servers. After failing silently a few times, I eventually realised what was going on, so make sure your Powershell is configured correctly before you start to you don’t waste time like I did!</p>
<p>Open the Powershell console (you may need to Run as Administrator) and execute the following commandlet to grant script execution:</p>
<pre class="brush: xml;">set-executionpolicy RemoteSigned</pre>
<p>Accept the warning by entering Y and you’re good to go.</p>
<h3>The Script</h3>
<p>The script itself is pretty simple. It basically imports the relevant modules, tells the caching service to look for the local installation to get the cluster settings and then starts the cache host based on the local machine name using the default cache port.</p>
<pre class="brush: xml;">import-module DistributedCacheAdministration 

$computer = gc env:computername 

use-cachecluster 

start-cachehost -hostname $computer -cacheport 22233</pre>
<p>I created this as a new Powershell script called StartCacheHost.ps1</p>
<h3>Scheduled Task</h3>
<p>In order to call this script at system startup, I created a new scheduled task using the Task Scheduler.</p>
<p>After opening the Task Scheduler, I created a new task as follows:</p>
<p><a href="http://jamesbroo.me/blog/wp-content/uploads/2011/02/CreateTask.png"><img style="display: inline; border-width: 0px;" title="CreateTask" src="http://jamesbroo.me/blog/wp-content/uploads/2011/02/CreateTask_thumb.png" border="0" alt="CreateTask" width="644" height="479" /></a></p>
<p>Make sure that this task is set to run whether the user is logged in or not, and that it’s configured to run for your flavour of OS. I also ticked the “Run with highest privileges” box as I usually have to run the Caching Administration Powershell Tool as an Administrator.</p>
<p>Moving to the Triggers tab, I added a new trigger to execute the script on system startup as follows:</p>
<p><a href="http://jamesbroo.me/blog/wp-content/uploads/2011/02/Trigger.png"><img style="display: inline; border-width: 0px;" title="Trigger" src="http://jamesbroo.me/blog/wp-content/uploads/2011/02/Trigger_thumb.png" border="0" alt="Trigger" width="644" height="341" /></a></p>
<p>I opted to delay execution for 30 seconds after startup. This may not be necessary, but it&#8217; felt like a minor trade-off to ensure everything’s up and running before we try to start the cache host.</p>
<p>Finally, moving to the Actions tab, I set the action to execute as follows:</p>
<p><a href="http://jamesbroo.me/blog/wp-content/uploads/2011/02/Action.png"><img style="display: inline; border-width: 0px;" title="Action" src="http://jamesbroo.me/blog/wp-content/uploads/2011/02/Action_thumb.png" border="0" alt="Action" width="644" height="369" /></a></p>
<p>The program/script to run is the Powershell executable and the argument to pass in is the full path to the saved StartCacheHost.ps1 script.</p>
<h2>Testing</h2>
<p>In order to test that everything’s hanging together nicely, I wanted to start at the bottom and build upwards. So firstly, I wanted to test that the script itself would work.</p>
<p>On a running cache cluster, I stopped the current host by executing the following commandlet in the Caching Administration Powershell Tool:</p>
<pre class="brush: xml;">stop-cachehost –hostname xxxxxxx –cacheport 22233</pre>
<p>where xxxxxxx is the local machine name (the current host).</p>
<p>Running:</p>
<pre class="brush: xml;">get-cachehost</pre>
<p>returns information about the hosts running in the cluster and indicates that my current host now has a status of “DOWN”.</p>
<p>I then opened the Windows Powershell console and executed my StartCacheHost.ps1 script at the command prompt. Running get-cachehost again indicates that my host is now back up and running again – i.e. it has rejoined the cluster.</p>
<p>I then moved on to testing the scheduled task by stopping the current cache host again. This time I selected my new task in Task Scheduler and manually executed it by clicking Run.</p>
<p>Again, running get-cachehost indicates that my host is back up and running again.</p>
<p>Finally, to piece everything together, I restart my cache host server. 30 seconds after the server comes back up, my script executes and the host has rejoined the cluster. Perfect.</p>
<h2>Considerations</h2>
<p>The script above assumes that you’re running in a cluster (i.e. more than one cache host) and that the cluster is in a working state so that the current host can rejoin the cluster. If the cluster was down (e.g. if too many lead hosts had gone down) then the host would not be able to re-join the cluster.</p>
<p>I would treat these cases however as critical failures as the entire cluster has gone down and manual intervention is probably required anyway. Ideally, I’d like to be able to check if the cluster is running before executing the start-cachehost command – if there’s no cluster running then this could be swapped for start-cachecluster, although whether this would work would depend on the configuration of lead hosts etc.</p>
<p>I also wanted this behaviour to function in my development environment to save me having to start the caching service whenever I rebooted my laptop. In this case, where I know that there’s only ever one host running in the cluster, I would change the script to execute the start-cachecluster command instead of the start-cachehost e.g.</p>
<pre class="brush: xml;">import-module DistributedCacheAdministration 

use-cachecluster 

start-cachecluster</pre>
<img src="http://feeds.feedburner.com/~r/JamesBroome/~4/qEGVboq9yvo" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://jamesbroo.me/automatically-starting-the-windows-server-appfabric-caching-service/feed/</wfw:commentRss>
		<slash:comments>10</slash:comments>
		<feedburner:origLink>http://jamesbroo.me/automatically-starting-the-windows-server-appfabric-caching-service/</feedburner:origLink></item>
		<item>
		<title>Spark view engine and HTML 5</title>
		<link>http://feedproxy.google.com/~r/JamesBroome/~3/uxIO_XNIIio/</link>
		<comments>http://jamesbroo.me/spark-view-engine-and-html-5/#comments</comments>
		<pubDate>Mon, 03 Jan 2011 10:45:31 +0000</pubDate>
		<dc:creator>James</dc:creator>
				<category><![CDATA[Uncategorized]]></category>
		<category><![CDATA[Asp.Net]]></category>
		<category><![CDATA[infusion]]></category>
		<category><![CDATA[MVC]]></category>
		<category><![CDATA[Spark]]></category>

		<guid isPermaLink="false">http://jamesbroo.me/?p=276</guid>
		<description><![CDATA[It’s no secret that I love the Spark view engine. I’ve blogged about it before and nearly two years down the line since I first used it (and a number of production projects later), I still think it’s the best view engine out there for ASP.NET MVC.
In a nutshell, there’s two reasons why I think [...]]]></description>
			<content:encoded><![CDATA[<p>It’s no secret that I love the Spark view engine. I’ve blogged about it before and nearly two years down the line since I first used it (and a number of production projects later), I still think it’s the best view engine out there for ASP.NET MVC.</p>
<p>In a nutshell, there’s two reasons why I think this.</p>
<h3>1. The in-built view-specific syntax is so well thought out and makes building view files really easy.</h3>
<p>For example, I love the ?{} conditional syntax which means that when placed next to an attribute, it will only be output if the statement evaluates to true:</p>
<pre class="brush: xml;">&lt;div id="errorMessage" style="display:none;?{Model.ErrorMessage == null}"&gt;
    Error message...
&lt;/div&gt;</pre>
<p>If you combine this inside a loop with the auto-defined xIsFirst, xIsLast variables you can do something like this:</p>
<pre class="brush: xml;">&lt;ul&gt;
    &lt;li each="var product in Model.Products" class="first?{productIsFirst} last?{productIsLast}"&gt;
        ${product.Name}
    &lt;/li&gt;
&lt;/ul&gt;</pre>
<p>This is really powerful stuff. Adding classes to the last or first element in a list is something I always get asked to do by my friendly interface developers and before Spark (and deep in WebForms territory) this always meant helper methods, or messy logic inside view files. Nasty business. (By the way, in the example above, if the item is neither the first or the last element, then the entire class=”” attribute will just be ingored, i.e. no messy empty HTML attributes are rendered).</p>
<h3>2. It fits the way I work in a multi-functional team.</h3>
<p>I tend to be lucky enough to have dedicated interface developers on a project who specialise in creating beautifully clean, standards compliant, accessible HTML. I let them do their job and they let me do mine. Spark allows us to work side by side nicely without treading on each other&#8217;s toes. Integrating static HTML pages delivered by an iDev is really easy as the syntax is terse and succinct. Equally, an iDev looking at a Spark view file doesn’t run a mile screaming (which they used to do when faced with a WebForms .aspx page full of server controls). As Louis states -</p>
<blockquote><p>The idea is to allow the HTML to dominate the flow and the code to fit seamlessly.</p></blockquote>
<p>I think it does this beautifully. If I was more of a one-man-band and was responsible for creating everything myself, or did not have experienced web developers to hand, I’d probably prefer NHaml, which seems to have a much more developer focussed approach. I can definitely see the appeal here, but like I say, I tend to work with guys who know HTML and give me HTML to integrate into my applications.</p>
<h3>Which brings me on to the subject of this post…</h3>
<p>So things have moved on a bit since I started my last project and this time around I was given a lovely set of static HTML pages from a completely separate digital agency altogether. These people obviously know what they’re doing and have fully embraced HTML 5 and all it’s new syntax and features.</p>
<p>“Great” I thought, this should be easy. Just need to go through the views, binding up my data and adding in Spark logic wherever possible. And then I got this:</p>
<p><a href="http://jamesbroo.me/blog/wp-content/uploads/2011/01/image.png"><img style="display: inline; border-width: 0px;" title="image" src="http://jamesbroo.me/blog/wp-content/uploads/2011/01/image_thumb.png" border="0" alt="image" width="644" height="360" /></a></p>
<p>Turns out that <strong>&lt;section&gt;</strong> is a new HTML 5 element which was being used to great effect in my HTML. Turns out, it’s also a key word in the world of Spark and the two don’t play together too nicely. A few others have run into this problem and there’s <a href="http://sparkviewengine.codeplex.com/workitem/5625" target="_blank">a couple of suggestions</a>:</p>
<p>Use the the namespace feature in Spark. This involves adding a prefix attribute in your Spark configuration like so:</p>
<pre class="brush: xml;">&lt;spark&gt;
  &lt;pages prefix="s"&gt;
  &lt;/pages&gt;
&lt;/spark&gt;</pre>
<p>Which then means you need to qualify all your Spark elements:</p>
<pre class="brush: xml;">&lt;s:use content="view" /&gt;</pre>
<p>I didn’t like this approach and found that it broke a lot of the terseness of the Spark syntax. It meant that I couldn’t use the shorthand method for calling partial views simply by specifying the file name.</p>
<p>The next suggestion was to wrap the &lt;section&gt; elements in the !{} syntax, effectively rendering them as non-encoded HTML literals:</p>
<pre class="brush: xml;">!{"&lt;section class='box error'&gt;"}
    Error message...
!{"&lt;/section&gt;"}</pre>
<p>This approached worked the best – whilst making the &lt;section&gt; elements themselves a bit ugly, it left everything else Spark related in tact.</p>
<p>So, I got past that issue, thinking I was home free, only to be faced with:</p>
<p><a href="http://jamesbroo.me/blog/wp-content/uploads/2011/01/image1.png"><img style="display: inline; border: 0px;" title="image" src="http://jamesbroo.me/blog/wp-content/uploads/2011/01/image_thumb1.png" border="0" alt="image" width="644" height="127" /></a></p>
<p>Oh dear. Turns out that &lt;header&gt; and &lt;footer&gt; are also new elements in HTML 5. I tend to create partial views for both my header and footer logic and up to now have named them (quite sensibly) _header.spark and _footer.spark. Using the shorthand syntax for rendering views, I was able to call them in my layout file like so:</p>
<pre class="brush: xml;">&lt;body&gt;
    &lt;header /&gt;
        &lt;use content="view" /&gt;
    &lt;footer /&gt;
&lt;/body&gt;</pre>
<p>Well, not any more. Spark is trying to render my partial view called _header.spark, which contains my HTML 5 markup, including the &lt;header&gt; element. Hence the recursive rendering error.</p>
<p>The only solution I found to this was to break from tradition and rename my partial view files to _headerNav.spark and _footerNav.spark, which avoids the naming conflicts altogether.</p>
<h3>Summary</h3>
</p>
<p>HTML 5 brings some new markup syntax which conflicts with the inner workings of the Spark view engine. The most noticeable impact is the &lt;section&gt; element, which cannot be used as it stands with Spark without applying one of the workarounds detailed above.</p>
<p>Care should also be taken when naming partial views so as not to create naming conflicts with the new HTML elements available in HTML 5.</p>
<p>That said, I would still use Spark on projects as the benefits still massively outweigh these downsides. Hopefully the &lt;section&gt; issue will be resolved in a future release, but for now I’m prepared to live with my views being slightly less sparkly.</p>
<img src="http://feeds.feedburner.com/~r/JamesBroome/~4/uxIO_XNIIio" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://jamesbroo.me/spark-view-engine-and-html-5/feed/</wfw:commentRss>
		<slash:comments>4</slash:comments>
		<feedburner:origLink>http://jamesbroo.me/spark-view-engine-and-html-5/</feedburner:origLink></item>
		<item>
		<title>And now for something completely different</title>
		<link>http://feedproxy.google.com/~r/JamesBroome/~3/1w6epsoIKX8/</link>
		<comments>http://jamesbroo.me/and-now-for-something-completely-different/#comments</comments>
		<pubDate>Wed, 15 Sep 2010 08:00:25 +0000</pubDate>
		<dc:creator>James</dc:creator>
				<category><![CDATA[Uncategorized]]></category>
		<category><![CDATA[infusion]]></category>

		<guid isPermaLink="false">http://jamesbroo.me/?p=264</guid>
		<description><![CDATA[I’ve been pretty quiet recently on the blogging, twitter, community, Sharp Architecture, Who Can Help? front – for a month or two (or three) at least. Those that know me will know why but for those that don’t, I made the decision to leave EMC Consulting a couple of months ago. It was a hard [...]]]></description>
			<content:encoded><![CDATA[<p>I’ve been pretty quiet recently on the blogging, <a href="http://twitter.com/broomej" target="_blank">twitter</a>, community, <a href="http://www.sharparchitecture.net" target="_blank">Sharp Architecture</a>, <a href="http://whocanhelpme.codeplex.com" target="_blank">Who Can Help?</a> front – for a month or two (or three) at least. Those that know me will know why but for those that don’t, I made the decision to leave EMC Consulting a couple of months ago. It was a hard decision as my time at Conchango/EMC had been the best years of my career and I met many great people who have influenced and helped me tremendously, not to mention some life-long friends. I hope those people know who they are. The majority of the content of this blog has come out of projects that I’ve directly worked on at EMC, or from offshoot community projects that I’ve worked on with former colleagues.</p>
<p>But, enough of the past. As well as leaving EMC, my wife and I decided to leave London and, in fact, the UK. I’m really pleased to say that I have just joined another awesome consultancy &#8211; <a href="http://www.infusion.com" target="_blank">Infusion</a> &#8211; and have relocated to their office in Dubai, UAE. This is obviously a big step – new job, new company, new country – hence why everything else has taken a back seat whilst we re-organise our lives<img style="margin: 12px 0px 5px 45px; display: inline;" src="http://www.infusion.com/images/header/infusion-logo.jpg" alt="" align="right" />!</p>
<p>I’ve been at Infusion for a week now and it’s starting to feel normal (although Dubai is going to take a bit longer to get used to!). As with any consultancy, I’m not sure exactly what I’ll be working on just yet, but there’s talk of exciting WPF and Surface projects, and conversations are being had about Azure so I’m pretty keen to get my teeth stuck into something big.</p>
<p>As time goes on, this should start to fuel more topics of discussion on this blog, but in the meantime hopefully a normal service will resume with everything else. And, I should now finally be able to get around to contributing properly to <a href="http://www.sharparchitecture.net" target="_blank">Sharp Architecture</a> after <a href="http://weblogs.asp.net/alecwhittington/" target="_blank">Alec</a> so kindly asked me to join the team.</p>
<img src="http://feeds.feedburner.com/~r/JamesBroome/~4/1w6epsoIKX8" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://jamesbroo.me/and-now-for-something-completely-different/feed/</wfw:commentRss>
		<slash:comments>3</slash:comments>
		<feedburner:origLink>http://jamesbroo.me/and-now-for-something-completely-different/</feedburner:origLink></item>
		<item>
		<title>My latest project has launched!</title>
		<link>http://feedproxy.google.com/~r/JamesBroome/~3/XIIrMj5cMuU/</link>
		<comments>http://jamesbroo.me/my-latest-project-has-launched/#comments</comments>
		<pubDate>Mon, 21 Jun 2010 16:40:33 +0000</pubDate>
		<dc:creator>James</dc:creator>
				<category><![CDATA[Uncategorized]]></category>
		<category><![CDATA[Azure]]></category>

		<guid isPermaLink="false">http://jamesbroo.me/my-latest-project-has-launched/</guid>
		<description><![CDATA[I’m really proud to announce that my latest project has now officially been released into the wild at www.seethedifference.org!

Some of my recent posts around Windows Azure have referred to this project and it will now be the subject of some upcoming posts too.
This was a great project from a technical perspective:

It was the first *full* [...]]]></description>
			<content:encoded><![CDATA[<p>I’m really proud to announce that my latest project has now officially been released into the wild at <a href="http://www.seethedifference.org">www.seethedifference.org</a>!</p>
<p><a href="http://www.seethedifference.org" target="_blank"><img style="display: block; float: none; margin-left: auto; margin-right: auto;" src="http://www.seethedifference.org/Content/images/logo.gif" alt="See the difference - home page" /></a></p>
<p>Some of my recent posts around Windows Azure have referred to this project and it will now be the subject of some upcoming posts too.</p>
<p>This was a great project from a technical perspective:</p>
<ul>
<li>It was the first *<strong>full</strong>* cloud solution that we have built/delivered at EMC Consulting – fully running on the Windows Azure platform, using Web Roles, Worker Roles, Azure Storage and SQL Azure</li>
<li>The total build time was 7 weeks due to properly re-using IP, patterns and practices from previous projects</li>
</ul>
<p>A publicity perspective:</p>
<ul>
<li>Members of the team have presented at least 5 Microsoft conferences, events and user groups about the project</li>
</ul>
<p>And the non-tangible feel good perspective:</p>
<ul>
<li>We helped a new UK charity startup launch their business by making it financially and technically possible</li>
<li>We contributed to something that will hopefully make a difference to a large number of good causes</li>
</ul>
<p>Please check out the site, promote it, and if you’re feeling generous make a donation!!</p>
<img src="http://feeds.feedburner.com/~r/JamesBroome/~4/XIIrMj5cMuU" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://jamesbroo.me/my-latest-project-has-launched/feed/</wfw:commentRss>
		<slash:comments>3</slash:comments>
		<feedburner:origLink>http://jamesbroo.me/my-latest-project-has-launched/</feedburner:origLink></item>
		<item>
		<title>Developing outside the cloud with Azure</title>
		<link>http://feedproxy.google.com/~r/JamesBroome/~3/l1dyj4LvYOw/</link>
		<comments>http://jamesbroo.me/developing-outside-the-cloud-with-azure/#comments</comments>
		<pubDate>Mon, 10 May 2010 13:36:20 +0000</pubDate>
		<dc:creator>James</dc:creator>
				<category><![CDATA[Uncategorized]]></category>
		<category><![CDATA[Azure]]></category>

		<guid isPermaLink="false">http://jamesbroo.me/?p=258</guid>
		<description><![CDATA[My colleague Simon Evans and I recently presented at the UK Azure .Net user group in London about a project that we have just delivered. The project is a 100% cloud solution, running in Windows Azure web roles and making use of Azure Table and Blob Storage and SQL Azure. Whilst development on the project [...]]]></description>
			<content:encoded><![CDATA[<p>My colleague <a href="http://consultingblogs.emc.com/simonevans/" target="_blank">Simon Evans</a> and I recently <a href="http://jamesbroo.me/uk-azurenet-user-group-presentation/" target="_blank">presented at the UK Azure .Net</a> user group in London about a project that we have just delivered. The project is a 100% cloud solution, running in Windows Azure web roles and making use of Azure Table and Blob Storage and SQL Azure. Whilst development on the project is complete, the site is not yet live to the public, but will be soon, which will enable me to talk more freely on this subject.</p>
<p>A few of the implementation specific details that we talked about in the presentation focussed on how we kept the footprint of Azure as small as possible within our solution. I explained why this is a good idea and how it can be achieved, so for those who don’t want to watch the video, here’s the write-up…</p>
<h2>Working with the Dev Fabric</h2>
<p>The Windows Azure SDK comes with the Dev Fabric, which is a simulation of the Azure platform that allows developers to run Azure solutions locally on their developer machines. It simulates the web and worker roles and also the various storage sources – table, blob and queue so that the entire solution can be run as-is on a single machine. Of course, this is just a simulation, and doesn’t provide any of the benefits that the real production Azure platform gives but it is a vital tool in being able to develop for the platform.</p>
<p>However, the Dev Fabric gets in the way of rapid development. Running in the Dev Fabric involves hitting F5 in Visual Studio which builds the solution, packages the solution, deploys the packaged solution, starts up the virtual environment, starts the storage services, loads the browser and finally loads the the site. This whole process, which Visual Studio orchestrates, can take a number of minutes, depending on the size of your solution and the spec of your machine.</p>
<p>A build in Visual Studio is not enough to see your changes. My development process of running all unit tests, seeing a green light, refreshing the browser to make sure my application still hangs together and I haven’t broken any UI logic now has a massive extra step which adds friction to the process. Even more so if all you changed was one line of HTML, or CSS – remember all these files form part of the deployed solution and so every time they change they need to get packaged up and copied somewhere else. Saving a file and hitting refresh in a browser is not going to work!</p>
<p>So, right from day one, I was looking to find ways to run our solution without depending on the Dev Fabric. This may seem slightly backwards – that I was building a cloud solution that would run outside the cloud, but reducing this overhead in the development process – a small one – but one that would happen numerous times a day meant we were able to deliver our project on time.</p>
<p>Interestingly, whilst the primary goal was breaking the dependency on the Azure platform to remove friction during the development process, the result is a well architected solution that has a minimal Azure footprint. Not only does this allow for greater flexibility down the line, but also means that a team with minimal Azure development experience can work effectively in an Azure solution as the necessary implementation specific knowledge is encapsulated in just a few places.</p>
<h2>Data Access and the Repository Pattern</h2>
<p>I tend to follow a similar pattern when building applications of having an Infrastructure or Data layer that deals with data access or any hard dependencies on external services. My friends <a href="http://howard.vanrooijen.co.uk/blog/" target="_blank">Howard</a> and <a href="http://jonathangeorge.co.uk/" target="_blank">Jon</a> and I have talked a lot about this in the <a href="http://whocanhelpme.codeplex.com/" target="_blank">Who Can Help Me? project</a>, which provides an architectural showcase for an MVC web application, building on top of the <a href="http://sharparchitecture.net/" target="_blank">Sharp Architecture project</a>. By adhering to these same patterns, we were able to encapsulate all our data access into repositories which dealt with our domain entities when reading and writing. This meant that our entire application has no concept of where these entities are stored until you get into the repository itself.</p>
<p>As Martin Fowler writes:</p>
<blockquote><p><em>&#8220;A Repository mediates between the domain and data mapping layers, acting like an in-memory domain object collection. Client objects construct query specifications declaratively and submit them to Repository for satisfaction. Objects can be added to and removed from the Repository, as they can from a simple collection of objects, and the mapping code encapsulated by the Repository will carry out the appropriate operations behind the scenes. Conceptually, a Repository encapsulates the set of objects persisted in a data store and the operations performed over them, providing a more object-oriented view of the persistence layer. Repository also supports the objective of achieving a clean separation and one-way dependency between the domain and data mapping layers.&#8221;</em></p></blockquote>
<p>So, in our case we were able to encapsulate all the Azure Table Storage specific logic inside the repository; we actually took this one step further and encapsulated specific queries into Commands which we could reuse across repositories if necessary.</p>
<h2>Dependency Injection and stub Repositories</h2>
<p>However, whilst keeping the Azure footprint small, this didn’t break the dependency on data access. In order to run the application we needed to retrieve data, which made calls into Table Storage, which meant we still needed the Dev Fabric to be running.</p>
<p>So… as our repositories all inherit from interfaces and are injected at runtime using the <a href="http://www.castleproject.org/container/index.html" target="_blank">Castle Windsor IOC</a> container, we were able to create stub implementations of these repositories which we could choose to inject instead, meaning we could run the application without the Dev Fabric. This becomes incredibly useful if you’re not actually concerned with the actual data that is being displayed at that point – e.g. you’re building validation logic, or the UI interactions etc.</p>
<p>We use the Fluent Registration feature of Castle Windsor which allows us to register dependencies based on a convention over configuration approach – finding components based on their namespace and location in this case. Rather than have to manually configure the solution to decide whether to use the ‘real’ table storage repositories, or the stub repositories, I wanted this to ‘just work’.</p>
<p>This was achieved by checking the RoleEnvironment.IsAvailable flag that is part of the Azure ServiceRuntime API. The code below shows how we change our conventions for registration based on this knowledge – so, if we’re running in the Dev Fabric (or the live Azure service) we get our real repositories, otherwise we get our stubs.</p>
<p>For more information on using the fluent registration approach, take a look at the <a href="http://whocanhelpme.codeplex.com/" target="_blank">Who Can Help Me? project</a>.</p>
<pre class="brush: csharp;">public void Register(IWindsorContainer container)
{
    var repositoryNamespace = ".Repositories";

    if (!RoleEnvironment.IsAvailable)
    {
        // If running outside role/dev fabric
        // then use stub repositories
        repositoryNamespace = ".Stub";
        Trace.WriteLine("RUNNING OUTSIDE OF AZURE ROLE - STARTING UP WITH STUB REPOSITORIES");
    }

    container.Register(
        AllTypes.Pick()
            .FromAssembly(Assembly.GetAssembly(typeof(InfrastructureRegistrarMarker)))
            .If(f =&gt; f.Namespace.Contains(repositoryNamespace))
            .WithService.FirstNonGenericCoreInterface("SeeTheDifference.Domain.Contracts.Repositories"));
}</pre>
<h2>Configuration</h2>
<p>The Azure environment changes the game slightly when it comes to application configuration as the web.config no longer provides the ability to change configuration at runtime. The reason behind this is that the web.config is packaged up and deployed just like any other code asset as part of your Azure deployment, which means that in order to change a value, you have to go through this whole process again.</p>
<p>The Azure environment does provide another source of configuration in the form of the .cscfg file, which is the Cloud Service Configuration and governs the details about your web or worker roles e.g. number of instances, endpoints, connection strings for Azure data stores. It can also be used to store any custom configuration settings in the form of key-value pairs, similar to the App Settings section you would find in a normal web.config.</p>
<p>So, the recommended approach is to use the .cscfg for any environment specific values as these can then be changed at runtime, which would cause your Azure roles to recycle without re-deployment, just like changing the web.config would in a normal IIS setup.</p>
<p>However, the downside to using the .cscfg is that Azure configuration is only available when the role environment is running – i.e. your using the Dev Fabric. Once again we wanted to break this dependency and be able to run our application outside of this environment.</p>
<p>The approach we took was twofold:</p>
<p>Firstly we encapsulated all our configuration calls into one place – a configuration manager that was injected into any class that needed information from configuration. By doing this we could implement a global switch to check whether we were running inside an Azure environment (just like when we decided which repositories to register) and act accordingly.</p>
<p>Secondly,  we chose to duplicate all our custom configuration settings in .cscfg into our web.config App Settings and read from the appropriate source, according to the RoleEnvironment.IsAvailable flag:</p>
<pre class="brush: csharp;">/// &lt;summary&gt;
/// Gets a named configuration setting from application configuration.
/// &lt;/summary&gt;
/// &lt;param name="name"&gt;The name of configuration setting.&lt;/param&gt;
/// &lt;returns&gt;&lt;/returns&gt;
public string GetSetting(string name)
{
    if (RoleEnvironment.IsAvailable)
    {
        return RoleEnvironment.GetConfigurationSettingValue(name);
    }

    return ConfigurationManager.AppSettings[name];
}</pre>
<h2>Diagnostics</h2>
<p>The Azure diagnostics are key to monitoring how your application is performing and are really the only way to know where and when you need to scale your application out or in. They’re also the source of information for events and custom tracing.</p>
<p>The <a href="http://msdn.microsoft.com/en-us/library/ee843890.aspx" target="_blank">documentation for configuring the Azure tracing</a> recommends that you add the following configuration to your application’s web.config (and in fact, adds this automatically if you use the role project templates):</p>
<pre class="brush: xml;">&lt;system.diagnostics&gt;
    &lt;trace&gt;
        &lt;listeners&gt;
            &lt;add type="Microsoft.WindowsAzure.Diagnostics.DiagnosticMonitorTraceListener, Microsoft.WindowsAzure.Diagnostics, Version=1.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35"
                name="AzureDiagnostics"&gt;
                &lt;filter type="" /&gt;
            &lt;/add&gt;
        &lt;/listeners&gt;
    &lt;/trace&gt;
&lt;/system.diagnostics&gt;</pre>
<p>The problem here is that we’re tightly coupled again to the role environment, and as this configuration gets loaded and read at application startup, you’re not going to get very far if you’re not running within an Azure environment.</p>
<p>We chose to remove this configuration and add the trace listener programmatically at application startup, after performing the same check on the RoleEnvironment.IsAvailable:</p>
<pre class="brush: csharp;">/// &lt;summary&gt;
/// Initialises the Azure diagnostics tracing
/// &lt;/summary&gt;
public void Initialise()
{
    if (RoleEnvironment.IsAvailable)
    {
        Trace.Listeners.Add(new DiagnosticMonitorTraceListener());
    }
}</pre>
<p>This means that our Azure diagnostics tracing is now only initialised if we need it, meaning we can run without it when we’re in a normal ISS set up.</p>
<h2>Summary</h2>
<p>Hopefully this has shown that developing an Azure application does not have to be a process that takes over your entire solution and forces you down a particular style of development.</p>
<p>By architecting your solution well you can minimise the footprint that Azure has within your solution, which means that it’s easy to break the dependencies if required.</p>
<p>Being able to run an application in a normal IIS setup, without the Dev Fabric speeds up the development process, especially for those working higher up the stack and dealing solely with UI and presentation logic.</p>
<p>Using RoleEnvironment.IsAvailable to determine whether your running “in the cloud” or not allows you to act accordingly if you want to provide alternative scenarios.</p>
<p>By reducing the footprint of Azure within the solution, inexperienced teams can work effectively and acquire the Azure specific knowledge as and when required.</p>
<img src="http://feeds.feedburner.com/~r/JamesBroome/~4/l1dyj4LvYOw" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://jamesbroo.me/developing-outside-the-cloud-with-azure/feed/</wfw:commentRss>
		<slash:comments>5</slash:comments>
		<feedburner:origLink>http://jamesbroo.me/developing-outside-the-cloud-with-azure/</feedburner:origLink></item>
		<item>
		<title>UK AzureNET User Group presentation</title>
		<link>http://feedproxy.google.com/~r/JamesBroome/~3/goQvQMYqYZM/</link>
		<comments>http://jamesbroo.me/uk-azurenet-user-group-presentation/#comments</comments>
		<pubDate>Tue, 04 May 2010 08:22:17 +0000</pubDate>
		<dc:creator>James</dc:creator>
				<category><![CDATA[Uncategorized]]></category>
		<category><![CDATA[Azure]]></category>
		<category><![CDATA[MVC]]></category>

		<guid isPermaLink="false">http://jamesbroo.me/?p=250</guid>
		<description><![CDATA[The video footage of our recent presentation at the UK AzureNET user group is now online. The presentation is a technical deep-dive into my most recent project at EMC Consulting &#8211; a 100% Azure based solution. The original video can be viewed in HD on exposureroom.com or inline below.
The presentation outline is as follows:


What is [...]]]></description>
			<content:encoded><![CDATA[<p>The video footage of our recent presentation at the <a href="http://ukazurenet.com/" target="_blank">UK AzureNET user group</a> is now online. The presentation is a technical deep-dive into my most recent project at <a href="http://uk.emc.com/services/index.htm" target="_blank">EMC Consulting</a> &#8211; a 100% Azure based solution. The original video can be <a title="UK AzureNET User Group: See The Difference by Ian Smith - View it on ExposureRoom" href="http://exposureroom.com/a64b69a011a94b6dbc17ae63dc20e286" target="_blank">viewed in HD on exposureroom.com</a> or inline below.</p>
<p>The presentation outline is as follows:</p>
<div id="_mcePaste">
<ul>
<li>What is See the Difference?</li>
<li>Demo</li>
<li>Design Goals</li>
<li>Why Azure?</li>
<li>Design Decisions</li>
<li>The Architecture</li>
<li>Table Storage Development</li>
<li>Cloud Configuration</li>
<li>Diagnostics</li>
</ul>
</div>
<p><object id="xrPa64b69a011a94b6dbc17ae63dc20e286" classid="clsid:d27cdb6e-ae6d-11cf-96b8-444553540000" width="640" height="360" codebase="http://download.macromedia.com/pub/shockwave/cabs/flash/swflash.cab#version=6,0,40,0"><param name="data" value="http://exposureroom.com/flash/XRVideoPlayer2.swf?domain=exposureroom.com/&amp;assetId=a64b69a011a94b6dbc17ae63dc20e286&amp;size=md&amp;titleColor=%23ffffff" /><param name="allowNetworking" value="all" /><param name="allowScriptAccess" value="always" /><param name="allowFullScreen" value="True" /><param name="wmode" value="opaque" /><param name="src" value="http://exposureroom.com/flash/XRVideoPlayer2.swf?domain=exposureroom.com/&amp;assetId=a64b69a011a94b6dbc17ae63dc20e286&amp;size=md&amp;titleColor=%23ffffff" /><param name="name" value="xrPlayerEmbededa64b69a011a94b6dbc17ae63dc20e286" /><param name="allowfullscreen" value="True" /><embed id="xrPa64b69a011a94b6dbc17ae63dc20e286" type="application/x-shockwave-flash" width="640" height="360" src="http://exposureroom.com/flash/XRVideoPlayer2.swf?domain=exposureroom.com/&amp;assetId=a64b69a011a94b6dbc17ae63dc20e286&amp;size=md&amp;titleColor=%23ffffff" name="xrPlayerEmbededa64b69a011a94b6dbc17ae63dc20e286" wmode="opaque" allowfullscreen="True" allowscriptaccess="always" allownetworking="all" data="http://exposureroom.com/flash/XRVideoPlayer2.swf?domain=exposureroom.com/&amp;assetId=a64b69a011a94b6dbc17ae63dc20e286&amp;size=md&amp;titleColor=%23ffffff"></embed></object></p>
<img src="http://feeds.feedburner.com/~r/JamesBroome/~4/goQvQMYqYZM" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://jamesbroo.me/uk-azurenet-user-group-presentation/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://jamesbroo.me/uk-azurenet-user-group-presentation/</feedburner:origLink></item>
		<item>
		<title>Integrating N2CMS into Who Can Help Me? Part 5</title>
		<link>http://feedproxy.google.com/~r/JamesBroome/~3/kIpp6MeiQSA/</link>
		<comments>http://jamesbroo.me/integrating-n2cms-into-who-can-help-me-part-5/#comments</comments>
		<pubDate>Mon, 26 Apr 2010 09:02:01 +0000</pubDate>
		<dc:creator>James</dc:creator>
				<category><![CDATA[Uncategorized]]></category>
		<category><![CDATA[.NET]]></category>
		<category><![CDATA[N2 CMS]]></category>
		<category><![CDATA[Who Can Help Me]]></category>

		<guid isPermaLink="false">http://jamesbroo.me/?p=246</guid>
		<description><![CDATA[This is part 5 in my series of posts about integrating the .Net open source content management system N2CMS into the Sharp Architecture demo application Who Can Help Me?.
So far, I’ve

Added the N2 assemblies
Added the edit site to the web project
Created the initial content definitions
Created the database schema
Added root nodes to the CMS database
Updated the [...]]]></description>
			<content:encoded><![CDATA[<p>This is part 5 in my series of posts about integrating the .Net open source content management system <a href="http://www.n2cms.com">N2CMS</a> into the <a href="http://sharparchitecture.net/">Sharp Architecture</a> demo application <a href="http://whocanhelpme.codeplex.com/">Who Can Help Me?</a>.</p>
<p>So far, I’ve</p>
<ul>
<li>Added the N2 assemblies</li>
<li>Added the edit site to the web project</li>
<li>Created the initial content definitions</li>
<li>Created the database schema</li>
<li>Added root nodes to the CMS database</li>
<li>Updated the Web.config</li>
<li>Set up the N2 Content Routes and intialised the CMS engine</li>
<li>Added a base CMS controller</li>
<li>Updated the HomeController to be a CMS controller</li>
<li>Tackled authentication with Open ID and the N2 membership providers</li>
<li>Built up the HomePage content definition</li>
<li>Updated the HomeController, the view model, mappers and the view</li>
</ul>
<p>We’ve now got content from inside N2 displaying on the Home page of the site, which is excellent and I could stop there. However, there’s just a couple more things I want to cover off before I wrap this series up.</p>
<p>N.B. It should be noted that a lot of this code is going to be out of data very soon! WCHM is still running against MVC 1.0 and my branch is running off an old version of N2CMS. Both the Sharp Architecture project and N2CMS are currently being updated for MVC 2.0 support, and I guess I will also have to do the same as soon as I find the time, but to keep things simple I’m going to stick with the codebase as it is for now.</p>
<p>I want to focus on adding more CMS definitions this time and creating a dynamic navigation that is populated from the CMS tree.</p>
<h2>Step 18 – Reworking the About page</h2>
<p>Our site only has one content managed page – the Home page, which is nice, but what if we wanted to add a new page to our site through N2 – that’s the point of content management after all! Well, at the minute, nothing much would happen as all our site navigation is hard coded in the Menu.spark view file. I want to be able to add new pages as I like and have them appear in this navigation dynamically. The WCHM site already has an About page, which is kind of a generic text page, so I’m going to re-work this into a N2 TextPage defintion.</p>
<p>I actually added a TextPage definition way back in <a href="http://whocanhelpme.codeplex.com/SourceControl/changeset/changes/54950" target="_blank">Changeset 54950</a> which we can use for a generic page in the site. For recap, here’s the definition:</p>
<pre class="brush: csharp;">[PageDefinition("Text Page",
    Description = "A text page.",
    SortOrder = 700,
    IconUrl = "~/edit/img/ico/png/page.png")]
[WithEditableTitle("Page Title", 5, Focus = true, ContainerName = Tabs.Content)]
[WithEditableName(ContainerName = Tabs.Content)]
[RestrictParents(typeof(HomePage), typeof(TextPage))]
public class TextPage : AbstractPage
{
    /// &lt;summary&gt;
    /// Gets or sets BodyText.
    /// &lt;/summary&gt;
    /// &lt;value&gt;
    /// The body text.
    /// &lt;/value&gt;
    [EditableFreeTextAreaAttribute("Body Text", 100, ContainerName = Tabs.Content,
        HelpText = "Set the body text for the page")]
    public string BodyText
    {
        get { return (string)GetDetail("BodyText"); }
        set { SetDetail("BodyText", value); }
    }
}</pre>
<p>We’re restricting this definition to only be available under the home page, or another text page and giving the user the ability to update one property – the Body Text, which is a string property and will be edited using a WYSIWYG HTML editor.</p>
<p>As this is already part of the solution, when I right click on the HomePage in the N2 site tree from within the admin interface and select New, I have the option to create a new TextPage:</p>
<p><a href="http://jamesbroo.me/blog/wp-content/uploads/2010/04/image2.png"><img style="display: inline; border-width: 0px;" title="image" src="http://jamesbroo.me/blog/wp-content/uploads/2010/04/image_thumb2.png" border="0" alt="image" width="644" height="442" /></a></p>
<p>I can populate some data into the new about page:</p>
<p><a href="http://jamesbroo.me/blog/wp-content/uploads/2010/04/image3.png"><img style="display: inline; border-width: 0px;" title="image" src="http://jamesbroo.me/blog/wp-content/uploads/2010/04/image_thumb3.png" border="0" alt="image" width="542" height="484" /></a></p>
<p>And save the page, which means it will now appear in the content tree:</p>
<p><a href="http://jamesbroo.me/blog/wp-content/uploads/2010/04/image4.png"><img style="display: inline; border-width: 0px;" title="image" src="http://jamesbroo.me/blog/wp-content/uploads/2010/04/image_thumb4.png" border="0" alt="image" width="242" height="204" /></a></p>
<p>As yet, we have no controller that handles the TextPage definitions, and no view to render them, however, as we have an existing non-CMS controller called AboutController, selecting the About page in the CMS tree requests a URL of /about, which calls the existing AboutController so we see the existing content.</p>
<p>If we add a new TextController to handle the TextPage definitions and the associated view, in a similar fashion to the HomeController and Index view for the home page the /about route will be handled by N2 instead to display our new CMS content.</p>
<pre class="brush: csharp;">[Controls(typeof(TextPage))]
public class TextController : N2Controller&lt;TextPage&gt;
{
    private readonly ITextPageViewModelMapper textPageViewModelMapper;

    public TextController(ITextPageViewModelMapper textPageViewModelMapper)
    {
        this.textPageViewModelMapper = textPageViewModelMapper;
    }

    public override ActionResult Index()
    {
        return View(textPageViewModelMapper.MapFrom(CurrentItem));
    }
}</pre>
<p>Here’s the associated mapper class – note that as it’s inheriting from the base page mapper class, which uses AutoMapper, we don’t actually need to add any mapping logic:</p>
<pre class="brush: csharp;">public class TextPageViewModelMapper :  BasePageViewModelMapper&lt;TextPage,TextPageViewModel&gt;,
                                        ITextPageViewModelMapper
{
    public TextPageViewModelMapper(IPageViewModelBuilder pageViewModelBuilder) : base(pageViewModelBuilder)
    {
    }
}</pre>
<p>This is because the TextPageViewModel has properties with the same name as the TextPage definition, so Automapper can just wire them up:</p>
<pre class="brush: csharp;">public class TextPageViewModel : PageViewModel
{
    public string BodyText { get; set; }

    public string Title { get; set; }
}</pre>
<p>And finally, here’s the Spark view:</p>
<pre class="brush: xml;">&lt;viewdata model="Text.Model.TextPageViewModel"/&gt;

&lt;content name="title"&gt;
 ${Model.Title}
&lt;/content&gt;

!{Model.BodyText}</pre>
<p>(pretty terse don’t you think!?)</p>
<p>So, know when we navigate to the /about URL, we see our CMS content:</p>
<p><a href="http://jamesbroo.me/blog/wp-content/uploads/2010/04/image5.png"><img style="display: inline; border-width: 0px;" title="image" src="http://jamesbroo.me/blog/wp-content/uploads/2010/04/image_thumb5.png" border="0" alt="image" width="608" height="484" /></a></p>
<p><a href="http://whocanhelpme.codeplex.com/SourceControl/changeset/changes/57978" target="_blank">Changeset reference 57978</a></p>
<h2>Step 19 – Updating the Navigation</h2>
<p>Ok. so now we can add as many pages in the CMS of type TextPage as we like. However, our navigation menu is still hard-coded to write out the original links. We need to make this dynamic so that as we add new pages, our navigation menu stays in synch.</p>
<p>We already have a NavigationController that is being called via the RenderAction method to render out the menu, so we need to update this and the associated view model to get the links from the CMS.</p>
<p>I start by updating the specification for the NavigationController by adding the following specs:</p>
<pre class="brush: csharp;">It should_ask_the_cms_tasks_for_the_navigation_items = () =&gt;
    cms_tasks.AssertWasCalled(x =&gt; x.GetNavigationItems());

It should_set_the_list_of_cms_links_correctly = () =&gt;
    result.Model&lt;MenuViewModel&gt;().CmsLinks.Count.ShouldEqual(3);</pre>
<p>This leads me to creating a new ICmsTasks interface and updating the MenuViewModel to add a list of CmsLinks, which I created as a new LinkViewModel as this could be something that I might re-use elsewhere.</p>
<pre class="brush: csharp;">public interface ICmsTasks
{
    List&lt;ContentItem&gt; GetNavigationItems();
}

public class MenuViewModel
{
    public MenuViewModel()
    {
        CmsLinks = new List&lt;LinkViewModel&gt;();
    }

    public bool IsLoggedIn { get; set; }

    public List&lt;LinkViewModel&gt; CmsLinks { get; set; }
}</pre>
<p>My new specifications fail until I update the NavigationController to call into the new ICmsTasks:</p>
<pre class="brush: csharp;">public class NavigationController : BaseController
{
    private readonly IIdentityTasks identityTasks;
    private readonly ICmsTasks cmsTasks;
    private readonly ILinkViewModelMapper linkViewModelMapper;

    public NavigationController(IIdentityTasks identityTasks, ICmsTasks cmsTasks, ILinkViewModelMapper linkViewModelMapper)
    {
        this.identityTasks = identityTasks;
        this.cmsTasks = cmsTasks;
        this.linkViewModelMapper = linkViewModelMapper;
    }

    public ActionResult Menu()
    {
        return View(
            string.Empty,
            string.Empty,
            new MenuViewModel
            {
                IsLoggedIn = this.identityTasks.IsSignedIn(),
                CmsLinks = cmsTasks.GetNavigationItems().MapAllUsing(linkViewModelMapper)
            });
    }
}</pre>
<p>So that’s all great, but now we need to create and implement our real CmsTasks layer. There’s various ways that we could implement the GetNavigationItems() functionality – we could add an extra property to the base page class – ShowInNavigation, and retrieve all of these items, or we could come up with any other complicated requirement. However, for the purposes of this demo, I’m just going to return all the top-level items, that is all the pages under the Home page. This logic would need updating if you want to show nested items or have more of a context specific navigation menu. There’s loads of help in the N2 samples and forums about all of this.</p>
<p>What’s great about integrating N2 and WCHM together is that both projects use CastleWindsor as the IOC container. When we initialise the N2 engine, we pass in our existing WindsorContainer, which means that at run time we can get any of the N2 dependencies out of the container that we need. Because of this, our CmsTasks can treat N2 as just a repository of data and it can depend on any of the N2 interfaces for accessing content. These dependencies will be inject automatically at runtime, meaning our solution is loosely coupled and we can test our tasks easily. Here’s my specs for the CmsTasks:</p>
<pre class="brush: csharp;">public abstract class specification_for_cms_tasks : Specification&lt;ICmsTasks, CmsTasks&gt;
{
    protected static IUrlParser n2Repository;

    Establish context = () =&gt;
    {
        n2Repository = DependencyOf&lt;IUrlParser&gt;();
    };
}

public class when_the_cms_tasks_is_asked_for_the_navigation_items : specification_for_cms_tasks
{
    static IList&lt;ContentItem&gt; result;

    Establish context = () =&gt;
        {
            n2Repository.Stub(x =&gt; x.StartPage).Return(An&lt;HomePage&gt;());
            n2Repository.StartPage.Children = new List&lt;ContentItem&gt;{new TextPage(), new TextPage()};
        };

    Because of = () =&gt; result = subject.GetNavigationItems();

    It should_ask_the_cms_repository_for_all_the_top_level_content_items = () =&gt;
        result.Count.ShouldEqual(2);
}</pre>
<p>In this case, I’m depending on the IUrlParser from N2, which gives me direct access to the StartPage content item property, which is my site Home page. From here, I can easily get the list of child content items.</p>
<p>Another good N2 interfaces is the IItemFinder, which gives you access to the fluent linq-style N2 sytnax for finding content items using filters etc. Take a while to look at the N2 codebase and you’ll see that you don’t need to tightly couple your app to the N2.Find… API, which forces you to create fake contexts etc for testing purposes.</p>
<p>Our actual CmsTasks implementation is then as follows:</p>
<pre class="brush: csharp;">public class CmsTasks : ICmsTasks
{
    private readonly IUrlParser n2UrlParser;

    public CmsTasks(IUrlParser n2UrlParser)
    {
        this.n2UrlParser = n2UrlParser;
    }

    public IList&lt;ContentItem&gt; GetNavigationItems()
    {
        return n2UrlParser.StartPage.Children;
    }
}</pre>
<p>All that’s left now is to update the Menu.spark view. I’ve removed the hard coded reference to the About page and added a loop of &lt;LI&gt; tags over the list of CmsLinks:</p>
<pre class="brush: xml;">&lt;ul&gt;
    &lt;li class="leaf first"&gt;!{Html.ActionLink&lt;WhoCanHelpMe.Web.Controllers.Home.HomeController&gt;(x =&gt; x.Index(), "Home")}&lt;/li&gt;
    &lt;li&gt;!{Html.ActionLink&lt;WhoCanHelpMe.Web.Controllers.Profile.ProfileController&gt;(x =&gt; x.Update(), "You!")}&lt;/li&gt;
    &lt;li if="Model.IsLoggedIn" class="leaf last"&gt;!{Html.ActionLink&lt;WhoCanHelpMe.Web.Controllers.User.UserController&gt;(x =&gt; x.SignOut(), "Sign Out")}&lt;/li&gt;
  &lt;!-- Loop over the cms links--&gt;
  &lt;li each="var cmsLink in Model.CmsLinks"&gt;
    &lt;a href="${cmsLink.Url}"&gt;${cmsLink.Title}&lt;/a&gt;
  &lt;/li&gt;
&lt;/ul&gt;</pre>
<p>Note that I’m not using the MVC HtmlHelper extension methods to build up the hyperlinks. This is simply because they’re not going to work in a CMS context. Remember that although we’re point to a TextController in this case, our pages are actually called something else (About) and it’s that which will appear in the URL. So, this breaks away from the standard controller/action/index routing convention that MVC uses. The N2ContentRoute handles this all for us, but it means that we lose some of the out the box MVC support – e.g. the HtmlHelperMethods. I think the N2 project has implemented a bunch of it’s own extension methods for this, but I don’t really like adding this to my views as it kind of feels wrong – accessing entities from data stores in the view isn’t something I want to do. I prefer my approach of accessing the N2 data further down the stack and converting to dumb view models before passing to the view.</p>
<p>Ok, so now we’re ready to add more pages. Every page that we add under the site root (the Home page) is going to render a new navigation menu link. I’ve added a few new pages here:</p>
<p><a href="http://jamesbroo.me/blog/wp-content/uploads/2010/04/image6.png"><img style="display: inline; border-width: 0px;" title="image" src="http://jamesbroo.me/blog/wp-content/uploads/2010/04/image_thumb6.png" border="0" alt="image" width="608" height="484" /></a></p>
<p><a href="http://whocanhelpme.codeplex.com/SourceControl/changeset/changes/57979" target="_blank">Changeset reference 57979</a></p>
<h2>Summary</h2>
<p>Hopefully I’ve shown here how I’d go about adding CMS driven navigation to my custom application. Remember – the point behind all of this is that what we’re building is not just a pure-CMS site. If this site was just pure content, entirely driven from a CMS then we could make things a whole lot simpler. However, experience tells me that most applications I built are more of the “custom web app” variety and content management is a supporting function. This is where N2 really comes into its own as it’s really easy to integrate into any form of .Net application.</p>
<h2>Next Time</h2>
<p>So I’ve just got one more thing to cover off before I wrap this up, and that’s Caching. This is important in a CMS backed application as there’s a lot of dynamic, changeable data and you need to find the right balance of performance and presenting the most up to date information. I’ll go through some of the approaches I’ve taken in the past.</p>
<p>Cheers</p>
<img src="http://feeds.feedburner.com/~r/JamesBroome/~4/kIpp6MeiQSA" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://jamesbroo.me/integrating-n2cms-into-who-can-help-me-part-5/feed/</wfw:commentRss>
		<slash:comments>4</slash:comments>
		<feedburner:origLink>http://jamesbroo.me/integrating-n2cms-into-who-can-help-me-part-5/</feedburner:origLink></item>
		<item>
		<title>Who Can Help Me – Q &amp; A</title>
		<link>http://feedproxy.google.com/~r/JamesBroome/~3/RUFAWGEke98/</link>
		<comments>http://jamesbroo.me/who-can-help-me-q-a/#comments</comments>
		<pubDate>Tue, 20 Apr 2010 15:41:40 +0000</pubDate>
		<dc:creator>James</dc:creator>
				<category><![CDATA[Uncategorized]]></category>
		<category><![CDATA[.NET]]></category>
		<category><![CDATA[MVC]]></category>
		<category><![CDATA[Who Can Help Me]]></category>

		<guid isPermaLink="false">http://jamesbroo.me/?p=231</guid>
		<description><![CDATA[I’ve recently been spending some time working on removing the friction in project start-up, by producing a skeleton solution for an ASP.NET MVC application, based on all the goodness that we’ve thrown into Who Can Help Me?. I ran this by my colleague Simon Brown and asked him to pull it apart and ask any [...]]]></description>
			<content:encoded><![CDATA[<p>I’ve recently been spending some time working on removing the friction in project start-up, by producing a skeleton solution for an ASP.NET MVC application, based on all the goodness that we’ve thrown into <a href="http://whocanhelpme.codeplex.com" target="_blank">Who Can Help Me?</a>. I ran this by my colleague <a href="http://consultingblogs.emc.com/simonbrown/default.aspx" target="_blank">Simon Brown</a> and asked him to pull it apart and ask any questions that came to mind.</p>
<p>The result of which is quite a good Q &amp; A session that relates directly to the Who Can Help Me solution. These are the kind of questions that people may not feel like asking in the forums, so I thought I’d post up the answers to the questions – kind of like an idiots guide to the reasoning behind a lot of the decisions we took in the journey leading to the Who Can Help Me solution.</p>
<p>It’s a bit of a long one, but here goes…</p>
<h3>How do you decide where to store interfaces? Should there be a separate interfaces project? Why are some interfaces in the Domain project and others in individual projects (e.g. Mapper interfaces are in the Web.Controllers project)?</h3>
<p>We try to reinforce a convention over configuration approach throughout the entire solution, which means that following the conventions (in this case, keeping things in the same place) means that the IOC registration is frictionless.</p>
<p>The interfaces that are used cross-project (Repositories, Services, Tasks) are stored in the Domain project. The reason for this is that the Domain project is already referenced by the other projects in the solution as the domain entities are used all the way from the repositories to the controller layer. The idea is to keep the solution as loosely coupled as possible, so minimizing the actual hard references between projects. For example – the Tasks project does not need to reference the Repositories project even though it uses repositories heavily as it just talks to repository interfaces which live in the domain layer. Equally, the Controllers project does not need to reference the Tasks project. Ideally, we wouldn’t need to have these references anywhere, but the Web project does have references to everything needed to run the application to ensure that everything is copied into the bin directory. This could be achieved using a custom build task, making the solution completely loosely coupled.</p>
<p>The interfaces that are used within a project (e.g. mappers in the controllers project) live with the implementations that they describe. These interfaces are not used cross-project and only referenced within a project.</p>
<p>Once these conventions are defined, it removes decisions about where to put things. On a micro-scale, this removes the friction and time it takes to add new interfaces to the solution. The Castle Windsor fluent registration exploits these conventions, making IOC registration frictionless i.e. adding new interfaces and implementations does not require any updates to registration code or configuration.</p>
<h3>What is the difference between a ViewModel and a FormModel? Is this really necessary? Why are they not all named ViewModel?</h3>
<p>A viewmodel is an object used to bind to a view (i.e. for display purposes) and a formmodel is an object used to bind to a set of form parameters (i.e. when an HTML form is submitted). We’ve found that keeping display and update models separate is definitely preferred as they’re rarely the same and serve different purposes. For example, a formmodel is likely to have validation requirements that a viewmodel wont. We’ve found that this naming convention works – the use of view or form is explicit enough to describe what the purpose of the class is. Some people take this a step further and use ViewModel, EditModel, CreateModel, DeleteModel however we’ve found this to be overkill in the applications we have built. However, in a heavy CRUD style application, this may be preferred.</p>
<h3>Why is MEF being used to determine Castle Windsor registrations?</h3>
<p>This is also to keep the solution as loosely coupled as possible and to reduce friction in adding new components or groups of components that need registering in the IOC container. The solution contains a number of Registrars and Initialisers. The Registrars are used for registering components in the IOC container (using the convention based fluent registration) and the Initialisers are used to set something up for the solution (e.g. replace the MVC view engine, configure the validation framework etc). All of these activities need to happen at application startup so we need something to orchestrate this activity.</p>
<p>We could have a component that does this by calling directly into all the Registrars and the Initialisers, however this tightly couples the Web project to all other layers in the solution as these components are present in all projects. Also, it adds an overhead in maintenance if a new Registrar or Initialiser is added as the central orchestrator needs to be updated.</p>
<p>The use of MEF avoids this as it treats Registrars and Initialisers as “plugins” that just need to be executed when the application starts. MEF is not performing the IOC registration, simply finding all the Registrar and Initialiser components that need to do something and calling them. This means that there are not hard coded references across all layers of the solution from the Web project and that adding a new Initialiser is simply a case of adding the new class. If it inherits from the correct interface and has the [Export] attribute then it will be found and executed. So, by looking at another initialiser, you have everything you need to know about how to create a new one – you do not need to trawl the solution trying to find the way that they are all wired up.</p>
<h3>All of your Castle registrations are dependent on the use of conventions and assume only one implementation of each interface is used by each component. How do you deal with the case for example where two services consume a different implementation of an IRepository?</h3>
<p>We’ve found the main benefit in using dependency injection and IOC is not of the ability to swap out components at runtime, but that it aids the development process by making a loosely coupled solution that is really easy to test. It is a very rare requirement that a registration needs to occur based on a condition and that there may be two possible implementations of one interface. The conventions used here do rely on the fact that there is a one to one mapping between contract and implementation, however this can be changed easily if required.</p>
<p>The fluent registrations can be overridden by using a Castle configuration file. When creating the WindsorContainer, passing in a configuration file reference will ensure that this overrides any registration.</p>
<p>Alternatively, the use of IHandlerSelectors in Castle Windsor can allow for dynamic selection of components at runtime. For more information, see this article from Ayende <a href="http://ayende.com/Blog/archive/2008/10/05/windsor-ihandlerselector.aspx">http://ayende.com/Blog/archive/2008/10/05/windsor-ihandlerselector.aspx</a></p>
<h3>Why are you using the Spark view engine rather than the standard ASP.NET MVC one? What benefits does it bring?</h3>
<p>The Spark view engine could be described as a DSL for a rendering view markup, whereas the out-the-box Webforms view engine feels more like reusing what’s already available to do the job. The Webforms syntax feels clunky when you require looping or conditional logic as the angle bracket syntax breaks up the flow of the HTML. There is also very little support for common view-specific scenarios.</p>
<p>Spark on the other hand embeds logic directly into the HTML markup, meaning the views still look and feel like HTML. As well as the purely aesthetic benefits, this makes it easier for non-.NET iDevs to understand and grok what’s going on in the view code. The view files are simpler, terser and also rely on a convention-based approach for defaults meaning they are quicker to work with. Team development has less friction as iDevs rely less on .Net devs for integrating markup into a solution. There are also a lot of really nice language features e.g. automatically creating and exposing Index, IsFirst and IsLast variables for use within a loop which makes formatting lists very easy. It supports automatic HTML encoding of strings and has cached-region support. The rendering logic is super fast as is simply writing to a StringBuilder. This also means that Spark can be used as a generic view renderer, outside the scope of a web-application with an HTTP context e.g. for rendering tokenized HTML views for an email.</p>
<p>The downsides are that you lose some tooling support – intellisense is limited but can be achieved through an installer available from the Spark website. ReSharper ignores .spark files so refactoring is more manual, however the benefits far outweigh these downsides.</p>
<p><a href="http://sparkviewengine.com/">http://sparkviewengine.com/</a></p>
<h3>How does the validation work? Looks like there is some client side validation (xVal) and some server side validation (DataAnnotations?). How does this all fit together?</h3>
<p>MVC 1.0 provided no out-the-box UI validation mechanism. The only validation support available is the System.ComponentModel.DataAnnotations namespace which provides some basic validation attributes that can be added to a class. However, there is no validation runner – e.g. to check whether a class is valid based on the attributes, and no way to represent this validation in the UI i.e. through JavaScript so validation is server-side only.</p>
<p>Steve Sanderson’s xVal framework was built to solve this problem, acting as a middleman between server side and client side validation. xVal is not a validation framework itself, but acts as a broker – translating server side validation rules from a number of supported frameworks (Data Annotations, NHibernate Validator…) into a canonical format and then outputting these rules in client side JavaScript for interpretation by one of the supported UI validation frameworks (jQuery.Validator, ASP.NET Ajax Validation).</p>
<p>xVal is initialized in the ValidationInitialiser – setting up the server side framework provider to use. An HTML helper method is used to add the client side validation rules, based on a particular class (see Q3 r.e. FormModels) and referencing the appropriate JavaScript files will wire up the UI validation.</p>
<p>There’s a few moving parts in this solution, but once it’s set up, adding client and server validation to forms is easy – by following the conventions.</p>
<p>N.B. In MVC 2.0, equivalent functionality to xVal has been rolled into the framework so this becomes largely redundant. xVal would still be useful in scenarios where an alternative validation framework is required e.g. NHibernate.Validator.</p>
<p><a href="http://xval.codeplex.com/">http://xval.codeplex.com/</a></p>
<h3>How does the error handing work? What is ELMAH and why are we using it?</h3>
<p>ELMAH stands for Error Logging Modules and Handlers and is a really easy way to set up logging for unhandled application errors. This is not a replacement for a logging framework e.g. Log4Net as only deals with unhandled exceptions but should be used alongside your standard logging and instrumentation for diagnostic purposes. It can be added to a solution without changing a single line of code – simply be referencing the assembly and adding the relevant web.config entries. However, more advanced config can be used and listeners can be added to log to email, file, database, twitter etc.</p>
<p>It’s a great tool to have in a solution from day one as during the development process, when bugs are often found, ELMAH can really help. It will log the “yellow screen of death” that was originally seen when the exception was thrown, along with the stack trace and which is invaluable when a system tester raises a bug – they can link to the ELMAH reference in order to diagnose what happened. ELMAH can also be used in a production environment to log exceptions whilst the live application is running. This can help Ops teams diagnose badly performing applications. Viewing the ELMAH logs is easy and can be done directly in the browser via the elmah.axd HTTP handler. This can be locked down using any standard authorization mechanism, restricting access to the error logs if necessary.</p>
<p><a href="http://code.google.com/p/elmah/">http://code.google.com/p/elmah/</a></p>
<h3>Looks like you are only creating mappers to map between single entities (i.e. a Person to a PersonViewModel) and not for mapping collections (i.e. List&lt;Person&gt; to List&lt;PersonViewModel&gt;). The lists seem to be mapped using extension methods (e.g. MapAllUsing). What would you do in the instance where a Trade is mapped to a List&lt;FinancialPosting&gt; etc?</h3>
<p>A mapper always returns one output, which could be of type List&lt;T&gt;. In this case, it depends on how the FinancialPostings are created from the Trade. If the Trade contains a list of information which is used to create the list of FinancialPostings then it could be that the mapping is actually from a child property of the Trade e.g.</p>
<p>var financialPostings = Trade.Transactions.MapAllUsing(mapper);</p>
<p>However, if the Trade object is needed for each FinancialPosting then I would simply have the mapper return a List&lt;T&gt;. This is completely acceptable.</p>
<p>Where one collection is mapped to another, then I would recommend using the MapAllUsing() extension method and create a mapper to map the single entities. This allows for a greater reuse, easier testability and a separation of concerns between the mapping logic and the iteration logic.</p>
<h3>There seem to be many overloaded IMapper interfaces (inputs 1-5). Why is this? How are these overloads used? What happens if I’m mapping 6 inputs?</h3>
<p>This is simply because the calling code has required this many inputs to map to one output. A controller could for example get data from a number of sources in order to display a complex view so the mapper interface has just been updated to suit this requirement. Adding more and more inputs to the mapper interface could highlight a code smell, but without context it’s hard to say whether this is a justified trade off. The benefits of using the IMapper interface are that the mappers are automatically registered into the IOC container and that the MapAllUsing extension method can be used to chain mappers together.</p>
<h3>How does auto-mapper work? How do I configure auto-mapper to deal with complex mappings?</h3>
<p>Automapper works great at mapping one object to another when property names match, or object hierarchies are to be flattened. This really suits entity -&gt; viewmodel and formmodel -&gt; entity type mapping in MVC controllers. It works via reflection, but mapping profiles are cached and lots of effort has been made to avoid performance problems.</p>
<p>Automapper relies on a convention based approach to mapping – i.e. when property names match it knows what to do, but these conventions can be overriden in mapping profiles to map non-standard names, ignore specific properties, or provide custom mapping logic for particular properties. In short, Automapper is very flexible and can be configured to map however you want, however its real benefit is when you stick to the conventions as mapping objects then becomes frictionless.</p>
<p>For more info see <a href="http://automapper.codeplex.com/">http://automapper.codeplex.com/</a></p>
<h3>Would you ever create a mapper which doesn’t use auto-mapper?</h3>
<p>Yes – if mapping one object to another results in a setting up a complex mapping profile with automapper, I would definitely consider whether using it is beneficial. In objects that are not using convention-based mapping it could often be easier to manually map properties.</p>
<h3>There seem to be a lot more classes than specs. Is this because the code is difficult to test or are the specs for these elsewhere?</h3>
<p>Whilst I am a big advocate of test first development, I’m also pragmatic when it comes to what to test. A lot of the code in the Framework project has come out of other projects and has been in use for a long time so it didn’t feel necessary to retro fit test code around it. Specs were written for nearly all new code that was created for the purposes of this solution. There are a number of supporting classes e.g. Registrars and Initialisers that are not tested, Domain and View and FormModels are dumb and provide no logic.</p>
<h3>Why are we using the term Tasks? What is a Task?</h3>
<p>The Tasks layer is a logical grouping of business logic that provides an application boundary in the solution. Anything above the tasks layer is deemed presentation logic and anything below is deemed reusable application logic. The Sharp Architecture framework originally called this layer of functionality the Application Services, however this led to confusion in teams over the use of the word Service. We found that as soon as we started talking about our Application Services layer as a Tasks Layer, then things seemed to start to make more sense.</p>
<h3>What is the granularity of each layer?</h3>
<h4>Web</h4>
<p>The web application project contains application initialization and pure presentation logic. View files, images, CSS etc. The only code at this layer is HTML helper style code for use in view markup and any necessary Initialisers.</p>
<h4>Web.Controllers</h4>
<p>Controllers are deemed presentation logic as are MVC specific and govern the “flow” of the application. I.e. they handle user inputs (the HTTP GET and POST requests made to the application) and return the correct response (HTML, Javascript, HTTP redirects, HTTP error codes etc). Controllers should hand off to the Tasks layer as soon as possible to “do stuff” and should contain as little logic as possible. This project is as high as the Domain entities go so Controllers contains the necessary Mappers to convert Entities to ViewModels and FormModels to Entities.</p>
<h4>Tasks</h4>
<p>The tasks layer contains the application business logic. It talks to repositories for retrieving and updating entities and to external services where necessary. It performs server side validation on entities yet is still persistence ignorant.</p>
<h4>Infrastructure</h4>
<p>The infrastructure project is where data access happens and real services are called. This could be via NHibernate, a web service or another specific implementation. For external services, mapping may be needed between entities and third party types, so there may be mappers present for this purpose.</p>
<h4>Domain</h4>
<p>Contains all domain entities, value types etc – the business model. Also contains the interfaces for the various other cross-project layers e.g. Tasks, Repositories and Infrastructure. The Domain project is used all the way from the Infrastructure layer up to the Controllers.</p>
<h4>Framework</h4>
<p>Supporting low level and utility code e.g. logging, caching, extension methods etc. Can be used throughout the solution.</p>
<h4>Specs</h4>
<p>BDD style tests for the entire application logic.</p>
<h3>What BDD/Test frameworks are being used? (MSpec?) Why? Is this going to be the standard?</h3>
<p>MSpec is being used as the BDD framework of choice. This has been down to personal preference of the teams that have worked with this framework, however, here are my personal views on why I would pick MSpec:</p>
<p>There seems to be two styles of BDD testing currently in use within the software development community:</p>
<p>The first are those frameworks that aim to produce unit tests in a BDD style syntax in C#. These could be described as an “internal DSL” for BDD testing. They tend to have unit test runner support from within Visual Studio, build tools for integrating into CI processes and produce some form of human readable output, either in HTML format, or within Visual Studio.</p>
<p>The second are those frameworks which are more aimed at QA or BA by providing a non-technical scenario based language for defining BDD style specifications. These could be described as an “external DSL” for BDD testing. These specs tend to be written in text files and suit high-level user story style specifications.</p>
<p>On a very crude level, the first set of frameworks suit how developers work and the second suit QA and business people. A project would benefit from both styles of testing – at a unit level within an automated CI process, and at a UI level via an automated UI testing tool e.g. Selenium running the scripts. Regarding the first scenario, I believe that MSpec is the most mature, featured framework, with the best integration into Visual Studio and the biggest community using it – i.e. it’s the best choice for developers.</p>
<p>This solution does not deal with the latter of these scenarios purely because we have not had that kind of input into the project. I would see more Cucumber-esque BDD style testing as an addition to the MSpec coverage, rather than a replacement.</p>
<h3>What is the ServiceLocatorHelper and how/when is it used? Tests only?</h3>
<p>Yes – the ServiceLocatorHelper exists to support testing by allowing an easy way to add components to the Service Locator that are required by executed code.</p>
<h3>Why is IWindsorContainer being passed around the application? Isn’t the point of having a ServiceLocator that we can easily switch out IoC implementations?</h3>
<p>No, the point isn’t really so we can switch out IOC implementations, but rather that we can share the container between anything else that uses the ServiceLocator. So, if a third party product is introduced into the solution and it uses the ServiceLocator to add and retrieve components, potentially we could also add to, remove from and access that list of components via the ServiceLocator too – i.e. the container is abstracted from the specific implementation. We’re not really exploiting this behavior and you’re right that we’re kind of hard coding the use of WindsorContainer in the solution. If/when we meet this requirement, this area will probably need to be revisited.</p>
<img src="http://feeds.feedburner.com/~r/JamesBroome/~4/RUFAWGEke98" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://jamesbroo.me/who-can-help-me-q-a/feed/</wfw:commentRss>
		<slash:comments>8</slash:comments>
		<feedburner:origLink>http://jamesbroo.me/who-can-help-me-q-a/</feedburner:origLink></item>
		<item>
		<title>Integrating Postmark into ASP.NET MVC</title>
		<link>http://feedproxy.google.com/~r/JamesBroome/~3/1cTP7OdGLRY/</link>
		<comments>http://jamesbroo.me/integrating-postmark-into-asp-net-mvc/#comments</comments>
		<pubDate>Thu, 08 Apr 2010 19:50:47 +0000</pubDate>
		<dc:creator>James</dc:creator>
				<category><![CDATA[Uncategorized]]></category>
		<category><![CDATA[.NET]]></category>
		<category><![CDATA[MVC]]></category>

		<guid isPermaLink="false">http://jamesbroo.me/?p=224</guid>
		<description><![CDATA[I was excited when I first heard about Postmark as it answered a problem that I’ve faced on many projects in the past &#8211; how do you send “triggered” emails from your web application? By triggered emails, I mean one time, one hit emails sent to a specific user in response to a specific action [...]]]></description>
			<content:encoded><![CDATA[<p>I was excited when I first heard about <a href="http://postmarkapp.com/" target="_blank">Postmark</a> as it answered a problem that I’ve faced on many projects in the past &#8211; how do you send “triggered” emails from your web application? By triggered emails, I mean one time, one hit emails sent to a specific user in response to a specific action e.g. user registration, order confirmation etc.</p>
<p>The answer in the .NET world has always been to “roll your own” email service using the System.Net.Mail namespace and the SMTP capabilities of IIS. Whilst the <a href="http://weblogs.asp.net/scottgu/archive/2005/12/10/432854.aspx" target="_blank">process of writing this code is straightforward</a>, the hard part is not developing the code, but all the stuff that the developers don’t actually think about. As <a href="http://wildbit.com/blog/2009/10/21/announcing-postmark-email-delivery-in-the-cloud/" target="_blank">Postmark describe</a>:</p>
<blockquote><p><em><strong>If you’ve ever built or launched a web application, you know that setting up an SMTP server is pretty easy. The basic steps can have you up in running in minutes. What you may not know, is that doing it correctly is complex. For instance:</strong></em></p>
<ul>
<li><em><strong>Setting up authentication like SPF and DomainKeys</strong></em></li>
<li><em><strong>The importance of Reverse DNS </strong></em></li>
<li><em><strong>Managing connection and message rules for each ISP </strong></em></li>
<li><em><strong>Applying for ISP whitelisting and feedback loops </strong></em></li>
<li><em><strong>Accreditation with ISIPP and ReturnPath </strong></em></li>
<li><em><strong>Tracking bounces and spam complaints </strong></em></li>
<li><em><strong>Understanding volume over time</strong></em></li>
</ul>
</blockquote>
<p>These problems have hit me in the past, which is why I’d always look to a third party service for sending emails from my application. There are many services that provide campaign style email sending (i.e. generic or targeted marketing emails sent to a list of users), however finding a company that provides a triggered service (via an API) has always proved impossible. On a recent project, we found a company that provided this service, only to find out that they were deprecating it 3 weeks prior to our application going live. Nice.</p>
<p>So, like I said, I was very excited to hear about Postmark and signed up for the private Beta trial straight away. The service has recently gone live, so now seemed like a good time to knock up a little demo application…</p>
<h2>The Demo App</h2>
<p>I mainly develop in .NET, especially when working for clients at <a href="http://uk.emc.com/services/index.htm" target="_blank">EMC Consulting</a>, so wanted to focus on this for the demo as it is likely that this will be the way I will use Postmark in anger on a “real” project. There’s already a <a href="http://github.com/lunarbits/postmark-dotnet" target="_blank">.NET API available on Github</a> so I set about hooking this up to an MVC application.</p>
<p>My application is just one screen with a text box for an email address. Clicking the submit button will send a test email to the email address entered via the Postmark service.</p>
<p><a href="http://jamesbroo.me/blog/wp-content/uploads/2010/04/image.png"><img style="display: inline; border-width: 0px;" title="image" src="http://jamesbroo.me/blog/wp-content/uploads/2010/04/image_thumb.png" border="0" alt="image" width="608" height="484" /></a></p>
<h3>Home Controller</h3>
<p>As I only have one screen, I only need one controller. My HomeController handles both the GET and POST requests to the root URL – the first simply returns the view and the second calls my messageSender to send the email and redirects back to the view.</p>
<p>A couple of things to note – my controller is talking to an IMessageSender, injected into the constructor, to keep the controller simple. There is no mention yet of anything to do with Postmark, or any implementation of how this message is going to be sent – to put it simply, the controller shouldn’t know or care about this implementation detail – it just handles the flow of the application.</p>
<p>The second thing is that the controller redirects back to the Index action after the form is submitted – i.e. it issues a HTTP 302 response to redirect back to the root URL. This follows a pretty standard pattern in web applications called <a href="http://en.wikipedia.org/wiki/Post/Redirect/Get" target="_blank">Post – Redirect – Get</a> which ensures that after a user submits a form, if they hit refresh in the browser, they’re not going to re-submit the form again. So, if the email is sent successfully, or even it something went wrong, refreshing the browser doesn’t initiate another POST request.</p>
<pre class="brush: csharp;">public class HomeController : Controller
{
    private readonly IMessageSender _messageSender;

    public HomeController(IMessageSender messageSender)
    {
        _messageSender = messageSender;
    }

    public ActionResult Index()
    {
        return View();
    }

    [AcceptVerbs(HttpVerbs.Post)]
    public ActionResult Index(string email)
    {
        var response = _messageSender.SendMessage(email);

        TempData["Message"] = response;

        return RedirectToAction("Index");
    }
}</pre>
<h3>Postmark Message Sender</h3>
<p>Whilst the HomeController is working against an IMessageSender, we’re going to need a real implementation in order to actually send messages. This is where our Postmark integration comes in. I’m using the <a href="http://github.com/lunarbits/postmark-dotnet" target="_blank">Postmark .Net API</a> in order to call the Postmark service, which requires two configuration values to be set – the API Key and the sender email address. These need to be valid values according to my Postmark account. For simplicity’s sake, I’m storing this in App Settings in my web.config:</p>
<pre class="brush: xml;">&lt;appSettings&gt;
  &lt;clear/&gt;
  &lt;!-- Set this to your email server's API token (Guid) --&gt;
  &lt;add key="ServerToken" value="XXXXXXX-XXXX-XXXX-XXXX-XXXXXXXXXXX"/&gt;

  &lt;!-- Set this to a valid sender signature (email address) --&gt;
  &lt;add key="From" value="user@email.com" /&gt;

&lt;/appSettings&gt;</pre>
<p>I don’t like hitting configuration sources directly as it makes classes hard to test, so I like to encapsulate configuration as some kind of service and inject that in to anything that needs it. Our PostmarkMessageSender therefore depends on an IConfigurationSource in order to access these values.</p>
<p>The IMessageSender has one method signature, SendMessage() which takes an email address input parameter and returns a string response – either a success message, or an error message according to what happened when trying to send the email.</p>
<p>Here’s my implementation:</p>
<pre class="brush: csharp;">public class PostmarkMessageSender : IMessageSender
{
    private readonly IConfigurationSource _configuration;

    public PostmarkMessageSender(IConfigurationSource configuration)
    {
        _configuration = configuration;
    }

    public string SendMessage(string email)
    {
        var client = new PostmarkClient(_configuration.ServerToken);

        try
        {
            var response = client.SendMessage(BuildMessage(email));

            if (response.Status != PostmarkStatus.Success)
            {
                return response.Message;
            }
        }
        catch (ValidationException ex)
        {
            return ex.Message;
        }

        return "Message sent successfully!";
    }

    private PostmarkMessage BuildMessage(string email)
    {
        return new PostmarkMessage
                   {
                       From =_configuration.FromAddress,
                       To = email,
                       Subject = "Postmark ASP.NET MVC Demo",
                       HtmlBody = "Hello!",
                       TextBody = "Hello!",
                   };
    }
}</pre>
<h3>Framework</h3>
<p>My IConfigurationSource implementation calls directly into the web.config application settings;</p>
<pre class="brush: csharp;">public class WebConfigurationSource : IConfigurationSource
{
    public string ServerToken
    {
        get { return WebConfigurationManager.AppSettings["ServerToken"];  }
    }

    public string FromAddress
    {
        get { return WebConfigurationManager.AppSettings["From"]; }
    }
}</pre>
<p>And the dependencies are wired up using a <a href="http://ninject.org/" target="_blank">Ninject</a> module:</p>
<pre class="brush: csharp;">public class WebModule : NinjectModule
{
    public override void Load()
    {
        Bind&lt;IMessageSender&gt;().To&lt;PostmarkMessageSender&gt;();
        Bind&lt;IConfigurationSource&gt;().To&lt;WebConfigurationSource&gt;();
    }
}</pre>
<p>Which is configured for the MVC application in the global.asax.cs by inheriting NinjectHttpApplication and overriding the CreateKernel() method:</p>
<pre class="brush: csharp;">public class MvcApplication : NinjectHttpApplication
{
    public static void RegisterRoutes(RouteCollection routes)
    {
        routes.IgnoreRoute("{resource}.axd/{*pathInfo}");

        routes.MapRoute(
            "Default", // Route name
            "{controller}/{action}/{id}", // URL with parameters
            new { controller = "Home", action = "Index", id = UrlParameter.Optional } // Parameter defaults
        );

    }

    protected override void OnApplicationStarted()
    {
        RegisterRoutes(RouteTable.Routes);
        RegisterAllControllersIn(Assembly.GetExecutingAssembly());
    }

    protected override IKernel CreateKernel()
    {
        return new StandardKernel(new WebModule());
    }
}</pre>
<p>And that’s it &#8211; this whole app took me about 30 minutes to build (and another 30 mins to make it look pretty <img src='http://jamesbroo.me/blog/wp-includes/images/smilies/icon_wink.gif' alt=';)' class='wp-smiley' /> ) and I now have a fully functioning email-sending application. This is a fairly simple and trivial example, but it shows just how easy this is to do. A real-world application might have requirements around batching up emails and sending them asynchronously or sending to multiple address. However, hopefully this shows that whatever the requirements, you now only have to focus on the code and let somebody else think about the actual task of sending the messages – and producing the stats:</p>
<p><a href="http://jamesbroo.me/blog/wp-content/uploads/2010/04/image1.png"><img style="display: inline; border-width: 0px;" title="image" src="http://jamesbroo.me/blog/wp-content/uploads/2010/04/image_thumb1.png" border="0" alt="image" width="608" height="484" /></a></p>
<h2>Source code</h2>
<p>Source code for this demo application is available on <a href="http://github.com/jamesbroome/PostmarkDemo" target="_blank">Github at the following location</a>. Enjoy…</p>
<img src="http://feeds.feedburner.com/~r/JamesBroome/~4/1cTP7OdGLRY" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://jamesbroo.me/integrating-postmark-into-asp-net-mvc/feed/</wfw:commentRss>
		<slash:comments>3</slash:comments>
		<feedburner:origLink>http://jamesbroo.me/integrating-postmark-into-asp-net-mvc/</feedburner:origLink></item>
		<item>
		<title>Integrating N2CMS into Who Can Help Me? Part 4</title>
		<link>http://feedproxy.google.com/~r/JamesBroome/~3/3zEw7VAoUrg/</link>
		<comments>http://jamesbroo.me/integrating-n2cms-into-who-can-help-me-part-4/#comments</comments>
		<pubDate>Sun, 28 Feb 2010 16:24:29 +0000</pubDate>
		<dc:creator>James</dc:creator>
				<category><![CDATA[Uncategorized]]></category>
		<category><![CDATA[MVC]]></category>
		<category><![CDATA[N2 CMS]]></category>
		<category><![CDATA[Who Can Help Me]]></category>

		<guid isPermaLink="false">http://jamesbroo.me/?p=206</guid>
		<description><![CDATA[This is part 4 in my series of posts about integrating the .Net open source content management system N2CMS into the Sharp Architecture demo application Who Can Help Me?.
In the first, second and third posts I

Added the N2 assemblies
Added the edit site to the web project
Created the initial content definitions
Created the database schema
Added root nodes [...]]]></description>
			<content:encoded><![CDATA[<p>This is part 4 in my series of posts about integrating the .Net open source content management system <a href="http://www.n2cms.com">N2CMS</a> into the <a href="http://sharparchitecture.net/">Sharp Architecture</a> demo application <a href="http://whocanhelpme.codeplex.com/">Who Can Help Me?</a>.</p>
<p>In <a href="http://jamesbroo.me/integrating-n2cms-into-who-can-help-me/">the first</a>, <a href="http://jamesbroo.me/integrating-n2cms-into-who-can-help-me-part-2/">second</a> and <a href="http://jamesbroo.me/integrating-n2cms-into-who-can-help-me-part-3/">third posts</a> I</p>
<ul>
<li>Added the N2 assemblies</li>
<li>Added the edit site to the web project</li>
<li>Created the initial content definitions</li>
<li>Created the database schema</li>
<li>Added root nodes to the CMS database</li>
<li>Updated the Web.config</li>
<li>Set up the N2 Content Routes and intialised the CMS engine</li>
<li>Added a base CMS controller</li>
<li>Updated the HomeController to be a CMS controller</li>
<li>Tackled authentication with Open ID and the N2 membership providers</li>
</ul>
<h2>Step 11 &#8211; Build up the HomePage content definition</h2>
<p>Our HomePage definition has nothing on it – which means that although we can create a HomePage in the N2, there’s no properties to set, so no CMS content is actually being displayed on the Home Page.</p>
<p>I’m going to keep this simple and just add a BodyText property, using the N2 FreeTextArea control so the user gets a full WYSIWYG editor. I add the following property definition to HomePage.cs:</p>
<pre class="brush: csharp; auto-links: false;">[PageDefinition("Home Page",
    Description = "A home page template.",
    SortOrder = 440,
    InstallerVisibility = InstallerHint.PreferredRootPage | InstallerHint.PreferredStartPage,
    IconUrl = "~/edit/img/ico/png/page_world.png")]
[WithEditableTitle("Title", 5, Focus = true, ContainerName = Tabs.Content)]
[RestrictParents(typeof(SiteRoot))]
public class HomePage : AbstractPage
{
    /// &lt;summary&gt;
    /// Gets or sets BodyText.
    /// &lt;/summary&gt;
    /// &lt;value&gt;
    /// The body text.
    /// &lt;/value&gt;
    [EditableFreeTextAreaAttribute("Body Text", 100, ContainerName = Tabs.Content,
        HelpText = "Set the body text for the page")]
    public string BodyText
    {
        get { return (string)GetDetail("BodyText"); }
        set { SetDetail("BodyText", value); }
    }
}</pre>
<p>This now means that when we browse to our edit site and edit the Home page, we see the following edit view:</p>
<p><a href="http://jamesbroo.me/blog/wp-content/uploads/2010/02/image3.png"><img style="display: inline; border-width: 0px;" title="image" src="http://jamesbroo.me/blog/wp-content/uploads/2010/02/image_thumb3.png" border="0" alt="image" width="644" height="471" /></a></p>
<p><a href="http://whocanhelpme.codeplex.com/SourceControl/changeset/view/56042" target="_blank">Changeset reference 56042</a></p>
<h2>Step 12 &#8211; Update the HomePageViewModelMapper</h2>
<p>Ultimately we want to display the CMS content on the HomePage view, but our Home page also displays a new feed that comes from the NewsTasks i.e. nothing to do with the CMS data. This is fine – it just means that we need to map both the CMS content and the News feed data to the view.</p>
<p>Lets start by updating our mapper interface:</p>
<pre class="brush: csharp; auto-links: false;">public interface IHomePageViewModelMapper : IMapper&lt;IList&lt;NewsItem&gt;, HomePage, HomePageViewModel&gt;
{
}</pre>
<p>We now map from a HomePage (from the CMS) and a list of NewsItems (from the NewsTasks) and return a HomePageViewModel. This is where the use of view models in MVC really becomes important – anything other than a really simple application will be displaying data from a variety of sources and so it’s not always possible to bind directly to your domain model. I find that it’s always a good idea to start with the use of view models from the offset as you will inevitably need them and it saves you refactoring time later on. As we already are inheriting from a base view model mapper, and utilising the power of Automapper, updating the HomePageViewModelMapper is easy. All we need to do is update the CreateMap method to set up the Automapper strategy for mapping from a HomePage to a HomePageViewModel. We’ll rely on the out the box behaviour of Automapper that properties with the same name are automatically mapped:</p>
<pre class="brush: csharp; auto-links: false;">public class HomePageViewModelMapper : BasePageViewModelMapper&lt;IList&lt;NewsItem&gt;, HomePage, HomePageViewModel&gt;,
                                       IHomePageViewModelMapper
{
    private readonly INewsItemViewModelMapper newsItemViewModelMapper;

    public HomePageViewModelMapper(
        IPageViewModelBuilder pageViewModelBuilder,
        INewsItemViewModelMapper newsItemViewModelMapper)
        : base(pageViewModelBuilder)
    {
        this.newsItemViewModelMapper = newsItemViewModelMapper;
    }

    protected override void CreateMap()
    {
        Mapper.CreateMap&lt;IList&lt;NewsItem&gt;, HomePageViewModel&gt;().ConvertUsing(list =&gt; this.DoMapping(list));
        Mapper.CreateMap&lt;HomePage, HomePageViewModel&gt;();
    }

    private HomePageViewModel DoMapping(IList&lt;NewsItem&gt; input)
    {
        return new HomePageViewModel
        {
            NewsItems = input.MapAllUsing(this.newsItemViewModelMapper)
        };
    }
}</pre>
<h2>Step 13 &#8211; Update the HomeController</h2>
<p>Now we’ve updated our mapper, our HomeController needs to change as it’s this which calls the mapper. I start by updating the specs for the HomeController, to make sure that both the HomePage and the list of news items are passed to the mapper:</p>
<pre class="brush: csharp; auto-links: false;">[Subject(typeof(HomeController))]
public class when_the_home_controller_is_asked_for_the_default_view : specification_for_home_controller
{
    static HomePageViewModel the_view_model;
    static IList&lt;NewsItem&gt; the_news_items;

    static ActionResult result;

    Establish context = () =&gt;
        {
            the_view_model = new HomePageViewModel();
            the_news_items = new List&lt;NewsItem&gt;();

            news_tasks.Stub(nt =&gt; nt.GetProjectBuzz()).Return(the_news_items);
            home_view_model_mapper.Stub(hvmm =&gt; hvmm.MapFrom(the_news_items, home_page)).Return(the_view_model);
        };

    Because of = () =&gt; result = subject.Index();

    It should_return_the_default_view = () =&gt;
        result.ShouldBeAView().And().ShouldUseDefaultView();

    It should_map_the_home_page_content_and_the_list_of_news_items_the_view_model =
        () =&gt; home_view_model_mapper.AssertWasCalled(hvmm =&gt; hvmm.MapFrom(the_news_items, home_page));

    It should_pass_the_view_model_to_the_view =
        () =&gt; result.Model&lt;HomePageViewModel&gt;().ShouldBeTheSameAs(the_view_model);
}</pre>
<p>And then we can update the HomeController itself, which should make the code compile again and make the tests pass. The HomePage content from the CMS is accessed via the CurrentItem property which is surfaced from the base N2Controller and kindly automatically populated for us by N2:</p>
<pre class="brush: csharp; auto-links: false;">[Cached(CacheName.AdHoc)]
private PageViewModel IndexInner()
{
    var buzz = this.newsTasks.GetProjectBuzz();

    return this.homePageViewModelMapper.MapFrom(buzz, CurrentItem);
}</pre>
<p><a href="http://whocanhelpme.codeplex.com/SourceControl/changeset/view/56163" target="_blank">Changeset reference 56163</a></p>
<h2>Step 14 &#8211; Update the HomePageViewModel</h2>
<p>All we need to do is add a new property that matches the BodyText property on our HomePage definition for Automapper to be able to map the properties:</p>
<pre class="brush: csharp; auto-links: false;">public class HomePageViewModel : PageViewModel
{
    public HomePageViewModel()
    {
        this.NewsItems = new List&lt;NewsItemViewModel&gt;();
    }

    public IList&lt;NewsItemViewModel&gt; NewsItems { get; set; }

    public string BodyText { get; set; }
}</pre>
<p><a href="http://whocanhelpme.codeplex.com/SourceControl/changeset/view/56164" target="_blank">Changeset reference 56164</a></p>
<h2>Step 15 &#8211; Update the view</h2>
<p>Now everything should be wired up, we need to display the CMS content on the home page view. I remove the hard coded text in the Spark view file and replace it with with the BodyText property of the view model. Note the Spark syntax start with !{} – the exclamation mark means that Spark will not HTML encode this value, which is what we need as the content from the CMS will be a HTML string:</p>
<pre class="brush: xml; auto-links: false;">&lt;viewdata model="WhoCanHelpMe.Web.Controllers.Home.ViewModels.HomePageViewModel"/&gt;

&lt;content name="title"&gt;
What's all this then?
&lt;/content&gt;

!{Model.BodyText}

&lt;h3&gt;The latest WCHM buzz...&lt;/h3&gt;
&lt;NewsHeadlines /&gt;</pre>
<p><a href="http://whocanhelpme.codeplex.com/SourceControl/changeset/view/56165" target="_blank">Changeset reference 56165</a></p>
<h2>Step 16 – Disable caching</h2>
<p>WCHM makes use of caching in an attempt to show how to set up different expiration times on related pieces of data. Unfortunately, as our CMS system allows users to update content, our views are going to need to be a bit more dynamic – for now I’m just going to disable the caching service so that any changes I make will be displayed. I’ll revisit this next time to try to come up with a better solution that works for the CMS:</p>
<p>The cache can be disabled in the container.components.config file:</p>
<pre class="brush: xml; auto-links: false;">&lt;configuration&gt;
  &lt;components&gt;
    &lt;component id="CachingService"
               service="WhoCanHelpMe.Framework.Caching.ICachingService, WhoCanHelpMe.Framework"
               type="WhoCanHelpMe.Infrastructure.Caching.HttpCachingService, WhoCanHelpMe.Infrastructure"
               lifestyle="singleton"&gt;
      &lt;parameters&gt;
        &lt;enabled&gt;false&lt;/enabled&gt;
        &lt;cacheDurations&gt;
          &lt;dictionary&gt;
            &lt;item key="VeryShort"&gt;60&lt;/item&gt;
            &lt;item key="Short"&gt;120&lt;/item&gt;
            &lt;item key="Medium"&gt;300&lt;/item&gt;
            &lt;item key="Long"&gt;10800&lt;/item&gt;
            &lt;item key="Permanent"&gt;86400&lt;/item&gt;
          &lt;/dictionary&gt;
        &lt;/cacheDurations&gt;
        &lt;caches&gt;
          &lt;dictionary&gt;
            &lt;item key="AdHoc"&gt;Medium&lt;/item&gt;
            &lt;item key="MvcTempData"&gt;Short&lt;/item&gt;
          &lt;/dictionary&gt;
        &lt;/caches&gt;
      &lt;/parameters&gt;
    &lt;/component&gt;
  &lt;/components&gt;
&lt;/configuration&gt;</pre>
<p><a href="http://whocanhelpme.codeplex.com/SourceControl/changeset/view/56166" target="_blank">Changeset reference 56166</a></p>
<h2>Step 17 – Update the N2 Item table schema (D’oh!)</h2>
<p>So my authentication workaround had a slight problem – the openId username that I’m using for my N2 username is considerably longer than the 50 character limit that N2 imposes on its Item table’s SavedBy column. I updated this to NVCHAR(255) to match the column in the WCHM profile table.</p>
<p><a href="http://whocanhelpme.codeplex.com/SourceControl/changeset/view/56167" target="_blank">Changeset reference 56167</a></p>
<h2>Try it all out!</h2>
<p>I can now browse to the N2 edit site and switch into edit mode of the Home Page:</p>
<p><a href="http://jamesbroo.me/blog/wp-content/uploads/2010/02/image4.png"><img style="display: inline; border-width: 0px;" title="image" src="http://jamesbroo.me/blog/wp-content/uploads/2010/02/image_thumb4.png" border="0" alt="image" width="617" height="484" /></a></p>
<p>If I add some content and click Save and Publish, we can now see the N2 content on the Who Can Help Me? home page! -</p>
<p><a href="http://jamesbroo.me/blog/wp-content/uploads/2010/02/image5.png"><img style="display: inline; border-width: 0px;" title="image" src="http://jamesbroo.me/blog/wp-content/uploads/2010/02/image_thumb5.png" border="0" alt="image" width="617" height="484" /></a></p>
<h2>Next…</h2>
<p>So we’ve now got a working content management system and we can set the body text for the HomePage and see it displayed in the view alongside our news feed content. Next time I’m going to try and deal with the caching issue and also do the same for the About page which will force me to tackle the navigation, which will also need to come from the CMS…</p>
<img src="http://feeds.feedburner.com/~r/JamesBroome/~4/3zEw7VAoUrg" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://jamesbroo.me/integrating-n2cms-into-who-can-help-me-part-4/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://jamesbroo.me/integrating-n2cms-into-who-can-help-me-part-4/</feedburner:origLink></item>
	</channel>
</rss>

