Take the 2-minute tour ×
Code Review Stack Exchange is a question and answer site for peer programmer code reviews. It's 100% free, no registration required.

I have the following example app: http://dev.driz.co.uk/jsfunction/

Which runs two types of script files with the same outcome.

Script1:

var script1 = {


    showMessage: function( message ) { 

        var el = document.getElementById('example1');

        el.innerHTML = message;

    }
}

and script 2:

window.script2 = function() {

    function showMessage( message ) {

        var el = document.getElementById('example2');

        el.innerHTML = message;

    }

    return {

        showMessage: showMessage

    }

}();

They are both namespaced so I can them like:

window.onload = function() {

    script1.showMessage('Hello world!');

    script2.showMessage('How are you?');

};

But what's the better way forward? Script1 is the type I would normally write but it requires you to sometimes call a init function first if you have some events that need running on document load.

For example:

var script = {

    init: function() {

        // some events such as onlick etc..

    }

};

script.init();

Script2 however is a self executing function and therefore would get around this but being a function itself would it allow the same flexibility?

Any thoughts? Suggestions or examples of how people namespace there script files to make them neater and more efficient?

share|improve this question

2 Answers 2

Try module-pattern, or somewhat like the module pattern, using an IIFE

In your case:

(function(ns){

  ns.showMessage = function(message){
    var el = document.getElementById('example1');
    el.innerHTML = message;
  }

}(this.script1 = this.script1 || {}));

window.onload = function() {
  script1.showMessage('Hello world!');
};

Here's the explanation

//basically, an IIFE is a function that executes itself
(function(ns){

  //in here, ns is a reference to our this.namespace

  //also, this IIFE provides us with a local scope
  //we can declare functions and variables that only this scope, by default, sees

  //a "private" variable
  var priv = "I can only be seen in the module";

  //a "private" function
  function privFn(){
    console.log('I am only usable in the module');
  }

  //a "public", or more accurately, an "exposed" variable
  //we attach it to the namespace
  ns.foo = 'I am an exposed value';

  //an exposed function
  ns.bar = function(){
    console.log('exposed!');
    //with an exposed function, we can also call a private function
    privFn();
  }

//this line creates the namespace or uses an existing one
//it then executes the function, passing the created/existing namespace
}(this.namespace = this.namespace || {}));

And so, using our module:

//we can use the exposed entities
namespace.bar(); 
//exposed! 
//I am only usable in the module <- since bar called privFn, it also prints
namespace.foo === 'I am an exposed value'
share|improve this answer

I think it depends on what you need.

For script1, every end point can be accessed. this can be referenced as the object. I like the pattern like:

var Car = {
    name: null,
    init: function (name) {
        this.name = name;
    }
};

For script2, it encapsulates some private variables or functions, which cannot be accessed outside of the anonymous function scope. You can choose what to expose and what to hide.

var Car = (function () {
    var MAX_SPEED = 120; //cannot be referenced

    function init() {
        //something cannot be referenced outside the Car
    }

    function run() {
        //...
    }

    return {
        run: run;
    };

})();

These are the ways to create simple namespaces. Because you can also make namespace into a module.

namespace("GLOBAL.app.Ticker");

namespace will be a simple module to parse the string GLOBAL.app.Ticker, and convert it to a new Object.

share|improve this answer

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.