Vuex (2) mutation

서영·2021년 10월 3일
0

Vue

목록 보기
2/6
post-thumbnail

Mutation은 state를 store로 옮기는 장점을 가지고 있다. 내부 component에서 직접 state를 추가해서 쓰지 말고, main.js에서 state를 정의해서 mutation으로 state를 작동시켜라!!

  • Mutation을 사용하는 이유 우리의 상태를 업데이트 하는 애플리케이션에서 우리가 바보같이 11을 더하는 실수를 했다면? 만약 우리가 2를 더하고 싶다고 결정하면? 우리는 두 개의 컴포넌트에서 그걸 바꿔야됨. 프로젝트가 커질수록 여러개의 컴포넌트에서 일일이 다 바꿔줘야 하는것. 이것이 mutation의 개념을 갖게 된 이유이다.

main.js에서 이용할 수 있다.

import { createApp } from 'vue';
import { createStore } from 'vuex';
import App from './App.vue';

const store = createStore({
    state() {
        return {
            counter: 0
        };
    },
    mutations: {
        increment(state) {
            state.counter += 2;
        },
    }
});
const app = createApp(App);
app.use(store);
app.mount('#app');
  • ChangeCounter.vue에서 addOne() 메소드 내부 this.$store.commit() 메소드를 이용한다.
  • commit은 Vuex의 빌트인 메소드이고 string값으로 내가 수행하고자 하는 mutation의 이름을 취한다.

한줄정리) main.js에서 mutations 속성을 통해 내가 정의한 state로 다양한 연산을 수행할 수 있고, mutation을 사용하려면 this.$store.commit() 메소드 안에 해당 mutation의 이름을 string값으로 넣어주면 된다.


일부 mutation은 arguments(parameter)를 필요로 할 수 있다.
increment mutation을 만들었을때 이건 하드코딩되어있다. → state.counter += 2;

🗣️ 우리는 value값으로만 increase되길 원해.

그래서 우리는 **payload**라는 두번째 argument를 사용할 수 있다.

main.js

mutations: {
        increment(state) {
            state.counter += 2;
        },
        increase(state, payload) {
            state.counter = state.counter + payload.value;
        }
    }
  • payload(이름은 아무거나 상관x)는 integer이거나 string이거나 object일수도 있고, 이를 통해 mutation의 모든 종류의 data가 predictable하다.
  • 우리는 state(counter)를 직접 조종하지 않고 오직 mutation만을 이용해서 state를 edit하고 approach할것이다.

App.vue(script의 methods 부분만)

methods: {
    addOne() {
      this.$store.commit('increase', { value: 10 }); //commit 표현법1

      this.$store.commit({ //commit 표현방법 2
        type:'increase',
        value:10
      });
    },
  },
  • 앞서 main.js의 increase mutation의 argument로 statepayload두 가지를 줬다.

  • value라고 쓴 건 내가 payload.value라고 이름붙였기 때문! 이름 붙이기 나름이다. (val 이라고 해도됨)

  • App.vue 전체 코드

    <template>
      <base-container title="Vuex">
        <the-counter></the-counter>
        <button @click="addOne">Add 10</button>
        <change-counter></change-counter>
      </base-container>
    </template>
    
    <script>
    import BaseContainer from './components/BaseContainer.vue';
    import TheCounter from './components/TheCounter.vue';
    import ChangeCounter from './components/ChangeCounter.vue';
    
    export default {
      components: {
        BaseContainer,
        TheCounter,
        ChangeCounter,
      },
      computed: {
        counter() {
          return this.$store.state.counter;
        },
      },
      methods: {
        addOne() {
          this.$store.commit('increase', { val: 10 }); //commit 표현법1
    
          this.$store.commit({ //commit 표현방법 2
            type:'increase',
            value:10
          });
        },
      },
    };
    </script>
    
    <style>
    * {
      box-sizing: border-box;
    }
    
    html {
      font-family: sans-serif;
    }
    
    body {
      margin: 0;
    }
    </style>
  • ChangeCounter.vue 전체 코드
    <template>
      <button @click="addOne">Add 2</button>
    </template>
    
    <script>
    export default {
      methods: {
        addOne() {
           this.$store.commit('increment');
        },
      },
    };
    </script>
    
    <style>
    </style>
  • main.js 전체 코드
import { createApp } from 'vue';
import { createStore } from 'vuex';
import App from './App.vue';
    
    const store = createStore({
        state() {
            return {
                counter: 0
            };
        },
        mutations: {
            increment(state) {
                state.counter += 2;
            },
            increase(state, payload) {
                state.counter = state.counter + payload.val;
            }
        }
    });
    
    const app = createApp(App);
    
    app.use(store);
    
    app.mount('#app');
profile
꾸준히 공부하기

0개의 댓글