vue-router 在beforeEach中添加每次跳转带上的参数,报错问题

博客主要讲述在Vue守卫导航中添加参数,路由跳转时出现'Redirected when going from “/a” to “/b” via a navigation guard'问题,并给出了解决办法,即添加最后两个方法。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

在守卫导航中添加参数,在路由跳转时会出现下面问题。
Redirected when going from “/a” to “/b” via a navigation guard. at createRouterError (vue-router.esm.js?8c4f:2008)

解决方法:添加下面最后两个方法

router.beforeEach((to, from, next) => {
  // 修改标题
  if (to.meta.title) {
    document.title = to.meta.title;
  }
  if (sessionStorage.getItem('appId') && sessionStorage.getItem('token') && !to.query.appid) {
    next({
      path: to.path,
      query: {
        ...to.query,
        appid: sessionStorage.getItem('appId'),
        grg_token: sessionStorage.getItem('token'),
      },
    });
  } else {
    next();
  }
});

// 解决上面跳转加参数报错问题
const originalPush = VueRouter.prototype.push;
VueRouter.prototype.push = function push(location, onResolve, onReject) {
  if (onResolve || onReject) return originalPush.call(this, location, onResolve, onReject);
  return originalPush.call(this, location).catch(err => err);
};

// 修改路由replace方法,阻止重复点击报错
const originalReplace = VueRouter.prototype.replace;
VueRouter.prototype.replace = function replace(location) {
  return originalReplace.call(this, location).catch(err => err);
};
<think>嗯,用户遇到了Vue Router 3.0以上版本在频繁点击导航菜单时出现的错误,具体是那个“NavigationDuplicated”的错误。我需要帮他们解决这个问题。首先,我得回忆一下Vue Router的相关知识,特别是3.x版本的处理方式。 根据引用3,错误信息是“Avoided redundant navigation to current location”,这说明当用户试图跳转到当前已经激活的路由时,Vue Router会抛出这个错误。常见于TabBar或导航栏的频繁点击。这可能是因为路由跳转被多次触发,而Vue Router检测到了冗余的导航。 接下来,我需要考虑解决方案。记得在Vue Router中,路由跳转的方法如push和replace返回的是Promise,所以如果在没有捕获异常的情况下,可能会触发控制台的错误提示。因此,处理Promise的异常可能是关键。 第一种方法可能是捕获push或replace时的错误。在调用this.$router.push的时候,添加.catch来忽略特定的错误。比如,判断错误是否为NavigationDuplicated,如果是,就忽略。这样可以防止错误冒泡到控制台。 第二种方法可能是通过重写Vue Router的原型方法,比如在全局的main.js中修改push和replace方法,自动添加错误处理。这样在整个项目中就不需要每次调用都写catch了。参考引用2中提到返回值的问题,可能返回false或undefined会影响导航行为,但这里主要需要处理的是Promise的reject情况。 第三种方法可能是给router-link添加事件修饰符,比如@click.native.prevent,然后手动处理导航。或者检查当前路由是否已经是目标路由,如果是的话就不执行跳转。例如,在点击事件中先比较this.$route.path和目标路径,避免重复跳转。 另外,用户可能是在使用编程式导航或者在组件中直接使用router-link,不同的场景可能需要不同的处理方式。例如,router-link会自动处理一些情况,但如果是自己写的按钮触发push方法,就需要手动处理。 还需要考虑Vue Router的版本问题,虽然用户提到的是3.x,但不同的小版本可能有细微差别。不过主要的问题处理方式应该是一致的。此外,可能还需要检查路由配置是否正确,是否有重复的路由定义,但根据错误信息来看,更多是重复导航问题而不是配置错误。 总结下来,解决方案可能有三种:捕获push/reject的错误,重写Vue Router方法全局处理,或者在跳转前检查当前路由。需要将这些方法详细地分步骤说明,确保用户能够理解和实施。 同时,用户可能需要知道为什么会出现这个问题,所以解释原因也很重要。比如,Vue Router 3.x版本之后,如果没有捕获push返回的Promise错误,就会在控制台显示,而之前版本可能静默失败。所以处理这些Promise的reject情况是必要的。 最后,还需要给出相关问题,帮助用户进一步理解可能遇到的类似问题,比如编程式导航的其他错误处理,router-link与push的区别,或者如何全局配置错误处理等。</think>### Vue Router 3.x 频繁点击导航菜单报错解决方案 #### 问题原因 当使用 Vue Router 3.x 以上版本时,**重复点击相同路径的导航菜单**会触发 `NavigationDuplicated` 错误。这是因为 Vue Router 内部对冗余路由跳转进行了严格检测,而路由跳转方法(如 `push` 或 `replace`)返回的 Promise 未被正确处理[^3]。 --- #### 解决方案分步说明 ##### 方法一:全局捕获路由错误 在 **路由配置文件(router/index.js)** 中添加以下代码,统一处理冗余导航错误: ```javascript const originalPush = VueRouter.prototype.push; VueRouter.prototype.push = function push(location) { return originalPush.call(this, location).catch(err => { if (err.name !== 'NavigationDuplicated') throw err; }); }; ``` *原理*:重写路由的 `push` 方法,在发生非关键错误时静默处理。 --- ##### 方法二:单次调用添加异常捕获 在触发导航的代码处(如按钮点击事件)显式捕获错误: ```javascript this.$router.push('/target-path').catch(err => { if (err.name === 'NavigationDuplicated') return; throw err; }); ``` --- ##### 方法三:通过路由守卫拦截 在全局前置守卫中判断目标路由是否与当前路由相同: ```javascript router.beforeEach((to, from, next) => { if (to.path === from.path) return; next(); }); ``` --- ##### 方法四:使用 `router-link` 的 `exact` 属性 在模板中为导航按钮添加精确匹配判断: ```html <router-link :to="{ path: '/home' }" exact @click.native.prevent> Home </router-link> ``` --- #### 核心原理总结 1. **Promise 链断裂**:Vue Router 3.x 的导航方法返回 Promise,未处理 `.catch` 会导致控制台报错[^2] 2. **路径重复检测**:当目标路径与当前路径完全匹配时,触发冗余导航保护机制[^3] ---
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值