插件
Nuxt Kit 提供了一组工具来帮助你创建和使用插件。你可以通过这些函数将插件或插件模板添加到你的模块中。
插件是自包含的代码,通常用于为 Vue 添加应用级功能。在 Nuxt 中,插件会自动从 plugins/
目录导入。然而,如果你需要在模块中附带插件,Nuxt Kit 提供了 addPlugin
和 addPluginTemplate
方法。这些工具允许你自定义插件配置,更好地满足你的需求。
addPlugin
注册一个 Nuxt 插件并将其添加到插件数组中。
用法
import { addPlugin, createResolver, defineNuxtModule } from '@nuxt/kit'
export default defineNuxtModule({
setup () {
const { resolve } = createResolver(import.meta.url)
addPlugin({
src: resolve('runtime/plugin.js'),
mode: 'client',
})
},
})
类型
function addPlugin(plugin: NuxtPlugin | string, options?: AddPluginOptions): NuxtPlugin
参数
plugin
:插件对象或插件路径字符串。若传入字符串,则会被转换为插件对象,src
属性设置为该字符串值。
若传入插件对象,则必须包含以下属性:
属性 | 类型 | 是否必需 | 描述 |
---|---|---|---|
src | string | true | 插件文件的路径。 |
mode | 'all' | 'server' | 'client' | false | 设置为 'all' 时,插件会包含在客户端和服务器端的构建中;设置为 'server' 时只包含在服务器端构建;设置为 'client' 时只包含在客户端构建。你也可以在指定 src 时使用 .client 和 .server 修饰符,使插件仅在客户端或服务器端使用。 |
order | number | false | 插件的执行顺序。用于更细粒度地控制插件顺序,仅建议高级用户使用。数字越小越先执行,用户插件默认顺序为 0 。建议将 order 设置在 -20 (在 Nuxt 插件之前运行的 pre 插件)到 20 (在 Nuxt 插件之后运行的 post 插件)之间。 |
除非必要,避免使用
order
。如果你只是想在 Nuxt 默认插件之后注册插件,请使用 append
。options
:可选对象,包含以下属性:
属性 | 类型 | 是否必需 | 描述 |
---|---|---|---|
append | boolean | false | 若为 true ,插件将追加到插件数组末尾;若为 false ,则会插入数组开头。默认为 false 。 |
示例
import { addPlugin, createResolver, defineNuxtModule } from '@nuxt/kit'
export default defineNuxtModule({
setup () {
const { resolve } = createResolver(import.meta.url)
addPlugin({
src: resolve('runtime/plugin.js'),
mode: 'client',
})
},
})
export default defineNuxtPlugin((nuxtApp) => {
const colorMode = useColorMode()
nuxtApp.hook('app:mounted', () => {
if (colorMode.preference !== 'dark') {
colorMode.preference = 'dark'
}
})
})
addPluginTemplate
添加一个模板并注册为 Nuxt 插件。此方法适用于需要在构建时生成代码的插件。
用法
import { addPluginTemplate, defineNuxtModule } from '@nuxt/kit'
export default defineNuxtModule({
setup (options) {
addPluginTemplate({
filename: 'module-plugin.mjs',
getContents: () => `import { defineNuxtPlugin } from '#app/nuxt'
export default defineNuxtPlugin({
name: 'module-plugin',
setup (nuxtApp) {
${options.log ? 'console.log("Plugin install")' : ''}
}
})`,
})
},
})
类型
function addPluginTemplate(pluginOptions: NuxtPluginTemplate, options?: AddPluginOptions): NuxtPlugin
参数
pluginOptions
:插件模板对象,包含以下属性:
属性 | 类型 | 是否必需 | 描述 |
---|---|---|---|
src | string | false | 模板文件路径。若未提供 src ,则必须提供 getContents 。 |
filename | string | false | 模板文件名。若未提供,将从 src 路径生成,此时 src 属性必填。 |
dst | string | false | 目标文件路径。若未提供,将基于 filename 路径和 Nuxt 的 buildDir 选项生成。 |
mode | 'all' | 'server' | 'client' | false | 设置为 'all' 时,插件会包含在客户端和服务器端的构建中;设置为 'server' 时只包含在服务器端构建;设置为 'client' 时只包含在客户端构建。你也可以在指定 src 时使用 .client 和 .server 修饰符,使插件仅在客户端或服务器端使用。 |
options | Record<string, any> | false | 传递给模板的参数。 |
getContents | (data: Record<string, any>) => string | Promise<string> | false | 接收 options 对象的函数,返回字符串或解析为字符串的 Promise。如果提供了 src ,该函数将被忽略。 |
write | boolean | false | 若为 true ,模板将被写入目标文件;否则只存在于虚拟文件系统中。 |
order | number | false | 插件的执行顺序。用于更细粒度地控制插件顺序,仅建议高级用户使用。数字越小越先执行,用户插件默认顺序为 0 。建议将 order 设置在 -20 (在 Nuxt 插件之前运行的 pre 插件)到 20 (在 Nuxt 插件之后运行的 post 插件)之间。 |
动态插件生成推荐使用
getContents
。除非必要,避免设置 order
。options
:可选对象,包含以下属性:
属性 | 类型 | 是否必需 | 描述 |
---|---|---|---|
append | boolean | false | 若为 true ,插件将追加到插件数组末尾;若为 false ,则会插入数组开头。默认为 false 。 |
示例
根据不同选项生成插件模板
当你需要在构建时动态生成插件代码时,使用 addPluginTemplate
。它允许你基于传入的选项动态生成不同的插件内容。例如,Nuxt 内部使用此功能生成 Vue 应用配置。
module.ts
import { addPluginTemplate, defineNuxtModule } from '@nuxt/kit'
export default defineNuxtModule({
setup (_, nuxt) {
if (nuxt.options.vue.config && Object.values(nuxt.options.vue.config).some(v => v !== null && v !== undefined)) {
addPluginTemplate({
filename: 'vue-app-config.mjs',
write: true,
getContents: () => `import { defineNuxtPlugin } from '#app/nuxt'
export default defineNuxtPlugin({
name: 'nuxt:vue-app-config',
enforce: 'pre',
setup (nuxtApp) {
${Object.keys(nuxt.options.vue.config!)
.map(k => `nuxtApp.vueApp.config[${JSON.stringify(k)}] = ${JSON.stringify(nuxt.options.vue.config![k as 'idPrefix'])}`)
.join('\n')
}
}
})`,
})
}
},
})
这会根据提供的配置生成不同的插件代码。
export default defineNuxtConfig({
vue: {
config: {
idPrefix: 'nuxt',
},
},
})
import { defineNuxtPlugin } from '#app/nuxt'
export default defineNuxtPlugin({
name: 'nuxt:vue-app-config',
enforce: 'pre',
setup (nuxtApp) {
nuxtApp.vueApp.config["idPrefix"] = "nuxt"
}
})
使用 EJS 模板生成插件
你也可以使用 EJS 模板生成插件。通过 options
属性传递参数,并在 EJS 模板内使用这些参数生成插件内容。
import { addPluginTemplate, createResolver, defineNuxtModule } from '@nuxt/kit'
export default defineNuxtModule({
setup (options, nuxt) {
const { resolve } = createResolver(import.meta.url)
addPluginTemplate({
src: resolve('templates/plugin.ejs'),
filename: 'plugin.mjs',
options: {
ssr: nuxt.options.ssr,
},
})
},
})
import { VueFire, useSSRInitialState } from 'vuefire'
import { defineNuxtPlugin } from '#imports'
export default defineNuxtPlugin((nuxtApp) => {
const firebaseApp = nuxtApp.$firebaseApp
nuxtApp.vueApp.use(VueFire, { firebaseApp })
<% if(options.ssr) { %>
if (import.meta.server) {
nuxtApp.payload.vuefire = useSSRInitialState(undefined, firebaseApp)
} else if (nuxtApp.payload?.vuefire) {
useSSRInitialState(nuxtApp.payload.vuefire, firebaseApp)
}
<% } %>
})
如果你将
compatibilityVersion
设置为 4
,Nuxt 默认不再使用 lodash.template
来编译模板。你仍然可以通过开启 experimental.compileTemplate
选项启用该功能,但 EJS 模板的支持将在下一个大版本中被完全移除。