Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

MomentJS type definition with Typescript 2.0

Alright, my first question on SO, how exciting! :)

I am trying to get MomentJS definitions to work with Typescript 2.0.

I have no issues in getting Angular definitions to work, simply by doing npm install @types/angular --save-dev.

However, MomentJS (2.15.1) already comes with moment.d.ts as part of the package you get when you install it.

If you try to do a similar approach to angular, i.e. npm install @types/moment --save-dev, this is what you get:

npm WARN deprecated @types/[email protected]: This is a stub types definition for Moment (https://github.com/moment/moment). Moment provides its own type definitions, so you don't need @types/moment installed!

And surely enough, if you go to node_modules\@types\moment, there's nothing useful in there.

Yes, I have added the tsconfig.json file on my root folder, so Typescript 2.0 will automatically pick up the @types on node_modules (this is why Angular works fine), but for MomentJS I get the error below (since the .d.ts is not on the place where TS2 expects it to be):

TS2304 Cannot find name 'moment'.

I also tried playing around with the "typeRoots" config on tsconfig.json without any luck.

This is the relevant piece of my package.json:

{
  "devDependencies": {
    "@types/angular": "^1.5.16"
  },
    "dependencies": {
        "moment": "^2.15.1"
    }
}

I am using VS2015, if this matters.

So... Any ideas on how to get Typescript 2.0 to read the type definition for Moment, that sits on an "unexpected" folder?

like image 954
Caio Campos Avatar asked Oct 21 '16 01:10

Caio Campos


3 Answers

You will find the moment.d.ts file under node_modules\moment since it is packaged with the moment itself.

With VS 2017 and TypeScript 2.2, you do not have to specify typeRoots; however, your environment may require specifying two or more of them such as:

typeRoots: [ 'node_modules/@types/', 'node_modules/moment/' ]

^ I forget if each @types subdirectory required an entry in typeRoots.

This is the process I use in VS 2017 and TypeScript 2.2 without any special changes to tsconfig.json (but this stuff changed in more recent versions):

It is automatically found via ES6 style import:

import * as moment from "moment";

This will import the functions named moment as well as the namespace moment merged into a single alias.

If you also want the Moment (return type) imported, perform the following as well:

import { Moment } from "moment";

In the current moment.d.ts (2.18.1), this type is otherwise inaccessible.

In the past I used var moment = require("moment"); but that may not be possible in your setup unless you're running browserify or requirejs to convert the CommonJS/AMD-style require to something the browser supports.

like image 113
Graeme Wicksted Avatar answered Nov 03 '22 02:11

Graeme Wicksted


I found somewhere else (but don't remember where), that you should

change moment.d.ts by replacing export statement with

declare module 'moment' {
   export default moment;
}

add dummy file fixmoment.ts to your project with following line

import * as moment from 'moment';

Compiling with tsc directly now compiles all files. Unfortunately VS2015 still gives an error tsc : error TS2688: Build:Cannot find type definition file for 'moment'. which I don't understand.

like image 42
rekna Avatar answered Nov 03 '22 01:11

rekna


I had same problem. I read this comment and add declare var moment; to custom-typings.d.ts. then it worked fine, but i don't understand why.

VS2015 SP3 + TypeScript2.0.6.0, angular2-webpack-starter based project.

like image 27
tsu1980 Avatar answered Nov 03 '22 02:11

tsu1980