Вопрос с
- как модули ES6 эмулируются в CommonJS
- как вы импортируете модуль
ES6 в CommonJS
На момент написания этой статьи ни одна среда не поддерживала модули ES6 изначально. При использовании их в Node.js вам нужно использовать что-то вроде Babel для преобразования модулей в CommonJS. Но как именно это происходит?
Многие люди считают, module.exports = ...
что эквивалентны export default ...
и exports.foo ...
эквивалентны export const foo = ...
. Это не совсем верно, или, по крайней мере, не так, как это делает Бабель.
default
Экспорт ES6 на самом деле также называется экспортом, за исключением того, что default
это «зарезервированное» имя, и для него существует специальная синтаксическая поддержка. Давайте посмотрим, как Babel компилирует именованные и экспорты по умолчанию:
// input
export const foo = 42;
export default 21;
// output
"use strict";
Object.defineProperty(exports, "__esModule", {
value: true
});
var foo = exports.foo = 42;
exports.default = 21;
Здесь мы видим, что экспорт по умолчанию становится свойством exports
объекта, так же, как foo
.
Импортировать модуль
Мы можем импортировать модуль двумя способами: используя CommonJS или import
синтаксис ES6 .
Ваша проблема: я считаю, что вы делаете что-то вроде:
var bar = require('./input');
new bar();
ожидая, что bar
присваивается значение экспорта по умолчанию. Но, как видно из приведенного выше примера, экспорту по умолчанию присваивается default
свойство!
Таким образом, чтобы получить доступ к экспорту по умолчанию, нам нужно сделать
var bar = require('./input').default;
Если мы используем синтаксис модуля ES6, а именно
import bar from './input';
console.log(bar);
Бабель превратит его в
'use strict';
var _input = require('./input');
var _input2 = _interopRequireDefault(_input);
function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
console.log(_input2.default);
Вы можете видеть, что каждый доступ к bar
конвертируется в доступ .default
.
module.exports
,exports
иmodule.exports
имеют разные значения, поэтому присвоениеexports.defaults
не имеет никакого эффекта (потому чтоmodule.exports
это то , что экспортируется). Другими словами, это точно так же, как если бы вы только сделалиmodule.exports = { ... }
.Вам нужно правильно настроить babel в вашем проекте, чтобы использовать экспорт по умолчанию и экспорт const foo
затем добавьте ниже конфигурацию в .babelrc
источник
Феликс Клинг провел отличное сравнение с этими двумя, для всех, кто интересуется, как сделать экспорт по умолчанию наряду с именованным экспортом с помощью module.exports в nodejs.
источник
tl; dr прямо сейчас, чтобы это работало, требуемый или импортируемый файл
SlimShady
должен быть скомпилирован с помощью Babel'use strict'
.Я использую
babel-cli
6.18.0 в проекте, где я изначально столкнулся с этой ошибкой.Без
'use strict'
плохих новостей Медведи«используйте строгое», пожалуйста
источник
import
объявления, является модулем, и он уже является строгим. Фактическая разница заключается в требовании импорта против.import
вместоrequire
иexport default
вместоexports.default
.