refactor(nuxt): define layouts as async vue components (#29957)

This commit is contained in:
Daniel Roe 2024-11-17 17:06:03 -05:00
parent c576d8b383
commit c4ede9bee3
No known key found for this signature in database
GPG Key ID: CBC814C393D93268
2 changed files with 4 additions and 7 deletions

View File

@ -16,7 +16,6 @@ import layouts from '#build/layouts'
// @ts-expect-error virtual file // @ts-expect-error virtual file
import { appLayoutTransition as defaultLayoutTransition } from '#build/nuxt.config.mjs' import { appLayoutTransition as defaultLayoutTransition } from '#build/nuxt.config.mjs'
// TODO: revert back to defineAsyncComponent when https://github.com/vuejs/core/issues/6638 is resolved
const LayoutLoader = defineComponent({ const LayoutLoader = defineComponent({
name: 'LayoutLoader', name: 'LayoutLoader',
inheritAttrs: false, inheritAttrs: false,
@ -24,13 +23,10 @@ const LayoutLoader = defineComponent({
name: String, name: String,
layoutProps: Object, layoutProps: Object,
}, },
async setup (props, context) { setup (props, context) {
// This is a deliberate hack - this component must always be called with an explicit key to ensure // This is a deliberate hack - this component must always be called with an explicit key to ensure
// that setup reruns when the name changes. // that setup reruns when the name changes.
return () => h(layouts[props.name], props.layoutProps, context.slots)
const LayoutComponent = await layouts[props.name]().then((r: any) => r.default || r)
return () => h(LayoutComponent, props.layoutProps, context.slots)
}, },
}) })

View File

@ -299,9 +299,10 @@ export const layoutTemplate: NuxtTemplate = {
filename: 'layouts.mjs', filename: 'layouts.mjs',
getContents ({ app }) { getContents ({ app }) {
const layoutsObject = genObjectFromRawEntries(Object.values(app.layouts).map(({ name, file }) => { const layoutsObject = genObjectFromRawEntries(Object.values(app.layouts).map(({ name, file }) => {
return [name, genDynamicImport(file)] return [name, `defineAsyncComponent(${genDynamicImport(file)})`]
})) }))
return [ return [
`import { defineAsyncComponent } from 'vue'`,
`export default ${layoutsObject}`, `export default ${layoutsObject}`,
].join('\n') ].join('\n')
}, },