@aihu/compiler 0.1.7 → 0.1.9

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 CHANGED
@@ -21,7 +21,7 @@ npm install @aihu/compiler
21
21
  bun add @aihu/compiler
22
22
  ```
23
23
 
24
- <sub><i>Auto-generated against `@aihu/compiler@0.1.6`.</i></sub>
24
+ <sub><i>Auto-generated against `@aihu/compiler@0.1.8`.</i></sub>
25
25
 
26
26
  <!-- END_AUTOGEN: install -->
27
27
 
@@ -32,12 +32,12 @@ bun add @aihu/compiler
32
32
 
33
33
  | | |
34
34
  |---|---|
35
- | **Version** | `0.1.6` |
35
+ | **Version** | `0.1.8` |
36
36
  | **Tier** | D — Compiler — Single-File Component (.aihu) → Web Component |
37
37
  | **Published files** | 5 entries |
38
38
  | **License** | MIT |
39
39
 
40
- <sub><i>Auto-generated against `@aihu/compiler@0.1.6`.</i></sub>
40
+ <sub><i>Auto-generated against `@aihu/compiler@0.1.8`.</i></sub>
41
41
 
42
42
  <!-- END_AUTOGEN: stats -->
43
43
 
@@ -50,7 +50,7 @@ bun add @aihu/compiler
50
50
  |---|---|---|
51
51
  | `.` | `./dist/index.js` | `—` |
52
52
 
53
- <sub><i>Auto-generated against `@aihu/compiler@0.1.6`.</i></sub>
53
+ <sub><i>Auto-generated against `@aihu/compiler@0.1.8`.</i></sub>
54
54
 
55
55
  <!-- END_AUTOGEN: exports -->
56
56
 
@@ -63,7 +63,7 @@ bun add @aihu/compiler
63
63
 
64
64
  - `vite` — `>=5.0.0`
65
65
 
66
- <sub><i>Auto-generated against `@aihu/compiler@0.1.6`.</i></sub>
66
+ <sub><i>Auto-generated against `@aihu/compiler@0.1.8`.</i></sub>
67
67
 
68
68
  <!-- END_AUTOGEN: deps -->
69
69
 
@@ -77,7 +77,7 @@ bun add @aihu/compiler
77
77
  - [Macro Vocabulary spec](../../docs/superpowers/specs/2026-05-02-spec-macro-vocabulary.md)
78
78
  - [Aihu framework root](../../README.md)
79
79
 
80
- <sub><i>Auto-generated against `@aihu/compiler@0.1.6`.</i></sub>
80
+ <sub><i>Auto-generated against `@aihu/compiler@0.1.8`.</i></sub>
81
81
 
82
82
  <!-- END_AUTOGEN: see-also -->
83
83
 
@@ -88,6 +88,6 @@ bun add @aihu/compiler
88
88
 
89
89
  MIT — see [LICENSE](../../LICENSE).
90
90
 
91
- <sub><i>Auto-generated against `@aihu/compiler@0.1.6`.</i></sub>
91
+ <sub><i>Auto-generated against `@aihu/compiler@0.1.8`.</i></sub>
92
92
 
93
93
  <!-- END_AUTOGEN: license -->
package/bin/aihu-compile CHANGED
Binary file
package/dist/index.js CHANGED
@@ -38,5 +38,5 @@ function __aihu_wrap_defer__<T extends typeof HTMLElement>(Ctor: T): T {
38
38
  })
39
39
  `)}`}function p(n,r){return{code:e(o,[`--stdin`,`--tag`,t(r,`.aihu`),`--path`,r],{input:n,encoding:`utf8`}),map:null}}function m(e){let t;t=e.includes(`from '@aihu/arbor'`)?e.replace(/import\s*\{([^}]*)\}\s*from\s*'@aihu\/arbor'/,(e,t)=>{let n=t.split(`,`).map(e=>e.trim()).filter(Boolean);return n.includes(`mount`)||n.push(`mount`),`import { ${n.join(`, `)} } from '@aihu/arbor'`}):`import { mount } from '@aihu/arbor'\n${e}`,/import\s+\{[^}]*\}\s+from\s+'@aihu\/signals'/.test(t)?t=t.replace(/import\s*\{([^}]*)\}\s*from\s*'@aihu\/signals'/,(e,t)=>{if(e.startsWith(`import type`))return e;let n=t.split(`,`).map(e=>e.trim()).filter(Boolean);return n.includes(`signal`)||n.push(`signal`),`import { ${n.join(`, `)} } from '@aihu/signals'`}):/import.*from\s*'@aihu\/signals'/.test(t)?/import\s+type\s+\{[^}]*\}\s+from\s+'@aihu\/signals'/.test(t)&&!t.match(/import\s+\{[^}]*\}\s+from\s+'@aihu\/signals'/)&&(t=t.replace(/(import\s+type\s+\{[^}]*\}\s+from\s+'@aihu\/signals')/,(e,t)=>`${t}\nimport { signal } from '@aihu/signals'`)):t=t.replace(/import\s*\{[^}]*\}\s*from\s*'@aihu\/arbor'/,e=>`${e}\nimport { signal } from '@aihu/signals'`),t=t.replace(/import\s*\{([^}]*)\}\s*from\s*'@aihu\/runtime'/,(e,t)=>{let n=t.split(`,`).map(e=>e.trim()).filter(Boolean);return n.includes(`_setMount`)||n.push(`_setMount`),n.includes(`_setSignal`)||n.push(`_setSignal`),`import { ${n.join(`, `)} } from '@aihu/runtime'`});let n=t.split(`
40
40
  `),r=-1;for(let e=n.length-1;e>=0;e--){let t=(n[e]??``).trim();if(t.startsWith(`import `)||t.startsWith(`import{`)){r=e;break}}return r!==-1&&(n.splice(r+1,0,`_setMount(mount)`,`_setSignal(signal)`,``),t=n.join(`
41
- `)),t}function h(e){let t=e?.islands!==!1,n=e?.shadowMode;return{name:`aihu-compiler`,enforce:`pre`,transform(e,r){let i=r.split(`?`)[0];if(i.endsWith(`.aihu`))return(async()=>{let r=p(e,i),a=n==null?r.code:s(r.code,n),o=l(a),h;t&&o!==null&&c(a)===`static`?h=f(a,o):o===null?(h=a,h=m(h)):(h=u(a,o),h=d(h,o),h=m(h));try{let e=await import(`vite`);return`transformWithOxc`in e&&typeof e.transformWithOxc==`function`?{code:h,moduleType:`ts`,map:null}:{code:(await e.transformWithEsbuild(h,`component.ts`,{target:`esnext`,sourcemap:!1})).code,map:null}}catch{return{code:h,map:null}}})()}}}export{d as _buildDeferredHydration,f as _buildStaticIsland,c as _classifyIsland,m as _injectAutoWiring,s as _injectShadowMode,h as aihuCompilerPlugin,p as transform};
41
+ `)),t}function h(e){let t=e?.islands!==!1,n=e?.shadowMode;return{name:`aihu-compiler`,enforce:`pre`,transform(e,r){let i=r.split(`?`)[0];if(i.endsWith(`.aihu`))return(async()=>{let r=p(e,i),a=n==null?r.code:s(r.code,n),o=l(a),h;t&&o!==null&&c(a)===`static`?h=f(a,o):o===null?(h=a,h=m(h)):(h=u(a,o),h=d(h,o),h=m(h));try{let e=await import(`vite`);return`transformWithEsbuild`in e&&typeof e.transformWithEsbuild==`function`?{code:(await e.transformWithEsbuild(h,`component.ts`,{target:`esnext`,sourcemap:!1})).code,map:null}:{code:h,moduleType:`ts`,map:null}}catch{return{code:h,map:null}}})()}}}export{d as _buildDeferredHydration,f as _buildStaticIsland,c as _classifyIsland,m as _injectAutoWiring,s as _injectShadowMode,h as aihuCompilerPlugin,p as transform};
42
42
  //# sourceMappingURL=index.js.map
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","names":[],"sources":["../js/index.ts"],"sourcesContent":["/**\n * @aihu/compiler — TypeScript wrapper around the aihu-compile Rust binary.\n *\n * Exports:\n * transform(source, id) — compile a single .aihu file to TypeScript\n * aihuCompilerPlugin() — Vite plugin that wires transform() into the build\n */\nimport { execFileSync } from 'node:child_process'\nimport { basename, dirname, resolve } from 'node:path'\nimport { fileURLToPath } from 'node:url'\n\n// Binary resolution: env var override, fallback to the bin/ directory written\n// by the postinstall hook (packages/compiler/bin/aihu-compile[.exe]).\nconst ext = process.platform === 'win32' ? '.exe' : ''\nconst binPath: string =\n process.env.SCRIBE_COMPILE_BIN ??\n resolve(dirname(fileURLToPath(import.meta.url)), `../bin/aihu-compile${ext}`)\n\n// Minimal VitePlugin interface — avoids importing from 'vite' at compile time.\n// Structurally compatible with Vite's Plugin type.\ninterface VitePlugin {\n readonly name: string\n enforce?: 'pre' | 'post'\n transform?: (\n code: string,\n id: string,\n ) => Promise<{ code: string; map: null }> | { code: string; map: null } | null | undefined\n}\n\n/**\n * Options for `aihuCompilerPlugin()` (Plan 3.3 — Islands).\n */\nexport interface AihuCompilerPluginOptions {\n /**\n * When `true` (default), components classified as `'static'` by\n * `_classifyIsland()` are emitted with a minimal HTML-only registration\n * shim that ships **zero** `@aihu/runtime` and `@aihu/signals` JS to\n * the browser. Components classified as `'interactive'` retain the\n * full runtime path.\n *\n * Setting `islands: false` opts every component back into the unified\n * runtime path (Plan 3.2 baseline behaviour).\n */\n islands?: boolean\n\n /**\n * Project-wide shadow-DOM mode applied to every `.aihu` SFC compiled\n * by this plugin instance. When set, the plugin post-processes the\n * compiled JS to inject `, { shadowMode: '<mode>' }` as the third arg\n * to the emitted `defineElement(tag, defineComponent(...))` call.\n *\n * - `'open'` — default browser behaviour (shadow root, externally readable).\n * - `'closed'` — shadow root, externally hidden.\n * - `'none'` — **no shadow root.** The component mounts into its own\n * element. Required for global utility-class CSS frameworks\n * like Tailwind, UnoCSS, Pico that rely on the cascade.\n *\n * Per-component override is not yet supported via SFC syntax (post-v1).\n * For per-component control today, hand-author the component with\n * `defineElement(tag, Ctor, { shadowMode: '...' })`.\n */\n shadowMode?: 'open' | 'closed' | 'none'\n}\n\n/**\n * Inject `{ shadowMode: '...' }` as the third argument to the emitted\n * `defineElement('tag', defineComponent(...))` call. The compiler emits\n * exactly two arguments today; this rewrites the closing of the\n * defineElement call to include the options object. Idempotent — leaves\n * code untouched when the closer is not in the expected shape.\n *\n * @internal\n */\nexport function _injectShadowMode(code: string, mode: 'open' | 'closed' | 'none'): string {\n // Match the trailing `))` that closes `defineElement(tag, defineComponent(setup))`.\n // The compiler always emits this exact two-paren close as the final tokens of\n // the defineElement call — we anchor on it and append the options object.\n // biome-ignore lint/correctness/noEmptyCharacterClassInRegex: [^] is valid JS — matches any char including newlines\n const re = /(defineElement\\(\\s*['\"][^'\"]+['\"]\\s*,\\s*defineComponent\\([^]*\\))\\s*\\)/\n const replaced = code.replace(re, (_m, inner: string) => `${inner}, { shadowMode: '${mode}' })`)\n return replaced\n}\n\n/**\n * Classify the compiled output of a single `.aihu` module as either a\n * **static** island (no reactive state — purely declarative DOM) or an\n * **interactive** island (uses the signals reactivity system).\n *\n * The heuristic is intentionally conservative: any source-level reference\n * to a primitive that requires the `defineComponent` owner context flips\n * the file to `'interactive'`. False positives (e.g. a string literal\n * containing `signal(`) are tolerable — they only forfeit the static-island\n * optimisation. False negatives are forbidden: a static-classified file\n * MUST NOT depend on the signals runtime at execution time.\n *\n * Owner-requiring primitives covered:\n * - `signal(`, `computed(`, `effect(`, `setSignal(` (signals runtime)\n * - `onMount(`, `onCleanup(` (lifecycle hooks — throw `no owner` outside\n * `defineComponent` because they push into the active owner's mount/\n * cleanup queues)\n *\n * Plan 3.3 / acceptance criterion 1.\n *\n * @internal\n */\nexport function _classifyIsland(compiledCode: string): 'static' | 'interactive' {\n // Match call sites of the reactive + lifecycle primitives. Use word-boundary\n // anchors so identifiers like `mySignal(` or `__effect(` do not trip the\n // heuristic. The `(` is required so that bare imports of the names in an\n // unused `import { signal }` line do not flip an otherwise-static module.\n return /\\b(?:signal|computed|effect|setSignal|onMount|onCleanup)\\s*\\(/.test(compiledCode)\n ? 'interactive'\n : 'static'\n}\n\n/**\n * Extract the custom element tag name from compiler-emitted code.\n * The compiler always emits `defineElement('tag-name', ...)` as the\n * first call — pull the first string literal argument.\n * Returns `null` if no `defineElement` call is found.\n * @internal\n */\nfunction _extractElementTag(code: string): string | null {\n const m = /defineElement\\(\\s*['\"]([^'\"]+)['\"]/m.exec(code)\n return m ? (m[1] ?? null) : null\n}\n\n/**\n * Instrument a compiled `.aihu` module with HMR support.\n *\n * The compiler always emits:\n *\n * import { defineComponent, defineElement } from '@aihu/runtime'\n * defineElement('tag', defineComponent((_ctx) => { ... }))\n *\n * This function:\n *\n * 1. Adds `_hmrReplace` to the `@aihu/runtime` import.\n * 2. Prepends a module-level slot variable `__aihu_setup__`.\n * 3. Rewrites the single `defineComponent(` call so the setup function\n * is captured via an assignment expression:\n * `defineComponent(__aihu_setup__ = ` (valid JS; assignment has\n * lower precedence than arrow fn, so `defineComponent` still\n * receives the function as its argument).\n * 4. Appends `export { __aihu_setup__ as default }` so that Vite's\n * `import.meta.hot.accept` callback receives the new setup via\n * `newModule.default` on hot reload.\n * 5. Appends the `import.meta.hot.accept` block, gated on `__DEV__`.\n *\n * The `__DEV__` guard ensures production bundlers (where they replace\n * `__DEV__` with `false`) dead-code-eliminate the entire HMR block.\n *\n * @internal\n */\nfunction _buildHmrCode(compiledCode: string, elementTag: string): string {\n // Step 1 — add _hmrReplace to the @aihu/runtime import.\n const withImport = compiledCode.replace(\n /import\\s*\\{([^}]*)\\}\\s*from\\s*'@aihu\\/runtime'/,\n (_m, imports: string) => {\n const parts = imports\n .split(',')\n .map((s) => s.trim())\n .filter(Boolean)\n if (!parts.includes('_hmrReplace')) parts.push('_hmrReplace')\n return `import { ${parts.join(', ')} } from '@aihu/runtime'`\n },\n )\n\n // Step 2+3 — prepend slot variable and rewrite the defineComponent call.\n // Compiler emits exactly one `defineComponent(` followed by a function expr.\n // Rewrite: defineComponent(fn) → defineComponent(__aihu_setup__ = fn)\n // Assignment expression evaluates to `fn`, so defineComponent still\n // receives the setup function as its first argument unchanged.\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n const preamble = `let __aihu_setup__: ((ctx: any) => any) | undefined\\n`\n\n const patchedBody = withImport.replace(/\\bdefineComponent\\(/, 'defineComponent(__aihu_setup__ = ')\n\n const tag = JSON.stringify(elementTag)\n // Step 4+5 — postamble with default export and HMR acceptance.\n const postamble = `\nexport { __aihu_setup__ as default }\n\nif (typeof __DEV__ !== 'undefined' && __DEV__ && import.meta.hot) {\n import.meta.hot.accept((newModule) => {\n if (!newModule) return\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n const newSetup = (newModule as any)['default']\n if (typeof newSetup !== 'function') return\n document.querySelectorAll(${tag}).forEach((el) => {\n _hmrReplace(el as HTMLElement, newSetup)\n })\n })\n}\n`\n\n return preamble + patchedBody + postamble\n}\n\n/**\n * Rewrite an interactive-island module so its `connectedCallback` waits\n * for the element to scroll into view before mounting. Plan 3.3 — applied\n * only when the consumer adds `defer` to the custom element tag (e.g.\n * `<my-counter defer>`); the runtime helper checks the attribute and\n * either mounts immediately or registers an `IntersectionObserver`.\n *\n * Implementation: the helper is added as a `_hydrateOnVisible` import\n * from `@aihu/runtime`, and the compiler-emitted `defineElement(...)`\n * call is wrapped in a `defineElement` that intercepts `connectedCallback`\n * to honour the `defer` attribute.\n *\n * The whole indirection is tree-shaken when no `.aihu` module reaches\n * this branch, because `_hydrateOnVisible` is exported from its own\n * sibling module inside `@aihu/runtime`.\n *\n * @internal\n */\nexport function _buildDeferredHydration(compiledCode: string, elementTag: string): string {\n // Add _hydrateOnVisible to the @aihu/runtime import.\n const withImport = compiledCode.replace(\n /import\\s*\\{([^}]*)\\}\\s*from\\s*'@aihu\\/runtime'/,\n (_m, imports: string) => {\n const parts = imports\n .split(',')\n .map((s) => s.trim())\n .filter(Boolean)\n if (!parts.includes('_hydrateOnVisible')) parts.push('_hydrateOnVisible')\n return `import { ${parts.join(', ')} } from '@aihu/runtime'`\n },\n )\n\n // Wrap the class returned by defineComponent BEFORE defineElement\n // consumes it. The HTML spec caches lifecycle callbacks at\n // customElements.define() time, so we MUST mutate the prototype\n // before that call — not after. We accomplish this with a synchronous\n // helper invoked between defineComponent and defineElement.\n //\n // Source pattern (compiler-emitted):\n // defineElement('tag', defineComponent((_ctx) => { ... }))\n //\n // After this rewrite:\n // defineElement('tag', __aihu_wrap_defer__(defineComponent((_ctx) => { ... })))\n //\n // …with __aihu_wrap_defer__ defined in the appended preamble.\n const patched = withImport.replace(\n /defineElement\\(\\s*('[^']+'|\"[^\"]+\")\\s*,\\s*defineComponent\\(/,\n (_m, tagLit: string) => `defineElement(${tagLit}, __aihu_wrap_defer__(defineComponent(`,\n )\n // Match the closing `))` of the defineElement call. The HMR pass may\n // have inserted `__aihu_setup__ = ` before the inner function, but\n // the trailing `))` shape is unchanged. Replace exactly one occurrence\n // by anchoring on end-of-string trim; bail if the shape does not match.\n if (patched === withImport) {\n // The expected `defineElement(<tag>, defineComponent(` shape was not\n // present (e.g. compiler output changed). Skip defer wrapping rather\n // than emit broken code.\n return compiledCode\n }\n // Add a trailing `)` to balance the extra `(` from __aihu_wrap_defer__.\n // Source shape after _buildHmrCode is:\n // defineElement('tag', defineComponent(__aihu_setup__ = (_ctx) => {...}))\n // export { __aihu_setup__ as default }\n // if (typeof __DEV__ !== ...) { ... }\n // We must close BEFORE the export line. Match the first `))` followed\n // by a newline and `export` (or end-of-string for the unwrapped case).\n let balanced = patched.replace(/\\)\\s*\\)\\s*\\nexport\\s/, ')))\\nexport ')\n if (balanced === patched) {\n // No HMR postamble — the `))` is at end-of-string.\n balanced = patched.replace(/\\)\\s*\\)\\s*$/, ')))\\n')\n }\n if (balanced === patched) {\n // Could not find the matching `))` — bail out.\n return compiledCode\n }\n\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n const helper = `\n// Plan 3.3 (Islands) — defer attribute support. Wraps the constructor\n// returned by defineComponent so instances bearing the \\`defer\\` attribute\n// hydrate lazily via IntersectionObserver. Bare instances retain the\n// eager Plan 3.2 hydration path.\nfunction __aihu_wrap_defer__<T extends typeof HTMLElement>(Ctor: T): T {\n const orig = (Ctor.prototype as unknown as { connectedCallback?: () => void }).connectedCallback\n if (typeof orig !== 'function') return Ctor\n ;(Ctor.prototype as unknown as { connectedCallback: () => void }).connectedCallback = function (this: HTMLElement) {\n if (this.hasAttribute('defer')) {\n _hydrateOnVisible(this, () => orig.call(this))\n } else {\n orig.call(this)\n }\n }\n return Ctor\n}\n`\n void elementTag\n return helper + balanced\n}\n\n/**\n * Build a static-island shim for a compiled module.\n *\n * The compiled module emitted by the Rust codegen has the shape:\n *\n * import { branch, leaf, slot } from '@aihu/arbor'\n * import { defineComponent, defineElement } from '@aihu/runtime'\n * defineElement('tag', defineComponent((_ctx) => { return <tree> }))\n *\n * For a static island we know `<tree>` contains no `signal(`/`computed(`\n * calls. We can therefore:\n *\n * 1. Drop the `@aihu/runtime` import (saves ~600 B gz of defineComponent\n * + defineElement + bootstrap glue).\n * 2. Replace `defineElement(tag, defineComponent(setup))` with a tiny\n * inline class that mounts the tree directly via `mount()` (which the\n * arbor barrel already exports).\n * 3. Tag the file with a `// SCRIBE_STATIC_ISLAND` comment so consumers\n * can audit which routes shipped zero-JS-runtime.\n *\n * Falls back to the original code if the regex shape does not match\n * (defensive: a future compiler change must opt back into static-island\n * emission explicitly rather than silently break).\n *\n * @internal\n */\nexport function _buildStaticIsland(compiledCode: string, elementTag: string): string {\n // Confirm the shape we expect: a single defineElement(...) call wrapping\n // a single defineComponent(...) call. Bail out otherwise.\n const callRe = /defineElement\\(\\s*['\"][^'\"]+['\"]\\s*,\\s*defineComponent\\(/\n if (!callRe.test(compiledCode)) return compiledCode\n\n // Strip the `@aihu/runtime` import line entirely — static islands\n // don't reference defineComponent/defineElement after the rewrite.\n const withoutRuntimeImport = compiledCode.replace(\n /^\\s*import\\s*\\{[^}]*\\}\\s*from\\s*'@aihu\\/runtime'\\s*;?\\s*$/m,\n '',\n )\n\n // Ensure `mount` is imported from @aihu/arbor (it already exposes\n // branch/leaf/slot, so we just append `mount` to the existing list).\n const withArborMount = withoutRuntimeImport.replace(\n /import\\s*\\{([^}]*)\\}\\s*from\\s*'@aihu\\/arbor'/,\n (_m, imports: string) => {\n const parts = imports\n .split(',')\n .map((s) => s.trim())\n .filter(Boolean)\n if (!parts.includes('mount')) parts.push('mount')\n return `import { ${parts.join(', ')} } from '@aihu/arbor'`\n },\n )\n\n // Replace `defineElement('tag', defineComponent((_ctx) => { ... }))`\n // with an inline `customElements.define` whose connectedCallback mounts\n // the static tree. The setup function is captured verbatim by replacing\n // the wrapping calls with anonymous-IIFE bookends.\n const tagJson = JSON.stringify(elementTag)\n const rewritten = withArborMount\n .replace(\n /defineElement\\(\\s*['\"][^'\"]+['\"]\\s*,\\s*defineComponent\\(/,\n `customElements.define(${tagJson}, class extends HTMLElement {\\n connectedCallback() {\\n const root = this.attachShadow({ mode: 'open' })\\n const __aihu_setup__ = (`,\n )\n .replace(\n /\\)\\s*\\)\\s*$/,\n `)\\n mount(__aihu_setup__({ host: root, element: this }), root)\\n }\\n})\\n`,\n )\n\n return `// SCRIBE_STATIC_ISLAND — zero @aihu/runtime references\\n${rewritten}`\n}\n\n/**\n * Compile a .aihu source string to TypeScript.\n * map is null — source maps are deferred to v1 (OQ-C8)\n */\nexport function transform(source: string, id: string): { code: string; map: null } {\n const stem = basename(id, '.aihu')\n const code = execFileSync(binPath, ['--stdin', '--tag', stem, '--path', id], {\n input: source,\n encoding: 'utf8',\n })\n return {\n code,\n map: null, // source maps deferred to v1 (OQ-C8)\n }\n}\n\n/**\n * Inject `_setMount(mount)` + `_setSignal(signal)` auto-wiring into a compiled\n * `.aihu` module. Adds the necessary symbols to existing imports and inserts\n * the boot calls right after the last `import` statement.\n *\n * @internal\n */\nexport function _injectAutoWiring(code: string): string {\n // 1. Add `mount` to the @aihu/arbor import (or create it).\n let result: string\n if (code.includes(\"from '@aihu/arbor'\")) {\n result = code.replace(\n /import\\s*\\{([^}]*)\\}\\s*from\\s*'@aihu\\/arbor'/,\n (_m: string, imports: string) => {\n const parts = imports\n .split(',')\n .map((s) => s.trim())\n .filter(Boolean)\n if (!parts.includes('mount')) parts.push('mount')\n return `import { ${parts.join(', ')} } from '@aihu/arbor'`\n },\n )\n } else {\n result = `import { mount } from '@aihu/arbor'\\n${code}`\n }\n\n // 2. Add `signal` to the non-type @aihu/signals import (or create it).\n // Note: `import\\s+\\{` does NOT match `import type {` (the regex needs `{` immediately\n // after whitespace, whereas `import type {` has `type` in between). No negation guard\n // is needed — the replace callback below already skips `import type` lines.\n if (/import\\s+\\{[^}]*\\}\\s+from\\s+'@aihu\\/signals'/.test(result)) {\n // There IS a value import from signals — add `signal` if missing.\n result = result.replace(\n /import\\s*\\{([^}]*)\\}\\s*from\\s*'@aihu\\/signals'/,\n (_m: string, imports: string) => {\n // Skip type-only imports\n if (_m.startsWith('import type')) return _m\n const parts = imports\n .split(',')\n .map((s) => s.trim())\n .filter(Boolean)\n if (!parts.includes('signal')) parts.push('signal')\n return `import { ${parts.join(', ')} } from '@aihu/signals'`\n },\n )\n } else if (!/import.*from\\s*'@aihu\\/signals'/.test(result)) {\n // No signals import at all — insert after arbor import\n result = result.replace(\n /import\\s*\\{[^}]*\\}\\s*from\\s*'@aihu\\/arbor'/,\n (m: string) => `${m}\\nimport { signal } from '@aihu/signals'`,\n )\n }\n // If only `import type { Signal }` exists, insert value import after it\n else if (\n /import\\s+type\\s+\\{[^}]*\\}\\s+from\\s+'@aihu\\/signals'/.test(result) &&\n !result.match(/import\\s+\\{[^}]*\\}\\s+from\\s+'@aihu\\/signals'/)\n ) {\n result = result.replace(\n /(import\\s+type\\s+\\{[^}]*\\}\\s+from\\s+'@aihu\\/signals')/,\n (_m: string, typeImport: string) => `${typeImport}\\nimport { signal } from '@aihu/signals'`,\n )\n }\n\n // 3. Add `_setMount`, `_setSignal` to the @aihu/runtime import.\n result = result.replace(\n /import\\s*\\{([^}]*)\\}\\s*from\\s*'@aihu\\/runtime'/,\n (_m: string, imports: string) => {\n const parts = imports\n .split(',')\n .map((s) => s.trim())\n .filter(Boolean)\n if (!parts.includes('_setMount')) parts.push('_setMount')\n if (!parts.includes('_setSignal')) parts.push('_setSignal')\n return `import { ${parts.join(', ')} } from '@aihu/runtime'`\n },\n )\n\n // 4. Insert boot calls after the last `import` statement.\n const lines = result.split('\\n')\n let lastImportIdx = -1\n for (let i = lines.length - 1; i >= 0; i--) {\n const t = (lines[i] ?? '').trim()\n if (t.startsWith('import ') || t.startsWith('import{')) {\n lastImportIdx = i\n break\n }\n }\n if (lastImportIdx !== -1) {\n lines.splice(lastImportIdx + 1, 0, '_setMount(mount)', '_setSignal(signal)', '')\n result = lines.join('\\n')\n }\n\n return result\n}\n\n/**\n * Vite plugin that compiles .aihu files to TypeScript during build and dev.\n *\n * Use `enforce: 'pre'` so the hook fires before Vite/Rollup's built-in\n * parsers attempt to process the raw .aihu content as JavaScript.\n *\n * @example\n * // vite.config.ts\n * import { aihuCompilerPlugin } from '@aihu/compiler'\n * export default { plugins: [aihuCompilerPlugin()] }\n *\n * **Known Limitation — Bun + Rollup4 ESM incompatibility (v0):**\n *\n * `bun vite build` fails in the `fixtures/vite-counter` fixture with two\n * cascading errors:\n *\n * 1. **Missing devDependency:** `vite` is declared only as an optional\n * `peerDependency` in `packages/compiler/package.json`. Bun does not\n * install optional peers automatically, so `bun vite build` exits\n * immediately with `Cannot find package 'vite'`.\n *\n * 2. **Bun + Rollup4 bridge:** Even with Vite installed, Bun processes\n * `vite.config.ts` through its own internal bundler before handing off\n * to Rollup4. When `@aihu/compiler` is resolved from the workspace\n * symlink (`dist/index.js`), Bun's ESM loader evaluates the module at\n * config-load time. The subprocess call inside `transform()` depends on\n * the Rust binary being at `../bin/aihu-compile` relative to `dist/`\n * (written by the postinstall hook). In a dev workspace where postinstall\n * has not run, this path does not exist and `execFileSync` throws. Bun surfaces\n * the error as a config-load failure, not a per-file transform error,\n * causing the entire build to abort before any `.aihu` file is\n * processed.\n *\n * **Workaround (v0):** Use `bun run integrate.ts` directly from\n * `packages/compiler/fixtures/vite-counter/`. This script calls\n * `transform()` from `@aihu/compiler` without involving Vite or Rollup.\n * Preconditions: (1) `cargo build --release` in `packages/compiler/`,\n * (2) `bun install` at the repo root.\n *\n * **v1 resolution:** Add `vite` as a `devDependency` in\n * `packages/compiler/package.json`; add a WASM or pre-built binary\n * strategy so the Rust binary is bundled with the npm package and does not\n * require a separate `cargo build --release` step.\n */\nexport function aihuCompilerPlugin(options?: AihuCompilerPluginOptions): VitePlugin {\n const islandsEnabled = options?.islands !== false\n const shadowMode = options?.shadowMode\n return {\n name: 'aihu-compiler',\n enforce: 'pre',\n transform(code, id) {\n // Strip Vite query strings (e.g. `?import`, `?t=...`) before checking the extension.\n const rawId = id.split('?')[0]!\n if (!rawId.endsWith('.aihu')) return\n return (async () => {\n const result = transform(code, rawId)\n const compiled =\n shadowMode != null ? _injectShadowMode(result.code, shadowMode) : result.code\n const elementTag = _extractElementTag(compiled)\n\n let out: string\n\n // Plan 3.3 — static-island fast path. Bypasses HMR injection because\n // a component with no signals has no setup state to hot-replace.\n // Static islands strip @aihu/runtime entirely — do NOT inject auto-wiring\n // (it would reference _setMount/_setSignal as undefined identifiers).\n if (islandsEnabled && elementTag !== null && _classifyIsland(compiled) === 'static') {\n out = _buildStaticIsland(compiled, elementTag)\n } else if (elementTag !== null) {\n // Inject HMR instrumentation. The injected block is gated on\n // `typeof __DEV__ !== 'undefined' && __DEV__` so production\n // bundlers dead-code-eliminate it when they set __DEV__ = false.\n out = _buildHmrCode(compiled, elementTag)\n // Plan 3.3 — interactive islands also gain `defer` attribute\n // support so individual instances can opt into lazy hydration.\n out = _buildDeferredHydration(out, elementTag)\n // Inject auto-wiring so consumers don't need a manual main.ts bootstrap.\n out = _injectAutoWiring(out)\n } else {\n out = compiled\n // Inject auto-wiring so consumers don't need a manual main.ts bootstrap.\n out = _injectAutoWiring(out)\n }\n\n // The Rust compiler emits TypeScript (type casts, import type, etc.) and\n // the injected HMR / defer helpers also contain TS generics and casts.\n // Vite does NOT re-run its TS-strip step when a plugin returns code for a\n // non-.ts ID, so we must strip types ourselves before returning.\n //\n // Vite 8+ (Rolldown/Oxc): transformWithEsbuild is a no-op; declare the\n // module type as 'ts' so Rolldown strips types natively. The extra\n // moduleType field is silently ignored by Vite 5 / esbuild.\n // Vite 5 (esbuild): transformWithEsbuild does the stripping.\n try {\n const vite = await import('vite')\n if ('transformWithOxc' in vite && typeof vite.transformWithOxc === 'function') {\n // Vite 8+: return TS and declare the module type — Rolldown strips types.\n // biome-ignore lint/suspicious/noExplicitAny: moduleType is vite 8 / rolldown API\n return { code: out, moduleType: 'ts', map: null } as any\n }\n const stripped = await vite.transformWithEsbuild(out, 'component.ts', {\n target: 'esnext',\n sourcemap: false,\n })\n return { code: stripped.code, map: null }\n } catch {\n // If running outside Vite (e.g. tests, standalone transform), return as-is.\n return { code: out, map: null }\n }\n })()\n },\n }\n}\n"],"mappings":"0JAaA,MAAM,EAAM,QAAQ,WAAa,QAAU,OAAS,GAC9C,EACJ,QAAQ,IAAI,oBACZ,EAAQ,EAAQ,EAAc,OAAO,KAAK,IAAI,CAAC,CAAE,sBAAsB,IAAM,CAyD/E,SAAgB,EAAkB,EAAc,EAA0C,CAOxF,OADiB,EAAK,QAAQ,yEAAK,EAAI,IAAkB,GAAG,EAAM,mBAAmB,EAAK,MAC3E,CAyBjB,SAAgB,EAAgB,EAAgD,CAK9E,MAAO,gEAAgE,KAAK,EAAa,CACrF,cACA,SAUN,SAAS,EAAmB,EAA6B,CACvD,IAAM,EAAI,sCAAsC,KAAK,EAAK,CAC1D,OAAO,EAAK,EAAE,IAAM,KAAQ,KA8B9B,SAAS,EAAc,EAAsB,EAA4B,CAEvE,IAoBM,EApBa,EAAa,QAC9B,kDACC,EAAI,IAAoB,CACvB,IAAM,EAAQ,EACX,MAAM,IAAI,CACV,IAAK,GAAM,EAAE,MAAM,CAAC,CACpB,OAAO,QAAQ,CAElB,OADK,EAAM,SAAS,cAAc,EAAE,EAAM,KAAK,cAAc,CACtD,YAAY,EAAM,KAAK,KAAK,CAAC,0BAYpB,CAAW,QAAQ,sBAAuB,oCAAoC,CAI5F,EAAY;;;;;;;;;gCAFN,KAAK,UAAU,EAWM,CAAC;;;;;EAOlC,MAAO;EAAW,EAAc,EAqBlC,SAAgB,EAAwB,EAAsB,EAA4B,CAExF,IAAM,EAAa,EAAa,QAC9B,kDACC,EAAI,IAAoB,CACvB,IAAM,EAAQ,EACX,MAAM,IAAI,CACV,IAAK,GAAM,EAAE,MAAM,CAAC,CACpB,OAAO,QAAQ,CAElB,OADK,EAAM,SAAS,oBAAoB,EAAE,EAAM,KAAK,oBAAoB,CAClE,YAAY,EAAM,KAAK,KAAK,CAAC,0BAEvC,CAeK,EAAU,EAAW,QACzB,+DACC,EAAI,IAAmB,iBAAiB,EAAO,wCACjD,CAKD,GAAI,IAAY,EAId,OAAO,EAST,IAAI,EAAW,EAAQ,QAAQ,uBAAwB;SAAe,CA8BtE,OA7BI,IAAa,IAEf,EAAW,EAAQ,QAAQ,cAAe;EAAQ,EAEhD,IAAa,EAER,EAuBF;;;;;;;;;;;;;;;;;EAAS,EA6BlB,SAAgB,EAAmB,EAAsB,EAA4B,CAInF,GAAI,CAAC,2DAAO,KAAK,EAAa,CAAE,OAAO,EAWvC,IAAM,EAPuB,EAAa,QACxC,6DACA,GAKyC,CAAC,QAC1C,gDACC,EAAI,IAAoB,CACvB,IAAM,EAAQ,EACX,MAAM,IAAI,CACV,IAAK,GAAM,EAAE,MAAM,CAAC,CACpB,OAAO,QAAQ,CAElB,OADK,EAAM,SAAS,QAAQ,EAAE,EAAM,KAAK,QAAQ,CAC1C,YAAY,EAAM,KAAK,KAAK,CAAC,wBAEvC,CAMK,EAAU,KAAK,UAAU,EAAW,CAW1C,MAAO,4DAVW,EACf,QACC,2DACA,yBAAyB,EAAQ,4IAClC,CACA,QACC,cACA;;;;EAGwE,GAO9E,SAAgB,EAAU,EAAgB,EAAyC,CAMjF,MAAO,CACL,KALW,EAAa,EAAS,CAAC,UAAW,QADlC,EAAS,EAAI,QACkC,CAAE,SAAU,EAAG,CAAE,CAC3E,MAAO,EACP,SAAU,OACX,CAEK,CACJ,IAAK,KACN,CAUH,SAAgB,EAAkB,EAAsB,CAEtD,IAAI,EACJ,AAaE,EAbE,EAAK,SAAS,qBAAqB,CAC5B,EAAK,QACZ,gDACC,EAAY,IAAoB,CAC/B,IAAM,EAAQ,EACX,MAAM,IAAI,CACV,IAAK,GAAM,EAAE,MAAM,CAAC,CACpB,OAAO,QAAQ,CAElB,OADK,EAAM,SAAS,QAAQ,EAAE,EAAM,KAAK,QAAQ,CAC1C,YAAY,EAAM,KAAK,KAAK,CAAC,wBAEvC,CAEQ,wCAAwC,IAO/C,+CAA+C,KAAK,EAAO,CAE7D,EAAS,EAAO,QACd,kDACC,EAAY,IAAoB,CAE/B,GAAI,EAAG,WAAW,cAAc,CAAE,OAAO,EACzC,IAAM,EAAQ,EACX,MAAM,IAAI,CACV,IAAK,GAAM,EAAE,MAAM,CAAC,CACpB,OAAO,QAAQ,CAElB,OADK,EAAM,SAAS,SAAS,EAAE,EAAM,KAAK,SAAS,CAC5C,YAAY,EAAM,KAAK,KAAK,CAAC,0BAEvC,CACS,kCAAkC,KAAK,EAAO,CASxD,sDAAsD,KAAK,EAAO,EAClE,CAAC,EAAO,MAAM,+CAA+C,GAE7D,EAAS,EAAO,QACd,yDACC,EAAY,IAAuB,GAAG,EAAW,0CACnD,EAbD,EAAS,EAAO,QACd,6CACC,GAAc,GAAG,EAAE,0CACrB,CAcH,EAAS,EAAO,QACd,kDACC,EAAY,IAAoB,CAC/B,IAAM,EAAQ,EACX,MAAM,IAAI,CACV,IAAK,GAAM,EAAE,MAAM,CAAC,CACpB,OAAO,QAAQ,CAGlB,OAFK,EAAM,SAAS,YAAY,EAAE,EAAM,KAAK,YAAY,CACpD,EAAM,SAAS,aAAa,EAAE,EAAM,KAAK,aAAa,CACpD,YAAY,EAAM,KAAK,KAAK,CAAC,0BAEvC,CAGD,IAAM,EAAQ,EAAO,MAAM;EAAK,CAC5B,EAAgB,GACpB,IAAK,IAAI,EAAI,EAAM,OAAS,EAAG,GAAK,EAAG,IAAK,CAC1C,IAAM,GAAK,EAAM,IAAM,IAAI,MAAM,CACjC,GAAI,EAAE,WAAW,UAAU,EAAI,EAAE,WAAW,UAAU,CAAE,CACtD,EAAgB,EAChB,OAQJ,OALI,IAAkB,KACpB,EAAM,OAAO,EAAgB,EAAG,EAAG,mBAAoB,qBAAsB,GAAG,CAChF,EAAS,EAAM,KAAK;EAAK,EAGpB,EA+CT,SAAgB,EAAmB,EAAiD,CAClF,IAAM,EAAiB,GAAS,UAAY,GACtC,EAAa,GAAS,WAC5B,MAAO,CACL,KAAM,gBACN,QAAS,MACT,UAAU,EAAM,EAAI,CAElB,IAAM,EAAQ,EAAG,MAAM,IAAI,CAAC,GACvB,KAAM,SAAS,QAAQ,CAC5B,OAAQ,SAAY,CAClB,IAAM,EAAS,EAAU,EAAM,EAAM,CAC/B,EACJ,GAAc,KAAoD,EAAO,KAApD,EAAkB,EAAO,KAAM,EAAW,CAC3D,EAAa,EAAmB,EAAS,CAE3C,EAMA,GAAkB,IAAe,MAAQ,EAAgB,EAAS,GAAK,SACzE,EAAM,EAAmB,EAAU,EAAW,CACrC,IAAe,MAWxB,EAAM,EAEN,EAAM,EAAkB,EAAI,GAT5B,EAAM,EAAc,EAAU,EAAW,CAGzC,EAAM,EAAwB,EAAK,EAAW,CAE9C,EAAM,EAAkB,EAAI,EAgB9B,GAAI,CACF,IAAM,EAAO,MAAM,OAAO,QAU1B,MATI,qBAAsB,GAAQ,OAAO,EAAK,kBAAqB,WAG1D,CAAE,KAAM,EAAK,WAAY,KAAM,IAAK,KAAM,CAM5C,CAAE,MAAM,MAJQ,EAAK,qBAAqB,EAAK,eAAgB,CACpE,OAAQ,SACR,UAAW,GACZ,CAAC,EACsB,KAAM,IAAK,KAAM,MACnC,CAEN,MAAO,CAAE,KAAM,EAAK,IAAK,KAAM,KAE/B,EAEP"}
1
+ {"version":3,"file":"index.js","names":[],"sources":["../js/index.ts"],"sourcesContent":["/**\n * @aihu/compiler — TypeScript wrapper around the aihu-compile Rust binary.\n *\n * Exports:\n * transform(source, id) — compile a single .aihu file to TypeScript\n * aihuCompilerPlugin() — Vite plugin that wires transform() into the build\n */\nimport { execFileSync } from 'node:child_process'\nimport { basename, dirname, resolve } from 'node:path'\nimport { fileURLToPath } from 'node:url'\n\n// Binary resolution: env var override, fallback to the bin/ directory written\n// by the postinstall hook (packages/compiler/bin/aihu-compile[.exe]).\nconst ext = process.platform === 'win32' ? '.exe' : ''\nconst binPath: string =\n process.env.SCRIBE_COMPILE_BIN ??\n resolve(dirname(fileURLToPath(import.meta.url)), `../bin/aihu-compile${ext}`)\n\n// Minimal VitePlugin interface — avoids importing from 'vite' at compile time.\n// Structurally compatible with Vite's Plugin type.\ninterface VitePlugin {\n readonly name: string\n enforce?: 'pre' | 'post'\n transform?: (\n code: string,\n id: string,\n ) => Promise<{ code: string; map: null }> | { code: string; map: null } | null | undefined\n}\n\n/**\n * Options for `aihuCompilerPlugin()` (Plan 3.3 — Islands).\n */\nexport interface AihuCompilerPluginOptions {\n /**\n * When `true` (default), components classified as `'static'` by\n * `_classifyIsland()` are emitted with a minimal HTML-only registration\n * shim that ships **zero** `@aihu/runtime` and `@aihu/signals` JS to\n * the browser. Components classified as `'interactive'` retain the\n * full runtime path.\n *\n * Setting `islands: false` opts every component back into the unified\n * runtime path (Plan 3.2 baseline behaviour).\n */\n islands?: boolean\n\n /**\n * Project-wide shadow-DOM mode applied to every `.aihu` SFC compiled\n * by this plugin instance. When set, the plugin post-processes the\n * compiled JS to inject `, { shadowMode: '<mode>' }` as the third arg\n * to the emitted `defineElement(tag, defineComponent(...))` call.\n *\n * - `'open'` — default browser behaviour (shadow root, externally readable).\n * - `'closed'` — shadow root, externally hidden.\n * - `'none'` — **no shadow root.** The component mounts into its own\n * element. Required for global utility-class CSS frameworks\n * like Tailwind, UnoCSS, Pico that rely on the cascade.\n *\n * Per-component override is not yet supported via SFC syntax (post-v1).\n * For per-component control today, hand-author the component with\n * `defineElement(tag, Ctor, { shadowMode: '...' })`.\n */\n shadowMode?: 'open' | 'closed' | 'none'\n}\n\n/**\n * Inject `{ shadowMode: '...' }` as the third argument to the emitted\n * `defineElement('tag', defineComponent(...))` call. The compiler emits\n * exactly two arguments today; this rewrites the closing of the\n * defineElement call to include the options object. Idempotent — leaves\n * code untouched when the closer is not in the expected shape.\n *\n * @internal\n */\nexport function _injectShadowMode(code: string, mode: 'open' | 'closed' | 'none'): string {\n // Match the trailing `))` that closes `defineElement(tag, defineComponent(setup))`.\n // The compiler always emits this exact two-paren close as the final tokens of\n // the defineElement call — we anchor on it and append the options object.\n // biome-ignore lint/correctness/noEmptyCharacterClassInRegex: [^] is valid JS — matches any char including newlines\n const re = /(defineElement\\(\\s*['\"][^'\"]+['\"]\\s*,\\s*defineComponent\\([^]*\\))\\s*\\)/\n const replaced = code.replace(re, (_m, inner: string) => `${inner}, { shadowMode: '${mode}' })`)\n return replaced\n}\n\n/**\n * Classify the compiled output of a single `.aihu` module as either a\n * **static** island (no reactive state — purely declarative DOM) or an\n * **interactive** island (uses the signals reactivity system).\n *\n * The heuristic is intentionally conservative: any source-level reference\n * to a primitive that requires the `defineComponent` owner context flips\n * the file to `'interactive'`. False positives (e.g. a string literal\n * containing `signal(`) are tolerable — they only forfeit the static-island\n * optimisation. False negatives are forbidden: a static-classified file\n * MUST NOT depend on the signals runtime at execution time.\n *\n * Owner-requiring primitives covered:\n * - `signal(`, `computed(`, `effect(`, `setSignal(` (signals runtime)\n * - `onMount(`, `onCleanup(` (lifecycle hooks — throw `no owner` outside\n * `defineComponent` because they push into the active owner's mount/\n * cleanup queues)\n *\n * Plan 3.3 / acceptance criterion 1.\n *\n * @internal\n */\nexport function _classifyIsland(compiledCode: string): 'static' | 'interactive' {\n // Match call sites of the reactive + lifecycle primitives. Use word-boundary\n // anchors so identifiers like `mySignal(` or `__effect(` do not trip the\n // heuristic. The `(` is required so that bare imports of the names in an\n // unused `import { signal }` line do not flip an otherwise-static module.\n return /\\b(?:signal|computed|effect|setSignal|onMount|onCleanup)\\s*\\(/.test(compiledCode)\n ? 'interactive'\n : 'static'\n}\n\n/**\n * Extract the custom element tag name from compiler-emitted code.\n * The compiler always emits `defineElement('tag-name', ...)` as the\n * first call — pull the first string literal argument.\n * Returns `null` if no `defineElement` call is found.\n * @internal\n */\nfunction _extractElementTag(code: string): string | null {\n const m = /defineElement\\(\\s*['\"]([^'\"]+)['\"]/m.exec(code)\n return m ? (m[1] ?? null) : null\n}\n\n/**\n * Instrument a compiled `.aihu` module with HMR support.\n *\n * The compiler always emits:\n *\n * import { defineComponent, defineElement } from '@aihu/runtime'\n * defineElement('tag', defineComponent((_ctx) => { ... }))\n *\n * This function:\n *\n * 1. Adds `_hmrReplace` to the `@aihu/runtime` import.\n * 2. Prepends a module-level slot variable `__aihu_setup__`.\n * 3. Rewrites the single `defineComponent(` call so the setup function\n * is captured via an assignment expression:\n * `defineComponent(__aihu_setup__ = ` (valid JS; assignment has\n * lower precedence than arrow fn, so `defineComponent` still\n * receives the function as its argument).\n * 4. Appends `export { __aihu_setup__ as default }` so that Vite's\n * `import.meta.hot.accept` callback receives the new setup via\n * `newModule.default` on hot reload.\n * 5. Appends the `import.meta.hot.accept` block, gated on `__DEV__`.\n *\n * The `__DEV__` guard ensures production bundlers (where they replace\n * `__DEV__` with `false`) dead-code-eliminate the entire HMR block.\n *\n * @internal\n */\nfunction _buildHmrCode(compiledCode: string, elementTag: string): string {\n // Step 1 — add _hmrReplace to the @aihu/runtime import.\n const withImport = compiledCode.replace(\n /import\\s*\\{([^}]*)\\}\\s*from\\s*'@aihu\\/runtime'/,\n (_m, imports: string) => {\n const parts = imports\n .split(',')\n .map((s) => s.trim())\n .filter(Boolean)\n if (!parts.includes('_hmrReplace')) parts.push('_hmrReplace')\n return `import { ${parts.join(', ')} } from '@aihu/runtime'`\n },\n )\n\n // Step 2+3 — prepend slot variable and rewrite the defineComponent call.\n // Compiler emits exactly one `defineComponent(` followed by a function expr.\n // Rewrite: defineComponent(fn) → defineComponent(__aihu_setup__ = fn)\n // Assignment expression evaluates to `fn`, so defineComponent still\n // receives the setup function as its first argument unchanged.\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n const preamble = `let __aihu_setup__: ((ctx: any) => any) | undefined\\n`\n\n const patchedBody = withImport.replace(/\\bdefineComponent\\(/, 'defineComponent(__aihu_setup__ = ')\n\n const tag = JSON.stringify(elementTag)\n // Step 4+5 — postamble with default export and HMR acceptance.\n const postamble = `\nexport { __aihu_setup__ as default }\n\nif (typeof __DEV__ !== 'undefined' && __DEV__ && import.meta.hot) {\n import.meta.hot.accept((newModule) => {\n if (!newModule) return\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n const newSetup = (newModule as any)['default']\n if (typeof newSetup !== 'function') return\n document.querySelectorAll(${tag}).forEach((el) => {\n _hmrReplace(el as HTMLElement, newSetup)\n })\n })\n}\n`\n\n return preamble + patchedBody + postamble\n}\n\n/**\n * Rewrite an interactive-island module so its `connectedCallback` waits\n * for the element to scroll into view before mounting. Plan 3.3 — applied\n * only when the consumer adds `defer` to the custom element tag (e.g.\n * `<my-counter defer>`); the runtime helper checks the attribute and\n * either mounts immediately or registers an `IntersectionObserver`.\n *\n * Implementation: the helper is added as a `_hydrateOnVisible` import\n * from `@aihu/runtime`, and the compiler-emitted `defineElement(...)`\n * call is wrapped in a `defineElement` that intercepts `connectedCallback`\n * to honour the `defer` attribute.\n *\n * The whole indirection is tree-shaken when no `.aihu` module reaches\n * this branch, because `_hydrateOnVisible` is exported from its own\n * sibling module inside `@aihu/runtime`.\n *\n * @internal\n */\nexport function _buildDeferredHydration(compiledCode: string, elementTag: string): string {\n // Add _hydrateOnVisible to the @aihu/runtime import.\n const withImport = compiledCode.replace(\n /import\\s*\\{([^}]*)\\}\\s*from\\s*'@aihu\\/runtime'/,\n (_m, imports: string) => {\n const parts = imports\n .split(',')\n .map((s) => s.trim())\n .filter(Boolean)\n if (!parts.includes('_hydrateOnVisible')) parts.push('_hydrateOnVisible')\n return `import { ${parts.join(', ')} } from '@aihu/runtime'`\n },\n )\n\n // Wrap the class returned by defineComponent BEFORE defineElement\n // consumes it. The HTML spec caches lifecycle callbacks at\n // customElements.define() time, so we MUST mutate the prototype\n // before that call — not after. We accomplish this with a synchronous\n // helper invoked between defineComponent and defineElement.\n //\n // Source pattern (compiler-emitted):\n // defineElement('tag', defineComponent((_ctx) => { ... }))\n //\n // After this rewrite:\n // defineElement('tag', __aihu_wrap_defer__(defineComponent((_ctx) => { ... })))\n //\n // …with __aihu_wrap_defer__ defined in the appended preamble.\n const patched = withImport.replace(\n /defineElement\\(\\s*('[^']+'|\"[^\"]+\")\\s*,\\s*defineComponent\\(/,\n (_m, tagLit: string) => `defineElement(${tagLit}, __aihu_wrap_defer__(defineComponent(`,\n )\n // Match the closing `))` of the defineElement call. The HMR pass may\n // have inserted `__aihu_setup__ = ` before the inner function, but\n // the trailing `))` shape is unchanged. Replace exactly one occurrence\n // by anchoring on end-of-string trim; bail if the shape does not match.\n if (patched === withImport) {\n // The expected `defineElement(<tag>, defineComponent(` shape was not\n // present (e.g. compiler output changed). Skip defer wrapping rather\n // than emit broken code.\n return compiledCode\n }\n // Add a trailing `)` to balance the extra `(` from __aihu_wrap_defer__.\n // Source shape after _buildHmrCode is:\n // defineElement('tag', defineComponent(__aihu_setup__ = (_ctx) => {...}))\n // export { __aihu_setup__ as default }\n // if (typeof __DEV__ !== ...) { ... }\n // We must close BEFORE the export line. Match the first `))` followed\n // by a newline and `export` (or end-of-string for the unwrapped case).\n let balanced = patched.replace(/\\)\\s*\\)\\s*\\nexport\\s/, ')))\\nexport ')\n if (balanced === patched) {\n // No HMR postamble — the `))` is at end-of-string.\n balanced = patched.replace(/\\)\\s*\\)\\s*$/, ')))\\n')\n }\n if (balanced === patched) {\n // Could not find the matching `))` — bail out.\n return compiledCode\n }\n\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n const helper = `\n// Plan 3.3 (Islands) — defer attribute support. Wraps the constructor\n// returned by defineComponent so instances bearing the \\`defer\\` attribute\n// hydrate lazily via IntersectionObserver. Bare instances retain the\n// eager Plan 3.2 hydration path.\nfunction __aihu_wrap_defer__<T extends typeof HTMLElement>(Ctor: T): T {\n const orig = (Ctor.prototype as unknown as { connectedCallback?: () => void }).connectedCallback\n if (typeof orig !== 'function') return Ctor\n ;(Ctor.prototype as unknown as { connectedCallback: () => void }).connectedCallback = function (this: HTMLElement) {\n if (this.hasAttribute('defer')) {\n _hydrateOnVisible(this, () => orig.call(this))\n } else {\n orig.call(this)\n }\n }\n return Ctor\n}\n`\n void elementTag\n return helper + balanced\n}\n\n/**\n * Build a static-island shim for a compiled module.\n *\n * The compiled module emitted by the Rust codegen has the shape:\n *\n * import { branch, leaf, slot } from '@aihu/arbor'\n * import { defineComponent, defineElement } from '@aihu/runtime'\n * defineElement('tag', defineComponent((_ctx) => { return <tree> }))\n *\n * For a static island we know `<tree>` contains no `signal(`/`computed(`\n * calls. We can therefore:\n *\n * 1. Drop the `@aihu/runtime` import (saves ~600 B gz of defineComponent\n * + defineElement + bootstrap glue).\n * 2. Replace `defineElement(tag, defineComponent(setup))` with a tiny\n * inline class that mounts the tree directly via `mount()` (which the\n * arbor barrel already exports).\n * 3. Tag the file with a `// SCRIBE_STATIC_ISLAND` comment so consumers\n * can audit which routes shipped zero-JS-runtime.\n *\n * Falls back to the original code if the regex shape does not match\n * (defensive: a future compiler change must opt back into static-island\n * emission explicitly rather than silently break).\n *\n * @internal\n */\nexport function _buildStaticIsland(compiledCode: string, elementTag: string): string {\n // Confirm the shape we expect: a single defineElement(...) call wrapping\n // a single defineComponent(...) call. Bail out otherwise.\n const callRe = /defineElement\\(\\s*['\"][^'\"]+['\"]\\s*,\\s*defineComponent\\(/\n if (!callRe.test(compiledCode)) return compiledCode\n\n // Strip the `@aihu/runtime` import line entirely — static islands\n // don't reference defineComponent/defineElement after the rewrite.\n const withoutRuntimeImport = compiledCode.replace(\n /^\\s*import\\s*\\{[^}]*\\}\\s*from\\s*'@aihu\\/runtime'\\s*;?\\s*$/m,\n '',\n )\n\n // Ensure `mount` is imported from @aihu/arbor (it already exposes\n // branch/leaf/slot, so we just append `mount` to the existing list).\n const withArborMount = withoutRuntimeImport.replace(\n /import\\s*\\{([^}]*)\\}\\s*from\\s*'@aihu\\/arbor'/,\n (_m, imports: string) => {\n const parts = imports\n .split(',')\n .map((s) => s.trim())\n .filter(Boolean)\n if (!parts.includes('mount')) parts.push('mount')\n return `import { ${parts.join(', ')} } from '@aihu/arbor'`\n },\n )\n\n // Replace `defineElement('tag', defineComponent((_ctx) => { ... }))`\n // with an inline `customElements.define` whose connectedCallback mounts\n // the static tree. The setup function is captured verbatim by replacing\n // the wrapping calls with anonymous-IIFE bookends.\n const tagJson = JSON.stringify(elementTag)\n const rewritten = withArborMount\n .replace(\n /defineElement\\(\\s*['\"][^'\"]+['\"]\\s*,\\s*defineComponent\\(/,\n `customElements.define(${tagJson}, class extends HTMLElement {\\n connectedCallback() {\\n const root = this.attachShadow({ mode: 'open' })\\n const __aihu_setup__ = (`,\n )\n .replace(\n /\\)\\s*\\)\\s*$/,\n `)\\n mount(__aihu_setup__({ host: root, element: this }), root)\\n }\\n})\\n`,\n )\n\n return `// SCRIBE_STATIC_ISLAND — zero @aihu/runtime references\\n${rewritten}`\n}\n\n/**\n * Compile a .aihu source string to TypeScript.\n * map is null — source maps are deferred to v1 (OQ-C8)\n */\nexport function transform(source: string, id: string): { code: string; map: null } {\n const stem = basename(id, '.aihu')\n const code = execFileSync(binPath, ['--stdin', '--tag', stem, '--path', id], {\n input: source,\n encoding: 'utf8',\n })\n return {\n code,\n map: null, // source maps deferred to v1 (OQ-C8)\n }\n}\n\n/**\n * Inject `_setMount(mount)` + `_setSignal(signal)` auto-wiring into a compiled\n * `.aihu` module. Adds the necessary symbols to existing imports and inserts\n * the boot calls right after the last `import` statement.\n *\n * @internal\n */\nexport function _injectAutoWiring(code: string): string {\n // 1. Add `mount` to the @aihu/arbor import (or create it).\n let result: string\n if (code.includes(\"from '@aihu/arbor'\")) {\n result = code.replace(\n /import\\s*\\{([^}]*)\\}\\s*from\\s*'@aihu\\/arbor'/,\n (_m: string, imports: string) => {\n const parts = imports\n .split(',')\n .map((s) => s.trim())\n .filter(Boolean)\n if (!parts.includes('mount')) parts.push('mount')\n return `import { ${parts.join(', ')} } from '@aihu/arbor'`\n },\n )\n } else {\n result = `import { mount } from '@aihu/arbor'\\n${code}`\n }\n\n // 2. Add `signal` to the non-type @aihu/signals import (or create it).\n // Note: `import\\s+\\{` does NOT match `import type {` (the regex needs `{` immediately\n // after whitespace, whereas `import type {` has `type` in between). No negation guard\n // is needed — the replace callback below already skips `import type` lines.\n if (/import\\s+\\{[^}]*\\}\\s+from\\s+'@aihu\\/signals'/.test(result)) {\n // There IS a value import from signals — add `signal` if missing.\n result = result.replace(\n /import\\s*\\{([^}]*)\\}\\s*from\\s*'@aihu\\/signals'/,\n (_m: string, imports: string) => {\n // Skip type-only imports\n if (_m.startsWith('import type')) return _m\n const parts = imports\n .split(',')\n .map((s) => s.trim())\n .filter(Boolean)\n if (!parts.includes('signal')) parts.push('signal')\n return `import { ${parts.join(', ')} } from '@aihu/signals'`\n },\n )\n } else if (!/import.*from\\s*'@aihu\\/signals'/.test(result)) {\n // No signals import at all — insert after arbor import\n result = result.replace(\n /import\\s*\\{[^}]*\\}\\s*from\\s*'@aihu\\/arbor'/,\n (m: string) => `${m}\\nimport { signal } from '@aihu/signals'`,\n )\n }\n // If only `import type { Signal }` exists, insert value import after it\n else if (\n /import\\s+type\\s+\\{[^}]*\\}\\s+from\\s+'@aihu\\/signals'/.test(result) &&\n !result.match(/import\\s+\\{[^}]*\\}\\s+from\\s+'@aihu\\/signals'/)\n ) {\n result = result.replace(\n /(import\\s+type\\s+\\{[^}]*\\}\\s+from\\s+'@aihu\\/signals')/,\n (_m: string, typeImport: string) => `${typeImport}\\nimport { signal } from '@aihu/signals'`,\n )\n }\n\n // 3. Add `_setMount`, `_setSignal` to the @aihu/runtime import.\n result = result.replace(\n /import\\s*\\{([^}]*)\\}\\s*from\\s*'@aihu\\/runtime'/,\n (_m: string, imports: string) => {\n const parts = imports\n .split(',')\n .map((s) => s.trim())\n .filter(Boolean)\n if (!parts.includes('_setMount')) parts.push('_setMount')\n if (!parts.includes('_setSignal')) parts.push('_setSignal')\n return `import { ${parts.join(', ')} } from '@aihu/runtime'`\n },\n )\n\n // 4. Insert boot calls after the last `import` statement.\n const lines = result.split('\\n')\n let lastImportIdx = -1\n for (let i = lines.length - 1; i >= 0; i--) {\n const t = (lines[i] ?? '').trim()\n if (t.startsWith('import ') || t.startsWith('import{')) {\n lastImportIdx = i\n break\n }\n }\n if (lastImportIdx !== -1) {\n lines.splice(lastImportIdx + 1, 0, '_setMount(mount)', '_setSignal(signal)', '')\n result = lines.join('\\n')\n }\n\n return result\n}\n\n/**\n * Vite plugin that compiles .aihu files to TypeScript during build and dev.\n *\n * Use `enforce: 'pre'` so the hook fires before Vite/Rollup's built-in\n * parsers attempt to process the raw .aihu content as JavaScript.\n *\n * @example\n * // vite.config.ts\n * import { aihuCompilerPlugin } from '@aihu/compiler'\n * export default { plugins: [aihuCompilerPlugin()] }\n *\n * **Known Limitation — Bun + Rollup4 ESM incompatibility (v0):**\n *\n * `bun vite build` fails in the `fixtures/vite-counter` fixture with two\n * cascading errors:\n *\n * 1. **Missing devDependency:** `vite` is declared only as an optional\n * `peerDependency` in `packages/compiler/package.json`. Bun does not\n * install optional peers automatically, so `bun vite build` exits\n * immediately with `Cannot find package 'vite'`.\n *\n * 2. **Bun + Rollup4 bridge:** Even with Vite installed, Bun processes\n * `vite.config.ts` through its own internal bundler before handing off\n * to Rollup4. When `@aihu/compiler` is resolved from the workspace\n * symlink (`dist/index.js`), Bun's ESM loader evaluates the module at\n * config-load time. The subprocess call inside `transform()` depends on\n * the Rust binary being at `../bin/aihu-compile` relative to `dist/`\n * (written by the postinstall hook). In a dev workspace where postinstall\n * has not run, this path does not exist and `execFileSync` throws. Bun surfaces\n * the error as a config-load failure, not a per-file transform error,\n * causing the entire build to abort before any `.aihu` file is\n * processed.\n *\n * **Workaround (v0):** Use `bun run integrate.ts` directly from\n * `packages/compiler/fixtures/vite-counter/`. This script calls\n * `transform()` from `@aihu/compiler` without involving Vite or Rollup.\n * Preconditions: (1) `cargo build --release` in `packages/compiler/`,\n * (2) `bun install` at the repo root.\n *\n * **v1 resolution:** Add `vite` as a `devDependency` in\n * `packages/compiler/package.json`; add a WASM or pre-built binary\n * strategy so the Rust binary is bundled with the npm package and does not\n * require a separate `cargo build --release` step.\n */\nexport function aihuCompilerPlugin(options?: AihuCompilerPluginOptions): VitePlugin {\n const islandsEnabled = options?.islands !== false\n const shadowMode = options?.shadowMode\n return {\n name: 'aihu-compiler',\n enforce: 'pre',\n transform(code, id) {\n // Strip Vite query strings (e.g. `?import`, `?t=...`) before checking the extension.\n const rawId = id.split('?')[0]!\n if (!rawId.endsWith('.aihu')) return\n return (async () => {\n const result = transform(code, rawId)\n const compiled =\n shadowMode != null ? _injectShadowMode(result.code, shadowMode) : result.code\n const elementTag = _extractElementTag(compiled)\n\n let out: string\n\n // Plan 3.3 — static-island fast path. Bypasses HMR injection because\n // a component with no signals has no setup state to hot-replace.\n // Static islands strip @aihu/runtime entirely — do NOT inject auto-wiring\n // (it would reference _setMount/_setSignal as undefined identifiers).\n if (islandsEnabled && elementTag !== null && _classifyIsland(compiled) === 'static') {\n out = _buildStaticIsland(compiled, elementTag)\n } else if (elementTag !== null) {\n // Inject HMR instrumentation. The injected block is gated on\n // `typeof __DEV__ !== 'undefined' && __DEV__` so production\n // bundlers dead-code-eliminate it when they set __DEV__ = false.\n out = _buildHmrCode(compiled, elementTag)\n // Plan 3.3 — interactive islands also gain `defer` attribute\n // support so individual instances can opt into lazy hydration.\n out = _buildDeferredHydration(out, elementTag)\n // Inject auto-wiring so consumers don't need a manual main.ts bootstrap.\n out = _injectAutoWiring(out)\n } else {\n out = compiled\n // Inject auto-wiring so consumers don't need a manual main.ts bootstrap.\n out = _injectAutoWiring(out)\n }\n\n // The Rust compiler emits TypeScript (type casts, import type, etc.) and\n // the injected HMR / defer helpers also contain TS generics and casts.\n // Vite does NOT re-run its TS-strip step when a plugin returns code for a\n // non-.ts ID, so we must strip types ourselves before returning.\n //\n // Priority: always try transformWithEsbuild first — it strips types to\n // plain JS in both Vite 5 (via esbuild) and Vite 8 (deprecated wrapper).\n // Using moduleType:'ts' only as a last resort because `import('vite')`\n // resolves to the root node_modules vite (which may be v8 even when a\n // consumer project runs v5), causing v5's Rollup to receive raw TypeScript\n // and fail on import-type / as-casts.\n try {\n const vite = await import('vite')\n if ('transformWithEsbuild' in vite && typeof vite.transformWithEsbuild === 'function') {\n const stripped = await vite.transformWithEsbuild(out, 'component.ts', {\n target: 'esnext',\n sourcemap: false,\n })\n return { code: stripped.code, map: null }\n }\n // Fallback for future Vite versions where esbuild is fully removed:\n // return TS and let Rolldown strip types natively.\n // biome-ignore lint/suspicious/noExplicitAny: moduleType is rolldown API\n return { code: out, moduleType: 'ts', map: null } as any\n } catch {\n // If running outside Vite (e.g. tests, standalone transform), return as-is.\n return { code: out, map: null }\n }\n })()\n },\n }\n}\n"],"mappings":"0JAaA,MAAM,EAAM,QAAQ,WAAa,QAAU,OAAS,GAC9C,EACJ,QAAQ,IAAI,oBACZ,EAAQ,EAAQ,EAAc,OAAO,KAAK,IAAI,CAAC,CAAE,sBAAsB,IAAM,CAyD/E,SAAgB,EAAkB,EAAc,EAA0C,CAOxF,OADiB,EAAK,QAAQ,yEAAK,EAAI,IAAkB,GAAG,EAAM,mBAAmB,EAAK,MAC3E,CAyBjB,SAAgB,EAAgB,EAAgD,CAK9E,MAAO,gEAAgE,KAAK,EAAa,CACrF,cACA,SAUN,SAAS,EAAmB,EAA6B,CACvD,IAAM,EAAI,sCAAsC,KAAK,EAAK,CAC1D,OAAO,EAAK,EAAE,IAAM,KAAQ,KA8B9B,SAAS,EAAc,EAAsB,EAA4B,CAEvE,IAoBM,EApBa,EAAa,QAC9B,kDACC,EAAI,IAAoB,CACvB,IAAM,EAAQ,EACX,MAAM,IAAI,CACV,IAAK,GAAM,EAAE,MAAM,CAAC,CACpB,OAAO,QAAQ,CAElB,OADK,EAAM,SAAS,cAAc,EAAE,EAAM,KAAK,cAAc,CACtD,YAAY,EAAM,KAAK,KAAK,CAAC,0BAYpB,CAAW,QAAQ,sBAAuB,oCAAoC,CAI5F,EAAY;;;;;;;;;gCAFN,KAAK,UAAU,EAWM,CAAC;;;;;EAOlC,MAAO;EAAW,EAAc,EAqBlC,SAAgB,EAAwB,EAAsB,EAA4B,CAExF,IAAM,EAAa,EAAa,QAC9B,kDACC,EAAI,IAAoB,CACvB,IAAM,EAAQ,EACX,MAAM,IAAI,CACV,IAAK,GAAM,EAAE,MAAM,CAAC,CACpB,OAAO,QAAQ,CAElB,OADK,EAAM,SAAS,oBAAoB,EAAE,EAAM,KAAK,oBAAoB,CAClE,YAAY,EAAM,KAAK,KAAK,CAAC,0BAEvC,CAeK,EAAU,EAAW,QACzB,+DACC,EAAI,IAAmB,iBAAiB,EAAO,wCACjD,CAKD,GAAI,IAAY,EAId,OAAO,EAST,IAAI,EAAW,EAAQ,QAAQ,uBAAwB;SAAe,CA8BtE,OA7BI,IAAa,IAEf,EAAW,EAAQ,QAAQ,cAAe;EAAQ,EAEhD,IAAa,EAER,EAuBF;;;;;;;;;;;;;;;;;EAAS,EA6BlB,SAAgB,EAAmB,EAAsB,EAA4B,CAInF,GAAI,CAAC,2DAAO,KAAK,EAAa,CAAE,OAAO,EAWvC,IAAM,EAPuB,EAAa,QACxC,6DACA,GAKyC,CAAC,QAC1C,gDACC,EAAI,IAAoB,CACvB,IAAM,EAAQ,EACX,MAAM,IAAI,CACV,IAAK,GAAM,EAAE,MAAM,CAAC,CACpB,OAAO,QAAQ,CAElB,OADK,EAAM,SAAS,QAAQ,EAAE,EAAM,KAAK,QAAQ,CAC1C,YAAY,EAAM,KAAK,KAAK,CAAC,wBAEvC,CAMK,EAAU,KAAK,UAAU,EAAW,CAW1C,MAAO,4DAVW,EACf,QACC,2DACA,yBAAyB,EAAQ,4IAClC,CACA,QACC,cACA;;;;EAGwE,GAO9E,SAAgB,EAAU,EAAgB,EAAyC,CAMjF,MAAO,CACL,KALW,EAAa,EAAS,CAAC,UAAW,QADlC,EAAS,EAAI,QACkC,CAAE,SAAU,EAAG,CAAE,CAC3E,MAAO,EACP,SAAU,OACX,CAEK,CACJ,IAAK,KACN,CAUH,SAAgB,EAAkB,EAAsB,CAEtD,IAAI,EACJ,AAaE,EAbE,EAAK,SAAS,qBAAqB,CAC5B,EAAK,QACZ,gDACC,EAAY,IAAoB,CAC/B,IAAM,EAAQ,EACX,MAAM,IAAI,CACV,IAAK,GAAM,EAAE,MAAM,CAAC,CACpB,OAAO,QAAQ,CAElB,OADK,EAAM,SAAS,QAAQ,EAAE,EAAM,KAAK,QAAQ,CAC1C,YAAY,EAAM,KAAK,KAAK,CAAC,wBAEvC,CAEQ,wCAAwC,IAO/C,+CAA+C,KAAK,EAAO,CAE7D,EAAS,EAAO,QACd,kDACC,EAAY,IAAoB,CAE/B,GAAI,EAAG,WAAW,cAAc,CAAE,OAAO,EACzC,IAAM,EAAQ,EACX,MAAM,IAAI,CACV,IAAK,GAAM,EAAE,MAAM,CAAC,CACpB,OAAO,QAAQ,CAElB,OADK,EAAM,SAAS,SAAS,EAAE,EAAM,KAAK,SAAS,CAC5C,YAAY,EAAM,KAAK,KAAK,CAAC,0BAEvC,CACS,kCAAkC,KAAK,EAAO,CASxD,sDAAsD,KAAK,EAAO,EAClE,CAAC,EAAO,MAAM,+CAA+C,GAE7D,EAAS,EAAO,QACd,yDACC,EAAY,IAAuB,GAAG,EAAW,0CACnD,EAbD,EAAS,EAAO,QACd,6CACC,GAAc,GAAG,EAAE,0CACrB,CAcH,EAAS,EAAO,QACd,kDACC,EAAY,IAAoB,CAC/B,IAAM,EAAQ,EACX,MAAM,IAAI,CACV,IAAK,GAAM,EAAE,MAAM,CAAC,CACpB,OAAO,QAAQ,CAGlB,OAFK,EAAM,SAAS,YAAY,EAAE,EAAM,KAAK,YAAY,CACpD,EAAM,SAAS,aAAa,EAAE,EAAM,KAAK,aAAa,CACpD,YAAY,EAAM,KAAK,KAAK,CAAC,0BAEvC,CAGD,IAAM,EAAQ,EAAO,MAAM;EAAK,CAC5B,EAAgB,GACpB,IAAK,IAAI,EAAI,EAAM,OAAS,EAAG,GAAK,EAAG,IAAK,CAC1C,IAAM,GAAK,EAAM,IAAM,IAAI,MAAM,CACjC,GAAI,EAAE,WAAW,UAAU,EAAI,EAAE,WAAW,UAAU,CAAE,CACtD,EAAgB,EAChB,OAQJ,OALI,IAAkB,KACpB,EAAM,OAAO,EAAgB,EAAG,EAAG,mBAAoB,qBAAsB,GAAG,CAChF,EAAS,EAAM,KAAK;EAAK,EAGpB,EA+CT,SAAgB,EAAmB,EAAiD,CAClF,IAAM,EAAiB,GAAS,UAAY,GACtC,EAAa,GAAS,WAC5B,MAAO,CACL,KAAM,gBACN,QAAS,MACT,UAAU,EAAM,EAAI,CAElB,IAAM,EAAQ,EAAG,MAAM,IAAI,CAAC,GACvB,KAAM,SAAS,QAAQ,CAC5B,OAAQ,SAAY,CAClB,IAAM,EAAS,EAAU,EAAM,EAAM,CAC/B,EACJ,GAAc,KAAoD,EAAO,KAApD,EAAkB,EAAO,KAAM,EAAW,CAC3D,EAAa,EAAmB,EAAS,CAE3C,EAMA,GAAkB,IAAe,MAAQ,EAAgB,EAAS,GAAK,SACzE,EAAM,EAAmB,EAAU,EAAW,CACrC,IAAe,MAWxB,EAAM,EAEN,EAAM,EAAkB,EAAI,GAT5B,EAAM,EAAc,EAAU,EAAW,CAGzC,EAAM,EAAwB,EAAK,EAAW,CAE9C,EAAM,EAAkB,EAAI,EAkB9B,GAAI,CACF,IAAM,EAAO,MAAM,OAAO,QAW1B,MAVI,yBAA0B,GAAQ,OAAO,EAAK,sBAAyB,WAKlE,CAAE,MAAM,MAJQ,EAAK,qBAAqB,EAAK,eAAgB,CACpE,OAAQ,SACR,UAAW,GACZ,CAAC,EACsB,KAAM,IAAK,KAAM,CAKpC,CAAE,KAAM,EAAK,WAAY,KAAM,IAAK,KAAM,MAC3C,CAEN,MAAO,CAAE,KAAM,EAAK,IAAK,KAAM,KAE/B,EAEP"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@aihu/compiler",
3
- "version": "0.1.7",
3
+ "version": "0.1.9",
4
4
  "license": "MIT",
5
5
  "type": "module",
6
6
  "main": "./dist/index.js",