Off Topic
To solve the blog title, because the first article commented that some people questioned the subject is far away, said half a day and angular material not half-hair relationship. In fact, my center in the second half of the "string Learning client development."
Require ()
Don't confuse the Require () and requirejs here. It is interesting, however, that Typescript's module definition even supports both of these modular mechanisms.
To import and use an external module, just a simple sentence require()
to see the Angular/material/docs under the compiled file Gulpfile.js code snippet. There is an intuitive sense of module import and use.
var gulp = require(‘gulp‘);var concat = require(‘gulp-concat‘);var fs = require(‘fs‘);... //对模块gulp的使用gulp.task(‘demos‘, function() { ... //对模块gulp-concat的使用gulp.src([ ‘node_modules/angularytics/dist/angularytics.js‘, ‘dist/docs/js/**/*.js‘ ]) .pipe(concat(‘docs.js‘))//对模块fs的使用fs.writeFileSync(dest + ‘/demo-data.js‘, file);
gulp.task
Used to define a task; cancat
to merge files; FS is a module that operates on disk files. As you can see, with the introduction of modules, the code is clearer and clearer, and these common modules are equivalent to the expansion of basic language functions.
Here, the keyword require () ties everything together. So what's going on behind this simple sentence?
- Require is actually not a language keyword, in the article behind the study, we can see.
- Developers who have not yet used require () or are not interested in its implementation mechanism can take this part slightly. Indeed, the latter implementation mechanism does not affect the use.
Most of the following are from the original: how require () actually Works
Because Nodejs is open source, we can require()
go back to node's core code. However, what we find is not a simple function, but a file module.js. This file implements the entire module loading system for node. The procedures covered are load, compile, and cache. And we're require()
only using a corner of the ice.
Module.js
function Module(id, parent) {this.id = id;this.exports = {};this.parent = parent;//...
We can see that module.js first defines a type (function) Module. This type has two functions. One, which is the base class for all modules, after which each module is an instance of this module. This is also the ultimate source of our previous discussion module.exports
.
The second function of this module is to complete the loading process of the node module. The require()
last thing we use is to call the Module.require method, and this method calls another internal method module._load. The final load method is the place where the module files are actually loaded, which is what I'm going to analyze and study.
Module._load
Module._load = function(request, parent, isMain) {//1. Check Module._cache for the cached module.//2. Create a new module instance if cache empty//3. Save it to the cache//4. Call module.load() with your the given filename, this will call module.compile() after reading the file contents.//5. If there was error loading /parsing the file, delete the bad module from cache.//6. return module.exports};
The module._load is responsible for loading the cache of new modules and management modules. The caching mechanism improves system performance by reducing the duplication of read files when each module is loaded. In addition, shared module instances allow the Singleton module to retain state throughout the project.
If the module is not found in the cache, Module._load creates a new module instance for the file. Use this instance to read the contents of the file and send it to module._compile.
Notice that in the 6th step above, the Module.exports is returned. This return statement explains why the exposed interface (method) is assigned to Module.exports (or alias exports) in your module file, which also explains the variables returned by require (), which can be called directly to the method of importing the module. There are no magical or special places to see.
Module._compile
Module.prototype._compile = function(content, filename) {// 1. Create the standalone require function that calls module require.// 2. Attach other helper methods to require.// 3. Wraps the JS code in a function that provides require, module, etc. variables locally to the module scope.// 4. Run that function.
This method, the first to create the Require function, this is the one we are very familiar with require()
(the module loading mechanism is not only the processing of loading modules, but also the process of importing and invoking, here can be regarded as the process of the caller, as we mentioned Main.js). The function itself simply encapsulates the module.require and adds some help properties and methods, as follows:
- Require () is the require () we use
- Require.main Main Module
- Require.cache All cached modules
- Require.extensions compilation methods for different file types (suffixes)
After building the require, the code for all the original files is encapsulated in a new function that takes require,module,exports as a parameter. This can also explain why we can call require () directly and why exports is the alias of Module.exports.
(function(exports,require, module, __filename, __dirname){//原模块文件的所有代码注入在这});
People who understand the module pattern can easily see that this is a meaningless re-account of the module pattern, which is to prevent the namespace of the system from being defined in the module file (remembering JavaScript global variables).
Finally, this newly created function is run directly, which is also part of the full module pattern, and finally the empty bracket is the running part:
(function(...){//...})();
If you are not familiar with module Patter, you can look at one of my other articles in-depth exploration of a section of Angularjs, module mode-modules pattern
Summary
So far, we've gone through the entire process of module loading. From creating a module module.exports to calling require, and calling an internal procedure for implementation. Although these do not have any effect on your code, how to do it in the original. However, can let you write the same code, the heart is more bottom, no longer force memory module syntax. The most important thing is to improve your architectural level by learning a good purchasing structure.
Angular Material String Learning Client development 2-node.js module loading mechanism require ()