← 返回文章

Vue 中监听全局变量方法

Vue 全局变量监听问题

在项目中遇到了一个问题: 由于我们的系统自己本身不提供登录功能,但又必须要在系统中有角色分类。所以,就希望:

  1. 在用户通过其他平台登录后,跳转到我们平台后,
  2. 将用户角色初始化,并将用户信息存放到全局变量中。
  3. 通过全局变量中存储的信息进而改变 Vue 中的前端界面。

其中遇到的问题: 由于使用的是 AJAX 调用后端请求,所以,并不是同步顺序的执行。

现存方案一

就算按照网上教程,在 Vue 中使用 AJAX 的同步调用,仍然出现问题。同步调用代码如下:


Vue.prototype.$role = {
    isPoeple: false,
    login: false,
    name: "姓名",
}

new Vue({
    async created() {
        try {
            //调用接口名前加 await
            let _self = Vue.prototype
            await axios.get("/test").then(function (response) {
                    // 相应处理
                    let people = response.data.LoginInfo
                    _self.$role.isPoeple = people.isPoeple;
                    _self.$role.name = people.name;
                    }
                }
            );
        } catch (error) {
            console.error(error);
        }
    },
...
})

通过在 生命周期 函数前加 async 然后在 ajax 调用前加 await 关键字。实现 Ajax 的同步调用。

问题在于:尽管 created() 函数中是同步调用,但是 Vue 框架对于 生命周期 函数貌似不是 同步调用。(不是按照我所想的顺序调用,但人家应该是同步调用的。)

所以,尽管再 Vue 初始化能获取到用户信息,但仍然不能通过全局变量控制前端界面。

现存方案二

在之后,看到网上有人使用 store 存储全局变量。并通过 witch 来监听全局变量。

// 在 store/index.js 文件中
export default new Vuex.Store({
  state: {
    loginState: {},
  },
})

// 在组件文件中
computed: {
      listenshowpage1() {
        return this.$store.state._achievements;
      }
    },
    watch:{
      listenshowpage1:function(newd,old){
        console.log(old);
       }
    }

我开始尝试这种方法,有效果么,有。但也存在一个问题。当我尝试点击进入下一页,再按返回键返回时,发现,效果就没了。相当于没有赋值(相当于没有人登录的状态)。原因是返回时,watch 并没有监听到 listenshowpage1 的变化。

解决方法

最后我的解决方法就是,结合以上两种方法混合而成的方法。第一次用户进入时通过 store 监听方法,来达到界面显示目的。当用户进入页面,再返回时,通过 Vue Property 中的数据进行页面控制。 最终方法:

// 在 store/index.js 文件中
export default new Vuex.Store({
  state: {
    loginState: {},
  },
})

在 main.js 文件中:

Vue.prototype.$role = {
    isPoeple: false,
    login: false,
    name: "姓名",
}

new Vue({
    async created() {
        try {
            //调用接口名前加 await
            let _self = Vue.prototype
            await axios.get("/test").then(function (response) {
                    // 相应处理
                    let people = response.data.LoginInfo
                    _self.$role.isPoeple = people.isPoeple;
                    _self.$role.name = people.name;
                    }
                }
            );
        } catch (error) {
            console.error(error);
        }
        // 这是关键语句,在 store 中也存储一份用户信息
        this.$store.state.loginState = Vue.prototype.$role
    },
...
})

在首页的组件中

    export default {
        data() {
            return {
                name: "姓名",
                isPeople: false,
            }
        },

        computed: {
            listenLoginSate() {
                return this.$store.state.loginState
            }
        },

        watch: {
            listenLoginSate: function (newd, old) {
                this.isPeople= newd.isPeople
                this.name = newd.name
            },
        },

        created() {

            let role = this.$role
            this.isPeople= newd.isPeople
            this.name = newd.name
        }
    }

尽管存在冗余数据,但首先是要解决问题。

END