// 添加请求拦截器,在请求头中加token
axios.interceptors.request.use(
config => {
let token = sessionStorage.getItem('Authorization');
if (token) {
config.headers.Authorization = token;
}
return config;
},
error => {
return Promise.reject(error);
}
);
axios.interceptors.response.use(function (response) {
return response
}, async function (error) {
// 1. 如果没有refresh_token,则直接跳转登录页
if (error.response && error.response.status === 401) {
const user = store.status.user
if (!user || user.refresh_token) {
redirectLogin()
return
}
}
// 2.如果有,则请求更新token
try {
const { data } = await axios({
method: 'PUT',
url: "http://ttapi.research.itcast.cn/app/v1_0/authorizations",
headers: {
Authorization: `Bearer ${user.refresh_token}`
}
})
// 3.如果刷新token成功了,则把新的token更新到容器中
store.commit('setUser', {
...user, //原来的数据不变
token: data.data.token //更新token
})
// 4.把之前失败的请求继续发出去
return axios(error.config)
} catch (error) {
console.log('刷新token失败', err)
redirectLogin();
}
return Promise.reject(error)
});
function redirectLogin() {
router.push({
name:'/login',
// query参数会以?key=value&key=value的格式添加到url后面
// query参数不需要配置路由规则,可以传递任何参数
// query是固定的语法给是,用来传递?key=value查询字符串
query:{
// 这里使用查询参数跳转回来的路由地址传递给了登录页面
// router.currentRoute就是当前路由对象,好比我们再组件中的this.$route
// 当前路由对象的fullPath,就是当前路由的路径
// redirect是我起的一个名字
redirect: router.currentRoute.fullPath
}
})
}
const redirect = this.$router.query.redirect || '/'
this.router.push(redirect)