export
命令用于规定模块的对外接口。
ECMAScript 规范中的模块化方案提供了两种导出模块的方式:
在声明的变量前添加 export
关键字即可将相对应的变量输出。
导出前声明的值:
这种写法能在脚本底部清晰看到所有输出模块,推荐。
const originModule = true;export { originModule };
在导出时重命名:
同样使用 as
关键字,同一函数可以定义多个不同的变量名输出。
export { originModule as newModule };export { originModule as smartModule };
声明后立即导出:
export var something = true;export let anything = true;export const nothing = true;export function everything (){}export class interesting = true;
默认导出让开发者无须知道源模块输出的模块名称即可完成导入。(默认导出的变量无法使用命名导入)
导出一个值作为源模块的默认导出:
export default something;
⚠️ 注意: 仅当源模块只有一个导出时,才建议使用此做法。
将默认和命名导出组合在同一个模块中是不好的做法,尽管它是规范允许的。
扩展:
本质上,export default
就是输出一个叫做 default
的变量或方法,然后系统允许你为它取任意名字。
所以,下面的写法是有效的。
模块导出:
function add(x, y) {return x * y;}export { add as default };// 等同于// export default add;
模块导入:
import { default as foo } from 'modules';// 等同于// import foo from 'modules';
正是因为 export default
命令其实只是输出一个叫做 default
的变量,所以它后面不能跟变量声明语句。
需要特别注意的是,export
命令规定的是 对外的接口,必须与模块内部的变量建立一一对应关系。
// Errorexport 1// Errorconst foo = 1export foo
如上两种写法都会报错,因为均会输出 1
,而 1
只是一个值 ,并非对外的接口。
export var foo = 1;var bar = 1;export { bar };var baz = 1;export { baz as bat };
其他脚本可以通过这个接口,取到值 1
。它们的实质是,在接口名与模块内部变量之间,建立了一一对应的关系。
同样地,函数和类必须遵守这种书写方法。
// Errorfunction foo(){}export foo// Goodexport function bar(){}// Goodfunction baz(){}export { baz }
另外,export
语句输出的接口,与其对应的值是动态绑定关系,即通过该接口,可以取到模块内部实时的值。
export
命令可以出现在模块的任何位置,只要处于模块顶层就可以。
如果处于块级作用域内,就会报错,import
命令也是如此。这是因为处于条件代码块之中,就没法做 静态优化 了,违背了 ES6 模块的设计初衷。
function foo() {export default 'bar';// SyntaxError}foo();