🤡官:你有遇到很难排查的问题吗

前言

  • 常网IT源码上线啦!
  • 本篇录入吊打面试官专栏,希望能祝君拿下Offer一臂之力,各位看官感兴趣可移步🚶。
  • 有人说面试造火箭,进去拧螺丝;其实个人觉得问的问题是项目中涉及的点 || 热门的技术栈都是很好的面试体验,不要是旁门左道冷门的知识,实际上并不会用到的。
  • 接下来想分享一些自己在项目中遇到的技术选型以及问题场景。

当别人给你发红包,如果你不想收~

你这样回:心意和红包,我就挑最贵重的收下啦,红包就不收了,谢谢!

地铁上看到一个文质彬彬的少年~

一、场景还原

请允许我用最简单朴素的话描述。

从A路由--->B路由,此时停留在B路由页面下,点击浏览器自带的返回,期望回到A页面。

结果发现:url是A页面的,但内容还是B页面。

而当前应用是嵌入到其他环境的,被包裹了一层。

二、分析

首先,有请第一位怀疑对象登场。

2.1 beforeEach

初步怀疑是router.beforeEach的哪个逻辑没有走next(),所以导致他停留下来。

我们写程序的时候,应该要有这种直觉。

于是,我们查看逻辑,发现此时调用H接口成功时,才会去走next()。

那是否是因为网络导致接口响应慢,而影响了next。

2.2 浏览器历史记录

正当我们调试一波,部署线上时,神奇的发现,点击【返回】的时候,连router.beforeEach都不走,这就有点神奇了。

心想:路由的一切变化,应该都会走beforeEach才对的,尽管的浏览器或者路由跳转。

于是,我咨询了一位朋友。

在使用 Vue Router 中,当使用 history 模式(HTML5 History 模式)时,浏览器返回上一个页面会触发浏览器的历史记录操作,而不会触发 Vue Router 的路由跳转。因为 Vue Router 的 beforeEach 守卫是在路由跳转之前触发的,而浏览器的返回按钮并不是触发路由跳转,而是操作浏览器历史记录。

所以,当用户点击浏览器返回按钮时,页面会直接从浏览器历史记录中获取上一个页面的 URL,并加载对应的页面内容,这个过程是浏览器自身的行为,不会经过 Vue Router,因此也不会触发 beforeEach 守卫以及其他 Vue Router 相关的路由导航守卫。

如果您希望在用户点击浏览器返回按钮时执行一些逻辑,可以使用浏览器原生的 popstate 事件来监听浏览器的历史记录变化。在 popstate 事件中,您可以执行相关的逻辑操作。但是需要注意的是,这种方式不会触发 Vue Router 的路由导航守卫。

完。

我看完是想笑的,虽然心里有一度觉得有点道理,但不管是浏览器操作历史记录,还是会走beforeEach守卫的,她是全局的。

2.3 popstate

提到了一个点,说可以利用popstate事件来执行路由跳转,可以router.go(-1) ,但我认为不好,因为无法确认他会不会走beforeEach,要是走了,里面next,你popstate也go(-1),就会跳转两次。

Out!

2.4 组件路由守卫

没事,我还有招,竟然全局的路由守卫,我还有其他守卫,我去组件守卫添加一下beforeRouteLeave让她next。

很遗憾,这里也不会执行。

Out!

2.5 外部js影响?

在html中,我们引入了n个js资源,如:wx的,埋点SDK等等。

是否是因为这些js资源引起,某个代码阻止了其跳转事件。

也有这个可能,但排查起来困难,因为引入资源较多。

2.6 找规律:刷新

如果阁下,阁下会怎么排查?

我将项目的对象都怀疑了一遍,突然想起小时候老师说的,遇到问题不要慌,先找问题所在,那怎么找问题呢?

找规律!

我们的应用,是嵌入到其他应用的,那边点击一个按钮a标签会跳转到我们这边来,其实一开始怀疑是不是那边有什么限制,比如nginx设置了。

但发现,在同等的其他应用没有这个情况,那还是我们自己先找原因。

回归正题,跳到我们应用来,A路由--->B路由。

突然发现:如果我们此时在任意的路由手动F5刷新一下,即可正常回退上一步。

有了这个规律,我突然想起,之前有一个需求:

url?token=base64,由于token很长,而且会显示在页面上,希望我们拿到token存到vuex中,用js程序把url上的token给清除掉。

vbnet 复制代码
delete to.query.token;
router.push({ name: to.name, query: {...to.query  }  });

即:

url?token=1

url

我想,或许和这里有关,导致路由、历史记录错乱,才会回退不回去。

然后我们手动刷新一下,记录就正常了,也就能正常回退。

三、解决方法

有两个解决方法。

3.1 去掉自动删除token

这一步去掉。

vbnet 复制代码
delete to.query.token;
router.push({ name: to.name, query: {...to.query  }  });

直接走next。

当然,原本的需求,我们最好不要去做更改,只能程序自己想办法了。

3.2 自动刷新

既然刷新能解决问题,那我们就让他进入我们的应用的时候,刷新一下,在源头处理就好。

源头解决好了,后面的路由跳转就没问题了。

我们只页面加载第一次的时候,做手动刷新。

javascript 复制代码
mounted(){
  if(this.$store.getters.get_isFirstRefresh){
    this.$store.dispatch('set_isFirstRefresh',false);
    this.$router.go(0) // 刷新
  }
}

vuex

javascript 复制代码
const homeInfos = {
    state: {
        isFirstRefresh: true 
    },
    mutations: {
        set_isFirstRefresh(state, isFirstRefresh) {
            state.isFirstRefresh = isFirstRefresh
        }
    },
    actions: {
        set_isFirstRefresh(state,isFirstRefresh) {
            state.commit('set_isFirstRefresh', isFirstRefresh)
        }
    },
    getters: {
        get_isFirstRefresh: (state) => {
            return state.isFirstRefresh
        }
    }
}

export default homeInfos

至此撒花~

后记

我们在实际项目中或多或少遇到一些奇奇怪怪的问题。

在此期间,不要慌是首选,多凭借自己的经验找感觉,或许是有一个需求改了一两行不起眼的代码导致。

大动脉没切中,即安心。

如果有其他更好的方法也欢迎评论区见,这里提供的只是诸多方法之一。

最后,祝君能拿下满意的offer。

我是Dignity_呱,来交个朋友呀,有朋自远方来,不亦乐乎呀!深夜末班车

👍 如果对您有帮助,您的点赞是我前进的润滑剂。

以往推荐

小小导出,我大前端足矣!

靓仔,说一下keep-alive缓存组件后怎么更新及原理?

面试官问我watch和computed的区别以及选择?

面试官问我new Vue阶段做了什么?

前端仔,快把dist部署到Nginx上

多图详解,一次性啃懂原型链(上万字)

Vue-Cli3搭建组件库

Vue实现动态路由(和面试官吹项目亮点)

项目中你不知道的Axios骚操作(手写核心原理、兼容性)

VuePress搭建项目组件文档

原文链接

juejin.cn/spost/73859...

相关推荐
幸运小男神6 分钟前
npm如何清空缓存并重新打包?
前端·npm
北原_春希9 分钟前
Vue的服务器代理如何配置
服务器·前端·vue.js
co松柏21 分钟前
在非 antd pro 项目中使用 umi OpenAPI
java·前端
乐吾乐科技42 分钟前
【国产开源可视化引擎Meta2d.js】快速上手
开发语言·前端·javascript·开源·编辑器·数据可视化·大屏端
草样的年华1 小时前
三维地图Cesium中,如何监听地图点击事件,实现在实体上面鼠标右击时做处理。
前端·cesium·三维地图
程序员微木1 小时前
【ajax实战03】拦截器
前端·ajax·okhttp
亿元程序员1 小时前
Cocos如何跟Android通信?
前端
AI视觉网奇1 小时前
vscode 前行复制到下一行
java·服务器·前端
一只开心鸭!1 小时前
vue引入并使用物理引擎matter.js
前端·javascript·vue.js
小满zs1 小时前
Nodejs 第八十三章(ElasticSearch全文检索)
前端·elasticsearch·node.js