node.js (ES6 / Babel) 中 import X 和 import * as X 的区别?

IT技术 javascript node.js ecmascript-6 babeljs
2021-01-24 10:41:10

我有一个lib用 ES6 编写的 node.js 库(用Babel编译),我在其中导出了以下子module:

"use strict";

import * as _config from './config';
import * as _db from './db';
import * as _storage from './storage';

export var config = _config;
export var db = _db;
export var storage = _storage;

如果从我的主项目中包含这样的库

import * as lib from 'lib';
console.log(lib);

我可以看到正确的输出并且它按预期工作{ config: ... }但是,如果我尝试包含这样的库:

import lib from 'lib';
console.log(lib);

会的undefined

有人可以解释这里发生了什么吗?这两种导入方法不应该是等效的吗?如果没有,我缺少什么区别?

3个回答
import * as lib from 'lib';

正在请求一个对象,其中包含所有命名为“lib”的导出。

export var config = _config;
export var db = _db;
export var storage = _storage;

被命名为导出,这就是为什么你最终会像你一样得到一个对象。

import lib from 'lib';

要求default出口lib. 例如

export default 4;

会让lib === 4. 它不获取命名的导出。要从默认导出中获取对象,您必须明确地执行

export default {
  config: _config,
  db: _db,
  storage: _storage
};

只是添加到Logan 的解决方案中,因为理解带括号的导入,* 并且没有为我解决问题。

import * as lib from 'lib';

相当于:

import {config, db, storage} as lib from 'lib';

其中 * 类似于导入所有export varfrom lib的通配符

export var config;
export var db;
export var storage;

或者,使用:

import lib from 'lib';

允许您仅访问默认导出:

// lib.js
export default storage;

使用 {} 也仅从module导入特定组件,这减少了 Webpack 等打包程序的占用空间。

尽管:

import storage, { config, db } from './lib'

将导入所有module,包括 export default storage;

请参阅 Dan Abramov 的回答: 何时应使用花括号进行 ES6 导入?

(当然没有扩展/休息语法,因为这不是对象文字/解构)。{…} as …导入中仍然没有语法,因此“相同是没有意义的。(我不认为你的意思是“产生与”相同的语法错误
2021-03-19 10:41:10
没错。为清楚起见更新了答案。我使用“与”相同,因为较小的词更容易理解。为了更具体,我已将其更改为“相当于”。
2021-03-22 10:41:10
但是你能解释一下是什么import {config, db, storage} as lib from 'lib';吗?它没有在任何地方描述
2021-04-03 10:41:10
已编辑。你是对的,{...} 没有展开运算符,我应该使用 etc 来代替。
2021-04-05 10:41:10
只是没有import {…} as … from …语法
2021-04-09 10:41:10

import X from Y; 是一种语法糖。

import lib from 'lib';

等于

import { default as lib } from 'lib';