In javascript is there a name for this idiom / pattern? A function which has about 10 inner functions and 10 vars, and returns an object literal usually name "that" which returns a a subselection of the inner functions and vars. For example:
function myFunction() {
var myVar1;
var myVar2;
var myVar3;
...
...
function myInnerFunction1() {
...
}
function myInnerFunction2() {
...
}
function myInnerFunction3() {
}
var that = {
inner1: myInnerFunction1,
inner2: myInnerFunction2,
var1: myVar1
}
return that;
}
It's called "the module pattern" and/or "creating a namespace." It's so you have a private scope for your stuff (the execution context of the call to the wrapper function, myFunction in your example), and you return an object that only has the things on it that you want to make publicly accessible. Those things (myInnerFunction1 for example) have access to the private information within the wrapper function, but nothing using the resulting object does.
In the module pattern, you may well not export anything, if you have nothing public you need to expose directly (for instance, your code is completely self-contained, setting up event handlers and such).
Related
I have a clarification in using IIFs in javascript .
I have downloaded a javascript file called called test.js as follows and I have got following questions after googling IIFs:
define(function () {
(function (window) {
this.test = function() {};
Test.prototype.function1 = function(){
//Do something
},
function Delete(){
//Code to Delete
}
window.Delete = Delete;
})(window);
});
I do have the following questions:
Is the line,
this.test = function() {}; a constructor?
If so can I have 2 constructors in a single file like for example:
this.test = function() {};
this.test2 = function() {};
And also, why would I need a constructor when I know that this is an automatically invoked file where everything gets executed initially itself.
Is this a private function?
Test.prototype.function1 = function(){
//Do something
},
Does this not get automatically? Should I need to create an object of the test and then invoke it?
Is this a public function?
function Delete(){
//Code to Delete
}
window.Delete = Delete;
The last line of the above says that . If it is so then whats the difference between first and second function?
What is keyword window here?
It's worth noting that this code will fail with an error, as Test is undefined, and you can't set the prototype property on undefined.
In JavaScript, any function can be a constructor. It's up to how you use it. You can add functions and properties to the .prototype property of any function, and any objects created from it using new will get them from the prototype chain. In your case, this.test = function(){} doesn't look like a prototype.
There's no such things a "public" or "private" functions in JavaScript, there's only what's exposed via return out of the function (or in your case, by using the global window object, which is considered bad practice) If the Test function is exposed somewhere, then Test.prototype.function1 is also exposed. All prototype methods are "public".
Yes, sort of. Like I said, "public" or "private" isn't a thing in JavaScript. You created a function and placed it on the window object, which is global. Essentially, you've made the function global.
window is the global browser object. Although when used like this (function(window) { ... })(window), the first window is the name of the parameter, (and any instances of window inside the function reference to that parameter, and the second one (passed to the function call), is the global window object.
Further reading:
The Revealing Module Pattern
I am learning JavaScript and have come across of the structure below:
var Test = (function () {
function func1() {
//do something.....
}
function func2() {
//do something.....
}
function func3() {
//do something.....
}
return {
func1: func1,
func2: func2,
func3: func3
};
})();
I am wondering what the return block is doing. Is this a very commonly used JavaScript structure? Please let me know where can I get more information about this.
This is the Revealing Module Pattern.
The returned object contains references to the functions defined inside the IIFE. So the functions defined inside are private to the anonymous function.
But if you want to use the inner functions outside, you can use the returned object.
The value of Test will be
var Test = {
func1: func1,
func2: func2,
func3: func3
};
And you can call func1 from outside as
Test.func1();
This is the way Javascript emulate class. As there is no visibility specifiers using Module pattern, variables/methods can be make public/private.
The revealing module pattern is inspired from Module pattern. In revealing module pattern, only reference to the private variables/methods is returned in an object.
The main idea behind the pattern is avoiding evil global variables. This looks similar to IIFE except an object is returned instead of function. The variables/methods defined inside the IIFE are private to the function. To access any variable/method inside the IIFE, it needs to be added in the returned object and then it can be accessed from outside of IIFE. This pattern takes advantage of closures, so the variables/methods defined inside the IIFE are accessible even after the object is returned.
From Addy Osmani's book Learning Javascript Design patterns
The Revealing Module pattern came about as Heilmann was frustrated with the fact that he had to repeat the name of the main object when we wanted to call one public method from another or access public variables. He also disliked the Module pattern’s requirement for having to switch to object literal notation for the things he wished to make public.
The result of his efforts was an updated pattern where we would simply define all of our functions and variables in the private scope and return an anonymous object with pointers to the private functionality we wished to reveal as public.
Advantages:
Encapsulation. The code inside the IIFE is encapsulated from outside world
Clean, organized and reusable code
Privacy. It allows to create private variables/methods. The private variables/methods cannot be touched from outside of the IIFE.
Disadvantages:
If a private function refers to a public function, that public function can't be overridden
Further Reading:
https://en.wikipedia.org/wiki/Module_pattern
https://carldanley.com/js-revealing-module-pattern/
How to use Revealing module pattern in JavaScript
EDIT
From comment from #Mike
It's of note that it's common to create an object (eg, var me = {};) and then declare the would-be public members on it (me.func1 = function() { /* ... */ };), returning that object at the end (return me;). This avoids the repetition that we see in the return statement of OP's code (where all the public stuff is repeated).
It's a literal object in the return statement. It's like creating an object and then returning it:
var obj = {
func1: func1,
func2: func2,
func3: func3
};
return obj;
The literal object syntax creates an object and sets its properties, just like:
var obj = new Object();
obj.func1 = func1;
obj.func2 = func2;
obj.func3 = func3;
return obj;
The purpose of returning the object is to reveal the functions inside the function to the code outside, while creating a scope for private variables that the functions can use.
When not using private variables, the code does the same thing as:
var Test = {
func1: function() {
//do something.....
},
func2: function() {
//do something.....
},
func3: function() {
//do something.....
}
};
Private variables are declared inside the function scope, and are only reachable by the functions inside it. Example:
var Test = (function () {
var name;
function setName(str) {
name = str;
}
function getName() {
return name;
}
return {
setName: setName,
getName: getName
};
})();
Test.setName("John Doe");
var name = Test.getName();
That works like a class in other programming languages. Therefore, you can access the public func1 member using Test.func1 and call it like a normal function using Test.func1().
I am learning JavaScript and have come across of the structure below:
var Test = (function () {
function func1() {
//do something.....
}
function func2() {
//do something.....
}
function func3() {
//do something.....
}
return {
func1: func1,
func2: func2,
func3: func3
};
})();
I am wondering what the return block is doing. Is this a very commonly used JavaScript structure? Please let me know where can I get more information about this.
This is the Revealing Module Pattern.
The returned object contains references to the functions defined inside the IIFE. So the functions defined inside are private to the anonymous function.
But if you want to use the inner functions outside, you can use the returned object.
The value of Test will be
var Test = {
func1: func1,
func2: func2,
func3: func3
};
And you can call func1 from outside as
Test.func1();
This is the way Javascript emulate class. As there is no visibility specifiers using Module pattern, variables/methods can be make public/private.
The revealing module pattern is inspired from Module pattern. In revealing module pattern, only reference to the private variables/methods is returned in an object.
The main idea behind the pattern is avoiding evil global variables. This looks similar to IIFE except an object is returned instead of function. The variables/methods defined inside the IIFE are private to the function. To access any variable/method inside the IIFE, it needs to be added in the returned object and then it can be accessed from outside of IIFE. This pattern takes advantage of closures, so the variables/methods defined inside the IIFE are accessible even after the object is returned.
From Addy Osmani's book Learning Javascript Design patterns
The Revealing Module pattern came about as Heilmann was frustrated with the fact that he had to repeat the name of the main object when we wanted to call one public method from another or access public variables. He also disliked the Module pattern’s requirement for having to switch to object literal notation for the things he wished to make public.
The result of his efforts was an updated pattern where we would simply define all of our functions and variables in the private scope and return an anonymous object with pointers to the private functionality we wished to reveal as public.
Advantages:
Encapsulation. The code inside the IIFE is encapsulated from outside world
Clean, organized and reusable code
Privacy. It allows to create private variables/methods. The private variables/methods cannot be touched from outside of the IIFE.
Disadvantages:
If a private function refers to a public function, that public function can't be overridden
Further Reading:
https://en.wikipedia.org/wiki/Module_pattern
https://carldanley.com/js-revealing-module-pattern/
How to use Revealing module pattern in JavaScript
EDIT
From comment from #Mike
It's of note that it's common to create an object (eg, var me = {};) and then declare the would-be public members on it (me.func1 = function() { /* ... */ };), returning that object at the end (return me;). This avoids the repetition that we see in the return statement of OP's code (where all the public stuff is repeated).
It's a literal object in the return statement. It's like creating an object and then returning it:
var obj = {
func1: func1,
func2: func2,
func3: func3
};
return obj;
The literal object syntax creates an object and sets its properties, just like:
var obj = new Object();
obj.func1 = func1;
obj.func2 = func2;
obj.func3 = func3;
return obj;
The purpose of returning the object is to reveal the functions inside the function to the code outside, while creating a scope for private variables that the functions can use.
When not using private variables, the code does the same thing as:
var Test = {
func1: function() {
//do something.....
},
func2: function() {
//do something.....
},
func3: function() {
//do something.....
}
};
Private variables are declared inside the function scope, and are only reachable by the functions inside it. Example:
var Test = (function () {
var name;
function setName(str) {
name = str;
}
function getName() {
return name;
}
return {
setName: setName,
getName: getName
};
})();
Test.setName("John Doe");
var name = Test.getName();
That works like a class in other programming languages. Therefore, you can access the public func1 member using Test.func1 and call it like a normal function using Test.func1().
I was just looking at the code of a simple demonstration of modular pattern, have a look :
// Global module
var myModule = (function ( jQ, _ ) {
function privateMethod1(){
jQ(".container").html("test");
}
function privateMethod2(){
console.log( _.min([10, 5, 100, 2, 1000]) );
}
return{
publicMethod: function(){
privateMethod1();
}
};
// Pull in jQuery and Underscore
})( jQuery, _ );
myModule.publicMethod();
The code is pretty straightforward, what I don't understand is what's the need for a publicMethod? Why are privateMethod1 and privateMethod2 inaccessible? I understand that privateMethod1 and privateMethod2 are classic js functions and publicMethod is more of a variable assigned to hold a function.
privateMethod1() and privateMethod2() are local functions declared inside the module function wrapper. As such, they are only visible and callable from within that function wrapper. They can't be reached from outside the module wrapper.
This is the same as a local variable inside a function.
function someFunc() {
// a function declared inside another function is ONLY available
// inside that function
function localFunc() {
// do something
}
// this is just like a local variable which is only available within
// the scope of the function itself
var myVariable = 2;
}
// can't call localFunc here - this will be an error
// because it is defined in a different scope and not available here
localFunc();
Private methods can be useful when you want to create functions or methods that the public methods can use, but you do not want outside callers to be able to also call or use those functions/methods.
Private variables can be used to store state that the public methods or private methods want to reference, but you don't want the outside callers to have access to or be able to mess with.
I'm using the FB.Event.subscribe() observer model to find out when a user logs in. This method takes two arguments, a string containing the thing to watch, and callback function.
I'm following several events that handle the event the same way, so I've set up the callback function as a pre defined method and passed this to FB.Event.subscribe() like this:
Controller.prototype.go = function() {
FB.Event.subscribe('auth.login', this.fbHandleStatusChange);
FB.Event.subscribe('auth.logout', this.fbHandleStatusChange);
}
Controller.prototype.fbHandleStatusChange = function(response) {
// Doesn't work
this.otherFunction();
}
Controller.prototype.otherFunction = function() {
alert('hello');
}
Unfortunately this means that I loose access to 'this' within the scope of fbHandleStatusChange, obviously I don't want to start coding references to concrete versions of Controller!
I'm guessing I'm passing the function incorrectly?
Thanks.
In JavaScript, this is defined entirely by how a function is called, not where it's defined. This is different than some other languages. (JavaScript doesn't have methods, it just has functions and some syntactic sugar that makes them look like methods sometimes.) So although you're passing in your function correctly, Facebook doesn't know about your object instance and can't set this correctly when calling your function.
Check the FB.Event.subscribe docs to see if it offers a way to say what "context" to use to call the event handler function. It may offer a way to do that. (This will usually be a context or thisArg parameter.)
If not, you can readily solve the problem with a closure:
Controller.prototype.go = function() {
var self = this;
FB.Event.subscribe('auth.login', handleChange);
FB.Event.subscribe('auth.logout', handleChange);
function handleChange() {
return self.fbHandleStatusChange();
}
}
That grabs a copy of this into a variable called self, which is used by the handleChange function (which is a closure over the scope containing the self variable) to call your function with the correct context. More about closures here: Closures are not complicated More about this here: You must remember this
Alternately, though, are you really going to have multiple instances of Controller? People coming to JavaScript from class-based languages tend to use constructor functions (a rough "class" analogue) unnecessarily. They're the right choice if you need to have more than one instance of an object, but if you're only ever going to have a single Controller object on the page, then using a constructor function and fiddling about with this is overkill.
If you don't need multiple, independent Controller instances, then:
var controllerObject = (function() {
var inst = {};
inst.go = go; // Make `go` a publicly-accessible function of the object
function go() {
FB.Event.subscribe('auth.login', fbHandleStatusChange);
FB.Event.subscribe('auth.logout', fbHandleStatusChange);
}
// This is private to us, so we don't expose it as a property on the object
function fbHandleStatusChange(response) {
// Doesn't work
otherFunction();
}
// This is also private to us
function otherFunction() {
alert('hello');
}
return inst;
})();
That creates a private scope via the outer anonymous function, and within that scope creates an instance (inst) which we then return and refer to as controllerObject. controllerObject in the above only has one property, the function go. All of our other functions are truly private. (I've also taken the liberty of ensuring that the functions have names, because that helps your tools help you.)
Note that we don't actually refer to inst anywhere in our function calls, because they're all local to the closure scope. We can even have private data, by having other vars within the outer closure.