在摸鱼学习中的大家好呀~,这里是蜘猪侠的专场,今天和大家浅聊一下token该如何处理
笔者仅以自己的实践,谈一谈自己的浅知拙见,以此与大家共同探讨与研究,敬请广大同仁不吝赐教
Vue项目中如何实现token验证
Vue项目中实现token验证的大致思路
- 当用户首次登录时,后端服务器会接收到登录请求,并判断用户信息是否正确。
- 如果验证成功,服务器会生成一个token,其中包含用户的id、用户名、定义好的密钥以及过期时间,并将token返回给客户端。
- 在客户端收到token后,可以选择使用
cookie或者localStorage来进行持久化存储。如果使用vuex来存储token,页面刷新后token会被清除,所以使用cookie或localStorage更适合。 - 客户端每次发起请求跳转路由都会通过axios请求拦截器验证,判断
localStorage中有无token,没有则跳转到登录页面,有则跳转到对应的路由页面 - 前端每次调用后端接口时,都要在请求头中携带token
// 1. 创建axios实例对象
const service = axios.create({
// 使用了环境变量
baseURL: process.env.VUE_APP_BASE_API,
timeout: 10000
})
// 2. 配置实例的请求拦截器
service.interceptors.request.use((config) => {
// 2.1 判断是否有token, 有则添加
const token = store.getters.token
if (token) {
config.headers.Authorization = `Bearer ${token}`
}
return config
}, (error) => {
return Promise.reject(error)
})
- 服务端收到请求后进行响应拦截,验证token合法性,
- header 中存在 token:验证 token 的合法性,成功则返回前端请求的数据;失败(如 token 过期)就返回 401 状态码(401 Unauthorized)
- header 中不存在 token:同样返回 401 状态码
- 如果前端接收到 401 状态码,则清除 token 信息并跳转到登陆页面
// 3. 配置实例的响应拦截器
service.interceptors.response.use((response) => {
// 3.1 解构数据
// 判断接口给回的数据是否是blob对象
if (response.data instanceof Blob) return response.data
const { success, data, message } = response.data
// 3.2 判断(请求成功, 但业务失败)
if (success) {
// 请求成功, 业务成功
return data
} else {
// 请求成功, 业务失败
Message.error(message || '')
return Promise.reject(new Error(message))
}
}, async(error) => {
// 处理401错误(token过期)
if (error.response.status === 401) {
// 提示用户
Message.warning('登录已经过期, 请重新登录~')
// 让仓库清除token和用户信息
await store.dispatch('user/logout')
// store.commit('user/logout')
// store.commit('user/setUserInfo', {})
// 跳转到登录页
router.push('/login')
} else {
// 其它错误
Message.error(error.message || '')
}
return Promise.reject(error)
})
下面是一个示例的代码,用于将token保存到cookie中:
下载js-cookie
yarn js-cookie
引入js-cookie
import Cookies from 'js-cookie'
获取token并存储到本地cookie
//调用cookie方法
import { getToken, setToken, removeToken } from '@/utils/auth'
// 在vuex中定义state和mutation
state:{
token:getToken() || {}
}
mutation:{
setToken(state,token){
state.token = token
setToken(token) // 设置token时, 将数据往本地存储一份
}
}
action:{
async login(context,payload){
const token = await reqLogin(payload) // 1. 发送请求, 获取token
context.commit('setToken',token) // 2. 调用mutation, 存入vuex
}
}
最后,感谢大家观看水文,第一次写介绍,文笔实在没有,欢迎各位提意见