@Watch 질문 드립니다!
646
작성한 질문수 8
안녕하세요? watch 속성 질문 드립니다.
<div>
<p>
@Watch
</p>
<button @click="changeMessage">메세지 변경</button>
<div>{{cMsg}}</div>
</div>
import { Component, Vue, Watch } from 'vue-property-decorator';
export default class Home extends Vue {
public message: string = 'hello children';
public cMsg: string | undefined;
public alertMsg: string = '변경이 감지되었습니다.';
// immediate : 즉시 호출하겠다는 의미.
// deep : object 내의 속성값까지 감시.
// @Watch('cMsg', {immediate: true, deep: true})
@Watch('cMsg')
public watchAlertMsg(value: string | undefined, oldValue: string | undefined) {
console.log(value);
console.log(oldValue);
alert(this.alertMsg);
}
public changeMessage() {
this.cMsg = 'change';
}
}
위와 같이 코딩을 했는데,
cMsg 상태변수에 '' 이런식으로 초기화를 해둔경우는 정상적으로 동작을 하는데,
위와 같이 하면 왜 변경감지가 안되는지 알고싶습니다.
TS를 사용안한 vue에서는 테스트를 해보지는 못했습니다..ㄷㄷ
public cMsg: string | undefined = '';
위와 같이 초기화를 해주면,
옆에 사진과 같이, 해당 컴포넌트 상태변수로 존재합니다.
= ''; 구문을 빼면, 상태변수 자체도 안보이구요
제가 TS구문을 잘 몰라서 이런거 같기는 한데..
public cMsg: string | undefined
해당 상태변수에 문자열 또는 undefined 가 할당이 될수 있어 이거 아닌가요? 그러면 제 생각은
cMsg = undefined; 이런거니 여기서 값이 바뀌면 감지가 되야 하는거같은데..ㅠㅠ 어렵네요
watch: {
testWatch(after, before) {
console.log('감지?');
console.log(before);
console.log(after);
}
},
data() {
return {
testWatch : undefined,
};
}
위 와 같이 하면, 정상적으로 감지(값을 변경할때마다)가 되어서 watch 속성 콜백함수가 호출이 됩니다.
TS 당신은 왜..ㅠㅠ
답변 2
1
안녕하세요! ChangHyeon Bae님!
Watch는 데이터의 변경을 관찰합니다.
질문 주신 케이스에서 Watch가 동작하지 않는 이유는,
cMsg라는 속성이 없기 때문입니다. 없는 속성에 Watch를 설정해놓은 것과 마찬가지지요.
public cMsg: string | undefined ;
위와 같이 분명히 선언했는데 왜 없을까요?
그 이유는, vue-cli로 코드를 빌드하면, webpack과 ts-loader로
타입스크립트 문법을 자바스크립트로 컴파일을 하게 됩니다.
이 때 프로퍼티를 확인해서 값이 할당된 프로퍼티만 객체의 속성으로 추가하기 때문입니다.
public cMsg: string | undefined = undefined;
또한 위와 같은 코드도 동일하게 동작하지 않습니다.
Vue 공식 문서에서 아래와 같이 설명하고 있습니다.
"Vue는 루트 수준의 반응성 속성을 동적으로 추가 할 수 없으므로
모든 루트 수준의 반응성 데이터 속성을 빈 값으로라도 초기에 선언하여 Vue 인스턴스를 초기화해야합니다."
export default class Home extends Vue {
public cMsg: string | undefined;
created() {
// undefined;
console.log(this);
}
}
위와 같이 created hook에서 this를 콘솔로 출력해보면,
cMsg라는 속성은 없는것을 확인하실 수 있습니다.
그래서 이로인해 발생하는 문제점을 막기 위해 타입스크립트에서는
tsconfig.json에 특별한 설정을 하지 않거나, !를 붙이지 않은 클래스 프로퍼티에 대해서는
에러를 발생하고 있습니다.
@Prop과 같이 특수한 경우가 아닐때는 반드시 undefined가 아닌 값으로 초기화 해주시기 바랍니다.
(공통된 빈값이 필요한 경우에는 null을 사용하세요.)
참고로, changeMessage라는 메서드에서 값을 할당하고 있긴 하지만,
이 경우에는 값을 수정하는것이 아닌 속성을 "추가"하는 것입니다!
Vue의 Watch는 속성의 추가/제거에 대해 감지할 수 없는 한계를 가지고 있습니다.
(자세한 내용은 https://kr.vuejs.org/v2/guide/reactivity.html<- 링크를 방문하세요.)
0
친절한 답변 정말로 감사합니다!
결론은 data 옵션에 해당 상태변수 자체가 존재하지 않는 상태에서 watch를 걸어버린거네요 ㅠㅠ
그래도 여전히 읽어보면서 의문인건.
public cMsg: string | undefined = undefined;
TS로 초기화 해준 undefined와
<template>
<div>
<button @click="changeValue">
watch 감지!
</button>
</div>
</template>
<script>
export default {
name: "Watch",
watch : {
changeVal(value, oldValue) {
console.log('감지?');
console.log(value);
console.log(oldValue);
},
},
data(){
return {
changeVal : undefined
}
},
methods : {
changeValue() {
this.changeVal = Math.floor(Math.random() * 10) + 1; // 1 ~ 10 난수 생성
}
}
}
</script>
<style scoped>
</style>
SFC 방식으로 한, 이거에 동작 차이는 역시 아직도 의문이네요.
소스 공유좀 해주세요
0
252
0
target null 에러뜨시는 분들
0
331
0
라우터 구조잡기 소스
0
285
0
새로 추가한 인스턴스 상태 관리
0
247
0
App.vue의 $store
0
193
0
npm run serve 에러
0
221
0
Cannot find module '@/components/message.vue' or its corresponding type declarations.
0
1152
2
prop !
0
194
0
@ MutationActions
0
179
0
mapGetters 내 정의가 안되요 ㅠ
0
260
0
안녕하세요! @Prop() readonly id(느낌표):string; 에서 !(느낌표) 를 찍는 이유가 궁금합니다 :)
0
227
0
store 사용 방법 관련 질문입니다.
0
240
1
moduleA.store.ts내에서 RootState가 하는일은 무엇인가요?
0
179
0
removeItem 에서 element 가 하나 남았을 때 삭제가 되지 않는 문제
0
373
2
Property '$route' does not exist on type 'ItemList'. 이 에러는 무엇인가요..?
0
862
1
Cannot find module '@/components/message.vue'.
0
2873
6
@Action, @Mutation 등으로 지정된 변수의 타입
0
231
1
안녕하세요. 강의 잘 들었습니다.
0
168
0
Axios Post보낼때 어떤 식으로 구성하는게 좋을까요?
0
663
1
안녕하세요! v-for(v-bind:key), slice() 관련 질문이 있어요!
2
667
3
에러 표시 질문이요!
1
403
3
vuex-module-decorators 보다 오리지널 모듈 형태를 선호하시는 이유가 무엇이신가요?
1
381
2
안녕하세요. 초기 셋팅시 질문있습니다.
1
296
2
안녕하세요! Vuex, actions 질문이 있습니다.
1
305
2





