反应路由器-dom v4 |上下文路由器和路由未定义
react-router-dom v4 | Context Router and Route Undefined
我正在 运行ning react-router-dom 4.1.1,我遵循了多个 React Router 指南,甚至做了在我的电脑上运行的 react-router-tutorial(虽然它正在使用 react-router v2 或类似的东西)。当我尝试在一个简单的应用程序上使用 react-router-dom v4 时,我 运行 遇到了很多错误。
向下滚动查看 当前代码和错误
//index.js
import React from 'react';
import ReactDOM from 'react-dom';
import {BrowserRouter as Router, Route, Switch} from 'react-router-dom';
import createBrowserHistory from 'history/createBrowserHistory'
import App from './components/App';
import About from './components/pages/about';
const customHistory = createBrowserHistory()
ReactDOM.render((
<Router history={customHistory}>
<Switch>
<Route path='/' component={App} />
<Route path='/about' component={About}/>
</Switch>
</Router>
), document.getElementById('root'))
此代码单独工作并呈现我的 'App' 组件
但是当我尝试在我的 App 组件中添加一个 'Link' 组件时,它无法识别它。
//App.js
import React from 'react';
import Header from './Header';
import { Link } from 'react-router-dom'
class App extends React.Component {
render() {
return (
<div className="App">
<Header className="Header" header="Header" />
<main className='main'>
<Link to='about'>About</Link>
</main>
</div>
);
}
}
export default App;
如果我运行这个,我得到错误:
TypeError: Cannot read property 'history' of undefined
at Link.render (/Users/Ryan/Desktop/df/grnd/node_modules/react-router-dom/Link.js:76:35)
at /Users/Ryan/Desktop/df/grnd/node_modules/react-dom/lib/ReactCompositeComponent.js:795:21
at measureLifeCyclePerf (/Users/Ryan/Desktop/df/grnd/node_modules/react-dom/lib/ReactCompositeComponent.js:75:12)
at ReactCompositeComponentWrapper._renderValidatedComponentWithoutOwnerOrContext
(/Users/Ryan/Desktop/df/grnd/node_modules/react-dom/lib/ReactCompositeComponent.js:794:25)
at ReactCompositeComponentWrapper._renderValidatedComponent (/Users/Ryan/Desktop/df/grnd/node_modules/react-dom/lib/ReactCompositeComponent.js:821:32)
at ReactCompositeComponentWrapper.performInitialMount (/Users/Ryan/Desktop/df/grnd/node_modules/react-dom/lib/ReactCompositeComponent.js:361:30)
at ReactCompositeComponentWrapper.mountComponent (/Users/Ryan/Desktop/df/grnd/node_modules/react-dom/lib/ReactCompositeComponent.js:257:21)
at Object.mountComponent (/Users/Ryan/Desktop/df/grnd/node_modules/react-dom/lib/ReactReconciler.js:45:35)
at ReactDOMComponent.mountChildren (/Users/Ryan/Desktop/df/grnd/node_modules/react-dom/lib/ReactMultiChild.js:236:44)
at ReactDOMComponent._createContentMarkup (/Users/Ryan/Desktop/df/grnd/node_modules/react-dom/lib/ReactDOMComponent.js:659:32)
如果我注释掉 App.js 中的 'Link' 组件,程序 运行 会从 index.js 加载 'App'。
这只是我收到的许多错误中的一个,因为我试图弄清楚为什么我不能 运行 它。我还收到错误消息,其中显示 'Route' 未定义或 'Router' 不能嵌套子项等等。我发现这个问题最简单。
我在这个例子中使用的历史是从给出的例子中提取的:
https://reacttraining.com/react-router/web/api/Router/history-object
首先,你使用一个BrowserRouter,这个创建它自己的历史对象并使用这个。因此,在您的情况下,您不应该将历史对象传递给它。实际上,在我查看 BrowserRouter 的代码后,它甚至应该在你的控制台中打印一条警告。如果我是你,我会把它命名为 BrowserRouter,这样当你阅读代码时它更不容易出错并且更清晰。
那么在v4中,Router只能有1个child。但在 Switch 的情况下,它实际上只挂载匹配的路由。我不确定它是否打算像这样,尝试将您的层次结构更改为不同的东西,并始终安装 Router 的子级。这是一个使用您的代码的示例:
//index.js
import React from 'react';
import ReactDOM from 'react-dom';
import {BrowserRouter, Route, Switch} from 'react-router-dom';
import App from './components/App';
ReactDOM.render((
<BrowserRouter>
<App />
</BrowserRouter>
), document.getElementById('root'));
然后在您的 App 中构建您的路由逻辑,这更有意义,因为您的 App 可能就是应用程序,因此它应该始终存在。
//App.js
import React from 'react';
import Header from './Header';
class App extends React.Component {
render() {
return (
<div className="App">
<Header className="Header" header="Header" />
<Switch>
<Route exact path='/' component={Home} />
<Route path='/about' component={About}/>
</Switch>
</div>
);
}
}
我想您的链接可能位于页眉内,或者您可能希望为此构建一个特殊的导航组件,该组件可能包含在页眉或其他地方。现在让我们在页眉中执行此操作,看看它是如何工作的:
//Header.js
import React from 'react';
import {Link} from 'react-router-dom';
class Header extends React.Component {
render() {
return (
<header className="header">
<Link to='/'>Home</Link>
<Link to='/about'>About</Link>
</header >
);
}
}
当前代码
//index.js
import React from 'react';
import ReactDOM from 'react-dom';
import { BrowserRouter } from 'react-router-dom';
import App from './components/App';
ReactDOM.render((
<BrowserRouter>
<App/>
</BrowserRouter>
), document.getElementById('root'))
//App.js
import React from 'react';
import Header from './Header';
import Main from './Main';
class App extends React.Component {
render() {
return (
<div className="App">
<Header className="Header" header="Header" />
<Main className="Main" />
</div>
);
}
}
export default App;
//Main.js
import React from 'react';
import { Switch, Route } from 'react-router-dom'
import Home from './Home';
import About from './About';
class Main extends React.Component {
render() {
return (
<div className='Main-Container'>
<Switch>
<Route exact path='/' component={Home} />
<Route path='/about' component={About} />
</Switch>
</div>
)
}
}
export default Main;
最近的错误
Warning: Failed context type: The context router
is marked as
required in Switch
, but its value is undefined
.
in Switch (created by Main)
in div (created by Main)
in Main (created by App)
in div (created by App)
in App TypeError: Cannot read property 'route' of undefined
at Switch.render (/Users/Ryan/Desktop/df/grnd/node_modules/react-router/Switch.js:48:36)
at /Users/Ryan/Desktop/df/grnd/node_modules/react-dom/lib/ReactCompositeComponent.js:795:21
at measureLifeCyclePerf (/Users/Ryan/Desktop/df/grnd/node_modules/react-dom/lib/ReactCompositeComponent.js:75:12)
at ReactCompositeComponentWrapper._renderValidatedComponentWithoutOwnerOrContext
(/Users/Ryan/Desktop/df/grnd/node_modules/react-dom/lib/ReactCompositeComponent.js:794:25)
at ReactCompositeComponentWrapper._renderValidatedComponent (/Users/Ryan/Desktop/df/grnd/node_modules/react-dom/lib/ReactCompositeComponent.js:821:32)
at ReactCompositeComponentWrapper.performInitialMount (/Users/Ryan/Desktop/df/grnd/node_modules/react-dom/lib/ReactCompositeComponent.js:361:30)
at ReactCompositeComponentWrapper.mountComponent (/Users/Ryan/Desktop/df/grnd/node_modules/react-dom/lib/ReactCompositeComponent.js:257:21)
at Object.mountComponent (/Users/Ryan/Desktop/df/grnd/node_modules/react-dom/lib/ReactReconciler.js:45:35)
at ReactDOMComponent.mountChildren (/Users/Ryan/Desktop/df/grnd/node_modules/react-dom/lib/ReactMultiChild.js:236:44)
at ReactDOMComponent._createContentMarkup (/Users/Ryan/Desktop/df/grnd/node_modules/react-dom/lib/ReactDOMComponent.js:659:32)
我找出了导致错误的原因:服务器渲染
目前我正在使用这段代码
//server.js
server.get('/', (req, res) => {
res.render('index', {
content: ReactDOMServer.renderToString(<App />)
});
});
呈现到我的 ejs 模板
//index.ejs
<%- include('header') -%>
<div id="root"><%- content -%></div>
<%- include('footer') -%>
当我注释掉 content: ReactDOMServer.renderToString(<App />)
并将其切换为类似 content: 'Hello'
.... <Route/>
和 <Link/>
工作。
我正在 运行ning react-router-dom 4.1.1,我遵循了多个 React Router 指南,甚至做了在我的电脑上运行的 react-router-tutorial(虽然它正在使用 react-router v2 或类似的东西)。当我尝试在一个简单的应用程序上使用 react-router-dom v4 时,我 运行 遇到了很多错误。
向下滚动查看 当前代码和错误
//index.js
import React from 'react';
import ReactDOM from 'react-dom';
import {BrowserRouter as Router, Route, Switch} from 'react-router-dom';
import createBrowserHistory from 'history/createBrowserHistory'
import App from './components/App';
import About from './components/pages/about';
const customHistory = createBrowserHistory()
ReactDOM.render((
<Router history={customHistory}>
<Switch>
<Route path='/' component={App} />
<Route path='/about' component={About}/>
</Switch>
</Router>
), document.getElementById('root'))
此代码单独工作并呈现我的 'App' 组件
但是当我尝试在我的 App 组件中添加一个 'Link' 组件时,它无法识别它。
//App.js
import React from 'react';
import Header from './Header';
import { Link } from 'react-router-dom'
class App extends React.Component {
render() {
return (
<div className="App">
<Header className="Header" header="Header" />
<main className='main'>
<Link to='about'>About</Link>
</main>
</div>
);
}
}
export default App;
如果我运行这个,我得到错误:
TypeError: Cannot read property 'history' of undefined at Link.render (/Users/Ryan/Desktop/df/grnd/node_modules/react-router-dom/Link.js:76:35) at /Users/Ryan/Desktop/df/grnd/node_modules/react-dom/lib/ReactCompositeComponent.js:795:21 at measureLifeCyclePerf (/Users/Ryan/Desktop/df/grnd/node_modules/react-dom/lib/ReactCompositeComponent.js:75:12) at ReactCompositeComponentWrapper._renderValidatedComponentWithoutOwnerOrContext (/Users/Ryan/Desktop/df/grnd/node_modules/react-dom/lib/ReactCompositeComponent.js:794:25) at ReactCompositeComponentWrapper._renderValidatedComponent (/Users/Ryan/Desktop/df/grnd/node_modules/react-dom/lib/ReactCompositeComponent.js:821:32) at ReactCompositeComponentWrapper.performInitialMount (/Users/Ryan/Desktop/df/grnd/node_modules/react-dom/lib/ReactCompositeComponent.js:361:30) at ReactCompositeComponentWrapper.mountComponent (/Users/Ryan/Desktop/df/grnd/node_modules/react-dom/lib/ReactCompositeComponent.js:257:21) at Object.mountComponent (/Users/Ryan/Desktop/df/grnd/node_modules/react-dom/lib/ReactReconciler.js:45:35) at ReactDOMComponent.mountChildren (/Users/Ryan/Desktop/df/grnd/node_modules/react-dom/lib/ReactMultiChild.js:236:44) at ReactDOMComponent._createContentMarkup (/Users/Ryan/Desktop/df/grnd/node_modules/react-dom/lib/ReactDOMComponent.js:659:32)
如果我注释掉 App.js 中的 'Link' 组件,程序 运行 会从 index.js 加载 'App'。
这只是我收到的许多错误中的一个,因为我试图弄清楚为什么我不能 运行 它。我还收到错误消息,其中显示 'Route' 未定义或 'Router' 不能嵌套子项等等。我发现这个问题最简单。
我在这个例子中使用的历史是从给出的例子中提取的: https://reacttraining.com/react-router/web/api/Router/history-object
首先,你使用一个BrowserRouter,这个创建它自己的历史对象并使用这个。因此,在您的情况下,您不应该将历史对象传递给它。实际上,在我查看 BrowserRouter 的代码后,它甚至应该在你的控制台中打印一条警告。如果我是你,我会把它命名为 BrowserRouter,这样当你阅读代码时它更不容易出错并且更清晰。
那么在v4中,Router只能有1个child。但在 Switch 的情况下,它实际上只挂载匹配的路由。我不确定它是否打算像这样,尝试将您的层次结构更改为不同的东西,并始终安装 Router 的子级。这是一个使用您的代码的示例:
//index.js
import React from 'react';
import ReactDOM from 'react-dom';
import {BrowserRouter, Route, Switch} from 'react-router-dom';
import App from './components/App';
ReactDOM.render((
<BrowserRouter>
<App />
</BrowserRouter>
), document.getElementById('root'));
然后在您的 App 中构建您的路由逻辑,这更有意义,因为您的 App 可能就是应用程序,因此它应该始终存在。
//App.js
import React from 'react';
import Header from './Header';
class App extends React.Component {
render() {
return (
<div className="App">
<Header className="Header" header="Header" />
<Switch>
<Route exact path='/' component={Home} />
<Route path='/about' component={About}/>
</Switch>
</div>
);
}
}
我想您的链接可能位于页眉内,或者您可能希望为此构建一个特殊的导航组件,该组件可能包含在页眉或其他地方。现在让我们在页眉中执行此操作,看看它是如何工作的:
//Header.js
import React from 'react';
import {Link} from 'react-router-dom';
class Header extends React.Component {
render() {
return (
<header className="header">
<Link to='/'>Home</Link>
<Link to='/about'>About</Link>
</header >
);
}
}
当前代码
//index.js
import React from 'react';
import ReactDOM from 'react-dom';
import { BrowserRouter } from 'react-router-dom';
import App from './components/App';
ReactDOM.render((
<BrowserRouter>
<App/>
</BrowserRouter>
), document.getElementById('root'))
//App.js
import React from 'react';
import Header from './Header';
import Main from './Main';
class App extends React.Component {
render() {
return (
<div className="App">
<Header className="Header" header="Header" />
<Main className="Main" />
</div>
);
}
}
export default App;
//Main.js
import React from 'react';
import { Switch, Route } from 'react-router-dom'
import Home from './Home';
import About from './About';
class Main extends React.Component {
render() {
return (
<div className='Main-Container'>
<Switch>
<Route exact path='/' component={Home} />
<Route path='/about' component={About} />
</Switch>
</div>
)
}
}
export default Main;
最近的错误
Warning: Failed context type: The context
router
is marked as required inSwitch
, but its value isundefined
. in Switch (created by Main) in div (created by Main) in Main (created by App) in div (created by App) in App TypeError: Cannot read property 'route' of undefined at Switch.render (/Users/Ryan/Desktop/df/grnd/node_modules/react-router/Switch.js:48:36) at /Users/Ryan/Desktop/df/grnd/node_modules/react-dom/lib/ReactCompositeComponent.js:795:21 at measureLifeCyclePerf (/Users/Ryan/Desktop/df/grnd/node_modules/react-dom/lib/ReactCompositeComponent.js:75:12) at ReactCompositeComponentWrapper._renderValidatedComponentWithoutOwnerOrContext (/Users/Ryan/Desktop/df/grnd/node_modules/react-dom/lib/ReactCompositeComponent.js:794:25) at ReactCompositeComponentWrapper._renderValidatedComponent (/Users/Ryan/Desktop/df/grnd/node_modules/react-dom/lib/ReactCompositeComponent.js:821:32) at ReactCompositeComponentWrapper.performInitialMount (/Users/Ryan/Desktop/df/grnd/node_modules/react-dom/lib/ReactCompositeComponent.js:361:30) at ReactCompositeComponentWrapper.mountComponent (/Users/Ryan/Desktop/df/grnd/node_modules/react-dom/lib/ReactCompositeComponent.js:257:21) at Object.mountComponent (/Users/Ryan/Desktop/df/grnd/node_modules/react-dom/lib/ReactReconciler.js:45:35) at ReactDOMComponent.mountChildren (/Users/Ryan/Desktop/df/grnd/node_modules/react-dom/lib/ReactMultiChild.js:236:44) at ReactDOMComponent._createContentMarkup (/Users/Ryan/Desktop/df/grnd/node_modules/react-dom/lib/ReactDOMComponent.js:659:32)
我找出了导致错误的原因:服务器渲染
目前我正在使用这段代码
//server.js
server.get('/', (req, res) => {
res.render('index', {
content: ReactDOMServer.renderToString(<App />)
});
});
呈现到我的 ejs 模板
//index.ejs
<%- include('header') -%>
<div id="root"><%- content -%></div>
<%- include('footer') -%>
当我注释掉 content: ReactDOMServer.renderToString(<App />)
并将其切换为类似 content: 'Hello'
.... <Route/>
和 <Link/>
工作。