Vue项目保持用户登录状态(localStorage + vuex 刷新页面后状态依然保持)

在前端项目开发的广阔领域中,实现用户登录与注册功能是构建任何交互式Web应用不可或缺的一部分。然而,这一过程中常常会遇到一个常见且需要细心处理的问题:当用户完成登录操作后,如果直接刷新浏览器页面,其登录状态往往会意外地消失,给用户体验带来不便。这一现象的核心原因在于,默认情况下 Web 应用并不具备跨页面请求或页面刷新时自动保存用户状态的能力。换句话说,用户登录状态(如登录令牌、会话 ID 等关键信息)仅仅存储在浏览器的内存中,而一旦页面刷新或关闭,这些内存中的状态信息就会被清除,导致应用无法识别用户的登录状态。

为了解决这一问题,开发者需要采取一系列措施来持久化或跨请求传递用户状态。这通常涉及到在客户端(如使用 localStorage、sessionStorage、cookies 等 Web 存储技术)和/或服务器端(如通过数据库、会话管理服务等)存储用户状态信息。通过这些技术,即便是在浏览器页面刷新或关闭后再次访问应用,也能够通过验证存储的状态信息来恢复用户的登录状态,从而提供更加流畅和连贯的用户体验。

这里小马演示使用的是 localStorage + vuex 方法(其他诸如 sessionStorage、cookie 等用法相同,只是功能有所区别)。 


一、实现效果

实现功能:用户登录成功后,刷新浏览器页面或者关闭浏览器再次打开网页后,登录状态依然保持,直到用户点击登出。

二、实现步骤及涉及要点

1. 首先在 vuex 中的 state 属性中添加一个空对象 userInfo{ } 用于保存用户登录后的状态;

涉及要点:

  • state 属性(状态)用于添加多个组件共享的变量,作用类似于 vue 中的 data;

2. 在登录页面中,判断登录成功后创建对象 userInfo{ },并添加描述登录状态的各属性,然后将该对象分别存入 localStorage 和 vuex; 

涉及要点:

  • localStorage 属性允许访问 Document 源的 Storage 对象,存储的数据保存在浏览器会话中;
  • 与 sessionStorage 的唯一区别就是 localStorage 属于永久性存储,除非我们手动清除,而 sessionStorage 属于临时存储,浏览器关闭后便会被清空。
    • 存:localStorage.setItem('myCat', 'Tom');
    • 取:var cat = localStorage.getItem("myCat");
    • 删:localStorage.removeItem("myCat"); 或 localStorage.clear("myCat");
  • JSON.stringify() 系列化对象,将返回的对象类型转为字符串类型;
  • this.$store.state,取 vuex 中 state 中的属性,如:
    • this.$store.state.userInfo = userInfo //取出 vuex 中的 userInfo 并赋值为新的 userInfo

3. 在挂载阶段,判断登录状态 userInfo;设置相关属性之后,就可以正常保存登录状态了。

因为 localStorage 为永久保存,所以即使关闭浏览器再次打开网页登录状态依然存在,除非手动清除 localStorage 数据;

4. 设置登出,清除 localStorage 中的数据;

5. 实现功能。

三、涉及代码

vuex(store/index.js)

import Vue from 'vue'
import Vuex from 'vuex'

Vue.use(Vuex)

export default new Vuex.Store({
  state: {
    userInfo:{}
  },
  mutations: {
  },
  actions: {
  },
  modules: {
  }
})

设置登录的页面(部分代码,无法复制即用,仅作参考)

登录方法

//登录方法
login() {
  //验证码的验证
  var randStr = this.rand.toString().replace(/,/g, ""); //随机生成的验证码为数组形式,此处将其转为字符串并去掉中间相隔的逗号
  var codeStr = this.code; //用户输入的验证码
  if (randStr.toLowerCase() == codeStr.toLowerCase()) { //比较用户输入的与随机生成的验证码,不区分大小写
    //获取登录接口
    axios.post("user/login", {
      name: this.name,
      password: this.password,
      administrator: this.usertyp
    }).then(result => {
      console.log(result.data);
      const code = result.data.code;
      this.token = code;
      if (this.token == 1003) {
        this.$message.error('用户名或密码未输入!');
      } else if (this.token == 1001) {
        this.$message.error('登录失败,请检查用户名或者密码是否正确。');
      } else if (this.token == 1005) {
        this.$message.error('您不是管理员,无管理员登录权限!');
      } else if (this.token == 200) {
        if (this.usertyp == "2") { //管理员登录
          this.$message.success('登录成功!');
          this.dialogFormVisible = false; //登录成功后登录插槽关闭
          this.loginReg = false;//隐藏登录注册按钮,显示欢迎信息
          this.manage = true;//显示管理员登录信息
          let userInfo = {
            isLogin: true,
            manage: true,
            name: this.name
          };
          localStorage.setItem("userInfo", JSON.stringify(userInfo));
          this.$store.state.userInfo = userInfo
          console.log('this.$store.state.userInfo', this.$store.state.userInfo)
          setTimeout(() => { //此处必须使用vue函数,否则this无法访vue实例
            this.$message(`欢迎您,管理员 ${this.name}!`)
          }, 2000);
          console.log(this.usertyp)
        } else if (this.usertyp == "") {  //普通用户
          this.$message.success('登录成功!');
          this.dialogFormVisible = false; //登录成功后插槽关闭
          this.loginReg = false;//隐藏登录注册按钮,显示欢迎信息
          this.user = true; //显示普通用户登录信息
          let userInfo = {
            isLogin: true,
            manage: false,
            name: this.name
          }
          localStorage.setItem("userInfo", JSON.stringify(userInfo));
          this.$store.state.userInfo = userInfo
          setTimeout(() => { //此处必须使用vue函数,否则this无法访vue实例
            this.$message(`欢迎您,尊贵的晋之魂用户 ${this.name}!`)
          }, 2000);
          console.log(this.usertyp)
        }
        this.Cookie.set("UserName", this.name); //将用户名存到cookie
        console.log('登录状态为:' + this.token);
      }
    })
  } else {
    this.$message.error('请输入正确的验证码');
  }
},

退出登录方法

//退出登录
logout() {
  this.Cookie.remove("UserName");
  this.loginReg = true;
  this.manage = false;
  this.user = false;
  this.log_out = false;
  localStorage.clear();
  setTimeout(() => {
    this.$router.push({
      path: '/'
    }, () => {
    }, () => {
    });//退出登录后2秒后跳转至首页
  }, 2000)
  //加()=>{},()=>{} 可解决路由重复后台报错问题
},

挂载阶段判断登录状态

mounted() {
      // 判断登录状态
      let userInfo = JSON.parse(localStorage.getItem('userInfo'));
      if (null === userInfo) return;
      console.log('userInfo', userInfo.isLogin);
      if (userInfo.isLogin) {
        this.dialogFormVisible = false; //登录成功后插槽关闭
        this.loginReg = false;//隐藏登录注册按钮,显示欢迎信息
        this.name = userInfo.name;
        if (userInfo.manage) {
          this.manage = true;//显示管理员登录信息
        } else {
          this.user = true;//显示普通用户登录信息
        }
      }
    }

提示:小马使用的是 vue + Element UI,使用其他技术代码可能不同,但思路是不变的。

  • 130
    点赞
  • 252
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 154
    评论
您可以使用 Vue.js 和 TypeScript 的结合,在组件中定义一个 computed 属性,来动态判断用户的登录状态。 具体实现步骤如下: 1. 定义一个 computed 属性,用来判断用户是否已登录: ``` import { defineComponent, computed } from 'vue' import { useStore } from 'vuex' export default defineComponent({ name: 'LoginStatus', setup () { const store = useStore() // 判断用户是否已登录 const isLoggedIn = computed(() => { return store.getters['user/isLoggedIn'] }) return { isLoggedIn } } }) ``` 2. 在组件的模板中使用该 computed 属性,根据用户的登录状态显示不同的内容: ``` <template> <div> <template v-if="isLoggedIn"> <!-- 已登录状态的内容 --> <p>您已登录</p> </template> <template v-else> <!-- 未登录状态的内容 --> <p>请先登录</p> </template> </div> </template> ``` 3. 在 Vuex 中定义一个 getter,用来获取用户的登录状态: ``` import { GetterTree } from 'vuex' import { RootState } from '@/store/types' const getters: GetterTree<RootState, RootState> = { isLoggedIn: state => state.user.isLoggedIn } export default getters ``` 4. 在 store 中定义一个 state,用来保存用户的登录状态: ``` import { Module } from 'vuex' import { RootState } from '@/store/types' interface UserState { isLoggedIn: boolean } const userModule: Module<UserState, RootState> = { namespaced: true, state: { isLoggedIn: false }, mutations: { setIsLoggedIn (state, isLoggedIn: boolean) { state.isLoggedIn = isLoggedIn } }, actions: { login ({ commit }) { // 调用登录接口 // 成功返回 true,失败返回 false const success = true commit('setIsLoggedIn', success) }, logout ({ commit }) { commit('setIsLoggedIn', false) } } } export default userModule ``` 以上就是用 Vue.js 和 TypeScript 判断用户登录状态的方法,您可以根据实际需要进行调整和完善。
评论 154
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

敬 之

您的鼓励就是我持续创作的动力~

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值