关于前端:vuerouter源码五routeraddRoute源码分析

前言

【vue-router源码】系列文章将带你从0开始理解vue-router的具体实现。该系列文章源码参考vue-router v4.0.15
源码地址:https://github.com/vuejs/router
浏览该文章的前提是你最好理解vue-router的根本应用,如果你没有应用过的话,可通过vue-router官网学习下。

该篇文章将剖析router.addRoute的实现。

应用

当应用addRoute增加路由时,如果第一个参数为路由name,那么会增加一个嵌套路由;否则增加的是个非嵌套路由。

// 增加非嵌套路由
router.addRoute({ name: 'admin', path: '/admin', component: Admin })
// 增加嵌套路由
router.addRoute('admin', { path: 'settings', component: AdminSettings })

以上代码等同于:

router.addRoute({
  name: 'admin',
  path: '/admin',
  component: Admin,
  children: [{ path: 'settings', component: AdminSettings }],
})

addRoute

function addRoute(
    parentOrRoute: RouteRecordName | RouteRecordRaw,
    route?: RouteRecordRaw
  ) {
    let parent: Parameters<typeof matcher['addRoute']>[1] | undefined
    let record: RouteRecordRaw
    // 如果parentOrRoute是路由名称,parent为parentOrRoute对应的matcher,被增加的route是个嵌套路由
    if (isRouteName(parentOrRoute)) {
      parent = matcher.getRecordMatcher(parentOrRoute)
      record = route!
    } else { // 如果parentOrRoute不是路由名称,parentOrRoute就是要增加的路由
      record = parentOrRoute
    }

    // 调用matcher.addRoute增加新的记录
    return matcher.addRoute(record, parent)
  }

在定义parent时,应用了一个Paramerer<Type>类型,对于该类型的应用可参考https://www.typescriptlang.org/docs/handbook/utility-types.html#parameterstype。在该办法中,parent的类型会取matcher.addRoute办法中的第2个参数的类型。

isRouteName:通过判断name是否为stringsymbol类型,来决定是不是routeName

export function isRouteName(name: any): name is RouteRecordName {
  return typeof name === 'string' || typeof name === 'symbol'
}

总结

addRoute外部,首先判断第一个参数是不是routeName,如果是routeName,那么被增加的路由是个嵌套路由,否则为非嵌套路由,最初会调用matcher.addRoute办法增加新的路由记录。

评论

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注

这个站点使用 Akismet 来减少垃圾评论。了解你的评论数据如何被处理