ASP.NET MVC: Script Registration Helper

While building out the MVC Storefront, I find that I'm creating quite a large "Helper" library for doing common things, like registering script tags and CSS sheets. I decided to tighten this up a bit and created a helper I kind of like.

While building out the MVC Storefront, I find that I’m creating quite a large “Helper” library for doing common things, like registering script tags and CSS sheets. I decided to tighten this up a bit and created a helper I kind of like.

The Need
I want to try and reduce repetition as much as possible throughout the application, and to that end I put as much logic as I can into “Helpers” so I can reduce the <%…%> as much as possible on the page. ANY logic whatsoever makes the ViewPage harder to read, and my general rule of thumb is that if I see an “If” anywhere, it’s ripe for a Helper. I know this rule doesn’t always apply… but it’s a good place to start.

The same logic applied to most UI elements – things like style sheets (if you have more than one), common images (like Product images), and script tags.

The Setup
I keep all my script tags in a directory called “scripts”. Right now there are only 3 files in there:

  • MicrosoftAjax.debug.js
  • MicrosoftAjax.js
  • MicrosoftAjaxMVC.js (this is a file I created)

Normally I would just make a simple function to return the script tags – something like:

        public static string RegisterJS(this System.Web.Mvc.HtmlHelper helper, string scriptLib) {            //get the directory where the scripts are            string scriptRoot = VirtualPathUtility.ToAbsolute("~/Scripts");            string scriptFormat="<script src=\"{0}/{1}\" type=\"text/javascript\"></script>\r\n";            return string.Format(scriptFormat,scriptRoot,scriptLib);        }

That’s helpful, but I can do better :) . I don’t like “magic strings” and even though it’s the name of a file – I’d rather use something else here. Also, if I have to use “Html.RegisterJS…” every line – I haven’t really saved much.

The Code
To start, I’m going to create an Enum that I know will grow (you can put this anywhere – I use a file called “Enums” and am putting it in the Helpers folder), and I’ll reference the names of my script libraries:

    /// <summary>    /// Enums which describe script libraries    /// </summary>    public enum ScriptLibrary {        All,        Default,        MicrosoftAjax,        MicrosoftAjaxMVC,    }

Next, I buff out the RegisterJS function a bit…

        /// <summary>        /// A helper for registering script tags on an MVC View page.        /// </summary>        public static string RegisterJS(this System.Web.Mvc.HtmlHelper helper, ScriptLibrary scriptLib) {            //get the directory where the scripts are            string scriptRoot = VirtualPathUtility.ToAbsolute("~/Scripts");            string scriptFormat="<script src=\"{0}/{1}\" type=\"text/javascript\"></script>\r\n";                        string scriptLibFile="";            string result = "";            System.Text.StringBuilder sb = new System.Text.StringBuilder();                        //all of the script tags            if (scriptLib == ScriptLibrary.All) {                string[] scripts = Enum.GetNames(typeof(ScriptLibrary));                                foreach (string script in scripts) {                   scriptLibFile = script + ".js";                   sb.AppendFormat(scriptFormat, scriptRoot,scriptLibFile);                }                result = sb.ToString();            //just the defaults please            } else if (scriptLib == ScriptLibrary.Default) {                sb.AppendFormat(scriptFormat, scriptRoot,"MicrosoftAjax.js");                sb.AppendFormat(scriptFormat, scriptRoot,"MicrosoftAjaxMVC.js");                result = sb.ToString();            } else {                //just the ones asked for                scriptLibFile=Enum.GetName(typeof(ScriptLibrary),scriptLib)+".js";                result = string.Format(scriptFormat, scriptRoot,scriptLibFile);            }            return result;        }

And there you are. Now I can reference my script libraries with one line, and I don’t have to have a bulk of <script> tags everywhere:

   <%=Html.RegisterJS(ScriptLibrary.Default) %>

I know the code above can be tightened some :) and I’d love to hear your ideas. I’m not sure how usable the “All” selection is – but I wanted to include so you could get the idea here… sort of a “thematic” way to register your scripts.

Technorati Tags: