2023-04-07 16:02:47 +00:00
|
|
|
import type { Configuration as WebpackConfig, WebpackPluginInstance } from 'webpack'
|
2024-10-09 13:57:54 +00:00
|
|
|
import type { RspackPluginInstance } from '@rspack/core'
|
2023-04-07 16:02:47 +00:00
|
|
|
import type { UserConfig as ViteConfig, Plugin as VitePlugin } from 'vite'
|
2021-11-21 16:14:46 +00:00
|
|
|
import { useNuxt } from './context'
|
2023-12-23 14:22:58 +00:00
|
|
|
import { toArray } from './utils'
|
2021-11-21 16:14:46 +00:00
|
|
|
|
|
|
|
export interface ExtendConfigOptions {
|
|
|
|
/**
|
|
|
|
* Install plugin on dev
|
|
|
|
* @default true
|
|
|
|
*/
|
2023-03-29 10:59:57 +00:00
|
|
|
dev?: boolean
|
|
|
|
/**
|
|
|
|
* Install plugin on build
|
|
|
|
* @default true
|
|
|
|
*/
|
|
|
|
build?: boolean
|
2021-11-21 16:14:46 +00:00
|
|
|
/**
|
|
|
|
* Install plugin on server side
|
|
|
|
* @default true
|
|
|
|
*/
|
|
|
|
server?: boolean
|
|
|
|
/**
|
|
|
|
* Install plugin on client side
|
|
|
|
* @default true
|
|
|
|
*/
|
|
|
|
client?: boolean
|
2023-04-29 22:39:08 +00:00
|
|
|
/**
|
2023-10-10 11:14:55 +00:00
|
|
|
* Prepends the plugin to the array with `unshift()` instead of `push()`.
|
2023-04-29 22:39:08 +00:00
|
|
|
*/
|
|
|
|
prepend?: boolean
|
2022-06-22 17:29:51 +00:00
|
|
|
}
|
|
|
|
|
2024-08-06 14:16:20 +00:00
|
|
|
// eslint-disable-next-line @typescript-eslint/no-empty-object-type
|
2023-04-29 22:39:08 +00:00
|
|
|
export interface ExtendWebpackConfigOptions extends ExtendConfigOptions {}
|
2021-11-21 16:14:46 +00:00
|
|
|
|
2024-08-06 14:16:20 +00:00
|
|
|
// eslint-disable-next-line @typescript-eslint/no-empty-object-type
|
2021-11-21 16:14:46 +00:00
|
|
|
export interface ExtendViteConfigOptions extends ExtendConfigOptions {}
|
|
|
|
|
2024-10-09 13:57:54 +00:00
|
|
|
const extendWebpackCompatibleConfig = (builder: 'rspack' | 'webpack') => (fn: ((config: WebpackConfig) => void), options: ExtendWebpackConfigOptions = {}) => {
|
2021-11-21 16:14:46 +00:00
|
|
|
const nuxt = useNuxt()
|
|
|
|
|
|
|
|
if (options.dev === false && nuxt.options.dev) {
|
|
|
|
return
|
|
|
|
}
|
|
|
|
if (options.build === false && nuxt.options.build) {
|
|
|
|
return
|
|
|
|
}
|
|
|
|
|
2024-10-09 13:57:54 +00:00
|
|
|
nuxt.hook(`${builder}:config`, (configs) => {
|
2021-11-21 16:14:46 +00:00
|
|
|
if (options.server !== false) {
|
|
|
|
const config = configs.find(i => i.name === 'server')
|
|
|
|
if (config) {
|
|
|
|
fn(config)
|
|
|
|
}
|
|
|
|
}
|
|
|
|
if (options.client !== false) {
|
|
|
|
const config = configs.find(i => i.name === 'client')
|
|
|
|
if (config) {
|
|
|
|
fn(config)
|
|
|
|
}
|
|
|
|
}
|
|
|
|
})
|
|
|
|
}
|
|
|
|
|
2024-10-09 13:57:54 +00:00
|
|
|
/**
|
|
|
|
* Extend webpack config
|
|
|
|
*
|
|
|
|
* The fallback function might be called multiple times
|
|
|
|
* when applying to both client and server builds.
|
|
|
|
*/
|
|
|
|
export const extendWebpackConfig = extendWebpackCompatibleConfig('webpack')
|
|
|
|
/**
|
|
|
|
* Extend rspack config
|
|
|
|
*
|
|
|
|
* The fallback function might be called multiple times
|
|
|
|
* when applying to both client and server builds.
|
|
|
|
*/
|
|
|
|
export const extendRspackConfig = extendWebpackCompatibleConfig('rspack')
|
|
|
|
|
2021-11-21 16:14:46 +00:00
|
|
|
/**
|
|
|
|
* Extend Vite config
|
|
|
|
*/
|
2024-10-09 13:57:54 +00:00
|
|
|
export function extendViteConfig (fn: ((config: ViteConfig) => void), options: ExtendViteConfigOptions = {}) {
|
2021-11-21 16:14:46 +00:00
|
|
|
const nuxt = useNuxt()
|
|
|
|
|
|
|
|
if (options.dev === false && nuxt.options.dev) {
|
|
|
|
return
|
|
|
|
}
|
|
|
|
if (options.build === false && nuxt.options.build) {
|
|
|
|
return
|
|
|
|
}
|
|
|
|
|
2022-07-15 21:34:29 +00:00
|
|
|
if (options.server !== false && options.client !== false) {
|
|
|
|
// Call fn() only once
|
|
|
|
return nuxt.hook('vite:extend', ({ config }) => fn(config))
|
|
|
|
}
|
|
|
|
|
2022-06-22 17:29:51 +00:00
|
|
|
nuxt.hook('vite:extendConfig', (config, { isClient, isServer }) => {
|
|
|
|
if (options.server !== false && isServer) {
|
|
|
|
return fn(config)
|
|
|
|
}
|
|
|
|
if (options.client !== false && isClient) {
|
|
|
|
return fn(config)
|
|
|
|
}
|
|
|
|
})
|
2021-11-21 16:14:46 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
/**
|
2023-01-13 15:00:57 +00:00
|
|
|
* Append webpack plugin to the config.
|
2021-11-21 16:14:46 +00:00
|
|
|
*/
|
2023-05-02 11:17:41 +00:00
|
|
|
export function addWebpackPlugin (pluginOrGetter: WebpackPluginInstance | WebpackPluginInstance[] | (() => WebpackPluginInstance | WebpackPluginInstance[]), options?: ExtendWebpackConfigOptions) {
|
2021-11-21 16:14:46 +00:00
|
|
|
extendWebpackConfig((config) => {
|
2023-05-02 11:17:41 +00:00
|
|
|
const method: 'push' | 'unshift' = options?.prepend ? 'unshift' : 'push'
|
|
|
|
const plugin = typeof pluginOrGetter === 'function' ? pluginOrGetter() : pluginOrGetter
|
|
|
|
|
2021-11-21 16:14:46 +00:00
|
|
|
config.plugins = config.plugins || []
|
2023-12-23 14:22:58 +00:00
|
|
|
config.plugins[method](...toArray(plugin))
|
2021-11-21 16:14:46 +00:00
|
|
|
}, options)
|
|
|
|
}
|
2024-10-09 13:57:54 +00:00
|
|
|
/**
|
|
|
|
* Append rspack plugin to the config.
|
|
|
|
*/
|
|
|
|
export function addRspackPlugin (pluginOrGetter: RspackPluginInstance | RspackPluginInstance[] | (() => RspackPluginInstance | RspackPluginInstance[]), options?: ExtendWebpackConfigOptions) {
|
|
|
|
extendRspackConfig((config) => {
|
|
|
|
const method: 'push' | 'unshift' = options?.prepend ? 'unshift' : 'push'
|
|
|
|
const plugin = typeof pluginOrGetter === 'function' ? pluginOrGetter() : pluginOrGetter
|
|
|
|
|
|
|
|
config.plugins = config.plugins || []
|
|
|
|
config.plugins[method](...toArray(plugin))
|
|
|
|
}, options)
|
|
|
|
}
|
2021-11-21 16:14:46 +00:00
|
|
|
|
|
|
|
/**
|
|
|
|
* Append Vite plugin to the config.
|
|
|
|
*/
|
2023-05-02 11:17:41 +00:00
|
|
|
export function addVitePlugin (pluginOrGetter: VitePlugin | VitePlugin[] | (() => VitePlugin | VitePlugin[]), options?: ExtendViteConfigOptions) {
|
2021-11-21 16:14:46 +00:00
|
|
|
extendViteConfig((config) => {
|
2023-05-02 11:17:41 +00:00
|
|
|
const method: 'push' | 'unshift' = options?.prepend ? 'unshift' : 'push'
|
|
|
|
const plugin = typeof pluginOrGetter === 'function' ? pluginOrGetter() : pluginOrGetter
|
|
|
|
|
2021-11-21 16:14:46 +00:00
|
|
|
config.plugins = config.plugins || []
|
2023-12-23 14:22:58 +00:00
|
|
|
config.plugins[method](...toArray(plugin))
|
2021-11-21 16:14:46 +00:00
|
|
|
}, options)
|
|
|
|
}
|
2023-05-14 11:55:26 +00:00
|
|
|
|
|
|
|
interface AddBuildPluginFactory {
|
|
|
|
vite?: () => VitePlugin | VitePlugin[]
|
|
|
|
webpack?: () => WebpackPluginInstance | WebpackPluginInstance[]
|
2024-10-09 13:57:54 +00:00
|
|
|
rspack?: () => RspackPluginInstance | RspackPluginInstance[]
|
2023-05-14 11:55:26 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
export function addBuildPlugin (pluginFactory: AddBuildPluginFactory, options?: ExtendConfigOptions) {
|
|
|
|
if (pluginFactory.vite) {
|
|
|
|
addVitePlugin(pluginFactory.vite, options)
|
|
|
|
}
|
|
|
|
|
|
|
|
if (pluginFactory.webpack) {
|
|
|
|
addWebpackPlugin(pluginFactory.webpack, options)
|
|
|
|
}
|
2024-10-09 13:57:54 +00:00
|
|
|
|
|
|
|
if (pluginFactory.rspack) {
|
|
|
|
addRspackPlugin(pluginFactory.rspack, options)
|
|
|
|
}
|
2023-05-14 11:55:26 +00:00
|
|
|
}
|