plugins

Nuxt에는 Vue 애플리케이션 생성 시 Vue 플러그인 등을 사용할 수 있는 플러그인 시스템이 있다.

 

Nuxt는 자동으로 plugins/ 디렉토리의 파일을 읽고 Vue 애플리케이션 생성 시 이를 로드한다.

내부의 모든 플러그인은 자동으로 등록되므로 nuxt.config 에 별도로 추가할 필요가 없다.

파일 이름에.server  또는 .client  접미사를 사용하여 서버 또는 클라이언트 측에서 플러그인을 로드할 수 있다.

 

 

등록된 플러그인

디렉터리의 최상위 수준에 있는 파일(또는 하위 디렉터리 내의 인덱스 파일)만 플러그인으로 자동 등록된다.

 

디렉토리 구조

-| plugins/
---| foo.ts      // scanned
---| bar/
-----| baz.ts    // not scanned
-----| foz.vue   // not scanned
-----| index.ts  // currently scanned but deprecated

여기서는 foo.ts  bar/index.ts만 등록된다.

 

plugins 하위 디렉토리에 플러그인을 추가하려면 nuxt.config.ts 에서 옵션을 추가한다.

 

nuxt.config.ts

// nuxt.config.ts

export default defineNuxtConfig({
  plugins: [
    '~/plugins/bar/baz',
    '~/plugins/bar/foz'
  ]
})

 

플러그인 만들기

플러그인에 전달되는 유일한 인수는 nuxtApp 이다.

 

plugins/hello.ts

// plugins/hello.ts

export default defineNuxtPlugin(nuxtApp => {
  // Doing something with nuxtApp
})

 

객체 구문 플러그인

객체 구문을 사용하여 플러그인을 정의하는 것도 가능하다. 예를 들어:

 

plugins/hello.ts

// plugins/hello.ts

export default defineNuxtPlugin({
  name: 'my-plugin',
  enforce: 'pre', // or 'post'
  async setup (nuxtApp) {
    // this is the equivalent of a normal functional plugin
  },
  hooks: {
    // You can directly register Nuxt app runtime hooks here
    'app:created'() {
      const nuxtApp = useNuxtApp()
      // do something in the hook
    }
  },
  env: {
    // Set this value to `false` if you don't want the plugin to run when rendering server-only or island components.
    islands: true
  }
})

 

객체 구문을 사용하는 경우 나중에 속성을 정적으로 분석하여 더욱 최적화된 빌드를 생성할 수 있다. 따라서 런타임에 정의하면 안된다. 예를 들어, enforce: process.server ? 'pre' : 'post'  설정은 Nuxt가 플러그인에 대해 수행할 수 있는 향후 최적화를 무효화한다.

 

등록 순서

'알파벳순' 접두사를 붙여 플러그인이 파일이름에 번호을 매기는 방식으로 등록되는 순서를 제어할 수 있다.

 

디렉토리 구조

plugins/
 | - 01.myPlugin.ts
 | - 02.myOtherPlugin.ts

위 예에서 02.myOtherPlugin.ts는 01.myPlugin.ts에 의해 삽입된 모든 항목에 액세스할 수 있다.

 

이는 다른 플러그인에 의존하는 플러그인이 있는 상황에서 유용할 수 있다.

 

로딩 전략

병렬 플러그인

기본적으로 Nuxt는 플러그인을 순차적으로 로드한다. 플러그인을 parallel로 정의하면 Nuxt는 다음 플러그인을 로드하기 전에 플러그인 실행이 끝날 때까지 기다리지 않는다.

 

plugins/my-plugin.ts

// plugins/my-plugin.ts

export default defineNuxtPlugin({
  name: 'my-plugin',
  parallel: true,
  async setup (nuxtApp) {
    // the next plugin will be executed immediately
  }
})

 

종속성이 있는 플러그인

플러그인이 실행되기 전에 병렬 플러그인을 기다려야 하는 경우 플러그인 이름을 dependsOn 배열에 추가할 수 있다.

 

plugins/depending-on-my-plugin.ts

// plugins/depending-on-my-plugin.ts

export default defineNuxtPlugin({
  name: 'depends-on-my-plugin',
  dependsOn: ['my-plugin']
  async setup (nuxtApp) {
    // this plugin will wait for the end of `my-plugin`'s execution before it runs
  }
})

 

컴포저블 사용

컴포저블과 유틸을 Nuxt 플러그인에서 사용할 수 있다.

 

plugins/hello.ts

// plugins/hello.ts

export default defineNuxtPlugin((nuxtApp) => {
  const foo = useFoo()
})

 

그러나 몇 가지 제한 사항과 차이점이 있다는 점에 유의하자.

컴포저블이 나중에 등록된 다른 플러그인에 종속되는 경우 작동하지 않을 수 있다.플러그인은 다른 모든 것보다 먼저 순차적으로 호출된다. 아직 호출되지 않은 다른 플러그인에 의존하는 컴포저블을 사용할 수도 있다.

컴포저블이 Vue.js 수명 주기에 의존하는 경우 작동하지 않는다.일반적으로 Vue.js 컴포저블은 현재 컴포넌트 인스턴스에 바인딩되지만 플러그인은 nuxtApp 인스턴스에 바인딩된다.

 

헬퍼 제공

NuxtApp 인스턴스에 헬퍼를 제공하려면 플러그인의 provide 키에서 이를 반환해야 한다.

 

plugins/hello.ts

// plugins/hello.ts

export default defineNuxtPlugin(() => {
  return {
    provide: {
      hello: (msg: string) => `Hello ${msg}!`
    }
  }
})

그런 다음 컴포넌트에서 헬퍼를 사용할 수 있습니다.

 

components/Hello.vue

<!--
components/Hello.vue
-->

<script setup lang="ts">
// alternatively, you can also use it here
const { $hello } = useNuxtApp()
</script>

<template>
  <div>
    {{ $hello('world') }}
  </div>
</template>
글로벌 네임스페이스 오염을 방지하고 기본 번들 항목을 작게 유지하려면 헬퍼를 제공하는 대신 composables 을 사용하는 것이 좋다.

 

플러그인 Type

플러그인에서 헬퍼를 반환하면 자동으로 타입이 지정된다. useNuxtApp() 및 템플릿 내에서 반환을 위해 타입을 지정한 것을 볼 수 있다.

다른 플러그인 내에서 제공된 헬퍼를 사용해야 하는 경우 useNuxtApp()을 호출하여 입력된 버전을 얻을 수 있다. 그러나 일반적으로 플러그인 순서가 확실하지 않은 한 이를 피해야한다.

 

고급 사용 사례의 경우 다음과 같이 삽입된 속성 유형을 선언할 수 있다.

 

index.d.ts

// index.d.ts

declare module '#app' {
  interface NuxtApp {
    $hello (msg: string): string
  }
}

declare module 'vue' {
  interface ComponentCustomProperties {
    $hello (msg: string): string
  }
}

export {}
WebStorm을 사용하는 경우 이 문제가 해결될 때까지 @vue/runtime-core를 보완해야 할 수도 있다.

 

Vue 플러그인

vue-gtag와 같은 Vue 플러그인을 사용하여 Google Analytics 태그를 추가하려는 경우 Nuxt 플러그인을 사용할 수 있다. 

 

먼저 Vue 플러그인 종속성을 설치한다.

# yarn
yarn add --dev vue-gtag-next

# npm
npm install --save-dev vue-gtag-next

# pnpm
pnpm add -D vue-gtag-next

# bun
bun add -D vue-gtag-next

그런 다음 플러그인 파일을 만든다.

 

plugins/vue-gtag.client.ts

//plugins/vue-gtag.client.ts

import VueGtag, { trackRouter } from 'vue-gtag-next'

export default defineNuxtPlugin((nuxtApp) => {
  nuxtApp.vueApp.use(VueGtag, {
    property: {
      id: 'GA_MEASUREMENT_ID'
    }
  })
  trackRouter(useRouter())
})

 

Vue 지시어(Directives)

마찬가지로 플러그인에 사용자 정의 Vue 지시문을 등록할 수 있다.

 

plugins/my-directive.ts

// plugins/my-directive.ts

export default defineNuxtPlugin((nuxtApp) => {
  nuxtApp.vueApp.directive('focus', {
    mounted (el) {
      el.focus()
    },
    getSSRProps (binding, vnode) {
      // you can provide SSR-specific props here
      return {}
    }
  })
})
Vue 지시문을 등록하는 경우 한쪽을 렌더링할 때를 제외하고, 클라이언트와 서버 모두에 등록해야 한다. 지시문이 클라이언트 측에서만 의미가 있는 경우 언제든지 ~/plugins/my-directive.client.ts로 이동하고 ~/plugins/my-directive.server.ts에서 서버에 대한 '스텁' 지시문을 제공할 수 있다. 

 

참고) Custom Directives

'Nuxt 공식문서 번역 > Directories' 카테고리의 다른 글

server  (1) 2023.12.17
public  (0) 2023.12.17
pages  (1) 2023.12.17
node_modules  (0) 2023.12.17
modules  (0) 2023.12.17
  • 네이버 블로그 공유
  • 네이버 밴드 공유
  • 페이스북 공유