momentjs是一个好用得不得了的时间组件库,我们最新的React项目中也引入了它。
由于我们强制规定使用Typescript作为前端的编程语言,那么引入moment时的代码是:import moment = require("moment”);
或import * as moment from 'moment’;
初期项目编译正常,运行正常。
而后我为了提高代码质量,引入了Jest做自动化测试,然后就跪了。
项目中一般是用import * as moment from 'moment’
,那么Jest会报:
moment is not a function
而后,若将引用改成:
import moment from 'moment’;
则Jest运行test正常,但是项目运行就会报:
moment_1.default is not a function
总之就是,项目运行和Jest运行测试不能两全,特别难搞。
一番折腾之后,所幸在Github上搜到一个类似的案例:
Importing moment in the TypeScript skeleton either breaks the app or the unit tests,和我的困境一模一样。
其中讲到其中至少两个解法:
方法一:将moment的引用改成:
import * as moment from "moment";
if ((moment as any).default) {
(moment as any) = (moment as any).default;
}
项目与Jest都能正常工作。只是代码丑陋,Tslint通不过。
方法二:使用moment-es6
,而不是moment
包。
import moment from “moment-es6”;
该方法最为简单,改动最小。
再查看这个带es6的模块实现,就一个文件:
declare module "moment-es6" {
import * as moment from "moment";
export default moment;
}
原来如此。
导致moment
在运行时和测试时不能正常工作的原因,是moment
项目对Typescript的支持不好,欠缺Type Definitions,其官方在着手补全,但工程量很大且不是高优先级的事项,官方进度缓慢。各位若有碰到类似问题,采用方法二解决即可。