我需要做一些类似的事情:

if (condition) {
    import something from 'something';
}
// ...
if (something) {
    something.doStuff();
}

上面的代码不能编译;它抛出SyntaxError:…“import”和“export”只能出现在顶层。

我尝试使用系统。导入如下所示,但我不知道系统来自哪里。是ES6提案最终没有被接受吗?那篇文章中的“程序化API”链接把我扔到了一个废弃的文档页面。


当前回答

在eval中隐藏它对我有用,在静态分析器中隐藏它……

if (typeof __CLI__ !== 'undefined') {
  eval("require('fs');")
}

其他回答

如果你愿意,你可以使用require。这是一种使用条件require语句的方法。

let something = null;
let other = null;

if (condition) {
    something = require('something');
    other = require('something').other;
}
if (something && other) {
    something.doStuff();
    other.doOtherStuff();
}

看起来答案是,就目前而言,你不能。

http://exploringjs.com/es6/ch_modules.html#sec_module-loader-api

我认为其目的是尽可能地支持静态分析,而有条件地导入模块则打破了这一点。另外值得一提的是——我使用的是Babel,我猜Babel不支持System,因为模块加载器API没有成为ES6标准。

Require()是一种在运行时导入某些模块的方法,如果与字符串文本路径一起使用,它同样有资格进行静态分析。这是捆绑器为捆绑包选择依赖项所必需的。

const defaultOne = require('path/to/component').default;
const NamedOne = require('path/to/component').theName;

对于具有完整静态分析支持的动态模块解析,首先在索引器(index.js)中索引模块,然后在主机模块中导入索引器。

// index.js
export { default as ModuleOne } from 'path/to/module/one';
export { default as ModuleTwo } from 'path/to/module/two';
export { SomeNamedModule } from 'path/to/named/module';

// host.js
import * as indexer from 'index';
const moduleName = 'ModuleOne';
const Module = require(indexer[moduleName]);

我可以使用立即调用的函数和require语句来实现这一点。

const something = (() => (
  condition ? require('something') : null
))();

if(something) {
  something.doStuff();
}

看一下这个例子,可以清楚地理解动态导入是如何工作的。

动态模块导入示例

对导入和导出模块有基本的了解。

JavaScript模块Github

Javascript模块MDN