• 1. What is modularity
  • 2. Why modularity
  • 3. Modularity in the source code
    • 3.1 AMD
    • 3.2 Commonjs
    • 3.3 Modularization of Vue source code analysis

1. What is modularity

Modularity is not unique to the front end. Modularization is a top-down process by which a large system is gradually divided into smaller modules that encapsulate certain functions and expose them through agreed interfaces. Each module does not interfere with each other and is easy to plug and remove. Modularization can decouple code, better reuse, each module does not affect each other, do not worry about variable pollution, naming conflicts and other problems, but also conducive to parallel development, improve efficiency.

Js was originally not modular. As front-end applications become more and more complex, for example, when an HTML page requests multiple JS files, how to ensure that the variables between these JS files do not interfere with each other? In order to solve problems such as variable pollution and naming conflicts, some modularity schemes began to appear in JS, from the closure modularity proposed in 2003, to CommonJS and AMD in 2009, and now ES modularity.

2. Why modularity

The benefits of modularity can be summarized as follows:

  • Independent scope to avoid variable contamination and naming conflicts
  • Reduce project complexity and improve development efficiency
  • Improve code reusability and maintainability

3. Modularity in the source code

The AMD and Commonjs specifications mentioned above have different definitions for modularity, which requires compatibility between different environments.

3.1 AMD

Asynchronous Module Definition (AMD) : Asynchronous Module Definition. When loading modules and other modules that modules depend on, AMD uses asynchronous loading mode to avoid module loading blocking web page rendering.

AMD, as a specification, just defines its syntax API, not its implementation. The AMD specification is so simple that there is only one API, the module define function:

define(name? , [dependencies]? , factory)

  • Name is the module identifier, or the file name if not provided.
  • Dependencies indicates the modules on which they depend.
  • Factory is the function or object that the module initializes to execute, only once if it is a function, or output a value for the module if it is an object.

The AMD specification is primarily a specification for the front-end browser.

3.2 Commonjs

The CommonJS specification states that within each module, the module variable represents the current module. This variable is an object whose exports property (module.exports) is the interface to the outside world. Loading a module loads the module.exports property of that module.

The CommonJS specification load module is loaded synchronously, which means that no subsequent operations can be performed until the load is complete.

Module definition syntax: module.exports=factory()

CommonJS is primarily a specification for JAVASCRIPT environments outside of browsers.

3.3 Modularization of Vue source code analysis

Take the source code for VUe2 as an example. If you fold the source code, you’ll see the following code:

This is an anonymous self-executing function that has its own scope to avoid contaminating or being contaminated by outside code.

If you need an external global variable, you can pass it in as an argument, like this, which is actually the Window object, and by passing this, you change the Window from a global variable to a local variable, and when you access this in the later code block, you don’t need to back up the scope chain to the top level scope, This allows faster access to the Window object; Passing Window as an argument can also be optimized when you compress your code. Such as: function (a, b) {}) (Windows); // Window is optimized to A.

Global is the this parameter passed in from execution, which is the Window object.

Factory is the second argument passed in, the anonymous function that follows.

Expand the first function to see the following code:

typeof exports= = ='object' && typeof module! = ='undefined' ? module.exports = factory() :
    typeof define === 'function' && define.amd ? define(factory) :
      (global = global || self, global.Vue = factory());
Copy the code

This code detects which modular specification is supported by the current runtime environment and modularizes Vue, exports being Commonjs and DEFINE being AMD.

As you can see from the source, factory() returns a Vue object at the end.

When the Commonjs specification is detected, the exported Vue object is written as follows:

The module exports = factory ();

When an AMD specification is detected, it is written as follows:

Define (factory).

To make it more intuitive, rewrite this code:

if(typeof exports= = ='object' && typeof module! = ='undefined') {/ / Commonjs specification
    module.exports = factory();
}else if(typeof define === 'function' && define.amd){
    / / AMD specification
    define(factory);
}else{
    // In other cases, mount the Vue into the global object
    // Add the Vue attribute to the Window object in the browser. The attribute value is the Vue object returned by factory()
    global = global || self,
    global.Vue = factory();
}
Copy the code