问题在于教程使用了无效的 ESM -> CommonJS 互操作。请改用import $ from jQuery;。在 ECMAScript 中调用命名空间导入 (* as) 无效。
TLDR:写
import $ from 'jquery';
import 'bootstrap-daterangepicker';
并设置--allowSyntheticDefaultImports("allowSyntheticDefaultImports": true in "compilerOptions")以便 TypeScript 正确使用合成的默认导入对代码进行类型检查。
我也在文章中添加了a comment to that effect。
详情:
基本上,ECMASCript 规范禁止将Module Namespace Objects 作为函数调用。当你使用语法时
import * as imported from 'some-module';
创建了一个名为 imported 的模块命名空间对象。此对象公开指定模块的每个导出以进行合格访问,例如imported.a,其中a 由'some-module' 导出。但是,在仅导出单个值的 AMD 或 CommonJS 模块中,通常将此值导出为 模块本身。这通常写成
// AMD
define(function () {
const $ = {...}; // jquery implementation
return $;
});
或者
// CommonJS
const $ = {...}; // jquery implementation
module.exports = $;
define 返回的值或分配给module.exports 的值代表模块本身。
要导入这样的导出,通常会这样写
// AMD
define(["jquery"], function ($) {
$('div').text('set via jQuery');
});
或者
// CommonJS
const $ = requere("jquery");
$('div').text('set via jQuery');
将其与通常写为的命名导出进行比较
// AMD
define(function () {
const $ = {...}; // jquery implementation
return {$};
});
或者
// CommonJS
const $ = {...}; // jquery implementation
module.exports.$ = $;
要导入这样的导出,通常会这样写
// AMD
define(["jquery"], function ($) {
$.$('div').text('set via jQuery');
});
或者
// CommonJS
const $ = require("jquery");
$.$('div').text('set via jQuery');
现在回到 ES 模块世界,* as 语法将命名的导出绑定聚合到一个对象中,以进行点 (.) 访问。
与 AMD 和 CommonJS 模块形成鲜明对比的是,在 ES 模块中,导出的所有内容都必须以 名称 导出。
然而,在 ES 模块中仍然通过 default 导出/导入语法和语义提供了导出和导入表示模块本身的单个值的实用性和简单性。该语法是
// ESM
const something = {...};
export default $;
并且通常被用作
// ESM
import $ from 'some-module';
这在概念上类似于分配给 module.exports 或从 define 返回单个值,但实际上,default 不是匿名的,它是一个导出命名 default。
所以问题就变成了,当我们有一个 AMD 或 CommonJS 模块导出一个值 as 模块本身(通常使用上述模式之一)时,我们如何将它导入到 ES模块? require 对我们不可用。我们不能导入没有名称的东西。很好的互操作,虽然有些变化是使module.exports 的值或define 返回的值作为default 导出可用。这带来了许多问题,但它允许我们编写
import $ from 'jquery';
这是可行的,因为 default 只是一个名为 default 的导出可以被调用。不能调用命名空间。
不幸的是,由于 ES 模块规范的波动、每次指定互操作机制的不确定性以及各种历史原因,TypeScript 在历史上走上了不同的道路,采取了
import * as imported from 'some-module';
暗示
const imported = require('some-module');
在类型级别。此外,它尚未自动提供导出为 AMD 和 CommonJS 模块的值作为 default,这意味着正确的语法可能在运行时失败。
然而,TypeScript 正在解决这个问题。
同时,如果你使用 SystemJS 或 Webpack 3 等模块互操作感知工具,你可以正确编写
import imported from 'some-module';
今天在 TypeScript 中。
指定 --allowSyntheticDefaultImports 编译器选项,以针对 AMD 或 CommonJS 模块启用此语法的正确类型检查。