feat(nuxt): allow remote sources for islands (#21592)

This commit is contained in:
Julien Huang 2023-07-30 23:00:41 +02:00 committed by GitHub
parent 620097241a
commit ffc4e798cd
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23

View File

@ -36,12 +36,17 @@ export default defineComponent({
context: {
type: Object,
default: () => ({})
},
source: {
type: String,
default: () => undefined
}
},
async setup (props, { slots }) {
const error = ref<unknown>(null)
const config = useRuntimeConfig()
const nuxtApp = useNuxtApp()
const hashId = computed(() => hash([props.name, props.props, props.context]))
const hashId = computed(() => hash([props.name, props.props, props.context, props.source]))
const instance = getCurrentInstance()!
const event = useRequestEvent()
// TODO: remove use of `$fetch.raw` when nitro 503 issues on windows dev server are resolved
@ -100,7 +105,8 @@ export default defineComponent({
const key = `${props.name}_${hashId.value}`
if (nuxtApp.payload.data[key] && !force) { return nuxtApp.payload.data[key] }
const url = `/__nuxt_island/${key}`
const url = props.source ? new URL(`/__nuxt_island/${key}`, props.source).href : `/__nuxt_island/${key}`
if (process.server && process.env.prerender) {
// Hint to Nitro to prerender the island component
appendResponseHeader(event, 'x-nitro-prerender', url)
@ -130,18 +136,23 @@ export default defineComponent({
delete nuxtApp[pKey]![uid.value]
})
}
const res: NuxtIslandResponse = await nuxtApp[pKey][uid.value]
cHead.value.link = res.head.link
cHead.value.style = res.head.style
ssrHTML.value = res.html.replace(UID_ATTR, () => {
return `nuxt-ssr-component-uid="${getId()}"`
})
key.value++
if (process.client) {
// must await next tick for Teleport to work correctly with static node re-rendering
await nextTick()
try {
const res: NuxtIslandResponse = await nuxtApp[pKey][uid.value]
cHead.value.link = res.head.link
cHead.value.style = res.head.style
ssrHTML.value = res.html.replace(UID_ATTR, () => {
return `nuxt-ssr-component-uid="${getId()}"`
})
key.value++
error.value = null
if (process.client) {
// must await next tick for Teleport to work correctly with static node re-rendering
await nextTick()
}
setUid()
} catch (e) {
error.value = e
}
setUid()
}
if (import.meta.hot) {
@ -160,6 +171,9 @@ export default defineComponent({
}
return () => {
if (error.value && slots.fallback) {
return [slots.fallback({ error: error.value })]
}
const nodes = [createVNode(Fragment, {
key: key.value
}, [h(createStaticVNode(html.value, 1))])]