Structuring JavaScript Code In Asp.Net MVC Application

In this post I’m going to show you how I structure my JavaScript code in most of my Asp.Net MVC apps, I’m writing this because this approach helped me a lot, and maybe because someone out there has a better approach than mine and let me know.

The Problem

As a web developer who uses Asp.Net MVC, we distribute our code around Model, View and Controllers, and that gives us the kind of structure we need, if we want to change something related to customers for example, we have a controller for that and that controller has actions, and when we want to change something we know exactly where to go, but JavaScript doesn’t enforce any kind to pattern or structure, I know there are a lot of JavaScript MVC and MVVM frameworks out there, but what if for some reasons we didn’t want to use any of those frameworks? Even if we did use them, we still might need the kind of structure I’m going to describe, for example here how you would use AMD module pattern with Knockout, In this kind of situations if our JavaScript app grows to let’s say more than 2000 line, that’s when navigating and changing that code can become an absolute hell, never mind that we don’t have any kind of encapsulation or clear ideas about dependency between our scripts and all the drawbacks that comes with writing spaghetti JavaScript code, so what can we do?

JavaScript Module Pattern to The Rescue

Module pattern is not the only pattern we can use to achieve cleaner and structured JavaScript code, but that’s what I’m going to use in this case, there is no shortage of good articles about JavaScript module pattern out there, so I won’t bother to explain something that other people did better than me, for understanding this pattern I recommend module pattern section from Addy Osmani’s book, also here’s another one(JavaScript Module Systems Showdown) that examine the progression of JavaScript module patterns over the years which can put things into perspective for you, the module I’m currently using is AMD modules, I also use simple revealing modules when there are no module loader available, module loader of my choice is systemjs, it’s an interesting loader in that it loads any kind of module, so I’m assuming that you’ve taken a look at those articles, let’s see how I structure my code in Asp.Net MVC apps.

Structuring JavaScript code in Asp.Net MVC apps

Let’s say we have a busy page; our page consists of:

  • Search form section with a lot of interaction between its input elements and a lot of checks and validations
  • A grid that will gets populated by what’s returned by our search with all kind of buttons that will do something with the data or show modals etc.

And I know that my example is not that complicated, but I guess you can imagine something more intimidating.

Here’s what we have, an Area called Admin and in that area we have a Controller called Customer:

 
public class CustomerController : Controller
    {
        public ActionResult SearchCustomer(SuperComplicatedQuery query)
        { 
  
        }
    }

And an Action called SeachCustomer, and a view by the same name, here’s how I compartmentalize my JavaScript code into modules, one directory for every area, controller and view:

Our first module is  CustomerSearchModule, this module represents my form, it may be a complicated form which has some controls that are dependent on each other, and it also should handle the call to our action and use the returned result and handling validation and much more, it also has a dependency on UtilityModule:

define("CustomerSearchModule", ["UtilityModule"], function (utilityModule) {
 
    function privateFunction() {
        utilityModule.publicFunction();
    }
 
    function publicFunction() {
        privateFunction();
    }
 
    return {
        publicFunction: publicFunction
    };
});

And I might also have a Utility module that gets used between other modules that are related to this page:

define("UtilityModule", function () {
 
    var privateVar = "Hello from UtilityModule";
 
    function privateFunction() {
        console.log(privateVar);
    }
 
    function publicFunction() {
        privateFunction();
    }
 
    return {
        publicFunction: publicFunction
    };
 
});

Also we have a module for our grid which will show the search results, suppose this grid can sort, update, delete and handle a lot of other UI and data manipulation interactions which will need a lot of JavaScript to be written:

define("CustomerGridModule", function () {
 
    var privateVar = "Hello form CustomerGridModule";
 
    function privateFunction() {
        console.log(privateVar);
    }
 
    function publicFunction() {
        privateFunction();
    }
 
    return {
        publicFunction: publicFunction
    };

});

And finally we’ll have a Main module that brings together all other modules and call their stuff!? or maybe pass some setting or arguments to other modules:


define("Main", ["CustomerSearchModule", "CustomerGridModule"], function (customerSearchModule, customerGridModule) {
    customerSearchModule.publicFunction();
    customerGridModule.publicFunction();
});

Now all we have to do is to import the main module and our module loader will load the Main module dependency and the dependencies of those modules if any, we simply include the system.js script and configure it with baseURL which is going to set the root path of our Main module and also defaultJSExtensions which tells the module loader to find the files even if we omit the .js file extension:



    

This was my approach of dealing with lack of structure in my JavaScript codes, one argument I hear a lot is that this might be an overkill for small JavaScript apps, but I think it’s better to put these structure in place from the outset, because having structure in place from the beginning doesn’t going to hurt you, but lack of it can, even if you could refactor it later, it is going to be more difficult in my experience, or maybe you think there are some better alternatives?

Share...
 

Hamid Mosalla

Hi, I'm Hamid Mosalla, I'm a software developer, indie cinema fan and a classical music aficionado. Here I write about my experiences mostly related to web development and .Net.