javascript模块化是如何发展的?_ES6模块与CommonJS模块在javascript中有何区别?

17次阅读

javaScript模块化历经IIFE、Commonjses6标准,前者为值拷贝且运行时加载,后者为绑定引用且编译时加载,语法、机制与环境支持均显著不同。

javascript模块化是如何发展的?_ES6模块与CommonJS模块在javascript中有何区别?

javascript模块化从无到有,经历了社区探索到官方标准化的过程。早期没有模块机制,开发者靠全局变量或立即执行函数(IIFE)模拟模块,但难以维护。node.js诞生后引入CommonJS,用requiremodule.exports实现服务端模块管理;而浏览器端长期依赖打包工具(如webpack)做模块转换。直到ES6(ecmascript 2015)正式定义import/export语法,浏览器才原生支持模块加载——这是模块化走向统一的关键一步。

语法写法与导出导入方式不同

CommonJS使用函数式调用:const utils = require('./utils'),导出靠赋值module.exports = {...}或简写exports.xxx = ...;ES6则用声明式语法:import { foo } from './utils.js',导出必须显式export const foo = ...export default ...。ES6不支持在条件语句中动态import(静态语法),而CommonJS的require可写在任意位置。

加载时机与依赖解析机制不同

CommonJS是运行时同步加载:脚本执行到require才去读文件、执行模块、返回结果;ES6模块在代码解析阶段就确定全部依赖关系,属于编译时加载。这使得ES6模块能被构建工具提前分析,支持tree-shaking(剔除未使用代码),也导致它无法像CommonJS那样根据条件加载不同模块(除非用import()动态导入)。

值传递方式与响应性差异

CommonJS导出的是值的拷贝(浅拷贝),比如导出一个数字或字符串,后续修改不影响已导入的值;ES6模块导出的是绑定的只读引用,导入后即使原模块内部更新了变量,导入方也能看到变化(但不能对导入的变量重新赋值,否则报错)。例如导出一个对象,两者都能修改其属性,但只有CommonJS允许utils = newUtils这种整体替换。

立即学习Java免费学习笔记(深入)”;

运行环境与兼容性现状

CommonJS原生仅限node.js(v12+默认支持ESM,但需文件后缀为.mjspackage.json中设"type": "module");ES6模块现代浏览器全支持(通过),Node.js也已全面兼容。构建场景中,typescriptvite、Webpack等默认以ESM为输入标准,CommonJS多用于遗留代码或特定npm包(如CJS格式的工具库)。

text=ZqhQzanResources