本文主要参考了react router 的官方文档。html
React Router是一套完整的配合React的路由解决方案,可能你已经知道前端路由,或者知道后端有路由的概念,以下图:
React Router能够帮助咱们将URL与组件状态同步,实现路由。前端
咱们先来看看,不使用React Router的话,动态图中的功能要如何实现:react
var React = require('react'); var About = React.createClass({ render: function () { return( <div> <h2>About</h2> <p>这里将会出现N多介绍文字balabala</p> </div> );} }); var blogs = React.createClass({ render: function () { return( <div> <h2>blogs</h2> <a href="#">文章A</a> <br /> <a href="#">文章B</a> <br /> <a href="#">文章C</a> <br /> <a href="#">文章D</a> </div> );} }); var Home = React.createClass({ render: function () { return( <div> <h2>Home</h2> <p>这里是首页</p> </div> );} }); var App = React.createClass({ render () { var Child; switch (this.props.route) { case 'about': Child = About; break; case 'blogs': Child = blogs; break; default: Child = Home; } return ( <div> <h1>App</h1> <Child/> </div> ) } }); function render () { var route = window.location.hash.substr(1); React.render(<App route={route} />, document.body); } window.addEventListener('hashchange', render); render();
关于react语法细节,请参考博主以前关于react的文章。webpack
每当URL中hash部分改变时,APP组件会渲染一个不一样的Child组件。很是简单明了。
可是,一旦咱们须要再嵌套一些路由,好比 blogs/react,about/communicate,那么 window.location.hash.substr(1);
这样的逻辑就会变的更为复杂,若是再多嵌套一点呢?web
多层嵌套的URL以及多层嵌套的组件结构之间的映射是React router的核心,React Router在路由上使用JSX来声明式编程。编程
var Router = require('react-router'); var Route = Router.Route; // declare our routes and their hierarchy var routes = ( <Route handler={App}> <Route path="about" handler={About}/> <Route path="blogs" handler={blogs}/> </Route> );
咱们如今能够去掉以前switch部分的代码,替换成RouteHandler后端
var RouteHandler = Router.RouteHandler; var App = React.createClass({ render () { return ( <div> <h1>App</h1> <RouteHandler/> </div> ) } });
最后,咱们侦听url的变化,并渲染组件。如下代码将routes渲染到RouteHandler。浏览器
Router.run(routes, Router.HashLocation, (Root) => { React.render(<Root/>, document.body); });
这里写 => 这种ES6会不会引发兼容性问题?大可放心,webpack会帮忙生成浏览器兼容的代码。react-router
全部的Route组件自己都是不会渲染的,它们只是用于配置。ui
咱们来看看如何解决以前说的嵌套问题。
再建立一个组件:
var ReactContent = React.createClass({ render: function () { return( <div> <p>这是一篇React 博文</p> </div> );} });
咱们能够这样写嵌套路由:
var routes = ( <Route path="/" handler={App}> <DefaultRoute handler={Home}/> <Route path="about" handler={About}/> <Route path="blogs" handler={Blogs}> <Route path="react" handler={ReactContent}/> </Route> </Route> );
也能够这样写:
var routes = ( <Route path="/" handler={App}> <DefaultRoute handler={Home}/> <Route path="about" handler={About}/> <Route path="blogs" handler={Blogs}/> <Route path="blogs/react" handler={ReactContent}/> </Route> );
这样固然也是能够的
<Route path="blogs/:id" handler={ReactContent}/>
刚才提到了:id,若是咱们想得到它,怎么作呢?
//没错,直接能够从handler组件的props中拿到。 var id = this.props.params.id;
咱们能够给路由提供默认渲染,好比给跟路由加一个,由它完成用户访问index.html(或者你的主页是其它什么。。。)时的渲染任务。
<Route path="/" handler={App}> <DefaultRoute handler={Home}/> </Route>
URL:xxx#a/b。 假设,a是有路由的,若a/b没有,那么,咱们称之为没法找到路由。请注意区分没法找到路由何没法找到资源的区别。
var NotFound = React.createClass({ render: function () { return( <h1>对不起,咱们找不到路由哦</h1> );} }); <Route path="/" handler={App}> <DefaultRoute handler={Home}/> <Route path="about" handler={About}/> <Route path="blogs" handler={Blogs}/> <Route path="blogs/react" handler={ReactContent}/> <NotFoundRoute handler={NotFound} /> </Route>
本文完。