개발이 좋아서/Vue가 좋아서

17장 Provide / Inject

zoaseo 2023. 9. 14. 16:34

1) Provide

하위 컴포넌트 항목에 데이터를 제공하려면 provider 역할을 하는 상위 컴포넌트 setup() 함수 내부에수 있습니다.

import { provide } from 'vue';

export default {
  setup() {
    provide('message', 'hello!');
  },
};

provide() 함수는 두 개의 파라미터를 받습니다.

  • 첫 번째 파라미터는 주입 키 : ****문자열 또는 Symbol이 될 수 있습니다. 주입 키는 하위 컴포넌트에서 주입된 값을 조회하는 데 사용됩니다.
  • 두 번째 파라미터는 제공된 값 : 값은 refs와 같은 반응성 데이터를 포함하여 모든 유형이 될 수 있습니다.
import { provide, ref } from 'vue';

export default {
  setup() {
    const message = ref('Hello World!');
    provide('message', message);
    return {
      message,
    };
  },
};

반응성 데이터를 사용하면 제곤된 값을 사용하는 하위 컴포넌트가 공급자 컴포넌트에 대한 반응 연결을 설정할 수 있습니다.

 

2) Inject

상위 컴포넌트에서 제공한 데이터를 삽입하려면 하위 컴포넌트 setup() 함수 내부에서 inject() 함수를 사용할 수 있습니다.

import { inject } from 'vue';
export default {
  setup() {
    const message = inject('message');
    const appMessage = inject('appMessage');
    return {
      message,
      appMessage,
    };
  },
};

주입된 값이 ref이면 반응성 연결을 유지할 수 있습니다.

 

3) Reactivity

Provide/Inject를 반응성 데이터로 제공할 때 가능한 모든 변경을 Provider 내부에서 하는 것이 좋습니다. 이렇게 Provider 내부에 배치되면 향후 유지관리가 용이합니다.

 

만약에 injector 내부 컴포넌트에서 반응성 데이터를 변경해야 하는 경우 데이터 변경을 제공하는 함수를 함께 제공하는 것이 좋습니다.

// Provider
const message = ref('Hello World!');
const updateMessage = () => {
  message.value = 'world!';
};
provide('message', { message, updateMessage });
// Injector
const { message, updateMessage } = inject('message');

그리고 주입된 컴포넌트에서 제공된 값을 변경할 수 없도록 하려면 readonly() 함수를 사용할 수 있습니다.

import { provide, readonly, ref } from 'vue';

provide('count', readonly(count));

4) Symbol 키 사용

대규모 애플리케이션에서 다른 개발자와 함께 작업할 때 잠재적 충돌을 피하기 위해 Symbol 주입 키를 사용하는 것이 가장 좋습니다.

// keys.js
export const myInjectionKey = Symbol()
// in provider component
import { provide } from 'vue'
import { myInjectionKey } from './keys.js'

provide(myInjectionKey, {
  /* data to provide */
})
// in injector component
import { inject } from 'vue'
import { myInjectionKey } from './keys.js'

const injected = inject(myInjectionKey)

5) App-level Provide

컴포넌트에서 데이터를 제공하는 것 외에도 App-level에서 제공할 수도 있습니다.

import { createApp } from 'vue';
import App from './App.vue';
const app = createApp(App);
app.provide('appMessage', 'Hello app message');
app.mount('#app');