react propTypes 组件类?

IT技术 javascript reactjs react-props
2021-04-06 02:57:06

如何验证提供的 prop 是组件类(不是实例)?

例如

export default class TimelineWithPicker extends React.PureComponent {

    static propTypes = {
        component: PropTypes.any, // <-- how can I validate that this is a component class (or stateless functional component)?
    };

    render() {
        return (
            <this.props.component {...this.props} start={this.state.start}/>
        );
    }
}
2个回答

对于在此拉取请求中添加并于20192 月 10 日发布PropTypes >= 15.7.0的新版本的任何人PropTypes.elementType

此 prop 类型支持所有组件(本机组件、无状态组件、有状态组件、前向引用React.forwardRef、上下文提供者/消费者)。

当不是这些元素中的任何一个时,它会发出警告,当传递的props是元素 ( PropTypes.element) 而不是类型时,它也会发出警告

最后,您可以像使用任何其他props类型一样使用它:

const propTypes = {
    component: PropTypes.elementType,
    requiredComponent: PropTypes.elementType.isRequired,
};
如果我理解React 元素什么,这个 prop 类型实际上是非常糟糕的命名: > 人们可能会将元素与更广为人知的“组件”概念混淆。
2021-06-04 02:57:06

编辑:将 React 的FancyButton示例添加到代码和框以及与React.forwardRefReact 16.3 中的新API一起使用的自定义props检查功能React.forwardRefAPI返回一个对象render的功能。我正在使用以下自定义props检查器来验证此props类型。- 感谢 Ivan Samovar 注意到这一需求。

FancyButton: function (props, propName, componentName) {
  if(!props[propName] || typeof(props[propName].render) != 'function') {
    return new Error(`${propName}.render must be a function!`);
  }
}

你会想要使用 PropTypes.element. 实际上......PropType.func适用于无状态功能组件和类组件。

我做了一个沙箱来证明这是有效的......考虑到我一开始给你错误的信息,我认为这是必要的。对此非常抱歉!

工作沙箱示例

这是链接失效时的测试代码:

import React from 'react';
import { render } from 'react-dom';
import PropTypes from "prop-types";

class ClassComponent extends React.Component {
  render() {
    return <p>I'm a class component</p>
  }
}

const FancyButton = React.forwardRef((props, ref) => (
  <button ref={ref} className="FancyButton">
    {props.children}
  </button>
));

// You can now get a ref directly to the DOM button:
const ref = React.createRef();
<FancyButton ref={ref}>Click me!</FancyButton>;

const FSComponent = () => (
    <p>I'm a functional stateless component</p>
);

const Test = ({ ClassComponent, FSComponent, FancyButton }) => (
  <div>
    <ClassComponent />
    <FSComponent />
    <FancyButton />
  </div>
);
Test.propTypes = {
  ClassComponent: PropTypes.func.isRequired,
  FSComponent: PropTypes.func.isRequired,
  FancyButton: function (props, propName, componentName) {
    if(!props[propName] || typeof(props[propName].render) != 'function') {
      return new Error(`${propName}.render must be a function!`);
    }
  },
}

render(<Test
         ClassComponent={ ClassComponent }
         FSComponent={ FSComponent }
         FancyButton={ FancyButton } />, document.getElementById('root'));
不:) 有一个单独的 PropType 。
2021-05-25 02:57:06
@btzr 如果您还没有解决这个问题,请检查更新。我做了一个沙箱,这样你就可以看到这确实有效。我在今天正在做的事情中遇到了这个问题,使用元素并想,“该死……我需要纠正那个”。文档可以使用更新。
2021-05-27 02:57:06
所以关于最初的问题,没有简单的道具类型可以验证任何可能的组件类型
2021-06-04 02:57:06
oneOfType用于不同类型:PropTypes.oneOfType([...])
2021-06-09 02:57:06
不就是个例吗?我认为<Foo>(又名React.createElement(Foo, null))是一个反应元素,而我想检查 raw Foo
2021-06-10 02:57:06