This article mainly introduces Node. the general module Encapsulation Method in js. For the encapsulation method, see Underscore. js implementation. For more information, see Node. the module loading and execution are encapsulated in js, so that the variables in the module File are in a closure, so that global variables are not contaminated and conflict with others.
Front-end modules are usually stored in a closure by our developers to avoid conflicts with others.
For details about how to encapsulate Node. js and common front-end modules, see Underscore. js. It is a Node. js and common front-end function modules. view the Code:
The Code is as follows:
// Create a safe reference to the Underscore object for use below.
Var _ = function (obj ){
If (obj instanceof _) return obj;
If (! (This instanceof _) return new _ (obj );
This. _ wrapped = obj;
};
// Export the Underscore object for ** Node. js **,
// Backwards-compatibility for the old 'require () 'API. If we're in
// The browser, add' _ 'as a global object via a string identifier,
// For Closure Compiler "advanced" mode.
If (typeof exports! = 'Undefined '){
If (typeof module! = 'Undefined' & module. exports ){
Exports = module. exports = _;
}
Exports. _ = _;
} Else {
Root. _ = _;
}
Determine whether exports exists and assign the local Variable _ to exports to be backward compatible with the old require () API, use a string identifier "_" as a global object. The complete closure is as follows:
The Code is as follows:
(Function (){
// Baseline setup
//--------------
// Establish the root object, 'window' in the browser, or 'exports' on the server.
Var root = this;
// Create a safe reference to the Underscore object for use below.
Var _ = function (obj ){
If (obj instanceof _) return obj;
If (! (This instanceof _) return new _ (obj );
This. _ wrapped = obj;
};
// Export the Underscore object for ** Node. js **,
// Backwards-compatibility for the old 'require () 'API. If we're in
// The browser, add' _ 'as a global object via a string identifier,
// For Closure Compiler "advanced" mode.
If (typeof exports! = 'Undefined '){
If (typeof module! = 'Undefined' & module. exports ){
Exports = module. exports = _;
}
Exports. _ = _;
} Else {
Root. _ = _;
}
}). Call (this );
A closure is built through the function definition. call (this) calls a function under the this object to avoid contamination of internal variables to the global scope. In the browser, this points to a global object (window object) and assigns the "_" variable to "root. _" on the Global Object for external calls.
Similar to Underscore. js, Lo-Dash also uses a similar solution, but is compatible with AMD module loading:
The Code is as follows:
; (Function (){
/** Used as a safe reference for 'undefined' in pre ES5 environments */
Var undefined;
/** Used to determine if values are of the language type Object */
Var objectTypes = {
'Boolean': false,
'Function': true,
'Object': true,
'Number': false,
'String': false,
'Undefined': false
};
/** Used as a reference to the global object */
Var root = (objectTypes [typeof window] & window) | this;
/** Detect free variable 'exports '*/
Var freeExports = objectTypes [typeof exports] & exports &&! Exports. nodeType & exports;
/** Detect free variable 'module '*/
Var freeModule = objectTypes [typeof module] & module &&! Module. nodeType & module;
/** Detect the popular CommonJS extension 'module. export '*/
Var moduleExports = freeModule & freeModule. exports === freeExports & freeExports;
/*--------------------------------------------------------------------------*/
// Expose Lo-Dash
Var _ = runInContext ();
// Some AMD build optimizers, like r. js, check for condition patterns like the following:
If (typeof define = 'function' & typeof define. amd = 'object' & define. amd ){
// Expose Lo-Dash to the global object even when an AMD loader is present in
// Case Lo-Dash was injected by a third-party script and not intended to be
// Loaded as a module. The global assignment can be reverted in the Lo-Dash
// Module by its 'noconflict () 'method.
Root. _ = _;
// Define as an anonymous module so, through path mapping, it can be
// Referenced as the "underscore" module
Define (function (){
Return _;
});
}
// Check for 'ports' after 'describe' in case a build optimizer adds an 'ports' object
Else if (freeExports & freeModule ){
// In Node. js or RingoJS
If (moduleExports ){
(FreeModule. exports = _). _ = _;
}
// In Narwhal or Rhino-require
Else {
FreeExports. _ = _;
}
}
Else {
// In a browser or Rhino
Root. _ = _;
}
}. Call (this ));
Let's take a look at the main code of Moment. js's encapsulation closure:
The Code is as follows:
(Function (undefined ){
Var moment;
// Check for nodeJS
Var hasModule = (typeof module! = 'Undefined' & module. exports );
/************************************
Exposing Moment
************************************/
Function makeGlobal (deprecate ){
Var warned = false, local_moment = moment;
/* Global ender: false */
If (typeof ender! = 'Undefined '){
Return;
}
// Here, 'I' means 'window' in the browser, or 'global' on the server
// Add 'moment 'as a global object via a string identifier,
// For Closure Compiler "advanced" mode
If (deprecate ){
This. moment = function (){
If (! Warned & console. warn ){
Warned = true;
Console. warn (
"Accessing Moment through the global scope is" +
"Deprecated, and will be removed in an upcoming" +
"Release .");
}
Return local_moment.apply (null, arguments );
};
} Else {
This ['moment '] = moment;
}
}
// CommonJS module is defined
If (hasModule ){
Module. exports = moment;
MakeGlobal (true );
} Else if (typeof define = "function" & define. amd ){
Define ("moment", function (require, exports, module ){
If (module. config (). noGlobal! = True ){
// If user provided noGlobal, he is aware of global
MakeGlobal (module. config (). noGlobal = undefined );
}
Return moment;
});
} Else {
MakeGlobal ();
}
}). Call (this );
The preceding examples show that the following logic can be used to encapsulate common modules of Node. js and the frontend:
The Code is as follows:
If (typeof exports! = "Undefined "){
Exports. ** = **;
} Else {
This. ** = **;
}
That is, if the exports object exists, local variables are loaded on the exports object. If not, local variables are loaded on the global object. If the compatibility of ADM specifications is added, add one more sentence:
The Code is as follows:
If (typeof define = "function" & define. amd ){}