Search code examples
javascriptrequirejsmustacheamd

Why is `Mustache` undefined? (Using RequireJS)


I can see that the mustache.js file has been loaded, (code 200 in Firebug Net tab) so why do I get an error saying "ReferenceError: Mustache is not defined"?

I've looked at several related SO posts on this subject, but none seem to shed light on the issue. Any help is appreciated.

Relevant HTML

<div class="contact"></div>

<script data-main="js/modules/app.js" src="js/lib/require.min.js"></script>

app.js

var KBCOM = KBCOM || {};
(function (kbcom) {
  kbcom.app = {
    data: {
      kboucher: "{ \"firstName\": \"Kevin\", \"lastName\": \"Boucher\", \"dob\": \"1970-05-01T05:00:00.000Z\", \"emailAddress\": \"[email protected]\", \"telephone\": \"512-555-1212\" }"
    },
    init: function () {
      kbcom.templates.loadTemplate(
        kbcom.templates.vcard,
        JSON.parse(this.data.kboucher),
        document.querySelector('.contact'));
    }
  };
}(KBCOM));
require.config({
  baseUrl: '/js/modules',
  paths: {
    Mustache: '/js/lib/mustache',
    domReady: '/js/lib/domReady'
  }
});
require(['domReady', 'templates', 'Mustache'], function (domReady) {
  domReady(function () {
    KBCOM.app.init();
  });
});

templates.js

var KBCOM = KBCOM || {};
(function (kbcom) {
  kbcom.templates = {
    vcard: '<ul>\
              <li class="fn">{{fisrtName}} {{lastName}}</li>\
              <li class="email">{{emailAddress}}</li>\
              <li class="tel">{{telephone}}</li>\
              <li class="bday">{{dob}}</li>\
            </ul>',
    loadTemplate: function (template, data, element) {
      element.innerHTML = Mustache.render(template, data);
    }
  };
}(KBCOM));

Solution

  • templates.js "requires" Mustache, therefore you need to define that dependency in templates.js. It also needs to be defined as a module, so you need to use define to properly create a module.

    app.js

    require(['domReady', 'templates'], function (domReady, templates) {
    
      //append templates to namespace
      KBCOM.templates = templates;
    
      domReady(function () {
        KBCOM.app.init();
      });
    });
    

    templates.js

    define([    
      //dependencies
      'Mustache'
    ], function( Mustache ){ 
    
      //module code
      return {
        vcard: '...',
        loadTemplate: function ( template, data, element ) {
          element.innerHTML = Mustache.render( template, data );
        }
      };
    
    });