目录

Vuex的使用

李羽秋
李羽秋 2022年02月01日  ·  阅读 1,020

Vuex的使用

1.什么是状态管理模式?

Vuex是一个专为Vue.js应用程序开发的状态管理模式。它采用集中式存储管理应用的所有组件的状态,

并以相应的规则保证状态以一种可预测的方式发生变化。Vuex也集成到Vue的官方调式工具devtools extension,

提供了诸如零配置的time-travel调式、状态快照导入导出等高级调式功能。

2.组成部分

  • state,驱动应用的数据源;

  • view,以声明方式将 state 映射到视图;

  • actions,响应在 view 上的用户输入导致的状态变化。

    以下是一个表示“单向数据流”理念的简单示意:

    image-20220127125605537

    3.什么情况应该使用Vuex?

    Vuex可以帮助我们管理共享状态,并附带了更多的概念和框架。这需要对短期和长期效益进行权衡。

    如果您不打算开发大型单页应用,使用Vuex可能是繁琐冗余的。确实是如此——如果您的应用够简单,您最好

    不要使用Vuex.一个简单的store模式就足够您所需。但是您需要构建一个中大型单页应用,您很可能会考虑如何更好地

    在组件外部管理状态,Vuex将会成为自然而然的选择。

    4.安装并使用vuex

    4.1 安装依赖

    npm install vuex --save
    

    4.2 在main.js中注入vuex

    import Vuex from 'vuex'
    Vue.use(Vuex)
    

    4.3 在src目录下,创建store文件夹,并新建index.js,内容如下

    import Vue from "vue";
    import Vuex from "vuex";
    Vue.use(Vuex)
      export default new Vuex.Store({
          state:{
              hello:12
          },
          mutations:{
              increment:state => state.hello++,
              decrement:state => state.hello--
          },
          getters:{
              change: state => {
                  return  "结果是"+state.hello
              }
    
          }
      })
    

    4.4 在main.js导入store

    import store from "@/store/store";
    new Vue({
      render: h => h(App),
      Router,
      store
    
    }).$mount('#app')
    

    4.5 新建hello.vue,内容如下

    <template>
      <div>
        {{count}}
        <button @click="add">增加</button>
        <button @click="minus">减1</button>
        <p>{{desc}}</p>
      </div>
    </template>
    
    <script>
    export default {
      name: "Hello",
      computed:{
        count(){
          return this.$store.state.hello;
        },
        desc(){
          return this.$store.getters.change;
        }
      },
      methods:{
        add(){
          this.$store.commit('increment');
        },
        minus(){
          this.$store.commit('decrement');
        }
    
      }
    
    }
    </script>
    <style scoped>
    
    </style>
    
    

5. Getter

有时候我们需要从 store 中的 state 中派生出一些状态,例如对列表进行过滤并计数

组件:
computed: {
  doneTodosCount () {
    return this.$store.state.todos.filter(todo => todo.done).length
  }
}
-------------------------------------------------------------------------------
index.js:
const store = new Vuex.Store({
  state: {
    todos: [
      { id: 1, text: '...', done: true },
      { id: 2, text: '...', done: false }
    ]
  },
  getters: {
    doneTodos: state => {
      return state.todos.filter(todo => todo.done)
    }
  }
})

Vuex 允许我们在 store 中定义“getter”(可以认为是 store 的计算属性)。就像计算属性一样,getter 的返回值会根据它的依赖被缓存起来,且只有当它的依赖值发生了改变才会被重新计算。

6.Mutations

6.1基本介绍

更改 Vuex 的 store 中的状态的唯一方法是提交 mutation。Vuex 中的 mutation 非常类似于事件:每个 mutation 都有一个字符串的 事件类型 (type) 和 一个 回调函数 (handler)。这个回调函数就是我们实际进行状态更改的地方,并且它会接受 state 作为第一个参数:

const store = new Vuex.Store({
  state: {
    count: 1
  },
  mutations: {
    increment (state) {
      // 变更状态
      state.count++
    }
  }
})

你不能直接调用一个 mutation handler。这个选项更像是事件注册:“当触发一个类型为 increment 的 mutation 时,调用此函数。”要唤醒一个 mutation handler,你需要以相应的 type 调用 store.commit 方法:

store.commit('increment')

6.2 提交负载

你可以向 store.commit 传入额外的参数,即 mutation 的 载荷(payload)

// ...
mutations: {
  increment (state, n) {
    state.count += n
  }
}
store.commit('increment', 10)

在大多数情况下,载荷应该是一个对象,这样可以包含多个字段并且记录的 mutation 会更易读:

// ...
mutations: {
  increment (state, payload) {
    state.count += payload.amount
  }
}
store.commit('increment', {
  amount: 10
})

6.3 使用常量代替Mutation事件类型

使用常量替代 mutation 事件类型在各种 Flux 实现中是很常见的模式。这样可以使 linter 之类的工具发挥作用,同时把这些常量放在单独的文件中可以让你的代码合作者对整个 app 包含的 mutation 一目了然:

// mutation-types.js
export const SOME_MUTATION = 'SOME_MUTATION'
// store.js
import Vuex from 'vuex'
import { SOME_MUTATION } from './mutation-types'

const store = new Vuex.Store({
  state: { ... },
  mutations: {
    // 我们可以使用 ES2015 风格的计算属性命名功能来使用一个常量作为函数名
    [SOME_MUTATION] (state) {
      // mutate state
    }
  }
})

7. actions

在mutation中我们讲到,mutation是存放处理数据的方法集合,我们使用的时候需要commit。但是commit是同步函数,而且只能是

同步执行。那我们想异步操作怎么办?这时候就需要用到actions,actions可以理解为通过将muations里面处理数据的方法变成可异步

的处理数据的方法,简单的说就是异步操作数据。

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

让我们来注册一个简单的action:

const store = new Vuex.Store({
  state: {
    count: 0
  },
  mutations: {
    increment (state) {
      state.count++
    }
  },
  actions: {
    increment (context) {
      context.commit('increment')
    }
  }
})
store.dispatch('increment')

Action函数接受一个与store实例具有相同方法和属性的context对象,因此你可以调用context.commit提交一个mutation,或者

通过context.state 和 context.getters来获取state和getters。

分类:
标签: