Vuex helpers - parent,child와 state
Vuex helpers를 한번 더 이용해보자
이 예제는 캡틴 판교의 게시글에 올라와 있다
먼저 프로젝트를 만들어주고 해당 프로젝트로 이동
cd vuex_example
일단 parent component랑 child component를 만들어야지
/src/components에 각각 vue 파일을 만들어주자
//Parents.vue
<template>
<div id="app">
Parent counter : {{ counter }} <br>
<button @click="addCounter">+</button>
<button @click="subCounter">-</button>
<!-- Child 컴포넌트를 등록하고 counter 데이터 속성을 props로 전달한다. -->
<child v-bind:num="counter"></child>
</div>
</template>
<script>
import Child from "./Child.vue";
export default {
components: {
child: Child
},
data() {
return {
counter: 0
};
},
methods: {
addCounter() {
this.counter++;
},
subCounter() {
this.counter--;
}
}
};
</script>
//Child.vue
<template>
<div>
<hr>
Child counter : {{ num }} <br>
<button>+</button>
<button>-</button>
</div>
</template>
<script>
export default {
props: ["num"]
};
</script>
당연히 Home.vue도 수정해줘야지
<template>
<div id="app">
<Parents></Parents>
</div>
</template>
<script>
// @ is an alias to /src
import Parents from '../components/Parents.vue'
export default {
name: 'Home',
components: {
Parents,
}
}
</script>
근데 이렇게 되면,
Parents.vue = 상위 component의 counter 데이터를 prop속성으로 받았기 때문에
=> 같은 데이터 속성을 2개의 component에서 접근해 같은 값을 표현하는 거라
=> 버튼 클릭 시 parent, child component의 숫자가 동일하게 올라간다
세상 비효율적인 컴포넌트 간 데이터 전달을 Vuex로 해결해보자
npm install vuex
바로 vuex를 등록할 js파일을 하나 생성해주자
=> src/store/index.js 로 이미 존재하면 store.js로 바꿔주기만 하자
import Vue from 'vue'
import Vuex from 'vuex'
Vue.use(Vuex)
export const store = new Vuex.Store({
state: {
counter: 0
},
mutations: {
},
actions: {
},
modules: {
}
})
store.js를 쓰기 위해 main.js에 등록해줘야 한다
=> 이거도 되어있네...
import Vue from 'vue'
import App from './App.vue'
import router from './router'
import {store} from './store/store'
new Vue({
router,
store,
render: h => h(App)
}).$mount('#app')
오케이
이제 state부터 등록해주자
아까 써줬던 src/store/store.js로 가서 state를 추가하면 끝
state: {
counter: 0
}
여기서의 counter는 Parent component에서 사용하던 data 속성 counter랑 같다
state를 등록해줬으니 접근해보자
$store.state.counter로 접근할 수 있다
// Parents.vue
<template>
<div id="app">
Parent counter : {{ $store.state.counter }} <br>
<button @click="addCounter">+</button>
<button @click="subCounter">-</button>
<Child></Child>
</div>
</template>
<script>
import Child from "./Child.vue";
export default {
components: {
child: Child
},
methods: {
addCounter() {
this.$store.state.counter++;
},
subCounter() {
this.$store.state.counter--;
}
}
};
</script>
// Child.vue
<template>
<div>
<hr>
Child counter : {{ $store.state.counter }} <br>
<button>+</button>
<button>-</button>
</div>
</template>
<script>
export default {};
</script>
**
그런데 에러가 생겼다
Child counter도 보이지 않는다
1. Parents.vue 의 template에서 <child></child>로 해주어야 한다 (오타)
// Parents.vue
<template>
<div id="app">
Parent counter : {{ $store.state.counter }} <br>
<button @click="addCounter">+</button>
<button @click="subCounter">-</button>
<child></child>
</div>
</template>
<script>
import Child from "./Child.vue";
export default {
components: {
child: Child
},
methods: {
addCounter() {
this.$store.state.counter++;
},
subCounter() {
this.$store.state.counter--;
}
}
};
</script>
그러면 Child counter가 나타난다
갑자기 에러도 해결
원래는 <script>태그내에 있는 컴퍼넌트 속성에 컴퍼넌트를 추가하지 않아서 발생하는 문제라고 하는데
왜 갑자기 발생했고, 해결됐는지는 모르겠다
state에 counter 속성 추가 및 적용으로 달라진 건
- data 속성으로 선언한 counter 값을 없애고
- child component로 counter 값을 전달하지 않는 것이다
그러니까,
Parent 컴포넌트에서 관리하던 counter 데이터를 vuex의 state에 넘기면
⇒ Child 컴포넌트에서 접근하던 Parent component의 data 속성이 vuex로 갔기 때문에
⇒ Child에서는 vuex의 state를 보면 된다
⇒ Parent와 Child 모두 state를 접근 가능하게 됐고
⇒ 어떤 component든 이제 vuex로 counter를 접근할 수 있게 된 거다
어려 component간에 공유할 데이터를 효과적으로 다룰 수 있게 되었다는 의미.