@ogygia/core 0.0.0 → 0.11.0

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.
Files changed (548) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +7 -1
  3. package/ambient.d.ts +194 -0
  4. package/dist/ClientBindingStub.svelte +6 -0
  5. package/dist/ClientBindingStub.svelte.d.ts +26 -0
  6. package/dist/KeepHost.svelte +19 -0
  7. package/dist/KeepHost.svelte.d.ts +10 -0
  8. package/dist/LakeBoundary.svelte +16 -0
  9. package/dist/LakeBoundary.svelte.d.ts +11 -0
  10. package/dist/LateIsland.svelte +22 -0
  11. package/dist/LateIsland.svelte.d.ts +15 -0
  12. package/dist/LateIslandAwait.svelte +17 -0
  13. package/dist/LateIslandAwait.svelte.d.ts +15 -0
  14. package/dist/LiveHost.svelte +19 -0
  15. package/dist/LiveHost.svelte.d.ts +10 -0
  16. package/dist/NestedProvider.svelte +13 -0
  17. package/dist/NestedProvider.svelte.d.ts +8 -0
  18. package/dist/OgygiaBoundary.svelte +5 -0
  19. package/dist/OgygiaBoundary.svelte.d.ts +17 -0
  20. package/dist/PromiseRegion.svelte +40 -0
  21. package/dist/PromiseRegion.svelte.d.ts +15 -0
  22. package/dist/PromiseRegionAwait.svelte +27 -0
  23. package/dist/PromiseRegionAwait.svelte.d.ts +15 -0
  24. package/dist/Provide.svelte +27 -0
  25. package/dist/Provide.svelte.d.ts +8 -0
  26. package/dist/RawHtml.svelte +9 -0
  27. package/dist/RawHtml.svelte.d.ts +6 -0
  28. package/dist/Region.svelte +1173 -0
  29. package/dist/Region.svelte.d.ts +68 -0
  30. package/dist/SlotBoundary.svelte +13 -0
  31. package/dist/SlotBoundary.svelte.d.ts +7 -0
  32. package/dist/app.d.ts +4 -0
  33. package/dist/app.js +3 -0
  34. package/dist/boundary.d.ts +35 -0
  35. package/dist/boundary.js +127 -0
  36. package/dist/build-cache.d.ts +13 -0
  37. package/dist/build-cache.js +77 -0
  38. package/dist/compiler/blank-styles.d.ts +1 -0
  39. package/dist/compiler/blank-styles.js +63 -0
  40. package/dist/compiler/bom.d.ts +2 -0
  41. package/dist/compiler/bom.js +15 -0
  42. package/dist/compiler/browser-full.d.ts +8 -0
  43. package/dist/compiler/browser-full.js +8 -0
  44. package/dist/compiler/browser.d.ts +11 -0
  45. package/dist/compiler/browser.js +11 -0
  46. package/dist/compiler/content/transportables.d.ts +26 -0
  47. package/dist/compiler/content/transportables.js +219 -0
  48. package/dist/compiler/ctx.d.ts +180 -0
  49. package/dist/compiler/ctx.js +183 -0
  50. package/dist/compiler/debarrel/barrel.d.ts +55 -0
  51. package/dist/compiler/debarrel/barrel.js +248 -0
  52. package/dist/compiler/debarrel/options.d.ts +67 -0
  53. package/dist/compiler/debarrel/options.js +31 -0
  54. package/dist/compiler/debarrel/parse.d.ts +65 -0
  55. package/dist/compiler/debarrel/parse.js +256 -0
  56. package/dist/compiler/debarrel/plugin.d.ts +31 -0
  57. package/dist/compiler/debarrel/plugin.js +190 -0
  58. package/dist/compiler/debarrel/rewrite.d.ts +27 -0
  59. package/dist/compiler/debarrel/rewrite.js +118 -0
  60. package/dist/compiler/debarrel/svelte.d.ts +13 -0
  61. package/dist/compiler/debarrel/svelte.js +56 -0
  62. package/dist/compiler/dev/css-scope.d.ts +16 -0
  63. package/dist/compiler/dev/css-scope.js +38 -0
  64. package/dist/compiler/dev/dev-hmr.d.ts +25 -0
  65. package/dist/compiler/dev/dev-hmr.js +29 -0
  66. package/dist/compiler/dev/hmr.d.ts +34 -0
  67. package/dist/compiler/dev/hmr.js +57 -0
  68. package/dist/compiler/dev/region-bytes.d.ts +34 -0
  69. package/dist/compiler/dev/region-bytes.js +126 -0
  70. package/dist/compiler/driver.d.ts +280 -0
  71. package/dist/compiler/driver.js +1352 -0
  72. package/dist/compiler/flags.d.ts +16 -0
  73. package/dist/compiler/flags.js +101 -0
  74. package/dist/compiler/fouc-css.d.ts +97 -0
  75. package/dist/compiler/fouc-css.js +335 -0
  76. package/dist/compiler/free-vars.d.ts +20 -0
  77. package/dist/compiler/free-vars.js +327 -0
  78. package/dist/compiler/host.d.ts +65 -0
  79. package/dist/compiler/host.js +51 -0
  80. package/dist/compiler/ids.d.ts +84 -0
  81. package/dist/compiler/ids.js +86 -0
  82. package/dist/compiler/index.d.ts +11 -0
  83. package/dist/compiler/index.js +11 -0
  84. package/dist/compiler/kit.d.ts +129 -0
  85. package/dist/compiler/kit.js +563 -0
  86. package/dist/compiler/link/build-output.d.ts +44 -0
  87. package/dist/compiler/link/build-output.js +147 -0
  88. package/dist/compiler/link/caps.d.ts +48 -0
  89. package/dist/compiler/link/caps.js +64 -0
  90. package/dist/compiler/link/context-detect.d.ts +23 -0
  91. package/dist/compiler/link/context-detect.js +137 -0
  92. package/dist/compiler/link/emit-gate.d.ts +11 -0
  93. package/dist/compiler/link/emit-gate.js +40 -0
  94. package/dist/compiler/link/entry-shim.d.ts +4 -0
  95. package/dist/compiler/link/entry-shim.js +29 -0
  96. package/dist/compiler/link/island-deps.d.ts +142 -0
  97. package/dist/compiler/link/island-deps.js +525 -0
  98. package/dist/compiler/link/manifest.d.ts +5 -0
  99. package/dist/compiler/link/manifest.js +9 -0
  100. package/dist/compiler/link/page-keys.d.ts +64 -0
  101. package/dist/compiler/link/page-keys.js +683 -0
  102. package/dist/compiler/link/registry-stub.d.ts +41 -0
  103. package/dist/compiler/link/registry-stub.js +212 -0
  104. package/dist/compiler/link/router-config.d.ts +11 -0
  105. package/dist/compiler/link/router-config.js +15 -0
  106. package/dist/compiler/link/router-css.d.ts +22 -0
  107. package/dist/compiler/link/router-css.js +142 -0
  108. package/dist/compiler/link/runtime-entry.d.ts +71 -0
  109. package/dist/compiler/link/runtime-entry.js +132 -0
  110. package/dist/compiler/link/server-manifest.d.ts +12 -0
  111. package/dist/compiler/link/server-manifest.js +45 -0
  112. package/dist/compiler/link/speculation.d.ts +17 -0
  113. package/dist/compiler/link/speculation.js +36 -0
  114. package/dist/compiler/link/transport.d.ts +31 -0
  115. package/dist/compiler/link/transport.js +67 -0
  116. package/dist/compiler/macros/bake.d.ts +20 -0
  117. package/dist/compiler/macros/bake.js +317 -0
  118. package/dist/compiler/macros/browser.d.ts +11 -0
  119. package/dist/compiler/macros/browser.js +69 -0
  120. package/dist/compiler/macros/dedent.d.ts +12 -0
  121. package/dist/compiler/macros/dedent.js +36 -0
  122. package/dist/compiler/macros/dollar.d.ts +15 -0
  123. package/dist/compiler/macros/dollar.js +387 -0
  124. package/dist/compiler/macros/pipeline.d.ts +31 -0
  125. package/dist/compiler/macros/pipeline.js +106 -0
  126. package/dist/compiler/macros/source.d.ts +6 -0
  127. package/dist/compiler/macros/source.js +127 -0
  128. package/dist/compiler/macros/store.d.ts +17 -0
  129. package/dist/compiler/macros/store.js +244 -0
  130. package/dist/compiler/macros/wire.d.ts +14 -0
  131. package/dist/compiler/macros/wire.js +160 -0
  132. package/dist/compiler/ownership-stamps.d.ts +6 -0
  133. package/dist/compiler/ownership-stamps.js +144 -0
  134. package/dist/compiler/parse/oxc.d.ts +34 -0
  135. package/dist/compiler/parse/oxc.js +59 -0
  136. package/dist/compiler/parse/scan.d.ts +43 -0
  137. package/dist/compiler/parse/scan.js +232 -0
  138. package/dist/compiler/program.d.ts +140 -0
  139. package/dist/compiler/program.js +242 -0
  140. package/dist/compiler/region/emit.d.ts +169 -0
  141. package/dist/compiler/region/emit.js +286 -0
  142. package/dist/compiler/region/identity.d.ts +28 -0
  143. package/dist/compiler/region/identity.js +75 -0
  144. package/dist/compiler/region/ir.d.ts +65 -0
  145. package/dist/compiler/region/ir.js +0 -0
  146. package/dist/compiler/region/transform.d.ts +178 -0
  147. package/dist/compiler/region/transform.js +1933 -0
  148. package/dist/compiler/script-request.d.ts +1 -0
  149. package/dist/compiler/script-request.js +43 -0
  150. package/dist/context-bridge.d.ts +65 -0
  151. package/dist/context-bridge.js +217 -0
  152. package/dist/context-registry.d.ts +40 -0
  153. package/dist/context-registry.js +15 -0
  154. package/dist/context.d.ts +72 -0
  155. package/dist/context.js +158 -0
  156. package/dist/current-region.d.ts +14 -0
  157. package/dist/current-region.js +36 -0
  158. package/dist/document.d.ts +41 -0
  159. package/dist/document.js +125 -0
  160. package/dist/entry-hydrate.d.ts +5 -0
  161. package/dist/entry-hydrate.js +42 -0
  162. package/dist/escape.d.ts +18 -0
  163. package/dist/escape.js +37 -0
  164. package/dist/events/bus.d.ts +33 -0
  165. package/dist/events/bus.js +153 -0
  166. package/dist/events/index.d.ts +4 -0
  167. package/dist/events/index.js +4 -0
  168. package/dist/events/schema.d.ts +389 -0
  169. package/dist/events/schema.js +23 -0
  170. package/dist/events/server-registry.d.ts +7 -0
  171. package/dist/events/server-registry.js +13 -0
  172. package/dist/events/sinks.d.ts +64 -0
  173. package/dist/events/sinks.js +85 -0
  174. package/dist/fn-transport.d.ts +33 -0
  175. package/dist/fn-transport.js +140 -0
  176. package/dist/frame.d.ts +20 -0
  177. package/dist/frame.js +19 -0
  178. package/dist/holes-record.d.ts +6 -0
  179. package/dist/holes-record.js +8 -0
  180. package/dist/hooks.d.ts +43 -0
  181. package/dist/hooks.js +1191 -0
  182. package/dist/hydration-info.d.ts +1 -0
  183. package/dist/hydration-info.js +31 -0
  184. package/dist/index.d.ts +21 -0
  185. package/dist/index.js +17 -0
  186. package/dist/insights/attr-rules.d.ts +15 -0
  187. package/dist/insights/attr-rules.js +27 -0
  188. package/dist/insights/cpu.d.ts +82 -0
  189. package/dist/insights/cpu.js +177 -0
  190. package/dist/insights/fp-drift.d.ts +28 -0
  191. package/dist/insights/fp-drift.js +148 -0
  192. package/dist/insights/hole-segments.d.ts +26 -0
  193. package/dist/insights/hole-segments.js +50 -0
  194. package/dist/insights/html-diff.d.ts +25 -0
  195. package/dist/insights/html-diff.js +157 -0
  196. package/dist/insights/hydration-hazards.d.ts +36 -0
  197. package/dist/insights/hydration-hazards.js +136 -0
  198. package/dist/insights/hydration-status.d.ts +2 -0
  199. package/dist/insights/hydration-status.js +0 -0
  200. package/dist/insights/index.d.ts +14 -0
  201. package/dist/insights/index.js +12 -0
  202. package/dist/insights/page-assets.d.ts +211 -0
  203. package/dist/insights/page-assets.js +608 -0
  204. package/dist/insights/page-insights.d.ts +749 -0
  205. package/dist/insights/page-insights.js +2157 -0
  206. package/dist/insights/session-data.d.ts +108 -0
  207. package/dist/insights/session-data.js +0 -0
  208. package/dist/insights/session-insights.d.ts +121 -0
  209. package/dist/insights/session-insights.js +548 -0
  210. package/dist/insights/switch.d.ts +53 -0
  211. package/dist/insights/switch.js +91 -0
  212. package/dist/insights/testing-version.d.ts +19 -0
  213. package/dist/insights/testing-version.js +21 -0
  214. package/dist/insights/third-party.d.ts +75 -0
  215. package/dist/insights/third-party.js +160 -0
  216. package/dist/internal-instruments.d.ts +13 -0
  217. package/dist/internal-instruments.js +12 -0
  218. package/dist/internal-reconcile.d.ts +3 -0
  219. package/dist/internal-reconcile.js +3 -0
  220. package/dist/internal-register.d.ts +7 -0
  221. package/dist/internal-register.js +7 -0
  222. package/dist/internal-server.d.ts +7 -0
  223. package/dist/internal-server.js +7 -0
  224. package/dist/internal.d.ts +13 -0
  225. package/dist/internal.js +13 -0
  226. package/dist/island-graph.d.ts +36 -0
  227. package/dist/island-graph.js +89 -0
  228. package/dist/keep-fallback-marker.d.ts +7 -0
  229. package/dist/keep-fallback-marker.js +9 -0
  230. package/dist/keep-fallback.d.ts +13 -0
  231. package/dist/keep-fallback.js +39 -0
  232. package/dist/kit-paths.d.ts +2 -0
  233. package/dist/kit-paths.js +39 -0
  234. package/dist/late-region-registry.d.ts +40 -0
  235. package/dist/late-region-registry.js +36 -0
  236. package/dist/live-transport.d.ts +57 -0
  237. package/dist/live-transport.js +145 -0
  238. package/dist/markup.d.ts +4 -0
  239. package/dist/markup.js +4 -0
  240. package/dist/own-package.d.ts +15 -0
  241. package/dist/own-package.js +20 -0
  242. package/dist/page-defer.d.ts +33 -0
  243. package/dist/page-defer.js +35 -0
  244. package/dist/page-facts-script.d.ts +7 -0
  245. package/dist/page-facts-script.js +9 -0
  246. package/dist/page-seed-registry.d.ts +72 -0
  247. package/dist/page-seed-registry.js +31 -0
  248. package/dist/plugin/capability.d.ts +14 -0
  249. package/dist/plugin/capability.js +44 -0
  250. package/dist/plugin/client.d.ts +39 -0
  251. package/dist/plugin/client.js +6 -0
  252. package/dist/plugin/css.d.ts +3 -0
  253. package/dist/plugin/css.js +54 -0
  254. package/dist/plugin/facts.d.ts +42 -0
  255. package/dist/plugin/facts.js +37 -0
  256. package/dist/plugin/hooks.d.ts +33 -0
  257. package/dist/plugin/hooks.js +38 -0
  258. package/dist/plugin/index.d.ts +127 -0
  259. package/dist/plugin/index.js +26 -0
  260. package/dist/plugin/routes.d.ts +32 -0
  261. package/dist/plugin/routes.js +35 -0
  262. package/dist/plugin/server.d.ts +27 -0
  263. package/dist/plugin/server.js +92 -0
  264. package/dist/plugin/standard-schema.d.ts +27 -0
  265. package/dist/plugin/standard-schema.js +0 -0
  266. package/dist/plugin/testing.d.ts +13 -0
  267. package/dist/plugin/testing.js +54 -0
  268. package/dist/plugin/utils.d.ts +13 -0
  269. package/dist/plugin/utils.js +19 -0
  270. package/dist/portable-form.d.ts +22 -0
  271. package/dist/portable-form.js +52 -0
  272. package/dist/preference.d.ts +35 -0
  273. package/dist/preference.js +84 -0
  274. package/dist/preload.d.ts +1 -0
  275. package/dist/preload.js +21 -0
  276. package/dist/ref-watch.d.ts +31 -0
  277. package/dist/ref-watch.js +66 -0
  278. package/dist/ref.d.ts +124 -0
  279. package/dist/ref.js +272 -0
  280. package/dist/region-brand.d.ts +8 -0
  281. package/dist/region-brand.js +10 -0
  282. package/dist/region-core.d.ts +2 -0
  283. package/dist/region-core.js +1 -0
  284. package/dist/region-snippet.d.ts +73 -0
  285. package/dist/region-snippet.js +351 -0
  286. package/dist/region.d.ts +127 -0
  287. package/dist/region.js +162 -0
  288. package/dist/request-event.d.ts +1 -0
  289. package/dist/request-event.js +37 -0
  290. package/dist/router-css.d.ts +39 -0
  291. package/dist/router-css.js +66 -0
  292. package/dist/runtime/app-transport.d.ts +2 -0
  293. package/dist/runtime/app-transport.js +13 -0
  294. package/dist/runtime/beacon.d.ts +271 -0
  295. package/dist/runtime/beacon.js +2190 -0
  296. package/dist/runtime/boot-link.d.ts +1 -0
  297. package/dist/runtime/boot-link.js +44 -0
  298. package/dist/runtime/client-hooks.d.ts +5 -0
  299. package/dist/runtime/client-hooks.js +22 -0
  300. package/dist/runtime/client-plugins.d.ts +8 -0
  301. package/dist/runtime/client-plugins.js +34 -0
  302. package/dist/runtime/concurrency.d.ts +12 -0
  303. package/dist/runtime/concurrency.js +29 -0
  304. package/dist/runtime/connected.d.ts +12 -0
  305. package/dist/runtime/connected.js +16 -0
  306. package/dist/runtime/context.d.ts +1 -0
  307. package/dist/runtime/context.js +19 -0
  308. package/dist/runtime/core.d.ts +15 -0
  309. package/dist/runtime/core.js +1173 -0
  310. package/dist/runtime/drift-watch.d.ts +9 -0
  311. package/dist/runtime/drift-watch.js +60 -0
  312. package/dist/runtime/entry-locations.d.ts +33 -0
  313. package/dist/runtime/entry-locations.js +119 -0
  314. package/dist/runtime/foreign-props.d.ts +8 -0
  315. package/dist/runtime/foreign-props.js +14 -0
  316. package/dist/runtime/form-continuity.d.ts +10 -0
  317. package/dist/runtime/form-continuity.js +107 -0
  318. package/dist/runtime/frame-nav.d.ts +36 -0
  319. package/dist/runtime/frame-nav.js +225 -0
  320. package/dist/runtime/frame-store.d.ts +62 -0
  321. package/dist/runtime/frame-store.js +214 -0
  322. package/dist/runtime/frames.d.ts +1 -0
  323. package/dist/runtime/frames.js +25 -0
  324. package/dist/runtime/full.d.ts +4 -0
  325. package/dist/runtime/full.js +32 -0
  326. package/dist/runtime/hash.d.ts +41 -0
  327. package/dist/runtime/hash.js +79 -0
  328. package/dist/runtime/hole-facts.d.ts +8 -0
  329. package/dist/runtime/hole-facts.js +57 -0
  330. package/dist/runtime/host-classes.d.ts +24 -0
  331. package/dist/runtime/host-classes.js +43 -0
  332. package/dist/runtime/hydrate-core.d.ts +101 -0
  333. package/dist/runtime/hydrate-core.js +605 -0
  334. package/dist/runtime/index.d.ts +2 -0
  335. package/dist/runtime/index.js +1 -0
  336. package/dist/runtime/interaction-replay.d.ts +11 -0
  337. package/dist/runtime/interaction-replay.js +70 -0
  338. package/dist/runtime/interaction.d.ts +33 -0
  339. package/dist/runtime/interaction.js +217 -0
  340. package/dist/runtime/island-graph-preload.d.ts +13 -0
  341. package/dist/runtime/island-graph-preload.js +99 -0
  342. package/dist/runtime/kit-boot.d.ts +29 -0
  343. package/dist/runtime/kit-boot.js +60 -0
  344. package/dist/runtime/kit-page-thread.svelte.d.ts +1 -0
  345. package/dist/runtime/kit-page-thread.svelte.js +116 -0
  346. package/dist/runtime/lake-anchors.d.ts +13 -0
  347. package/dist/runtime/lake-anchors.js +19 -0
  348. package/dist/runtime/lakes.d.ts +15 -0
  349. package/dist/runtime/lakes.js +212 -0
  350. package/dist/runtime/live.d.ts +3 -0
  351. package/dist/runtime/live.js +17 -0
  352. package/dist/runtime/load-scheduler.d.ts +53 -0
  353. package/dist/runtime/load-scheduler.js +317 -0
  354. package/dist/runtime/morph.d.ts +42 -0
  355. package/dist/runtime/morph.js +671 -0
  356. package/dist/runtime/nav-handle.d.ts +25 -0
  357. package/dist/runtime/nav-handle.js +71 -0
  358. package/dist/runtime/nav-hooks.d.ts +2 -0
  359. package/dist/runtime/nav-hooks.js +23 -0
  360. package/dist/runtime/nearest-attr.d.ts +4 -0
  361. package/dist/runtime/nearest-attr.js +16 -0
  362. package/dist/runtime/observe.d.ts +27 -0
  363. package/dist/runtime/observe.js +63 -0
  364. package/dist/runtime/own-cost.d.ts +9 -0
  365. package/dist/runtime/own-cost.js +35 -0
  366. package/dist/runtime/ownership.d.ts +101 -0
  367. package/dist/runtime/ownership.js +115 -0
  368. package/dist/runtime/page-cache.d.ts +23 -0
  369. package/dist/runtime/page-cache.js +74 -0
  370. package/dist/runtime/page-defer.d.ts +14 -0
  371. package/dist/runtime/page-defer.js +103 -0
  372. package/dist/runtime/parse-html.d.ts +40 -0
  373. package/dist/runtime/parse-html.js +81 -0
  374. package/dist/runtime/reconcile.d.ts +41 -0
  375. package/dist/runtime/reconcile.js +194 -0
  376. package/dist/runtime/region-attrs.d.ts +95 -0
  377. package/dist/runtime/region-attrs.js +153 -0
  378. package/dist/runtime/region-endpoint-url.d.ts +76 -0
  379. package/dist/runtime/region-endpoint-url.js +169 -0
  380. package/dist/runtime/region-ids.d.ts +8 -0
  381. package/dist/runtime/region-ids.js +33 -0
  382. package/dist/runtime/remote-seeds.d.ts +2 -0
  383. package/dist/runtime/remote-seeds.js +21 -0
  384. package/dist/runtime/render-blocking.d.ts +2 -0
  385. package/dist/runtime/render-blocking.js +30 -0
  386. package/dist/runtime/restore.d.ts +34 -0
  387. package/dist/runtime/restore.js +390 -0
  388. package/dist/runtime/router-nav.d.ts +63 -0
  389. package/dist/runtime/router-nav.js +740 -0
  390. package/dist/runtime/router.d.ts +201 -0
  391. package/dist/runtime/router.js +593 -0
  392. package/dist/runtime/schedule.d.ts +49 -0
  393. package/dist/runtime/schedule.js +256 -0
  394. package/dist/runtime/seeds.d.ts +50 -0
  395. package/dist/runtime/seeds.js +208 -0
  396. package/dist/runtime/session.d.ts +52 -0
  397. package/dist/runtime/session.js +130 -0
  398. package/dist/runtime/sidecar.d.ts +3 -0
  399. package/dist/runtime/sidecar.js +56 -0
  400. package/dist/runtime/slots.d.ts +183 -0
  401. package/dist/runtime/slots.js +44 -0
  402. package/dist/runtime/spa-cacheable.d.ts +7 -0
  403. package/dist/runtime/spa-cacheable.js +18 -0
  404. package/dist/runtime/speculate-hint.d.ts +1 -0
  405. package/dist/runtime/speculate-hint.js +35 -0
  406. package/dist/runtime/svelte-warnings.d.ts +28 -0
  407. package/dist/runtime/svelte-warnings.js +71 -0
  408. package/dist/runtime/wire-classes.d.ts +3 -0
  409. package/dist/runtime/wire-classes.js +69 -0
  410. package/dist/runtime/wire-format.d.ts +7 -0
  411. package/dist/runtime/wire-format.js +22 -0
  412. package/dist/script.d.ts +134 -0
  413. package/dist/script.js +184 -0
  414. package/dist/seed-refs.d.ts +105 -0
  415. package/dist/seed-refs.js +487 -0
  416. package/dist/server/capability-lifetime.d.ts +28 -0
  417. package/dist/server/capability-lifetime.js +31 -0
  418. package/dist/server/dead-kit-resolves.d.ts +1 -0
  419. package/dist/server/dead-kit-resolves.js +39 -0
  420. package/dist/server/document-assembly.d.ts +30 -0
  421. package/dist/server/document-assembly.js +26 -0
  422. package/dist/server/document-tail.d.ts +113 -0
  423. package/dist/server/document-tail.js +208 -0
  424. package/dist/server/endpoint.d.ts +51 -0
  425. package/dist/server/endpoint.js +90 -0
  426. package/dist/server/entry-location.d.ts +8 -0
  427. package/dist/server/entry-location.js +29 -0
  428. package/dist/server/fingerprint.d.ts +1 -0
  429. package/dist/server/fingerprint.js +25 -0
  430. package/dist/server/head-presence.d.ts +45 -0
  431. package/dist/server/head-presence.js +156 -0
  432. package/dist/server/hmac.d.ts +38 -0
  433. package/dist/server/hmac.js +89 -0
  434. package/dist/server/hole-graph.d.ts +7 -0
  435. package/dist/server/hole-graph.js +71 -0
  436. package/dist/server/hole-urls.d.ts +3 -0
  437. package/dist/server/hole-urls.js +76 -0
  438. package/dist/server/html-scan.d.ts +19 -0
  439. package/dist/server/html-scan.js +60 -0
  440. package/dist/server/kit-context.d.ts +78 -0
  441. package/dist/server/kit-context.js +110 -0
  442. package/dist/server/late-wire.d.ts +22 -0
  443. package/dist/server/late-wire.js +28 -0
  444. package/dist/server/page-facts.d.ts +25 -0
  445. package/dist/server/page-facts.js +138 -0
  446. package/dist/server/page-seed.d.ts +33 -0
  447. package/dist/server/page-seed.js +60 -0
  448. package/dist/server/page-stream.d.ts +55 -0
  449. package/dist/server/page-stream.js +121 -0
  450. package/dist/server/payload.d.ts +6 -0
  451. package/dist/server/payload.js +22 -0
  452. package/dist/server/personal-response.d.ts +6 -0
  453. package/dist/server/personal-response.js +13 -0
  454. package/dist/server/props-wire.d.ts +56 -0
  455. package/dist/server/props-wire.js +178 -0
  456. package/dist/server/rate-limit.d.ts +22 -0
  457. package/dist/server/rate-limit.js +63 -0
  458. package/dist/server/region-css.d.ts +5 -0
  459. package/dist/server/region-css.js +30 -0
  460. package/dist/server/region-endpoint.d.ts +35 -0
  461. package/dist/server/region-endpoint.js +142 -0
  462. package/dist/server/region-props.d.ts +6 -0
  463. package/dist/server/region-props.js +44 -0
  464. package/dist/server/remote-seed-gate.d.ts +50 -0
  465. package/dist/server/remote-seed-gate.js +66 -0
  466. package/dist/server/render-cache.d.ts +26 -0
  467. package/dist/server/render-cache.js +51 -0
  468. package/dist/server/render-page.d.ts +51 -0
  469. package/dist/server/render-page.js +176 -0
  470. package/dist/server/render-region-html.d.ts +2 -0
  471. package/dist/server/render-region-html.js +19 -0
  472. package/dist/server/request-stats.d.ts +174 -0
  473. package/dist/server/request-stats.js +54 -0
  474. package/dist/server/reversible.d.ts +83 -0
  475. package/dist/server/reversible.js +994 -0
  476. package/dist/server/seed-shape.d.ts +22 -0
  477. package/dist/server/seed-shape.js +24 -0
  478. package/dist/server/shared-cache.d.ts +35 -0
  479. package/dist/server/shared-cache.js +104 -0
  480. package/dist/server/signing-key.d.ts +11 -0
  481. package/dist/server/signing-key.js +47 -0
  482. package/dist/server/sized-lru.d.ts +20 -0
  483. package/dist/server/sized-lru.js +68 -0
  484. package/dist/server/split-regions.d.ts +81 -0
  485. package/dist/server/split-regions.js +368 -0
  486. package/dist/server/stream-regions.d.ts +5 -0
  487. package/dist/server/stream-regions.js +36 -0
  488. package/dist/shared-state.d.ts +7 -0
  489. package/dist/shared-state.js +152 -0
  490. package/dist/shims/app-environment.d.ts +4 -0
  491. package/dist/shims/app-environment.js +6 -0
  492. package/dist/shims/app-navigation.d.ts +33 -0
  493. package/dist/shims/app-navigation.js +119 -0
  494. package/dist/shims/app-paths.d.ts +6 -0
  495. package/dist/shims/app-paths.js +18 -0
  496. package/dist/shims/app-state.svelte.d.ts +23 -0
  497. package/dist/shims/app-state.svelte.js +50 -0
  498. package/dist/shims/app-stores.d.ts +21 -0
  499. package/dist/shims/app-stores.js +54 -0
  500. package/dist/shims/kit-bridge.d.ts +29 -0
  501. package/dist/shims/kit-bridge.js +7 -0
  502. package/dist/shims/kit-remote/client-stub.d.ts +27 -0
  503. package/dist/shims/kit-remote/client-stub.js +43 -0
  504. package/dist/shims/kit-remote/paths-internal-stub.d.ts +3 -0
  505. package/dist/shims/kit-remote/paths-internal-stub.js +5 -0
  506. package/dist/shims/kit-remote/remote-cache.d.ts +49 -0
  507. package/dist/shims/kit-remote/remote-cache.js +73 -0
  508. package/dist/shims/kit-remote/state-stub.d.ts +8 -0
  509. package/dist/shims/kit-remote/state-stub.js +8 -0
  510. package/dist/shims/page-store.svelte.d.ts +39 -0
  511. package/dist/shims/page-store.svelte.js +77 -0
  512. package/dist/source.d.ts +29 -0
  513. package/dist/source.js +87 -0
  514. package/dist/store-transport.d.ts +86 -0
  515. package/dist/store-transport.js +229 -0
  516. package/dist/tool-fetches.d.ts +5 -0
  517. package/dist/tool-fetches.js +41 -0
  518. package/dist/transport.d.ts +48 -0
  519. package/dist/transport.js +181 -0
  520. package/dist/unscoped-css.d.ts +26 -0
  521. package/dist/unscoped-css.js +53 -0
  522. package/dist/vite/dev-maps.d.ts +33 -0
  523. package/dist/vite/dev-maps.js +140 -0
  524. package/dist/vite/index.d.ts +19 -0
  525. package/dist/vite/index.js +820 -0
  526. package/dist/vite/kit-dirs.d.ts +7 -0
  527. package/dist/vite/kit-dirs.js +67 -0
  528. package/dist/vite/late-island.d.ts +25 -0
  529. package/dist/vite/late-island.js +33 -0
  530. package/dist/vite/module-map.d.ts +8 -0
  531. package/dist/vite/module-map.js +144 -0
  532. package/dist/vite/options.d.ts +208 -0
  533. package/dist/vite/options.js +74 -0
  534. package/dist/vite/package-files.d.ts +3 -0
  535. package/dist/vite/package-files.js +84 -0
  536. package/dist/vite/paths.d.ts +45 -0
  537. package/dist/vite/paths.js +112 -0
  538. package/dist/vite/plugin-api.d.ts +166 -0
  539. package/dist/vite/plugin-api.js +212 -0
  540. package/dist/vite/profiler-maps.d.ts +23 -0
  541. package/dist/vite/profiler-maps.js +178 -0
  542. package/dist/vite/server-sourcemaps.d.ts +8 -0
  543. package/dist/vite/server-sourcemaps.js +80 -0
  544. package/dist/vite/sourcemaps.d.ts +18 -0
  545. package/dist/vite/sourcemaps.js +80 -0
  546. package/dist/vite/style-preprocess.d.ts +2 -0
  547. package/dist/vite/style-preprocess.js +96 -0
  548. package/package.json +180 -6
package/dist/hooks.js ADDED
@@ -0,0 +1,1191 @@
1
+ import { REGION_BRAND } from "./region-brand.js";
2
+ import { signing_key } from "./server/signing-key.js";
3
+ import { mpaSpeculationRules } from "./compiler/link/speculation.js";
4
+ import { set_page_route_config } from "./plugin/routes.js";
5
+ import { kit_page_facts_tail, kit_page_ready, kit_render_context, set_kit_event_reader, set_kit_page_reader, set_render_page_port } from "./server/kit-context.js";
6
+ import { PAGE_FACTS_ROUTE_HEADER } from "./server/page-facts.js";
7
+ import { configure_render_page, note_render_page_ask, page_url_of, prepare_render_page, render_page, render_page_facts_script, render_page_version } from "./server/render-page.js";
8
+ import { absolutize_hole_html } from "./server/hole-urls.js";
9
+ import { is_keep_fallback } from "./keep-fallback.js";
10
+ import { set_source_recorder } from "./source.js";
11
+ import { kit_asset } from "./kit-paths.js";
12
+ import { region_mac_message, sign, verify } from "./server/hmac.js";
13
+ import { expiry_refusal, note_cache_control } from "./server/shared-cache.js";
14
+ import { app_lifetime } from "./server/region-endpoint.js";
15
+ import { cached_render, render_cache_key } from "./server/render-cache.js";
16
+ import { B64Url } from "./server/payload.js";
17
+ import { REF_WIRE_KEY, ref_reviver } from "./ref.js";
18
+ import { current_facts, facts_of, mark_per_visitor, set_current_request } from "./plugin/facts.js";
19
+ import { around, request_contexts, start_plugins } from "./plugin/server.js";
20
+ import { register_wire_kind } from "./live-transport.js";
21
+ import { register_derived_kind, register_store_kind } from "./store-transport.js";
22
+ import { register_snippet_kind } from "./region-snippet.js";
23
+ import { register_fn_kind } from "./fn-transport.js";
24
+ import { configure_islands_endpoint, is_region_id, is_region_ttl, islands_endpoint } from "./server/endpoint.js";
25
+ import { build_parcel, done_parcel } from "./server/stream-regions.js";
26
+ import { dedupe_head_links, page_declares_dev_hmr_script, page_declares_router_meta, page_declares_runtime_script, page_declares_speculation_rules, runtime_first } from "./server/head-presence.js";
27
+ import { assemble, locate } from "./server/document-assembly.js";
28
+ import { error_route_is_csr_true, route_is_csr_true } from "./context.js";
29
+ import { merge_seed_ask, shape_page_data } from "./server/seed-shape.js";
30
+ import { html_has_kit_bootstrap } from "./runtime/kit-boot.js";
31
+ import { STAND_IN_CSS, check_script, mark, settle } from "./server/reversible.js";
32
+ import { hole_head } from "./server/hole-graph.js";
33
+ import { restore, restore_adopt } from "./runtime/restore.js";
34
+ import { RateLimiter } from "./server/rate-limit.js";
35
+ import { KEEP_FALLBACK_HTML } from "./keep-fallback-marker.js";
36
+ import { PageSeed } from "./server/page-seed.js";
37
+ import { analyze, index_seed, json_culprit, set_measure_memo_reader } from "./seed-refs.js";
38
+ import { WIRE_FORMAT_ATTR, WIRE_FORMAT_JSON } from "./server/props-wire.js";
39
+ import { page_seed_reducers, resolve_script, settle_deferred, stage_deferred } from "./server/page-stream.js";
40
+ import { PAGE_DEFER_BOOTSTRAP, PAGE_DEFER_GLOBAL } from "./page-defer.js";
41
+ import { ConcurrencyGate } from "./runtime/concurrency.js";
42
+ import { serialize_provided_context } from "./context-bridge.js";
43
+ import { escape_script_text } from "./escape.js";
44
+ import { hole_copy_key } from "./runtime/hash.js";
45
+ import { PAGE_CTX_MARKER, set_ctx_recorder } from "./context-registry.js";
46
+ import { set_ask_scope_opener, set_page_recorder, set_seed_ask_reader } from "./page-seed-registry.js";
47
+ import { collect_remote_seed } from "./server/remote-seed-gate.js";
48
+ import { DocumentTail, set_tail_reader } from "./server/document-tail.js";
49
+ import { runtime_bootstrap } from "./server/entry-location.js";
50
+ import { region_css_tag } from "./server/region-css.js";
51
+ import { set_late_recorder, set_late_scope_opener, set_late_taker } from "./late-region-registry.js";
52
+ import { has_batch_hole_listener, record_batch_hole_stats, record_hole_stats, record_request_stats, request_stats_detailed, request_stats_wanted } from "./server/request-stats.js";
53
+ import { set_server_devtools_recorder } from "./events/server-registry.js";
54
+ import { drop_dead_kit_resolves } from "./server/dead-kit-resolves.js";
55
+ import "./events/schema.js";
56
+ import { DEVTOOLS_COOKIE, SWITCH_COOKIE_OPTIONS, switch_in_url } from "./insights/switch.js";
57
+ import { mark_personal } from "./server/personal-response.js";
58
+ import { ogygiaTransport } from "./transport.js";
59
+ import { document } from "./document.js";
60
+ import { liftRegions, restoreRegions, scanRegions } from "./server/split-regions.js";
61
+ import { render } from "svelte/server";
62
+ import * as devalue from "devalue";
63
+ import { stringify } from "devalue";
64
+ import runtime_url from "virtual:ogygia/runtime-url";
65
+ import { fnManifest, islandCss } from "virtual:ogygia/island-deps";
66
+ import { try_get_request_store } from "@sveltejs/kit/internal/server";
67
+ import dev_hmr_url from "virtual:ogygia/dev-hmr-url";
68
+ import { enabled, viewTransitions } from "virtual:ogygia/router-config";
69
+ import { island_name, island_reads_page_data, island_url, load_islands, render_island } from "virtual:ogygia/server-manifest";
70
+ import { create_remote_key } from "virtual:ogygia/kit-wire";
71
+ import { building, dev } from "$app/env";
72
+ import { rateLimit } from "virtual:ogygia/rate-limit";
73
+ import { sessionCookie } from "virtual:ogygia/session-cookie";
74
+ import { route_config } from "virtual:ogygia/route-config";
75
+ import devtools_boot_url from "virtual:ogygia/devtools-boot-url";
76
+ import { plugins } from "virtual:ogygia/server-plugins";
77
+ // src/hooks.ts
78
+ /**
79
+ * SvelteKit server `handle` for signed region holes (`defer` / remount:`swr`).
80
+ *
81
+ * Serves `GET <base>/__ogygia__?id=…&props=…&exp=…&sig=…` by verifying the region MAC,
82
+ * rendering the region component server-side (cookies, remote functions, and `await` work),
83
+ * and returning HTML for the client runtime to swap in.
84
+ *
85
+ * Composable with `sequence()` — intercepts only the region endpoint path; otherwise
86
+ * calls `resolve(event)`. Also injects the document-level page seed used by islands.
87
+ *
88
+ * @example
89
+ * ```ts
90
+ * // src/hooks.server.ts
91
+ * import { ogygiaHandle } from 'ogygia/hooks';
92
+ * import { sequence } from '@sveltejs/kit/hooks';
93
+ * export const handle = sequence(ogygiaHandle(), myOtherHandle);
94
+ * ```
95
+ *
96
+ * @packageDocumentation
97
+ */
98
+ /** Is devtools on for this request's browser (a devtools BUILD): the URL's `?og-devtools=on|off`
99
+ * wins and is written to the response's cookie, else the cookie (insights/switch.ts). */
100
+ function devtools_switch(event) {
101
+ if (building) return false;
102
+ const want = switch_in_url(event.url);
103
+ if (want === null) return event.cookies.get(DEVTOOLS_COOKIE) === "on";
104
+ if (want) event.cookies.set(DEVTOOLS_COOKIE, "on", SWITCH_COOKIE_OPTIONS);
105
+ else event.cookies.delete(DEVTOOLS_COOKIE, { path: "/" });
106
+ return want;
107
+ }
108
+ /** Hard cap on rendered region HTML (bytes). */
109
+ const MAX_REGION_BODY = 2e6;
110
+ const DEVTOOLS = typeof __OGYGIA_DEVTOOLS__ !== "undefined" ? __OGYGIA_DEVTOOLS__ : false;
111
+ const DEVTOOLS_LAZY = typeof __OGYGIA_DEVTOOLS_LAZY__ !== "undefined" ? __OGYGIA_DEVTOOLS_LAZY__ : false;
112
+ /** High-res clock for server-realm devtools timestamps. */
113
+ const dt_now = () => typeof performance !== "undefined" && performance.now ? performance.now() : Date.now();
114
+ const bags = /* @__PURE__ */ new WeakMap();
115
+ /** This request's bag, or `undefined` outside a Kit page request (a hole endpoint, a remote-function
116
+ * call, a render with no Kit store around it). */
117
+ function bag_of() {
118
+ const request = try_get_request_store()?.event?.request;
119
+ return request ? bags.get(request) : void 0;
120
+ }
121
+ set_ctx_recorder((key, value) => {
122
+ const bag = bag_of();
123
+ if (bag) bag.ctx.set(key, value);
124
+ });
125
+ const doc_asks = /* @__PURE__ */ new WeakMap();
126
+ const request_of = () => try_get_request_store()?.event?.request;
127
+ set_ask_scope_opener(() => {
128
+ const request = request_of();
129
+ if (request && !bags.has(request) && !doc_asks.has(request)) doc_asks.set(request, {
130
+ wanted: false,
131
+ keys: null
132
+ });
133
+ });
134
+ set_seed_ask_reader(() => {
135
+ const bag = bag_of();
136
+ if (bag) return {
137
+ wanted: bag.seed_wanted,
138
+ keys: bag.seed_keys
139
+ };
140
+ const request = request_of();
141
+ const d = request ? doc_asks.get(request) : void 0;
142
+ return d ? {
143
+ wanted: d.wanted,
144
+ keys: d.keys
145
+ } : void 0;
146
+ });
147
+ set_page_recorder((snapshot, seed, remotes, entry) => {
148
+ const event = try_get_request_store()?.event;
149
+ if (event && note_render_page_ask(event, seed)) return;
150
+ const bag = bag_of();
151
+ if (!bag) {
152
+ const request = request_of();
153
+ const d = request ? doc_asks.get(request) : void 0;
154
+ if (d && seed !== false) {
155
+ d.wanted = true;
156
+ d.keys = merge_seed_ask(d.keys, seed);
157
+ }
158
+ return;
159
+ }
160
+ bag.page = {
161
+ ...bag.page,
162
+ ...snapshot
163
+ };
164
+ if (seed !== false) {
165
+ bag.seed_wanted = true;
166
+ bag.seed_keys = merge_seed_ask(bag.seed_keys, seed);
167
+ }
168
+ if (bag.seed_asks && entry && seed !== false) bag.seed_asks.set(entry, seed);
169
+ if (remotes === null) bag.remotes_wanted = null;
170
+ else if (bag.remotes_wanted) for (const h of remotes) bag.remotes_wanted.add(h);
171
+ });
172
+ set_tail_reader(() => bag_of()?.tail ?? null);
173
+ set_measure_memo_reader(() => bag_of()?.measure_memo ?? null);
174
+ configure_render_page({ warn: dev ? (m) => console.warn(m) : null });
175
+ set_kit_event_reader(() => try_get_request_store()?.event ?? null);
176
+ /** Does this hole's server tree read `page.data` (the build's answer; unknown in dev → yes). */
177
+ const hole_reads_page_data = (id) => island_reads_page_data === null || island_reads_page_data[id] !== false;
178
+ set_render_page_port({
179
+ ready(reads_data) {
180
+ const store = try_get_request_store();
181
+ return prepare_render_page(store?.event, store?.state?.transport, reads_data);
182
+ },
183
+ tail() {
184
+ const store = try_get_request_store();
185
+ return render_page_facts_script(store?.event, store?.state?.transport);
186
+ },
187
+ version(hole_id) {
188
+ if (!hole_reads_page_data(hole_id)) return "";
189
+ const v = render_page_version(try_get_request_store()?.event, bag_of()?.page ?? void 0);
190
+ return v ? "&pv=" + v : "";
191
+ }
192
+ });
193
+ set_kit_page_reader(() => {
194
+ const bag = bag_of();
195
+ return render_page(bag ? bag.page ?? {} : void 0, try_get_request_store()?.event);
196
+ });
197
+ set_late_scope_opener(() => {
198
+ const bag = bag_of();
199
+ if (bag) bag.late_open = true;
200
+ });
201
+ set_late_recorder((promise) => {
202
+ const bag = bag_of();
203
+ if (!bag?.late_open) return null;
204
+ const id = `r${bag.late_next++}`;
205
+ (bag.late ??= []).push({
206
+ id,
207
+ promise
208
+ });
209
+ return id;
210
+ });
211
+ set_late_taker(() => {
212
+ const bag = bag_of();
213
+ if (!bag?.late?.length) return null;
214
+ const list = bag.late;
215
+ bag.late = null;
216
+ return list;
217
+ });
218
+ set_current_request(() => try_get_request_store()?.event?.request);
219
+ set_source_recorder((tag) => {
220
+ current_facts()?.sources?.push(tag);
221
+ });
222
+ set_page_route_config(route_config);
223
+ const plugins$1 = start_plugins(plugins, {
224
+ sign: (message) => sign(signing_key().secret, message),
225
+ verify: (message, signature) => verify(signing_key().secret, message, signature),
226
+ lifetime: app_lifetime,
227
+ deny: region_denied
228
+ });
229
+ const dt_buffers = /* @__PURE__ */ new WeakMap();
230
+ function dt_record(bag, input) {
231
+ const buf = bag ? dt_buffers.get(bag) : void 0;
232
+ if (!buf) return;
233
+ buf.events.push({
234
+ ...input,
235
+ v: 1,
236
+ seq: buf.seq++,
237
+ t: dt_now(),
238
+ realm: "server"
239
+ });
240
+ }
241
+ if (DEVTOOLS) set_server_devtools_recorder((input) => dt_record(bag_of(), input));
242
+ /** Cap on a batch POST body before `request.json()` buffers it. 32 endpoints × ~8.5kB (props cap
243
+ * 8192 + URL overhead) ≈ 270kB; 512kB leaves margin. Rejected up front via `content-length`. */
244
+ const MAX_BATCH_BODY = 524288;
245
+ /** Abort waiting on slow region SSR (work may continue — see INVARIANTS · RENDER-TIMEOUT). */
246
+ const RENDER_TIMEOUT_MS = 1e4;
247
+ /** Process-local cap on concurrent region SSR (M1 CPU amp under valid MAC). */
248
+ const render_gate = new ConcurrencyGate(4);
249
+ /** The per-plugin contexts of an app with no plugins (shared: never written to). */
250
+ const NO_CTXS = [];
251
+ /**
252
+ * Anti-framing + MIME + Referrer on every region response.
253
+ * Referrer-Policy strips capability query strings from third-party asset requests (H6).
254
+ */
255
+ const REGION_FRAME_HEADERS = {
256
+ "X-Frame-Options": "DENY",
257
+ "Content-Security-Policy": "frame-ancestors 'none'",
258
+ "X-Content-Type-Options": "nosniff",
259
+ "Referrer-Policy": "no-referrer"
260
+ };
261
+ function region_response(body, init) {
262
+ return new Response(body, {
263
+ status: init.status,
264
+ headers: {
265
+ ...REGION_FRAME_HEADERS,
266
+ ...init.headers
267
+ }
268
+ });
269
+ }
270
+ /**
271
+ * Every refused region request: a 403 that says why (`x-ogygia-deny`) and which key answered
272
+ * (`x-ogygia-key`, the fingerprint a capability carries as `&k=`). Neither is an oracle: every
273
+ * reason past `sig` is reached only with a capability this key signed (an unknown id still never
274
+ * tells from a bad MAC, SEC-01), and the fingerprint is an HMAC of a constant.
275
+ */
276
+ function region_denied(why) {
277
+ return region_response("Forbidden", {
278
+ status: 403,
279
+ headers: {
280
+ "x-ogygia-deny": why,
281
+ "x-ogygia-key": signing_key().fp
282
+ }
283
+ });
284
+ }
285
+ /** A capability minted under another key than this deployment's (its `&k=` fingerprint). One
286
+ * without `k` (minted before capabilities named their key) is left to the MAC. */
287
+ function foreign_key(k) {
288
+ return k !== null && k !== signing_key().fp;
289
+ }
290
+ function capability_of(params) {
291
+ return {
292
+ id: params.get("id") ?? "",
293
+ render: params.get("r") ?? "",
294
+ payload: params.get("props") ?? "",
295
+ exp: params.get("exp") ?? "",
296
+ ttl: params.get("ttl") ?? "",
297
+ sig: params.get("sig") ?? "",
298
+ k: params.get("k")
299
+ };
300
+ }
301
+ /**
302
+ * The server entry that answers a verified capability: its own id when this build has it, else an
303
+ * entry of this build rendering the same component (its signed render identity) — the capability
304
+ * came from another build: an older cached page, another deployment, a changed schedule or salt.
305
+ * Null when this build renders neither: the component is gone, moved or renamed.
306
+ */
307
+ function capability_target(cap) {
308
+ if (Object.hasOwn(island_url, cap.id)) return cap.id;
309
+ if (cap.render !== "" && Object.hasOwn(render_island, cap.render)) return render_island[cap.render];
310
+ return null;
311
+ }
312
+ /**
313
+ * Decode a request pathname without throwing on malformed percent-encoding (SEC-05).
314
+ * @returns decoded path, or null if the encoding is invalid
315
+ */
316
+ function decode_pathname(pathname) {
317
+ try {
318
+ return decodeURIComponent(pathname);
319
+ } catch {
320
+ return null;
321
+ }
322
+ }
323
+ /** Resolve a rate-limit key; fail closed (null) when the adapter cannot identify the client.
324
+ * Never trust X-Forwarded-For / spoofable proxy headers — adapters must provide getClientAddress(). */
325
+ function client_ip(event) {
326
+ try {
327
+ return event.getClientAddress();
328
+ } catch {
329
+ return null;
330
+ }
331
+ }
332
+ /**
333
+ * Stylesheet `<link>`s a server-picked region needs so a page that never imported the component
334
+ * still styles the fetched HTML (the whole point of a held region — the page can't know which
335
+ * component the server will choose). Tagged `data-ogygia-region-css` so the client runtime HOISTS
336
+ * them into `<head>`: a body `<link>` wouldn't load inside a `<template>` batch parcel, and a head
337
+ * link loads once and is deduped across regions. Empty for a plain island (its CSS is already in the
338
+ * page's own stylesheet) or before a build (`islandCss` reads the build-time handoff).
339
+ */
340
+ function region_css_links(id) {
341
+ const url = island_url[id];
342
+ if (!url) return "";
343
+ let out = "";
344
+ for (const href of islandCss(url)) out += region_css_tag(href, kit_asset(href));
345
+ return out;
346
+ }
347
+ /**
348
+ * Wrap a payload as an `application/ogygia-*` side-channel `<script>` the runtime reads. The
349
+ * `payload` MUST be `<`-safe already: devalue output is by construction (it writes `<`), a
350
+ * JSON payload goes through `escape_script_text` first — so this only builds the tag. One spot for
351
+ * the side-channel shape (page / remote / ctx / devtools).
352
+ */
353
+ function emit_ogygia_script(subtype, escaped_payload, marker = "") {
354
+ return `<script type="application/ogygia-${subtype}"${marker ? " " + marker : ""}>${escaped_payload}<\/script>`;
355
+ }
356
+ const DOUBLE_QUOTE_G = /"/g;
357
+ /** Stamped into the head of a csr=true document: the runtime reads it (`kit_hydrates_page`)
358
+ * instead of scanning the page's inline scripts for Kit's bootstrap. */
359
+ const CSR_META = "<meta name=\"ogygia-csr\" content=\"true\">";
360
+ const CSR_FALSE_META = "<meta name=\"ogygia-csr\" content=\"false\">";
361
+ /** the og.$ factory script, per manifest object (the build's, the same every request) */
362
+ const fnm_script_cache = /* @__PURE__ */ new WeakMap();
363
+ /** A document fetched by ogygia's router (runtime/router-nav.ts `nav_headers`: a navigation or a
364
+ * prefetch) — morphed into the live page rather than loaded as one. */
365
+ function router_fetched(event) {
366
+ return event.request.headers.get("x-ogygia-spa") !== null;
367
+ }
368
+ const NO_TRANSPORT = {};
369
+ const seed_codec_cache = /* @__PURE__ */ new WeakMap();
370
+ /** The seed's devalue reducers — the app's transport encoders merged with the defer markers — and a
371
+ * stringify bound to them, made once per transport object (Kit hands the same one every request). */
372
+ function seed_codecs(transport) {
373
+ const key = transport ?? NO_TRANSPORT;
374
+ let hit = seed_codec_cache.get(key);
375
+ if (!hit) {
376
+ const seed_reducers = {
377
+ ...Object.fromEntries(Object.entries(transport ?? {}).map(([name, codec]) => [name, codec.encode])),
378
+ ...page_seed_reducers
379
+ };
380
+ hit = {
381
+ seed_reducers,
382
+ seed_stringify: ((v) => stringify(v, seed_reducers))
383
+ };
384
+ seed_codec_cache.set(key, hit);
385
+ }
386
+ return hit;
387
+ }
388
+ /** `</body>` as bytes (ASCII: the same in every UTF-8 document). */
389
+ const BODY_CLOSE_BYTES = [
390
+ 60,
391
+ 47,
392
+ 98,
393
+ 111,
394
+ 100,
395
+ 121,
396
+ 62
397
+ ];
398
+ /** Does `</body>` end in `chunk` — searched backwards from its end, where it sits — or straddle the
399
+ * boundary with the previous chunk's last bytes (`carry`, at most 6)? No decode. */
400
+ function has_body_close(carry, chunk) {
401
+ const at_bytes = (buf, i) => {
402
+ for (let k = 0; k < 7; k++) if (buf[i + k] !== BODY_CLOSE_BYTES[k]) return false;
403
+ return true;
404
+ };
405
+ for (let i = chunk.lastIndexOf(60); i !== -1; i = i === 0 ? -1 : chunk.lastIndexOf(60, i - 1)) if (at_bytes(chunk, i)) return true;
406
+ if (!carry.length) return false;
407
+ const seam = new Uint8Array(carry.length + Math.min(6, chunk.length));
408
+ seam.set(carry);
409
+ seam.set(chunk.subarray(0, seam.length - carry.length), carry.length);
410
+ for (let i = 0; i + 7 <= seam.length; i++) if (at_bytes(seam, i)) return true;
411
+ return false;
412
+ }
413
+ function csr_page_of(html, body_end, event, bag) {
414
+ return event?.route?.id != null ? bag?.page?.error != null ? error_route_is_csr_true(event.route.id) : route_is_csr_true(event.route.id) : body_end !== -1 && html_has_kit_bootstrap(html, body_end);
415
+ }
416
+ /** The restorer, inline (runtime/restore.ts — self-contained, so its source runs as is): restores the
417
+ * document now, and stays as `__og_restore` / `__og_restore_adopt` for hole answers and router swaps. */
418
+ const RESTORER_SCRIPT = `<script data-og-restore>(function(){var r=${restore.toString()};window.__og_restore=r;window.__og_restore_adopt=${restore_adopt.toString()};r(document)})()<\/script>`;
419
+ var OgygiaHandle = class {
420
+ #endpoint;
421
+ #speculation_rules;
422
+ /** The app's server transform (documents and region answers) — see OgygiaHandleOptions. */
423
+ #transform;
424
+ render_rate;
425
+ probe_rate;
426
+ constructor(options = {}) {
427
+ this.#transform = options.transform;
428
+ configure_islands_endpoint(options.endpoint);
429
+ this.#endpoint = islands_endpoint();
430
+ this.#speculation_rules = enabled ? "" : mpaSpeculationRules(this.#endpoint);
431
+ this.render_rate = new RateLimiter({
432
+ max: rateLimit.max,
433
+ windowMs: rateLimit.windowMs
434
+ });
435
+ /** Cheap pre-HMAC probe budget — forged traffic pays this, not full render quota (HMAC-CPU-DOS). */
436
+ this.probe_rate = new RateLimiter({
437
+ max: rateLimit.max <= 0 ? 0 : Math.max(rateLimit.max * 5, 120),
438
+ windowMs: rateLimit.windowMs
439
+ });
440
+ }
441
+ handle = around(plugins$1, (input) => this.#core(input));
442
+ #core = async ({ event, resolve }) => {
443
+ const path = decode_pathname(event.url.pathname);
444
+ if (path === null) return new Response("Bad Request", { status: 400 });
445
+ const facts = facts_of(event.request);
446
+ if (plugins$1.length === 0) return this.#route(event, resolve, path, NO_CTXS, facts);
447
+ const ctxs = request_contexts(plugins$1, event, path, facts, (endpoint) => this.#render_hole(endpoint, event));
448
+ try {
449
+ for (let i = 0; i < plugins$1.length; i++) {
450
+ const answer = await plugins$1[i].def.request?.(ctxs[i]);
451
+ if (answer) return answer;
452
+ }
453
+ return await this.#route(event, resolve, path, ctxs, facts);
454
+ } finally {
455
+ for (let i = 0; i < plugins$1.length; i++) try {
456
+ plugins$1[i].def.done?.(ctxs[i]);
457
+ } catch {}
458
+ }
459
+ };
460
+ /** One signed hole rendered in place with THIS request's event (a plugin's `ctx.renderHole`:
461
+ * the stored-page stitch). Null keeps the fallback: a refused capability, a failed render, or
462
+ * an answer that asks to keep it. */
463
+ async #render_hole(endpoint, event) {
464
+ const out = await this.#render_capability(endpoint, event);
465
+ return out && out.html !== "<!--ogygia:keep-fallback-->" ? out.html : null;
466
+ }
467
+ async #route(event, resolve, path, ctxs, facts) {
468
+ if (!path.endsWith(this.#endpoint)) {
469
+ if (event.isDataRequest && event.request.headers.has("x-ogygia-page-facts")) {
470
+ const res = await resolve(event);
471
+ try {
472
+ res.headers.set(PAGE_FACTS_ROUTE_HEADER, encodeURIComponent(JSON.stringify({
473
+ id: event.route.id,
474
+ params: event.params
475
+ })));
476
+ } catch {}
477
+ return res;
478
+ }
479
+ const devtools_on = DEVTOOLS && (!DEVTOOLS_LAZY || devtools_switch(event));
480
+ const devtools_personal = DEVTOOLS_LAZY && !building && (devtools_on || switch_in_url(event.url) !== null);
481
+ facts.private = devtools_personal;
482
+ facts.answerForm = !!this.#transform && router_fetched(event);
483
+ const store = try_get_request_store();
484
+ const bag = {
485
+ ctx: /* @__PURE__ */ new Map(),
486
+ page: null,
487
+ seed_wanted: false,
488
+ seed_keys: null,
489
+ seed_asks: request_stats_detailed() ? /* @__PURE__ */ new Map() : null,
490
+ remotes_wanted: /* @__PURE__ */ new Set(),
491
+ tail: new DocumentTail(),
492
+ measure_memo: /* @__PURE__ */ new Map(),
493
+ deferred: null,
494
+ defer_next_id: 0,
495
+ late: null,
496
+ late_next: 0,
497
+ late_open: false,
498
+ seed_reducers: null,
499
+ facts
500
+ };
501
+ const lean = devtools_on && !building && (event.cookies.get("og_testing") === "lean" || event.url.searchParams.get("og-testing") === "lean");
502
+ if (devtools_on && !lean) dt_buffers.set(bag, {
503
+ events: [],
504
+ seq: 0
505
+ });
506
+ bags.set(event.request, bag);
507
+ for (let i = 0; i < ctxs.length; i++) {
508
+ const answer = await plugins$1[i].def.page?.(ctxs[i]);
509
+ if (answer) return answer;
510
+ }
511
+ const set_headers = event.setHeaders;
512
+ event.setHeaders = (headers) => {
513
+ set_headers(headers);
514
+ for (const key in headers) if (key.toLowerCase() === "cache-control") note_cache_control(event.request, headers[key]);
515
+ };
516
+ const response = await resolve(event, { transformPageChunk: async ({ html }) => this.inject_client_seeds(this.#transform ? await this.#transform_document(html, event, bag) : html, store?.state, event, bag) });
517
+ if (devtools_personal) mark_personal(response);
518
+ if (this.#transform && (response.headers.get("content-type") ?? "").includes("text/html")) try {
519
+ response.headers.append("vary", "x-ogygia-spa");
520
+ } catch {}
521
+ if (devtools_on && DEVTOOLS_LAZY && (response.headers.get("content-type") ?? "").includes("text/html")) try {
522
+ if (!response.headers.has("document-policy")) response.headers.set("document-policy", "js-profiling");
523
+ if (event.route?.id) response.headers.append("server-timing", `og-route;desc=${JSON.stringify(event.route.id)}`);
524
+ } catch {}
525
+ if (bag.deferred && bag.deferred.length) facts.streamed = true;
526
+ let out = response;
527
+ for (let i = 0; i < ctxs.length; i++) out = await plugins$1[i].def.response?.(ctxs[i], out) ?? out;
528
+ if (out !== response) return out;
529
+ if (bag.deferred && bag.deferred.length) return this.stream_page_deferred(response, bag.deferred, bag.defer_next_id, bag.seed_reducers ?? void 0);
530
+ if (!bag.kit_client && !response.headers.has("content-length") && (response.headers.get("content-type") ?? "").includes("text/html")) return drop_dead_kit_resolves(response);
531
+ return response;
532
+ }
533
+ if (event.request.method.toUpperCase() === "POST") return this.render_batch(event);
534
+ return this.render_region(event);
535
+ }
536
+ /**
537
+ * Batch frame stream (client navigation, single-flight). POST body: a JSON `string[]` of signed
538
+ * region endpoints — the calls the client needs. Renders them in parallel and flushes each as a
539
+ * `<template data-ogygia-slot="sig">…</template>` frame the moment IT settles (out of order); a
540
+ * done sentinel ends it. One response, many frames. Every call carries its own MAC so there's no
541
+ * extra auth; same-origin + per-IP budget mirror the single-region path.
542
+ */
543
+ async render_batch(event) {
544
+ const MAX_BATCH = 32;
545
+ if (event.request.headers.get("sec-fetch-site") === "cross-site") return region_denied("cross-site");
546
+ const ip = client_ip(event);
547
+ if (!ip) return region_response("Too Many Requests", { status: 429 });
548
+ if (this.probe_rate.limited(ip) || this.render_rate.limited(ip)) return region_response("Too Many Requests", { status: 429 });
549
+ const content_length = Number(event.request.headers.get("content-length"));
550
+ if (Number.isFinite(content_length) && content_length > MAX_BATCH_BODY) return region_response("Payload Too Large", { status: 413 });
551
+ let parsed;
552
+ try {
553
+ parsed = await event.request.json();
554
+ } catch {
555
+ return region_response("Bad Request", { status: 400 });
556
+ }
557
+ if (!Array.isArray(parsed) || parsed.length === 0) return region_response("Bad Request", { status: 400 });
558
+ const calls = parsed.filter((e) => typeof e === "string").slice(0, MAX_BATCH);
559
+ const render = (endpoint) => this.#render_capability(endpoint, event, true);
560
+ const encoder = new TextEncoder();
561
+ return region_response(new ReadableStream({ async start(controller) {
562
+ await Promise.all(calls.map(async (endpoint) => {
563
+ const out = await render(endpoint).catch(() => null);
564
+ const parcel = out ? build_parcel(out.slot, out.html) : null;
565
+ if (parcel) controller.enqueue(encoder.encode(parcel));
566
+ }));
567
+ controller.enqueue(encoder.encode(done_parcel()));
568
+ controller.close();
569
+ } }), {
570
+ status: 200,
571
+ headers: {
572
+ "content-type": "text/html; charset=utf-8",
573
+ "cache-control": "no-store",
574
+ "x-accel-buffering": "no"
575
+ }
576
+ });
577
+ }
578
+ /**
579
+ * THE APP'S TRANSFORM ON A DOCUMENT (server/reversible.ts): the chunk carrying `</head>` (the
580
+ * document; a streamed tail chunk passes untouched) is marked, handed to the transform, settled.
581
+ * Then the head gets the transform's `data-og-head` assets (deduped) and, when the parser would have
582
+ * restructured a tag, the stand-ins' sheet; the body gets the restorer — inline, before `</body>`,
583
+ * so it runs before any island wakes, before Kit starts, and before a deferred module upgrades a
584
+ * host. It also stays on the page as a global for the runtime's hole answers and router swaps.
585
+ */
586
+ async #transform_document(html, event, bag) {
587
+ if (html.indexOf("</head>") === -1) return html;
588
+ const csr = csr_page_of(html, html.lastIndexOf("</body>"), event, bag);
589
+ const answer = router_fetched(event);
590
+ const marked = mark(html, "document", csr, answer);
591
+ const out = await this.#transform(marked ? marked.html : html, {
592
+ kind: "document",
593
+ csr,
594
+ event
595
+ });
596
+ const s = marked ? settle(out, marked.record, { dev }) : null;
597
+ let first_load = false;
598
+ if (marked && !answer) {
599
+ for (const h of marked.record.hosts.values()) if (!h.planned) first_load = true;
600
+ }
601
+ bag.transform_head = (s?.head.join("") ?? "") + (s?.stand_ins ? `<style data-og-stand-ins>${STAND_IN_CSS}</style>` : "") + (first_load ? "<meta name=\"ogygia-first-load\">" : "");
602
+ bag.transform_body = (s?.check ? check_script(s.check) : "") + RESTORER_SCRIPT;
603
+ return s ? s.html : out;
604
+ }
605
+ /** THE APP'S TRANSFORM ON A REGION ANSWER: marked, transformed, settled. The runtime restores it
606
+ * before insertion (and hoists its `data-og-head` assets), so no stand-in sheet is needed. */
607
+ async #transform_region(html, event) {
608
+ const marked = mark(html, "region", false);
609
+ const out = await this.#transform(marked ? marked.html : html, {
610
+ kind: "region",
611
+ csr: false,
612
+ event
613
+ });
614
+ if (!marked) return out;
615
+ const s = settle(out, marked.record, { dev });
616
+ return s.check ? s.html + check_script(s.check) : s.html;
617
+ }
618
+ /**
619
+ * Document-level side-channels: one page snapshot + optional remote query seed.
620
+ * Skips Kit-booted (csr=true) pages which serialize remotes themselves.
621
+ */
622
+ async inject_client_seeds(html, state, event, bag) {
623
+ const t_start = performance.now();
624
+ const spans = locate(html);
625
+ const head = spans.head_end === -1 ? null : html.slice(0, spans.head_end);
626
+ const csr_page = csr_page_of(html, spans.body_end, event, bag);
627
+ if (csr_page && bag) bag.kit_client = true;
628
+ if (csr_page) {
629
+ let head_inject = "";
630
+ if (head !== null) {
631
+ head_inject = CSR_META;
632
+ if (devtools_boot_url && !head.includes("data-ogygia-devtools-boot")) head_inject += `<script type="module" data-ogygia-devtools-boot src="${devtools_boot_url}"><\/script>`;
633
+ }
634
+ if (head !== null && bag?.transform_head) head_inject = bag.transform_head + head_inject;
635
+ const tail = spans.body_end !== -1 && bag ? (bag.transform_body ?? "") + bag.tail.render(null) : "";
636
+ if (head === null && !tail) return html;
637
+ const ordered = head === null ? null : runtime_first(head, null);
638
+ return assemble(html, spans, ordered === head ? null : ordered, head_inject, tail);
639
+ }
640
+ let head_out = null;
641
+ let head_inject = head !== null ? CSR_FALSE_META : "";
642
+ if (head !== null) {
643
+ const deduped = dedupe_head_links(head);
644
+ if (deduped !== head) head_out = deduped;
645
+ const probe = head_out ?? head;
646
+ if (!enabled && !page_declares_speculation_rules(probe)) head_inject += `<script type="speculationrules" data-ogygia-speculate>${this.#speculation_rules}<\/script>`;
647
+ if (enabled && !page_declares_router_meta(probe)) head_inject += `<meta name="ogygia-router" content="${viewTransitions ? "vt" : "plain"}">`;
648
+ const runtime_tag = enabled && runtime_url && !page_declares_runtime_script(probe) ? runtime_bootstrap(kit_asset) : null;
649
+ const ordered = runtime_first(probe, runtime_tag);
650
+ if (ordered !== probe) head_out = ordered;
651
+ if (dev_hmr_url && !page_declares_dev_hmr_script(probe)) {
652
+ head_inject += `<script type="module" data-ogygia-dev-hmr src="${kit_asset(dev_hmr_url)}"><\/script>`;
653
+ const scope = (event?.route.id ?? "").split("/").filter(Boolean)[0] ?? "";
654
+ head_inject += `<meta name="ogygia-dev-scope" content="${scope.replace(DOUBLE_QUOTE_G, "")}">`;
655
+ }
656
+ }
657
+ if (head !== null && bag?.transform_head) head_inject = bag.transform_head + head_inject;
658
+ if (spans.body_end === -1) return assemble(html, spans, head_out, head_inject, "");
659
+ const rendered = !!bag && bag.page !== null;
660
+ const scripts = bag?.transform_body ? [bag.transform_body] : [];
661
+ if (!rendered) {
662
+ this.append_devtools_seed(scripts, bag);
663
+ return assemble(html, spans, head_out, head_inject, scripts.join(""));
664
+ }
665
+ const page_snap = bag.page;
666
+ const seed_wanted = bag.seed_wanted;
667
+ const detail = request_stats_detailed();
668
+ const tail_html = bag.tail.render(seed_wanted ? index_seed(page_snap.data) : null, detail);
669
+ let seed_keys = bag.seed_keys;
670
+ if (seed_wanted && seed_keys !== "all" && seed_keys !== null) for (const k of index_seed(page_snap.data).touched) seed_keys.add(k);
671
+ const shaped_data = shape_page_data(page_snap.data, seed_keys);
672
+ let seed_data = shaped_data;
673
+ let seed_form = page_snap.form;
674
+ const { seed_reducers, seed_stringify } = seed_codecs(state?.transport);
675
+ const data_shape = analyze(shaped_data);
676
+ const form_shape = analyze(page_snap.form ?? null);
677
+ const has_pending = data_shape.thenable || form_shape.thenable;
678
+ if (has_pending) mark_per_visitor(bag.facts, "streamed load (promise in page data)");
679
+ const can_stream = event?.request.headers.get("sec-fetch-mode") === "navigate";
680
+ if (has_pending && can_stream && seed_wanted) {
681
+ const staged_data = stage_deferred(shaped_data, 0);
682
+ const staged_form = stage_deferred(page_snap.form, staged_data.next_id);
683
+ seed_data = staged_data.staged;
684
+ seed_form = staged_form.staged;
685
+ bag.deferred = [...staged_data.deferred, ...staged_form.deferred];
686
+ bag.defer_next_id = staged_form.next_id;
687
+ bag.seed_reducers = seed_reducers;
688
+ scripts.push(`<script>${PAGE_DEFER_BOOTSTRAP}<\/script>`);
689
+ } else if (has_pending && seed_wanted) {
690
+ seed_data = await settle_deferred(shaped_data);
691
+ seed_form = await settle_deferred(page_snap.form);
692
+ }
693
+ if (tail_html) scripts.push(tail_html);
694
+ let remote_seed_bytes = 0;
695
+ let fnm_bytes = 0;
696
+ let ctx_bytes = 0;
697
+ const page_payload = event && seed_wanted ? PageSeed.serialize({
698
+ url: event.url,
699
+ params: event.params,
700
+ route: event.route,
701
+ status: page_snap.status ?? 200,
702
+ data: seed_data,
703
+ form: seed_form,
704
+ error: page_snap.error
705
+ }, seed_stringify, !has_pending && data_shape.json && form_shape.json && analyze(page_snap.error ?? null).json) : null;
706
+ if (page_payload) {
707
+ scripts.push(emit_ogygia_script("page", page_payload.text, "data-ogygia-page" + (page_payload.json ? ` ${WIRE_FORMAT_ATTR}="${WIRE_FORMAT_JSON}"` : "")));
708
+ if (DEVTOOLS) dt_record(bag, {
709
+ domain: "server",
710
+ name: "server.seed.injected",
711
+ kind: "page",
712
+ bytes: page_payload.text.length
713
+ });
714
+ }
715
+ if (state?.remote?.implicit) {
716
+ const remote_script = await this.build_remote_seed_script(state, bag.remotes_wanted);
717
+ if (remote_script) {
718
+ scripts.push(remote_script);
719
+ remote_seed_bytes = remote_script.length;
720
+ if (DEVTOOLS) dt_record(bag, {
721
+ domain: "server",
722
+ name: "server.seed.injected",
723
+ kind: "remote",
724
+ bytes: remote_script.length
725
+ });
726
+ }
727
+ }
728
+ const fnm = fnManifest();
729
+ if (fnm) {
730
+ let fnm_script = fnm_script_cache.get(fnm);
731
+ if (fnm_script === void 0) {
732
+ fnm_script = `<script data-ogygia-fnm>globalThis.__OG_FNM=Object.assign(globalThis.__OG_FNM||{},{${Object.entries(fnm).map(([tag, src]) => `${JSON.stringify(tag)}:(${src})`).join(",")}});<\/script>`;
733
+ fnm_script_cache.set(fnm, fnm_script);
734
+ }
735
+ scripts.push(fnm_script);
736
+ fnm_bytes = fnm_script.length;
737
+ }
738
+ const provided = bag?.ctx;
739
+ if (provided?.size) {
740
+ const payload = serialize_provided_context(provided);
741
+ if (payload) {
742
+ scripts.push(emit_ogygia_script("ctx", payload, PAGE_CTX_MARKER));
743
+ ctx_bytes = payload.length;
744
+ }
745
+ }
746
+ this.append_devtools_seed(scripts, bag);
747
+ const out = assemble(html, spans, head_out, head_inject, scripts.join(""));
748
+ if (event && request_stats_wanted()) {
749
+ const size = bag.tail.size;
750
+ record_request_stats(event.request, {
751
+ transform_ms: Math.round((performance.now() - t_start) * 100) / 100,
752
+ islands: size.props,
753
+ hints: size.hints,
754
+ holes: size.holes,
755
+ seed_bytes: page_payload ? page_payload.text.length : 0,
756
+ remote_seed_bytes,
757
+ tail_bytes: tail_html.length,
758
+ fnm_bytes,
759
+ ctx_bytes,
760
+ seed_json: page_payload?.json ?? false,
761
+ ...detail ? {
762
+ seed_culprit: page_payload && !page_payload.json ? json_culprit(seed_data) : null,
763
+ island_rows: bag.tail.island_rows() ?? [],
764
+ seed: this.explain_seed(page_snap.data, seed_keys, bag),
765
+ hole_rows: bag.tail.hole_rows()
766
+ } : {}
767
+ });
768
+ }
769
+ return out;
770
+ }
771
+ /**
772
+ * THE SEED EXPLAINER: per top-level `page.data` key, its size and why it ships — an island's
773
+ * client code reads it (the build's per-entry keys), a sidecar points into it (seed refs), or
774
+ * some island reads the page whole and everything ships. Profiler detail only.
775
+ */
776
+ explain_seed(data, seed_keys, bag) {
777
+ const rows = bag.tail.island_rows() ?? [];
778
+ const names = /* @__PURE__ */ new Map();
779
+ for (const row of rows) if (row.name && !names.has(row.entry)) names.set(row.entry, row.name);
780
+ const name_of = (entry) => names.get(entry) ?? entry;
781
+ const add = (m, k, v) => (m.get(k) ?? m.set(k, /* @__PURE__ */ new Set()).get(k)).add(v);
782
+ const whole = /* @__PURE__ */ new Set();
783
+ const readers = /* @__PURE__ */ new Map();
784
+ for (const [entry, ask] of bag.seed_asks ?? []) if (ask === "all") whole.add(name_of(entry));
785
+ else if (ask !== false) for (const k of ask) add(readers, k, name_of(entry));
786
+ const referenced = /* @__PURE__ */ new Map();
787
+ for (const row of rows) for (const k of row.ref_keys) add(referenced, k, name_of(row.entry));
788
+ const whole_by = [...whole];
789
+ const keys = [];
790
+ if (data && typeof data === "object" && !Array.isArray(data)) for (const key of Object.keys(data)) {
791
+ const shipped = seed_keys === "all" || seed_keys !== null && seed_keys.has(key);
792
+ const read = [...readers.get(key) ?? []];
793
+ const refd = [...referenced.get(key) ?? []];
794
+ keys.push({
795
+ key,
796
+ bytes: analyze(data[key]).bytes,
797
+ readers: read,
798
+ referenced_by: refd,
799
+ shipped,
800
+ reason: !shipped ? null : read.length ? "read" : refd.length ? "referenced" : whole_by.length ? "whole" : "read"
801
+ });
802
+ }
803
+ keys.sort((a, b) => b.bytes - a.bytes);
804
+ return {
805
+ keys,
806
+ whole_by
807
+ };
808
+ }
809
+ /** DEVTOOLS: drain this request's server-realm events (region renders, capability mints, seeds)
810
+ * into an `application/ogygia-devtools` side-channel the client bus ingests — one stream, both
811
+ * realms, correlated by fingerprint. Appended LAST so the seed.injected events are included. */
812
+ append_devtools_seed(scripts, bag) {
813
+ const dt_buf = DEVTOOLS && bag ? dt_buffers.get(bag) : void 0;
814
+ if (DEVTOOLS && dt_buf && dt_buf.events.length) scripts.push(emit_ogygia_script("devtools", escape_script_text(JSON.stringify(dt_buf.events))));
815
+ }
816
+ /**
817
+ * Stream the captured `$page.data` promises into islands (csr=false, real browser load). The
818
+ * document — carrying the pending seed + resolve-global bootstrap — is already built by `resolve`;
819
+ * here we (1) forward it, (2) DRAIN Kit's own dead csr=false resolve tail so its
820
+ * `__sveltekit_<hash> is not defined` never reaches the browser, and (3) emit one
821
+ * `<script>__ogygia_page_resolve(id, ok, value)<\/script>` per promise AS IT SETTLES — completion
822
+ * order, non-blocking. Each island's `{#await page.data.x}` flips pending → resolved live.
823
+ */
824
+ stream_page_deferred(response, deferred, initial_next_id, reducers) {
825
+ const source = response.body;
826
+ if (!source) return response;
827
+ const reader = source.getReader();
828
+ const encoder = new TextEncoder();
829
+ const stream = new ReadableStream({
830
+ async start(controller) {
831
+ let carry = /* @__PURE__ */ new Uint8Array(0);
832
+ try {
833
+ for (;;) {
834
+ const { value, done } = await reader.read();
835
+ if (done) break;
836
+ controller.enqueue(value);
837
+ if (has_body_close(carry, value)) break;
838
+ carry = value.length >= 6 ? value.subarray(value.length - 6) : value;
839
+ }
840
+ } catch {}
841
+ (async () => {
842
+ try {
843
+ for (;;) {
844
+ const { done } = await reader.read();
845
+ if (done) break;
846
+ }
847
+ } catch {}
848
+ })();
849
+ let pending = deferred.length;
850
+ let next_id = initial_next_id;
851
+ let closed = false;
852
+ const maybe_close = () => {
853
+ if (pending === 0 && !closed) {
854
+ closed = true;
855
+ try {
856
+ controller.close();
857
+ } catch {}
858
+ }
859
+ };
860
+ const push = (id, ok, value) => {
861
+ try {
862
+ controller.enqueue(encoder.encode(resolve_script(PAGE_DEFER_GLOBAL, id, {
863
+ ok,
864
+ value
865
+ }, reducers)));
866
+ } catch {}
867
+ };
868
+ const stream_one = (id, promise) => {
869
+ Promise.resolve(promise).then((value) => {
870
+ const { staged, deferred: nested, next_id: after } = stage_deferred(value, next_id);
871
+ next_id = after;
872
+ push(id, true, staged);
873
+ pending += nested.length;
874
+ for (const n of nested) stream_one(n.id, n.promise);
875
+ pending -= 1;
876
+ maybe_close();
877
+ }, (error) => {
878
+ push(id, false, error);
879
+ pending -= 1;
880
+ maybe_close();
881
+ });
882
+ };
883
+ for (const { id, promise } of deferred) stream_one(id, promise);
884
+ maybe_close();
885
+ },
886
+ cancel() {
887
+ reader.cancel().catch(() => {});
888
+ }
889
+ });
890
+ const headers = new Headers(response.headers);
891
+ headers.delete("content-length");
892
+ return new Response(stream, {
893
+ status: response.status,
894
+ statusText: response.statusText,
895
+ headers
896
+ });
897
+ }
898
+ /**
899
+ * True when a remote's resolved value (deep) contains a region carrying baked SSR HTML — a
900
+ * page-sized render, not seed data (see the skip in {@link build_remote_seed_script}). Depth-capped:
901
+ * a region ticket sits shallow in any sane payload (a DocView's `entry.body` is 2 levels deep).
902
+ */
903
+ has_baked_region(value, depth = 0) {
904
+ if (depth > 6 || value === null || typeof value !== "object") return false;
905
+ const r = value;
906
+ if (r[REGION_BRAND] === true && typeof r.html === "string") return true;
907
+ if (Array.isArray(value)) return value.some((x) => this.has_baked_region(x, depth + 1));
908
+ for (const k in r) if (this.has_baked_region(r[k], depth + 1)) return true;
909
+ return false;
910
+ }
911
+ async build_remote_seed_script(state, wanted = null) {
912
+ const implicit = state.remote?.implicit;
913
+ if (!implicit) return null;
914
+ const data = await collect_remote_seed(implicit, wanted, {
915
+ memo: (internals) => state.remote.data?.get(internals),
916
+ skip_value: (v) => this.has_baked_region(v),
917
+ key: create_remote_key
918
+ });
919
+ if (!Object.values(data).some((b) => Object.keys(b).length > 0)) return null;
920
+ const transport = state.transport || {};
921
+ const reducers = Object.fromEntries(Object.entries(transport).map(([name, codec]) => [name, codec.encode]));
922
+ return emit_ogygia_script("remote", devalue.stringify(data, reducers));
923
+ }
924
+ /**
925
+ * `render()` the island under the concurrency gate + timeout. Returns the HTML body, or `null`
926
+ * if the render threw or timed out. Shared by the endpoint ({@link render_region}) and the
927
+ * batch path ({@link #render_capability}).
928
+ */
929
+ async #render_component(load, props, cache, report, timing, base, reads_page_data = false) {
930
+ const render_body = async () => {
931
+ const mod = await load();
932
+ const rendered = render(mod.default, {
933
+ props,
934
+ context: kit_render_context()
935
+ });
936
+ return await Promise.race([Promise.resolve(rendered).then((out) => {
937
+ const body = out.body;
938
+ if (body === "<!--ogygia:keep-fallback-->") return body;
939
+ return hole_head(out.head, base) + body + kit_page_facts_tail();
940
+ }), new Promise((_, rej) => setTimeout(() => rej(/* @__PURE__ */ new Error("region render timeout")), RENDER_TIMEOUT_MS))]);
941
+ };
942
+ try {
943
+ return await cached_render(async () => {
944
+ await kit_page_ready(reads_page_data);
945
+ if (!timing) return render_gate.run(render_body);
946
+ const asked = performance.now();
947
+ return render_gate.run(async () => {
948
+ const entered = performance.now();
949
+ timing.queue_ms = entered - asked;
950
+ try {
951
+ return await render_body();
952
+ } finally {
953
+ timing.render_ms = performance.now() - entered;
954
+ }
955
+ });
956
+ }, cache, Date.now(), report);
957
+ } catch (e) {
958
+ if (is_keep_fallback(e)) return KEEP_FALLBACK_HTML;
959
+ if (import.meta.env.DEV) console.warn("[ogygia] region render failed:", e);
960
+ return null;
961
+ }
962
+ }
963
+ /** A cached hole's memo key: the call and the visitor's session, and — when its tree reads
964
+ * `page.data` — the page it renders for (one page's facts never answer another page's hole). */
965
+ #hole_cache_key(id, payload, event, reads_page_data) {
966
+ const session = this.#region_session(event);
967
+ return render_cache_key(id, payload, reads_page_data ? session + "\n" + page_url_of(event).href : session);
968
+ }
969
+ /** The session cookie value sealed into a region capability (empty when no `sessionCookie` is
970
+ * configured) — the same read the MAC verify uses, and the per-user part of the render-cache key. */
971
+ #region_session(event) {
972
+ return sessionCookie ? event.cookies.get(sessionCookie) ?? "" : "";
973
+ }
974
+ /**
975
+ * Every check a capability passes BEFORE any HMAC (P5-HMAC-CPU), in order: charset/length (ids
976
+ * are 12-hex from the transform; `ttl` is signed, but charset-gated here so a forged value never
977
+ * reaches a response header), expiry (a renewal instead needs one inside the renew window: a URL
978
+ * that has not expired never renews), and the signing key it names. Null when it passes, else why
979
+ * it is refused.
980
+ */
981
+ #capability_precheck(cap, renewal = false) {
982
+ if (!is_region_id(cap.id) || cap.render !== "" && !is_region_id(cap.render) || cap.payload.length > 8192 || !is_region_ttl(cap.ttl)) return "shape";
983
+ const expiry = expiry_refusal(cap.exp, Math.floor(Date.now() / 1e3), renewal, app_lifetime.renew_window);
984
+ if (expiry) return expiry;
985
+ if (foreign_key(cap.k)) return "foreign-key";
986
+ return null;
987
+ }
988
+ /**
989
+ * RENEWAL (server/shared-cache.ts): re-sign an EXPIRED capability this app minted for an
990
+ * anonymous hole — the rescue for a hole on a document a cache kept longer than the hole's
991
+ * capability. Refused (null) unless the visitor carries no session and the MAC over the ORIGINAL
992
+ * tuple verifies with an empty session: nothing session-bound is ever renewed, and only a URL the
993
+ * app itself put in public HTML can be. The caller has already gated shape + the renew window
994
+ * and charged the probe budget. Returns the fresh `exp` + `sig`.
995
+ */
996
+ #renew_capability(cap, event) {
997
+ if (this.#region_session(event) !== "") return null;
998
+ const { secret } = signing_key();
999
+ if (!verify(secret, region_mac_message(cap.id, cap.exp, cap.payload, "", cap.ttl, cap.render), cap.sig)) return null;
1000
+ const exp = String(app_lifetime.renewed_expiry());
1001
+ return {
1002
+ ...cap,
1003
+ exp,
1004
+ sig: sign(secret, region_mac_message(cap.id, exp, cap.payload, "", cap.ttl, cap.render)),
1005
+ k: signing_key().fp
1006
+ };
1007
+ }
1008
+ /** THE auth check: session-bound region MAC verify (its render identity inside, when it has one). */
1009
+ #verify_region_mac(cap, event) {
1010
+ const session = sessionCookie ? event.cookies.get(sessionCookie) ?? "" : "";
1011
+ return verify(signing_key().secret, region_mac_message(cap.id, cap.exp, cap.payload, session, cap.ttl, cap.render), cap.sig);
1012
+ }
1013
+ /** Eval the island module (registers transportable codecs the reviver needs on a cold-start defer),
1014
+ * then decode + revive the props payload. Null on parse failure or a non-object/array result. */
1015
+ async #decode_region_props(payload, load) {
1016
+ let props;
1017
+ try {
1018
+ await load();
1019
+ register_wire_kind();
1020
+ register_store_kind();
1021
+ register_snippet_kind();
1022
+ register_fn_kind();
1023
+ register_derived_kind();
1024
+ props = devalue.parse(B64Url.decode(payload), { [REF_WIRE_KEY]: ref_reviver(false) });
1025
+ } catch (e) {
1026
+ if (import.meta.env.DEV) console.warn("[ogygia] region endpoint 403: island module load / props decode failed", e);
1027
+ return null;
1028
+ }
1029
+ if (props === null || typeof props !== "object" || Array.isArray(props)) return null;
1030
+ return props;
1031
+ }
1032
+ /**
1033
+ * Batch (single-flight navigation): verify a hole's OWN signed capability URL and render it in-process. Same
1034
+ * trust boundary as the endpoint (verify the MAC before touching the manifest), but every failure —
1035
+ * bad/expired MAC, unknown id, non-serializable props, render error, oversize — resolves to
1036
+ * `null` so the hole silently falls back to a client fetch. Never throws.
1037
+ */
1038
+ async #render_capability(endpoint, event, batch = false) {
1039
+ const q = endpoint.indexOf("?");
1040
+ if (q === -1) return null;
1041
+ const cap = capability_of(new URLSearchParams(endpoint.slice(q + 1)));
1042
+ const { id, payload, sig } = cap;
1043
+ if (this.#capability_precheck(cap)) return null;
1044
+ if (!this.#verify_region_mac(cap, event)) return null;
1045
+ const target = capability_target(cap);
1046
+ if (target === null) return null;
1047
+ const load = (await load_islands()).islands[target];
1048
+ if (typeof load !== "function") return null;
1049
+ const props = await this.#decode_region_props(payload, load);
1050
+ if (!props) return null;
1051
+ const ttl = Number(cap.ttl) || 0;
1052
+ const reads_page_data = hole_reads_page_data(target);
1053
+ const cache = ttl > 0 ? {
1054
+ key: this.#hole_cache_key(target, payload, event, reads_page_data),
1055
+ ttl
1056
+ } : void 0;
1057
+ const stats = batch && has_batch_hole_listener();
1058
+ const t0 = stats ? performance.now() : 0;
1059
+ const timing = {};
1060
+ let outcome = "none";
1061
+ const body = await this.#render_component(load, props, cache, stats ? (o) => outcome = o : void 0, stats ? timing : void 0, event.url, reads_page_data);
1062
+ if (stats) record_batch_hole_stats(event.request, {
1063
+ kind: "hole",
1064
+ id,
1065
+ cache: outcome,
1066
+ ttl,
1067
+ ...timing.queue_ms !== void 0 ? { queue_ms: Math.round(timing.queue_ms * 10) / 10 } : {},
1068
+ ...island_name?.[target] ? { name: island_name[target] } : {},
1069
+ p: hole_copy_key(payload),
1070
+ ms: performance.now() - t0,
1071
+ status: body === null ? 500 : 200
1072
+ });
1073
+ if (body === null || body.length > MAX_REGION_BODY) return null;
1074
+ if (body === "<!--ogygia:keep-fallback-->") return {
1075
+ slot: sig,
1076
+ html: KEEP_FALLBACK_HTML
1077
+ };
1078
+ let html = absolutize_hole_html(region_css_links(target) + body, event.url);
1079
+ if (batch && this.#transform) html = await this.#transform_region(html, event);
1080
+ return {
1081
+ slot: sig,
1082
+ html
1083
+ };
1084
+ }
1085
+ /**
1086
+ * Verify the region MAC, then render. Unknown ids and bad MACs both return 403 so the
1087
+ * existence of a region id is not an oracle (SEC-01). Expiry is part of the MAC message.
1088
+ *
1089
+ * Ordering: length/exp → probe rate (pre-HMAC) → verify → render rate → render.
1090
+ * Probe stops forged CPU amplification; render budget is only charged after a valid MAC.
1091
+ * A renewal (`&renew=1`) swaps the first three for its own: shape + renew window → probe →
1092
+ * anonymous-only re-verify of the original tuple + re-sign; then the same render rate + render.
1093
+ */
1094
+ async render_region(event) {
1095
+ const method = event.request.method.toUpperCase();
1096
+ if (method !== "GET" && method !== "HEAD") return region_response("Method Not Allowed", {
1097
+ status: 405,
1098
+ headers: { allow: "GET, HEAD" }
1099
+ });
1100
+ if (event.request.headers.get("sec-fetch-site") === "cross-site") return region_denied("cross-site");
1101
+ const url = event.url;
1102
+ const ip = client_ip(event);
1103
+ if (!ip) return region_response("Too Many Requests", { status: 429 });
1104
+ let cap = capability_of(url.searchParams);
1105
+ const { id, payload } = cap;
1106
+ const ttl_raw = cap.ttl;
1107
+ let renewed = null;
1108
+ const renewal = url.searchParams.get("renew") === "1";
1109
+ const refused = this.#capability_precheck(cap, renewal);
1110
+ if (refused) {
1111
+ if (import.meta.env.DEV && refused === "foreign-key") console.warn(`[ogygia] region endpoint 403: id "${id}" was signed by key ${cap.k}, this server signs with ${signing_key().fp}`);
1112
+ return region_denied(refused);
1113
+ }
1114
+ if (this.probe_rate.limited(ip)) return region_response("Too Many Requests", { status: 429 });
1115
+ if (renewal) {
1116
+ const fresh = this.#renew_capability(cap, event);
1117
+ if (!fresh) return region_denied(this.#region_session(event) !== "" ? "renew-session" : "sig");
1118
+ cap = fresh;
1119
+ renewed = `${url.pathname}?id=${encodeURIComponent(id)}${cap.render ? `&r=${cap.render}` : ""}&props=${payload}&exp=${cap.exp}${ttl_raw ? `&ttl=${ttl_raw}` : ""}&sig=${cap.sig}&k=${cap.k}`;
1120
+ } else if (!this.#verify_region_mac(cap, event)) {
1121
+ if (import.meta.env.DEV) console.warn(`[ogygia] region endpoint 403: bad signature for id "${id}"`);
1122
+ return region_denied("sig");
1123
+ }
1124
+ const cache_control = ttl_raw && !renewed ? `private, max-age=${Number(ttl_raw)}` : "no-store";
1125
+ /** The fresh capability rides every successful answer to a renewal (the 204 too). */
1126
+ const renew_headers = renewed ? { "x-ogygia-capability": renewed } : {};
1127
+ if (this.render_rate.limited(ip)) return region_response("Too Many Requests", { status: 429 });
1128
+ const target = capability_target(cap);
1129
+ if (target === null) {
1130
+ if (import.meta.env.DEV) console.warn(`[ogygia] region endpoint 403: id "${id}"${cap.render ? ` (component ${cap.render})` : ""} is not in the server manifest (${Object.keys(island_url).length} known)`);
1131
+ return region_denied("unknown-id");
1132
+ }
1133
+ const load = (await load_islands()).islands[target];
1134
+ if (typeof load !== "function") return region_denied("unknown-id");
1135
+ const props = await this.#decode_region_props(payload, load);
1136
+ if (!props) return region_denied("props");
1137
+ const ttl = Number(ttl_raw) || 0;
1138
+ const reads_page_data = hole_reads_page_data(target);
1139
+ const cache = ttl > 0 ? {
1140
+ key: this.#hole_cache_key(target, payload, event, reads_page_data),
1141
+ ttl
1142
+ } : void 0;
1143
+ const timing = {};
1144
+ let outcome = "none";
1145
+ const body = await this.#render_component(load, props, cache, (o) => outcome = o, timing, event.url, reads_page_data);
1146
+ record_hole_stats(event.request, {
1147
+ kind: "hole",
1148
+ id,
1149
+ cache: outcome,
1150
+ ttl,
1151
+ ...timing.queue_ms !== void 0 ? { queue_ms: Math.round(timing.queue_ms * 10) / 10 } : {},
1152
+ ...island_name?.[target] ? { name: island_name[target] } : {},
1153
+ p: hole_copy_key(payload)
1154
+ });
1155
+ const server_timing = timing.queue_ms !== void 0 && (import.meta.env.DEV || DEVTOOLS && event.cookies.get("og_devtools") === "on" || event.cookies.get("og_profiler_beacon") === "1") ? { "server-timing": `og-queue;dur=${timing.queue_ms.toFixed(1)}, og-render;dur=${(timing.render_ms ?? 0).toFixed(1)}` } : {};
1156
+ if (body === null) return region_response("Region render failed", { status: 500 });
1157
+ if (body === "<!--ogygia:keep-fallback-->") return region_response(null, {
1158
+ status: 204,
1159
+ headers: renewed ? {
1160
+ "cache-control": "no-store",
1161
+ ...renew_headers
1162
+ } : void 0
1163
+ });
1164
+ if (body.length > MAX_REGION_BODY) return region_denied("oversize");
1165
+ let html = absolutize_hole_html(region_css_links(target) + body, event.url);
1166
+ if (this.#transform) html = await this.#transform_region(html, event);
1167
+ if (method === "HEAD") return region_response(null, {
1168
+ status: 200,
1169
+ headers: {
1170
+ "content-type": "text/html; charset=utf-8",
1171
+ "content-length": String(new TextEncoder().encode(html).byteLength),
1172
+ "cache-control": cache_control,
1173
+ ...renew_headers
1174
+ }
1175
+ });
1176
+ return region_response(html, {
1177
+ status: 200,
1178
+ headers: {
1179
+ "content-type": "text/html; charset=utf-8",
1180
+ "cache-control": cache_control,
1181
+ ...renew_headers,
1182
+ ...server_timing
1183
+ }
1184
+ });
1185
+ }
1186
+ };
1187
+ function handle(options = {}) {
1188
+ const instance = new OgygiaHandle(options);
1189
+ return (args) => instance.handle(args);
1190
+ }
1191
+ export { document, handle, liftRegions, restoreRegions, scanRegions, ogygiaTransport as transport };