본문 바로가기
개발/Vue

[Vue] Vuex 활용해보기 03 - Mutations

by JaeHoist 2022. 12. 28.

출처 : https://joshua1988.github.io/web-development/vuejs/vuex-getters-mutations/

(1) Mutations 란?

State 값을 변경하는 로직을 의미한다

-Getters 와의 차이점

  1. 인자를 받아 Vuex에 넘겨줄 수 있다.
  2. computed가 아닌 methods에 등록한다.

-Actrions 와의 차이점

  1.  Mutations는 동기적 로직을 정의
  2.  Actions는 비동기적 로직을 정의
    (Mutations의 성격 상 안에 정의한 로직들이 순차적으로 일어나야 각 컴포넌트의 반영 여부를 제대로 추적할 수 있기 때문)

이전까지의 진행 내용 중

 

맞지 않는 구현 방식

addCounter() {
                this.$store.state.counter++;
            },
subCounter() {
                this.$store.state.counter--;
            }

위와 같이 컴포넌트에서 직접 state에 접근하여 변경하는 방식은 상태관리 패턴에 맞지 않는 구현 방식이다.

여러 컴포넌트에서 같은 state 값을 동시에 제어하게 되면, state 값이 어느 컴포넌트에서 호출해서 변경된건지 추적하기 어렵기 때문이다.

따라서 commit을 이용하여 state를 변경해야 한다.

 

(2) Mutations 등록

store.js

import Vue from "vue";
import Vuex from "vuex";

Vue.use(Vuex);

export const store = new Vuex.Store({
    state:{
        counter: 0 
    },
    getters: {
      getCounter: function (state) {
          return state.counter;
      }
    },
    mutations: {		//mutations 등록
        addCounter: function (state) {
            return state.counter++;
        },
        subCounter: function (state) {
            return state.counter--;
        }
    }
});

 

(3) Mutations 사용

App.vue

<template>
  <div id="app">
    Parent counter : {{ getCounter }} <br>
    <button @click="addCounter">+</button>
    <button @click="subCounter">-</button>

    <child></child> <!--v-bind 삭제-->
  </div>
</template>

<script>
    import Child from "./Child.vue";
    import { mapGetters } from 'vuex'

    export default {
        components: {
            
            child: Child
        },
        data() {
            return {
                counter: 0
            };
        },
        methods: {
            // 이벤트 추가
            addCounter() {
                this.$store.commit('addCounter');	//this.$store.commit으로 mutaions 이벤트 호출
            },
            subCounter() {
                this.$store.commit('subCounter');
            }
        },
        computed:{
            ...mapGetters([
            'getCounter'
            ])
        }
    };
</script>

 

 

(4) Mutaions에 인자 값 넘기기

각 컴포넌트에서 state를 조작하는데 필요한 특정 값들을 넘기고 싶을 때는 commit에 두번째 인자를 추가한다.

 

store.js

import Vue from "vue";
import Vuex from "vuex";

Vue.use(Vuex);

export const store = new Vuex.Store({
    state:{
        counter: 0 
    },
    getters: {
      getCounter: function (state) {
          return state.counter;
      }
    },
    mutations: {
        addCounter: function (state) {
            return state.counter++;
        },
        subCounter: function (state) {
            return state.counter--;
        },
        addDoubleCounter: function (state, payload) { 
		//데이터 인자 명은 보통 payload를 많이 쓴다.
            return state.counter+= payload;
        }
    }
});

 

App.vue

<template>
  <div id="app">
    Parent counter : {{ getCounter }} <br>
    <button @click="addCounter">+</button>
    <button @click="subCounter">-</button>
    <button @click="addDoubleCounter">+2</button> //버튼 추가
    <child></child> 
  </div>
</template>

<script>
    import Child from "./Child.vue";
    import { mapGetters } from 'vuex'

    export default {
        components: {
            
            child: Child
        },
        data() {
            return {
                counter: 0
            };
        },
        methods: {
            // 이벤트 추가
            addCounter() {
                this.$store.commit('addCounter');
            },
            subCounter() {
                this.$store.commit('subCounter');
            },
            addDoubleCounter() {
                this.$store.commit('addDoubleCounter',2)
				//commit에 두번째 인자를 넘겨준다.
            }
        },
        computed:{
            ...mapGetters([
            'getCounter'
            ])
        }
    };
</script>

 

(5) mapMutations

mapGetters 와 마찬가지로, Vuex에 내장된 mapMutaions를 이용하여 코드 가독성을 높일 수 있다.

<template>
  <div id="app">
    Parent counter : {{ getCounter }} <br>
    <button @click="addCounter">+</button>
    <button @click="subCounter">-</button>
    <button @click="addDoubleCounter">+2</button>
    <child></child> 
  </div>
</template>

<script>
    import Child from "./Child.vue";
    import { mapGetters } from 'vuex'
    import { mapMutations } from 'vuex' //mapMutations import

    export default {
        components: {            
            child: Child
        },
        data() {
            return {
                counter: 0
            };
        },
        methods: {
            ...mapMutations([ //mapMutations 사용
               'addCounter'
            ]),
            ...mapMutations([
                'subCounter'
            ]),
            addDoubleCounter() {
                this.$store.commit('addDoubleCounter',2)
            }
        },
        computed:{
            ...mapGetters([
            'getCounter'
            ])
        }
    };
</script>

'개발 > Vue' 카테고리의 다른 글

[Vue] [Vue3] 템플릿 문법  (0) 2022.12.28
[Vue] [Vue3] Vue 앱 만들기  (0) 2022.12.28
[Vue] Vuex 활용해보기 01 - Vue앱과 비교, Vuex의 state  (0) 2022.12.28
[Vue] Vuex와 Store  (0) 2022.12.28
[Vue] Vue02  (0) 2022.12.28