Сегодня я обновился с 1.9.2 до 1.10.2, и для меня миксины больше не работают при использовании require('underscore');
Это не удается с TypeError: _.camelcase is not a function
:
const _ = require('underscore');
const underscoreString = require('underscore.string');
_.mixin(underscoreString.exports());
console.log(_.camelcase('foo-bar'));
но это работает:
import _ from 'underscore';
const underscoreString = require('underscore.string');
_.mixin(underscoreString.exports());
console.log(_.camelcase('foo-bar'));
Сожалею, что это тебя кусает, @dmaicher. Однако я не могу воспроизвести это с помощью Underscore 1.10.2 и underscore.string 3.3.5. Есть ли что-нибудь особенное в вашей настройке?
Спасибо за быстрый ответ: blush:
Я использую [email protected]
и проблема возникает из-за кода, связанного с браузером. Когда я запускаю код с узлом в интерфейсе командной строки, все в порядке: confused:
Вот минимальный репродуктор: https://github.com/dmaicher/underscore_issue_2852
Вот твоя проблема:
Этот путь импорта, underscore/modules/index-all.js
, должен быть получен WebPack из поля module
в нашем package.json
:
тогда как поле main
- это то, что нужно было использовать, учитывая, что вы используете импорт CommonJS. module
- для импорта ES в инструментах, которые его поддерживают, main
- для всех остальных. Это объясняет, почему ваш код работает с import
но не с require()
.
По-видимому, в настоящее время WebPack по умолчанию принимает модули ES, но имеет запасной вариант для импорта CommonJS. Думаю, вам придется как-то настроить его, чтобы не использовать модули ES или игнорировать поле module
. Или, может быть, вы захотите перейти на модули ES.
Я закрываю это сейчас, потому что это проблема WebPack, а не проблема Underscore. Тем не менее, не стесняйтесь продолжать комментировать.
@jgonggrijp спасибо за проверку: +1:
Я смог исправить это, добавив псевдоним для разрешения в конфигурации веб-пакета:
'underscore': 'underscore/underscore.js',
Но мне это кажется немного странным. Многие другие пакеты, которые я использую, указывают "main"
и "module"
внутри своих package.json
и для них это работает нормально.
Webpack берет первое найденное поле в порядке ['browser', 'module', 'main']
См. Https://webpack.js.org/configuration/resolve/#resolvemainfields.
Мне любопытно, почему он не работает только для подчеркивания, но, похоже, работает для других пакетов: blush:
Если вы назовете эти другие пакеты, я буду рад взглянуть. В любом случае, module
и main
не должны быть взаимозаменяемыми, поэтому WebPack рассматривает их как таковые неоправданно:
https://github.com/rollup/rollup/wiki/pkg.module
Документация, с которой вы связались, намекает на, возможно, немного менее уродливое решение, которое заключается в установке resolve.mainFields
на ['main']
. Опять же, я считаю, что WebPack в первую очередь не должен рассматривать module
, поскольку вы используете импорт CommonJS.
На всякий случай вот несколько пакетов, которые я использую, в которых есть как module
и main
:
https://www.npmjs.com/package/vuejs-datepicker
https://www.npmjs.com/package/bootstrap-vue
https://www.npmjs.com/package/acorn
https://www.npmjs.com/package/perfect-scrollbar
Связанная проблема с веб-пакетом: https://github.com/webpack/webpack/issues/5756
Да, это твоя проблема. Хотя также, похоже, что-то не так с тем, как WebPack эмулирует CommonJS при разрешении на module
. Похоже, что он делает что-то вроде этого:
// converting modules/index-all.js to ES3
var underscoreESModule = {
'default': _,
map: _.map,
filter: _.filter,
// ...
};
// in your code that imports underscore
var _ = underscoreESModule;
Последняя строка имела бы смысл, если бы вы делали это:
import * as _ from 'underscore';
но то, что вы на самом деле делаете, эквивалентно этому:
import _ from 'underscore';
и правильный способ перевести это на ES3 в WebPack будет следующим:
var _ = underscoreESModule['default'];
Это как раз та проблема, с которой сталкиваются другие люди в webpack / webpack # 5756.
Другие инструменты сборки, такие как Browserify и Rollup, справляются с этим более разумно. Просто говорю...