Skip to content
Permalink
Browse files

[React] strictify `React$ComponentType` and `React$ElementType`

Summary:
This takes advantage of the fact that the `Config` type argument to `React$AbstractComponent` is contravariant, and the `Instance` argument is covariant to replace some important `any` types in the react libdefs.

This should have the additional benefit of allowing people to use `React.Element<React.ElementType>` in strict mode instead of `React.Element<any>`.

Reviewed By: jbrown215

Differential Revision: D14549278

fbshipit-source-id: 7043d3f9197eeaa25b343a507f7588561acae24f
  • Loading branch information...
dsainati1 authored and facebook-github-bot committed May 20, 2019
1 parent e952176 commit 59a8fdecff3005fab3e6b4c861eabb0905d34b26
@@ -156,7 +156,7 @@ declare type React$StatelessFunctionalComponent<Props> = {
* - ES6 class component. Components with state defined either using the ES6
* class syntax, or with the legacy `React.createClass()` helper.
*/
declare type React$ComponentType<-Config> = React$AbstractComponent<Config, any>;
declare type React$ComponentType<-Config> = React$AbstractComponent<Config, mixed>;

/**
* The type of an element in React. A React element may be a:
@@ -168,7 +168,7 @@ declare type React$ComponentType<-Config> = React$AbstractComponent<Config, any>
*/
declare type React$ElementType =
| string
| React$AbstractComponent<any, any>;
| React$AbstractComponent<empty, mixed>;

/**
* Type of a React element. React elements are commonly created using JSX
@@ -568,6 +568,42 @@ References:
^^ [1]


Error --------------------------------------------------------------------------------------------------- strict.js:4:11

Cannot create `Component` element because props [1] is incompatible with empty [2].

strict.js:4:11
4| const c = <Component f = {3}/>;
^^^^^^^^^^^^^^^^^^^^ [1]

References:
<BUILTINS>/react.js:171:29
171| | React$AbstractComponent<empty, mixed>;
^^^^^ [2]


Error ---------------------------------------------------------------------------------------------------- strict.js:9:5

Cannot call `foo` with `ref` bound to `a` because:
- `HTMLElement` [1] is incompatible with `React.Component` [2].
- mixed [3] is incompatible with `React.Component` [2].

strict.js:9:5
9| foo(ref);
^^^

References:
<BUILTINS>/react-dom.js:416:13
416| instance: HTMLElement,
^^^^^^^^^^^ [1]
strict.js:7:26
7| declare function foo(a: ?React$Component<any, any>): void;
^^^^^^^^^^^^^^^^^^^^^^^^^ [2]
<BUILTINS>/react.js:171:36
171| | React$AbstractComponent<empty, mixed>;
^^^^^ [3]


Error ------------------------------------------------------------------------------------------------- test_prop.js:5:7

Property `notOnEitherSFCOrClass` is missing in `React.AbstractComponentStatics` [1].
@@ -607,7 +643,7 @@ References:



Found 42 errors
Found 45 errors

Only showing the most relevant union/intersection branches.
To see all branches, re-run Flow with --show-all-branches
@@ -0,0 +1,29 @@
const React = require('react');

declare var Component : React$ElementType;
const c = <Component f = {3}/>;
(c : React$Element<React$ElementType>);

declare function foo(a: ?React$Component<any, any>): void;
declare var ref: ?React$ElementRef<React$ElementType>;
foo(ref);

class Component2 extends React.Component<{}> {};
const d = <Component2/>;
(d: React$Element<React$ElementType>);

type Props = {someProp : string};
type State = {};

class MyComponent extends React.Component<Props, State> {
static _cloneElement(
element: React$Element<React$ElementType>,
): React$Element<React$ElementType> {
const someProp = 'some value';
return React.cloneElement(element, {someProp});
}
}


declare var e : React$Element<Class<Component2>>;
(e : React$Element<React$ElementType>);
@@ -182,7 +182,7 @@ react_component.js:32:29 = {
"kind":"Generic",
"typeArgs":[{"kind":"Bound","bound":"P"}],
"type":{
"provenance":{"kind":"Library","loc":"[LIB] react.js:159:45-80"},
"provenance":{"kind":"Library","loc":"[LIB] react.js:159:45-82"},
"name":"React$ComponentType"
},
"kind":"type alias"

0 comments on commit 59a8fde

Please sign in to comment.
You can’t perform that action at this time.