我正在应用中生成路由器组件:
render() {
return (
<div className="App container-fluid">
<CharacterProvider>
<Router>
<div>
<Link to="/new">New Character</Link>
<Link to="/load">Load Character</Link>
<Route path="/new" component={NewCharacter} />
<Route path="/load" component={CharacterSheet} />
<Route path="/edit" component={EditCharacter} />
<Route exact path="/" component={MenuImages} />
</div>
</Router>
</CharacterProvider>
</div>
);
}
但是我需要将历史记录推送到提供程序组件中包含的功能中:
import React, {Component} from "react";
import {withRouter} from "react-router-dom";
import CharacterDataService from "../service/CharacterDataService";
const CharacterContext = React.createContext()
const CharacterConsumer = CharacterContext.Consumer
class CharacterProvider extends Component {
constructor(props) {
super(props);
this.state = {
...
getCharacter: this.getCharacter,
}
}
getCharacter = (id) => {
console.log("Getting character...")
CharacterDataService.getCharacterById(id)
.then(
response => {
console.log(response);
this.setState({
...
});
}
);
this.props.history.push('/load');
}
render() {
return (
<CharacterContext.Provider
value={this.state}>
{
this.props.children
}
</CharacterContext.Provider>
)
}
}
export { CharacterContext, CharacterConsumer}
export default withRouter(CharacterProvider)
这样做会导致此堆栈跟踪出错:
tiny-invariant.esm.js:12 Uncaught Error: Invariant failed: You should not use <Route> outside a <Router>
at invariant (tiny-invariant.esm.js:12)
at react-router.js:409
at updateContextConsumer (react-dom.development.js:16085)
at beginWork (react-dom.development.js:16306)
at performUnitOfWork (react-dom.development.js:20285)
at workLoop (react-dom.development.js:20326)
at HTMLUnknownElement.callCallback (react-dom.development.js:147)
at Object.invokeGuardedCallbackDev (react-dom.development.js:196)
at invokeGuardedCallback (react-dom.development.js:250)
at replayUnitOfWork (react-dom.development.js:19509)
at renderRoot (react-dom.development.js:20439)
at performWorkOnRoot (react-dom.development.js:21363)
at performWork (react-dom.development.js:21273)
at performSyncWork (react-dom.development.js:21247)
at requestWork (react-dom.development.js:21102)
at scheduleWork (react-dom.development.js:20915)
at scheduleRootUpdate (react-dom.development.js:21610)
at updateContainerAtExpirationTime (react-dom.development.js:21636)
at updateContainer (react-dom.development.js:21704)
at ReactRoot.push../node_modules/react-dom/cjs/react-dom.development.js.ReactRoot.render (react-dom.development.js:22017)
at react-dom.development.js:22169
at unbatchedUpdates (react-dom.development.js:21492)
at legacyRenderSubtreeIntoContainer (react-dom.development.js:22165)
at Object.render (react-dom.development.js:22240)
at Module../src/index.js (index.js:8)
at __webpack_require__ (bootstrap:781)
at fn (bootstrap:149)
at Object.0 (serviceWorker.js:135)
at __webpack_require__ (bootstrap:781)
at checkDeferredModules (bootstrap:45)
at Array.webpackJsonpCallback [as push] (bootstrap:32)
at main.chunk.js:1
invariant @ tiny-invariant.esm.js:12
(anonymous) @ react-router.js:409
updateContextConsumer @ react-dom.development.js:16085
beginWork @ react-dom.development.js:16306
performUnitOfWork @ react-dom.development.js:20285
workLoop @ react-dom.development.js:20326
callCallback @ react-dom.development.js:147
invokeGuardedCallbackDev @ react-dom.development.js:196
invokeGuardedCallback @ react-dom.development.js:250
replayUnitOfWork @ react-dom.development.js:19509
renderRoot @ react-dom.development.js:20439
performWorkOnRoot @ react-dom.development.js:21363
performWork @ react-dom.development.js:21273
performSyncWork @ react-dom.development.js:21247
requestWork @ react-dom.development.js:21102
scheduleWork @ react-dom.development.js:20915
scheduleRootUpdate @ react-dom.development.js:21610
updateContainerAtExpirationTime @ react-dom.development.js:21636
updateContainer @ react-dom.development.js:21704
push../node_modules/react-dom/cjs/react-dom.development.js.ReactRoot.render @ react-dom.development.js:22017
(anonymous) @ react-dom.development.js:22169
unbatchedUpdates @ react-dom.development.js:21492
legacyRenderSubtreeIntoContainer @ react-dom.development.js:22165
render @ react-dom.development.js:22240
./src/index.js @ index.js:8
__webpack_require__ @ bootstrap:781
fn @ bootstrap:149
0 @ serviceWorker.js:135
__webpack_require__ @ bootstrap:781
checkDeferredModules @ bootstrap:45
webpackJsonpCallback @ bootstrap:32
(anonymous) @ main.chunk.js:1
Show 2 more frames
index.js:1437 The above error occurred in the <Context.Consumer> component:
in Route (created by withRouter(CharacterProvider))
in withRouter(CharacterProvider) (at App.js:41)
in div (at App.js:40)
in App (at src/index.js:8)
我正在做的是使用更改提供者状态的函数-但是,由于该函数用于onClick动作中,因此我还需要根据触发该动作的元素来更改路由。提供者的类不在路由器的结构之外,因此我需要一种在提供者组件中启用历史记录的方法。有比使用withRouter更好的方法来解决问题吗?我怎么用错了?
答案 0 :(得分:1)
由于您的Router
不是withRouter(CharacterProvider)
的父级组件(这是react-router
的要求),因此会出现错误。
尝试更改Router
和CharacterProvider
组件的顺序:
<Router>
<CharacterProvider>
{ /* The rest of your components */ }
</CharacterProvider>
</Router>