module
Description
为了编写可维护的代码,我们把很多函数分组,分别放到不同的文件里,这样,每个文件包含的代码就相对较少,很多编程语言都采用这种组织代码的方式。在 Node 环境中,一个 js 文件就称之为一个模块(module)
使用模块可以避免函数名和变量名冲突,相同名字的函数和变量完全可以分别存在不同的模块中。
Code
hello 模块
'use strict'
var s = 'Hello'
function greet(name) {
console.log(s + ', ' + name + '!')
}
module.exports = greet
函数 greet()
是我们在 hello
模块中定义的,你可能注意到最后一行是一个奇怪的赋值语句,它的意思是,把函数 greet
作为模块的输出暴露出去,这样其他模块就可以使用 greet
函数了
调用模块
'use strict'
// 引入 hello 模块
var greet = require('./hello')
var s = 'Michael'
greet(s) // Hello, Michael
require 引入的就是 hello 模块输出的 greet
CommonJS 规范
NodeJS
的模块加载机制被称为 CommonJS
规范。在这个规范下,每个 .js
文件都是一个模块,它们内部各自使用的变量名和函数名都互不冲突,例如,hello.js
和 main.js
都申明了全局变量 var s = 'xxx'
,但互不影响
用法
在模块中对外输出变量,用:
module.exports = variable
输出的变量可以是任意对象、函数、数组等
要引入其他模块输出的对象,用:
var foo = require('other_module')
引入的对象具体是什么,取决于引入模块输出的对象
Node 模块原理
require
Node.js 加载模块时,会将代码包装:
(function () {
// 读取的 hello.js 代码
var s = 'Hello'
var name = 'world'
console.log(s + ' ' + name + '!')
// hello.js 代码结束
})()
这样,模块中的变量都会变成匿名函数内部的局部变量,即使 NodeJS 继续加载其他模块,模块之间的变量也不会互相干扰
exports
NodeJS
输出模块时,会先准备一个对象 module
// 准备 module 对象
var module = {
id: 'hello',
exports: {}
}
var load = function (module) {
// 读取的 hello.js 代码
function greet(name) {
console.log('Hello, ' + name + '!')
}
module.exports = greet
// hello.js 代码结束
return module.exports
}
var exported = load(module)
// 保存 module
save(module, exported)
通过把参数 module
传递给 load
函数,hello.js
就顺利地把一个变量传递给了 Node
执行环境,Node
会把 module
变量保存到某个地方。
由于 Node
保存了所有导入的 module
,当我们用 require()
获取 module
时,Node
找到对应的 module
,把这个 module
的 exports
变量返回,这样,另一个模块就顺利拿到了模块的输出:
var greet = require('./hello')
以上是 Node
实现 javascript
模块的一个简单的原理
Last updated
Was this helpful?