Some checks failed
Build and deploy updated apps / Build & deploy (push) Failing after 50s
106 lines
3.4 KiB
TypeScript
106 lines
3.4 KiB
TypeScript
import { addVitePlugin, defineNuxtModule, getLayerDirectories } from '@nuxt/kit'
|
|
import { getLayerFiles, getLayerContent } from '../app/utils/content-files'
|
|
import {
|
|
getRoutes,
|
|
getExpandedRoutes,
|
|
getRouteShortcuts,
|
|
getConfig,
|
|
} from '../app/utils/content-routes'
|
|
import { join, relative, dirname, basename, extname } from 'path'
|
|
import { existsSync } from 'fs'
|
|
|
|
/* Rationale:
|
|
1) Every project file containing useInjectedContent() is transformed and virtual modules are imported
|
|
2) Upon request the virtual modules are compiled from ts/yaml files
|
|
3) If any of the files that back a virtual module change the module is invalidated
|
|
*/
|
|
|
|
export default defineNuxtModule({
|
|
setup() {
|
|
addVitePlugin(() => ({
|
|
name: 'content-import-injector',
|
|
resolveId(id) {
|
|
if (id.startsWith('virtual:content/')) {
|
|
return '\0' + id // convention, hide from further processing
|
|
}
|
|
},
|
|
async load(id) {
|
|
if (id.startsWith('\0' + 'virtual:content/')) {
|
|
const slug = id.slice(17)
|
|
|
|
if (slug === 'shortcuts') {
|
|
const routes = await getRoutes()
|
|
const shortcuts = getRouteShortcuts(routes)
|
|
|
|
return `export default ${JSON.stringify(shortcuts)}`
|
|
} else if (slug === 'content.config') {
|
|
const file = getLayerDirectories()
|
|
.map((d) => join(d.app, 'content.config.ts'))
|
|
.find((f) => existsSync(f))
|
|
|
|
if (file) {
|
|
this.addWatchFile(file)
|
|
return `export {default} from '${file}'`
|
|
}
|
|
} else {
|
|
const files = getLayerFiles(slug)
|
|
const content = await getLayerContent(files)
|
|
|
|
files.filter((f) => existsSync(f)).forEach((f) => this.addWatchFile(f))
|
|
|
|
return `export const content = ${JSON.stringify(content)}`
|
|
}
|
|
}
|
|
},
|
|
hotUpdate({ file, server }) {
|
|
const root = getLayerDirectories()
|
|
.map((d) => d.app)
|
|
.find((r) => file.startsWith(r))
|
|
|
|
if (root !== undefined) {
|
|
const path = relative(root, file)
|
|
const slug = join(dirname(path), basename(path, extname(path)))
|
|
|
|
const module = server.moduleGraph.getModuleById('\0' + `virtual:content/${slug}`)
|
|
|
|
if (module) {
|
|
server.moduleGraph.invalidateModule(module)
|
|
this.environment.hot.send({ type: 'full-reload' })
|
|
}
|
|
}
|
|
|
|
return []
|
|
},
|
|
transform(code, id) {
|
|
let slug: string | undefined = undefined
|
|
|
|
for (const root of getLayerDirectories().map((d) => d.app)) {
|
|
if (id.startsWith(root)) {
|
|
const path = relative(root, id).split('?')[0]!
|
|
slug = join(dirname(path), basename(path, extname(path)))
|
|
break
|
|
}
|
|
}
|
|
|
|
if (slug === undefined) {
|
|
return null
|
|
}
|
|
|
|
const expression = /\buseContentInjected\s*\(\s*\)/g
|
|
if (!expression.test(code)) return null
|
|
|
|
const transformed = code.replace(
|
|
expression,
|
|
`useContentInjected('${slug}', a23631da455de90c5a945da16897d0bd, d61397115e513f2bb1d8e872b7e7788f)`
|
|
)
|
|
|
|
return `
|
|
import {content as a23631da455de90c5a945da16897d0bd} from 'virtual:content/content.global';
|
|
import {content as d61397115e513f2bb1d8e872b7e7788f} from 'virtual:content/${slug}';
|
|
${transformed}
|
|
`
|
|
},
|
|
}))
|
|
},
|
|
})
|