前言

想开始编写Node.js代码,那么我们就必须先熟悉它的模块化规范CommonJS,本文将详细讲解CommonJS规范

本文代码 >>> github 地址

CommonJS

Node 应用由模块组成,采用 CommonJS 模块规范。

每个文件就是一个模块,有自己的作用域。在一个文件里面定义的变量、函数、类,都是私有的,对其他文件不可见。

【特点】

  • 所有代码都运行在模块作用域,不会污染全局作用域。
  • 模块可以多次加载,但是只会在第一次加载时运行一次,然后运行结果就被缓存了,以后再加载,就直接读取缓存结果。要想让模块再次运行,必须清除缓存。
  • 模块加载的顺序,按照其在代码中出现的顺序。

新建文件example.js

// example.js
var x = 5;
var addX = function (value) {
return value + x;
};

上面代码中,变量x和函数addX,是当前文件example.js私有的,其他文件不可见。

如果想在多个文件分享变量,必须定义为global对象的属性。

global.warning = true;

上面代码的warning变量,可以被所有文件读取。当然,这样写法是不推荐的。

module.exports

CommonJS规范规定,每个模块内部,module变量代表当前模块。

这个变量是一个对象,它的exports属性(即module.exports)是对外的接口。

加载某个模块,其实是加载该模块的module.exports属性。

新建文件02_module.js

console.log('module');

const NUM = 100;

function test (){
console.log(NUM);
} // 输出常量
module.exports.num = NUM;
// 输出函数
module.exports.testFn = test;

exports 与 module.exports

它们之间是一层引用关系,exports 引用了 module.exports对象

06_exports.js

console.log(exports,module.exports); // {} , {}
exports.num = '100';
console.log(exports,module.exports); // { num: '100' } { num: '100' }

看上面的代码的输出可以证明exports 引用了 module.exports。那么之前我们采用module.exports输出的内容,其实可以简写为exports输出

【错误的做法】

exports = {
a:1,
b:2
};

上面代码会切断 exports 对 module.exports的引用关系。导致输出的文件,在其它文件是无法使用的

[注意]建议还是使用module.exports规范些,不会产生额外的错误!

require

require方法用于加载模块。

新建文件 03_require.js

const m1 = require('./02_module');

m1.testFn();

执行命令:

node 03_require.js

运行结果:

【路径】

[1] / 表示绝对路径,./ 表示相对于当前文件的路径,

[2] 不写路径则认为是 build-in模块或者各级 node_modules内的第三方模块

const m1 = require('./02_module.js'); // 这样就会在同级目录中寻找02_module.js文件
const m = require('02_module.js'); // 这样只会去 node_modules去寻找相应的文件

【加载文件】

[1]支持js、json、node 拓展名,不写依次尝试加载

const m1 = require('./02_module'); // 这样会在同级目录中寻找 是否有02_module.js 的文件如果有则加载,如果没有则去寻找是否有02_module.json 或者 02_module.node 文件

【特性】

[1]module 被加载的时候执行,加载后缓存

创建文件 04_catch.js

>>> 当我们连续两次引入同一个文件其实只会执行一次

const m1 = require('./02_module');
const m2 = require('./02_module');
// 同时引入两次 02_module文件

我们执行命令 :node 04_catch.js,输出结果:

[2]一旦出现某个模块被循环加载,就只输出已执行的部分,还未执行的部分不会输出

// 1、创建文件:05_modA.js
module.exports.test = 'A'; const modB = require('./05_modB');
console.log('modA: ', modB.test); module.exports.test = 'AA'; // 2、创建文件:05_modB.js
module.exports.test = 'B'; const modA = require('./05_modA');
console.log('modB: ', modA.test); module.exports.test = 'BB'; // 3、创建文件:05_main.js
const modA = require('./05_modA');
const modB = require('./05_modB');

我们可以看到 modA中引入modB,modB中也引入了modA,它们形成了循环引用。那么此时执行 node 05_main.js 会输出什么呢?

其实就是遵循上诉原理:一旦出现某个模块被循环加载,就只输出已执行的部分,还未执行的部分不会输出。大家可以动起手来敲敲代码很好理解的。

[注意]平时写代码的时候切记要避免循环引用

Node.js实战项目学习系列(3) CommonJS 模块化规范的更多相关文章

  1. Node.js实战项目学习系列(1) 初识Node.js

    前言 一直想好好学习node.js都是半途而废的状态,这次沉下心来,想好好的学习下node.js.打算写一个系列的文章大概10几篇文章,会一直以实际案例作为贯穿的学习. 什么是node Node.js ...

  2. Node.js实战项目学习系列(2) 开发环境和调试工具

    前言 上一节让我们对Node.js有一个初步的了解,那么现在可以开始正式学习下Node.js的开发了,但是任何一门语言要设计到开发,就必须先学习开发环境以及调试.本文将主要讲解这些内容. 本文涉及到的 ...

  3. Node.js实战项目学习系列(4) node 对象(global、process进程、debug调试)

    前言 在之前的课程我们学习了Node的模块化规则,接下来我们将学习下 Node的几个新特性:global ,process进程,debug调试 global 跟在浏览器中的window一样都是全局变量 ...

  4. Node.js实战项目学习系列(5) node基础模块 path

    前言 前面已经学习了很多跟Node相关的知识,譬如开发环境.CommonJs,那么从现在开始要正式学习node的基本模块了,开始node编程之旅了. path path 模块提供用于处理文件路径和目录 ...

  5. iKcamp团队制作|基于Koa2搭建Node.js实战项目教学(含视频)☞ 环境准备

    安装搭建项目的开发环境 视频地址:https://www.cctalk.com/v/15114357764004 文章 Koa 起手 - 环境准备 由于 koa2 已经开始使用 async/await ...

  6. 前端(Node.js)(3)-- Node.js实战项目开发:“技术问答”

    1.Web 与 Node.js 相关技术介绍 1.1.Web应用的基本组件 web应用的三大部分 brower(GUI)<==>webserver(business logic.data ...

  7. 开始连载啦~每周2更共11堂iKcamp课|基于Koa2搭建Node.js实战项目教学(含视频)| 课程大纲介绍

  8. Node.js 实战 & 最佳 Express 项目架构

    Node.js 实战 & 最佳 Express 项目架构 Express Koa refs https://github.com/xgqfrms/learn-node.js-by-practi ...

  9. 《Node.js实战(双色)》作者之一——吴中骅访谈录

随机推荐

  1. centos下 telnet访问百度

    先在命令行输入以下命令: telnet www.baidu.com 80 点击确认之后出现如下界面 然后接着输入以下两行命令 GET /index.html HTTP/1.1 Host: www.ba ...

  2. 数据库訪问技术之JDBC

    版权声明:本文为博主原创文章,未经博主同意不得转载. https://blog.csdn.net/zhuojiajin/article/details/32150883     在了解JDBC之前呢, ...

  3. Java获取泛化类型

    @Retention(RetentionPolicy.RUNTIME) public @interface MongodbTable { String name(); } public class A ...

  4. Cookie 版购物车

    写一个JS文件  把相应的方法写在JS文件内 为了方便以后的调用 具体代码为 var Cart = function () { this.Count = 0; this.Total = 0; this ...

  5. 解决 tomcat 重启上传文件消失

    开发模式 首先开发者模式下,部署在 Tomcat 上没有什么好的办法,否则无法调试 除非使用绝对路径,缺点:不同的操作系统路径不同,自动设置 对于图片上传一般我们使用图片服务器,上传 CDN中 一般获 ...

  6. java 面试题整理(不定期更新)

    一.Java基础 1.Java面向对象的三个特征与含义 三大特征是:封装.继承和多态. 封装是指将某事物的属性和行为包装到对象中,这个对象只对外公布需要公开的属性和行为,而这个公布也是可以有选择性的公 ...

  7. JSOI2019 Round2 极限生还

    江苏省省队一共13个名额,去掉女生名额, 按1/3校内限制,我们南外只有4个名额, 在noip爆炸(占比35%),省选一轮爆炸(占比40%),(此时蒟蒻在校内排不进前10...) 总算在省选二轮(占比 ...

  8. vue 中使用jquery

    vue-cli搭建的项目 第一种方式:npm 引包的方式 1.安装jquery npm install jquery --save 2.webpack配置 在项目根目录下的build目录下找到webp ...

  9. Lepus搭建企业级数据库全方位监控系统

    前言 Lepus(天兔)数据库企业监控系统是一套由专业DBA针对互联网企业开发的一款专业.强大的企业数据库监控管理系统,企业通过Lepus可以对数据库的实时健康和各种性能指标进行全方位的监控.目前已经 ...

  10. CodeForces 280B Maximum Xor Se

    题目链接:http://codeforces.com/contest/280/problem/B 题目大意: 给定一个由n个数组成的一个序列,s[l..r] (1 ≤ l < r ≤ n)代表原 ...