klyngbaek klyngbaek - 5 months ago 14
Javascript Question

Can you annotate classes that are not defined with the ES6 class keyword with Facebook's Flow?

I have a lot of legacy ES5 code that does not use the class keyword to define "classes". I would like to annotate and do type checking with Flow. Is that possible?

I've only found examples that use the class keyword:
https://flowtype.org/docs/classes.html#_

Hal Hal
Answer

Since ES5 "classes" are just functions you can most certainly add type annotations for many of the same checks

e.g. this ES6 Class deinition with Flow

class Hello {
  name: string;
  constructor(name: string) {
    this.name = name;
  }

  hello(): string {
    return 'Hello ' + this.name + '!';
  }

  static sayHelloAll(): string {
    return 'Hello everyone!';
  }
}

could be written like this:

function Hello(name: string) {
  this.name = name;
}

Hello.prototype.hello = function hello(): string {
  return 'Hello ' + this.name + '!';
};

Hello.sayHelloAll = function (): string {
  return 'Hello everyone!';
};

though you do miss the extra class property check on name.

More pertinent to your question I suspect, it seems you can check other variables/arguments etc to see if they match your ES5 "Class" by using the constructor function name as a type annotation:

https://flowtype.org/docs/objects.html#constructor-functions-and-prototype-objects

EDIT: Yeah I just tried naively adding an annotation like this:

this.name: string = name;

but flowtype doesn't currently like that. Unless someone knows better I guess the only workaround is something like

const tmpName: string = name;
this.name = tmpName;

though this is obviously not great.