美文网首页
React-Router-v4 (2)实用技巧

React-Router-v4 (2)实用技巧

作者: 风之化身呀 | 来源:发表于2018-05-27 16:14 被阅读178次

1、与 v3 的差异

v3 的特点:

  • 路由配置集中在一个地方
  • 布局和页面嵌套是由<Route>组件的嵌套派生而来的
    v4 的特点:
  • 不提倡将路由配置集中,而是分散化
  • Route直接参与布局和页面嵌套
  • Route本身就是组件
  • Route 代替 props.children 实现嵌套

2、V4 的一些特性

  • 包容路由(Inclusive Routing)
      <Route path="/"  component={HomePage} />
      <Route path="/users" component={UsersPage} />

当访问/users,HomePage 和 UserPage 都会被渲染

  • 独占路由(Exclusive Routing)
    可以使用switch组件来实现v3式的独占路由,为了避免包容路由的规则,仍需使用exact
const PrimaryLayout = () => (
  <div className="primary-layout">
    <PrimaryHeader />
    <main>
      <Switch>
        <Route path="/" exact component={HomePage} />                // 使用exact来精准匹配
        <Route path="/users/add" component={UserAddPage} />     // /users/add 放在 /users前面就可以避免对/users使用exact
        <Route path="/users" component={UsersPage} />                 // /users 放在 /users/add后面就可以避免对/users使用exact
        <Redirect to="/" />                                                                   // 都不匹配时,走 redirect
      </Switch>
    </main>
  </div>
)

3、一些技巧

  • 嵌套
    子路由中用this.props.match.path来获取父路由的匹配规则
<Switch>
        <Route path={props.match.path} exact component={BrowseUsersPage} />
        <Route path={`${props.match.path}/:userId`} component={UserProfilePage} />
</Switch>
  • 指定参数类型(/:userId(\d+))
<Route path={`/users/:userId(\\d+)`} component={UserProfilePage} />   // /users/edit 不会匹配,/users/123才会匹配
  • <Link> & <NavLink>
    功能一样,只是navlink组件可更加方便定制激活时的样式
  • match & history 常用属性
    match.params.XX
    match.path // 用于嵌套 Routes
    match.url // 用于嵌套 Links
    history.push
  • URL Query Strings
    v4里不能直接获取类似hash或者query string这样的参数,可以使用这个三方库 query-string
// 1、取查询字符串
const parsed = queryString.parse(location.search);  // location.search='?foo=bar'
console.log(parsed);    //  {foo: 'bar'}

// 2、取hash
const parsedHash = queryString.parse(location.hash);  // location.hash = '#token=bada55cafe'
console.log(parsedHash);  // {token: 'bada55cafe'}
// 3、制作location.search
parsed.foo = 'unicorn';
parsed.ilike = 'pizza';
const stringified = queryString.stringify(parsed);      //  'foo=unicorn&ilike=pizza'
location.search = stringified;
// note that `location.search` automatically prepends a question mark
console.log(location.search);       //  '?foo=unicorn&ilike=pizza'
  • 布局上
    当应用里有登录这种逻辑时,最好将登录和主应用分离,将其作为两个顶级路由
class App extends React.Component {
  render() {
    return (
      <Provider store={store}>
        <BrowserRouter>
          <Switch>
            <Route path="/auth" component={UnauthorizedLayout} />
            <AuthorizedRoute path="/app" component={PrimaryLayout} />
          </Switch>
        </BrowserRouter>
      </Provider>
    )
  }
}

class AuthorizedRoute extends React.Component {
  componentWillMount() {
    getLoggedUser()
  }

  render() {
    const { component: Component, pending, logged, ...rest } = this.props
    return (
      <Route {...rest} render={props => {
        if (pending) return <div>Loading...</div>
        return logged
          ? <Component {...this.props} />
          : <Redirect to="/auth/login" />
      }} />
    )
  }
}

const stateToProps = ({ loggedUserState }) => ({
  pending: loggedUserState.pending,
  logged: loggedUserState.logged
})

export default connect(stateToProps)(AuthorizedRoute)
  • 组件命名
    顶级组件以 Layout结尾,页面级组件以 Page 结尾
  • Route的三种渲染方式
    component // 本质调用React.createElement 创建Component
    render // 适用于要封装高阶组件的情形,如封装一个<FadingRoute>
// wrapping/composing
const FadingRoute = ({ component: Component, ...rest }) => (
  <Route {...rest} render={props => (
    <FadeIn>
      <Component {...props}/>
    </FadeIn>
  )}/>
)
<FadingRoute path="/cool" component={Something}/>

children // 不管路径是否匹配,总是渲染。只是当路径不匹配时,match为null

<ul>
  <ListItemLink to="/somewhere"/>
  <ListItemLink to="/somewhere-else"/>
</ul>

const ListItemLink = ({ to, ...rest }) => (
  <Route path={to} children={({ match }) => (
    <li className={match ? 'active' : ''}>
      <Link to={to} {...rest}/>
    </li>
  )}/>
)

参考

相关文章

网友评论

      本文标题:React-Router-v4 (2)实用技巧

      本文链接:https://www.haomeiwen.com/subject/bkvbjftx.html