@getforma/core 0.6.1 → 0.8.1
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/README.md +93 -8
- package/dist/chunk-3U57L2TY.cjs +38 -0
- package/dist/chunk-3U57L2TY.cjs.map +1 -0
- package/dist/{chunk-TKGUHASG.js → chunk-N522P3G6.js} +20 -12
- package/dist/chunk-N522P3G6.js.map +1 -0
- package/dist/chunk-OZCHIVAZ.js +35 -0
- package/dist/chunk-OZCHIVAZ.js.map +1 -0
- package/dist/{chunk-YSKF3VRA.cjs → chunk-YMIMKO4W.cjs} +51 -20
- package/dist/chunk-YMIMKO4W.cjs.map +1 -0
- package/dist/forma-runtime-csp.js +1 -1
- package/dist/forma-runtime.js +1 -1
- package/dist/formajs-runtime-hardened.global.js +1 -1
- package/dist/formajs-runtime-hardened.global.js.map +1 -1
- package/dist/formajs-runtime.global.js +1 -1
- package/dist/formajs-runtime.global.js.map +1 -1
- package/dist/formajs.global.js +1 -1
- package/dist/formajs.global.js.map +1 -1
- package/dist/index.cjs +112 -115
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +30 -21
- package/dist/index.d.ts +30 -21
- package/dist/index.js +25 -50
- package/dist/index.js.map +1 -1
- package/dist/runtime-hardened.cjs +106 -27
- package/dist/runtime-hardened.cjs.map +1 -1
- package/dist/runtime-hardened.js +107 -28
- package/dist/runtime-hardened.js.map +1 -1
- package/dist/runtime.cjs +128 -50
- package/dist/runtime.cjs.map +1 -1
- package/dist/runtime.js +102 -24
- package/dist/runtime.js.map +1 -1
- package/dist/signal-B4_wQJHs.d.cts +53 -0
- package/dist/signal-B4_wQJHs.d.ts +53 -0
- package/dist/ssr/index.cjs +19 -2
- package/dist/ssr/index.cjs.map +1 -1
- package/dist/ssr/index.js +19 -2
- package/dist/ssr/index.js.map +1 -1
- package/dist/tc39-compat.cjs +4 -12
- package/dist/tc39-compat.cjs.map +1 -1
- package/dist/tc39-compat.d.cts +1 -1
- package/dist/tc39-compat.d.ts +1 -1
- package/dist/tc39-compat.js +3 -11
- package/dist/tc39-compat.js.map +1 -1
- package/package.json +2 -2
- package/dist/chunk-DPSAVBCP.js +0 -26
- package/dist/chunk-DPSAVBCP.js.map +0 -1
- package/dist/chunk-KH3F5NRU.cjs +0 -29
- package/dist/chunk-KH3F5NRU.cjs.map +0 -1
- package/dist/chunk-TKGUHASG.js.map +0 -1
- package/dist/chunk-YSKF3VRA.cjs.map +0 -1
- package/dist/signal-CfLDwMyg.d.cts +0 -29
- package/dist/signal-CfLDwMyg.d.ts +0 -29
package/dist/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/dom/text.ts","../src/dom/mount.ts","../src/dom/switch.ts","../src/dom/portal.ts","../src/dom/error-boundary.ts","../src/dom/suspense.ts","../src/dom/activate.ts","../src/component/define.ts","../src/component/context.ts","../src/state/store.ts","../src/state/history.ts","../src/state/persist.ts","../src/events/bus.ts","../src/events/delegate.ts","../src/events/keyboard.ts","../src/dom-utils/query.ts","../src/dom-utils/mutate.ts","../src/dom-utils/traverse.ts","../src/dom-utils/observe.ts","../src/storage/local.ts","../src/storage/session.ts","../src/storage/indexed.ts","../src/http/fetch.ts","../src/http/sse.ts","../src/http/ws.ts","../src/server/action.ts","../src/server/mutation.ts","../src/server/rpc-client.ts","../src/server/rpc-handler.ts","../src/wasm/forma-wasm.ts"],"names":["fragment","parent","children","registry","cleanup","setter","on"],"mappings":"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","file":"index.js","sourcesContent":["/**\n * Forma DOM - Text\n *\n * Creates static or reactive Text nodes.\n * Zero dependencies -- native browser APIs only.\n */\n\nimport { internalEffect } from 'forma/reactive';\n\n/**\n * Create a Text node that is either static or reactively bound.\n *\n * - If `value` is a string, creates a plain Text node.\n * - If `value` is a function (signal getter), creates a Text node and sets up\n * an effect that auto-updates `textContent` whenever the signal changes.\n *\n * @returns The Text node.\n */\nexport function createText(value: string | (() => string)): Text {\n if (typeof value === 'function') {\n // \"Track Limits\": new Text() bypasses Document factory dispatch\n const node = new Text('');\n internalEffect(() => {\n // \"DAS\": CharacterData.data is the rawest text setter\n node.data = value();\n });\n return node;\n }\n return new Text(value);\n}\n","/**\n * Forma DOM - Mount\n *\n * Mounts a component function into a DOM container, returning an unmount handle.\n * Uses createRoot() for automatic effect disposal — no global state.\n *\n * When the container has `data-forma-ssr`, uses hydrateIsland() for zero-flash\n * descriptor-based hydration instead of tearing down and rebuilding the DOM.\n */\n\nimport { createRoot } from 'forma/reactive';\nimport { hydrateIsland } from './hydrate.js';\n\n// ---------------------------------------------------------------------------\n// Public API\n// ---------------------------------------------------------------------------\n\n/**\n * Mount a component into a DOM container.\n *\n * All effects created during the component's render are tracked via\n * `createRoot()` and automatically disposed when unmount is called.\n *\n * When `data-forma-ssr` is present on the container, the component runs\n * inside `createRoot` in hydration mode — h() returns descriptors that are\n * walked against SSR DOM to attach handlers and reactive bindings.\n *\n * @param component A function returning an HTMLElement or DocumentFragment.\n * @param container An HTMLElement or a CSS selector string.\n * @returns An unmount function that removes the DOM and disposes all effects.\n *\n * ```ts\n * const unmount = mount(() => h('h1', null, 'Hello'), '#app');\n * // later…\n * unmount();\n * ```\n */\nexport function mount(\n component: () => HTMLElement | DocumentFragment,\n container: HTMLElement | string,\n): () => void {\n const target =\n typeof container === 'string'\n ? document.querySelector<HTMLElement>(container)\n : container;\n\n if (!target) {\n throw new Error(`mount: container not found — \"${container}\"`);\n }\n\n let disposeRoot!: () => void;\n\n if (target.hasAttribute('data-forma-ssr')) {\n // SSR content present — hydrate in-place using descriptor-based adoption.\n // The component MUST run inside createRoot so effects are tracked.\n createRoot((dispose) => {\n disposeRoot = dispose;\n hydrateIsland(component, target);\n });\n } else {\n // Normal mount — clear and append\n const dom = createRoot((dispose) => {\n disposeRoot = dispose;\n return component();\n });\n target.innerHTML = '';\n target.appendChild(dom);\n }\n\n // Return unmount function\n let unmounted = false;\n return () => {\n if (unmounted) return;\n unmounted = true;\n disposeRoot();\n target.innerHTML = '';\n };\n}\n","/**\n * Forma DOM - Switch (Multi-branch Conditional)\n *\n * Maps a reactive value to one of N render branches.\n * Caches previously rendered nodes for instant swap-back.\n *\n * Each cached branch gets its own reactive root (ownership scope) so that:\n * 1. Inner effects survive when the switch effect re-runs (alien-signals\n * would otherwise dispose child effects linked to the parent).\n * 2. Inner effects are explicitly disposed when the branch is evicted\n * from the cache or the switch itself is torn down.\n *\n * SolidJS equivalent: <Switch><Match when={}>\n */\n\nimport { internalEffect, untrack, createRoot } from 'forma/reactive';\n\ninterface SwitchCase<T> {\n match: T;\n render: () => Node;\n}\n\n/** Cached branch: the rendered DOM node + a dispose function for its root. */\ninterface CachedBranch {\n node: Node;\n dispose: () => void;\n}\n\n/**\n * Multi-branch conditional rendering with node caching.\n *\n * ```ts\n * const [tab, setTab] = createSignal('home');\n * const fragment = createSwitch(tab, [\n * { match: 'home', render: () => h('div', null, 'Home page') },\n * { match: 'about', render: () => h('div', null, 'About page') },\n * { match: 'contact', render: () => h('div', null, 'Contact page') },\n * ], () => h('div', null, '404'));\n * ```\n *\n * Previously rendered branches are cached — switching back to a tab\n * re-inserts the cached node without re-rendering.\n */\nexport function createSwitch<T>(\n value: () => T,\n cases: SwitchCase<T>[],\n fallback?: () => Node,\n): DocumentFragment {\n const startMarker = document.createComment('forma-switch');\n const endMarker = document.createComment('/forma-switch');\n const fragment = document.createDocumentFragment();\n fragment.appendChild(startMarker);\n fragment.appendChild(endMarker);\n\n // Branch cache: value → { node, dispose }\n // Each branch has its own reactive root for explicit lifecycle management.\n const cache = new Map<T, CachedBranch>();\n let currentNode: Node | null = null;\n let currentMatch: T | typeof UNSET = UNSET;\n\n const switchDispose = internalEffect(() => {\n const val = value();\n if (val === currentMatch) return; // Same branch, skip\n\n const DEBUG = typeof (globalThis as any).__FORMA_DEBUG__ !== 'undefined';\n if (DEBUG) console.log('[forma:switch] transition', String(currentMatch), '→', String(val));\n\n currentMatch = val;\n\n const parent = startMarker.parentNode;\n if (!parent) {\n if (DEBUG) console.warn('[forma:switch] markers not in DOM yet, skipping');\n return;\n }\n\n // Remove current content between markers.\n // If currentNode was a DocumentFragment, its children transferred to the\n // DOM on insertion and the fragment is now detached (parentNode === null).\n // We must scoop the children BACK into the fragment so the cache stays\n // valid for re-insertion later.\n if (currentNode) {\n if (currentNode.parentNode === parent) {\n if (DEBUG) console.log('[forma:switch] removing single node');\n parent.removeChild(currentNode);\n } else if (currentNode.nodeType === 11 /* DOCUMENT_FRAGMENT_NODE */) {\n // Scoop DOM nodes back into the fragment for cache reuse\n if (DEBUG) console.log('[forma:switch] scooping nodes back into fragment');\n let scooped = 0;\n while (startMarker.nextSibling && startMarker.nextSibling !== endMarker) {\n currentNode.appendChild(startMarker.nextSibling);\n scooped++;\n }\n if (DEBUG) console.log('[forma:switch] scooped', scooped, 'nodes back into fragment');\n } else {\n // Other detached node — just clear between markers\n if (DEBUG) console.log('[forma:switch] clearing detached node between markers');\n while (startMarker.nextSibling && startMarker.nextSibling !== endMarker) {\n parent.removeChild(startMarker.nextSibling);\n }\n }\n }\n\n // Find matching case\n const matchedCase = cases.find(c => c.match === val);\n if (matchedCase) {\n let entry = cache.get(val);\n if (!entry) {\n // Render inside a createRoot so child effects are tracked for\n // disposal, and inside untrack so they are NOT linked to the\n // switch effect (alien-signals disposes child effects on parent\n // re-run, which would kill reactivity in cached branches).\n let branchDispose!: () => void;\n const node = createRoot((dispose) => {\n branchDispose = dispose;\n return untrack(() => matchedCase.render());\n });\n entry = { node, dispose: branchDispose };\n cache.set(val, entry);\n if (DEBUG) console.log('[forma:switch] rendered new branch for', String(val), '→', node.nodeName, 'type', node.nodeType);\n } else {\n if (DEBUG) console.log('[forma:switch] reusing cached branch for', String(val), '→', entry.node.nodeName, 'type', entry.node.nodeType, 'childNodes', entry.node.childNodes?.length);\n }\n currentNode = entry.node;\n } else {\n // Fallback — not cached, effects are owned by the switch effect\n // and correctly torn down on next re-run.\n currentNode = fallback?.() ?? null;\n if (DEBUG) console.log('[forma:switch] no match, using fallback');\n }\n\n if (currentNode) {\n parent.insertBefore(currentNode, endMarker);\n if (DEBUG) console.log('[forma:switch] inserted', currentNode.nodeName, 'before end marker');\n }\n });\n\n // Attach a cleanup marker so external disposal (via disposeComponent or\n // parent root teardown) can clean up all cached branches.\n (fragment as any).__switchDispose = () => {\n switchDispose();\n for (const entry of cache.values()) {\n entry.dispose();\n }\n cache.clear();\n };\n\n return fragment;\n}\n\n// Sentinel value for \"no match yet\"\nconst UNSET = Symbol('unset');\n","/**\n * Forma DOM - Portal\n *\n * Renders children into a different DOM container than the parent.\n * Useful for modals, tooltips, dropdowns that need to escape overflow.\n *\n * SolidJS equivalent: <Portal mount={}>\n */\n\nimport { createEffect } from 'forma/reactive';\n\n/**\n * Render content into an external DOM container.\n *\n * ```ts\n * const modal = createPortal(\n * () => h('div', { class: 'modal' }, 'Modal content'),\n * document.body,\n * );\n * ```\n *\n * Returns a comment node placeholder. The actual content is rendered\n * into the target container. Cleanup removes content from target.\n */\nexport function createPortal(\n children: () => Node,\n target?: Element | string,\n): Comment {\n const placeholder = document.createComment('forma-portal');\n\n const resolvedTarget = typeof target === 'string'\n ? document.querySelector(target)\n : (target ?? document.body);\n\n if (!resolvedTarget) {\n throw new Error(`createPortal: target not found: ${target}`);\n }\n\n let mountedNode: Node | null = null;\n const removeMountedNode = () => {\n if (mountedNode && mountedNode.parentNode === resolvedTarget) {\n resolvedTarget.removeChild(mountedNode);\n }\n mountedNode = null;\n };\n\n createEffect(() => {\n const node = children();\n\n // Remove previous\n removeMountedNode();\n\n mountedNode = node;\n resolvedTarget.appendChild(node);\n\n // Ensure portal content is removed when the owner root disposes.\n return () => {\n removeMountedNode();\n };\n });\n\n return placeholder;\n}\n","/**\n * Forma DOM - Error Boundary\n *\n * Catches errors during rendering and shows a fallback UI.\n * Provides a retry function to re-attempt the original render.\n *\n * SolidJS equivalent: <ErrorBoundary fallback={}>\n */\n\nimport { createSignal, internalEffect } from 'forma/reactive';\n\n/**\n * Wrap a render function with error recovery.\n *\n * ```ts\n * const fragment = createErrorBoundary(\n * () => h('div', null, riskyComponent()),\n * (error, retry) => h('div', { class: 'error' },\n * h('p', null, `Error: ${error.message}`),\n * h('button', { onClick: retry }, 'Retry'),\n * ),\n * );\n * ```\n *\n * If `tryFn` throws, `catchFn` is called with the error and a retry function.\n * Calling `retry()` re-runs `tryFn`.\n */\nexport function createErrorBoundary(\n tryFn: () => Node,\n catchFn: (error: Error, retry: () => void) => Node,\n): DocumentFragment {\n const startMarker = document.createComment('forma-error-boundary');\n const endMarker = document.createComment('/forma-error-boundary');\n const fragment = document.createDocumentFragment();\n fragment.appendChild(startMarker);\n fragment.appendChild(endMarker);\n\n const [retryCount, setRetryCount] = createSignal(0);\n let currentNode: Node | null = null;\n\n internalEffect(() => {\n // Subscribe to retryCount so retry() triggers re-run\n retryCount();\n\n const parent = startMarker.parentNode;\n if (!parent) return;\n\n // Remove current\n if (currentNode && currentNode.parentNode === parent) {\n parent.removeChild(currentNode);\n }\n\n try {\n currentNode = tryFn();\n } catch (e) {\n const error = e instanceof Error ? e : new Error(String(e));\n const retry = () => setRetryCount(c => c + 1);\n currentNode = catchFn(error, retry);\n }\n\n if (currentNode) {\n parent.insertBefore(currentNode, endMarker);\n }\n });\n\n return fragment;\n}\n","/**\n * Forma DOM - Suspense\n *\n * A Suspense boundary that shows fallback content while async resources\n * inside the children function are loading. Uses comment markers\n * (like createShow, createList) for zero-wrapper rendering.\n *\n * When all resources resolve, the fallback is swapped for the real content.\n * If a resource errors, the fallback remains (pair with createErrorBoundary\n * for error handling).\n *\n * SolidJS equivalent: <Suspense fallback={}>\n */\n\nimport { createSignal, internalEffect } from 'forma/reactive';\nimport {\n type SuspenseContext,\n pushSuspenseContext,\n popSuspenseContext,\n} from 'forma/reactive/suspense-context';\n\n// Re-export context utilities so consumers can import from dom/suspense\nexport { getSuspenseContext, pushSuspenseContext, popSuspenseContext } from 'forma/reactive/suspense-context';\nexport type { SuspenseContext } from 'forma/reactive/suspense-context';\n\n// ---------------------------------------------------------------------------\n// createSuspense\n// ---------------------------------------------------------------------------\n\n/**\n * Create a Suspense boundary that shows fallback content while async resources\n * inside the children function are loading.\n *\n * Uses comment markers: `<!--forma-suspense-->` / `<!--/forma-suspense-->`\n *\n * When all resources resolve, the fallback is swapped for the real content.\n * If a resource errors, the fallback remains (pair with createErrorBoundary\n * for errors).\n *\n * ```ts\n * const frag = createSuspense(\n * () => h('div', null, 'Loading...'),\n * () => {\n * const data = createResource(source, fetcher);\n * return h('div', null, () => data()?.name ?? '');\n * },\n * );\n * container.appendChild(frag);\n * ```\n */\nexport function createSuspense(\n fallback: () => Node,\n children: () => Node,\n): DocumentFragment {\n const startMarker = document.createComment('forma-suspense');\n const endMarker = document.createComment('/forma-suspense');\n const fragment = document.createDocumentFragment();\n fragment.appendChild(startMarker);\n fragment.appendChild(endMarker);\n\n const [pending, setPending] = createSignal(0);\n let currentNode: Node | null = null;\n let resolvedNode: Node | null = null;\n let fallbackNode: Node | null = null;\n\n const ctx: SuspenseContext = {\n increment() { setPending(p => p + 1); },\n decrement() { setPending(p => Math.max(0, p - 1)); },\n };\n\n // Render children within the Suspense context so that any createResource\n // calls inside will register with this boundary.\n pushSuspenseContext(ctx);\n try {\n resolvedNode = children();\n } finally {\n popSuspenseContext();\n }\n\n // Reactively swap between fallback and children based on pending count\n internalEffect(() => {\n const parent = startMarker.parentNode;\n if (!parent) return;\n\n const isPending = pending() > 0;\n const newNode = isPending ? (fallbackNode ??= fallback()) : resolvedNode;\n\n if (newNode === currentNode) return;\n\n // Remove current node\n if (currentNode && currentNode.parentNode === parent) {\n parent.removeChild(currentNode);\n }\n\n // Insert new node\n if (newNode) {\n parent.insertBefore(newNode, endMarker);\n }\n\n currentNode = newNode;\n });\n\n return fragment;\n}\n","/**\n * Forma DOM - Island Activation\n *\n * Discovers SSR-rendered islands via [data-forma-island] attributes,\n * loads props (inline or script_tag), and hydrates each island inside\n * an independent createRoot scope with try/catch error isolation.\n */\n\nimport { createRoot, __DEV__ } from 'forma/reactive';\nimport { hydrateIsland } from './hydrate.js';\n\n/**\n * Function that hydrates an island.\n *\n * @param el The root element of the island (`[data-forma-island]`).\n * Useful for layout measurement, focus management, CSS class\n * toggling, third-party library init, or reading extra `data-*`\n * attributes from the server-rendered shell.\n * @param props Parsed props from `data-forma-props` (inline or script block),\n * or `null` if no props were provided.\n * @returns A component tree (from `h()` calls) for descriptor-based\n * hydration, or `undefined` for imperative islands that set up\n * their own effects.\n */\nexport type IslandHydrateFn = (el: HTMLElement, props: Record<string, unknown> | null) => unknown;\n\n/**\n * Load props for an island from either inline attribute or shared script block.\n */\nfunction loadIslandProps(\n root: HTMLElement,\n id: number,\n sharedProps: Record<string, unknown> | null,\n): Record<string, unknown> | null {\n // Mode 1: Inline (small props, < 1KB)\n const inline = root.getAttribute('data-forma-props');\n if (inline) {\n return JSON.parse(inline);\n }\n\n // Mode 2: Script tag (1KB–50KB, pre-parsed)\n if (sharedProps && String(id) in sharedProps) {\n return (sharedProps as any)[String(id)] as Record<string, unknown>;\n }\n\n // No props — island creates its own state\n return null;\n}\n\n/**\n * Discover and activate all SSR-rendered islands on the page.\n *\n * Each island is activated inside its own createRoot scope with try/catch\n * isolation — a broken island never takes down its siblings.\n *\n * @param registry Map of component names to hydration functions.\n */\nexport function activateIslands(registry: Record<string, IslandHydrateFn>): void {\n // Parse shared props once before the loop\n const scriptBlock = document.getElementById('__forma_islands');\n const sharedProps: Record<string, unknown> | null =\n scriptBlock ? JSON.parse(scriptBlock.textContent!) : null;\n\n const islands = document.querySelectorAll<HTMLElement>('[data-forma-island]');\n\n for (const root of islands) {\n const id = parseInt(root.getAttribute('data-forma-island')!, 10);\n const componentName = root.getAttribute('data-forma-component')!;\n const hydrateFn = registry[componentName];\n\n if (!hydrateFn) {\n if (__DEV__) console.warn(`[forma] No hydrate function for island \"${componentName}\" (id=${id})`);\n root.setAttribute('data-forma-status', 'error');\n continue;\n }\n\n const trigger = root.getAttribute('data-forma-hydrate') || 'load';\n\n if (trigger === 'visible') {\n // Defer hydration until island enters the viewport\n const observer = new IntersectionObserver(\n (entries) => {\n for (const entry of entries) {\n if (!entry.isIntersecting) continue;\n observer.disconnect();\n hydrateIslandRoot(root, id, componentName, hydrateFn, sharedProps);\n }\n },\n { rootMargin: '200px' },\n );\n observer.observe(root);\n } else if (trigger === 'idle') {\n const hydrate = () => hydrateIslandRoot(root, id, componentName, hydrateFn, sharedProps);\n if (typeof requestIdleCallback === 'function') {\n requestIdleCallback(hydrate);\n } else {\n setTimeout(hydrate, 200);\n }\n } else if (trigger === 'interaction') {\n const hydrate = () => {\n root.removeEventListener('pointerdown', hydrate, true);\n root.removeEventListener('focusin', hydrate, true);\n hydrateIslandRoot(root, id, componentName, hydrateFn, sharedProps);\n };\n root.addEventListener('pointerdown', hydrate, { capture: true, once: true });\n root.addEventListener('focusin', hydrate, { capture: true, once: true });\n } else {\n // load (default) — hydrate immediately\n hydrateIslandRoot(root, id, componentName, hydrateFn, sharedProps);\n }\n }\n}\n\n/**\n * Dispose a single island, tearing down its reactive root and all effects.\n *\n * Safe to call multiple times (idempotent). Sets `data-forma-status` to\n * `\"disposed\"` so the island can be distinguished from active/error states.\n */\nexport function deactivateIsland(el: HTMLElement): void {\n const dispose = (el as any).__formaDispose;\n if (typeof dispose === 'function') {\n dispose();\n delete (el as any).__formaDispose;\n el.setAttribute('data-forma-status', 'disposed');\n }\n}\n\n/**\n * Dispose ALL active islands under a root element (or the whole document).\n *\n * Use this when swapping module content — e.g., replacing the contents of\n * a `<forma-stage>` Shadow DOM during AI generation. Prevents leaked effects\n * and event listeners from accumulating across swaps.\n */\nexport function deactivateAllIslands(root: Element | Document = document): void {\n const islands = root.querySelectorAll<HTMLElement>('[data-forma-status=\"active\"]');\n for (const island of islands) {\n deactivateIsland(island);\n }\n}\n\n/** Hydrate a single island root with error isolation. */\nfunction hydrateIslandRoot(\n root: HTMLElement,\n id: number,\n componentName: string,\n hydrateFn: IslandHydrateFn,\n sharedProps: Record<string, unknown> | null,\n): void {\n try {\n const props = loadIslandProps(root, id, sharedProps);\n root.setAttribute('data-forma-status', 'hydrating');\n\n // hydrateIsland may replace the shell element with the component's own\n // root element (CSR fallback for empty islands). Track the active root.\n let activeRoot: Element = root;\n createRoot((dispose) => {\n activeRoot = hydrateIsland(() => hydrateFn(root, props), root);\n (activeRoot as any).__formaDispose = dispose;\n });\n\n activeRoot.setAttribute('data-forma-status', 'active');\n } catch (err) {\n if (__DEV__) console.error(`[forma] Island \"${componentName}\" (id=${id}) failed:`, err);\n root.setAttribute('data-forma-status', 'error');\n }\n}\n","/**\n * Forma Component - Define\n *\n * Component definition system where the setup function runs ONCE.\n * Reactivity comes from signals, not re-rendering.\n * Backed by alien-signals via forma/reactive.\n */\n\nimport { reportError } from '../reactive/dev.js';\n\n// ---------------------------------------------------------------------------\n// Types\n// ---------------------------------------------------------------------------\n\ntype CleanupFn = () => void;\ntype SetupFn = () => HTMLElement | DocumentFragment;\n\ninterface ComponentDef {\n setup: SetupFn;\n name?: string;\n}\n\n// ---------------------------------------------------------------------------\n// Lifecycle context stack\n// ---------------------------------------------------------------------------\n\ninterface LifecycleContext {\n /** Dispose functions for all effects created during setup. */\n disposers: (() => void)[];\n /** Callbacks registered via onMount(). */\n mountCallbacks: (() => void | CleanupFn)[];\n /** Callbacks registered via onUnmount(). */\n unmountCallbacks: (() => void)[];\n}\n\nlet currentLifecycleContext: LifecycleContext | null = null;\nconst lifecycleStack: (LifecycleContext | null)[] = [];\n\nfunction pushLifecycleContext(ctx: LifecycleContext): void {\n lifecycleStack.push(currentLifecycleContext);\n currentLifecycleContext = ctx;\n}\n\nfunction popLifecycleContext(): void {\n currentLifecycleContext = lifecycleStack.pop() ?? null;\n}\n\n// ---------------------------------------------------------------------------\n// Public API - Lifecycle hooks\n// ---------------------------------------------------------------------------\n\n/**\n * Register a callback that runs after the component's setup completes.\n * If the callback returns a function, that function is called on unmount.\n * Must be called inside a setup function.\n */\nexport function onMount(fn: () => void | CleanupFn): void {\n if (currentLifecycleContext === null) {\n throw new Error('onMount() must be called inside a component setup function');\n }\n currentLifecycleContext.mountCallbacks.push(fn);\n}\n\n/**\n * Register a callback that runs when the component is disposed.\n * Must be called inside a setup function.\n */\nexport function onUnmount(fn: () => void): void {\n if (currentLifecycleContext === null) {\n throw new Error('onUnmount() must be called inside a component setup function');\n }\n currentLifecycleContext.unmountCallbacks.push(fn);\n}\n\n// ---------------------------------------------------------------------------\n// Internal: symbol for attaching dispose to DOM nodes\n// ---------------------------------------------------------------------------\n\nconst DISPOSE_KEY = Symbol('forma:component:dispose');\n\ninterface DisposableNode {\n [DISPOSE_KEY]?: () => void;\n}\n\n// ---------------------------------------------------------------------------\n// Public API - defineComponent\n// ---------------------------------------------------------------------------\n\n/**\n * Define a component from a setup function or definition object.\n * Returns a factory function that, when called, produces a DOM element\n * with attached lifecycle and disposal logic.\n *\n * The setup function runs ONCE per factory call. Reactivity is driven\n * by signals, not by re-running setup.\n */\nexport function defineComponent(\n setupOrDef: SetupFn | ComponentDef,\n): () => HTMLElement | DocumentFragment {\n const setup: SetupFn =\n typeof setupOrDef === 'function' ? setupOrDef : setupOrDef.setup;\n const name: string | undefined =\n typeof setupOrDef === 'function' ? undefined : setupOrDef.name;\n\n return function componentFactory(): HTMLElement | DocumentFragment {\n // Create a fresh lifecycle context for this component instance\n const ctx: LifecycleContext = {\n disposers: [],\n mountCallbacks: [],\n unmountCallbacks: [],\n };\n\n // Push lifecycle context so onMount/onUnmount calls register here\n pushLifecycleContext(ctx);\n\n let dom: HTMLElement | DocumentFragment;\n try {\n dom = setup();\n } finally {\n popLifecycleContext();\n }\n\n // Build the dispose function that tears down the entire component\n const dispose = (): void => {\n // Run onUnmount callbacks\n for (const cb of ctx.unmountCallbacks) {\n try {\n cb();\n } catch (e) {\n reportError(e, 'onUnmount');\n }\n }\n\n // Dispose all effects\n for (const d of ctx.disposers) {\n try {\n d();\n } catch (e) {\n reportError(e, 'component disposer');\n }\n }\n\n // Clean up\n ctx.disposers.length = 0;\n ctx.mountCallbacks.length = 0;\n ctx.unmountCallbacks.length = 0;\n };\n\n // Attach dispose to the DOM node so callers can tear it down\n (dom as unknown as DisposableNode)[DISPOSE_KEY] = dispose;\n\n // Run mount callbacks (synchronously, after setup completes)\n // If a mount callback returns a cleanup, register it as an unmount callback\n for (const cb of ctx.mountCallbacks) {\n try {\n const cleanup = cb();\n if (typeof cleanup === 'function') {\n ctx.unmountCallbacks.push(cleanup);\n }\n } catch (e) {\n reportError(e, 'onMount');\n }\n }\n\n return dom;\n };\n}\n\n/**\n * Dispose a component that was created via defineComponent.\n * This runs all onUnmount callbacks and disposes all tracked effects.\n */\nexport function disposeComponent(dom: HTMLElement | DocumentFragment): void {\n const disposable = dom as unknown as DisposableNode;\n if (typeof disposable[DISPOSE_KEY] === 'function') {\n disposable[DISPOSE_KEY]();\n delete disposable[DISPOSE_KEY];\n }\n}\n\n/**\n * Track an effect disposal within the current component's lifecycle.\n * Call this inside a setup function to ensure effects are cleaned up\n * when the component is disposed.\n */\nexport function trackDisposer(dispose: () => void): void {\n if (currentLifecycleContext !== null) {\n currentLifecycleContext.disposers.push(dispose);\n }\n}\n","/**\n * Forma Component - Context\n *\n * Dependency injection via stack-based context.\n * Simpler than React's Provider component tree: provide() pushes a value,\n * inject() reads the top, component teardown pops automatically.\n * Zero dependencies -- native browser APIs only.\n */\n\n// ---------------------------------------------------------------------------\n// Types\n// ---------------------------------------------------------------------------\n\nexport interface Context<T> {\n /** Unique identifier for this context. */\n readonly id: symbol;\n /** Value returned when no provider is active. */\n readonly defaultValue: T;\n}\n\n// ---------------------------------------------------------------------------\n// Internal storage\n// ---------------------------------------------------------------------------\n\n/**\n * Per-context value stacks.\n * Each context id maps to a stack of provided values.\n * The top of the stack is the \"current\" value.\n */\nconst contextStacks = new Map<symbol, unknown[]>();\n\n// ---------------------------------------------------------------------------\n// Public API\n// ---------------------------------------------------------------------------\n\n/**\n * Create a new context with a default value.\n *\n * ```ts\n * const ThemeCtx = createContext('light');\n * ```\n */\nexport function createContext<T>(defaultValue: T): Context<T> {\n return {\n id: Symbol('forma:context'),\n defaultValue,\n };\n}\n\n/**\n * Provide a value for a context.\n * The value is pushed onto the context's stack and will be returned by\n * inject() until it is removed via unprovide() or overridden by a nested provide().\n *\n * ```ts\n * provide(ThemeCtx, 'dark');\n * ```\n */\nexport function provide<T>(ctx: Context<T>, value: T): void {\n let stack = contextStacks.get(ctx.id);\n if (stack === undefined) {\n stack = [];\n contextStacks.set(ctx.id, stack);\n }\n stack.push(value);\n}\n\n/**\n * Read the current value of a context.\n * Returns the most recently provided value, or the default if none was provided.\n *\n * ```ts\n * const theme = inject(ThemeCtx); // 'dark' if provided, else 'light'\n * ```\n */\nexport function inject<T>(ctx: Context<T>): T {\n const stack = contextStacks.get(ctx.id);\n if (stack === undefined || stack.length === 0) {\n return ctx.defaultValue;\n }\n return stack[stack.length - 1] as T;\n}\n\n/**\n * Remove the most recent provided value for a context.\n * Used during component teardown to restore the previous scope.\n *\n * ```ts\n * unprovide(ThemeCtx);\n * ```\n */\nexport function unprovide<T>(ctx: Context<T>): void {\n const stack = contextStacks.get(ctx.id);\n if (stack !== undefined && stack.length > 0) {\n stack.pop();\n // Clean up empty stacks to avoid memory leaks\n if (stack.length === 0) {\n contextStacks.delete(ctx.id);\n }\n }\n}\n","/**\n * Forma State - Store\n *\n * Deep reactive store with path-based signal granularity.\n * Every property path (e.g. `user.name`, `items.0.done`) gets its own signal,\n * so only effects that read a specific path are notified when it changes.\n *\n * Inspired by SolidJS's createStore and Vue's reactive(), with:\n * - Lazy proxy wrapping (child objects proxied on first access)\n * - Structural sharing (replacing an object invalidates child signals)\n * - Array mutation batching (push/pop/splice/sort etc. batch their signals)\n *\n * Backed by alien-signals via forma/reactive.\n */\n\nimport { createSignal, batch, untrack } from 'forma/reactive';\n\n// ---------------------------------------------------------------------------\n// Types\n// ---------------------------------------------------------------------------\n\ntype SignalPair = [get: () => unknown, set: (v: unknown) => void];\n\ntype StoreSetter<T extends object> = (\n partial: Partial<T> | ((prev: T) => Partial<T>),\n) => void;\n\n// ---------------------------------------------------------------------------\n// Symbols\n// ---------------------------------------------------------------------------\n\n/** Access the underlying raw (unproxied) object from a store proxy. */\nconst RAW = Symbol('forma-raw');\n\n/** Marker: true on every store proxy so we can detect them. */\nconst PROXY = Symbol('forma-proxy');\n\n// ---------------------------------------------------------------------------\n// Helpers\n// ---------------------------------------------------------------------------\n\nconst ARRAY_MUTATORS = new Set([\n 'push',\n 'pop',\n 'shift',\n 'unshift',\n 'splice',\n 'sort',\n 'reverse',\n 'fill',\n 'copyWithin',\n]);\n\nfunction isPlainObject(v: unknown): v is Record<string, unknown> {\n if (v == null || typeof v !== 'object') return false;\n const proto = Object.getPrototypeOf(v);\n return proto === Object.prototype || proto === null || Array.isArray(v);\n}\n\nfunction shouldWrap(v: unknown): v is object {\n if (v == null || typeof v !== 'object') return false;\n // Don't wrap special built-ins (Date, RegExp, Map, Set, etc.)\n if (v instanceof Date || v instanceof RegExp || v instanceof Map ||\n v instanceof Set || v instanceof WeakMap || v instanceof WeakSet ||\n v instanceof Error || v instanceof Promise) {\n return false;\n }\n // Already a store proxy — no double wrapping\n if ((v as any)[PROXY]) return false;\n return true;\n}\n\n// ---------------------------------------------------------------------------\n// Deep-clone helper (used for functional setter snapshots)\n// ---------------------------------------------------------------------------\n\nfunction deepClone<T>(obj: T): T {\n if (obj == null || typeof obj !== 'object') return obj;\n if (Array.isArray(obj)) return obj.map(deepClone) as unknown as T;\n if (obj instanceof Date) return new Date(obj.getTime()) as unknown as T;\n const out: Record<string, unknown> = {};\n for (const key of Object.keys(obj as object)) {\n out[key] = deepClone((obj as Record<string, unknown>)[key]);\n }\n return out as T;\n}\n\n// ---------------------------------------------------------------------------\n// Public API\n// ---------------------------------------------------------------------------\n\n/**\n * Create a deep reactive store.\n *\n * Returns a tuple of `[getter proxy, setter function]`.\n * The getter proxy tracks reads at every property path via dedicated signals.\n * Setting a property (either via `setState()` or direct mutation like\n * `state.user.name = 'Bob'`) only notifies effects that actually read that\n * specific path.\n *\n * ```ts\n * const [state, setState] = createStore({\n * count: 0,\n * user: { name: 'Alice', age: 30 },\n * items: [{ text: 'Buy milk', done: false }],\n * });\n *\n * // Fine-grained reads\n * state.user.name; // tracked at path \"user.name\"\n * state.items[0].done; // tracked at path \"items.0.done\"\n *\n * // Setter API (batched)\n * setState({ count: 1 });\n * setState(prev => ({ count: prev.count + 1 }));\n *\n * // Direct mutation (via Proxy set trap)\n * state.user.name = 'Bob'; // only \"user.name\" subscribers notified\n * state.items[0].done = true;\n *\n * // Array mutations\n * state.items.push({ text: 'Walk dog', done: false });\n * ```\n */\nexport function createStore<T extends object>(\n initial: T,\n): [get: T, set: StoreSetter<T>] {\n // -------------------------------------------------------------------------\n // Signal-per-path map\n // -------------------------------------------------------------------------\n\n /** Map of dot-separated paths -> signal pairs. */\n const signals = new Map<string, SignalPair>();\n\n /** Parent path -> set of direct child paths for O(1) child invalidation. */\n const children = new Map<string, Set<string>>();\n\n /**\n * Register a signal path with its parent in the adjacency map.\n * This allows walking the tree instead of scanning all signals.\n */\n function registerChild(path: string): void {\n const lastDot = path.lastIndexOf('.');\n if (lastDot === -1) return; // root-level, no parent\n const parentPath = path.substring(0, lastDot);\n let set = children.get(parentPath);\n if (!set) { set = new Set(); children.set(parentPath, set); }\n set.add(path);\n }\n\n /**\n * Get or create the signal for a given path.\n * When creating, seeds with `initialValue`.\n */\n function getSignal(path: string, initialValue?: unknown): SignalPair {\n let pair = signals.get(path);\n if (!pair) {\n pair = createSignal<unknown>(initialValue) as SignalPair;\n signals.set(path, pair);\n registerChild(path);\n }\n return pair;\n }\n\n // -------------------------------------------------------------------------\n // Proxy cache (raw object -> proxy)\n // -------------------------------------------------------------------------\n\n /**\n * WeakMap so proxies for child objects are reused as long as the raw object\n * is alive. When an object is replaced, the old entry is GC'd naturally.\n */\n const proxyCache = new WeakMap<object, object>();\n\n // -------------------------------------------------------------------------\n // Invalidation\n // -------------------------------------------------------------------------\n\n /**\n * Recursively delete all child signals using the adjacency map.\n * Called when an entire sub-tree is replaced so stale signals are not reused.\n * O(k) where k = number of descendant signals, instead of O(n) over all signals.\n */\n function invalidateChildren(parentPath: string): void {\n const childSet = children.get(parentPath);\n if (!childSet) return;\n for (const childPath of childSet) {\n // Recursively invalidate grandchildren first\n invalidateChildren(childPath);\n // Remove the signal itself\n signals.delete(childPath);\n // Clean up this child's entry in the adjacency map\n children.delete(childPath);\n }\n // Clear the parent's children set (all children have been removed)\n childSet.clear();\n }\n\n // -------------------------------------------------------------------------\n // Proxy factory (lazy, recursive)\n // -------------------------------------------------------------------------\n\n function wrap(raw: object, basePath: string): object {\n // Primitives / non-wrappable values pass through\n if (!shouldWrap(raw)) return raw;\n\n // Return cached proxy if we already have one for this raw object\n const cached = proxyCache.get(raw);\n if (cached) return cached;\n\n const isArr = Array.isArray(raw);\n // Pre-compute the path prefix to avoid repeated string concatenation in hot paths\n const basePrefix = basePath ? basePath + '.' : '';\n\n // Inline cache: skip Map lookup when the same key is accessed repeatedly\n // (very common in render loops and effects that read the same property)\n let lastKey: string = '';\n let lastSignal: SignalPair | undefined;\n\n const proxy: object = new Proxy(raw, {\n // -------------------------------------------------------------------\n // GET\n // -------------------------------------------------------------------\n get(target: any, prop: PropertyKey, receiver: unknown): unknown {\n // Escape hatches\n if (prop === RAW) return target;\n if (prop === PROXY) return true;\n\n // Symbols pass through (Symbol.iterator, Symbol.toPrimitive, etc.)\n if (typeof prop === 'symbol') {\n return Reflect.get(target, prop, receiver);\n }\n\n const key = String(prop);\n // Cache-friendly path construction: avoid template literals in hot path\n const childPath = basePrefix + key;\n\n // ------------------------------------------------------------------\n // Array mutator methods — wrap to batch signal updates\n // ------------------------------------------------------------------\n if (isArr && ARRAY_MUTATORS.has(key)) {\n return (...args: unknown[]) => {\n let result: unknown;\n batch(() => {\n // Unwrap proxy arguments (e.g. pushing a store proxy)\n const rawArgs = args.map((a) =>\n a != null && typeof a === 'object' && (a as any)[RAW]\n ? (a as any)[RAW]\n : a,\n );\n result = (target as any)[key].apply(target, rawArgs);\n\n // Invalidate all child paths so they recreate from the\n // mutated raw array on next access.\n invalidateChildren(basePath);\n\n // Notify the length signal\n const [, setLen] = getSignal(\n basePrefix + 'length',\n (target as unknown[]).length,\n );\n setLen((target as unknown[]).length);\n });\n return result;\n };\n }\n\n // ------------------------------------------------------------------\n // Array `length` — special-case so it's always tracked\n // ------------------------------------------------------------------\n if (isArr && key === 'length') {\n const [getter] = getSignal(childPath, target.length);\n getter(); // subscribe\n return target.length;\n }\n\n // ------------------------------------------------------------------\n // Regular property access\n // ------------------------------------------------------------------\n const value = Reflect.get(target, prop);\n\n // Inline cache: if same key as last access, skip Map lookup\n let pair: SignalPair;\n if (key === lastKey && lastSignal) {\n pair = lastSignal;\n } else {\n pair = getSignal(childPath, value);\n lastKey = key;\n lastSignal = pair;\n }\n\n pair[0](); // subscribe to this path\n\n // Lazily wrap child objects/arrays\n if (shouldWrap(value)) {\n return wrap(value, childPath);\n }\n\n return value;\n },\n\n // -------------------------------------------------------------------\n // SET\n // -------------------------------------------------------------------\n set(target: any, prop: PropertyKey, value: unknown): boolean {\n if (typeof prop === 'symbol') {\n return Reflect.set(target, prop, value);\n }\n\n const key = String(prop);\n const childPath = basePrefix + key;\n\n // Unwrap if the value being set is itself a proxy\n const rawValue =\n value != null && typeof value === 'object' && (value as any)[RAW]\n ? (value as any)[RAW]\n : value;\n\n // Write to the underlying object\n Reflect.set(target, prop, rawValue);\n\n // If we're replacing with an object, invalidate all child signals\n // and evict the old proxy so sub-paths are recreated on next access.\n if (rawValue != null && typeof rawValue === 'object') {\n invalidateChildren(childPath);\n // Remove cached proxy for the old value so a fresh one is created\n // on the next access.\n }\n\n // Update the length signal when setting indexed array elements\n if (isArr && key !== 'length') {\n const lengthPath = basePrefix + 'length';\n const lenPair = signals.get(lengthPath);\n if (lenPair) {\n lenPair[1](target.length);\n }\n }\n\n // Notify (or create) the signal for this path\n const [, setter] = getSignal(childPath, rawValue);\n setter(rawValue);\n\n return true;\n },\n\n // -------------------------------------------------------------------\n // HAS — track membership checks\n // -------------------------------------------------------------------\n has(target: any, prop: PropertyKey): boolean {\n if (typeof prop === 'symbol') {\n return Reflect.has(target, prop);\n }\n const key = String(prop);\n const childPath = basePrefix + key;\n // Subscribe so that `'x' in state` is tracked\n const [getter] = getSignal(childPath, Reflect.get(target, prop));\n getter();\n return Reflect.has(target, prop);\n },\n\n // -------------------------------------------------------------------\n // OWNKEYS — return keys from the raw target\n // -------------------------------------------------------------------\n ownKeys(target: any): (string | symbol)[] {\n return Reflect.ownKeys(target);\n },\n\n // -------------------------------------------------------------------\n // GETOWNPROPERTYDESCRIPTOR — needed for Object.keys / spread / ...\n // -------------------------------------------------------------------\n getOwnPropertyDescriptor(target: any, prop: PropertyKey) {\n return Object.getOwnPropertyDescriptor(target, prop);\n },\n\n // -------------------------------------------------------------------\n // DELETEPROPERTY — clean up signals when a key is removed\n // -------------------------------------------------------------------\n deleteProperty(target: any, prop: PropertyKey): boolean {\n if (typeof prop === 'symbol') {\n return Reflect.deleteProperty(target, prop);\n }\n\n const key = String(prop);\n const childPath = basePrefix + key;\n\n const result = Reflect.deleteProperty(target, prop);\n\n // Clean up the signal for this path and all children via adjacency map\n invalidateChildren(childPath);\n signals.delete(childPath);\n\n // Remove from parent's children set in the adjacency map\n const parentPath = basePath;\n if (parentPath !== undefined) {\n const parentSet = children.get(parentPath);\n if (parentSet) {\n parentSet.delete(childPath);\n if (parentSet.size === 0) children.delete(parentPath);\n }\n }\n // Clean up the deleted path's own children entry\n children.delete(childPath);\n\n return result;\n },\n });\n\n proxyCache.set(raw, proxy);\n return proxy;\n }\n\n // -------------------------------------------------------------------------\n // Root proxy\n // -------------------------------------------------------------------------\n\n const rootProxy = wrap(initial, '') as T;\n\n // -------------------------------------------------------------------------\n // Snapshot (for functional setter)\n // -------------------------------------------------------------------------\n\n /**\n * Produce a plain-object snapshot of the store's current state.\n * Reads are untracked so calling `setState(prev => ...)` inside an effect\n * does not create additional subscriptions.\n */\n function getCurrentSnapshot(): T {\n return untrack(() => deepClone(initial));\n }\n\n // -------------------------------------------------------------------------\n // Setter\n // -------------------------------------------------------------------------\n\n const setter: StoreSetter<T> = (\n partial: Partial<T> | ((prev: T) => Partial<T>),\n ) => {\n // Resolve functional updates by snapshotting current state\n const updates: Partial<T> =\n typeof partial === 'function' ? partial(getCurrentSnapshot()) : partial;\n\n // Batch all top-level key writes so effects run only once\n batch(() => {\n for (const key of Object.keys(updates) as (keyof T & string)[]) {\n (rootProxy as Record<string, unknown>)[key] = (updates as Record<string, unknown>)[key];\n }\n });\n };\n\n return [rootProxy, setter];\n}\n","/**\n * Forma State - History\n *\n * Undo/redo for any signal. Tracks changes and maintains undo/redo stacks\n * with reactive canUndo/canRedo signals.\n * Zero dependencies -- native browser APIs only.\n */\n\nimport { createSignal, internalEffect, batch } from 'forma/reactive';\n\n// ---------------------------------------------------------------------------\n// Types\n// ---------------------------------------------------------------------------\n\nexport interface HistoryControls<T> {\n /** Undo the last change, restoring the previous value. */\n undo: () => void;\n /** Redo the last undone change. */\n redo: () => void;\n /** Reactive getter: true if undo is available. */\n canUndo: () => boolean;\n /** Reactive getter: true if redo is available. */\n canRedo: () => boolean;\n /** Reactive getter: the full history stack (past + current + future). */\n history: () => T[];\n /** Reactive getter: current position in the history stack (0-based). */\n cursor: () => number;\n /** Clear all history, keeping only the current value. */\n clear: () => void;\n}\n\n// ---------------------------------------------------------------------------\n// Public API\n// ---------------------------------------------------------------------------\n\n/**\n * Create undo/redo history tracking for a signal.\n *\n * ```ts\n * const [count, setCount] = createSignal(0);\n * const h = createHistory([count, setCount], { maxLength: 50 });\n *\n * setCount(1);\n * setCount(2);\n * h.undo(); // count() === 1\n * h.redo(); // count() === 2\n * h.canUndo(); // true (reactive)\n * ```\n */\nexport function createHistory<T>(\n source: [get: () => T, set: (v: T) => void],\n options?: { maxLength?: number },\n): HistoryControls<T> {\n const [sourceGet, sourceSet] = source;\n const maxLength = options?.maxLength ?? 100;\n\n // ---------- Internal mutable state (not signals) ----------\n // We use plain arrays/numbers to avoid creating signal dependencies\n // inside the source-tracking effect, which would cause re-entrance issues.\n let _stack: T[] = [sourceGet()];\n let _cursor = 0;\n\n // ---------- Reactive output signals ----------\n // These are signals that external consumers can subscribe to.\n // We update them explicitly after every mutation.\n const [stackSignal, setStackSignal] = createSignal<T[]>([..._stack]);\n const [cursorSignal, setCursorSignal] = createSignal(_cursor);\n // Separate signal for stack length so canRedo only depends on numeric\n // signals and doesn't re-fire when array reference changes but length stays.\n const [stackLenSignal, setStackLenSignal] = createSignal(_stack.length);\n\n /** Sync the reactive output signals with internal mutable state. */\n function syncSignals(): void {\n batch(() => {\n setStackSignal([..._stack]);\n setCursorSignal(_cursor);\n setStackLenSignal(_stack.length);\n });\n }\n\n // Track whether the next source change should be ignored\n // (because it was caused by undo/redo, not an external set).\n let ignoreNext = false;\n let isFirstRun = true;\n\n // Watch the source signal for external changes\n internalEffect(() => {\n const value = sourceGet();\n\n // Skip the initial effect run -- the initial value is already in the stack\n if (isFirstRun) {\n isFirstRun = false;\n return;\n }\n\n if (ignoreNext) {\n ignoreNext = false;\n return;\n }\n\n // New value from an external set: push onto history\n // Discard any \"future\" entries after the current cursor (redo is cleared)\n _stack = _stack.slice(0, _cursor + 1);\n _stack.push(value);\n\n // Enforce maxLength\n if (_stack.length > maxLength) {\n _stack.splice(0, _stack.length - maxLength);\n }\n\n _cursor = _stack.length - 1;\n syncSignals();\n });\n\n // Reactive derived getters\n const canUndo = (): boolean => cursorSignal() > 0;\n const canRedo = (): boolean => cursorSignal() < stackLenSignal() - 1;\n\n const undo = (): void => {\n if (_cursor <= 0) return;\n\n _cursor--;\n ignoreNext = true;\n sourceSet(_stack[_cursor] as T);\n syncSignals();\n };\n\n const redo = (): void => {\n if (_cursor >= _stack.length - 1) return;\n\n _cursor++;\n ignoreNext = true;\n sourceSet(_stack[_cursor] as T);\n syncSignals();\n };\n\n const clear = (): void => {\n const currentValue = sourceGet();\n _stack = [currentValue];\n _cursor = 0;\n syncSignals();\n };\n\n return {\n undo,\n redo,\n canUndo,\n canRedo,\n history: () => stackSignal(),\n cursor: () => cursorSignal(),\n clear,\n };\n}\n","/**\n * Forma State - Persist\n *\n * Auto-persist a signal to localStorage (or any Storage-compatible backend).\n * Reads stored value on creation; writes on every signal change.\n * Zero dependencies -- native browser APIs only.\n */\n\nimport { internalEffect } from 'forma/reactive';\n\n// ---------------------------------------------------------------------------\n// Types\n// ---------------------------------------------------------------------------\n\ninterface PersistOptions<T> {\n /** Storage backend. Defaults to localStorage. */\n storage?: Storage;\n /** Custom serializer. Defaults to JSON.stringify. */\n serialize?: (v: T) => string;\n /** Custom deserializer. Defaults to JSON.parse. */\n deserialize?: (s: string) => T;\n /** Optional validator — return true if the deserialized value is valid. Rejects corrupt/tampered data. */\n validate?: (v: unknown) => v is T;\n}\n\n// ---------------------------------------------------------------------------\n// Public API\n// ---------------------------------------------------------------------------\n\n/**\n * Persist a signal's value to storage.\n *\n * On creation, reads the stored value (if any) and hydrates the signal.\n * Then sets up an effect to write to storage whenever the signal changes.\n *\n * ```ts\n * const [theme, setTheme] = createSignal('light');\n * persist([theme, setTheme], 'app:theme');\n *\n * setTheme('dark'); // auto-saved to localStorage under key 'app:theme'\n * ```\n */\nexport function persist<T>(\n source: [get: () => T, set: (v: T) => void],\n key: string,\n options?: PersistOptions<T>,\n): void {\n const [sourceGet, sourceSet] = source;\n const storage = options?.storage ?? globalThis.localStorage;\n const serialize = options?.serialize ?? JSON.stringify;\n const deserialize = options?.deserialize ?? JSON.parse;\n const validate = options?.validate;\n\n // Step 1: Hydrate from storage (if a value exists)\n try {\n const stored = storage.getItem(key);\n if (stored !== null) {\n const value = deserialize(stored);\n if (!validate || validate(value)) {\n sourceSet(value);\n }\n }\n } catch {\n // Stored data is invalid or storage is unavailable -- ignore and keep\n // the signal's current value.\n }\n\n // Step 2: Set up effect to persist on changes\n internalEffect(() => {\n const value = sourceGet();\n try {\n const serialized = serialize(value);\n storage.setItem(key, serialized);\n } catch {\n // Storage write failed (e.g., quota exceeded) -- silently ignore.\n }\n });\n}\n","// Typed event bus — pub/sub pattern\n\nexport interface EventBus<T extends Record<string, unknown>> {\n on<K extends keyof T>(event: K, handler: (payload: T[K]) => void): () => void;\n once<K extends keyof T>(event: K, handler: (payload: T[K]) => void): () => void;\n emit<K extends keyof T>(event: K, payload: T[K]): void;\n off<K extends keyof T>(event: K, handler: (payload: T[K]) => void): void;\n clear(): void;\n}\n\nexport function createBus<\n T extends Record<string, unknown> = Record<string, unknown>,\n>(): EventBus<T> {\n const listeners = new Map<keyof T, Set<(payload: any) => void>>();\n\n function getHandlers<K extends keyof T>(event: K): Set<(payload: any) => void> {\n let set = listeners.get(event);\n if (!set) {\n set = new Set();\n listeners.set(event, set);\n }\n return set;\n }\n\n function on<K extends keyof T>(\n event: K,\n handler: (payload: T[K]) => void,\n ): () => void {\n const set = getHandlers(event);\n set.add(handler);\n return () => {\n set.delete(handler);\n };\n }\n\n function once<K extends keyof T>(\n event: K,\n handler: (payload: T[K]) => void,\n ): () => void {\n const wrapper = (payload: T[K]) => {\n off(event, wrapper);\n handler(payload);\n };\n return on(event, wrapper);\n }\n\n function emit<K extends keyof T>(event: K, payload: T[K]): void {\n const set = listeners.get(event);\n if (set) {\n // Iterate over a snapshot so removals during emit are safe\n for (const handler of [...set]) {\n try {\n handler(payload);\n } catch (e) {\n console.error(`[forma] Bus handler error on \"${String(event)}\":`, e);\n }\n }\n }\n }\n\n function off<K extends keyof T>(\n event: K,\n handler: (payload: T[K]) => void,\n ): void {\n const set = listeners.get(event);\n if (set) {\n set.delete(handler);\n }\n }\n\n function clear(): void {\n listeners.clear();\n }\n\n return { on, once, emit, off, clear };\n}\n","// Event delegation — single listener on parent, matches children by selector\n\nexport function delegate<K extends keyof HTMLElementEventMap>(\n container: HTMLElement | Document,\n selector: string,\n event: K,\n handler: (e: HTMLElementEventMap[K], matchedEl: HTMLElement) => void,\n options?: AddEventListenerOptions,\n): () => void {\n const listener = (e: Event) => {\n const target = e.target;\n if (!(target instanceof HTMLElement)) return;\n\n const root =\n container instanceof Document ? container.documentElement : container;\n const matched = target.closest(selector);\n\n if (matched instanceof HTMLElement && root.contains(matched)) {\n handler(e as HTMLElementEventMap[K], matched);\n }\n };\n\n container.addEventListener(event, listener, options);\n\n return () => {\n container.removeEventListener(event, listener, options);\n };\n}\n","// Keyboard shortcut handler\n\ntype KeyCombo = string; // e.g., 'ctrl+s', 'shift+enter', 'escape', 'ctrl+shift+z'\n\ninterface KeyOptions {\n target?: EventTarget;\n preventDefault?: boolean;\n}\n\ninterface ParsedCombo {\n ctrl: boolean;\n shift: boolean;\n alt: boolean;\n meta: boolean;\n key: string;\n}\n\nfunction parseCombo(combo: KeyCombo): ParsedCombo {\n const parts = combo.toLowerCase().split('+').map((p) => p.trim());\n const modifiers: ParsedCombo = {\n ctrl: false,\n shift: false,\n alt: false,\n meta: false,\n key: '',\n };\n\n for (const part of parts) {\n switch (part) {\n case 'ctrl':\n case 'control':\n modifiers.ctrl = true;\n break;\n case 'shift':\n modifiers.shift = true;\n break;\n case 'alt':\n modifiers.alt = true;\n break;\n case 'meta':\n case 'cmd':\n case 'command':\n modifiers.meta = true;\n break;\n default:\n modifiers.key = part;\n }\n }\n\n return modifiers;\n}\n\nfunction matchesCombo(e: KeyboardEvent, parsed: ParsedCombo): boolean {\n if (e.ctrlKey !== parsed.ctrl) return false;\n if (e.shiftKey !== parsed.shift) return false;\n if (e.altKey !== parsed.alt) return false;\n if (e.metaKey !== parsed.meta) return false;\n return e.key.toLowerCase() === parsed.key;\n}\n\nexport function onKey(\n combo: KeyCombo,\n handler: (e: KeyboardEvent) => void,\n options?: KeyOptions,\n): () => void {\n const target: EventTarget = options?.target ?? document;\n const shouldPreventDefault = options?.preventDefault ?? true;\n const parsed = parseCombo(combo);\n\n const listener = (e: Event) => {\n if (!(e instanceof KeyboardEvent)) return;\n if (matchesCombo(e, parsed)) {\n if (shouldPreventDefault) {\n e.preventDefault();\n }\n handler(e);\n }\n };\n\n target.addEventListener('keydown', listener);\n\n return () => {\n target.removeEventListener('keydown', listener);\n };\n}\n","// Typed query helpers\n\nexport function $<T extends HTMLElement = HTMLElement>(\n selector: string,\n parent?: ParentNode,\n): T | null {\n return (parent ?? document).querySelector<T>(selector);\n}\n\nexport function $$<T extends HTMLElement = HTMLElement>(\n selector: string,\n parent?: ParentNode,\n): T[] {\n return Array.from((parent ?? document).querySelectorAll<T>(selector));\n}\n","// DOM mutation helpers\n\nexport function addClass(el: HTMLElement, ...classes: string[]): void {\n el.classList.add(...classes);\n}\n\nexport function removeClass(el: HTMLElement, ...classes: string[]): void {\n el.classList.remove(...classes);\n}\n\nexport function toggleClass(\n el: HTMLElement,\n className: string,\n force?: boolean,\n): boolean {\n return el.classList.toggle(className, force);\n}\n\nexport function setStyle(\n el: HTMLElement,\n styles: Partial<CSSStyleDeclaration>,\n): void {\n for (const [key, value] of Object.entries(styles)) {\n if (value !== undefined) {\n (el.style as any)[key] = value;\n }\n }\n}\n\nexport function setAttr(\n el: HTMLElement,\n attrs: Record<string, string | boolean | null>,\n): void {\n for (const [name, value] of Object.entries(attrs)) {\n if (value === false || value === null) {\n el.removeAttribute(name);\n } else if (value === true) {\n el.setAttribute(name, '');\n } else {\n el.setAttribute(name, value);\n }\n }\n}\n\nexport function setText(el: HTMLElement, text: string): void {\n el.textContent = text;\n}\n\n/**\n * Set raw HTML on an element. **No sanitization is performed.**\n *\n * Prefer `setText()` for user-controlled content. Only use this when you\n * trust the HTML source (e.g., server-rendered markup you control).\n *\n * @deprecated Use `setHTMLUnsafe` instead — renamed to signal risk.\n */\nexport function setHTML(el: HTMLElement, html: string): void {\n el.innerHTML = html;\n}\n\n/**\n * Set raw HTML on an element. **No sanitization is performed.**\n *\n * Prefer `setText()` for user-controlled content. Only use this when you\n * trust the HTML source (e.g., server-rendered markup you control).\n */\nexport function setHTMLUnsafe(el: HTMLElement, html: string): void {\n el.innerHTML = html;\n}\n","// DOM traversal helpers\n\nexport function closest<T extends HTMLElement = HTMLElement>(\n el: HTMLElement,\n selector: string,\n): T | null {\n return el.closest<T>(selector);\n}\n\nexport function children<T extends HTMLElement = HTMLElement>(\n el: HTMLElement,\n selector?: string,\n): T[] {\n const all = Array.from(el.children) as HTMLElement[];\n if (!selector) return all as T[];\n return all.filter((child) => child.matches(selector)) as T[];\n}\n\nexport function siblings<T extends HTMLElement = HTMLElement>(\n el: HTMLElement,\n selector?: string,\n): T[] {\n const parentEl = el.parentElement;\n if (!parentEl) return [];\n const all = Array.from(parentEl.children) as HTMLElement[];\n const sibs = all.filter((child) => child !== el);\n if (!selector) return sibs as T[];\n return sibs.filter((child) => child.matches(selector)) as T[];\n}\n\nexport function parent<T extends HTMLElement = HTMLElement>(\n el: HTMLElement,\n): T | null {\n return el.parentElement as T | null;\n}\n\nexport function nextSibling<T extends HTMLElement = HTMLElement>(\n el: HTMLElement,\n selector?: string,\n): T | null {\n let sib = el.nextElementSibling;\n while (sib) {\n if (sib instanceof HTMLElement) {\n if (!selector || sib.matches(selector)) {\n return sib as T;\n }\n }\n sib = sib.nextElementSibling;\n }\n return null;\n}\n\nexport function prevSibling<T extends HTMLElement = HTMLElement>(\n el: HTMLElement,\n selector?: string,\n): T | null {\n let sib = el.previousElementSibling;\n while (sib) {\n if (sib instanceof HTMLElement) {\n if (!selector || sib.matches(selector)) {\n return sib as T;\n }\n }\n sib = sib.previousElementSibling;\n }\n return null;\n}\n","// Observer wrappers — clean API for ResizeObserver, IntersectionObserver, MutationObserver\n\nexport function onResize(\n el: HTMLElement,\n handler: (entry: ResizeObserverEntry) => void,\n): () => void {\n const observer = new ResizeObserver((entries) => {\n for (const entry of entries) {\n handler(entry);\n }\n });\n observer.observe(el);\n return () => {\n observer.disconnect();\n };\n}\n\nexport function onIntersect(\n el: HTMLElement,\n handler: (entry: IntersectionObserverEntry) => void,\n options?: IntersectionObserverInit,\n): () => void {\n const observer = new IntersectionObserver((entries) => {\n for (const entry of entries) {\n handler(entry);\n }\n }, options);\n observer.observe(el);\n return () => {\n observer.disconnect();\n };\n}\n\nexport function onMutation(\n el: HTMLElement,\n handler: (mutations: MutationRecord[]) => void,\n options?: MutationObserverInit,\n): () => void {\n const observer = new MutationObserver((mutations) => {\n handler(mutations);\n });\n observer.observe(el, options ?? { childList: true, subtree: true });\n return () => {\n observer.disconnect();\n };\n}\n","/**\n * Forma Storage - Local\n *\n * Typed localStorage wrapper with graceful error handling.\n * Zero dependencies — native browser APIs only.\n */\n\nimport { TypedStorage, StorageOptions } from './types.js';\n\n/**\n * Create a typed localStorage wrapper for the given key.\n *\n * ```ts\n * const store = createLocalStorage<{ name: string }>('user');\n * store.set({ name: 'Alice' });\n * store.get(); // { name: 'Alice' }\n * store.remove();\n * ```\n */\nexport function createLocalStorage<T>(\n key: string,\n options?: StorageOptions<T>,\n): TypedStorage<T> {\n const serialize = options?.serialize ?? JSON.stringify;\n const deserialize = options?.deserialize ?? JSON.parse;\n const validate = options?.validate;\n\n return {\n key,\n\n get(): T | null {\n try {\n const raw = localStorage.getItem(key);\n if (raw === null) return null;\n const value = deserialize(raw);\n if (validate && !validate(value)) return null;\n return value as T;\n } catch {\n return null;\n }\n },\n\n set(value: T): void {\n try {\n const serialized = serialize(value);\n localStorage.setItem(key, serialized);\n } catch { /* QuotaExceededError or storage disabled — silently ignore */ }\n },\n\n remove(): void {\n localStorage.removeItem(key);\n },\n };\n}\n","/**\n * Forma Storage - Session\n *\n * Typed sessionStorage wrapper with graceful error handling.\n * Zero dependencies — native browser APIs only.\n */\n\nimport { TypedStorage, StorageOptions } from './types.js';\n\n/**\n * Create a typed sessionStorage wrapper for the given key.\n *\n * ```ts\n * const store = createSessionStorage<{ token: string }>('auth');\n * store.set({ token: 'abc123' });\n * store.get(); // { token: 'abc123' }\n * store.remove();\n * ```\n */\nexport function createSessionStorage<T>(\n key: string,\n options?: StorageOptions<T>,\n): TypedStorage<T> {\n const serialize = options?.serialize ?? JSON.stringify;\n const deserialize = options?.deserialize ?? JSON.parse;\n const validate = options?.validate;\n\n return {\n key,\n\n get(): T | null {\n try {\n const raw = sessionStorage.getItem(key);\n if (raw === null) return null;\n const value = deserialize(raw);\n if (validate && !validate(value)) return null;\n return value as T;\n } catch {\n return null;\n }\n },\n\n set(value: T): void {\n try {\n const serialized = serialize(value);\n sessionStorage.setItem(key, serialized);\n } catch { /* QuotaExceededError or storage disabled — silently ignore */ }\n },\n\n remove(): void {\n sessionStorage.removeItem(key);\n },\n };\n}\n","/**\n * Forma Storage - IndexedDB\n *\n * Simplified IndexedDB wrapper with lazy connection and promise-based API.\n * Zero dependencies — native browser APIs only.\n */\n\nexport interface IDBStore<T> {\n get(key: string): Promise<T | undefined>;\n set(key: string, value: T): Promise<void>;\n delete(key: string): Promise<void>;\n getAll(): Promise<T[]>;\n keys(): Promise<string[]>;\n clear(): Promise<void>;\n}\n\n/** Cached database connections keyed by \"dbName::storeName\". */\nconst dbCache = new Map<string, Promise<IDBDatabase>>();\n\n/**\n * Open (or retrieve a cached) IndexedDB database, ensuring the\n * requested object store exists.\n */\nfunction openDB(dbName: string, storeName: string): Promise<IDBDatabase> {\n const cacheKey = `${dbName}::${storeName}`;\n const cached = dbCache.get(cacheKey);\n if (cached) return cached;\n\n const promise = new Promise<IDBDatabase>((resolve, reject) => {\n // First, try opening at the current (or default) version.\n const probe = indexedDB.open(dbName);\n\n probe.onerror = () => reject(probe.error);\n\n probe.onsuccess = () => {\n const db = probe.result;\n if (db.objectStoreNames.contains(storeName)) {\n resolve(db);\n return;\n }\n // Store doesn't exist yet — close and reopen with a version bump.\n const nextVersion = db.version + 1;\n db.close();\n\n const upgrade = indexedDB.open(dbName, nextVersion);\n upgrade.onerror = () => reject(upgrade.error);\n upgrade.onupgradeneeded = () => {\n const upgradedDB = upgrade.result;\n if (!upgradedDB.objectStoreNames.contains(storeName)) {\n upgradedDB.createObjectStore(storeName);\n }\n };\n upgrade.onsuccess = () => resolve(upgrade.result);\n };\n\n probe.onupgradeneeded = () => {\n const db = probe.result;\n if (!db.objectStoreNames.contains(storeName)) {\n db.createObjectStore(storeName);\n }\n };\n });\n\n dbCache.set(cacheKey, promise);\n\n // If the open fails, remove from cache so the next call retries.\n promise.catch(() => {\n dbCache.delete(cacheKey);\n });\n\n return promise;\n}\n\n/**\n * Create a simplified IndexedDB store.\n *\n * ```ts\n * const store = createIndexedDB<User>('myApp', 'users');\n * await store.set('u1', { name: 'Alice' });\n * const user = await store.get('u1'); // { name: 'Alice' }\n * ```\n */\nexport function createIndexedDB<T>(\n dbName: string,\n storeName: string = 'default',\n): IDBStore<T> {\n /** Helper: run a single read/write transaction and return the request result. */\n function withStore<R>(\n mode: IDBTransactionMode,\n fn: (store: IDBObjectStore) => IDBRequest<R>,\n ): Promise<R> {\n return openDB(dbName, storeName).then(\n (db) =>\n new Promise<R>((resolve, reject) => {\n const tx = db.transaction(storeName, mode);\n const store = tx.objectStore(storeName);\n const request = fn(store);\n request.onsuccess = () => resolve(request.result);\n request.onerror = () => reject(request.error);\n }),\n );\n }\n\n return {\n get(key: string): Promise<T | undefined> {\n return withStore('readonly', (store) => store.get(key)) as Promise<T | undefined>;\n },\n\n set(key: string, value: T): Promise<void> {\n return withStore('readwrite', (store) => store.put(value, key)).then(\n () => undefined,\n );\n },\n\n delete(key: string): Promise<void> {\n return withStore('readwrite', (store) => store.delete(key)).then(\n () => undefined,\n );\n },\n\n getAll(): Promise<T[]> {\n return withStore('readonly', (store) => store.getAll()) as Promise<T[]>;\n },\n\n keys(): Promise<string[]> {\n return withStore('readonly', (store) => store.getAllKeys()).then(\n (keys) => keys.map(String),\n );\n },\n\n clear(): Promise<void> {\n return withStore('readwrite', (store) => store.clear()).then(\n () => undefined,\n );\n },\n };\n}\n","/**\n * Forma HTTP - Fetch\n *\n * Typed fetch wrapper with reactive signal integration.\n * Zero dependencies — native browser APIs only.\n */\n\nimport { createSignal, internalEffect } from 'forma/reactive';\n\n// ---------------------------------------------------------------------------\n// Types\n// ---------------------------------------------------------------------------\n\nexport interface FetchOptions<T> extends Omit<RequestInit, 'signal'> {\n base?: string;\n params?: Record<string, string>;\n timeout?: number; // ms, default 30000\n transform?: (data: unknown) => T;\n}\n\nexport interface FetchResult<T> {\n data: () => T | null;\n error: () => Error | null;\n loading: () => boolean;\n refetch: () => Promise<void>;\n abort: () => void;\n}\n\n// ---------------------------------------------------------------------------\n// createFetch — reactive fetch with signals\n// ---------------------------------------------------------------------------\n\n/**\n * Create a reactive fetch that exposes data/error/loading as signals.\n *\n * If `url` is a signal getter (function), an effect auto-refetches when it\n * changes.\n *\n * ```ts\n * const { data, loading, error, refetch, abort } = createFetch<User[]>('/api/users');\n * ```\n */\nexport function createFetch<T>(\n url: string | (() => string),\n options?: FetchOptions<T>,\n): FetchResult<T> {\n const [data, setData] = createSignal<T | null>(null);\n const [error, setError] = createSignal<Error | null>(null);\n const [loading, setLoading] = createSignal<boolean>(false);\n\n let currentController: AbortController | null = null;\n\n /** Resolve the URL string, applying base and params. */\n function resolveURL(): string {\n const raw = typeof url === 'function' ? url() : url;\n const base = options?.base ?? '';\n const fullURL = new URL(raw, base || undefined);\n\n if (options?.params) {\n for (const [key, value] of Object.entries(options.params)) {\n fullURL.searchParams.set(key, value);\n }\n }\n\n return fullURL.toString();\n }\n\n /** Execute a single fetch request. */\n async function execute(): Promise<void> {\n // Abort any in-flight request\n if (currentController) {\n currentController.abort();\n }\n\n currentController = new AbortController();\n const controller = currentController;\n const timeoutMs = options?.timeout ?? 30_000;\n\n // Set up timeout\n const timeoutId = setTimeout(() => controller.abort(), timeoutMs);\n\n setLoading(true);\n setError(null);\n\n try {\n const resolvedURL = resolveURL();\n\n const { base: _base, params: _params, timeout: _timeout, transform, ...fetchInit } =\n options ?? {};\n\n const response = await fetch(resolvedURL, {\n ...fetchInit,\n signal: controller.signal,\n });\n\n if (!response.ok) {\n throw new Error(`HTTP ${response.status}: ${response.statusText}`);\n }\n\n const json: unknown = await response.json();\n const transformed = transform ? transform(json) : (json as T);\n setData(transformed);\n } catch (err) {\n if (err instanceof Error && err.name === 'AbortError') {\n // Ignore aborts — they are intentional or timeouts\n return;\n }\n setError(err instanceof Error ? err : new Error(String(err)));\n } finally {\n clearTimeout(timeoutId);\n // Only update loading if this controller is still current\n if (currentController === controller) {\n currentController = null;\n setLoading(false);\n }\n }\n }\n\n // If url is a reactive getter, set up an effect to auto-refetch.\n if (typeof url === 'function') {\n internalEffect(() => {\n // Read the signal so the effect re-runs when it changes\n url();\n execute();\n });\n } else {\n // Kick off the first request immediately\n execute();\n }\n\n return {\n data,\n error,\n loading,\n refetch: execute,\n abort() {\n if (currentController) {\n currentController.abort();\n }\n },\n };\n}\n\n// ---------------------------------------------------------------------------\n// fetchJSON — simple one-shot helper\n// ---------------------------------------------------------------------------\n\n/**\n * One-shot fetch that returns parsed JSON.\n *\n * ```ts\n * const users = await fetchJSON<User[]>('/api/users');\n * ```\n */\nexport async function fetchJSON<T>(url: string, options?: RequestInit): Promise<T> {\n const response = await fetch(url, options);\n if (!response.ok) {\n throw new Error(`HTTP ${response.status}: ${response.statusText}`);\n }\n return (await response.json()) as T;\n}\n","/**\n * Forma HTTP - Server-Sent Events\n *\n * Reactive SSE wrapper with signal integration.\n * Zero dependencies — native browser APIs only.\n */\n\nimport { createSignal } from 'forma/reactive';\n\n// ---------------------------------------------------------------------------\n// Types\n// ---------------------------------------------------------------------------\n\nexport interface SSEOptions<T = unknown> {\n withCredentials?: boolean;\n headers?: Record<string, string>; // Note: native EventSource does not support custom headers\n /** Custom parser for incoming messages. Defaults to JSON.parse with raw data fallback. */\n parse?: (data: string) => T;\n}\n\nexport interface SSEConnection<T = unknown> {\n data: () => T | null;\n error: () => Event | null;\n connected: () => boolean;\n close: () => void;\n on(event: string, handler: (data: unknown) => void): () => void;\n}\n\n// ---------------------------------------------------------------------------\n// createSSE\n// ---------------------------------------------------------------------------\n\n/**\n * Create a reactive Server-Sent Events connection.\n *\n * ```ts\n * const sse = createSSE<{ message: string }>('/api/events');\n * createEffect(() => {\n * const msg = sse.data();\n * if (msg) console.log(msg.message);\n * });\n * ```\n */\nexport function createSSE<T = unknown>(\n url: string,\n options?: SSEOptions<T>,\n): SSEConnection<T> {\n const [data, setData] = createSignal<T | null>(null);\n const [error, setError] = createSignal<Event | null>(null);\n const [connected, setConnected] = createSignal<boolean>(false);\n\n const source = new EventSource(url, {\n withCredentials: options?.withCredentials ?? false,\n });\n\n source.onopen = () => {\n setConnected(true);\n setError(null);\n };\n\n const parseMessage = options?.parse ?? ((raw: string): T => {\n try { return JSON.parse(raw) as T; }\n catch { return raw as T; }\n });\n\n source.onmessage = (event: MessageEvent) => {\n setData(parseMessage(event.data as string));\n };\n\n source.onerror = (event: Event) => {\n setError(event);\n setConnected(false);\n };\n\n return {\n data,\n error,\n connected,\n\n close(): void {\n source.close();\n setConnected(false);\n },\n\n on(event: string, handler: (data: unknown) => void): () => void {\n const parseEvent = options?.parse ?? ((raw: string) => {\n try { return JSON.parse(raw); }\n catch { return raw; }\n });\n const listener = (e: MessageEvent) => {\n handler(parseEvent(e.data as string));\n };\n source.addEventListener(event, listener as EventListener);\n return () => {\n source.removeEventListener(event, listener as EventListener);\n };\n },\n };\n}\n","/**\n * Forma HTTP - WebSocket\n *\n * Reactive WebSocket wrapper with auto-reconnect and signal integration.\n * Zero dependencies — native browser APIs only.\n */\n\nimport { createSignal } from 'forma/reactive';\n\n// ---------------------------------------------------------------------------\n// Types\n// ---------------------------------------------------------------------------\n\nexport type WSStatus = 'connecting' | 'open' | 'closed' | 'error';\n\nexport interface WSOptions<TReceive = unknown> {\n protocols?: string | string[];\n reconnect?: boolean; // default true\n reconnectInterval?: number; // ms, default 1000\n maxReconnects?: number; // default 5\n /** Custom parser for incoming messages. Defaults to JSON.parse with raw data fallback. */\n parse?: (data: string) => TReceive;\n}\n\nexport interface WSConnection<TSend = unknown, TReceive = unknown> {\n data: () => TReceive | null;\n status: () => WSStatus;\n send(data: TSend): void;\n close(): void;\n on(handler: (data: TReceive) => void): () => void;\n}\n\n// ---------------------------------------------------------------------------\n// createWebSocket\n// ---------------------------------------------------------------------------\n\n/**\n * Create a reactive WebSocket connection with auto-reconnect.\n *\n * ```ts\n * const ws = createWebSocket<string, ChatMessage>('wss://chat.example.com');\n * ws.send('hello');\n * createEffect(() => {\n * const msg = ws.data();\n * if (msg) console.log(msg);\n * });\n * ```\n */\nexport function createWebSocket<TSend = unknown, TReceive = unknown>(\n url: string,\n options?: WSOptions<TReceive>,\n): WSConnection<TSend, TReceive> {\n const shouldReconnect = options?.reconnect ?? true;\n const baseInterval = options?.reconnectInterval ?? 1000;\n const maxReconnects = options?.maxReconnects ?? 5;\n\n const [data, setData] = createSignal<TReceive | null>(null);\n const [status, setStatus] = createSignal<WSStatus>('connecting');\n\n const handlers = new Set<(data: TReceive) => void>();\n\n let socket: WebSocket | null = null;\n let reconnectCount = 0;\n let reconnectTimer: ReturnType<typeof setTimeout> | null = null;\n let permanentlyClosed = false;\n\n function connect(): void {\n if (permanentlyClosed) return;\n\n setStatus('connecting');\n socket = new WebSocket(url, options?.protocols);\n\n socket.onopen = () => {\n setStatus('open');\n reconnectCount = 0; // Reset on successful connection\n };\n\n const parseMessage = options?.parse ?? ((raw: string): TReceive => {\n try { return JSON.parse(raw) as TReceive; }\n catch { return raw as TReceive; }\n });\n\n socket.onmessage = (event: MessageEvent) => {\n const parsed = parseMessage(event.data as string);\n setData(parsed);\n for (const handler of handlers) {\n handler(parsed);\n }\n };\n\n socket.onerror = () => {\n setStatus('error');\n };\n\n socket.onclose = () => {\n if (permanentlyClosed) {\n setStatus('closed');\n return;\n }\n\n setStatus('closed');\n\n if (shouldReconnect && reconnectCount < maxReconnects) {\n // Exponential backoff: baseInterval * 2^reconnectCount\n const delay = baseInterval * Math.pow(2, reconnectCount);\n reconnectCount++;\n reconnectTimer = setTimeout(connect, delay);\n }\n };\n }\n\n // Initiate the first connection\n connect();\n\n return {\n data,\n status,\n\n send(value: TSend): void {\n if (socket && socket.readyState === WebSocket.OPEN) {\n socket.send(JSON.stringify(value));\n }\n },\n\n close(): void {\n permanentlyClosed = true;\n if (reconnectTimer !== null) {\n clearTimeout(reconnectTimer);\n reconnectTimer = null;\n }\n if (socket) {\n socket.close();\n socket = null;\n }\n setStatus('closed');\n },\n\n on(handler: (data: TReceive) => void): () => void {\n handlers.add(handler);\n return () => {\n handlers.delete(handler);\n };\n },\n };\n}\n","/**\n * FormaJS Server - Action\n *\n * Creates an action that wraps a server function with optimistic UI support.\n * The action immediately applies an optimistic update, then reconciles when\n * the server responds (or rolls back on error).\n */\n\nimport { createSignal, batch } from '../reactive/index.js';\nimport type { Resource } from '../reactive/resource.js';\n\n// ---------------------------------------------------------------------------\n// Types\n// ---------------------------------------------------------------------------\n\nexport interface ActionOptions<Args extends unknown[], Result> {\n /**\n * Apply an optimistic update immediately when the action is called.\n * This runs BEFORE the server function.\n * Store whatever you need to roll back in the return value or via closures.\n */\n optimistic?: (...args: Args) => void;\n\n /**\n * Called when the server function resolves successfully.\n * Use this to apply the server result to local state.\n */\n onSuccess?: (result: Result, ...args: Args) => void;\n\n /**\n * Called when the server function rejects.\n * Use this to roll back the optimistic update.\n */\n onError?: (error: unknown, ...args: Args) => void;\n\n /**\n * Resources to refetch after the action completes successfully.\n * Used with single-flight mutations: if the server response includes\n * revalidation data, these resources are updated without a refetch.\n */\n invalidates?: Resource<unknown>[];\n}\n\nexport interface Action<Args extends unknown[], Result> {\n /** Execute the action. */\n (...args: Args): Promise<Result>;\n /** Whether the action is currently in-flight. */\n pending: () => boolean;\n /** The last error from the action (or undefined). */\n error: () => unknown;\n /** Clear the error state. */\n clearError: () => void;\n}\n\n/**\n * Create an action that wraps a server function with optimistic UI.\n *\n * ```ts\n * const addTodo = createAction(\n * serverCreateTodo,\n * {\n * optimistic: (text) => {\n * // Immediately add to local list\n * setTodos(prev => [...prev, { text, done: false, id: 'temp' }]);\n * },\n * onSuccess: (result) => {\n * // Replace temp item with server result\n * setTodos(prev => prev.map(t => t.id === 'temp' ? result : t));\n * },\n * onError: (err, text) => {\n * // Remove the optimistic item\n * setTodos(prev => prev.filter(t => t.id !== 'temp'));\n * },\n * invalidates: [todosResource],\n * },\n * );\n *\n * // Use:\n * await addTodo('Buy milk');\n * ```\n */\nexport function createAction<Args extends unknown[], Result>(\n serverFn: (...args: Args) => Promise<Result>,\n options?: ActionOptions<Args, Result>,\n): Action<Args, Result> {\n const [pending, setPending] = createSignal(false);\n const [error, setError] = createSignal<unknown>(undefined);\n\n const action = async (...args: Args): Promise<Result> => {\n setPending(true);\n setError(undefined);\n\n // Apply optimistic update immediately\n if (options?.optimistic) {\n try {\n batch(() => options.optimistic!(...args));\n } catch {\n // Swallow errors in optimistic callback\n }\n }\n\n try {\n const result = await serverFn(...args);\n\n // Apply success handler\n if (options?.onSuccess) {\n batch(() => options.onSuccess!(result, ...args));\n }\n\n // Revalidate dependent resources\n if (options?.invalidates) {\n for (const resource of options.invalidates) {\n resource.refetch();\n }\n }\n\n setPending(false);\n return result;\n } catch (err) {\n // Apply error/rollback handler\n if (options?.onError) {\n try {\n batch(() => options.onError!(err, ...args));\n } catch {\n // Swallow errors in rollback\n }\n }\n\n setError(err);\n setPending(false);\n throw err;\n }\n };\n\n // Attach signal accessors to the action function\n const typedAction = action as Action<Args, Result>;\n typedAction.pending = pending;\n typedAction.error = error;\n typedAction.clearError = () => setError(undefined);\n\n return typedAction;\n}\n","/**\n * FormaJS Server - Mutation\n *\n * Single-flight mutation pattern: the server response carries both the\n * mutation result AND fresh data for dependent resources in one round trip.\n *\n * Without single-flight:\n * Client -> Server: createTodo(\"Buy milk\")\n * Server -> Client: { id: 1, text: \"Buy milk\" }\n * Client -> Server: GET /api/todos (refetch to update list)\n * Server -> Client: [all todos]\n *\n * With single-flight:\n * Client -> Server: createTodo(\"Buy milk\")\n * Server -> Client: { data: {...}, __revalidate: { \"/api/todos\": [all todos] } }\n * (No second request needed!)\n */\n\nimport type { Resource } from '../reactive/resource.js';\n\n// ---------------------------------------------------------------------------\n// Types\n// ---------------------------------------------------------------------------\n\nexport interface MutationResponse<T> {\n /** The mutation result. */\n data: T;\n /**\n * Fresh data for dependent resources, keyed by resource identifier.\n * When present, the client updates these resources directly instead of refetching.\n */\n __revalidate?: Record<string, unknown>;\n}\n\n// ---------------------------------------------------------------------------\n// Resource registry for revalidation\n// ---------------------------------------------------------------------------\n\nconst resourceRegistry = new Map<string, Resource<unknown>>();\n\n/**\n * Register a resource with a key so it can be revalidated by single-flight mutations.\n *\n * ```ts\n * const todos = createResource(\n * () => true,\n * () => fetch('/api/todos').then(r => r.json()),\n * );\n * registerResource('/api/todos', todos);\n * ```\n */\nexport function registerResource(key: string, resource: Resource<unknown>): void {\n resourceRegistry.set(key, resource);\n}\n\n/**\n * Unregister a resource (call on cleanup/unmount).\n */\nexport function unregisterResource(key: string): void {\n resourceRegistry.delete(key);\n}\n\n/**\n * Apply revalidation data from a single-flight mutation response.\n * For each key in the revalidate map, find the matching resource\n * and mutate it directly with the fresh data (skipping a refetch).\n */\nexport function applyRevalidation(revalidateData: Record<string, unknown>): void {\n for (const [key, freshData] of Object.entries(revalidateData)) {\n const resource = resourceRegistry.get(key);\n if (resource) {\n resource.mutate(freshData);\n }\n }\n}\n\n/**\n * Listen for revalidation events dispatched by $$serverFunction.\n * Call this once during app initialization to enable automatic\n * single-flight mutation handling.\n *\n * ```ts\n * // In your app entry:\n * import { enableAutoRevalidation } from 'forma/server/mutation';\n * enableAutoRevalidation();\n * ```\n */\nexport function enableAutoRevalidation(): () => void {\n if (typeof window === 'undefined') {\n // SSR/Node.js — no-op\n return () => {};\n }\n\n const handler = (event: Event) => {\n const detail = (event as CustomEvent).detail;\n if (detail && typeof detail === 'object') {\n applyRevalidation(detail as Record<string, unknown>);\n }\n };\n\n window.addEventListener('forma:revalidate', handler);\n\n // Return cleanup function\n return () => window.removeEventListener('forma:revalidate', handler);\n}\n\n/**\n * Wrap a server function response to include revalidation data.\n * Use this on the server side to enable single-flight mutations.\n *\n * ```ts\n * // Server-side:\n * async function createTodo(text: string) {\n * \"use server\";\n * const newTodo = await db.insert('todos', { text, done: false });\n * const allTodos = await db.query('todos');\n * return withRevalidation(newTodo, {\n * '/api/todos': allTodos,\n * });\n * }\n * ```\n */\nexport function withRevalidation<T>(data: T, revalidate: Record<string, unknown>): MutationResponse<T> {\n return { data, __revalidate: revalidate };\n}\n","/**\n * FormaJS Server - RPC Client\n *\n * Provides the client-side stub function that replaces \"use server\" function\n * bodies after compilation. Each call becomes a fetch POST to the server endpoint.\n */\n\n/**\n * Create an RPC stub function for a server function.\n * This replaces the original function body on the client side.\n *\n * @param endpoint - The RPC endpoint path (e.g. \"/rpc/createTodo_a1b2c3\")\n * @returns An async function that sends args to the server and returns the result\n */\nexport function $$serverFunction<T extends (...args: unknown[]) => Promise<unknown>>(\n endpoint: string,\n): T {\n const rpcFn = async (...args: unknown[]): Promise<unknown> => {\n const response = await fetch(endpoint, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/json',\n 'X-Forma-RPC': '1',\n },\n body: JSON.stringify({ args }),\n });\n\n if (!response.ok) {\n const errorText = await response.text();\n throw new Error(`Server function failed (${response.status}): ${errorText}`);\n }\n\n const result = await response.json();\n\n // If the response includes revalidation data (single-flight mutations),\n // return it alongside the result\n if (result && typeof result === 'object' && '__revalidate' in result) {\n // Dispatch a custom event so createAction can pick up the revalidation data\n if (typeof window !== 'undefined') {\n window.dispatchEvent(new CustomEvent('forma:revalidate', {\n detail: result.__revalidate,\n }));\n }\n return result.data;\n }\n\n return result;\n };\n\n return rpcFn as T;\n}\n","/**\n * FormaJS Server - RPC Handler\n *\n * Server-side registry and request handler for \"use server\" functions.\n * Framework-agnostic — works with any Node.js HTTP server, Express, Hono, etc.\n */\n\ntype ServerFunction = (...args: unknown[]) => Promise<unknown>;\n\n/** Registry of server functions by endpoint path. */\nconst registry = new Map<string, ServerFunction>();\n\n/**\n * Register a server function at a specific endpoint.\n * Called by the server-side compiled output.\n */\nexport function registerServerFunction(endpoint: string, fn: ServerFunction): void {\n registry.set(endpoint, fn);\n}\n\n/**\n * Get a registered server function by endpoint.\n */\nexport function getServerFunction(endpoint: string): ServerFunction | undefined {\n return registry.get(endpoint);\n}\n\n/**\n * Get all registered server function endpoints.\n */\nexport function getRegisteredEndpoints(): string[] {\n return [...registry.keys()];\n}\n\nexport interface RPCRequest {\n args: unknown[];\n}\n\nexport interface RPCResponse {\n data?: unknown;\n error?: string;\n __revalidate?: Record<string, unknown>;\n}\n\n/**\n * Handle an incoming RPC request.\n * Call this from your HTTP server's request handler.\n *\n * Usage with any HTTP framework:\n * ```ts\n * import { handleRPC } from 'forma/server/rpc-handler';\n *\n * // Express example:\n * app.post('/rpc/:endpoint', async (req, res) => {\n * const result = await handleRPC(req.path, req.body);\n * res.json(result);\n * });\n *\n * // Hono example:\n * app.post('/rpc/*', async (c) => {\n * const body = await c.req.json();\n * const result = await handleRPC(c.req.path, body);\n * return c.json(result);\n * });\n * ```\n *\n * @param endpoint - The full endpoint path (e.g. \"/rpc/createTodo_a1b2c3\")\n * @param body - The parsed request body containing { args: [...] }\n * @param revalidateData - Optional revalidation data to include in the response\n * (for single-flight mutations)\n */\n/** \"Crash Barrier\": block prototype pollution attacks via endpoint names. */\nconst FORBIDDEN_KEYS = new Set(['__proto__', 'constructor', 'prototype']);\n\nexport async function handleRPC(\n endpoint: string,\n body: RPCRequest,\n revalidateData?: Record<string, unknown>,\n): Promise<RPCResponse> {\n // Security: prevent prototype pollution via crafted endpoint names\n const endpointName = endpoint.split('/').pop() ?? '';\n if (FORBIDDEN_KEYS.has(endpointName)) {\n return { error: 'Forbidden endpoint name' };\n }\n\n const fn = registry.get(endpoint);\n if (!fn) {\n return { error: `Unknown server function: ${endpoint}` };\n }\n\n try {\n const result = await fn(...body.args);\n\n if (revalidateData) {\n return { data: result, __revalidate: revalidateData };\n }\n\n return { data: result };\n } catch (err) {\n // Don't leak internal error details to clients\n const isDev = typeof process !== 'undefined'\n && process.env?.NODE_ENV === 'development';\n const message = isDev && err instanceof Error\n ? err.message\n : 'Internal server error';\n return { error: message };\n }\n}\n\n/**\n * Create a middleware-style handler for use with Express-like frameworks.\n *\n * ```ts\n * import { createRPCMiddleware } from 'forma/server/rpc-handler';\n * app.use('/rpc', createRPCMiddleware());\n * ```\n */\nexport function createRPCMiddleware() {\n return async (req: { url: string; method: string; body?: unknown }, res: { json: (data: unknown) => void; status: (code: number) => { json: (data: unknown) => void } }) => {\n if (req.method !== 'POST') {\n res.status(405).json({ error: 'Method not allowed' });\n return;\n }\n\n const body = req.body as RPCRequest;\n if (!body || !Array.isArray(body.args)) {\n res.status(400).json({ error: 'Invalid RPC request: missing args array' });\n return;\n }\n\n const result = await handleRPC(req.url, body);\n if (result.error) {\n res.status(500).json(result);\n } else {\n res.json(result);\n }\n };\n}\n","// Client-side WASM walker loader.\n// Reads URLs from window.__FORMA_WASM__, lazy-loads WASM module + IR bytes,\n// provides renderLocal() and renderIsland() for zero-server-trip re-renders.\n\ndeclare global {\n interface Window {\n __FORMA_WASM__?: {\n loader: string;\n binary: string;\n ir: string;\n };\n }\n}\n\ninterface WasmExports {\n render(ir_bytes: Uint8Array, slots_json: string): string;\n render_island(ir_bytes: Uint8Array, slots_json: string, island_id: number): string;\n}\n\nlet wasmModule: WasmExports | null = null;\nlet irCache: Map<string, Uint8Array> = new Map();\n\nasync function ensureWasm(): Promise<WasmExports> {\n if (wasmModule) return wasmModule;\n\n const config = window.__FORMA_WASM__;\n if (!config) throw new Error('No __FORMA_WASM__ config');\n\n // Dynamic import of wasm-pack generated loader\n const mod = await import(/* @vite-ignore */ config.loader);\n await mod.default(config.binary);\n wasmModule = mod as unknown as WasmExports;\n return wasmModule;\n}\n\nasync function getIR(): Promise<Uint8Array> {\n const config = window.__FORMA_WASM__;\n if (!config) throw new Error('No __FORMA_WASM__ config');\n\n const cached = irCache.get(config.ir);\n if (cached) return cached;\n\n const response = await fetch(config.ir);\n const bytes = new Uint8Array(await response.arrayBuffer());\n irCache.set(config.ir, bytes);\n return bytes;\n}\n\n/** Full page render via WASM. */\nexport async function renderLocal(slotsJson: string): Promise<string> {\n const [wasm, ir] = await Promise.all([ensureWasm(), getIR()]);\n return wasm.render(ir, slotsJson);\n}\n\n/** Fragment render (single island) via WASM. */\nexport async function renderIsland(slotsJson: string, islandId: number): Promise<string> {\n const [wasm, ir] = await Promise.all([ensureWasm(), getIR()]);\n return wasm.render_island(ir, slotsJson, islandId);\n}\n"]}
|
|
1
|
+
{"version":3,"sources":["../src/dom/text.ts","../src/dom/mount.ts","../src/dom/switch.ts","../src/dom/portal.ts","../src/dom/error-boundary.ts","../src/dom/suspense.ts","../src/dom/activate.ts","../src/component/define.ts","../src/component/context.ts","../src/state/store.ts","../src/state/history.ts","../src/state/persist.ts","../src/events/bus.ts","../src/events/delegate.ts","../src/events/keyboard.ts","../src/dom-utils/query.ts","../src/dom-utils/mutate.ts","../src/dom-utils/traverse.ts","../src/dom-utils/observe.ts","../src/storage/local.ts","../src/storage/session.ts","../src/storage/indexed.ts","../src/http/fetch.ts","../src/http/sse.ts","../src/http/ws.ts","../src/server/action.ts","../src/server/mutation.ts","../src/server/rpc-client.ts","../src/server/rpc-handler.ts"],"names":["fragment","parent","children","registry","trigger","cleanup","setter","on"],"mappings":"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","file":"index.js","sourcesContent":["/**\n * Forma DOM - Text\n *\n * Creates static or reactive Text nodes.\n * Zero dependencies -- native browser APIs only.\n */\n\nimport { internalEffect } from 'forma/reactive';\n\n/**\n * Create a Text node that is either static or reactively bound.\n *\n * - If `value` is a string, creates a plain Text node.\n * - If `value` is a function (signal getter), creates a Text node and sets up\n * an effect that auto-updates `textContent` whenever the signal changes.\n *\n * @returns The Text node.\n */\nexport function createText(value: string | (() => string)): Text {\n if (typeof value === 'function') {\n // \"Track Limits\": new Text() bypasses Document factory dispatch\n const node = new Text('');\n internalEffect(() => {\n // \"DAS\": CharacterData.data is the rawest text setter\n node.data = value();\n });\n return node;\n }\n return new Text(value);\n}\n","/**\n * Forma DOM - Mount\n *\n * Mounts a component function into a DOM container, returning an unmount handle.\n * Uses createRoot() for automatic effect disposal — no global state.\n *\n * When the container has `data-forma-ssr`, uses hydrateIsland() for zero-flash\n * descriptor-based hydration instead of tearing down and rebuilding the DOM.\n */\n\nimport { createRoot } from 'forma/reactive';\nimport { hydrateIsland } from './hydrate.js';\n\n// ---------------------------------------------------------------------------\n// Public API\n// ---------------------------------------------------------------------------\n\n/**\n * Mount a component into a DOM container.\n *\n * All effects created during the component's render are tracked via\n * `createRoot()` and automatically disposed when unmount is called.\n *\n * When `data-forma-ssr` is present on the container, the component runs\n * inside `createRoot` in hydration mode — h() returns descriptors that are\n * walked against SSR DOM to attach handlers and reactive bindings.\n *\n * @param component A function returning an HTMLElement or DocumentFragment.\n * @param container An HTMLElement or a CSS selector string.\n * @returns An unmount function that removes the DOM and disposes all effects.\n *\n * ```ts\n * const unmount = mount(() => h('h1', null, 'Hello'), '#app');\n * // later…\n * unmount();\n * ```\n */\nexport function mount(\n component: () => HTMLElement | DocumentFragment,\n container: HTMLElement | string,\n): () => void {\n const target =\n typeof container === 'string'\n ? document.querySelector<HTMLElement>(container)\n : container;\n\n if (!target) {\n throw new Error(`mount: container not found — \"${container}\"`);\n }\n\n let disposeRoot!: () => void;\n\n if (target.hasAttribute('data-forma-ssr')) {\n // SSR content present — hydrate in-place using descriptor-based adoption.\n // The component MUST run inside createRoot so effects are tracked.\n createRoot((dispose) => {\n disposeRoot = dispose;\n hydrateIsland(component, target);\n });\n } else {\n // Normal mount — clear and append\n const dom = createRoot((dispose) => {\n disposeRoot = dispose;\n return component();\n });\n target.innerHTML = '';\n target.appendChild(dom);\n }\n\n // Return unmount function\n let unmounted = false;\n return () => {\n if (unmounted) return;\n unmounted = true;\n disposeRoot();\n target.innerHTML = '';\n };\n}\n","/**\n * Forma DOM - Switch (Multi-branch Conditional)\n *\n * Maps a reactive value to one of N render branches.\n * Caches previously rendered nodes for instant swap-back.\n *\n * Each cached branch gets its own reactive root (ownership scope) so that:\n * 1. Inner effects survive when the switch effect re-runs (alien-signals\n * would otherwise dispose child effects linked to the parent).\n * 2. Inner effects are explicitly disposed when the branch is evicted\n * from the cache or the switch itself is torn down.\n *\n * SolidJS equivalent: <Switch><Match when={}>\n */\n\nimport { internalEffect, untrack, createRoot } from 'forma/reactive';\n\ninterface SwitchCase<T> {\n match: T;\n render: () => Node;\n}\n\n/** Cached branch: the rendered DOM node + a dispose function for its root. */\ninterface CachedBranch {\n node: Node;\n dispose: () => void;\n}\n\n/**\n * Multi-branch conditional rendering with node caching.\n *\n * ```ts\n * const [tab, setTab] = createSignal('home');\n * const fragment = createSwitch(tab, [\n * { match: 'home', render: () => h('div', null, 'Home page') },\n * { match: 'about', render: () => h('div', null, 'About page') },\n * { match: 'contact', render: () => h('div', null, 'Contact page') },\n * ], () => h('div', null, '404'));\n * ```\n *\n * Previously rendered branches are cached — switching back to a tab\n * re-inserts the cached node without re-rendering.\n */\nexport function createSwitch<T>(\n value: () => T,\n cases: SwitchCase<T>[],\n fallback?: () => Node,\n): DocumentFragment {\n const startMarker = document.createComment('forma-switch');\n const endMarker = document.createComment('/forma-switch');\n const fragment = document.createDocumentFragment();\n fragment.appendChild(startMarker);\n fragment.appendChild(endMarker);\n\n // Branch cache: value → { node, dispose }\n // Each branch has its own reactive root for explicit lifecycle management.\n const cache = new Map<T, CachedBranch>();\n let currentNode: Node | null = null;\n let currentMatch: T | typeof UNSET = UNSET;\n\n const switchDispose = internalEffect(() => {\n const val = value();\n if (val === currentMatch) return; // Same branch, skip\n\n const DEBUG = typeof (globalThis as any).__FORMA_DEBUG__ !== 'undefined';\n if (DEBUG) console.log('[forma:switch] transition', String(currentMatch), '→', String(val));\n\n currentMatch = val;\n\n const parent = startMarker.parentNode;\n if (!parent) {\n if (DEBUG) console.warn('[forma:switch] markers not in DOM yet, skipping');\n return;\n }\n\n // Remove current content between markers.\n // If currentNode was a DocumentFragment, its children transferred to the\n // DOM on insertion and the fragment is now detached (parentNode === null).\n // We must scoop the children BACK into the fragment so the cache stays\n // valid for re-insertion later.\n if (currentNode) {\n if (currentNode.parentNode === parent) {\n if (DEBUG) console.log('[forma:switch] removing single node');\n parent.removeChild(currentNode);\n } else if (currentNode.nodeType === 11 /* DOCUMENT_FRAGMENT_NODE */) {\n // Scoop DOM nodes back into the fragment for cache reuse\n if (DEBUG) console.log('[forma:switch] scooping nodes back into fragment');\n let scooped = 0;\n while (startMarker.nextSibling && startMarker.nextSibling !== endMarker) {\n currentNode.appendChild(startMarker.nextSibling);\n scooped++;\n }\n if (DEBUG) console.log('[forma:switch] scooped', scooped, 'nodes back into fragment');\n } else {\n // Other detached node — just clear between markers\n if (DEBUG) console.log('[forma:switch] clearing detached node between markers');\n while (startMarker.nextSibling && startMarker.nextSibling !== endMarker) {\n parent.removeChild(startMarker.nextSibling);\n }\n }\n }\n\n // Find matching case\n const matchedCase = cases.find(c => c.match === val);\n if (matchedCase) {\n let entry = cache.get(val);\n if (!entry) {\n // Render inside a createRoot so child effects are tracked for\n // disposal, and inside untrack so they are NOT linked to the\n // switch effect (alien-signals disposes child effects on parent\n // re-run, which would kill reactivity in cached branches).\n let branchDispose!: () => void;\n const node = createRoot((dispose) => {\n branchDispose = dispose;\n return untrack(() => matchedCase.render());\n });\n entry = { node, dispose: branchDispose };\n cache.set(val, entry);\n if (DEBUG) console.log('[forma:switch] rendered new branch for', String(val), '→', node.nodeName, 'type', node.nodeType);\n } else {\n if (DEBUG) console.log('[forma:switch] reusing cached branch for', String(val), '→', entry.node.nodeName, 'type', entry.node.nodeType, 'childNodes', entry.node.childNodes?.length);\n }\n currentNode = entry.node;\n } else {\n // Fallback — not cached, effects are owned by the switch effect\n // and correctly torn down on next re-run.\n currentNode = fallback?.() ?? null;\n if (DEBUG) console.log('[forma:switch] no match, using fallback');\n }\n\n if (currentNode) {\n parent.insertBefore(currentNode, endMarker);\n if (DEBUG) console.log('[forma:switch] inserted', currentNode.nodeName, 'before end marker');\n }\n });\n\n // Attach a cleanup marker so external disposal (via disposeComponent or\n // parent root teardown) can clean up all cached branches.\n (fragment as any).__switchDispose = () => {\n switchDispose();\n for (const entry of cache.values()) {\n entry.dispose();\n }\n cache.clear();\n };\n\n return fragment;\n}\n\n// Sentinel value for \"no match yet\"\nconst UNSET = Symbol('unset');\n","/**\n * Forma DOM - Portal\n *\n * Renders children into a different DOM container than the parent.\n * Useful for modals, tooltips, dropdowns that need to escape overflow.\n *\n * SolidJS equivalent: <Portal mount={}>\n */\n\nimport { createEffect } from 'forma/reactive';\n\n/**\n * Render content into an external DOM container.\n *\n * ```ts\n * const modal = createPortal(\n * () => h('div', { class: 'modal' }, 'Modal content'),\n * document.body,\n * );\n * ```\n *\n * Returns a comment node placeholder. The actual content is rendered\n * into the target container. Cleanup removes content from target.\n */\nexport function createPortal(\n children: () => Node,\n target?: Element | string,\n): Comment {\n const placeholder = document.createComment('forma-portal');\n\n const resolvedTarget = typeof target === 'string'\n ? document.querySelector(target)\n : (target ?? document.body);\n\n if (!resolvedTarget) {\n throw new Error(`createPortal: target not found: ${target}`);\n }\n\n let mountedNode: Node | null = null;\n const removeMountedNode = () => {\n if (mountedNode && mountedNode.parentNode === resolvedTarget) {\n resolvedTarget.removeChild(mountedNode);\n }\n mountedNode = null;\n };\n\n createEffect(() => {\n const node = children();\n\n // Remove previous\n removeMountedNode();\n\n mountedNode = node;\n resolvedTarget.appendChild(node);\n\n // Ensure portal content is removed when the owner root disposes.\n return () => {\n removeMountedNode();\n };\n });\n\n return placeholder;\n}\n","/**\n * Forma DOM - Error Boundary\n *\n * Catches errors during rendering and shows a fallback UI.\n * Provides a retry function to re-attempt the original render.\n *\n * SolidJS equivalent: <ErrorBoundary fallback={}>\n */\n\nimport { createSignal, internalEffect } from 'forma/reactive';\n\n/**\n * Wrap a render function with error recovery.\n *\n * ```ts\n * const fragment = createErrorBoundary(\n * () => h('div', null, riskyComponent()),\n * (error, retry) => h('div', { class: 'error' },\n * h('p', null, `Error: ${error.message}`),\n * h('button', { onClick: retry }, 'Retry'),\n * ),\n * );\n * ```\n *\n * If `tryFn` throws, `catchFn` is called with the error and a retry function.\n * Calling `retry()` re-runs `tryFn`.\n */\nexport function createErrorBoundary(\n tryFn: () => Node,\n catchFn: (error: Error, retry: () => void) => Node,\n): DocumentFragment {\n const startMarker = document.createComment('forma-error-boundary');\n const endMarker = document.createComment('/forma-error-boundary');\n const fragment = document.createDocumentFragment();\n fragment.appendChild(startMarker);\n fragment.appendChild(endMarker);\n\n const [retryCount, setRetryCount] = createSignal(0);\n let currentNode: Node | null = null;\n\n internalEffect(() => {\n // Subscribe to retryCount so retry() triggers re-run\n retryCount();\n\n const parent = startMarker.parentNode;\n if (!parent) return;\n\n // Remove current\n if (currentNode && currentNode.parentNode === parent) {\n parent.removeChild(currentNode);\n }\n\n try {\n currentNode = tryFn();\n } catch (e) {\n const error = e instanceof Error ? e : new Error(String(e));\n const retry = () => setRetryCount(c => c + 1);\n currentNode = catchFn(error, retry);\n }\n\n if (currentNode) {\n parent.insertBefore(currentNode, endMarker);\n }\n });\n\n return fragment;\n}\n","/**\n * Forma DOM - Suspense\n *\n * A Suspense boundary that shows fallback content while async resources\n * inside the children function are loading. Uses comment markers\n * (like createShow, createList) for zero-wrapper rendering.\n *\n * When all resources resolve, the fallback is swapped for the real content.\n * If a resource errors, the fallback remains (pair with createErrorBoundary\n * for error handling).\n *\n * SolidJS equivalent: <Suspense fallback={}>\n */\n\nimport { createSignal, internalEffect } from 'forma/reactive';\nimport {\n type SuspenseContext,\n pushSuspenseContext,\n popSuspenseContext,\n} from 'forma/reactive/suspense-context';\n\n// Re-export context utilities so consumers can import from dom/suspense\nexport { getSuspenseContext, pushSuspenseContext, popSuspenseContext } from 'forma/reactive/suspense-context';\nexport type { SuspenseContext } from 'forma/reactive/suspense-context';\n\n// ---------------------------------------------------------------------------\n// createSuspense\n// ---------------------------------------------------------------------------\n\n/**\n * Create a Suspense boundary that shows fallback content while async resources\n * inside the children function are loading.\n *\n * Uses comment markers: `<!--forma-suspense-->` / `<!--/forma-suspense-->`\n *\n * When all resources resolve, the fallback is swapped for the real content.\n * If a resource errors, the fallback remains (pair with createErrorBoundary\n * for errors).\n *\n * ```ts\n * const frag = createSuspense(\n * () => h('div', null, 'Loading...'),\n * () => {\n * const data = createResource(source, fetcher);\n * return h('div', null, () => data()?.name ?? '');\n * },\n * );\n * container.appendChild(frag);\n * ```\n */\nexport function createSuspense(\n fallback: () => Node,\n children: () => Node,\n): DocumentFragment {\n const startMarker = document.createComment('forma-suspense');\n const endMarker = document.createComment('/forma-suspense');\n const fragment = document.createDocumentFragment();\n fragment.appendChild(startMarker);\n fragment.appendChild(endMarker);\n\n const [pending, setPending] = createSignal(0);\n let currentNode: Node | null = null;\n let resolvedNode: Node | null = null;\n let fallbackNode: Node | null = null;\n\n const ctx: SuspenseContext = {\n increment() { setPending(p => p + 1); },\n decrement() { setPending(p => Math.max(0, p - 1)); },\n };\n\n // Render children within the Suspense context so that any createResource\n // calls inside will register with this boundary.\n pushSuspenseContext(ctx);\n try {\n resolvedNode = children();\n } finally {\n popSuspenseContext();\n }\n\n // Reactively swap between fallback and children based on pending count\n internalEffect(() => {\n const parent = startMarker.parentNode;\n if (!parent) return;\n\n const isPending = pending() > 0;\n const newNode = isPending ? (fallbackNode ??= fallback()) : resolvedNode;\n\n if (newNode === currentNode) return;\n\n // Remove current node\n if (currentNode && currentNode.parentNode === parent) {\n parent.removeChild(currentNode);\n }\n\n // Insert new node\n if (newNode) {\n parent.insertBefore(newNode, endMarker);\n }\n\n currentNode = newNode;\n });\n\n return fragment;\n}\n","/**\n * Forma DOM - Island Activation\n *\n * Discovers SSR-rendered islands via [data-forma-island] attributes,\n * loads props (inline or script_tag), and hydrates each island inside\n * an independent createRoot scope with try/catch error isolation.\n */\n\nimport { createRoot, __DEV__ } from 'forma/reactive';\nimport { hydrateIsland } from './hydrate.js';\n\n/**\n * Function that hydrates an island.\n *\n * @param el The root element of the island (`[data-forma-island]`).\n * Useful for layout measurement, focus management, CSS class\n * toggling, third-party library init, or reading extra `data-*`\n * attributes from the server-rendered shell.\n * @param props Parsed props from `data-forma-props` (inline or script block),\n * or `null` if no props were provided.\n * @returns A component tree (from `h()` calls) for descriptor-based\n * hydration, or `undefined` for imperative islands that set up\n * their own effects.\n */\nexport type IslandHydrateFn = (el: HTMLElement, props: Record<string, unknown> | null) => unknown;\n\nconst FORBIDDEN_PROP_KEYS = new Set(['__proto__', 'constructor', 'prototype']);\n\nfunction sanitizeProps(obj: Record<string, unknown>): Record<string, unknown> {\n for (const key of FORBIDDEN_PROP_KEYS) {\n if (key in obj) delete (obj as any)[key];\n }\n return obj;\n}\n\n/**\n * Load props for an island from either inline attribute or shared script block.\n */\nfunction loadIslandProps(\n root: HTMLElement,\n id: number,\n sharedProps: Record<string, unknown> | null,\n): Record<string, unknown> | null {\n // Mode 1: Inline (small props, < 1KB)\n const inline = root.getAttribute('data-forma-props');\n if (inline) {\n return sanitizeProps(JSON.parse(inline));\n }\n\n // Mode 2: Script tag (1KB–50KB, pre-parsed)\n if (sharedProps && String(id) in sharedProps) {\n return sanitizeProps((sharedProps as any)[String(id)] as Record<string, unknown>);\n }\n\n // No props — island creates its own state\n return null;\n}\n\n/**\n * Discover and activate all SSR-rendered islands on the page.\n *\n * Each island is activated inside its own createRoot scope with try/catch\n * isolation — a broken island never takes down its siblings.\n *\n * @param registry Map of component names to hydration functions.\n */\nexport function activateIslands(registry: Record<string, IslandHydrateFn>): void {\n // Parse shared props once before the loop\n const scriptBlock = document.getElementById('__forma_islands');\n const sharedProps: Record<string, unknown> | null =\n scriptBlock ? JSON.parse(scriptBlock.textContent!) : null;\n\n const islands = document.querySelectorAll<HTMLElement>('[data-forma-island]');\n\n for (const root of islands) {\n const id = parseInt(root.getAttribute('data-forma-island')!, 10);\n const componentName = root.getAttribute('data-forma-component')!;\n const hydrateFn = registry[componentName];\n\n if (!hydrateFn) {\n if (__DEV__) console.warn(`[forma] No hydrate function for island \"${componentName}\" (id=${id})`);\n root.setAttribute('data-forma-status', 'error');\n continue;\n }\n\n const trigger = root.getAttribute('data-forma-hydrate') || 'load';\n\n if (trigger === 'visible') {\n // Defer hydration until island enters the viewport\n const observer = new IntersectionObserver(\n (entries) => {\n for (const entry of entries) {\n if (!entry.isIntersecting) continue;\n observer.disconnect();\n hydrateIslandRoot(root, id, componentName, hydrateFn, sharedProps);\n }\n },\n { rootMargin: '200px' },\n );\n observer.observe(root);\n } else if (trigger === 'idle') {\n const hydrate = () => hydrateIslandRoot(root, id, componentName, hydrateFn, sharedProps);\n if (typeof requestIdleCallback === 'function') {\n requestIdleCallback(hydrate);\n } else {\n setTimeout(hydrate, 200);\n }\n } else if (trigger === 'interaction') {\n const hydrate = () => {\n root.removeEventListener('pointerdown', hydrate, true);\n root.removeEventListener('focusin', hydrate, true);\n hydrateIslandRoot(root, id, componentName, hydrateFn, sharedProps);\n };\n root.addEventListener('pointerdown', hydrate, { capture: true, once: true });\n root.addEventListener('focusin', hydrate, { capture: true, once: true });\n } else {\n // load (default) — hydrate immediately\n hydrateIslandRoot(root, id, componentName, hydrateFn, sharedProps);\n }\n }\n}\n\n/**\n * Dispose a single island, tearing down its reactive root and all effects.\n *\n * Safe to call multiple times (idempotent). Sets `data-forma-status` to\n * `\"disposed\"` so the island can be distinguished from active/error states.\n */\nexport function deactivateIsland(el: HTMLElement): void {\n const dispose = (el as any).__formaDispose;\n if (typeof dispose === 'function') {\n dispose();\n delete (el as any).__formaDispose;\n el.setAttribute('data-forma-status', 'disposed');\n }\n}\n\n/**\n * Dispose ALL active islands under a root element (or the whole document).\n *\n * Use this when swapping module content — e.g., replacing the contents of\n * a `<forma-stage>` Shadow DOM during AI generation. Prevents leaked effects\n * and event listeners from accumulating across swaps.\n */\nexport function deactivateAllIslands(root: Element | Document = document): void {\n const islands = root.querySelectorAll<HTMLElement>('[data-forma-status=\"active\"]');\n for (const island of islands) {\n deactivateIsland(island);\n }\n}\n\n/** Hydrate a single island root with error isolation. */\nfunction hydrateIslandRoot(\n root: HTMLElement,\n id: number,\n componentName: string,\n hydrateFn: IslandHydrateFn,\n sharedProps: Record<string, unknown> | null,\n): void {\n try {\n const props = loadIslandProps(root, id, sharedProps);\n root.setAttribute('data-forma-status', 'hydrating');\n\n // hydrateIsland may replace the shell element with the component's own\n // root element (CSR fallback for empty islands). Track the active root.\n let activeRoot: Element = root;\n createRoot((dispose) => {\n activeRoot = hydrateIsland(() => hydrateFn(root, props), root);\n (activeRoot as any).__formaDispose = dispose;\n });\n\n activeRoot.setAttribute('data-forma-status', 'active');\n } catch (err) {\n if (__DEV__) console.error(`[forma] Island \"${componentName}\" (id=${id}) failed:`, err);\n root.setAttribute('data-forma-status', 'error');\n }\n}\n","/**\n * Forma Component - Define\n *\n * Component definition system where the setup function runs ONCE.\n * Reactivity comes from signals, not re-rendering.\n * Backed by alien-signals via forma/reactive.\n */\n\nimport { reportError } from '../reactive/dev.js';\n\n// ---------------------------------------------------------------------------\n// Types\n// ---------------------------------------------------------------------------\n\ntype CleanupFn = () => void;\ntype SetupFn = () => HTMLElement | DocumentFragment;\n\ninterface ComponentDef {\n setup: SetupFn;\n name?: string;\n}\n\n// ---------------------------------------------------------------------------\n// Lifecycle context stack\n// ---------------------------------------------------------------------------\n\ninterface LifecycleContext {\n /** Dispose functions for all effects created during setup. */\n disposers: (() => void)[];\n /** Callbacks registered via onMount(). */\n mountCallbacks: (() => void | CleanupFn)[];\n /** Callbacks registered via onUnmount(). */\n unmountCallbacks: (() => void)[];\n}\n\nlet currentLifecycleContext: LifecycleContext | null = null;\nconst lifecycleStack: (LifecycleContext | null)[] = [];\n\nfunction pushLifecycleContext(ctx: LifecycleContext): void {\n lifecycleStack.push(currentLifecycleContext);\n currentLifecycleContext = ctx;\n}\n\nfunction popLifecycleContext(): void {\n currentLifecycleContext = lifecycleStack.pop() ?? null;\n}\n\n// ---------------------------------------------------------------------------\n// Public API - Lifecycle hooks\n// ---------------------------------------------------------------------------\n\n/**\n * Register a callback that runs after the component's setup completes.\n * If the callback returns a function, that function is called on unmount.\n * Must be called inside a setup function.\n */\nexport function onMount(fn: () => void | CleanupFn): void {\n if (currentLifecycleContext === null) {\n throw new Error('onMount() must be called inside a component setup function');\n }\n currentLifecycleContext.mountCallbacks.push(fn);\n}\n\n/**\n * Register a callback that runs when the component is disposed.\n * Must be called inside a setup function.\n */\nexport function onUnmount(fn: () => void): void {\n if (currentLifecycleContext === null) {\n throw new Error('onUnmount() must be called inside a component setup function');\n }\n currentLifecycleContext.unmountCallbacks.push(fn);\n}\n\n// ---------------------------------------------------------------------------\n// Internal: symbol for attaching dispose to DOM nodes\n// ---------------------------------------------------------------------------\n\nconst DISPOSE_KEY = Symbol('forma:component:dispose');\n\ninterface DisposableNode {\n [DISPOSE_KEY]?: () => void;\n}\n\n// ---------------------------------------------------------------------------\n// Public API - defineComponent\n// ---------------------------------------------------------------------------\n\n/**\n * Define a component from a setup function or definition object.\n * Returns a factory function that, when called, produces a DOM element\n * with attached lifecycle and disposal logic.\n *\n * The setup function runs ONCE per factory call. Reactivity is driven\n * by signals, not by re-running setup.\n */\nexport function defineComponent(\n setupOrDef: SetupFn | ComponentDef,\n): () => HTMLElement | DocumentFragment {\n const setup: SetupFn =\n typeof setupOrDef === 'function' ? setupOrDef : setupOrDef.setup;\n const name: string | undefined =\n typeof setupOrDef === 'function' ? undefined : setupOrDef.name;\n\n return function componentFactory(): HTMLElement | DocumentFragment {\n // Create a fresh lifecycle context for this component instance\n const ctx: LifecycleContext = {\n disposers: [],\n mountCallbacks: [],\n unmountCallbacks: [],\n };\n\n // Push lifecycle context so onMount/onUnmount calls register here\n pushLifecycleContext(ctx);\n\n let dom: HTMLElement | DocumentFragment;\n try {\n dom = setup();\n } finally {\n popLifecycleContext();\n }\n\n // Build the dispose function that tears down the entire component\n const dispose = (): void => {\n // Run onUnmount callbacks\n for (const cb of ctx.unmountCallbacks) {\n try {\n cb();\n } catch (e) {\n reportError(e, 'onUnmount');\n }\n }\n\n // Dispose all effects\n for (const d of ctx.disposers) {\n try {\n d();\n } catch (e) {\n reportError(e, 'component disposer');\n }\n }\n\n // Clean up\n ctx.disposers.length = 0;\n ctx.mountCallbacks.length = 0;\n ctx.unmountCallbacks.length = 0;\n };\n\n // Attach dispose to the DOM node so callers can tear it down\n (dom as unknown as DisposableNode)[DISPOSE_KEY] = dispose;\n\n // Run mount callbacks (synchronously, after setup completes)\n // If a mount callback returns a cleanup, register it as an unmount callback\n for (const cb of ctx.mountCallbacks) {\n try {\n const cleanup = cb();\n if (typeof cleanup === 'function') {\n ctx.unmountCallbacks.push(cleanup);\n }\n } catch (e) {\n reportError(e, 'onMount');\n }\n }\n\n return dom;\n };\n}\n\n/**\n * Dispose a component that was created via defineComponent.\n * This runs all onUnmount callbacks and disposes all tracked effects.\n */\nexport function disposeComponent(dom: HTMLElement | DocumentFragment): void {\n const disposable = dom as unknown as DisposableNode;\n if (typeof disposable[DISPOSE_KEY] === 'function') {\n disposable[DISPOSE_KEY]();\n delete disposable[DISPOSE_KEY];\n }\n}\n\n/**\n * Track an effect disposal within the current component's lifecycle.\n * Call this inside a setup function to ensure effects are cleaned up\n * when the component is disposed.\n */\nexport function trackDisposer(dispose: () => void): void {\n if (currentLifecycleContext !== null) {\n currentLifecycleContext.disposers.push(dispose);\n }\n}\n","/**\n * Forma Component - Context\n *\n * Dependency injection via stack-based context.\n * Simpler than React's Provider component tree: provide() pushes a value,\n * inject() reads the top, component teardown pops automatically.\n * Zero dependencies -- native browser APIs only.\n */\n\n// ---------------------------------------------------------------------------\n// Types\n// ---------------------------------------------------------------------------\n\nexport interface Context<T> {\n /** Unique identifier for this context. */\n readonly id: symbol;\n /** Value returned when no provider is active. */\n readonly defaultValue: T;\n}\n\n// ---------------------------------------------------------------------------\n// Internal storage\n// ---------------------------------------------------------------------------\n\n/**\n * Per-context value stacks.\n * Each context id maps to a stack of provided values.\n * The top of the stack is the \"current\" value.\n */\nconst contextStacks = new Map<symbol, unknown[]>();\n\n// ---------------------------------------------------------------------------\n// Public API\n// ---------------------------------------------------------------------------\n\n/**\n * Create a new context with a default value.\n *\n * ```ts\n * const ThemeCtx = createContext('light');\n * ```\n */\nexport function createContext<T>(defaultValue: T): Context<T> {\n return {\n id: Symbol('forma:context'),\n defaultValue,\n };\n}\n\n/**\n * Provide a value for a context.\n * The value is pushed onto the context's stack and will be returned by\n * inject() until it is removed via unprovide() or overridden by a nested provide().\n *\n * ```ts\n * provide(ThemeCtx, 'dark');\n * ```\n */\nexport function provide<T>(ctx: Context<T>, value: T): void {\n let stack = contextStacks.get(ctx.id);\n if (stack === undefined) {\n stack = [];\n contextStacks.set(ctx.id, stack);\n }\n stack.push(value);\n}\n\n/**\n * Read the current value of a context.\n * Returns the most recently provided value, or the default if none was provided.\n *\n * ```ts\n * const theme = inject(ThemeCtx); // 'dark' if provided, else 'light'\n * ```\n */\nexport function inject<T>(ctx: Context<T>): T {\n const stack = contextStacks.get(ctx.id);\n if (stack === undefined || stack.length === 0) {\n return ctx.defaultValue;\n }\n return stack[stack.length - 1] as T;\n}\n\n/**\n * Remove the most recent provided value for a context.\n * Used during component teardown to restore the previous scope.\n *\n * ```ts\n * unprovide(ThemeCtx);\n * ```\n */\nexport function unprovide<T>(ctx: Context<T>): void {\n const stack = contextStacks.get(ctx.id);\n if (stack !== undefined && stack.length > 0) {\n stack.pop();\n // Clean up empty stacks to avoid memory leaks\n if (stack.length === 0) {\n contextStacks.delete(ctx.id);\n }\n }\n}\n","/**\n * Forma State - Store\n *\n * Deep reactive store with path-based signal granularity.\n * Every property path (e.g. `user.name`, `items.0.done`) gets its own signal,\n * so only effects that read a specific path are notified when it changes.\n *\n * Inspired by SolidJS's createStore and Vue's reactive(), with:\n * - Lazy proxy wrapping (child objects proxied on first access)\n * - Structural sharing (replacing an object invalidates child signals)\n * - Array mutation batching (push/pop/splice/sort etc. batch their signals)\n *\n * Backed by alien-signals via forma/reactive.\n */\n\nimport { createSignal, batch, untrack } from 'forma/reactive';\n\n// ---------------------------------------------------------------------------\n// Types\n// ---------------------------------------------------------------------------\n\ntype SignalPair = [get: () => unknown, set: (v: unknown) => void];\n\ntype StoreSetter<T extends object> = (\n partial: Partial<T> | ((prev: T) => Partial<T>),\n) => void;\n\n// ---------------------------------------------------------------------------\n// Symbols\n// ---------------------------------------------------------------------------\n\n/** Access the underlying raw (unproxied) object from a store proxy. */\nconst RAW = Symbol('forma-raw');\n\n/** Marker: true on every store proxy so we can detect them. */\nconst PROXY = Symbol('forma-proxy');\n\n// ---------------------------------------------------------------------------\n// Helpers\n// ---------------------------------------------------------------------------\n\nconst ARRAY_MUTATORS = new Set([\n 'push',\n 'pop',\n 'shift',\n 'unshift',\n 'splice',\n 'sort',\n 'reverse',\n 'fill',\n 'copyWithin',\n]);\n\nfunction isPlainObject(v: unknown): v is Record<string, unknown> {\n if (v == null || typeof v !== 'object') return false;\n const proto = Object.getPrototypeOf(v);\n return proto === Object.prototype || proto === null || Array.isArray(v);\n}\n\nfunction shouldWrap(v: unknown): v is object {\n if (v == null || typeof v !== 'object') return false;\n // Don't wrap special built-ins (Date, RegExp, Map, Set, etc.)\n if (v instanceof Date || v instanceof RegExp || v instanceof Map ||\n v instanceof Set || v instanceof WeakMap || v instanceof WeakSet ||\n v instanceof Error || v instanceof Promise) {\n return false;\n }\n // Already a store proxy — no double wrapping\n if ((v as any)[PROXY]) return false;\n return true;\n}\n\n// ---------------------------------------------------------------------------\n// Deep-clone helper (used for functional setter snapshots)\n// ---------------------------------------------------------------------------\n\nfunction deepClone(obj: unknown, seen?: WeakSet<object>): unknown {\n if (obj === null || typeof obj !== 'object') return obj;\n if (!seen) seen = new WeakSet();\n if (seen.has(obj as object)) return obj; // circular — return ref as-is\n seen.add(obj as object);\n if (Array.isArray(obj)) return obj.map(item => deepClone(item, seen));\n const out: Record<string, unknown> = {};\n for (const key of Object.keys(obj as Record<string, unknown>)) {\n out[key] = deepClone((obj as any)[key], seen);\n }\n return out;\n}\n\n// ---------------------------------------------------------------------------\n// Public API\n// ---------------------------------------------------------------------------\n\n/**\n * Create a deep reactive store.\n *\n * Returns a tuple of `[getter proxy, setter function]`.\n * The getter proxy tracks reads at every property path via dedicated signals.\n * Setting a property (either via `setState()` or direct mutation like\n * `state.user.name = 'Bob'`) only notifies effects that actually read that\n * specific path.\n *\n * ```ts\n * const [state, setState] = createStore({\n * count: 0,\n * user: { name: 'Alice', age: 30 },\n * items: [{ text: 'Buy milk', done: false }],\n * });\n *\n * // Fine-grained reads\n * state.user.name; // tracked at path \"user.name\"\n * state.items[0].done; // tracked at path \"items.0.done\"\n *\n * // Setter API (batched)\n * setState({ count: 1 });\n * setState(prev => ({ count: prev.count + 1 }));\n *\n * // Direct mutation (via Proxy set trap)\n * state.user.name = 'Bob'; // only \"user.name\" subscribers notified\n * state.items[0].done = true;\n *\n * // Array mutations\n * state.items.push({ text: 'Walk dog', done: false });\n * ```\n *\n * **Limitation:** `Object.keys(state)`, `for...in`, and spread (`{...state}`)\n * are NOT reactive. Adding or removing a property will not trigger effects\n * that iterated over keys. Use signals or explicit arrays for collections\n * that need to react to membership changes.\n */\nexport function createStore<T extends object>(\n initial: T,\n): [get: T, set: StoreSetter<T>] {\n // -------------------------------------------------------------------------\n // Signal-per-path map\n // -------------------------------------------------------------------------\n\n /** Map of dot-separated paths -> signal pairs. */\n const signals = new Map<string, SignalPair>();\n\n /** Parent path -> set of direct child paths for O(1) child invalidation. */\n const children = new Map<string, Set<string>>();\n\n /**\n * Register a signal path with its parent in the adjacency map.\n * This allows walking the tree instead of scanning all signals.\n */\n function registerChild(path: string): void {\n const lastDot = path.lastIndexOf('.');\n if (lastDot === -1) return; // root-level, no parent\n const parentPath = path.substring(0, lastDot);\n let set = children.get(parentPath);\n if (!set) { set = new Set(); children.set(parentPath, set); }\n set.add(path);\n }\n\n /**\n * Get or create the signal for a given path.\n * When creating, seeds with `initialValue`.\n */\n function getSignal(path: string, initialValue?: unknown): SignalPair {\n let pair = signals.get(path);\n if (!pair) {\n pair = createSignal<unknown>(initialValue) as SignalPair;\n signals.set(path, pair);\n registerChild(path);\n }\n return pair;\n }\n\n // -------------------------------------------------------------------------\n // Proxy cache (raw object -> proxy)\n // -------------------------------------------------------------------------\n\n /**\n * WeakMap so proxies for child objects are reused as long as the raw object\n * is alive. When an object is replaced, the old entry is GC'd naturally.\n */\n const proxyCache = new WeakMap<object, object>();\n\n // -------------------------------------------------------------------------\n // Invalidation\n // -------------------------------------------------------------------------\n\n /**\n * Recursively delete all child signals using the adjacency map.\n * Called when an entire sub-tree is replaced so stale signals are not reused.\n * O(k) where k = number of descendant signals, instead of O(n) over all signals.\n */\n function invalidateChildren(parentPath: string): void {\n const childSet = children.get(parentPath);\n if (!childSet) return;\n for (const childPath of childSet) {\n // Recursively invalidate grandchildren first\n invalidateChildren(childPath);\n // Remove the signal itself\n signals.delete(childPath);\n // Clean up this child's entry in the adjacency map\n children.delete(childPath);\n }\n // Clear the parent's children set (all children have been removed)\n childSet.clear();\n }\n\n // -------------------------------------------------------------------------\n // Proxy factory (lazy, recursive)\n // -------------------------------------------------------------------------\n\n function wrap(raw: object, basePath: string): object {\n // Primitives / non-wrappable values pass through\n if (!shouldWrap(raw)) return raw;\n\n // Return cached proxy if we already have one for this raw object\n const cached = proxyCache.get(raw);\n if (cached) return cached;\n\n const isArr = Array.isArray(raw);\n // Pre-compute the path prefix to avoid repeated string concatenation in hot paths\n const basePrefix = basePath ? basePath + '.' : '';\n\n // Inline cache: skip Map lookup when the same key is accessed repeatedly\n // (very common in render loops and effects that read the same property)\n let lastKey: string = '';\n let lastSignal: SignalPair | undefined;\n\n const proxy: object = new Proxy(raw, {\n // -------------------------------------------------------------------\n // GET\n // -------------------------------------------------------------------\n get(target: any, prop: PropertyKey, receiver: unknown): unknown {\n // Escape hatches\n if (prop === RAW) return target;\n if (prop === PROXY) return true;\n\n // Symbols pass through (Symbol.iterator, Symbol.toPrimitive, etc.)\n if (typeof prop === 'symbol') {\n return Reflect.get(target, prop, receiver);\n }\n\n const key = String(prop);\n // Cache-friendly path construction: avoid template literals in hot path\n const childPath = basePrefix + key;\n\n // ------------------------------------------------------------------\n // Array mutator methods — wrap to batch signal updates\n // ------------------------------------------------------------------\n if (isArr && ARRAY_MUTATORS.has(key)) {\n return (...args: unknown[]) => {\n let result: unknown;\n batch(() => {\n // Unwrap proxy arguments (e.g. pushing a store proxy)\n const rawArgs = args.map((a) =>\n a != null && typeof a === 'object' && (a as any)[RAW]\n ? (a as any)[RAW]\n : a,\n );\n result = (target as any)[key].apply(target, rawArgs);\n\n // Invalidate all child paths so they recreate from the\n // mutated raw array on next access.\n invalidateChildren(basePath);\n\n // Notify the length signal\n const [, setLen] = getSignal(\n basePrefix + 'length',\n (target as unknown[]).length,\n );\n setLen((target as unknown[]).length);\n });\n return result;\n };\n }\n\n // ------------------------------------------------------------------\n // Array `length` — special-case so it's always tracked\n // ------------------------------------------------------------------\n if (isArr && key === 'length') {\n const [getter] = getSignal(childPath, target.length);\n getter(); // subscribe\n return target.length;\n }\n\n // ------------------------------------------------------------------\n // Regular property access\n // ------------------------------------------------------------------\n const value = Reflect.get(target, prop);\n\n // Inline cache: if same key as last access, skip Map lookup\n let pair: SignalPair;\n if (key === lastKey && lastSignal) {\n pair = lastSignal;\n } else {\n pair = getSignal(childPath, value);\n lastKey = key;\n lastSignal = pair;\n }\n\n pair[0](); // subscribe to this path\n\n // Lazily wrap child objects/arrays\n if (shouldWrap(value)) {\n return wrap(value, childPath);\n }\n\n return value;\n },\n\n // -------------------------------------------------------------------\n // SET\n // -------------------------------------------------------------------\n set(target: any, prop: PropertyKey, value: unknown): boolean {\n if (typeof prop === 'symbol') {\n return Reflect.set(target, prop, value);\n }\n\n const key = String(prop);\n const childPath = basePrefix + key;\n\n // Unwrap if the value being set is itself a proxy\n const rawValue =\n value != null && typeof value === 'object' && (value as any)[RAW]\n ? (value as any)[RAW]\n : value;\n\n // Write to the underlying object\n Reflect.set(target, prop, rawValue);\n\n // If we're replacing with an object, invalidate all child signals\n // and evict the old proxy so sub-paths are recreated on next access.\n if (rawValue != null && typeof rawValue === 'object') {\n invalidateChildren(childPath);\n // Remove cached proxy for the old value so a fresh one is created\n // on the next access.\n }\n\n // Update the length signal when setting indexed array elements\n if (isArr && key !== 'length') {\n const lengthPath = basePrefix + 'length';\n const lenPair = signals.get(lengthPath);\n if (lenPair) {\n lenPair[1](target.length);\n }\n }\n\n // Notify (or create) the signal for this path\n const [, setter] = getSignal(childPath, rawValue);\n setter(rawValue);\n\n return true;\n },\n\n // -------------------------------------------------------------------\n // HAS — track membership checks\n // -------------------------------------------------------------------\n has(target: any, prop: PropertyKey): boolean {\n if (typeof prop === 'symbol') {\n return Reflect.has(target, prop);\n }\n const key = String(prop);\n const childPath = basePrefix + key;\n // Subscribe so that `'x' in state` is tracked\n const [getter] = getSignal(childPath, Reflect.get(target, prop));\n getter();\n return Reflect.has(target, prop);\n },\n\n // -------------------------------------------------------------------\n // OWNKEYS — return keys from the raw target\n // -------------------------------------------------------------------\n ownKeys(target: any): (string | symbol)[] {\n return Reflect.ownKeys(target);\n },\n\n // -------------------------------------------------------------------\n // GETOWNPROPERTYDESCRIPTOR — needed for Object.keys / spread / ...\n // -------------------------------------------------------------------\n getOwnPropertyDescriptor(target: any, prop: PropertyKey) {\n return Object.getOwnPropertyDescriptor(target, prop);\n },\n\n // -------------------------------------------------------------------\n // DELETEPROPERTY — clean up signals when a key is removed\n // -------------------------------------------------------------------\n deleteProperty(target: any, prop: PropertyKey): boolean {\n if (typeof prop === 'symbol') {\n return Reflect.deleteProperty(target, prop);\n }\n\n const key = String(prop);\n const childPath = basePrefix + key;\n\n const result = Reflect.deleteProperty(target, prop);\n\n // Clean up the signal for this path and all children via adjacency map\n invalidateChildren(childPath);\n signals.delete(childPath);\n\n // Remove from parent's children set in the adjacency map\n const parentPath = basePath;\n if (parentPath !== undefined) {\n const parentSet = children.get(parentPath);\n if (parentSet) {\n parentSet.delete(childPath);\n if (parentSet.size === 0) children.delete(parentPath);\n }\n }\n // Clean up the deleted path's own children entry\n children.delete(childPath);\n\n return result;\n },\n });\n\n proxyCache.set(raw, proxy);\n return proxy;\n }\n\n // -------------------------------------------------------------------------\n // Root proxy\n // -------------------------------------------------------------------------\n\n const rootProxy = wrap(initial, '') as T;\n\n // -------------------------------------------------------------------------\n // Snapshot (for functional setter)\n // -------------------------------------------------------------------------\n\n /**\n * Produce a plain-object snapshot of the store's current state.\n * Reads are untracked so calling `setState(prev => ...)` inside an effect\n * does not create additional subscriptions.\n */\n function getCurrentSnapshot(): T {\n return untrack(() => deepClone(initial) as T);\n }\n\n // -------------------------------------------------------------------------\n // Setter\n // -------------------------------------------------------------------------\n\n const setter: StoreSetter<T> = (\n partial: Partial<T> | ((prev: T) => Partial<T>),\n ) => {\n // Resolve functional updates by snapshotting current state\n const updates: Partial<T> =\n typeof partial === 'function' ? partial(getCurrentSnapshot()) : partial;\n\n // Batch all top-level key writes so effects run only once\n batch(() => {\n for (const key of Object.keys(updates) as (keyof T & string)[]) {\n (rootProxy as Record<string, unknown>)[key] = (updates as Record<string, unknown>)[key];\n }\n });\n };\n\n return [rootProxy, setter];\n}\n","/**\n * Forma State - History\n *\n * Undo/redo for any signal. Tracks changes and maintains undo/redo stacks\n * with reactive canUndo/canRedo signals.\n * Zero dependencies -- native browser APIs only.\n */\n\nimport { createSignal, internalEffect, batch } from 'forma/reactive';\n\n// ---------------------------------------------------------------------------\n// Types\n// ---------------------------------------------------------------------------\n\nexport interface HistoryControls<T> {\n /** Undo the last change, restoring the previous value. */\n undo: () => void;\n /** Redo the last undone change. */\n redo: () => void;\n /** Reactive getter: true if undo is available. */\n canUndo: () => boolean;\n /** Reactive getter: true if redo is available. */\n canRedo: () => boolean;\n /** Reactive getter: the full history stack (past + current + future). */\n history: () => T[];\n /** Reactive getter: current position in the history stack (0-based). */\n cursor: () => number;\n /** Clear all history, keeping only the current value. */\n clear: () => void;\n}\n\n// ---------------------------------------------------------------------------\n// Public API\n// ---------------------------------------------------------------------------\n\n/**\n * Create undo/redo history tracking for a signal.\n *\n * ```ts\n * const [count, setCount] = createSignal(0);\n * const h = createHistory([count, setCount], { maxLength: 50 });\n *\n * setCount(1);\n * setCount(2);\n * h.undo(); // count() === 1\n * h.redo(); // count() === 2\n * h.canUndo(); // true (reactive)\n * ```\n */\nexport function createHistory<T>(\n source: [get: () => T, set: (v: T) => void],\n options?: { maxLength?: number },\n): HistoryControls<T> {\n const [sourceGet, sourceSet] = source;\n const maxLength = options?.maxLength ?? 100;\n\n // ---------- Internal mutable state (not signals) ----------\n // We use plain arrays/numbers to avoid creating signal dependencies\n // inside the source-tracking effect, which would cause re-entrance issues.\n let _stack: T[] = [sourceGet()];\n let _cursor = 0;\n\n // ---------- Reactive output signals ----------\n // These are signals that external consumers can subscribe to.\n // We update them explicitly after every mutation.\n const [stackSignal, setStackSignal] = createSignal<T[]>([..._stack]);\n const [cursorSignal, setCursorSignal] = createSignal(_cursor);\n // Separate signal for stack length so canRedo only depends on numeric\n // signals and doesn't re-fire when array reference changes but length stays.\n const [stackLenSignal, setStackLenSignal] = createSignal(_stack.length);\n\n /** Sync the reactive output signals with internal mutable state. */\n function syncSignals(): void {\n batch(() => {\n setStackSignal([..._stack]);\n setCursorSignal(_cursor);\n setStackLenSignal(_stack.length);\n });\n }\n\n // Track whether the next source change should be ignored\n // (because it was caused by undo/redo, not an external set).\n let ignoreNext = false;\n let isFirstRun = true;\n\n // Watch the source signal for external changes\n internalEffect(() => {\n const value = sourceGet();\n\n // Skip the initial effect run -- the initial value is already in the stack\n if (isFirstRun) {\n isFirstRun = false;\n return;\n }\n\n if (ignoreNext) {\n ignoreNext = false;\n return;\n }\n\n // New value from an external set: push onto history\n // Discard any \"future\" entries after the current cursor (redo is cleared)\n _stack = _stack.slice(0, _cursor + 1);\n _stack.push(value);\n\n // Enforce maxLength\n if (_stack.length > maxLength) {\n _stack.splice(0, _stack.length - maxLength);\n }\n\n _cursor = _stack.length - 1;\n syncSignals();\n });\n\n // Reactive derived getters\n const canUndo = (): boolean => cursorSignal() > 0;\n const canRedo = (): boolean => cursorSignal() < stackLenSignal() - 1;\n\n const undo = (): void => {\n if (_cursor <= 0) return;\n\n _cursor--;\n ignoreNext = true;\n sourceSet(_stack[_cursor] as T);\n syncSignals();\n };\n\n const redo = (): void => {\n if (_cursor >= _stack.length - 1) return;\n\n _cursor++;\n ignoreNext = true;\n sourceSet(_stack[_cursor] as T);\n syncSignals();\n };\n\n const clear = (): void => {\n const currentValue = sourceGet();\n _stack = [currentValue];\n _cursor = 0;\n syncSignals();\n };\n\n return {\n undo,\n redo,\n canUndo,\n canRedo,\n history: () => stackSignal(),\n cursor: () => cursorSignal(),\n clear,\n };\n}\n","/**\n * Forma State - Persist\n *\n * Auto-persist a signal to localStorage (or any Storage-compatible backend).\n * Reads stored value on creation; writes on every signal change.\n * Zero dependencies -- native browser APIs only.\n */\n\nimport { internalEffect } from 'forma/reactive';\n\n// ---------------------------------------------------------------------------\n// Types\n// ---------------------------------------------------------------------------\n\ninterface PersistOptions<T> {\n /** Storage backend. Defaults to localStorage. */\n storage?: Storage;\n /** Custom serializer. Defaults to JSON.stringify. */\n serialize?: (v: T) => string;\n /** Custom deserializer. Defaults to JSON.parse. */\n deserialize?: (s: string) => T;\n /** Optional validator — return true if the deserialized value is valid. Rejects corrupt/tampered data. */\n validate?: (v: unknown) => v is T;\n}\n\n// ---------------------------------------------------------------------------\n// Public API\n// ---------------------------------------------------------------------------\n\n/**\n * Persist a signal's value to storage.\n *\n * On creation, reads the stored value (if any) and hydrates the signal.\n * Then sets up an effect to write to storage whenever the signal changes.\n *\n * ```ts\n * const [theme, setTheme] = createSignal('light');\n * persist([theme, setTheme], 'app:theme');\n *\n * setTheme('dark'); // auto-saved to localStorage under key 'app:theme'\n * ```\n */\nexport function persist<T>(\n source: [get: () => T, set: (v: T) => void],\n key: string,\n options?: PersistOptions<T>,\n): void {\n const [sourceGet, sourceSet] = source;\n const storage = options?.storage ?? globalThis.localStorage;\n const serialize = options?.serialize ?? JSON.stringify;\n const deserialize = options?.deserialize ?? JSON.parse;\n const validate = options?.validate;\n\n // Step 1: Hydrate from storage (if a value exists)\n try {\n const stored = storage.getItem(key);\n if (stored !== null) {\n const value = deserialize(stored);\n if (!validate || validate(value)) {\n sourceSet(value);\n }\n }\n } catch {\n // Stored data is invalid or storage is unavailable -- ignore and keep\n // the signal's current value.\n }\n\n // Step 2: Set up effect to persist on changes\n internalEffect(() => {\n const value = sourceGet();\n try {\n const serialized = serialize(value);\n storage.setItem(key, serialized);\n } catch {\n // Storage write failed (e.g., quota exceeded) -- silently ignore.\n }\n });\n}\n","// Typed event bus — pub/sub pattern\n\nexport interface EventBus<T extends Record<string, unknown>> {\n on<K extends keyof T>(event: K, handler: (payload: T[K]) => void): () => void;\n once<K extends keyof T>(event: K, handler: (payload: T[K]) => void): () => void;\n emit<K extends keyof T>(event: K, payload: T[K]): void;\n off<K extends keyof T>(event: K, handler: (payload: T[K]) => void): void;\n clear(): void;\n}\n\nexport function createBus<\n T extends Record<string, unknown> = Record<string, unknown>,\n>(): EventBus<T> {\n const listeners = new Map<keyof T, Set<(payload: any) => void>>();\n\n function getHandlers<K extends keyof T>(event: K): Set<(payload: any) => void> {\n let set = listeners.get(event);\n if (!set) {\n set = new Set();\n listeners.set(event, set);\n }\n return set;\n }\n\n function on<K extends keyof T>(\n event: K,\n handler: (payload: T[K]) => void,\n ): () => void {\n const set = getHandlers(event);\n set.add(handler);\n return () => {\n set.delete(handler);\n };\n }\n\n function once<K extends keyof T>(\n event: K,\n handler: (payload: T[K]) => void,\n ): () => void {\n const wrapper = (payload: T[K]) => {\n off(event, wrapper);\n handler(payload);\n };\n return on(event, wrapper);\n }\n\n function emit<K extends keyof T>(event: K, payload: T[K]): void {\n const set = listeners.get(event);\n if (set) {\n // Iterate over a snapshot so removals during emit are safe\n for (const handler of [...set]) {\n try {\n handler(payload);\n } catch (e) {\n console.error(`[forma] Bus handler error on \"${String(event)}\":`, e);\n }\n }\n }\n }\n\n function off<K extends keyof T>(\n event: K,\n handler: (payload: T[K]) => void,\n ): void {\n const set = listeners.get(event);\n if (set) {\n set.delete(handler);\n }\n }\n\n function clear(): void {\n listeners.clear();\n }\n\n return { on, once, emit, off, clear };\n}\n","// Event delegation — single listener on parent, matches children by selector\n\nexport function delegate<K extends keyof HTMLElementEventMap>(\n container: HTMLElement | Document,\n selector: string,\n event: K,\n handler: (e: HTMLElementEventMap[K], matchedEl: HTMLElement) => void,\n options?: AddEventListenerOptions,\n): () => void {\n const listener = (e: Event) => {\n const target = e.target;\n if (!(target instanceof HTMLElement)) return;\n\n const root =\n container instanceof Document ? container.documentElement : container;\n const matched = target.closest(selector);\n\n if (matched instanceof HTMLElement && root.contains(matched)) {\n handler(e as HTMLElementEventMap[K], matched);\n }\n };\n\n container.addEventListener(event, listener, options);\n\n return () => {\n container.removeEventListener(event, listener, options);\n };\n}\n","// Keyboard shortcut handler\n\ntype KeyCombo = string; // e.g., 'ctrl+s', 'shift+enter', 'escape', 'ctrl+shift+z'\n\ninterface KeyOptions {\n target?: EventTarget;\n preventDefault?: boolean;\n}\n\ninterface ParsedCombo {\n ctrl: boolean;\n shift: boolean;\n alt: boolean;\n meta: boolean;\n key: string;\n}\n\nfunction parseCombo(combo: KeyCombo): ParsedCombo {\n const parts = combo.toLowerCase().split('+').map((p) => p.trim());\n const modifiers: ParsedCombo = {\n ctrl: false,\n shift: false,\n alt: false,\n meta: false,\n key: '',\n };\n\n for (const part of parts) {\n switch (part) {\n case 'ctrl':\n case 'control':\n modifiers.ctrl = true;\n break;\n case 'shift':\n modifiers.shift = true;\n break;\n case 'alt':\n modifiers.alt = true;\n break;\n case 'meta':\n case 'cmd':\n case 'command':\n modifiers.meta = true;\n break;\n default:\n modifiers.key = part;\n }\n }\n\n return modifiers;\n}\n\nfunction matchesCombo(e: KeyboardEvent, parsed: ParsedCombo): boolean {\n if (e.ctrlKey !== parsed.ctrl) return false;\n if (e.shiftKey !== parsed.shift) return false;\n if (e.altKey !== parsed.alt) return false;\n if (e.metaKey !== parsed.meta) return false;\n return e.key.toLowerCase() === parsed.key;\n}\n\nexport function onKey(\n combo: KeyCombo,\n handler: (e: KeyboardEvent) => void,\n options?: KeyOptions,\n): () => void {\n const target: EventTarget = options?.target ?? document;\n const shouldPreventDefault = options?.preventDefault ?? true;\n const parsed = parseCombo(combo);\n\n const listener = (e: Event) => {\n if (!(e instanceof KeyboardEvent)) return;\n if (matchesCombo(e, parsed)) {\n if (shouldPreventDefault) {\n e.preventDefault();\n }\n handler(e);\n }\n };\n\n target.addEventListener('keydown', listener);\n\n return () => {\n target.removeEventListener('keydown', listener);\n };\n}\n","// Typed query helpers\n\nexport function $<T extends HTMLElement = HTMLElement>(\n selector: string,\n parent?: ParentNode,\n): T | null {\n return (parent ?? document).querySelector<T>(selector);\n}\n\nexport function $$<T extends HTMLElement = HTMLElement>(\n selector: string,\n parent?: ParentNode,\n): T[] {\n return Array.from((parent ?? document).querySelectorAll<T>(selector));\n}\n","// DOM mutation helpers\n\nexport function addClass(el: HTMLElement, ...classes: string[]): void {\n el.classList.add(...classes);\n}\n\nexport function removeClass(el: HTMLElement, ...classes: string[]): void {\n el.classList.remove(...classes);\n}\n\nexport function toggleClass(\n el: HTMLElement,\n className: string,\n force?: boolean,\n): boolean {\n return el.classList.toggle(className, force);\n}\n\nexport function setStyle(\n el: HTMLElement,\n styles: Partial<CSSStyleDeclaration>,\n): void {\n for (const [key, value] of Object.entries(styles)) {\n if (value !== undefined) {\n (el.style as any)[key] = value;\n }\n }\n}\n\nexport function setAttr(\n el: HTMLElement,\n attrs: Record<string, string | boolean | null>,\n): void {\n for (const [name, value] of Object.entries(attrs)) {\n if (value === false || value === null) {\n el.removeAttribute(name);\n } else if (value === true) {\n el.setAttribute(name, '');\n } else {\n el.setAttribute(name, value);\n }\n }\n}\n\nexport function setText(el: HTMLElement, text: string): void {\n el.textContent = text;\n}\n\n/**\n * Set raw HTML on an element. **No sanitization is performed.**\n *\n * Prefer `setText()` for user-controlled content. Only use this when you\n * trust the HTML source (e.g., server-rendered markup you control).\n *\n * @deprecated Use `setHTMLUnsafe` instead — renamed to signal risk.\n */\nexport function setHTML(el: HTMLElement, html: string): void {\n el.innerHTML = html;\n}\n\n/**\n * Set raw HTML on an element. **No sanitization is performed.**\n *\n * Prefer `setText()` for user-controlled content. Only use this when you\n * trust the HTML source (e.g., server-rendered markup you control).\n */\nexport function setHTMLUnsafe(el: HTMLElement, html: string): void {\n el.innerHTML = html;\n}\n","// DOM traversal helpers\n\nexport function closest<T extends HTMLElement = HTMLElement>(\n el: HTMLElement,\n selector: string,\n): T | null {\n return el.closest<T>(selector);\n}\n\nexport function children<T extends HTMLElement = HTMLElement>(\n el: HTMLElement,\n selector?: string,\n): T[] {\n const all = Array.from(el.children) as HTMLElement[];\n if (!selector) return all as T[];\n return all.filter((child) => child.matches(selector)) as T[];\n}\n\nexport function siblings<T extends HTMLElement = HTMLElement>(\n el: HTMLElement,\n selector?: string,\n): T[] {\n const parentEl = el.parentElement;\n if (!parentEl) return [];\n const all = Array.from(parentEl.children) as HTMLElement[];\n const sibs = all.filter((child) => child !== el);\n if (!selector) return sibs as T[];\n return sibs.filter((child) => child.matches(selector)) as T[];\n}\n\nexport function parent<T extends HTMLElement = HTMLElement>(\n el: HTMLElement,\n): T | null {\n return el.parentElement as T | null;\n}\n\nexport function nextSibling<T extends HTMLElement = HTMLElement>(\n el: HTMLElement,\n selector?: string,\n): T | null {\n let sib = el.nextElementSibling;\n while (sib) {\n if (sib instanceof HTMLElement) {\n if (!selector || sib.matches(selector)) {\n return sib as T;\n }\n }\n sib = sib.nextElementSibling;\n }\n return null;\n}\n\nexport function prevSibling<T extends HTMLElement = HTMLElement>(\n el: HTMLElement,\n selector?: string,\n): T | null {\n let sib = el.previousElementSibling;\n while (sib) {\n if (sib instanceof HTMLElement) {\n if (!selector || sib.matches(selector)) {\n return sib as T;\n }\n }\n sib = sib.previousElementSibling;\n }\n return null;\n}\n","// Observer wrappers — clean API for ResizeObserver, IntersectionObserver, MutationObserver\n\nexport function onResize(\n el: HTMLElement,\n handler: (entry: ResizeObserverEntry) => void,\n): () => void {\n const observer = new ResizeObserver((entries) => {\n for (const entry of entries) {\n handler(entry);\n }\n });\n observer.observe(el);\n return () => {\n observer.disconnect();\n };\n}\n\nexport function onIntersect(\n el: HTMLElement,\n handler: (entry: IntersectionObserverEntry) => void,\n options?: IntersectionObserverInit,\n): () => void {\n const observer = new IntersectionObserver((entries) => {\n for (const entry of entries) {\n handler(entry);\n }\n }, options);\n observer.observe(el);\n return () => {\n observer.disconnect();\n };\n}\n\nexport function onMutation(\n el: HTMLElement,\n handler: (mutations: MutationRecord[]) => void,\n options?: MutationObserverInit,\n): () => void {\n const observer = new MutationObserver((mutations) => {\n handler(mutations);\n });\n observer.observe(el, options ?? { childList: true, subtree: true });\n return () => {\n observer.disconnect();\n };\n}\n","/**\n * Forma Storage - Local\n *\n * Typed localStorage wrapper with graceful error handling.\n * Zero dependencies — native browser APIs only.\n */\n\nimport { TypedStorage, StorageOptions } from './types.js';\n\n/**\n * Create a typed localStorage wrapper for the given key.\n *\n * ```ts\n * const store = createLocalStorage<{ name: string }>('user');\n * store.set({ name: 'Alice' });\n * store.get(); // { name: 'Alice' }\n * store.remove();\n * ```\n */\nexport function createLocalStorage<T>(\n key: string,\n options?: StorageOptions<T>,\n): TypedStorage<T> {\n const serialize = options?.serialize ?? JSON.stringify;\n const deserialize = options?.deserialize ?? JSON.parse;\n const validate = options?.validate;\n\n return {\n key,\n\n get(): T | null {\n try {\n const raw = localStorage.getItem(key);\n if (raw === null) return null;\n const value = deserialize(raw);\n if (validate && !validate(value)) return null;\n return value as T;\n } catch {\n return null;\n }\n },\n\n set(value: T): void {\n try {\n const serialized = serialize(value);\n localStorage.setItem(key, serialized);\n } catch { /* QuotaExceededError or storage disabled — silently ignore */ }\n },\n\n remove(): void {\n localStorage.removeItem(key);\n },\n };\n}\n","/**\n * Forma Storage - Session\n *\n * Typed sessionStorage wrapper with graceful error handling.\n * Zero dependencies — native browser APIs only.\n */\n\nimport { TypedStorage, StorageOptions } from './types.js';\n\n/**\n * Create a typed sessionStorage wrapper for the given key.\n *\n * ```ts\n * const store = createSessionStorage<{ token: string }>('auth');\n * store.set({ token: 'abc123' });\n * store.get(); // { token: 'abc123' }\n * store.remove();\n * ```\n */\nexport function createSessionStorage<T>(\n key: string,\n options?: StorageOptions<T>,\n): TypedStorage<T> {\n const serialize = options?.serialize ?? JSON.stringify;\n const deserialize = options?.deserialize ?? JSON.parse;\n const validate = options?.validate;\n\n return {\n key,\n\n get(): T | null {\n try {\n const raw = sessionStorage.getItem(key);\n if (raw === null) return null;\n const value = deserialize(raw);\n if (validate && !validate(value)) return null;\n return value as T;\n } catch {\n return null;\n }\n },\n\n set(value: T): void {\n try {\n const serialized = serialize(value);\n sessionStorage.setItem(key, serialized);\n } catch { /* QuotaExceededError or storage disabled — silently ignore */ }\n },\n\n remove(): void {\n sessionStorage.removeItem(key);\n },\n };\n}\n","/**\n * Forma Storage - IndexedDB\n *\n * Simplified IndexedDB wrapper with lazy connection and promise-based API.\n * Zero dependencies — native browser APIs only.\n */\n\nexport interface IDBStore<T> {\n get(key: string): Promise<T | undefined>;\n set(key: string, value: T): Promise<void>;\n delete(key: string): Promise<void>;\n getAll(): Promise<T[]>;\n keys(): Promise<string[]>;\n clear(): Promise<void>;\n}\n\n/** Cached database connections keyed by \"dbName::storeName\". */\nconst dbCache = new Map<string, Promise<IDBDatabase>>();\n\n/**\n * Open (or retrieve a cached) IndexedDB database, ensuring the\n * requested object store exists.\n */\nfunction openDB(dbName: string, storeName: string): Promise<IDBDatabase> {\n const cacheKey = `${dbName}::${storeName}`;\n const cached = dbCache.get(cacheKey);\n if (cached) return cached;\n\n const promise = new Promise<IDBDatabase>((resolve, reject) => {\n // First, try opening at the current (or default) version.\n const probe = indexedDB.open(dbName);\n\n probe.onerror = () => reject(probe.error);\n\n probe.onsuccess = () => {\n const db = probe.result;\n if (db.objectStoreNames.contains(storeName)) {\n resolve(db);\n return;\n }\n // Store doesn't exist yet — close and reopen with a version bump.\n const nextVersion = db.version + 1;\n db.close();\n\n const upgrade = indexedDB.open(dbName, nextVersion);\n upgrade.onerror = () => reject(upgrade.error);\n upgrade.onupgradeneeded = () => {\n const upgradedDB = upgrade.result;\n if (!upgradedDB.objectStoreNames.contains(storeName)) {\n upgradedDB.createObjectStore(storeName);\n }\n };\n upgrade.onsuccess = () => resolve(upgrade.result);\n };\n\n probe.onupgradeneeded = () => {\n const db = probe.result;\n if (!db.objectStoreNames.contains(storeName)) {\n db.createObjectStore(storeName);\n }\n };\n });\n\n dbCache.set(cacheKey, promise);\n\n // If the open fails, remove from cache so the next call retries.\n promise.catch(() => {\n dbCache.delete(cacheKey);\n });\n\n return promise;\n}\n\n/**\n * Create a simplified IndexedDB store.\n *\n * ```ts\n * const store = createIndexedDB<User>('myApp', 'users');\n * await store.set('u1', { name: 'Alice' });\n * const user = await store.get('u1'); // { name: 'Alice' }\n * ```\n */\nexport function createIndexedDB<T>(\n dbName: string,\n storeName: string = 'default',\n): IDBStore<T> {\n /** Helper: run a single read/write transaction and return the request result. */\n function withStore<R>(\n mode: IDBTransactionMode,\n fn: (store: IDBObjectStore) => IDBRequest<R>,\n ): Promise<R> {\n return openDB(dbName, storeName).then(\n (db) =>\n new Promise<R>((resolve, reject) => {\n const tx = db.transaction(storeName, mode);\n const store = tx.objectStore(storeName);\n const request = fn(store);\n request.onsuccess = () => resolve(request.result);\n request.onerror = () => reject(request.error);\n }),\n );\n }\n\n return {\n get(key: string): Promise<T | undefined> {\n return withStore('readonly', (store) => store.get(key)) as Promise<T | undefined>;\n },\n\n set(key: string, value: T): Promise<void> {\n return withStore('readwrite', (store) => store.put(value, key)).then(\n () => undefined,\n );\n },\n\n delete(key: string): Promise<void> {\n return withStore('readwrite', (store) => store.delete(key)).then(\n () => undefined,\n );\n },\n\n getAll(): Promise<T[]> {\n return withStore('readonly', (store) => store.getAll()) as Promise<T[]>;\n },\n\n keys(): Promise<string[]> {\n return withStore('readonly', (store) => store.getAllKeys()).then(\n (keys) => keys.map(String),\n );\n },\n\n clear(): Promise<void> {\n return withStore('readwrite', (store) => store.clear()).then(\n () => undefined,\n );\n },\n };\n}\n","/**\n * Forma HTTP - Fetch\n *\n * Typed fetch wrapper with reactive signal integration.\n * Zero dependencies — native browser APIs only.\n */\n\nimport { createSignal, internalEffect } from 'forma/reactive';\n\n// ---------------------------------------------------------------------------\n// Types\n// ---------------------------------------------------------------------------\n\nexport interface FetchOptions<T> extends Omit<RequestInit, 'signal'> {\n base?: string;\n params?: Record<string, string>;\n timeout?: number; // ms, default 30000\n transform?: (data: unknown) => T;\n}\n\nexport interface FetchResult<T> {\n data: () => T | null;\n error: () => Error | null;\n loading: () => boolean;\n refetch: () => Promise<void>;\n abort: () => void;\n}\n\n// ---------------------------------------------------------------------------\n// createFetch — reactive fetch with signals\n// ---------------------------------------------------------------------------\n\n/**\n * Create a reactive fetch that exposes data/error/loading as signals.\n *\n * If `url` is a signal getter (function), an effect auto-refetches when it\n * changes.\n *\n * ```ts\n * const { data, loading, error, refetch, abort } = createFetch<User[]>('/api/users');\n * ```\n */\nexport function createFetch<T>(\n url: string | (() => string),\n options?: FetchOptions<T>,\n): FetchResult<T> {\n const [data, setData] = createSignal<T | null>(null);\n const [error, setError] = createSignal<Error | null>(null);\n const [loading, setLoading] = createSignal<boolean>(false);\n\n let currentController: AbortController | null = null;\n\n /** Resolve the URL string, applying base and params. */\n function resolveURL(): string {\n const raw = typeof url === 'function' ? url() : url;\n const base = options?.base ?? '';\n const fullURL = new URL(raw, base || undefined);\n\n if (options?.params) {\n for (const [key, value] of Object.entries(options.params)) {\n fullURL.searchParams.set(key, value);\n }\n }\n\n return fullURL.toString();\n }\n\n /** Execute a single fetch request. */\n async function execute(): Promise<void> {\n // Abort any in-flight request\n if (currentController) {\n currentController.abort();\n }\n\n currentController = new AbortController();\n const controller = currentController;\n const timeoutMs = options?.timeout ?? 30_000;\n\n // Set up timeout\n const timeoutId = setTimeout(() => controller.abort(), timeoutMs);\n\n setLoading(true);\n setError(null);\n\n try {\n const resolvedURL = resolveURL();\n\n const { base: _base, params: _params, timeout: _timeout, transform, ...fetchInit } =\n options ?? {};\n\n const response = await fetch(resolvedURL, {\n ...fetchInit,\n signal: controller.signal,\n });\n\n if (!response.ok) {\n throw new Error(`HTTP ${response.status}: ${response.statusText}`);\n }\n\n const json: unknown = await response.json();\n const transformed = transform ? transform(json) : (json as T);\n setData(transformed);\n } catch (err) {\n if (err instanceof Error && err.name === 'AbortError') {\n // Ignore aborts — they are intentional or timeouts\n return;\n }\n setError(err instanceof Error ? err : new Error(String(err)));\n } finally {\n clearTimeout(timeoutId);\n // Only update loading if this controller is still current\n if (currentController === controller) {\n currentController = null;\n setLoading(false);\n }\n }\n }\n\n // If url is a reactive getter, set up an effect to auto-refetch.\n if (typeof url === 'function') {\n internalEffect(() => {\n // Read the signal so the effect re-runs when it changes\n url();\n execute();\n });\n } else {\n // Kick off the first request immediately\n execute();\n }\n\n return {\n data,\n error,\n loading,\n refetch: execute,\n abort() {\n if (currentController) {\n currentController.abort();\n }\n },\n };\n}\n\n// ---------------------------------------------------------------------------\n// fetchJSON — simple one-shot helper\n// ---------------------------------------------------------------------------\n\n/**\n * One-shot fetch that returns parsed JSON.\n *\n * ```ts\n * const users = await fetchJSON<User[]>('/api/users');\n * ```\n */\nexport async function fetchJSON<T>(url: string, options?: RequestInit): Promise<T> {\n const response = await fetch(url, options);\n if (!response.ok) {\n throw new Error(`HTTP ${response.status}: ${response.statusText}`);\n }\n return (await response.json()) as T;\n}\n","/**\n * Forma HTTP - Server-Sent Events\n *\n * Reactive SSE wrapper with signal integration.\n * Zero dependencies — native browser APIs only.\n */\n\nimport { createSignal } from 'forma/reactive';\n\n// ---------------------------------------------------------------------------\n// Types\n// ---------------------------------------------------------------------------\n\nexport interface SSEOptions<T = unknown> {\n withCredentials?: boolean;\n headers?: Record<string, string>; // Note: native EventSource does not support custom headers\n /** Custom parser for incoming messages. Defaults to JSON.parse with raw data fallback. */\n parse?: (data: string) => T;\n}\n\nexport interface SSEConnection<T = unknown> {\n data: () => T | null;\n error: () => Event | null;\n connected: () => boolean;\n close: () => void;\n on(event: string, handler: (data: unknown) => void): () => void;\n}\n\n// ---------------------------------------------------------------------------\n// createSSE\n// ---------------------------------------------------------------------------\n\n/**\n * Create a reactive Server-Sent Events connection.\n *\n * ```ts\n * const sse = createSSE<{ message: string }>('/api/events');\n * createEffect(() => {\n * const msg = sse.data();\n * if (msg) console.log(msg.message);\n * });\n * ```\n */\nexport function createSSE<T = unknown>(\n url: string,\n options?: SSEOptions<T>,\n): SSEConnection<T> {\n const [data, setData] = createSignal<T | null>(null);\n const [error, setError] = createSignal<Event | null>(null);\n const [connected, setConnected] = createSignal<boolean>(false);\n\n const source = new EventSource(url, {\n withCredentials: options?.withCredentials ?? false,\n });\n\n source.onopen = () => {\n setConnected(true);\n setError(null);\n };\n\n const parseMessage = options?.parse ?? ((raw: string): T => {\n try { return JSON.parse(raw) as T; }\n catch { return raw as T; }\n });\n\n source.onmessage = (event: MessageEvent) => {\n setData(parseMessage(event.data as string));\n };\n\n source.onerror = (event: Event) => {\n setError(event);\n setConnected(false);\n };\n\n return {\n data,\n error,\n connected,\n\n close(): void {\n source.close();\n setConnected(false);\n },\n\n on(event: string, handler: (data: unknown) => void): () => void {\n const parseEvent = options?.parse ?? ((raw: string) => {\n try { return JSON.parse(raw); }\n catch { return raw; }\n });\n const listener = (e: MessageEvent) => {\n handler(parseEvent(e.data as string));\n };\n source.addEventListener(event, listener as EventListener);\n return () => {\n source.removeEventListener(event, listener as EventListener);\n };\n },\n };\n}\n","/**\n * Forma HTTP - WebSocket\n *\n * Reactive WebSocket wrapper with auto-reconnect and signal integration.\n * Zero dependencies — native browser APIs only.\n */\n\nimport { createSignal } from 'forma/reactive';\n\n// ---------------------------------------------------------------------------\n// Types\n// ---------------------------------------------------------------------------\n\nexport type WSStatus = 'connecting' | 'open' | 'closed' | 'error';\n\nexport interface WSOptions<TReceive = unknown> {\n protocols?: string | string[];\n reconnect?: boolean; // default true\n reconnectInterval?: number; // ms, default 1000\n maxReconnects?: number; // default 5\n /** Custom parser for incoming messages. Defaults to JSON.parse with raw data fallback. */\n parse?: (data: string) => TReceive;\n}\n\nexport interface WSConnection<TSend = unknown, TReceive = unknown> {\n data: () => TReceive | null;\n status: () => WSStatus;\n send(data: TSend): void;\n close(): void;\n on(handler: (data: TReceive) => void): () => void;\n}\n\n// ---------------------------------------------------------------------------\n// createWebSocket\n// ---------------------------------------------------------------------------\n\n/**\n * Create a reactive WebSocket connection with auto-reconnect.\n *\n * ```ts\n * const ws = createWebSocket<string, ChatMessage>('wss://chat.example.com');\n * ws.send('hello');\n * createEffect(() => {\n * const msg = ws.data();\n * if (msg) console.log(msg);\n * });\n * ```\n */\nexport function createWebSocket<TSend = unknown, TReceive = unknown>(\n url: string,\n options?: WSOptions<TReceive>,\n): WSConnection<TSend, TReceive> {\n const shouldReconnect = options?.reconnect ?? true;\n const baseInterval = options?.reconnectInterval ?? 1000;\n const maxReconnects = options?.maxReconnects ?? 5;\n\n const [data, setData] = createSignal<TReceive | null>(null);\n const [status, setStatus] = createSignal<WSStatus>('connecting');\n\n const handlers = new Set<(data: TReceive) => void>();\n\n let socket: WebSocket | null = null;\n let reconnectCount = 0;\n let reconnectTimer: ReturnType<typeof setTimeout> | null = null;\n let permanentlyClosed = false;\n\n function connect(): void {\n if (permanentlyClosed) return;\n\n setStatus('connecting');\n socket = new WebSocket(url, options?.protocols);\n\n socket.onopen = () => {\n setStatus('open');\n reconnectCount = 0; // Reset on successful connection\n };\n\n const parseMessage = options?.parse ?? ((raw: string): TReceive => {\n try { return JSON.parse(raw) as TReceive; }\n catch { return raw as TReceive; }\n });\n\n socket.onmessage = (event: MessageEvent) => {\n const parsed = parseMessage(event.data as string);\n setData(parsed);\n for (const handler of handlers) {\n handler(parsed);\n }\n };\n\n socket.onerror = () => {\n setStatus('error');\n };\n\n socket.onclose = () => {\n if (permanentlyClosed) {\n setStatus('closed');\n return;\n }\n\n setStatus('closed');\n\n if (shouldReconnect && reconnectCount < maxReconnects) {\n // Exponential backoff: baseInterval * 2^reconnectCount\n const delay = baseInterval * Math.pow(2, reconnectCount);\n reconnectCount++;\n reconnectTimer = setTimeout(connect, delay);\n }\n };\n }\n\n // Initiate the first connection\n connect();\n\n return {\n data,\n status,\n\n send(value: TSend): void {\n if (socket && socket.readyState === WebSocket.OPEN) {\n socket.send(JSON.stringify(value));\n }\n },\n\n close(): void {\n permanentlyClosed = true;\n if (reconnectTimer !== null) {\n clearTimeout(reconnectTimer);\n reconnectTimer = null;\n }\n if (socket) {\n socket.close();\n socket = null;\n }\n setStatus('closed');\n },\n\n on(handler: (data: TReceive) => void): () => void {\n handlers.add(handler);\n return () => {\n handlers.delete(handler);\n };\n },\n };\n}\n","/**\n * FormaJS Server - Action\n *\n * Creates an action that wraps a server function with optimistic UI support.\n * The action immediately applies an optimistic update, then reconciles when\n * the server responds (or rolls back on error).\n */\n\nimport { createSignal, batch } from '../reactive/index.js';\nimport type { Resource } from '../reactive/resource.js';\n\n// ---------------------------------------------------------------------------\n// Types\n// ---------------------------------------------------------------------------\n\nexport interface ActionOptions<Args extends unknown[], Result> {\n /**\n * Apply an optimistic update immediately when the action is called.\n * This runs BEFORE the server function.\n * Store whatever you need to roll back in the return value or via closures.\n */\n optimistic?: (...args: Args) => void;\n\n /**\n * Called when the server function resolves successfully.\n * Use this to apply the server result to local state.\n */\n onSuccess?: (result: Result, ...args: Args) => void;\n\n /**\n * Called when the server function rejects.\n * Use this to roll back the optimistic update.\n */\n onError?: (error: unknown, ...args: Args) => void;\n\n /**\n * Resources to refetch after the action completes successfully.\n * Used with single-flight mutations: if the server response includes\n * revalidation data, these resources are updated without a refetch.\n */\n invalidates?: Resource<unknown>[];\n}\n\nexport interface Action<Args extends unknown[], Result> {\n /** Execute the action. */\n (...args: Args): Promise<Result>;\n /** Whether the action is currently in-flight. */\n pending: () => boolean;\n /** The last error from the action (or undefined). */\n error: () => unknown;\n /** Clear the error state. */\n clearError: () => void;\n}\n\n/**\n * Create an action that wraps a server function with optimistic UI.\n *\n * ```ts\n * const addTodo = createAction(\n * serverCreateTodo,\n * {\n * optimistic: (text) => {\n * // Immediately add to local list\n * setTodos(prev => [...prev, { text, done: false, id: 'temp' }]);\n * },\n * onSuccess: (result) => {\n * // Replace temp item with server result\n * setTodos(prev => prev.map(t => t.id === 'temp' ? result : t));\n * },\n * onError: (err, text) => {\n * // Remove the optimistic item\n * setTodos(prev => prev.filter(t => t.id !== 'temp'));\n * },\n * invalidates: [todosResource],\n * },\n * );\n *\n * // Use:\n * await addTodo('Buy milk');\n * ```\n */\nexport function createAction<Args extends unknown[], Result>(\n serverFn: (...args: Args) => Promise<Result>,\n options?: ActionOptions<Args, Result>,\n): Action<Args, Result> {\n const [pending, setPending] = createSignal(false);\n const [error, setError] = createSignal<unknown>(undefined);\n\n const action = async (...args: Args): Promise<Result> => {\n setPending(true);\n setError(undefined);\n\n // Apply optimistic update immediately\n if (options?.optimistic) {\n try {\n batch(() => options.optimistic!(...args));\n } catch {\n // Swallow errors in optimistic callback\n }\n }\n\n try {\n const result = await serverFn(...args);\n\n // Apply success handler\n if (options?.onSuccess) {\n batch(() => options.onSuccess!(result, ...args));\n }\n\n // Revalidate dependent resources\n if (options?.invalidates) {\n for (const resource of options.invalidates) {\n resource.refetch();\n }\n }\n\n setPending(false);\n return result;\n } catch (err) {\n // Apply error/rollback handler\n if (options?.onError) {\n try {\n batch(() => options.onError!(err, ...args));\n } catch {\n // Swallow errors in rollback\n }\n }\n\n setError(err);\n setPending(false);\n throw err;\n }\n };\n\n // Attach signal accessors to the action function\n const typedAction = action as Action<Args, Result>;\n typedAction.pending = pending;\n typedAction.error = error;\n typedAction.clearError = () => setError(undefined);\n\n return typedAction;\n}\n","/**\n * FormaJS Server - Mutation\n *\n * Single-flight mutation pattern: the server response carries both the\n * mutation result AND fresh data for dependent resources in one round trip.\n *\n * Without single-flight:\n * Client -> Server: createTodo(\"Buy milk\")\n * Server -> Client: { id: 1, text: \"Buy milk\" }\n * Client -> Server: GET /api/todos (refetch to update list)\n * Server -> Client: [all todos]\n *\n * With single-flight:\n * Client -> Server: createTodo(\"Buy milk\")\n * Server -> Client: { data: {...}, __revalidate: { \"/api/todos\": [all todos] } }\n * (No second request needed!)\n */\n\nimport type { Resource } from '../reactive/resource.js';\n\n// ---------------------------------------------------------------------------\n// Types\n// ---------------------------------------------------------------------------\n\nexport interface MutationResponse<T> {\n /** The mutation result. */\n data: T;\n /**\n * Fresh data for dependent resources, keyed by resource identifier.\n * When present, the client updates these resources directly instead of refetching.\n */\n __revalidate?: Record<string, unknown>;\n}\n\n// ---------------------------------------------------------------------------\n// Resource registry for revalidation\n// ---------------------------------------------------------------------------\n\nconst resourceRegistry = new Map<string, Resource<unknown>>();\n\n/**\n * Register a resource with a key so it can be revalidated by single-flight mutations.\n *\n * ```ts\n * const todos = createResource(\n * () => true,\n * () => fetch('/api/todos').then(r => r.json()),\n * );\n * registerResource('/api/todos', todos);\n * ```\n */\nexport function registerResource(key: string, resource: Resource<unknown>): void {\n resourceRegistry.set(key, resource);\n}\n\n/**\n * Unregister a resource (call on cleanup/unmount).\n */\nexport function unregisterResource(key: string): void {\n resourceRegistry.delete(key);\n}\n\n/**\n * Apply revalidation data from a single-flight mutation response.\n * For each key in the revalidate map, find the matching resource\n * and mutate it directly with the fresh data (skipping a refetch).\n */\nexport function applyRevalidation(revalidateData: Record<string, unknown>): void {\n for (const [key, freshData] of Object.entries(revalidateData)) {\n const resource = resourceRegistry.get(key);\n if (resource) {\n resource.mutate(freshData);\n }\n }\n}\n\n/**\n * Listen for revalidation events dispatched by $$serverFunction.\n * Call this once during app initialization to enable automatic\n * single-flight mutation handling.\n *\n * ```ts\n * // In your app entry:\n * import { enableAutoRevalidation } from 'forma/server/mutation';\n * enableAutoRevalidation();\n * ```\n */\nexport function enableAutoRevalidation(): () => void {\n if (typeof window === 'undefined') {\n // SSR/Node.js — no-op\n return () => {};\n }\n\n const handler = (event: Event) => {\n const detail = (event as CustomEvent).detail;\n if (detail && typeof detail === 'object') {\n applyRevalidation(detail as Record<string, unknown>);\n }\n };\n\n window.addEventListener('forma:revalidate', handler);\n\n // Return cleanup function\n return () => window.removeEventListener('forma:revalidate', handler);\n}\n\n/**\n * Wrap a server function response to include revalidation data.\n * Use this on the server side to enable single-flight mutations.\n *\n * ```ts\n * // Server-side:\n * async function createTodo(text: string) {\n * \"use server\";\n * const newTodo = await db.insert('todos', { text, done: false });\n * const allTodos = await db.query('todos');\n * return withRevalidation(newTodo, {\n * '/api/todos': allTodos,\n * });\n * }\n * ```\n */\nexport function withRevalidation<T>(data: T, revalidate: Record<string, unknown>): MutationResponse<T> {\n return { data, __revalidate: revalidate };\n}\n","/**\n * FormaJS Server - RPC Client\n *\n * Provides the client-side stub function that replaces \"use server\" function\n * bodies after compilation. Each call becomes a fetch POST to the server endpoint.\n */\n\n/**\n * Create an RPC stub function for a server function.\n * This replaces the original function body on the client side.\n *\n * @param endpoint - The RPC endpoint path (e.g. \"/rpc/createTodo_a1b2c3\")\n * @returns An async function that sends args to the server and returns the result\n */\nexport function $$serverFunction<T extends (...args: unknown[]) => Promise<unknown>>(\n endpoint: string,\n): T {\n const rpcFn = async (...args: unknown[]): Promise<unknown> => {\n const response = await fetch(endpoint, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/json',\n 'X-Forma-RPC': '1',\n },\n body: JSON.stringify({ args }),\n });\n\n if (!response.ok) {\n const errorText = await response.text();\n throw new Error(`Server function failed (${response.status}): ${errorText}`);\n }\n\n const result = await response.json();\n\n // If the response includes revalidation data (single-flight mutations),\n // return it alongside the result\n if (result && typeof result === 'object' && '__revalidate' in result) {\n // Dispatch a custom event so createAction can pick up the revalidation data\n if (typeof window !== 'undefined') {\n window.dispatchEvent(new CustomEvent('forma:revalidate', {\n detail: result.__revalidate,\n }));\n }\n return result.data;\n }\n\n return result;\n };\n\n return rpcFn as T;\n}\n","/**\n * FormaJS Server - RPC Handler\n *\n * Server-side registry and request handler for \"use server\" functions.\n * Framework-agnostic — works with any Node.js HTTP server, Express, Hono, etc.\n */\n\ntype ServerFunction = (...args: unknown[]) => Promise<unknown>;\n\n/** Registry of server functions by endpoint path. */\nconst registry = new Map<string, ServerFunction>();\n\n/**\n * Register a server function at a specific endpoint.\n * Called by the server-side compiled output.\n */\nexport function registerServerFunction(endpoint: string, fn: ServerFunction): void {\n registry.set(endpoint, fn);\n}\n\n/**\n * Get a registered server function by endpoint.\n */\nexport function getServerFunction(endpoint: string): ServerFunction | undefined {\n return registry.get(endpoint);\n}\n\n/**\n * Get all registered server function endpoints.\n */\nexport function getRegisteredEndpoints(): string[] {\n return [...registry.keys()];\n}\n\nexport interface RPCRequest {\n args: unknown[];\n}\n\nexport interface RPCResponse {\n data?: unknown;\n error?: string;\n __revalidate?: Record<string, unknown>;\n}\n\n/**\n * Handle an incoming RPC request.\n * Call this from your HTTP server's request handler.\n *\n * Usage with any HTTP framework:\n * ```ts\n * import { handleRPC } from 'forma/server/rpc-handler';\n *\n * // Express example:\n * app.post('/rpc/:endpoint', async (req, res) => {\n * const result = await handleRPC(req.path, req.body);\n * res.json(result);\n * });\n *\n * // Hono example:\n * app.post('/rpc/*', async (c) => {\n * const body = await c.req.json();\n * const result = await handleRPC(c.req.path, body);\n * return c.json(result);\n * });\n * ```\n *\n * @param endpoint - The full endpoint path (e.g. \"/rpc/createTodo_a1b2c3\")\n * @param body - The parsed request body containing { args: [...] }\n * @param revalidateData - Optional revalidation data to include in the response\n * (for single-flight mutations)\n */\n/** \"Crash Barrier\": block prototype pollution attacks via endpoint names. */\nconst FORBIDDEN_KEYS = new Set(['__proto__', 'constructor', 'prototype']);\n\nexport async function handleRPC(\n endpoint: string,\n body: RPCRequest,\n revalidateData?: Record<string, unknown>,\n): Promise<RPCResponse> {\n // Security: prevent prototype pollution via crafted endpoint names\n const endpointName = endpoint.split('/').pop() ?? '';\n if (FORBIDDEN_KEYS.has(endpointName)) {\n return { error: 'Forbidden endpoint name' };\n }\n\n const fn = registry.get(endpoint);\n if (!fn) {\n return { error: `Unknown server function: ${endpoint}` };\n }\n\n try {\n const result = await fn(...body.args);\n\n if (revalidateData) {\n return { data: result, __revalidate: revalidateData };\n }\n\n return { data: result };\n } catch (err) {\n // Don't leak internal error details to clients\n const isDev = typeof process !== 'undefined'\n && process.env?.NODE_ENV === 'development';\n const message = isDev && err instanceof Error\n ? err.message\n : 'Internal server error';\n return { error: message };\n }\n}\n\n/**\n * Create a middleware-style handler for use with Express-like frameworks.\n *\n * ```ts\n * import { createRPCMiddleware } from 'forma/server/rpc-handler';\n * app.use('/rpc', createRPCMiddleware());\n * ```\n */\nexport function createRPCMiddleware() {\n return async (req: { url: string; method: string; body?: unknown }, res: { json: (data: unknown) => void; status: (code: number) => { json: (data: unknown) => void } }) => {\n if (req.method !== 'POST') {\n res.status(405).json({ error: 'Method not allowed' });\n return;\n }\n\n const body = req.body as RPCRequest;\n if (!body || !Array.isArray(body.args)) {\n res.status(400).json({ error: 'Invalid RPC request: missing args array' });\n return;\n }\n\n const result = await handleRPC(req.url, body);\n if (result.error) {\n res.status(500).json(result);\n } else {\n res.json(result);\n }\n };\n}\n"]}
|