Skip to content

Commit 0903d61

Browse files
committed
feat: expose experimental vite plugin
1 parent 7206b8f commit 0903d61

File tree

3 files changed

+81
-40
lines changed

3 files changed

+81
-40
lines changed

playground/src/pages/users/colada-loader.[id].vue

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,12 @@ import { simulateError, useUserData } from '@/loaders/colada-loaders'
33
import { serialize } from '@pinia/colada'
44
import { getActivePinia } from 'pinia'
55
6+
definePage({
7+
meta: {
8+
title: 'Colada Loader',
9+
},
10+
})
11+
612
const route = useRoute('/users/colada-loader.[id]')
713
814
const pinia = getActivePinia()!

src/data-loaders/auto-exports.ts

Lines changed: 72 additions & 40 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
11
import { createFilter } from '@rollup/pluginutils'
2+
import type { Plugin } from 'vite'
23
import MagicString from 'magic-string'
34
import { findStaticImports, parseStaticImport } from 'mlly'
45
import { resolve } from 'pathe'
@@ -33,50 +34,81 @@ export function extractLoadersToExport(
3334
return importNames
3435
}
3536

36-
export function createAutoExportPlugin({
37-
filterPageComponents,
38-
loadersPathsGlobs,
39-
root,
40-
}: {
41-
filterPageComponents: (id: string) => boolean
37+
const PLUGIN_NAME = 'unplugin-vue-router:data-loaders-auto-export'
38+
39+
/**
40+
* {@link AutoExportLoaders} options.
41+
*/
42+
export interface AutoExportLoadersOptions {
43+
/**
44+
* Filter page components to apply the auto-export (defined with `createFilter()` from `@rollup/pluginutils`) or array
45+
* of globs.
46+
*/
47+
filterPageComponents: ((id: string) => boolean) | string[]
48+
49+
/**
50+
* Globs to match the paths of the loaders.
51+
*/
4252
loadersPathsGlobs: string | string[]
43-
root: string
44-
}): UnpluginOptions {
53+
54+
/**
55+
* Root of the project. All paths are resolved relatively to this one.
56+
* @default `process.cwd()`
57+
*/
58+
root?: string
59+
}
60+
61+
/**
62+
* Vite Plugin to automatically export loaders from page components.
63+
*
64+
* @param options Options
65+
* @experimental - This API is experimental and can be changed in the future. It's used internally by `experimental.autoExportsDataLoaders`
66+
67+
*/
68+
export function AutoExportLoaders({
69+
filterPageComponents: filterPagesOrGlobs,
70+
loadersPathsGlobs,
71+
root = process.cwd(),
72+
}: AutoExportLoadersOptions) {
4573
const filterPaths = createFilter(loadersPathsGlobs)
74+
const filterPageComponents =
75+
typeof filterPagesOrGlobs === 'function'
76+
? filterPagesOrGlobs
77+
: createFilter(filterPagesOrGlobs)
4678

4779
return {
48-
name: 'unplugin-vue-router:data-loaders-auto-export',
49-
enforce: 'post',
50-
vite: {
51-
transform: {
52-
order: 'post',
53-
handler(code, id) {
54-
// strip query to also match .vue?vue&lang=ts etc
55-
const queryIndex = id.indexOf('?')
56-
const idWithoutQuery = queryIndex >= 0 ? id.slice(0, queryIndex) : id
57-
if (!filterPageComponents(idWithoutQuery)) {
58-
return
59-
}
60-
61-
const loadersToExports = extractLoadersToExport(
62-
code,
63-
filterPaths,
64-
root
65-
)
66-
67-
if (loadersToExports.length <= 0) return
68-
69-
const s = new MagicString(code)
70-
s.append(
71-
`\nexport const __loaders = [\n${loadersToExports.join(',\n')}\n];\n`
72-
)
73-
74-
return {
75-
code: s.toString(),
76-
map: s.generateMap(),
77-
}
78-
},
80+
name: PLUGIN_NAME,
81+
transform: {
82+
order: 'post',
83+
handler(code, id) {
84+
// strip query to also match .vue?vue&lang=ts etc
85+
const queryIndex = id.indexOf('?')
86+
const idWithoutQuery = queryIndex >= 0 ? id.slice(0, queryIndex) : id
87+
if (!filterPageComponents(idWithoutQuery)) {
88+
return
89+
}
90+
91+
const loadersToExports = extractLoadersToExport(code, filterPaths, root)
92+
93+
if (loadersToExports.length <= 0) return
94+
95+
const s = new MagicString(code)
96+
s.append(
97+
`\nexport const __loaders = [\n${loadersToExports.join(',\n')}\n];\n`
98+
)
99+
100+
return {
101+
code: s.toString(),
102+
map: s.generateMap(),
103+
}
79104
},
80105
},
81-
}
106+
} satisfies Plugin
107+
}
108+
109+
export function createAutoExportPlugin(options: AutoExportLoadersOptions) {
110+
return {
111+
name: PLUGIN_NAME,
112+
vite: AutoExportLoaders(options),
113+
} satisfies UnpluginOptions
82114
}

src/index.ts

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -26,6 +26,9 @@ export * from './types'
2626

2727
export { DEFAULT_OPTIONS }
2828

29+
export { AutoExportLoaders } from './data-loaders/auto-exports'
30+
export type { AutoExportLoadersOptions } from './data-loaders/auto-exports'
31+
2932
export default createUnplugin<Options | undefined>((opt = {}, _meta) => {
3033
const options = resolveOptions(opt)
3134
const ctx = createRoutesContext(options)

0 commit comments

Comments
 (0)