【Vue】状态管理

  页面应用需要Vuex管理全局/模块的状态,大型单页面组件如果靠事件(events)/属性(props)通讯传值会把各个组件耦合在一起。因
此需要Vuex统一管理,当然如是小型单页面应用,引用Vuex反而会增加复杂度。因此需要衡量引用Vuex增加的收益是否大于成本。
 

快速入门

1. 安装vuex库

cnpm install -S vuex

2. 创建Vuex.Store

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

Vue.use(Vuex);

const store = new Vuex.Store({
    //组件数据源,单一的state属性
    state: {
        clickCount: 0
    },
    //相当于属性,封装获取state
    getters: {
        getClickCount: state => {
            return state.clickCount;
        }
    },
    //封装引起状态变化的方法
    mutations: {
        increment(state) {
            state.clickCount++;
        }
    },
    //类似于 mutation,不同在于actions支持异步,不是直接变更状态,而是提交到mutation
    actions: {
        increment(context) {
            context.commit('increment')
        },
        async incrementAsync({ commit }) {
            return new Promise((resolve, reject) => {
                setTimeout(() => {
                    try {
                        commit('increment');
                        resolve(new Date().getTime() + '  成功执行');
                    } catch (e) {
                        reject(e);
                    }
                }, 1000)
            });
        }
    }
});
export default store;

3. Vue实例加入store

new Vue({
    router: router,
    store: store,
    render: h => h(App),
}).$mount('#app')

4. 组件获取store值

<script>
import { mapGetters } from "vuex";

export default {
  computed: mapGetters({ count: ["getClickCount"] }),
};
</script>

5. 组件触发更新

<script>
export default {
  data() {
    return { times: 0 };
  },
  methods: {
    increment() {
      this.times++;
      //分发到action
      this.$store.dispatch("incrementAsync");
      //提交到mutations
      this.$store.commit("increment");
    },
  },
};
</script>

解析

Vuex 是什么?


  

  Vuex 是一个专为 Vue.js 应用程序开发的状态管理模式。它采用集中式存储管理应用的所有组件的状态,并以相应的规则保证状态以一种可预测的方式发生变化。Vuex 也集成到 Vue 的官方调试工具devtools extension,提供了诸如零配置的 time-travel 调试、状态快照导入导出等高级调试功能。

State - 数据源


Vuex 使用单一状态树——是的,用一个对象就包含了全部的应用层级状态。

Vue通过store选项,调用Vue.use(Vuex)注入到每一个子组件中(类似路由)

组件获取State

computed: {
    count () {
      return this.$store.state.count
 }
}

或者使用辅助函数mapState

computed: mapState({
    // 箭头函数可使代码更简练
    count: state => state.count
})

Getter - 数据封装读取(类似属性)


Getter 接受 state 作为其第一个参数

getters: {
    doneTodos: state => {
      return state.todos.filter(todo => todo.done)
    },
    getTodoById: (state) => (id) => {
      return state.todos.find(todo => todo.id === id)
    }
  }

通过属性访问

store.getters.doneTodos

通过方法访问

store.getters.getTodoById(2)

Getters 也提供了一个辅助函数方便访问(mapGetters )

Mutation - 进行状态更改的地方


定义Mutation

mutations: {
  increment (state, n) {
    state.count += n
  }
}

组件触发变更

store.commit('increment', 1)

Mutations也提供辅助函数(mapMutations)

import { mapMutations } from 'vuex'

export default {
  // ...
  methods: {
    ...mapMutations([
      'increment', // 将 `this.increment()` 映射为 `this.$store.commit('increment')`

      // `mapMutations` 也支持载荷:
      'incrementBy' // 将 `this.incrementBy(amount)` 映射为 `this.$store.commit('incrementBy', amount)`
    ]),
    ...mapMutations({
      add: 'increment' // 将 `this.add()` 映射为 `this.$store.commit('increment')`
    })
  }
}

注意事项

  • Mutation 必须是同步函数
  • 最好提前在你的 store 中初始化好所有所需属性。
  • 需要在对象上添加新属性时使用 Vue.set 或 替换旧对象

Action - 对Mutation封装


Action 类似于 mutation,不同在于:

  • Action 提交的是 mutation,而不是直接变更状态。
  • Action 可以包含任意异步操作。

定义Action

actions: {
  increment ({ commit }) {
    commit('increment')
  }
}

组件分发Action

store.dispatch('increment')

支持异步方式分发

actions: {
        async incrementAsync({ commit }) {
            return new Promise((resolve, reject) => {
                setTimeout(() => {
                    try {
                        commit('increment');
                        resolve(new Date().getTime() + '  成功执行');
                    } catch (e) {
                        reject(e);
                    }
                }, 1000)
            });
        }
    }

组件调用异步分发

this.$store.dispatch("incrementAsync").then(
        (data) => {
          console.log(data);
        },
        (err) => {
          console.log(err);
        }
      );

参考文章

转发请标明出处:https://www.cnblogs.com/WilsonPan/p/12773090.html

(0)

相关推荐

  • 在vue-element-admin中使用Vuex

    参考: vuex官方文档 https://vuex.vuejs.org/zh/ Vuex快速使用 https://mp.weixin.qq.com/s/OnVcgBQlSLHiR12WXN5nbQ 模 ...

  • vue中 Vuex

    一.什么是Vuex Vuex 是一个专为 Vue.js 应用程序开发的状态管理模式.它采用集中式存储管理应用的所有组件的状态,并以相应的规则保证状态以一种可预测的方式发生变化. 状态,其实指的是实例之 ...

  • 一切前端概念,都是纸老虎

    (给前端大学加星标,提升前端技能.) 作者:姜小抖 https://zhuanlan.zhihu.com/p/53599723 这篇文章试着聊明白这一堆看起来挺复杂的东西.在聊之前,大家要始终记得一句 ...

  • Vue3.x 从零开始(五)—— Router + Vuex + TypeScript 实战演练(上)

    前面的几篇文章已经大致介绍了 Vue 3 的常用 API,现在综合起来做一个实战演练 配合完整代码食用更香哦,项目地址:https://github.com/wisewrong/test-vue3-d ...

  • nuxt中使用Vuex

    问题 如何在nuxt中使用Vuex? 以官网例子, 模块方式引用--计数器为例子 图1 计数器示例 目录结构 图2 目录结构 js模块写法 // user.js // state为一个函数, 注意箭头 ...

  • vue系列教程之微商城项目|vuex全局状态管理-加入购物车

    问题描述 vuex简介 vuex是vue项目中用于管理全局状态的插件,如果对状态二字不明了,就简单理解成全局变量即可. 全局状态管理方式有很多,千奇百怪,比如bus总线.自定义一个js文件等,感兴趣可 ...

  • 航空复杂系统技术状态管理方法研究

    图片来源:航空工业 二战及战后期间,美国开始研制先进的武器系统.产品变得越来越复杂,涉及多个学科,研制难度大,常常需要多个公司的广泛协作,例如阿特拉斯参与单位就有2000多个,这就要求参与研制的部门接 ...

  • 通过Dapr实现一个简单的基于.net的微服务电商系统(五)——一步一步教你如何撸Dapr之状态管理

    今天 状态管理和上一章的订阅发布都算是Dapr相较于其他服务网格框架来讲提供的比较特异性的内容,今天我们来讲讲状态管理. 附录:(如果你觉得对你有用,请给个star) 一.电商Demo地址:https ...

  • 甘超波:NLP中EMBA状态管理

    哈喽,大家好我是甘超波,一名NLP爱好者,每天一篇文章,分享我的NLP实战经验和案例,希望给你些启发和帮助,这是第23篇原创文章 什么是EMBA EMBA:是总裁班吗? 在NLP中EMBA指的一种状态 ...

  • 15 个优秀的 Vue 后台管理模板

    Vue中文社区 今天 以下文章来源于大迁世界 ,作者前端小智 大迁世界我要先坚持分享20年,大家来一起见证吧. 后台的模板是我们做后台管理系统经常所需要的东西.虽然,我们总可以花很多时间从头开始设计自 ...

  • 技术状态管理必备知识,找全了!

    技术状态管理必备知识,找全了!

  • 航天工程的技术状态管理流程探讨

    周文明 李孝鹏 李福秋陈露 刘金燕 (中国航天标准化与产品保证研究院,北京,100071) 关键词:航天工程:技术状态管理:管理流程. 技术状态管理是在产品寿命周期内对性能.功能.物理特性等进行监控和 ...

  • 指南解读:老年2型糖尿病合并体力虚弱状态管理声明

    中国研究型医院学会糖尿病学专业委员会联合医咖会推出:研医论道.针对糖尿病领域的指南.最新文献.会议资讯,学会专家深度解读,全方位剖析领域热点!第23期由华中科技大学同济医学院附属同济医院的刘喆隆教授带 ...

  • 07 | 状态管理:Flutter 状态管理及对比选型

    上一课时我详细介绍了有/无状态组件的应用设计,但是在设计过程中,还缺乏一个对状态管理的考虑.本课时介绍状态管理设计的必要性,以及一些常见的状态管理技术对比,最后再着重通过 Provider 来优化前一 ...