我写了一些代码:
function renderGreeting(Elem: React.Component<any, any>) {
return <span>Hello, <Elem />!</span>;
}
我得到一个错误:
JSX元素类型Elem没有任何构造或调用签名
这是什么意思?
我写了一些代码:
function renderGreeting(Elem: React.Component<any, any>) {
return <span>Hello, <Elem />!</span>;
}
我得到一个错误:
JSX元素类型Elem没有任何构造或调用签名
这是什么意思?
当前回答
这是构造函数和实例之间的混淆。
记住,当你在React中编写一个组件时:
class Greeter extends React.Component<any, any> {
render() {
return <div>Hello, {this.props.whoToGreet}</div>;
}
}
你可以这样用:
return <Greeter whoToGreet='world' />;
你不能这样用:
let Greet = new Greeter();
return <Greet whoToGreet='world' />;
在第一个例子中,我们传递了组件的构造函数Greeter。这是正确的用法。在第二个例子中,我们传递了一个Greeter实例。这是不正确的,将在运行时失败,并出现类似“对象不是函数”的错误。
这段代码的问题
function renderGreeting(Elem: React.Component<any, any>) {
return <span>Hello, <Elem />!</span>;
}
它期待一个React.Component的实例。你需要的是一个带有React构造函数的函数。组件:
function renderGreeting(Elem: new() => React.Component<any, any>) {
return <span>Hello, <Elem />!</span>;
}
或类似的:
function renderGreeting(Elem: typeof React.Component) {
return <span>Hello, <Elem />!</span>;
}
其他回答
正如@Jthorpe所提到的,ComponentClass只允许Component或PureComponent,而不允许FunctionComponent。
如果你试图传递一个FunctionComponent, typescript将抛出一个类似于…
Type '(props: myProps) => Element' provides no match for the signature 'new (props: myProps, context?: any): Component<myProps, any, any>'.
但是,通过使用ComponentType而不是ComponentClass,可以同时满足这两种情况。根据react声明文件,类型定义为…
type ComponentType<P = {}> = ComponentClass<P, any> | FunctionComponent<P>
当声明React Class组件时,使用React。ComponentClass而不是React。组件,那么它将修复ts错误。
这是我搜索错误时的第一个结果,所以我想在我的特定情况下分享解决方案:
我正在使用的库是这样的:
export { default as Arc } from './shapes/Arc';
我导入错误,导致错误:
import Arc from "@visx/shape";
它应该是
import { Arc } from "@visx/shape";
如果你真的不关心道具,那么最广泛的可能类型是React.ElementType。
这将允许将原生dom元素作为字符串传递。反应。ElementType涵盖了所有这些:
renderGreeting('button');
renderGreeting(() => 'Hello, World!');
renderGreeting(class Foo extends React.Component {
render() {
return 'Hello, World!'
}
});
我通过在导出组件之前使用Type Assertions来解决这个问题。TypeScript在使用redux 'compose'组合后无法识别,因此我将道具类型分为IParentProps和IProps,并在做类型断言时使用IParentProps
import { compose } from 'react-redux'
import HOC1 from 'HOCs/HOC1'
import HOC2 from 'HOCs/HOC2'
type IParentProps = {}
type IProps = {}
const Component: React.FC<IProps & IParentProps> = React.memo((props) => {
return <SomeComponent {...props}/>
})
return compose(HOC1,HOC2)(Component) as React.FunctionComponent<IParentProps>