目录
一、模块化演变过程
第一阶段:早期模块化开发 (完全依靠约定)
- 污染全局作用域
- 命名冲突问题
- 无法管理模块依赖关系
第二阶段:命名空间方式
- 将方法包裹在一个对象里,减少命名冲突,但是仍然没有解决私有化空间,所以模块成员仍然可以在外部被访问和修改,也无法解决模块依赖关系
第三阶段:IIFE (立即执行函数)
- 需要外部访问的成员挂载到 window 全局对象里,私有成员只能在内部用闭包方式调用,在外部没有办法使用,这样确保了私有变量的安全
第四阶段:利用自执行函数的参数(jQuery)去作为我们的依赖说明,这样就使每个模块依赖关系变得更加明显
二、模块化规范的出现
CommonJs 规范
- 一个文件就是一个模块
- 每个模块都有但单独的作用域
- 通过 module.exports 导出成员
- 通过 require 函数载入模块
之前不使用 CommonJs 模块发开发,是因为它是以同步模块模式加载模块,在node执行机制中,CommonJs是在node 启动时加载模块,在执行过程中是不需要加载的,不会有问题。而在浏览器端使用加载会很慢。会有大量的同步请求模式出现,所以为浏览器端重新设计了一个模式 AMD(Asynchronous Module Definition) 叫异步的模块定义规范,同期出了一个非常出名的库 Require.js。
AMD和 Require的使用
两者区别是 AMD 是定义模块,require 是加载模块
缺点:
- AMD 使用起来相对复杂
- 模块 JS 文件请求频繁
最终 AMD 不是最终好的解决方案 ,同期,淘宝出现了 Sea,js + CMD,在使用上和 require.js 差不多
三、模块化标准规范
- 在 node 环境下,使用 CommonJS
- 在浏览器端下,使用 ES Modules(关于这个主题在另一篇博客中)
四、AMD、CMD、UMD的区别
(参考文章:CommonJS, AMD, CMD是什么及区别 - 简书)
- 三者都属于前端模块化开发规范
- commonJS是服务器端 js 模块化的规范,NodeJS是这种规范的实现。
- AMD(异步模块定义)和CMD(通用模块定义)都是浏览器端js模块化的规范。
AMD规范通过define方法去定义模块,通过require方法去加载模块。
- CMD 推崇依赖就近,AMD 推崇依赖前置
- RequireJS 遵循的是 AMD
- SeaJS 遵循的是 CMD
- 上述三个规范更多的是个人或者社区行为,2015年 tc39 发布了 ES Module,将语言本身的层面讲模块纳入了规范