Building Modular Web Applications with Backbone.js and RequireJS — Sample App


In recent months, I have been sharing different versions of the Employee Directory sample application built with different technology stacks, different frameworks, and different back-end (REST services) implementations.

A number of you have asked for a modular version of the application built using RequireJS. So here it is.


If you are already familiar with RequireJS and just want to dive into the Backbone.js/RequireJS sample, you can safely skip this section.

A complete discussion of the benefits of Asynchronous Module Definition (AMD) and RequireJS is beyond the scope of this article, but a quick look at index.html in a recent version of the employee directory app highlights one of the problems when you don’t use a script loader like RequireJS:

<script src="lib/jquery-1.9.1.min.js"></script>
<script src="lib/underscore-min.js"></script>
<script src="lib/backbone-min.js"></script>
<script src="bootstrap/js/bootstrap.js"></script>
<script src="js/app.js"></script>
<script src="js/views/shell.js"></script>
<script src="js/views/home.js"></script>
<script src="js/views/contact.js"></script>
<script src="js/views/employeelist.js"></script>
<script src="js/views/employeedetails.js"></script>
<script src="js/models/model-in-memory.js"></script>

While small, the Employee Directory sample application imports eleven scripts. Imagine what a large application would look like. Of course, you can (and should) use a build process to concatenate and minify these scripts before deploying your application. But that doesn’t solve all the problems: In what order should these scripts be loaded to make sure all dependencies can be resolved? If this application is built by a team of developers, what’s the process for managing the list of dependencies between scripts/modules and make sure they can still be resolved as new modules are added by members of the team? How do you write code that actually minimizes hard dependencies between modules?

RequireJS is a script and module loader that addresses these issues:

  • When you run the application during development, it will load modules from separate files as needed and automatically resolve dependencies. Before deploying the application, you can run the RequireJS optimizer to combine scripts and minify them using UglifyJS (or the Closure Compiler).
  • It provides an implementation of the module pattern.
  • It manages dependencies between modules, ensuring a module is loaded before it is used by other modules.
  • It allows you to centrally manage dependency mappings (using a map config) so you can easily swap the version of a module that is injected in other modules. For example, you could choose to inject a mock dataprovider for testing, and later replace it with the actual JSON dataprovider for deployment. See the “Map Config” section below for an example.

There are other ways to achieve these goals. A discussion of the pros and cons of AMD compared to other options is beyond the scope of this article. The goal of this post is simply to share a practical example of a modular application built with Backbone.js and RequireJS.

The Sample Application

Click here to run the Backbone.js/RequireJS version of the application.

Below are a few simplified examples of the modularized Backbone.js components used in the application. Check out the source code of the application on GitHub for the complete implementation.

Modularized Model

define(function (require) {

    "use strict";

    var $           = require('jquery'),
        Backbone    = require('backbone'),

        Employee = Backbone.Model.extend({

            urlRoot: "http://localhost:3000/employees",

            initialize: function () {
                this.reports = new EmployeeCollection();
                this.reports.url = this.urlRoot + "/" + + "/reports";


        EmployeeCollection = Backbone.Collection.extend({

            model: Employee,

            url: "http://localhost:3000/employees"


    return {
        Employee: Employee,
        EmployeeCollection: EmployeeCollection

This application uses the syntactic sugar described here. This version of the define() function is less error-prone, and easier to read and to manage.

Modularized View

define(function (require) {

    "use strict";

    var $           = require('jquery'),
        _           = require('underscore'),
        Backbone    = require('backbone'),
        tpl         = require('text!tpl/Employee.html'),

        template = _.template(tpl);

    return Backbone.View.extend({

        render: function () {
            return this;



Modularized Router

define(function (require) {

    "use strict";

    var $           = require('jquery'),
        Backbone    = require('backbone'),
        $content = $("#content");

    return Backbone.Router.extend({

        routes: {
            "":                 "home",
            "employees/:id":    "employee"

        home: function () {
            require(["app/views/Home"], function (HomeView) {
                var view = new HomeView({el: $content});

        employee: function (id) {
            require(["app/views/Employee", "app/models"], function (EmployeeView, models) {
                var employee = new models.Employee({id: id});
                    success: function (data) {
                        var view = new EmployeeView({model: data, el: $content});



Loading Templates with the Text Plugin

It is a lot easier to author your HTML templates in separate files. The RequireJS text plugin makes it easy to load these templates as dependencies.

var tpl = require('text!tpl/Employee.html');

Map Config

RequireJS allows you to centrally manage dependency mappings (using a map config) so you can easily replace the version of a module that is injected in other modules. In the map configuration below, I mapped the ‘app/models/employee’ dependency to the ‘app/models/memory/employee’ module which is a simple in-memory data provider. You can easily replace the in-memory data with actual JSON services throughout the application by replacing ‘app/models/memory/employee’ with ‘app/models/json/employee’ in the mapping below defined in app.js.


    baseUrl: 'js/lib',

    paths: {
        app: '../app',
        tpl: '../tpl'

    map: {
        '*': {
            'app/models/employee': 'app/models/memory/employee'

    shim: {
        'backbone': {
            deps: ['underscore', 'jquery'],
            exports: 'Backbone'
        'underscore': {
            exports: '_'

Source Code

The source code for this application is available in this GitHub repository.

Because the modules of this application are loaded using XMLHTTPRequest, you will get a cross domain error (Access-Control-Allow-Origin) if you load index.html from the file system (with the file:// protocol). Make sure you load the application from a web server. For example: http://localhost/directory-backbone-bootstrap-require.

If you want to go beyond the in-memory datastore, you can download the REST services in the following repositories:

directory-rest-nodejs (Node.js/MongoDB implementation)
directory-rest-php (PHP implementation)
directory-rest-java (Java implementation coming soon)

25 Responses to Building Modular Web Applications with Backbone.js and RequireJS — Sample App

  1. Roland June 28, 2013 at 7:10 am #

    Great! Thank you so much for that gem tutorial!

  2. Aaron July 7, 2013 at 3:33 pm #

    Thanks for the post – i’ve had trouble with slowness at startup when trying to use require with phonegap but this example is quite snappy.

    One question – the navigation between the employee list and detail screens is done with regular anchor tags. After integrating into phonegap, I’m noticing that there is a short lag after tapping one of these elements and the page transitioning – presumably due to “click” vs “touch” on the phone. What’s the best way to make that more responsive?

  3. Noah July 8, 2013 at 9:45 am #

    Thanks for this tutorial Christophe. Just a query. How would I call RESTful APIs in this modular structure? Would I use .ajax ?

    • Christophe Coenraets July 8, 2013 at 10:34 pm #

      Since this is a Backbone.js application, calls to the RESTful API will be handled automatically by the models. In general, the fact that an application is modular doesn’t change the way you call your RESTful services.

      • Viswanathan July 25, 2013 at 10:16 am #

        please update restful web service using java and also db insert query.

  4. Helga B July 25, 2013 at 10:09 am #

    Thank you for this informative sample.

    • Viswanathan July 25, 2013 at 10:20 am #

      I want run this app using android+phonegap with localhost java base restful service can you please update the project with all this. really your are doing great job.

      Thanks a Lot :-)

  5. frye boots sale August 17, 2013 at 3:32 am #

    Thank you for this informative sample

  6. Web application development services August 20, 2013 at 6:51 am #

    “RequireJS allows you to centrally manage dependency mappings (using a map config) so you can easily replace the version of a module that is injected in other modules.” This is a great possibility but I have a question. I’m working on web application development servicesand would like to know, the map fits under all of these projects?

  7. Muhaimin August 26, 2013 at 4:42 am #


    is there anyway you could make an example combining the google map. I have a difficulty to load it with backbone

  8. Amreen August 27, 2013 at 5:27 am #

    Thanks for your helpful information.

  9. Muhaimin August 27, 2013 at 5:42 am #

    Hi chris

    i try to follow your example by combine the google map. I dont really understand / familiar with your programming style. Hope you can enlighten my by form it on my github

    thanks chris

  10. Jason September 3, 2013 at 12:39 am #

    Hi Chris,

    Thanks for the wonderful tutorial. I’m facing a problem here running the programme that I hope you can help me with. I’m using your Node.js/MongoDB implementation to run the app from localhost:3000, but I ended up with an empty homepage i.e. the is not rendered. If I request for localhost:3000/employees/:id for example, I get the JSON object of that employee, so I believe that the server is able to retrieve the data from the database.

    I just can’t seem to get why I have an empty … It seems that there must be something wrong with the Backbone views rendering…

    Would appreciate any help!

    • Jason September 3, 2013 at 3:10 am #

      Sorry, I forgot to use the tag. I wanted to say I get an empty “body”

      • Longchi March 4, 2014 at 7:03 am #

        Hi Jason,

        Did you ever get a response to this answer? I am having the same problem.


  11. metal buildings houston September 13, 2013 at 9:33 pm #

    Having read this I believed it was very enlightening.
    I appreciate you taking the time and energy to put this short article together.
    I once again find myself spending a significant amount of time both reading and leaving comments.
    But so what, it was still worth it!

  12. Razvan September 26, 2013 at 7:05 am #

    Hi! I noticed that if I add a button in the employee template:
    And in the view I add:
    events : {
    “click #save” : “saveInfo”

    saveInfo: function() {

    If I walk a bit through the app, everytime I enter employee page, and press the button, the number of prints increases:
    The first time I enter the page I click save -> enter
    After this, I go to home page, I go back to employee, hit the button save -> enter\n enter
    and so on

  13. Todd October 29, 2013 at 2:02 am #

    The directory-rest-php library doesn’t seem to work with this example. If i remove the reports section from the employee.html tpl file then it works … seems the php service isn’t returning reports correctly (what is this reportscount as opposed to just reports being returned by the memory service?).

    Removing the code from the tpl below makes the rest of the app function… how do i get the reports in there?

    0) { %>
    <a href="#employees//reports”>View Direct Reports

  14. Max November 19, 2013 at 3:37 pm #

    Nice article!!

    But, first of all i work on linux maschines so i had to rename all files spelled bad, because my webserver can not find them and require.js can not resolve the dependencys.

  15. Jonathan Gravois January 31, 2014 at 12:26 pm #

    Any thoughts on implementing this in SharePoint 2013 Foundation?

    We are in need of an Employee Directory for our Intranet and I have yet to see one as good-looking or complete as yours so I want to try to build this on the SharePoint platform. Since SP2013 is all about using JavaScript rather than XSLT, I think it is possible.

    I am just wondering if you would suggest a specific framework (you’ve done this in Angular and BackBone, at least, maybe more) or if you have any other thoughts that may help me.

  16. Erik Ringsmuth February 19, 2014 at 3:36 pm #

    I have a new solution for routing AMD modules.

    RequireJS Router

    This takes the approach of lazy loading AMD modules as you navigate to each page. With the Backbone router you need to require all of your views as dependencies up front. This loads all of your apps Javascript on the first page load. The RequireJS Router lazy loads modules as you navigate to each route.

    Example main.js used to run your app

    define([], function() {
    'use strict';

    // Configure require.js paths and shims
    paths: {
    'text': 'bower_components/requirejs-text/text',
    'router': 'bower_components/requirejs-router/router'

    // Load the router and your layout
    require(['router', 'js/layout/layoutView'], function(router, LayoutView) {
    var layoutView = new LayoutView();
    // The layout's render method should draw the header, footer, and an empty main-content section
    // then load the content section.
    // render: function() {
    // this.$el.html(this.template({model: this.model}));
    // router.loadCurrentRoute();
    // }

    // Configure the router
    home: {path: '/', moduleId: 'home/homeView'},
    order: {path: '/order', moduleId: 'order/orderView'},
    notFound: {path: '*', moduleId: 'notFound/notFoundView'}
    .on('statechange', function() {
    // Render the layout before loading the current route's module;
    .on('routeload', function(module, routeArguments) {
    // Attach the content view to the layoutView's main-content section
    layoutView.$('#main-content').replaceWith(new module(routeArguments).render().el);
    // We're manually calling loadCurrentRoute() from layoutView.render()
    loadCurrentRouteOnStateChange: false

  17. erwin October 4, 2013 at 5:51 am #

    I reply to myself !!!
    I added a cors.js script to the server
    module.exports = function(req, res, next) {
    res.header(“Access-Control-Allow-Origin”, “*”);
    res.header(“Access-Control-Allow-Headers”, “X-Requested-With”);

    and I added the following lines into server.js below var app = express();

    var app = express();

    cors = require(‘./cors’);

    and it’s running fine now…


  1. Building Modular Mobile / PhoneGap Apps with Backbone.js, RequireJS and Topcoat | Christophe Coenraets - June 27, 2013

    [...] my previous post, I discussed the process of building modular applications with Backbone.js and RequireJS, and I [...]

  2. Sample Mobile Application with AngularJS | Christophe Coenraets - November 5, 2013

    [...] Employee Directory with Backbone.js, RequireJS, and Twitter Bootstrap [...]

Leave a Reply