Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to specify a Moment.js object annotation in Flow

Tags:

I'm currently learning Flow by applying it to an existing project and looking to annotate function parameters as a Moment.JS objects.

Using flow-typed I was able to install a library definition for Moment.JS which appears to have the type I'm looking for:

declare class moment$Moment {   static ISO_8601: string;   static (string?: string, format?: string|Array<string>, locale?: string, strict?: bool): moment$Moment;   static (initDate: ?Object|number|Date|Array<number>|moment$Moment|string): moment$Moment;   static unix(seconds: number): moment$Moment;   static utc(): moment$Moment;   ... 

However when I try to annotate function parameters as Moment.JS objects, Flow fails to recognize them as such. In the following function startDate and endDate are Moment.JS date objects.

const filterByDateWhereClause = (startDate: Moment, endDate: Moment): string => {...}; 

Flow gives the following error:

const filterByDateWhereClause = (startDate: Moment, endDate: Moment): string =>                                                  ^^^^^^ identifier `Moment`. Could not resolve name 

Is this even possible with Flow? Or do I need to duplicate the type for the Moment.JS object identical to the one in the library definition provided by flow-type? I'd prefer not to do this as the libdef is fairly lengthy.

For example:

declare class Moment {   static ISO_8601: string;   static (string?: string, format?: string|Array<string>, locale?: string, strict?: bool): moment$Moment;   static (initDate: ?Object|number|Date|Array<number>|moment$Moment|string): moment$Moment;   static unix(seconds: number): moment$Moment;   static utc(): moment$Moment;   ...  const filterByDateWhereClause = (startDate: Moment, endDate: Moment): string => {...}; 

What am I missing?

like image 661
clhenrick Avatar asked Mar 27 '17 01:03

clhenrick


People also ask

How do you define a moment in JavaScript?

Creating a moment object with a specific date and time is possible by calling the moment() function with arguments. Like the JavaScript Date, a moment object can be created from the number of milliseconds since 1970/1/1. Another possibility is using an array [year, month, day, hour, minute, second, milliseconds] .

How do I get the current time in MomentJS?

To get the current date and time, just call javascript moment() with no parameters like so: var now = moment(); This is essentially the same as calling moment(new Date()) .

Is MomentJS still used?

Conclusion. MomentJS isn't completely gone yet. But on their website they suggest you look beyond Moment unless you fall into specific usecases. Luxon seems to be the biggest replacement for Moment that is futureproof for now.

Is JavaScript moment immutable?

The moment object in Moment. js is mutable. This means that operations like add, subtract, or set change the original moment object.


1 Answers

There are three ways to get the type you want.

If your file already require's moment as a module you should be able to use that type

import moment from 'moment';  const filterByDateWhereClause = (startDate: moment, endDate: moment): string => {...}; 

or if you don't use the source but just the type within your file.

import type Moment from 'moment';  const filterByDateWhereClause = (startDate: Moment, endDate: Moment): string => {...}; 

You can do this because that's what the libdef specifies as the module export: https://github.com/flowtype/flow-typed/blob/7822da72587078a4b8e0f2b56746d0da41a3ddde/definitions/npm/moment_v2.x.x/flow_v0.34.x-/moment_v2.x.x.js#L233

Alternatively, it looks like that libdef declares a type moment$Moment in the global namespace too so you can use that.

const filterByDateWhereClause = (startDate: moment$Moment, endDate: moment$Moment): string => {...}; 

I wouldn't recommend the global usage though since it's less explicit where the type is coming from.

like image 169
Lewis Chung Avatar answered Sep 21 '22 12:09

Lewis Chung