Help with revealing module pattern

Hi all,

I’m looking at moving from writing all my code in one file in a
non-modular format to using the revealing module pattern. I’ve read
numerous articles around on the web, however there’s a few things I’d
appreciate if someone could help clear things on.

I tend to use jQuery for most things and therefore need to incorporate
that into this. I’ve added a basic add to the body class in two places
just to show I may need to write jQuery in both places.

Below is a very basic example of what I’m doing at the moment. They will
be split into two files at a later date and the module will be
included. My questions are below this block of code.

// File: module.js
var Module = (function () {

  var _privateMethod = function (message) {
    alert(message);
  };

  var publicMethod = function (text) {
    _privateMethod(text);
    $('body').addClass('firstClass');
  };
  
  return {
    publicMethod: publicMethod
  };

})();

//---------------

// File: main.js
(function($){

  Module.publicMethod('Hello!');
  $('body').addClass('secondClass');

})(jQuery);

Question 1: I’ve seen people use var Module = Module || {}; to namespace. Should I be using this instead of how I’ve written it above? I’d guess something like…

var Module = Module || {};

Module._privateMethod = function () { };

Module.publicMethod =  function (message) {};
  
return {
   publicMethod: Module.publicMethod
};

Question 2: Follows on from the previous question, I’ve seen the
following used as well, how is this different and when should it be
used? Presume this is for sub-modules, but an if anyone could show an example that would be great

var Module = (function () {
  // code
}(Module || {}));

Question 3: I’ve seen people use publicMethod: function (text) { } instead of var publicMethod = function (text) { }. Why is that and if it’s a shorthand way of adding, how would I use it? I’ve tried using this way but am getting errors.

If there’s anything outside of these 3 questions which will benefit how the block of code is written I’d appreciate any advice. The aim of this is to write my code in a more modular way and avoid spaghetti code.

Thanks in advance.

Hey, you’re off to a great start and asking all of the right questions! The example in question 2 is basically a different way to do namespacing as defined in example one. The difference is that you’re execution an anonymous function in example 2, and calling it on Module (if defined), or an empty object if module doesn’t already exist. As for Question 3, you’re probably getting errors because you’re using a return statement to present the final object, and assigning a variable in a return statement doesn’t give return anything to ,well, return!

Thanks tevko, very helpful reply. Which of these ways of structuring your code do you use out of interest?

With regard to example two using var Module = Module || {}; which you say calls on Module if defined or creates an empty object if it doesn’t already exist, I presume my first example could run into issues if Module has been defined elsewhere (e.g. 3rd party libraries that I could be using)? If so, can var Module = Module || {}; be included into my first example to stop this issue from happening and if so how would it be done?

No problem! I use the module patern w/ the var Module = Module || {}; syntax. Yes, you can run into collision issues without unique namespacing in your code. Take a look at how I structure the library in this codepen example - http://codepen.io/tevko/pen/ogKxXq

1 Like

Depends. Module || {} solves a specific problem, such as when you have several JS files that put different sub-modules into the same namespace. For example:

// module1.js
var moduleNamespace = (function (moduleNamespace) {
    moduleNamespace.AwesomeModule1 = { /* ... */ };

    return moduleNamespace;
}(moduleNamespace || {}));
// module2.js
var moduleNamespace = (function (moduleNamespace) {
    moduleNamespace.SuperModule2 = { /* ... */ };

    return moduleNamespace;
}(moduleNamespace || {}));

If you were to load just module1 or just module2, there you won’t have the problem this is meant to solve. But if you might need to load module1 and module2, then you want to make sure any subsequent modules don’t clobber the namespace of any previous modules. So if you load just module2, then moduleNamespace will be undefined, and it will make a new namespace object. But if you load module1 then module2, then module2 will use the already existing namespace object and add to it.

Is it worth looking at something like requireJS, which helps you to handle dependencies between your modules.

We have a few articles here that can help with learning more about requireJS too, such as:

Tevko - Thanks. Nice to see your example, looks like your using object literal notation.

Jeff_Mott - This is really helpful and good to see an example. Clears up my confusion around the use.

Paul_Wilkins - My next step is to look into using something to help handle module dependencides. I’ve looked at RequireJS and Browserify which both look interesting depending on if I need synchronous or asynchronous. Interestingly though ECMAScript 6 comes with an import statement which you can use a transpiler like Babel and then SystemJS to make ECMAScript 6 available in browser that only support up to ECMAScript 5. From what I gather, this support both synchronous and asynchronous use. Having said that, I think at this point in time I’ll stick to similicity and probably lean towards Browserify.

Edit: literally just spotted this article on the site which I’m going to look at - http://www.sitepoint.com/setting-up-es6-project-using-babel-browserify/

One other thing which I’ve come across is the use of an init function. Is it good practice to use this? I’m a bit unclear though of it’s use, is it’s purpose to make use of the other functions within the module and therefore be the ‘master’ function? So for example if you had a responsive carousel which would show a different number of slides depending on the browser width, would the init function call the appropriate function depending on the browser width and that function would display the number of slides based on the browser width? Hope that makes sense!

var Module = function(){
   var labels = {
      'speed': 600,
      'myElement': $('.carousel'),
      'slides': 6
   };
   var init = function(){
      // code
   };
   var firstFunc = function(){
      // code
   };
   var secondFunc = function(){
   }
   return{
     init:init,
     show:show,
     current:current
   }
}();
Module.init();

That sounds typical for a function named init. But then if that’s the case, it should probably be a constructor function with prototype methods.

This isn’t a simple yes or no. This is a very implementation-specific question.

This topic was automatically closed 91 days after the last reply. New replies are no longer allowed.