UNPKG

nuxt

Version:

Nuxt is a free and open-source framework with an intuitive and extendable way to create type-safe, performant and production-grade full-stack web applications and websites with Vue.js.

83 lines (82 loc) 2.77 kB
import { appRootTag } from "#internal/nuxt.config.mjs"; const ROOT_NODE_REGEX = new RegExp(`^<${appRootTag}[^>]*>([\\s\\S]*)<\\/${appRootTag}>$`); export function getServerComponentHTML(body) { const match = body.match(ROOT_NODE_REGEX); return match?.[1] || body; } const SSR_SLOT_TELEPORT_MARKER = /^uid=([^;]*);slot=(.*)$/; const SSR_CLIENT_TELEPORT_MARKER = /^uid=([^;]*);client=(.*)$/; const SSR_CLIENT_SLOT_MARKER = /^island-slot=([^;]*);(.*)$/; export function getSlotIslandResponse(ssrContext) { if (!ssrContext.islandContext || !Object.keys(ssrContext.islandContext.slots).length) { return void 0; } const response = {}; for (const [name, slot] of Object.entries(ssrContext.islandContext.slots)) { response[name] = { ...slot, fallback: ssrContext.teleports?.[`island-fallback=${name}`] }; } return response; } export function getClientIslandResponse(ssrContext) { if (!ssrContext.islandContext || !Object.keys(ssrContext.islandContext.components).length) { return void 0; } const response = {}; for (const [clientUid, component] of Object.entries(ssrContext.islandContext.components)) { const html = ssrContext.teleports?.[clientUid]?.replaceAll("<!--teleport start anchor-->", "") || ""; response[clientUid] = { ...component, html, slots: getComponentSlotTeleport(clientUid, ssrContext.teleports ?? {}) }; } return response; } export function getComponentSlotTeleport(clientUid, teleports) { const entries = Object.entries(teleports); const slots = {}; for (const [key, value] of entries) { const match = key.match(SSR_CLIENT_SLOT_MARKER); if (match) { const [, id, slot] = match; if (!slot || clientUid !== id) { continue; } slots[slot] = value; } } return slots; } export function replaceIslandTeleports(ssrContext, html) { const { teleports, islandContext } = ssrContext; if (islandContext || !teleports) { return html; } for (const key in teleports) { const matchClientComp = key.match(SSR_CLIENT_TELEPORT_MARKER); if (matchClientComp) { const [, uid, clientId] = matchClientComp; if (!uid || !clientId) { continue; } html = html.replace(new RegExp(` data-island-uid="${uid}" data-island-component="${clientId}"[^>]*>`), (full) => { return full + teleports[key]; }); continue; } const matchSlot = key.match(SSR_SLOT_TELEPORT_MARKER); if (matchSlot) { const [, uid, slot] = matchSlot; if (!uid || !slot) { continue; } html = html.replace(new RegExp(` data-island-uid="${uid}" data-island-slot="${slot}"[^>]*>`), (full) => { return full + teleports[key]; }); } } return html; }