vue3+pinia用户信息持久缓存token的问题解决
作者:栀椩
对博主来说,这是个相当复杂的问题。
当初在使用vue2+vuex进行用户信息持久登录时,写了不下3篇博客,确实是解决了问题,博客链接如下
第一篇博客是记录前端如何使用token,简言之,就是先把后端传过来的token写入到浏览器的localstorage缓存中,前端在处理路由之前,先检查localstorage中有没有token,有token就放行,没有token就跳转到登录界面
第二篇博客是发现token过期后的处理方式,最后我的vue2项目都没有使用这篇博客中的解决方案,而是使用了第三篇博客的解决方案
第三篇博客出现的问题是,**每次刷新页面,store里面的数据没了,而localstorage中还有数据,**这样的话,页面上有些地方需要store的数据就加载不出来了,但token并没有更新,出现了逻辑错误。解决方案就是每次在启动页面的时候,检查一下localstorage中有没有数据,有数据的话,重新设置一下store,当然,在路由守卫环节也添加了路由的放行规则
我把第三种方案当做终极解决方案,确实很长一段时间都没有再受到困扰
知道我现在开始使用vue3+pinia来写前端项目,问题又来了
pinia和vuex遇到的问题是一样的,我尝试用第三篇博客来解决,按道理应该是可以解决的,但实际上一直没能解决。折腾很长一段时间,找到了一种比较折中的解决方案
pinia-plugin-persistedstate持久化存储数据
实际上就是使用这个pinia-plugin-persistedstate
插件,它解决的问题是,帮你把store中的数据持久化的存储在localstorage中,并且比较好的一点是,当你需要使用store中的数据时,它又从localstorage中取出来给你去渲染页面,其实就和我上面第3篇博客的内容差不多,这样就不怕刷新页面了,先来看看怎么写和怎么中
store文件的写法
直接看代码:
import { ref } from "vue"; import { defineStore } from "pinia"; import { loginAPI } from "@/apis/user"; export const useUserStore = defineStore( "user", () => { const userInfo = ref({}); const getUserInfo = async (data) => { const res = await loginAPI(data); // console.log(res); userInfo.value = res; // console.log(userInfo.value) }; // 解决刷新页面丢失store信息的问题 const clearUserInfo = () => { userInfo.value = {}; localStorage.removeItem('user') }; return { userInfo, getUserInfo, clearUserInfo, }; }, { persist: true, } );
pinia用的组合式api写法
- userInfo是用户信息
- getUserInfo是通过调用登录接口,修改userInfo
- clearUserInfo是清除用户信息
在代码的最后面,加了个对象persist: true
,之后每次登录,就会在localstorage中生成一个key为user的字符串对象,刷新页面而这个对象不会消失,模板上需要渲染的时候,又把内容添加给store,相对来说比较靠谱。命名规则就是definstore时定义的变量名。
在我没有添加路由守卫规则之前,这么写的话,会有个问题,退出登录后,还能返回到原来的路由,只是页面上该有的用户信息都没有了,因为clearUserInfo
并没有删除localstorage中的user对象,user一直都在,那按照之前的逻辑,当然行不通了
退出登录时的操作
看看具体怎么解决吧
//这是退出登录用到的方法 const logout = () => { // userStore.clearUserInfo() localStorage.removeItem('user') router.push('/login') }
其实就是清除localstorage中的user对象
路由守卫
路由守卫是最麻烦的地方,逻辑理不清楚,就没法正常跳转
我的写法
// 路由守卫 import jwt_decode from "jwt-decode"; router.beforeEach((to, from, next) => { const isLogin = localStorage.user ? true : false; if (isLogin) { const user = JSON.parse(localStorage.user) const decode = jwt_decode(user.userInfo.token); const date = parseInt(new Date().getTime() / 1000); if (date - decode.iat > decode.exp - decode.iat) { localStorage.removeItem("user"); next("/login"); } } if (to.path == "/login") { next(); } else { isLogin ? next() : next("/login"); } });
还是根据localstorage中是否有user对象来判断是否登录,但是前面说过了,它存在localstorage中的是一个字符串,大体是下面这个样子
可以看出来,里面有你定义的state数据,所以,需要解析先成json才能正常取值,取值后,就是解析其中的token了,解析完token,就可以判断有没有过期来清除token了
总之,过程相当繁琐,希望不要再写第5篇了。
到此这篇关于vue3+pinia用户信息持久缓存token的问题解决的文章就介绍到这了,更多相关vue3 pinia用户信息持久缓存token内容请搜索脚本之家以前的文章或继续浏览下面的相关文章希望大家以后多多支持脚本之家!