@kimesh/head 0.1.0-nightly.20260119170404 → 0.1.0-nightly.20260120063147

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.d.mts CHANGED
@@ -290,5 +290,4 @@ interface KimeshHeadConfig {
290
290
  */
291
291
  type KimeshHeadOptions = MergeHead$1 & Head$1;
292
292
  //#endregion
293
- export { type ActiveHeadEntry, type Head, type HeadClient, type HeadEntryOptions, type HeadSafe, KIMESH_HEAD_KEY, type KimeshHeadConfig, type KimeshHeadOptions, KimeshHeadPlugin, KmBody, KmHead, KmHtml, KmLink, KmMeta, KmScript, KmStyle, KmTitle, type MergeHead, type UseHeadInput, type UseHeadSafeInput, type UseSeoMetaInput, useHead, useHeadSafe, useRouteHead, useSeoMeta };
294
- //# sourceMappingURL=index.d.mts.map
293
+ export { type ActiveHeadEntry, type Head, type HeadClient, type HeadEntryOptions, type HeadSafe, KIMESH_HEAD_KEY, type KimeshHeadConfig, type KimeshHeadOptions, KimeshHeadPlugin, KmBody, KmHead, KmHtml, KmLink, KmMeta, KmScript, KmStyle, KmTitle, type MergeHead, type UseHeadInput, type UseHeadSafeInput, type UseSeoMetaInput, useHead, useHeadSafe, useRouteHead, useSeoMeta };
package/dist/index.mjs CHANGED
@@ -426,5 +426,4 @@ const KmBody = defineComponent({
426
426
  });
427
427
 
428
428
  //#endregion
429
- export { KIMESH_HEAD_KEY, KimeshHeadPlugin, KmBody, KmHead, KmHtml, KmLink, KmMeta, KmScript, KmStyle, KmTitle, useHead, useHeadSafe, useRouteHead, useSeoMeta };
430
- //# sourceMappingURL=index.mjs.map
429
+ export { KIMESH_HEAD_KEY, KimeshHeadPlugin, KmBody, KmHead, KmHtml, KmLink, KmMeta, KmScript, KmStyle, KmTitle, useHead, useHeadSafe, useRouteHead, useSeoMeta };
package/dist/plugin.d.mts CHANGED
@@ -15,5 +15,4 @@ declare const KIMESH_HEAD_KEY: unique symbol;
15
15
  */
16
16
  declare const KimeshHeadPlugin: any;
17
17
  //#endregion
18
- export { type HeadClient, KIMESH_HEAD_KEY, KimeshHeadPlugin, KimeshHeadPlugin as default };
19
- //# sourceMappingURL=plugin.d.mts.map
18
+ export { type HeadClient, KIMESH_HEAD_KEY, KimeshHeadPlugin, KimeshHeadPlugin as default };
package/dist/plugin.mjs CHANGED
@@ -67,5 +67,4 @@ const KimeshHeadPlugin = defineKimeshRuntimePlugin({
67
67
  var plugin_default = KimeshHeadPlugin;
68
68
 
69
69
  //#endregion
70
- export { KIMESH_HEAD_KEY, KimeshHeadPlugin, plugin_default as default };
71
- //# sourceMappingURL=plugin.mjs.map
70
+ export { KIMESH_HEAD_KEY, KimeshHeadPlugin, plugin_default as default };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@kimesh/head",
3
- "version": "0.1.0-nightly.20260119170404",
3
+ "version": "0.1.0-nightly.20260120063147",
4
4
  "description": "Head meta management for Kimesh framework",
5
5
  "type": "module",
6
6
  "exports": {
@@ -34,10 +34,10 @@
34
34
  },
35
35
  "peerDependencies": {
36
36
  "vue": "^3.5.0",
37
- "@kimesh/router-runtime": "0.1.0-nightly.20260119170404"
37
+ "@kimesh/router-runtime": "0.1.0-nightly.20260120063147"
38
38
  },
39
39
  "devDependencies": {
40
- "@kimesh/router-runtime": "0.1.0-nightly.20260119170404",
40
+ "@kimesh/router-runtime": "0.1.0-nightly.20260120063147",
41
41
  "@types/node": "^25.0.8",
42
42
  "@vue/test-utils": "^2.4.6",
43
43
  "jsdom": "^27.4.0",
@@ -1 +0,0 @@
1
- {"version":3,"file":"index.d.mts","names":[],"sources":["../src/composables/use-head.ts","../src/composables/use-seo-meta.ts","../src/composables/use-head-safe.ts","../src/composables/use-route-head.ts","../src/components/KmHead.ts","../src/components/KmTitle.ts","../src/components/KmMeta.ts","../src/components/KmLink.ts","../src/components/KmScript.ts","../src/components/KmStyle.ts","../src/components/KmHtml.ts","../src/components/KmBody.ts","../src/types/index.ts"],"mappings":";;;;;;;;;AA+BA;;;;ACLA;;;;ACAA;;;;ACwCA;;;;ACzDA;;;;iBJsBgB,OAAA,WAAkB,cAAA,CAAA,CAAA,KAAA,EAAqB,CAAA;;;;ACLvD;;;;ACAA;;;;ACwCA;;;;ACzDA;;;;;iBHiBgB,UAAA,CAAA,KAAA,EAAkB,iBAAA;;;;ACAlC;;;;ACwCA;;;;ACzDA;;;;;;;;;iBFiBgB,WAAA,CAAA,KAAA,EAAmB,kBAAA;;;;ACwCnC;;;;ACzDA;;;;;;;;;iBDyDgB,YAAA,CAAA,GAAgB,GAAA,CAAI,eAAA;;;;ACzDpC;;;;;cAAa,MAAA,OAAM,eAAA,WAAA,IAAA,CAAA,KAAA,CAMjB,IAAA,CANiB,YAAA,EAAA,IAAA,CAAA,eAAA;EAAA,CAAA,GAAA;AAAA,yBAAA,IAAA,CAAA,qBAAA;;;;ACcnB;;;;;;;cAAa,OAAA,EAAO,IAAA,CAAA,eAAA,6BAclB,IAAA,CAdkB,qBAAA,EAAA,IAAA,CAAA,qBAAA,cAAA,IAAA,CAAA,WAAA,EAAA,QAAA,OAAA,QAAA,8BAAA,IAAA,CAAA,uBAAA;;;;ACVpB;;;;;;;;;cAAa,MAAA,OAAM,eAAA,MAAA,gBAAA;EAAA,IAAA;;;;;4BAAA,IAAA,CAAA,qBAAA;;;;;;;;;KCVd,OAAA;AAAA;AAYL;;;;;;;;;AAZK,cAYQ,MAAA,OAAM,eAAA,MAAA,gBAAA;EAAA,GAAA;;;MAOD,QAAA,CAAS,OAAA;EAAA,WAAA,EACA,QAAA;EAAA,KAAA;;;;4BARR,IAAA,CAAA,qBAAA;;;;MAOD,QAAA,CAAS,OAAA;EAAA,WAAA,EACA,QAAA;EAAA,KAAA;;;;;;;KCpBtB,cAAA;AAAA;AA2BL;;;;;;;;;;;;AA3BK,cA2BQ,QAAA,OAAQ,eAAA,CAYiB,IAAA,CAZjB,gBAAA;EAAA,GAAA;;;;eAQM,QAAA;EAAA,SAAA;;;kBAIG,QAAA,CAAS,cAAA;AAAA,4BAZlB,IAAA,CAAA,qBAAA,qEAYiB,IAAA,CAAA,gBAAA;EAAA,GAAA;;;;eAJX,QAAA;EAAA,SAAA;;;kBAIG,QAAA,CAAS,cAAA;AAAA;;;;;;;;ACVvC;;;;;;;;;;;;;;;;cAAa,OAAA,OAAO,eAAA,MAAA,gBAAA;EAAA,IAAA;;;4BAAA,IAAA,CAAA,qBAAA;;;;;;;;ACpBpB;;;;;;;;cAAa,MAAA,OAAM,eAAA,MAAA,gBAAA;EAAA,IAAA;OAKA,QAAA;EAAA,KAAA;4BALA,IAAA,CAAA,qBAAA;;OAKA,QAAA;EAAA,KAAA;;;;;ACNnB;;;;;;;cAAa,MAAA,OAAM,eAAA,MAAA,gBAAA;EAAA,KAAA;4BAAA,IAAA,CAAA,qBAAA;;;;;;ACoBnB;AAcA;UAdiB,gBAAA;EAAA;EAAA,OAAA;EAAA;EAAA,aAAA,cAAA,KAAA;EAAA;EAAA,cAAA,GAQE,MAAA;AAAA;AAAA;AAMnB;;AANmB,KAMP,iBAAA,GAAoB,WAAA,GAAY,MAAA"}
@@ -1 +0,0 @@
1
- {"version":3,"file":"index.mjs","names":["extractTextContent","extractTextContent"],"sources":["../src/composables/use-head.ts","../src/composables/use-seo-meta.ts","../src/composables/use-head-safe.ts","../src/composables/use-route-head.ts","../src/components/KmHead.ts","../src/components/KmTitle.ts","../src/components/KmMeta.ts","../src/components/KmLink.ts","../src/components/KmScript.ts","../src/components/KmStyle.ts","../src/components/KmHtml.ts","../src/components/KmBody.ts"],"sourcesContent":["/**\n * @kimesh/head - useHead composable\n *\n * Set head meta tags with full reactivity support.\n */\n\nimport { useHead as unheadUseHead, type UseHeadInput } from '@unhead/vue'\nimport { getCurrentInstance } from 'vue'\nimport { tryUseKimeshApp } from '@kimesh/router-runtime'\n\n/**\n * Set head meta tags with full reactivity support\n *\n * @example Basic usage\n * ```ts\n * useHead({\n * title: 'My Page',\n * meta: [\n * { name: 'description', content: 'Page description' }\n * ]\n * })\n * ```\n *\n * @example Reactive values\n * ```ts\n * const title = ref('Dynamic Title')\n * useHead({\n * title: () => title.value\n * })\n * ```\n */\nexport function useHead<T extends UseHeadInput>(input: T): void {\n const instance = getCurrentInstance()\n\n if (!instance) {\n const app = tryUseKimeshApp()\n if (app?.head) {\n app.head.push(input as Parameters<typeof app.head.push>[0])\n return\n }\n console.warn('[Kimesh Head] useHead called outside component context')\n return\n }\n\n unheadUseHead(input)\n}\n","/**\n * @kimesh/head - useSeoMeta composable\n *\n * Flat API for SEO meta tags.\n */\n\nimport { useSeoMeta as unheadUseSeoMeta, type UseSeoMetaInput } from '@unhead/vue'\n\n/**\n * Flat API for SEO meta tags\n *\n * Provides a cleaner, flat interface for setting SEO-related meta tags\n * without needing to manually structure the meta array.\n *\n * @example\n * ```ts\n * useSeoMeta({\n * title: 'My Site',\n * description: 'Site description',\n * ogTitle: 'Open Graph Title',\n * ogDescription: 'OG Description',\n * ogImage: 'https://example.com/image.png',\n * twitterCard: 'summary_large_image',\n * })\n * ```\n */\nexport function useSeoMeta(input: UseSeoMetaInput): void {\n unheadUseSeoMeta(input)\n}\n","/**\n * @kimesh/head - useHeadSafe composable\n *\n * XSS-safe version of useHead that sanitizes all input.\n */\n\nimport { useHeadSafe as unheadUseHeadSafe, type UseHeadSafeInput } from '@unhead/vue'\n\n/**\n * XSS-safe version of useHead - sanitizes all input\n *\n * Use this when head values come from user input or external sources.\n * This prevents XSS attacks by sanitizing potentially malicious content.\n *\n * @example\n * ```ts\n * const userTitle = ref(userInput) // potentially unsafe\n *\n * useHeadSafe({\n * title: userTitle,\n * meta: [\n * { name: 'description', content: userDescription }\n * ]\n * })\n * ```\n */\nexport function useHeadSafe(input: UseHeadSafeInput): void {\n try {\n unheadUseHeadSafe(input)\n } catch (error) {\n console.error('[Kimesh Head] Failed to set head:', error)\n }\n}\n","/**\n * @kimesh/head - useRouteHead composable\n *\n * Applies head configuration from matched routes.\n */\n\nimport { computed, watch, type Ref } from 'vue'\nimport { useRoute, type RouteLocationNormalizedLoaded } from 'vue-router'\nimport { useHead } from './use-head'\nimport type { RouteHeadConfig, RouteHeadFn, RouteHeadContext } from '@kimesh/router-runtime'\n\ninterface RouteDefinitionWithHead {\n head?: RouteHeadFn | RouteHeadConfig\n}\n\n/**\n * Get head configuration from route\n */\nfunction getRouteHead(\n route: RouteLocationNormalizedLoaded\n): RouteHeadConfig | undefined {\n // Collect head from all matched routes (parent -> child)\n const heads: RouteHeadConfig[] = []\n\n for (const record of route.matched) {\n const routeDef = record.meta?.__kimesh as RouteDefinitionWithHead | undefined\n if (!routeDef?.head) continue\n\n const headConfig = typeof routeDef.head === 'function'\n ? routeDef.head({\n params: route.params as Record<string, string>,\n loaderData: undefined, // TODO: integrate with loader data\n route,\n })\n : routeDef.head\n\n heads.push(headConfig)\n }\n\n if (heads.length === 0) return undefined\n\n // Merge all heads (later ones override earlier)\n return heads.reduce((merged, head) => ({\n ...merged,\n ...head,\n meta: [...(merged.meta || []), ...(head.meta || [])],\n link: [...(merged.link || []), ...(head.link || [])],\n script: [...(merged.script || []), ...(head.script || [])],\n style: [...(merged.style || []), ...(head.style || [])],\n }), {} as RouteHeadConfig)\n}\n\n/**\n * Apply head configuration from current route\n *\n * Call this in your root layout/app component to enable route-based head.\n *\n * @example\n * ```vue\n * <script setup>\n * import { useRouteHead } from '@kimesh/head'\n *\n * useRouteHead()\n * </script>\n * ```\n */\nexport function useRouteHead(): Ref<RouteHeadConfig | undefined> {\n const route = useRoute()\n\n const routeHead = computed(() => getRouteHead(route))\n\n // Apply head reactively when route changes\n useHead((() => routeHead.value || {}) as Parameters<typeof useHead>[0])\n\n return routeHead\n}\n","import { defineComponent, h, type Slots } from 'vue'\nimport { useHead } from '../composables/use-head'\n\n/**\n * KmHead - Container component for head tags\n *\n * This is a wrapper component that renders slot content.\n * Use the specific components (KmTitle, KmMeta, etc.) inside.\n */\nexport const KmHead = defineComponent({\n name: 'KmHead',\n\n setup(_, { slots }: { slots: Slots }) {\n return () => (slots.default ? slots.default() : null)\n },\n})\n","import { defineComponent, h, watchEffect, type Slots, type VNode } from 'vue'\nimport { useHead } from '../composables/use-head'\n\nfunction extractTextContent(vnodes: VNode[]): string {\n let text = ''\n for (const vnode of vnodes) {\n if (typeof vnode.children === 'string') {\n text += vnode.children\n } else if (Array.isArray(vnode.children)) {\n text += extractTextContent(vnode.children as VNode[])\n }\n }\n return text\n}\n\n/**\n * KmTitle - Set page title\n *\n * @example\n * ```vue\n * <KmTitle>My Page Title</KmTitle>\n * ```\n */\nexport const KmTitle = defineComponent({\n name: 'KmTitle',\n\n setup(_, { slots }: { slots: Slots }) {\n useHead({\n title: () => {\n const content = slots.default?.()\n if (!content) return ''\n return extractTextContent(content)\n },\n })\n\n return () => null\n },\n})\n","import { defineComponent, type PropType } from 'vue'\nimport { useHead } from '../composables/use-head'\n\n/**\n * KmMeta - Set meta tags\n *\n * @example\n * ```vue\n * <KmMeta name=\"description\" content=\"Page description\" />\n * <KmMeta property=\"og:title\" content=\"OG Title\" />\n * <KmMeta charset=\"utf-8\" />\n * ```\n */\nexport const KmMeta = defineComponent({\n name: 'KmMeta',\n\n props: {\n name: String,\n property: String,\n httpEquiv: String,\n content: String,\n charset: String,\n },\n\n setup(props) {\n useHead({\n meta: [\n {\n ...(props.name && { name: props.name }),\n ...(props.property && { property: props.property }),\n ...(props.httpEquiv && { 'http-equiv': props.httpEquiv }),\n ...(props.content && { content: props.content }),\n ...(props.charset && { charset: props.charset }),\n },\n ],\n })\n\n return () => null\n },\n})\n","import { defineComponent, type PropType } from 'vue'\nimport { useHead } from '../composables/use-head'\n\ntype AsValue = 'object' | 'audio' | 'document' | 'embed' | 'fetch' | 'font' | 'image' | 'script' | 'style' | 'track' | 'video' | 'worker'\n\n/**\n * KmLink - Set link tags (stylesheets, preload, favicon, etc.)\n *\n * @example\n * ```vue\n * <KmLink rel=\"stylesheet\" href=\"/styles.css\" />\n * <KmLink rel=\"icon\" type=\"image/x-icon\" href=\"/favicon.ico\" />\n * <KmLink rel=\"preload\" href=\"/font.woff2\" as=\"font\" type=\"font/woff2\" crossorigin=\"anonymous\" />\n * ```\n */\nexport const KmLink = defineComponent({\n name: 'KmLink',\n\n props: {\n rel: String,\n href: String,\n type: String,\n as: String as PropType<AsValue>,\n crossorigin: String as PropType<'' | 'anonymous' | 'use-credentials'>,\n media: String,\n sizes: String,\n hreflang: String,\n title: String,\n },\n\n setup(props) {\n useHead({\n link: [\n {\n ...(props.rel && { rel: props.rel }),\n ...(props.href && { href: props.href }),\n ...(props.type && { type: props.type }),\n ...(props.as && { as: props.as }),\n ...(props.crossorigin && { crossorigin: props.crossorigin }),\n ...(props.media && { media: props.media }),\n ...(props.sizes && { sizes: props.sizes }),\n ...(props.hreflang && { hreflang: props.hreflang }),\n ...(props.title && { title: props.title }),\n },\n ],\n })\n\n return () => null\n },\n})\n","import { defineComponent, type PropType, type Slots, type VNode } from 'vue'\nimport { useHead } from '../composables/use-head'\n\ntype ReferrerPolicy = '' | 'no-referrer' | 'no-referrer-when-downgrade' | 'origin' | 'origin-when-cross-origin' | 'same-origin' | 'strict-origin' | 'strict-origin-when-cross-origin' | 'unsafe-url'\n\nfunction extractTextContent(vnodes: VNode[]): string {\n let text = ''\n for (const vnode of vnodes) {\n if (typeof vnode.children === 'string') {\n text += vnode.children\n } else if (Array.isArray(vnode.children)) {\n text += extractTextContent(vnode.children as VNode[])\n }\n }\n return text\n}\n\n/**\n * KmScript - Set script tags\n *\n * @example External script\n * ```vue\n * <KmScript src=\"https://example.com/script.js\" async />\n * ```\n *\n * @example Inline script\n * ```vue\n * <KmScript>console.log('Hello')</KmScript>\n * ```\n */\nexport const KmScript = defineComponent({\n name: 'KmScript',\n\n props: {\n src: String,\n type: String,\n async: Boolean,\n defer: Boolean,\n crossorigin: String as PropType<'' | 'anonymous' | 'use-credentials'>,\n integrity: String,\n nomodule: Boolean,\n nonce: String,\n referrerpolicy: String as PropType<ReferrerPolicy>,\n },\n\n setup(props, { slots }: { slots: Slots }) {\n useHead({\n script: [\n {\n ...(props.src && { src: props.src }),\n ...(props.type && { type: props.type }),\n ...(props.async && { async: props.async }),\n ...(props.defer && { defer: props.defer }),\n ...(props.crossorigin && { crossorigin: props.crossorigin }),\n ...(props.integrity && { integrity: props.integrity }),\n ...(props.nomodule && { nomodule: props.nomodule }),\n ...(props.nonce && { nonce: props.nonce }),\n ...(props.referrerpolicy && { referrerpolicy: props.referrerpolicy }),\n innerHTML: () => {\n const content = slots.default?.()\n if (!content) return undefined\n return extractTextContent(content)\n },\n },\n ],\n })\n\n return () => null\n },\n})\n","import { defineComponent, type Slots, type VNode } from 'vue'\nimport { useHead } from '../composables/use-head'\n\nfunction extractTextContent(vnodes: VNode[]): string {\n let text = ''\n for (const vnode of vnodes) {\n if (typeof vnode.children === 'string') {\n text += vnode.children\n } else if (Array.isArray(vnode.children)) {\n text += extractTextContent(vnode.children as VNode[])\n }\n }\n return text\n}\n\n/**\n * KmStyle - Set inline styles\n *\n * @example\n * ```vue\n * <KmStyle>\n * body { background: #fff; }\n * </KmStyle>\n * ```\n *\n * @example With media query\n * ```vue\n * <KmStyle media=\"print\">\n * body { font-size: 12pt; }\n * </KmStyle>\n * ```\n */\nexport const KmStyle = defineComponent({\n name: 'KmStyle',\n\n props: {\n type: String,\n media: String,\n nonce: String,\n },\n\n setup(props, { slots }: { slots: Slots }) {\n useHead({\n style: [\n {\n innerHTML: () => {\n const content = slots.default?.()\n if (!content) return ''\n return extractTextContent(content)\n },\n ...(props.type && { type: props.type }),\n ...(props.media && { media: props.media }),\n ...(props.nonce && { nonce: props.nonce }),\n },\n ],\n })\n\n return () => null\n },\n})\n","import { defineComponent, type PropType } from 'vue'\nimport { useHead } from '../composables/use-head'\n\n/**\n * KmHtml - Set HTML element attributes\n *\n * @example\n * ```vue\n * <KmHtml lang=\"en\" dir=\"ltr\" />\n * <KmHtml lang=\"vi\" class=\"dark-mode\" />\n * ```\n */\nexport const KmHtml = defineComponent({\n name: 'KmHtml',\n\n props: {\n lang: String,\n dir: String as PropType<'ltr' | 'rtl' | 'auto'>,\n class: String,\n },\n\n setup(props) {\n useHead({\n htmlAttrs: {\n ...(props.lang && { lang: props.lang }),\n ...(props.dir && { dir: props.dir }),\n ...(props.class && { class: props.class }),\n },\n })\n\n return () => null\n },\n})\n","import { defineComponent } from 'vue'\nimport { useHead } from '../composables/use-head'\n\n/**\n * KmBody - Set body element attributes\n *\n * @example\n * ```vue\n * <KmBody class=\"dark-mode\" />\n * ```\n */\nexport const KmBody = defineComponent({\n name: 'KmBody',\n\n props: {\n class: String,\n },\n\n setup(props) {\n useHead({\n bodyAttrs: {\n ...(props.class && { class: props.class }),\n },\n })\n\n return () => null\n },\n})\n"],"mappings":"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"}
@@ -1 +0,0 @@
1
- {"version":3,"file":"plugin.d.mts","names":[],"sources":["../src/plugin.ts"],"mappings":";;;;AAaA;AA6CA;;;cA7Ca,eAAA;AAAA;AA6Cb;;;;;AA7Ca,cA6CA,gBAAA"}
@@ -1 +0,0 @@
1
- {"version":3,"file":"plugin.mjs","names":[],"sources":["../src/plugin.ts"],"sourcesContent":["/**\n * @kimesh/head - Runtime Plugin\n *\n * CSR-only head management plugin using @unhead/vue.\n */\n\nimport { defineKimeshRuntimePlugin } from '@kimesh/router-runtime'\nimport { createHead, renderDOMHead, type VueHeadClient } from '@unhead/vue/client'\nimport { nextTick } from 'vue'\nimport type { RouteLocationNormalizedLoaded } from 'vue-router'\nimport type { KimeshHeadOptions } from './types'\nimport type { RouteHeadConfig } from '@kimesh/router-runtime'\n\nexport const KIMESH_HEAD_KEY = Symbol('kimesh:head')\n\ninterface RouteDefinitionWithHead {\n head?: ((ctx: { params: Record<string, string>; loaderData: unknown; route: RouteLocationNormalizedLoaded }) => RouteHeadConfig) | RouteHeadConfig\n}\n\n/**\n * Get merged head configuration from matched routes\n */\nfunction getRouteHead(route: RouteLocationNormalizedLoaded): RouteHeadConfig | undefined {\n const heads: RouteHeadConfig[] = []\n\n for (const record of route.matched) {\n const routeDef = record.meta?.__kimesh as RouteDefinitionWithHead | undefined\n if (!routeDef?.head) continue\n\n const headConfig = typeof routeDef.head === 'function'\n ? routeDef.head({\n params: route.params as Record<string, string>,\n loaderData: undefined,\n route,\n })\n : routeDef.head\n\n heads.push(headConfig)\n }\n\n if (heads.length === 0) return undefined\n\n return heads.reduce((merged, head) => ({\n ...merged,\n ...head,\n meta: [...(merged.meta || []), ...(head.meta || [])],\n link: [...(merged.link || []), ...(head.link || [])],\n script: [...(merged.script || []), ...(head.script || [])],\n style: [...(merged.style || []), ...(head.style || [])],\n }), {} as RouteHeadConfig)\n}\n\n/**\n * Kimesh Head Plugin\n *\n * Provides head meta management for Kimesh apps.\n * Uses @unhead/vue for CSR-only head management.\n */\nexport const KimeshHeadPlugin = defineKimeshRuntimePlugin<{\n head: VueHeadClient\n}>({\n name: 'kimesh:head',\n enforce: 'pre',\n\n setup(app) {\n const headOptions = app.$config.head as KimeshHeadOptions | undefined\n\n const head = createHead()\n\n app.vueApp.use(head)\n\n if (headOptions) {\n head.push(headOptions)\n }\n\n let routeHeadEntry: ReturnType<typeof head.push> | null = null\n\n app.router.afterEach((to) => {\n if (routeHeadEntry) {\n routeHeadEntry.dispose()\n routeHeadEntry = null\n }\n\n const routeHead = getRouteHead(to)\n if (routeHead) {\n routeHeadEntry = head.push(routeHead as Parameters<typeof head.push>[0])\n }\n\n nextTick(() => {\n renderDOMHead(head)\n })\n })\n\n return {\n provide: { head },\n }\n },\n\n hooks: {\n 'app:mounted': () => {\n },\n },\n})\n\nexport default KimeshHeadPlugin\n\nexport type { VueHeadClient as HeadClient } from '@unhead/vue/client'\n"],"mappings":";;;;;;;;;;AAaA,MAAa,kBAAkB,OAAO,cAAc;;;;AASpD,SAAS,aAAa,OAAmE;CACvF,MAAM,QAA2B,EAAE;AAEnC,MAAK,MAAM,UAAU,MAAM,SAAS;EAClC,MAAM,WAAW,OAAO,MAAM;AAC9B,MAAI,CAAC,UAAU,KAAM;EAErB,MAAM,aAAa,OAAO,SAAS,SAAS,aACxC,SAAS,KAAK;GACZ,QAAQ,MAAM;GACd,YAAY;GACZ;GACD,CAAC,GACF,SAAS;AAEb,QAAM,KAAK,WAAW;;AAGxB,KAAI,MAAM,WAAW,EAAG,QAAO;AAE/B,QAAO,MAAM,QAAQ,QAAQ,UAAU;EACrC,GAAG;EACH,GAAG;EACH,MAAM,CAAC,GAAI,OAAO,QAAQ,EAAE,EAAG,GAAI,KAAK,QAAQ,EAAE,CAAE;EACpD,MAAM,CAAC,GAAI,OAAO,QAAQ,EAAE,EAAG,GAAI,KAAK,QAAQ,EAAE,CAAE;EACpD,QAAQ,CAAC,GAAI,OAAO,UAAU,EAAE,EAAG,GAAI,KAAK,UAAU,EAAE,CAAE;EAC1D,OAAO,CAAC,GAAI,OAAO,SAAS,EAAE,EAAG,GAAI,KAAK,SAAS,EAAE,CAAE;EACxD,GAAG,EAAE,CAAoB;;;;;;;;AAS5B,MAAa,mBAAmB,0BAE7B;CACD,MAAM;CACN,SAAS;CAET,MAAM,KAAK;EACT,MAAM,cAAc,IAAI,QAAQ;EAEhC,MAAM,OAAO,YAAY;AAEzB,MAAI,OAAO,IAAI,KAAK;AAEpB,MAAI,YACF,MAAK,KAAK,YAAY;EAGxB,IAAI,iBAAsD;AAE1D,MAAI,OAAO,WAAW,OAAO;AAC3B,OAAI,gBAAgB;AAClB,mBAAe,SAAS;AACxB,qBAAiB;;GAGnB,MAAM,YAAY,aAAa,GAAG;AAClC,OAAI,UACF,kBAAiB,KAAK,KAAK,UAA6C;AAG1E,kBAAe;AACb,kBAAc,KAAK;KACnB;IACF;AAEF,SAAO,EACL,SAAS,EAAE,MAAM,EAClB;;CAGH,OAAO,EACL,qBAAqB,IAEtB;CACF,CAAC;AAEF,qBAAe"}