Vuex 정리
2020-09-14 15:54:16

Vuex란

Vuex는 전역 저장소(data)를 사용하여 상태 관리를 하는 라이브러리

사용 이유

규모가 있는 app에서 같은 상태를 가진 여러 컴포넌트(부모/자식 또는 같은 레벨)끼리

데이터를 관리 를 하게 될 때 기존의 props나 $emit으로 하게 되면 코드가 복잡해져서

유지 보수 하기가 힘들어 지기 때문에 사용 한다고 한다.

설치

1
npm i vuex -S

저장소

시작은 src/store

MyStore.js

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
import Vue from "vue";
import Vuex from "vuex"; // vuex import

Vue.use(Vuex); // vuex 사용

const state = {
// 데이터
msg: "Hello! Vuex",
};

const mutations = {
// 데이터를 조작할 함수
changeMessage(state, msg) {
state.msg = msg;
},
};

export default new Vuex.Store({
state,
mutations,
});

실습

webpack-simple 버전으로 만들어서 실습을 해 본다.

1
vue init webpack-simple vuex_study

Message.vue

1
2
3
4
5
6
7
8
9
10
11
12
13
14
<template>
<h1>{{ msg }}</h1>
<!-- 데이터 표시 -->
</template>

<script>
export default {
computed: {
msg() {
return this.$store.state.msg; // this.$store.@@으로 저장소 데이터 접근
},
},
};
</script>

Input.vue

1
2
3
4
5
6
7
8
9
10
11
12
13
14
<template>
<input @keyup="changeMsg" />
<!-- 키보드 누를때마다 이벤트 -->
</template>

<script>
export default {
methods: {
changeMsg(event) {
this.$store.commit("changeMessage", event.target.value); // this.$store.commit("작성한 데이터 조작 함수", 값)
},
},
};
</script>

App.vue

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
<template>
<div id="app">
<img src="./assets/logo.png" />
<MessageComponent></MessageComponent>
<InputComponent></InputComponent>
</div>
</template>

<script>
import MessageComponent from "./components/Message";
import InputComponent from "./components/Input";
import Store from "./store/MyStore";

export default {
name: "app",
components: {
MessageComponent,
InputComponent,
},
store: Store, // store init
};
</script>

Getter

여러 컴포넌트에서 똑같은 방식으로 데이터를 조작해야할 경우 copy/paste해도 되지만 유지

관리할 때 골치 아프므로 이러한 케이스를 위해 Getter를 지원을 한다.

MyStore.js

1
2
3
4
5
6
7
8
9
10
11
12
// ...
const getters = {
lowerCase(state) {
return state.msg.toLowerCase(); // 데이터를 모두 소문자로 바꿈
},
};

export default new Vuex.Store({
state,
mutations,
getters,
});
1
2
3
4
5
6
7
8
9
10
11
12
13
14
<template>
<h1>{{ msg }}</h1>
</template>

<script>
export default {
computed: {
msg() {
// return this.$store.state.msg;
return this.$store.getters.lowerCase; // getter 호출
},
},
};
</script>

또는

1
2
3
4
5
6
7
8
9
10
11
<script>
import { mapGetters } from "vuex"; // helper, 내가 만든 getter 들을 가져올 수 있다.

export default {
computed: {
...mapGetters({
msg: "lowerCase",
}),
},
};
</script>

이러면 input에 대문자로 입력해도 자동으로 소문자로 바뀌어서 볼 수 있다.

작은 규모라도 기존에 알고 있는 props, $emit 보다 Vuex가 더 깔끔한 느낌이 든다.

다음 연습 프로젝트에서는 써봐야겠다.

참고

Prev
2020-09-14 15:54:16
Next