5

Sometime ago I heard that it was good practice to wrap your code in a big object to serve as a namespace in order to reduce global namespace cluttering and to facilitate library export, so I tried this.

var wrapper = {
    foo: function(){
        return 42;
    },
    bar: this.foo()
};

It fails, claiming that "foo is not defined". Calling methods before finishing the object declaration is probably bad, so I moved bar, and it worked.

var wrapper = {
    foo: function(){
        return 42;
    },
};
wrapper.bar = wrapper.foo();

I feel that this can become kind of ugly, especially with nested namespaces and such, so are there any workarounds that don't make it hard to see all of the wrapper's members at once?

Name Here
  • 113
  • 8
  • Why would you need to call any method at declaration? Maybe you want to use an immediately-invoked function (*IEFE*). Also check out the *module pattern*. – Bergi Aug 26 '13 at 22:32

3 Answers3

1

The problem is that this is going to equal the global context. You need to access the function like so:

var wrapper = {
    foo: function(){
        return 42;
    },
    bar: null,
    init : function() {
       // all initialization code goes here
       wrapper.bar = wrapper.foo();
    }
};

wrapper.init();

This method is great for organizing your code into logical chunks so you and future developers can easily find what you are looking for in your javascript.

Jonathan Crowe
  • 5,793
  • 1
  • 18
  • 28
  • Hm, Chrome claims that it "Cannot call method 'foo' of undefined", implying that wrapper is undefined? – Name Here Aug 26 '13 at 04:29
  • Updated code to be usable. The most common usage of this architecture is to include some sort of init function that does all variable initializations. This can be done in a document onload event in the case that your variables will contain references to the DOM ie: `wrapper.bar = document.getElementById('bar');` which is useful when you want to limit the number of times you search the DOM – Jonathan Crowe Aug 26 '13 at 05:02
0

Using this like that will not work unless wrapper is 1) a function, and 2) you instantiate it to use it:

var wrapper = function() {
  this.foo = function() { return 42; }
  this.bar = this.foo();
};

var wrapperInstance = new wrapper();
alert(wrapperInstance.bar()); // 42
wrapperInstance.foo(); // also works
Ezekiel Victor
  • 3,877
  • 1
  • 27
  • 28
  • I assume you meant `alert(wrapperInstance.bar); wrapperInstance.foo();`, considering that bar is not a function and that wrapper has no members. This also seems overkill for a wrapper, since making a constructor you're only going to use once seems silly... – Name Here Aug 26 '13 at 04:38
  • Yes, I went ahead and edited it accordingly. It's not that silly -- think singleton pattern. :) – Ezekiel Victor Aug 27 '13 at 06:53
0
var wrapper = {
foo: (function(){
    return 42;
     })()

};

alert(wrapper.foo);

http://jsfiddle.net/ee8Ww/