如何为高阶组件编写类型注释?

时间:2017-09-01 14:21:12

标签: javascript reactjs flowtype

我想为我的react 15.6项目写一个Higher-Order Component,但我不知道如何为它编写类型注释。

我做了一些搜索

1。 The typeof type

喜欢typeof Component

2。功能类型

这对我来说似乎是正确的,因为一个类实际上是一个函数。但是函数的类型应该写成()=>Component<*>吗?在以下代码中,使用any是否正确?它使类型&#34;更广泛&#34;。

 // @flow
    import React, {type Component} from 'react'

    const faded = (componentKlass:()=>{}) => class FadedWrapper
        extends React.Component<any> {
        //...
    }

3。见截图

这看起来并不正确,因为我们需要一个班级,但警告让我想知道*是什么(我也在上面的#2中提出了它的可能用途。 )?

警告说&#34;应用多态类型需求。 (可以使用*表示可推断的那些)&#34;

我猜测,在param应该是Component的某个子类的实例的情况下,flow可以推断出类型。

enter image description here

4。 from TypeScript

建议使用React.ComponentClass

1 个答案:

答案 0 :(得分:2)

感谢@Paolo Moretti在评论中指出the link,已经出现了解决方案。

// @flow
import React from 'react';
import type { ComponentType } from 'react';
import { CSSTransitionGroup } from 'react-transition-group';
import './faded.css';

export const FirstChild = (props: any) => {
  const children = React.Children.toArray(props.children);
  return children[0] || null;
};

const faded = (ComponentKlass: ComponentType<*>) =>
  class extends React.Component<*> {
    render() {
      return (
        <CSSTransitionGroup
          transitionName="fade"
          transitionAppear={false}
          transitionAppearTimeout={1500}
          transitionEnter={true}
          transitionEnterTimeout={500}
          transitionLeaveTimeout={500}
          component={FirstChild}
        >
        {this.props.shouldRender ? 
          <ComponentKlass {...this.props} /> : null}
        </CSSTransitionGroup>
      );
    }
  };

export default faded;

应注意ComponentType应以这种方式导入:import type { ComponentType} from 'react',因为它不是React的属性(默认导出为&#39;反应&#39)。除非我们React.ComponentType,否则我们无法以import * as React from 'react'的方式使用它。

我使用componentKlass代替ComponentKlass,似乎jsx / flow并不介意我们是否使用大写名称作为组件名称。当然通常不应该这样。但是它会在运行时引发错误,例如:

  

警告:未知道具onCancel,cities,shouldRender on tag。

onCancel&amp; cities适用于我的装饰组件。)