Monday, January 3, 2011

MVC: Making my life a bit easier using UrlHelper and HtmlHelperExtensions

In this post I’m going to outline some of the Extension methods that I use to make my life a bit easier when authoring views pages in MVC.

Through the process of developing code I do my best to avoid “Magik Str!ngs”.. sorry I mean “Magic Strings”. They are prone to misspellings and can add a headache especially if you have variants of the some Html snippet throughout your views that can be avoided with some forethought.

For View pages in MVC I do my best to avoid

[sourcecode language="html"]
<link href="/css/sidebar.css" id="Link1" rel="Stylesheet" type="text/css" />
<link href="/css/styles.css" id="cssStyleSheet" rel="Stylesheet" type="text/css" />
<link href="/css/custom-theme/jquery-ui-1.7.2.custom.css" type="text/css" rel="stylesheet" />
<link href="/css/standard.css" rel="stylesheet" type="text/css" />
<link href="/css/custom-theme/jquery-ui-1.7.2.custom.css" type="text/css" rel="Stylesheet" />

@Html.ActionLink("About", "About", "Home")
[/sourcecode]

To help me avoid passing the controller, action or route name as string, I create extension methods for UrlHelper and HtmlHelper to encapsulate the required Html Output:

[sourcecode language="csharp"]
public static class UrlHelperExtension
{
public static string About(this UrlHelper urlHelper)
{
return urlHelper.Action("About", "Home");
}
}
[/sourcecode]

Combining this with a HtmlExtension:

[sourcecode language="csharp"]
public static class HtmlHelperExtension
{
public static IHtmlString AnchorLink(this HtmlHelper htmlHelper, string url, string anchorDisplayName)
{
return new HtmlString("<a href=\"{0}\">{1}</a>".FormatWith(url, anchorDisplayName));
}
}
[/sourcecode]

I use an extension method called “AnchorLink” to which I pass two string variables, one for the required Url and another for the display text for the anchor link. Note that I also use IHtmlString. If I returned a string object from this method I would always have to remember to use Html.Raw or HtmlString in my views, which certainly opens up the possibility of adding some rendering issues to some of the views.

[sourcecode language="html"]
@Html.AnchorLink(Url.About(), "About")
[/sourcecode]

which will output the following HtmlSnippet

[sourcecode language="html"]
<a href="/Home/About">About</a>
[/sourcecode]

I use a similar pattern for Css and Javascript registration in the Views using the following signatures:

[sourcecode language="csharp"]
public static IHtmlString StyleSheet(this UrlHelper urlHelper, string css)

public static IHtmlString Javascript(this UrlHelper urlHelper, string js)
[/sourcecode]

then in my view for the registration of css I just use

[sourcecode language="csharp"]
@Url.StyleSheet("style.css")
[/sourcecode]

I will also register the Namespace of my Helpers in the config file. If you are using the Razor ViewEngine note that the namespace needs to be be registered as such

[sourcecode language="xml"]
<system.web.webPages.razor>
<host factoryType="System.Web.Mvc.MvcWebRazorHostFactory, System.Web.Mvc, Version=3.0.0.0, Culture=neutral, PublicKeyToken=31BF3856AD364E35" />
<pages pageBaseType="System.Web.Mvc.WebViewPage">
<namespaces>
<add namespace="System.Web.Mvc" />
<add namespace="System.Web.Mvc.Ajax" />
<add namespace="System.Web.Mvc.Html" />
<add namespace="System.Web.Routing" />
<add namespace="CUSTOM_NAMESPACE_HERE" />
</namespaces>
</pages>
</system.web.webPages.razor>
[/sourcecode]

Hope this post helps someone else’s development sanity.

No comments:

Post a Comment