1

我按照2ality的最终语法示例对 ES6 模块进行了编码,没有.js后缀。

我还将模块组织成供应商/项目目录层次结构和模块命名方案,因为System.register()模块格式有效地将已注册的模块放置到相同的命名空间中。

问题如下,如果我引用 2ality 的例子:

//------ lib.js ------
export const sqrt = Math.sqrt;
export function square(x) {
    return x * x;
}
export function diag(x, y) {
    return sqrt(square(x) + square(y));
}

//------ main.js ------
import { square, diag } from 'lib';
console.log(square(11)); // 121
console.log(diag(4, 3)); // 5

上面的代码可以直接在浏览器中正常工作,例如,使用traceures6-module-loader(请参阅参考资料example-es6-modules.html)。当import遇到声明时,.js后缀似乎会自动附加到文件名,并被lib.js加载。只要System.paths配置为指向 vendor/project 目录的顶部,就可以直接在浏览器中执行 ES6 模块。

当使用SystemJS builder捆绑到单个System.register()模块格式文件时,上述内容也可以正常工作(请参阅参考资料)。只要在生成模块时设置为供应商/项目层次结构的顶部(请参阅builder.js),那么模块就会以供应商/项目前缀命名。example-system-register.htmlbaseURL

问题是,当我尝试为 browserify 的输入生成 CommonJS 模块,同时执行转换traceur并且es6ify不将.js后缀附加到声明中的文件名时import,会导致以下几行错误:

$ cd src/es6
$ traceur --out ./out.js --modules commonjs gso/eonjs/EonJS.js

Error: File not found '/home/ ... /src/es6/gso/eonjs/MomentRecurRule'

上面的错误是因为traceur没有给import声明添加.js后缀。'gso/eonjs/MomentRecurRule'否则会找到该文件。

如果 ES6 模块被转编译为单个 CommonJS 模块,browserify 会报告相同的错误,找不到要导入的文件 - browserify 也不会类似地自动.js为导入文件名添加后缀。

那么问题是,ES6 模块在浏览器中执行没有问题,System.register()也可以作为捆绑模块加载,但是如何转换为浏览器可执行文件?

4

1 回答 1

0

相对路径的browserify API别名模块 ID:

var browserify = require('browserify');

var b = browserify();
b.add('./index.js');

b.require('./gso/eonjs/EonJS.js',  { expose: 'gso/eonjs/EonJS' });
b.require('./gso/eonjs/AbstractRecurRule.js', { expose: 'gso/eonjs/AbstractRecurRule' });
b.require('./gso/eonjs/MomentRecurRule.js', { expose: 'gso/eonjs/MomentRecurRule' });
b.require('./gso/eonjs/RRuleRecurRule.js', { expose: 'gso/eonjs/RRuleRecurRule' });
b.require('./gso/eonjs/RecurRuleContainer.js',  { expose: 'gso/eonjs/RecurRuleContainer' });
b.require('./gso/eonjs/Occurrence.js',  { expose: 'gso/eonjs/Occurrence' });

b.bundle().pipe(process.stdout);

快速浏览 CommonJS 以类似于System.import()(请参阅 RrequireJS加载 JavaScript 文件)的方式解析模块 ID 字符串。但是 browserify 需要这个额外的别名步骤。

grunt-browserify任务:

    browserify: {
        options: {  // https://github.com/substack/node-browserify#browserifyfiles--opts
            require: [
                './src/commonjs/build/gso/eonjs/EonJS.js:gso/eonjs/EonJS',
                './src/commonjs/build/gso/eonjs/AbstractRecurRule.js:gso/eonjs/AbstractRecurRule',
                './src/commonjs/build/gso/eonjs/MomentRecurRule.js:gso/eonjs/MomentRecurRule',
                './src/commonjs/build/gso/eonjs/RRuleRecurRule.js:gso/eonjs/RRuleRecurRule',
                './src/commonjs/build/gso/eonjs/RecurRuleContainer.js:gso/eonjs/RecurRuleContainer',
                './src/commonjs/build/gso/eonjs/Occurrence.js:gso/eonjs/Occurrence'
            ]
        },
        debug: {
            debug: true,
            src: './index.js',
            dest: 'src/browserify/eonjs-traceur-debug.js'
        },
    },
于 2015-04-29T11:48:38.280 回答