reactjs - 如何在 React Typescript 中绑定 match?
我有这段代码:
...
import { match, RouteComponentProps } from "react-router";
import * as H from 'history';
interface oneRoute {
path: string;
exact?: boolean;
main: any;
}
interface ITestProps {
id: string;
}
class Test extends React.Component<RouteComponentProps<ITestProps>, {}> {
public render() {
return <div>Hallow id:{this.props.match.params.id} -- {JSON.stringify(this.props.match)}</div>
}
}
export const routesData: oneRoute[] = [
{
path: '/',
exact: true,
main: (match: match<any>, location: H.Location, history: H.History) => <Home match={match} location={location} history={history} />
},
{
path: '/test/:id',
exact: false,
main: (match: match<ITestProps>, location: H.Location, history: H.History) => <Test match={match} location={location} history={history} />
}
]
export const routes = <Layout>
{
routesData.map((route, index) => {
return <Route exact={route.exact} key={index} path={route.path} component={route.main} />;
})
}
</Layout>;
我在链接 "/test/12" 的测试中有一个错误。
未捕获的类型错误:无法读取未定义的属性 'id'。
如果我注释掉 this.props.match.params.id,JSON.stringify(this.props.match) 显示 "match":{"path":"/test/:id","url":"/test/12","isExact":true,"params":{"id":"12"}},所以是有 params.id 的。怎么会这样,以及如何解决获取 this.props.match.params.id 的问题?
答案#1
你在这里的设置方式是,你的组件 Test 会得到一个名为 match 的参数,它有一个名为 match 的 属性,这个属性包含你想要的实际对象(this.props.match.match.params.id)。
你告诉你的 Route 要渲染的 component 是:
(match: match<ITestProps>, location: H.Location, history: H.History) => <Test match={match} location={location} history={history} />
组件只会被调用一次参数,该参数是一个 props 对象。在运行时,这里的变量 match 并不是 match<ITestProps>,而是整个 RouteComponentProps 对象。
当设置 component={route.main} 时,Typescript 不会对此发出警告,因为 route.main 的类型是 any,所以默认认为它是兼容的。
在你的界面中更加具体:
interface oneRoute {
path: string;
exact?: boolean;
main: React.ComponentType<RouteComponentProps<any>>;
}
你可以让 main 成为一个函数,该函数解构属性 match、location 和 history 并将它们传递给组件,但鉴于你没有更改任何属性,这实际上没有意义。main 可以直接就是组件本身。
export const routesData: oneRoute[] = [
{
path: '/',
exact: true,
main: Home,
},
{
path: '/test/:id',
exact: false,
main: Test,
}
]
