在Angular Typescript库中使用MomentJS时出错

Chr*_*own 16 momentjs typescript angular

我正在使用jvandemo/generator-angular2-library作为启动器构建一个Angular(2+)组件库,它使用Rollup作为模块构建器.我在库中创建的组件使用MomentJS.

包含MomentJS后,我遇到了各种构建问题.

我首先用于import moment from 'moment';将时刻导入组件,但是在构建时会产生以下错误;

[17:26:28] Starting 'ngc'...
Error at /Users/chris/angular-library/.tmp/components/my-library/my-component.component.ts:6:8: Module '"/Users/chris/my-library/node_modules/moment/moment"' has no default export.
Run Code Online (Sandbox Code Playgroud)

我发现这个问题据说可以使用import * as moment from 'moment';我得到的;

'moment' is imported by build/components/my-component.component.js, but could not be resolved – treating it as an external dependency

events.js:182
      throw er; // Unhandled 'error' event
      ^
Error: Cannot call a namespace ('moment')
    at error (/Users/chris/angular-library/node_modules/rollup/dist/rollup.js:185:14)
Run Code Online (Sandbox Code Playgroud)

据我所知,这是唯一的两个选项,我无法工作,我错过了什么?

编辑

我已将此问题添加到库的Github存储库中,其中包含简化复制步骤

Alu*_*dad 29

错误非常明确且具体

错误:无法在出错时调用命名空间('时刻')(/ Users/chris/angular-library/node_modules/rollup/dist/rollup.js:185:14)

这是根据ES模块规范.

这意味着以下是导入时刻或您打算调用的任何内容的无效方法,因为* as ns可能无法调用模块名称空间对象(例如创建的对象).

import * as moment from 'moment';
Run Code Online (Sandbox Code Playgroud)

正确的表单ngc是引发错误的表单

import moment from 'moment';
Run Code Online (Sandbox Code Playgroud)

首先要做到这一点,你需要指定--allowSyntheticDefaultImports标志.

tsconfig.json

{
  "compilerOptions": {
    "allowSyntheticDefaultImports": true
  }
}
Run Code Online (Sandbox Code Playgroud)

假设ngc它将识别该选项,您还有一个问题需要解决.

上面的标志是用于执行综合的SystemJS或Webpack等工具的用户,允许这样的代码进行类型检查.

从TypeScript 2.7开始,您现在可以指定--esModuleInterop标志以使语言提供合成作为转换过程的一部分.

{
  "compilerOptions": {
    "allowSyntheticDefaultImports": true,
    "esModuleInterop": true
  }
}
Run Code Online (Sandbox Code Playgroud)

请注意,如果您使用的是2.7之前的TypeScript版本,并且您正在编译CommonJS,AMD或UMD模块(例如,使用--module commonjs),那么正确的导入语法是

import moment = require('moment');
Run Code Online (Sandbox Code Playgroud)

import = require语法是打字稿特定构建体,现在基本上是不必要的.它的存在是为了获取AMD,CommonJS或UMD模块的模块导出的类型值."和"很重要,因为a const,varlet = require调用只在值空间中创建一个名称,而不是在类型空间中.


PeS*_*PeS 5

无论谁在 2018 年以上发现这个,使用 Angular6 和当前的 @angular/cli:

今天我遇到了这个问题并在这里找到了解决方案

import * as moment_ from 'moment';
const moment = moment_;
Run Code Online (Sandbox Code Playgroud)

现在库对我来说编译正常。