前端工作小结6-vue处理token
最开始后端来和我说 token 时候,
虽然装着很懂的样子,但当时我听的是一脸懵逼
之前学习的时候,根本没接触过token,
后来查了一些资料,终于明白了token 的原理,以及应用。
token 原理
token 的意思是 令牌, 就像是我们登陆某个账号时,会向你的安全令发送验证一样。
一个道理, 在前端处理登陆时,并非简单的验证账号密码是否正确, 而是发送给后台。
后台验证成功后, 会发送给我们一个 token。
token 大概长这样:27d2da79303d4abaa271e71c2d6f3b48.d86c828583c5c6160e8acfee88ba1590
在我们登陆成功之后,后台会返回给我们token ,之后的每一次请求, 都要先验证token。
就是说,我们要将token 放到请求里。 token正确,才能执行下一步操作。
总而言之,使用token 会很安全。
处理 token
token 的处理思路很简单:
1.把冰箱门打开
2.向后台发送登陆请求,
3.接收到后台传来的 token
4.将 token 储存起来,
5.将 token 放到请求的 header 里
6.关上冰箱门
我这里储存 token 选择的是放到本地的Session Storage
里面,也用到了 vuex
vuex 需要提前配置好, 我这里使用的是单文件配置下载什么的就略过了…
还有 store/index.js 的文件配置
-
import Vue from 'vue'
-
import Vuex from 'vuex'
-
Vue.use(Vuex)
-
export default new Vuex.Store({
-
state: {
-
token: ''
-
},
-
mutations: {
-
set_token (state, token) {
-
state.token = token
-
sessionStorage.token = token
-
},
-
del_token (state) {
-
state.token = ''
-
sessionStorage.removeItem('token')
-
}
-
}
-
})
这里在 mutation
里设置了两个方法 set :设置 和 del :删除 两个方法。
具体操作
首先在登陆界面写一个有关登陆的函数,在其中发送ajax 请求,这里用的是 axios。
-
login () {
-
this.$axios({
-
method: 'post',
-
url: '/api/v1/teacher/login',
-
params: {
-
't_num': this.t_num,
-
't_pwd': this.t_pwd
-
}
-
}).then(res => {
-
console.log(res)
-
let data = 'brear ' + res.data.access_token
-
this.$store.commit('set_token', data)
-
if (store.state.token) {
-
this.$router.push('/home')
-
console.log(store.state.token)
-
} else {
-
this.$router.replace('/login')
-
}
-
}).catch(err => {
-
console.log(err)
-
})
-
}
在这里要注意的是后台与我约定好了 ,在每次发送请求时,在token前面加一个 字符串和一个空格。
所以是这样 let data = 'brear ' + res.data.access_token
总之具体的需求 还是根据实际情况而定,这里只是储存token,以及登陆成功跳转到主页
还要注意的是我们这里用到的是 access_token ,有关 access_token 和 refresh_token ,有兴趣的同学 可以去百度一下。
这里成功获取到了token,但是之前提到过,我们每次发送请求时,都需要验证 token,
这就需要把 token 放到 header 里,就需要配置 ajax 拦截器。
还是axios…
我这里直接在 main.js 文件里配置
-
axios.defaults.headers.common['authorization'] = store.state.token
-
axios.interceptors.request.use(config => {
-
if (store.state.token) {
-
config.headers.common['authorization'] = store.state.token
-
}
-
return config
-
},
-
error => {
-
return Promise.reject(error)
-
})
-
axios.interceptors.response.use(
-
response => {
-
return response
-
},
-
error => {
-
if (error.response) {
-
switch (error.response.status) {
-
case 401:
-
this.$store.commit('del_token')
-
router.replace({
-
path: '/login',
-
query: {
-
redirect: router.currentRoute.fullPath
-
}
-
})
-
}
-
}
-
return Promise.reject(error.response.data)
-
}
-
)
这里用到的是 ajax 拦截器
在发送请求之前 先将 token 放到 header 里面 ,
如 axios.defaults.headers.common['authorization'] = store.state.token
还需要处理两个情况,
1.token 不存在,跳转到登陆页,重新获取 token
2.token 过期 ,如 error 返回 401 也是跳转到登录页, 重新获取token
关于路由 router
配置 token 时还需要判定跳转页面时 token 的授权。
还是直接上代码
-
router.beforeEach((to, from, next) => {
-
if (to.matched.some(r => r.meta.requireAuth)) {
-
if (store.state.token) {
-
next()
-
} else {
-
next({
-
path: '/login',
-
query: {
-
redirect: to.fullPath
-
}
-
})
-
}
-
} else {
-
next()
-
}
-
})
同样是在 main.js 中配置,当然还要安装vue-router …
同样是单文件
这里的 router/index.js 就不仔细说了…
重要的是配置
-
if (sessionStorage.getItem('token')) {
-
store.commit('set_token', sessionStorage.getItem('token'))
-
}
这个写到 router/index.js 文件中,
在 main.js 里 :
引入 router…
import router from './router'
在每次跳转页面之前 判断是否需要登陆 后查看
-
router.beforeEach((to, from, next) => {
-
if (to.matched.some(r => r.meta.requireAuth)) {
-
if (store.state.token) {
-
next()
-
} else {
-
next({
-
path: '/login',
-
query: {
-
redirect: to.fullPath
-
}
-
})
-
}
-
} else {
-
next()
-
}
-
})
这里的if (to.matched.some(r => r.meta.requireAuth))
需要在router/index 中配置:
-
{
-
path: '/paper',
-
name: 'Paper',
-
component: Paper,
-
meta: {
-
requireAuth: true
-
}
-
}
就是在需要 登陆 才能操作的页面里加入 meta
判断是否需要登陆
最后附上 main.js 的所有代码
-
// The Vue build version to load with the `import` command
-
// (runtime-only or standalone) has been set in webpack.base.conf with an alias.
-
import Vue from 'vue'
-
import Vuex from 'vuex'
-
import App from './App'
-
import router from './router'
-
import store from './store/index'
-
import axios from 'axios'
-
Vue.prototype.$axios = axios
-
Vue.use(Vuex)
-
Vue.config.productionTip = false
-
axios.defaults.headers.common['Content-type'] = 'application/json'
-
axios.defaults.headers.common['authorization'] = store.state.token
-
axios.interceptors.request.use(config => {
-
if (store.state.token) {
-
config.headers.common['authorization'] = store.state.token
-
}
-
return config
-
},
-
error => {
-
return Promise.reject(error)
-
})
-
axios.interceptors.response.use(
-
response => {
-
return response
-
},
-
error => {
-
if (error.response) {
-
switch (error.response.status) {
-
case 401:
-
this.$store.commit('del_token')
-
router.replace({
-
path: '/login',
-
query: {
-
redirect: router.currentRoute.fullPath
-
}
-
})
-
}
-
}
-
return Promise.reject(error.response.data)
-
}
-
)
-
router.beforeEach((to, from, next) => {
-
if (to.matched.some(r => r.meta.requireAuth)) {
-
if (store.state.token) {
-
next()
-
} else {
-
next({
-
path: '/login',
-
query: {
-
redirect: to.fullPath
-
}
-
})
-
}
-
} else {
-
next()
-
}
-
})
-
/* eslint-disable no-new */
-
new Vue({
-
el: '#app',
-
router,
-
store,
-
components: { App },
-
template: '<App/>'
-
})
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 被坑几百块钱后,我竟然真的恢复了删除的微信聊天记录!
· 没有Manus邀请码?试试免邀请码的MGX或者开源的OpenManus吧
· 【自荐】一款简洁、开源的在线白板工具 Drawnix
· 园子的第一款AI主题卫衣上架——"HELLO! HOW CAN I ASSIST YOU TODAY
· Docker 太简单,K8s 太复杂?w7panel 让容器管理更轻松!