之前收到私信很多朋友說react當中的router使用經常報錯。現在總結一下 使用的常規操作希望對你的學習帶來一點幫助
1.package引入
之前的版本中我們習慣性:npm install react-router
版本4后,不再引入react-router,變更為:npm install react-router-dom
目前的react-router-dom最新版本是:4.2.2
2.Router的變更
在3.x版本中的Router里需配置history屬性,當前版本中無需配置此屬性,4.x版本中提供三種不同的路由組件用來代替history屬性的作用,分別是<BrowserRouter>,<HashRouter>,<MemoryRouter>
//3.x版本引入
import{Router,Route, browserHistory} from'react-router';
import routes from'./routes'
<Router history={browserHistory} routes={routes} />
// 或者
<Router history={browserHistory}>
<Route path='/' component={App}>
</Route>
</Router>
//4.2.2版本
import {BrowserRouter,Route}from 'react-router-dom';
<BrowserRouter>
<div>
<Route path='/about' component={About}/>
<Route path='/contact' component={Contact}/>
</div>
</BrowserRouter>
//需要注意的一點是V4中的router組件只能有一個子元素,因此可以在route組件的最外層嵌套一個div
//3.X版本 Route的變更
3.X版本中<Route>實際上并不是一個個組件,而是路由配置對象。
4.x版本中<Route>就是真正的組件了,當基于路徑去渲染一個頁面時,
實際上就是渲染的這個路由組件。因此當輸入正確的路徑時,會渲染該路由的組件,
屬性,子組件,當路徑錯誤時則不會顯示
//在3.x版本中的的元素
<Route path='contact' component={Contact} />
// 相當于
{
path: 'contact',
component: Contact
}
4.路由嵌套
在3.x版本中中通過給<Route>添加子<Route>來嵌套路由
<Route path='parent' component={Parent}>
<Route path='child' component={Child} />
<Route path='other' component={Other} />
</Route>
當輸入正確的<Route>路徑時,react會渲染其與其父組件,子元素將作為父元素的子屬性被傳遞過去。就像下面這樣:
<Parent {...routeProps}>
<Child {...routeProps} />
</Parent>
在4.x版本中子<Route>可以作為父<Route>的component屬性值
<Route path='parent' component={Parent} />
const Parent = () => (
<div>
<Route path='child' component={Child} />
<Route path='other' component={Other} />
</div>
)
5.on*方法的變更
react-router 3.x版本中提供的onEnter,onUpdate,onLeave等方法,貫穿于react生命周期。
在4.x版本中可
使用componentDidMount或componentWillMount來代替onEnter,
使用componentDidUpdate 或 componentWillUpdate來代替onUpdate,
使用componentWillUnmount來代替onLeave。
6.新增<Switch>組件
在3.x版本中,你可以指定很多子路由,但是只有第一個匹配的路徑才會被渲染。
// 3.x版本
<Route path='/' component={App}>
<IndexRoute component={Home} />
<Route path='about' component={About} />
<Route path='contact' component={Contact} />
</Route>
4.x版本中提供了一個相似的方法用來取代<IndexRoute>,那就是<Switch>組件,當一個<Switch>組件被渲染時,react只會渲染Switch下與當前路徑匹配的第一個子<Route>
// 4.x版本
const App = () => (
<Switch>
<Route exact path='/' component={Home} />
<Route path='/about' component={About} />
<Route path='/contact' component={Contact} />
</Switch>
)
7.注解@withRouter
如果當前的組件并非路由組件 也就是并沒有被掛載在react-router上但依然需要使用history對象那么 react-router4.X給我提供了一個注解 @withRouter
import React from 'react';
import ReactDom from 'react-dom';
import {BrowserRouter,Route,Redirect,Switch } from 'react-router-dom';
import Login from './container/login';
import Register from './container/register';
import AuthRoute from './component/AuthRoute'
ReactDom.render(
(<Provider store={store}>
<BrowserRouter>
<div className="container">
<AuthRoute></AuthRoute>//這個組件就用來判斷用戶是否有相對的權限,跳轉到什么頁面,但是并沒有掛載在路由上 按道理來說這個組件使用不了router的history對象 但是react-router-dom 給我們提供了一個注解@withRouter
<Route path='/login' component={Login}></Route>
<Route path='/register' component={Register}></Route>
</div>
</BrowserRouter>
</Provider>
),
document.getElementById("root")
)
- 上面路由組件中的<AuthRoute></AuthRoute>組件就用來判斷用戶是否有相對的權限,跳轉到什么頁面,但是并沒有掛載在路由上 按道理來說這個組件使用不了router的history對象 但是react-router-dom 給我們提供了一個注解@withRouter
//這是一個測試組件但是并未掛載在react-router上
//需求:這個組件是在所有的router
import React from 'react'
import axios from 'axios'
//導入的react-router-dom 提供的withRouter
import {withRouter} from 'react-router-dom'
//加上這個注解之后 及時該組件未被掛載在react-router上也可以使用react-router里的對象history等
@withRouter
class AuthRoute extends React.Component{
componentDidMount(){//conponentDidMount 組件加載完成時觸發
axios.get('/user/info')
.then(res=>{
if(res.status===200){
if(res.data.code===0){
}else{
如果沒加這個注解你會發現答應出來的是undefind
console.log(this.props.history)
}
}
})
}
constructor(props){
super(props)
this.state={
data:''
}
}
render(){
return <p>測試組件</p>
}
}
export default AuthRoute
不定檔期更新 如有問題請留言 或者聯系我的郵箱solitaryhao8@hotmail.com