在开发vue的前端项目中,咱们经常使用编程式路由来完成导航页面的切换。你们基本上都会使用到this.$router.push的方法。
常见的使用方法是:javascript
this.$router.push({name:'a'}); this.$router.push({path:'/a'})
在项目的开发过程当中,我使用了push方法采用上面的第二种方式,可是我书写的方式并无带'/',我当时的路由假设为'/a',执行下面的方法,个人页面切换为'/b',这和咱们通常书写的方式不一致,可是路径跳转是正常的。前端
this.$router.push({path:'b'})
我想知道path匹配的方式是带有'/'是从根路由开始替换的,可是若是我不带'/',为何一切正常?我查询了官方文档,官方一样也有不带'/'的写法,可是并无解释其中具体的逻辑。vue
因而我就去看了官方的源码。java
顺着push方法一路找下去,我发现了一个方法utils/path.js有一个处理路径的方式:
resolvePath编程
export function resolvePath ( relative: string, base: string, append?: boolean ): string { const firstChar = relative.charAt(0) if (firstChar === '/') { return relative } if (firstChar === '?' || firstChar === '#') { return base + relative } const stack = base.split('/') // remove trailing segment if: // - not appending // - appending to trailing slash (last segment is empty) if (!append || !stack[stack.length - 1]) { stack.pop() } // resolve relative path const segments = relative.replace(/^\//, '').split('/') for (let i = 0; i < segments.length; i++) { const segment = segments[i] if (segment === '..') { stack.pop() } else if (segment !== '.') { stack.push(segment) } } // ensure leading slash if (stack[0] !== '') { stack.unshift('') } return stack.join('/') }
我传入的path路径在这里获得了解析,而后恢复正常了。
后来我在官方编写的测试用例中看到了这个方法的测试代码。app
describe('Path utils', () => { describe('resolvePath', () => { it('absolute', () => { const path = resolvePath('/a', '/b') expect(path).toBe('/a') }) it('relative', () => { const path = resolvePath('c/d', '/b') expect(path).toBe('/c/d') }) it('relative with append', () => { const path = resolvePath('c/d', '/b', true) expect(path).toBe('/b/c/d') }) it('relative parent', () => { const path = resolvePath('../d', '/a/b/c') expect(path).toBe('/a/d') }) it('relative parent with append', () => { const path = resolvePath('../d', '/a/b/c', true) expect(path).toBe('/a/b/d') }) it('relative query', () => { const path = resolvePath('?foo=bar', '/a/b') expect(path).toBe('/a/b?foo=bar') }) it('relative hash', () => { const path = resolvePath('#hi', '/a/b') expect(path).toBe('/a/b#hi') }) }) ... })
结合实际代码和测试用例咱们发现:
当咱们的原路径为/a,当咱们push({path:b}),最终为生成'/b'
当咱们的原路径为/a/c,当咱们push({path:b}),最终为生成'/a/b'测试
固然还有其余各类状况,可是解决了我对于路径当前跳转的疑惑。你们有兴趣也能够试试别的方式。'../b'等方式,可是官方文档上并无标出这些使用方式,因此你们仍是尽可能按照标准的方式。this
但愿能够解决你们对于官方文档上path前不带'/'的具体问题。code