watch
watch 사용법, watchcomputed의 차이

watch

1. 기본

watch(감시할 데이터, 콜백함수, 기타옵션(ex.즉시실행))


<h1>{{ msg }}</h1>
<input v-model="msg">

const msg = ref('');
watch(msg, (newValue, oldValue) => {
  // DOM 조작 ~
  // API ~
  // state 변경 ~
  console.log('newValue:', newValue);
  console.log('oldValue:', oldValue);
});

2. getter와 watch

<p>
  x:
</p>
<input v-model="x">

<p>
  y:
</p>
<input v-model="y">
const x = ref(0);
const y = ref(0);

watch(
  () => x.value + y.value,
  (sum, oldValue) => {
    console.log('sum:', sum);
    console.log('oldValue:', oldValue);
  },
);

여기서 sum은? x.value + y.value이다
즉, x.value+y.value이 값의 결과 자체가 변화가 있다면 콜백함수가 실행된다

3. 하나씩 조회 => array

watch(
  [x, y],
  ([newX, newY], [oldX, oldY])=>{
    console.log('값이 변화했습니다')
    console.log('new:', newX, newY);
    console.log('old:', oldX, oldY);
});

xy값이 개별적으로 인식되는 것을 확인할 수 있다

4. object와 watch

object를 watch의 감시 대상데이터로 설정해보자

준비

object 선언

const person = reactive({
  name: '홍길동',
  age: 30,
  hobby: '운동',
  obj: {
    count: 0,
  },
});

버튼 선언

<button @click="countUp">
    person.obj.countUp
</button>
const countUp = () => person.obj.count++;

object를 감시 대상으로 할 경우

reactive(object)를 감시 대상으로 했을 경우는 정상적으로 동작한다

watch(
  person,
  (newValue, oldValue) => {
    console.log('newValue', newValue.obj.count);
    console.log('oldValue', oldValue.obj.count);
  }
);

oldValuenewValue두개 모두
같은 Object를 가르키기때문에 출력값이 서로 동일하게 나온다

//클릭한번째
newValue 1
oldValue 1

//클릭두번째
newValue 2
oldValue 2

object의 속성값을 대상으로 할 경우

watch(
  person.obj.count,
  (newValue, oldValue) => {
    console.log('newValue', newValue);
    console.log('oldValue', oldValue);
  }
);

반응하지않는다.

  • personreactive객체이지, person.objperson.obj.countreactive객체가 아니기때문이다

그렇다면 getter를 사용

getter를 사용하해보자 대신 person.obj로 해보자

watch(
  () => person.obj,
  (newValue, oldValue) => {
    console.log('newObj', newValue);
    console.log('oldObj', oldValue);
  }
);

되지 않는다 왜냐하면 getter는 최종적인 값만 인식한다. obj.count가 변경되어도 obj의 자체 즉 오브젝트 객체는 변함이 없기때문이다(주소참조이기때문)
이때는 person.obj 자체가 변해야한다.

const person = reactive({
  ...
  obj: {
    count: 0 -> 1
  }
})
// person.obj 감지안됨

person.obj = "hello"
// 감지됨, obj가 변경되었기때문

object 자체를 바꿔야한다


person.obj.countgetter하면 예상과 같이 잘 동작한다

watch(
  	() => person.obj.count,
    (newValue, oldValue) => {
      console.log('newObj', newValue);
      console.log('oldObj', oldValue);
    }
  );

computed vs watch
computedrefreactive같은 Vue데이터들과 종속관계를 자동으로 세팅하고자 하는경우
watchrefreactive같은 Vue데이터들 변경시점에 특정 액션(call api, push route, state)를 취하고자할때
웬만하면 computed를 사용하자

watchEffect

watchEffect(() =>{
    console.log('watchEffect 실행!');
    console.log('x:', x.value);
    console.log('y:', y.value);
  }
  )

x.valuey.value에 변화가 있으면 콜백함수가 실행된다.

watchwatchEffect의 차이점

  • watch는 명시적으로 관찰할 소스를 나타낼수 있다. 즉시 실행되지않는다.
  • watchEffect는 명시적으로 관찰할 소스를 나타내지않고, 콜백함수 안에 있는 값(ref, reactive)들의 변화가 있을때 실행된다. 또한, 즉시 실행된다.



참고자료: Vue3 완벽 마스터: 기초부터 실전까지 - “기본편”

소스코드 바로확인하기

댓글 쓰기