更新2 根据{{3}}的第二条评论,我可以通过更改来解决我的问题
component: <TestRoute />
到
component: TestRoute
更新 根据{{3}}的评论,我将代码修改为以下代码,并且我遇到的错误已经消失,但是这次我在分配给组件的构造函数中将其替换为新的错误属性:
[加载器]中的错误。/src/ts/components/app/StandardRouter.tsx:34:13 TS2322:类型'Element'不能分配给类型'ComponentClass | FunctionComponent”。 类型“元素”不可分配给类型“功能组件”。 类型'Element'不提供签名'(props:any,context ?: any)的匹配:ReactElement |空”。
StandardRouter.tsx
// React router component. Connects all routes to the application.
import * as React from 'react';
import { connect } from 'react-redux';
import { Route, Switch, withRouter } from 'react-router-dom';
import { ConnectedRouter } from 'connected-react-router';
import { IntlProvider } from 'react-intl';
import _forEach from 'lodash/forEach';
import _find from 'lodash/find';
import { History, createHashHistory } from 'history';
import { connectRouter } from 'connected-react-router';
import reducerRegistry from '../../api/private/core/reducer-registry';
import routeRegistry from '../../api/private/core/route-registry';
import RouteObject from '../../interfaces/route-object';
import TestRoute from '../test/test-route';
class StandardRouter extends React.Component {
constructor(props: object) {
super(props);
this._history = createHashHistory();
reducerRegistry.register({
name: 'router',
key: 'cb3dceb0-367b-4c2a-a0fb-a8d8671283e2',
reducer: connectRouter(this._history)
});
routeRegistry.setChangeListener(() => {
if (this._isMounted) {
this.forceUpdate();
} else if (!this._isMounted && !this._doUpdate) {
this._doUpdate = true;
}
});
routeRegistry.register({
key: '90e8246f-96a6-49a5-920a-a2cf0d347fcd',
component: <TestRoute />, // <-- New error here
paths: '/',
text: 'Test 123'
});
}
componentDidMount(): void {
this._isMounted = true;
if (this._doUpdate) {
this.forceUpdate();
}
}
private _history: History;
private _isMounted: boolean = false;
private _doUpdate: boolean = false;
chooseRender(path: string, Comp: React.ComponentType): React.ReactNode {
return <Comp />;
}
// Creates Route objects based on routes collection from registry
renderPages(): React.ReactNode[] {
const routes: React.ReactNode[] = [];
const loadedRoutes: RouteObject[] = routeRegistry.getRoutes();
_forEach(loadedRoutes, page => {
const Component = withRouter(
connect<any, any, any>(() => ({
pageid: page.pageId
}))(page.component) // <-- Error on this line, on page.component.
);
if (Array.isArray(page.paths)) {
// Multiple paths available for a single route. For example "/" and "/Home" for the
// home page.
_forEach(page.paths, inner => {
routes.push(<Route key={inner} path={inner} render={() => this.chooseRender(inner, Component)} />);
});
} else {
// A single path for a route.
routes.push(
<Route
key={page.paths}
path={page.paths}
render={() => this.chooseRender(page.paths as string, Component)}
/>
);
}
});
return routes;
}
render() {
return (
<div style={{ zIndex: -1 }}>
<IntlProvider locale="en">
<div>
<ConnectedRouter history={this._history}>
<Switch>{this.renderPages()}</Switch>
</ConnectedRouter>
</div>
</IntlProvider>
</div>
);
}
}
export default StandardRouter;
route-object.ts
type RouteObject = {
key: string;
component: React.ComponentType<any>;
paths: string | string[];
text: string;
shortText?: string;
index?: number;
pageId?: string;
icon?: React.ReactNode;
};
export default RouteObject;
test-route.tsx
import React from 'react';
class TestRoute extends React.PureComponent {
render() {
return <div />;
}
}
export default TestRoute;
同样,我不确定为什么无法将,它是PureComponent分配给ComponentType的属性。预先感谢!
下面的原始问题
我正在努力将我们的JavaScript应用程序转换为TypeScript,并且遇到了问题。我仍在尝试掌握所有TypeScript的复杂性。
我们正在运行时动态地将路由路由到redux和路由器。在使用javascript时,这可以正常工作,但是由于我已将其转换为TypeScript,因此无法对其进行编译。我收到的错误是
[加载器]中的错误。/src/ts/components/app/StandardRouter.tsx:63:21 TS2345:无法将类型“ ReactNode”的参数分配给类型“ ComponentType”的参数。 类型'undefined'不能分配给类型'ComponentType'。
我可以看到错误是由无效类型引起的,但是我不确定为什么。
StandardRouter.tsx
// React router component. Connects all routes to the application.
import * as React from 'react';
import { connect } from 'react-redux';
import { Route, Switch, withRouter } from 'react-router-dom';
import { ConnectedRouter } from 'connected-react-router';
import { IntlProvider } from 'react-intl';
import _forEach from 'lodash/forEach';
import _find from 'lodash/find';
import { History, createHashHistory } from 'history';
import { connectRouter } from 'connected-react-router';
import reducerRegistry from '../../api/private/core/reducer-registry';
import routeRegistry from '../../api/private/core/route-registry';
import RouteObject from '../../interfaces/route-object';
import TestRoute from '../test/test-route';
class StandardRouter extends React.Component {
constructor(props: object) {
super(props);
this._history = createHashHistory();
reducerRegistry.register({
name: 'router',
key: 'cb3dceb0-367b-4c2a-a0fb-a8d8671283e2',
reducer: connectRouter(this._history)
});
routeRegistry.setChangeListener(() => {
if (this._isMounted) {
this.forceUpdate();
} else if (!this._isMounted && !this._doUpdate) {
this._doUpdate = true;
}
});
routeRegistry.register({
key: '90e8246f-96a6-49a5-920a-a2cf0d347fcd',
component: <TestRoute />,
paths: '/',
text: 'Test 123'
});
}
componentDidMount(): void {
this._isMounted = true;
if (this._doUpdate) {
this.forceUpdate();
}
}
private _history: History;
private _isMounted: boolean = false;
private _doUpdate: boolean = false;
chooseRender(path: string, Comp: React.ComponentType): React.ReactNode {
return <Comp />;
}
// Creates Route objects based on routes collection from registry
renderPages(): React.ReactNode[] {
const routes: React.ReactNode[] = [];
const loadedRoutes: RouteObject[] = routeRegistry.getRoutes();
_forEach(loadedRoutes, page => {
const Component = withRouter(
connect(() => ({
pageid: page.pageId
}))(page.component) // <-- Error on this line, on page.component.
);
if (Array.isArray(page.paths)) {
// Multiple paths available for a single route. For example "/" and "/Home" for the
// home page.
_forEach(page.paths, inner => {
routes.push(<Route key={inner} path={inner} render={() => this.chooseRender(inner, Component)} />);
});
} else {
// A single path for a route.
routes.push(
<Route
key={page.paths}
path={page.paths}
render={() => this.chooseRender(page.paths as string, Component)}
/>
);
}
});
return routes;
}
render() {
return (
<div style={{ zIndex: -1 }}>
<IntlProvider locale="en">
<div>
<ConnectedRouter history={this._history}>
<Switch>{this.renderPages()}</Switch>
</ConnectedRouter>
</div>
</IntlProvider>
</div>
);
}
}
export default StandardRouter;
route-object.ts
type RouteObject = {
key: string;
component: React.ReactNode;
paths: string | string[];
text: string;
shortText?: string;
index?: number;
pageId?: string;
icon?: React.ReactNode;
};
export default RouteObject;
test-route.tsx
import React from 'react';
class TestRoute extends React.PureComponent {
render() {
return <div />;
}
}
export default TestRoute;
是否有任何东西会导致这种情况?我不确定为什么不使用ReactNode。