1、问题现象

  页面长时间未操作,再刷新页面时,第一次弹出“token失效,请重新登录!”提示,然后跳转到登录页面,接下来又弹出了n个“Token已过期”的后端返回消息提示。

2、原因分析

  当前页面初始化,有多个向后端查询系统参数的调用,代码如下:

  created () {
// ========================================================================
// 获取需要的系统参数,注意:getParameterClass方法是异步加载数据的。
// 如需要打印观察,需要通过watch来处理 // 获取用户类型的参数类别
this.commonFuncs.getParameterClass(this,"user_type","userTypeList","userTypeMap"); // 获取用户状态的参数类别
for(var i = 0; i < this.userStatusList.length; i++){
var item = this.userStatusList[i];
var mapKey = parseInt(item.itemKey);
this.userStatusMap.set(mapKey, item);
} // 获取性别的参数类别
this.commonFuncs.getParameterClass(this,"gender","","genderMap"); // 获取部门的参数类别
this.commonFuncs.getParameterClass(this,"department","","deptMap"); // 获取角色的参数类别
this.commonFuncs.getParameterClass(this,"role","","roleMap"); // 查询用户记录
this.queryUsers();
},

  这些请求,是axios调用,是异步执行的,因此,刷新页面时,这些请求几乎立即就发出了。然后,这些请求的响应会陆续返回。

  响应首先被下面的response拦截器处理:

// token相关的response拦截器
instance.interceptors.response.use(response => {
if (response) {
switch (response.data.code) {
case 3: //token为空
case 4: //token过期
case 5: //token不正确
localStorage.clear(); //删除用户信息
alert('token失效,请重新登录!');
// 要跳转登陆页
router.replace({
path: '/login',
});
break;
case 6: //禁止访问
// 跳到403页面
router.replace({
path: '/forbidden',
});
break;
default:
break;
}
}
return response;
}, error => {
return Promise.reject(error.response.data.message) //返回接口返回的错误信息
})

  然后再进入请求调用处的代码:

    this.instance.getParameterClass(
this.$baseUrl, {"classKey" : classKey}
).then(res => {
//console.log(res.data);
if (res.data.code == parent.global.SucessRequstCode){
// 如果查询成功
// 成功的处理代码...
}else{
alert(res.data.message);
}
}).catch(error => {
//alert('查询系统参数失败!');
console.log(error);
});

  现在的问题:

  1. 对应一个请求,如果token过期,reponse拦截器首先弹出告警提示,然后,调用处又有提示:

    alert(res.data.message);

    这样就重复了。

  2. 对于同时发出的多个请求,需要有标记来记住这次token过期是否已提示,只提示一次,如已提示,就不必再提示。

3、解决方案

3.1、消除拦截器和请求调用处对token过期的重复提示

  编写一个公共方法,检查是否是被拦截处理的返回码,放于/src/common/commonFuncs.js文件中,代码如下:

  /**
* 判断是否被拦截处理的返回码,返回true,表示被拦截
* 此方法的作用是调用处,无需处理被拦截的返回码的错误提示
* @param {请求的返回码} code
*/
isInterceptorCode(code){
switch (code) {
case 3: //token为空
case 4: //token过期
case 5: //token不正确
case 6: //禁止访问
return true;
default:
break;
}
return false;
}

  然后所有调用处,针对非成功返回的处理均改为:

        if (!this.commonFuncs.isInterceptorCode(res.data.code)){
alert(res.data.message);
}

  这样,消除了拦截处理和调用处理的重复告警。

3.2、多个请求只提示一次的处理

  在全局变量文件/src/common/global.js中,增加token无效标记,代码如下:

//全局变量

export default {
// 请求成功返回码
SucessRequstCode:0, // token无效标记
TokenInvalidFlag : 0
}

  然后,修改拦截器代码:

// token相关的response拦截器
instance.interceptors.response.use(response => {
if (response) {
switch (response.data.code) {
case 0: //正常
// 复位token无效标记置
global.TokenInvalidFlag = 0;
break;
case 3: //token为空
case 4: //token过期
case 5: //token不正确
localStorage.clear(); //删除用户信息
if (global.TokenInvalidCounter == 0){
alert('token失效,请重新登录!');
}
// token无效标记置1
global.TokenInvalidFlag = 1; // 要跳转登陆页
router.replace({
path: '/login',
});
break;
case 6: //禁止访问
// 跳到403页面
router.replace({
path: '/forbidden',
});
break;
default:
break;
}
}
return response;
}, error => {
return Promise.reject(error.response.data.message) //返回接口返回的错误信息
})

  即在第一次收到token过期消息(此时TokenInvalidFlag=0)时,进行提示,然后设置为1(此时TokenInvalidFlag=1),后续的若干个请求的响应,都不会在告警提示了。直到收到成功返回码时复位为0,此时表示重新登录成功了。

  经测试,这样处理达到预期效果,即token过期时,刷新页面,只提示一次告警。

Vue 消除Token过期时刷新页面的重复提示的更多相关文章

  1. Vue build打包之后,刷新页面出现404解决方案

    Vue build打包之后,刷新页面出现404,HTML5 History 模式 原因分析: vue-router 默认 hash 模式 —— 使用 URL 的 hash 来模拟一个完整的 URL,于 ...

  2. 用HTTP状态码实现提交表单后刷新页面不重复提交

    正常情况下,表单提交后如果用户刷新页面会重复提交表单,有些情况下我们不希望表单重复提交,利用HTTP协议中的307状态码重定向页面可以实现这个目的.实例如下: 表单页面代码: <form act ...

  3. 请求时token过期自动刷新token

    1.在开发过程中,我们都会接触到token,token的作用是什么呢?主要的作用就是为了安全,用户登陆时,服务器会随机生成一个有时效性的token,用户的每一次请求都需要携带上token,证明其请求的 ...

  4. Jenkins安装时Web页面报错提示离线安装

    先跳过所有. 方法1 先看它的提示:”参考离线Jenkins安装文档“发现链接点不开,我还以为是被墙了呢,FQ以后还是打不开.看来这个参考文档是没有用滴.点击配置HTTP代理跳出如下界面:安装Jenk ...

  5. vue.js中 v-show在刷新页面时,会闪一下,如何解决?

    因为浏览器是html从上到下执行,先执行Dom元素,然后执行javaScript元素,v-show实在javaScript中控制,当走到javaScript时,Dom元素已经开始走动,所以如果网慢的话 ...

  6. 关于微信小程序返回页面时刷新页面的实现

    在小程序开发中,我们通常会遇到这样的需求:提交某个表单成功后跳转该表单详情页面,但是返回时需要跳转回到首页(注意:我这里的首页是提交表单页的前一个页面),而不能再返回提交表单的页面,并且要在首页中刷新 ...

  7. vue 路由传参中刷新页面参数丢失 及传参的几种方式?

    在页面跳转中,我通过路由传参,结果发现页面参数丢失了.路径返回了根目录.... 1. 先说下路由传参的几种方式吧? 比如:<div v-for="item in items" ...

  8. 防止表单提交时刷新页面-阻止form表单的默认提交行为

    最近在写 ajax 提交的时候遇到一个问题,在执行 ajax 提交之后,浏览器页面自动刷新了,主要是没有 由于form 表单的默认提交行为.一下是几种阻止 form 表单默认提交行为的方式. 1.使用 ...

  9. pyqt5-实时刷新页面(QApplication.processEvents())

    对于执行很耗时的程序来说,由于PyQt需要等待程序执行完毕才能进行下一步,这个过程表现在界面上就是卡顿,而如果需要执行这个耗时程序时不断的刷新界面.那么就可以使用QApplication.proces ...

随机推荐

  1. 【CentOS_7】一行shell实现自动清理过期日志

    昨日web测试环境登录白屏,慌忙登上机器查看,半天没找到问题. 不知哪根筋不对,df -h 一看 , /dev/sda1 已经100%. 立马 du -sh *,发现log日志有点大. 手工清理后,业 ...

  2. 通过format学习,python的内部方法是面象对象的-python面向对象

    1.常用的形式 s ="{0} {0} qqq {0} xxx {1}".format('dog','cat')print(s) 结果:dog dog qqq dog xxx ca ...

  3. CentOS 7 设置时区、日期和时间

    CentOS 7 设置时区.日期和时间 changhr2013关注 2019.04.19 01:33:09字数 307阅读 139 在 CentOS 7 中,引入了一个叫 timedatectl 的设 ...

  4. Linux中的防火墙

    firewalld 一.防火墙安全概述 firewalld支持命令行也支持GUI设置,相对于iptables,firewalld配置更加的方便.在底层的命令都是iptables, firewalld ...

  5. JavaEE 前后端分离以及优缺点

    前端概念 前端是一切直接与用户交互的页面或软件(用户看得见.摸得着)的统称,比如各种网站网页.andorid 手机各种 App.苹果手机各种 app.微信小程序.网络游戏客户端等.所以,普通人使用计算 ...

  6. iapp后台一本通php源码+iapp源码

    给大家分享一个后台源码,内有后台php源码,还有iapp对接源码,一本通 iapp+ PHP源码 经过一个小时的研究看看,测试了一下, 1.注册登录以修复正常,签到正常 2.所有工具正常 3.接口,i ...

  7. python 匹配中文字符

    参考: http://hi.baidu.com/nivrrex/blog/item/e6ccaf511d0926888d543071.html           http://topic.csdn. ...

  8. golang快速入门(五)初尝web服务

    提示:本系列文章适合对Go有持续冲动的读者 初探golang web服务 golang web开发是其一项重要且有竞争力的应用,本小结来看看再golang中怎么创建一个简单的web服务. 在不适用we ...

  9. SpringBoot基础学习(三) 自定义配置、随机数设置及参数间引用

    自定义配置 SpringBoot免除了项目中大部分手动配置,可以说,几乎所有的配置都可以写在全局配置文件application.peroperties中,SpringBoot会自动加载全局配置文件从而 ...

  10. 通过CSS设计模式搭建自己系统的CSS架构

    theme: qklhk-chocolate 传统的CSS书写风格是随意命名,堆叠样式,造成了混乱不堪的结果,复杂页面的样式书写通常会出现几百行甚至上千行的代码,CSS设计模式在实际应用中的横空出世拯 ...