Compiler pipeline
Status: Implemented architecture and contributor contract.
Goldar has one template compiler split across a Go semantic core and TypeScript integrations. Go
owns template meaning and artifact emission. TypeScript owns process management, project graph
integration, CSS transformation, editor coordination, and runtime validation. Application authors
do not install Go or call either layer directly when using the published goldar package.
Ownership map
compiler/typedhandlebars/scanner.goandsemantics.goscan incomplete source, build the recoverable source document, validate the supported language, and create one semantic model.compiler/typedhandlebars/compiler.goemits the Typecheck probe and UTF-16 source mappings.compiler/typedhandlebars/lower.goemits the recursive View program from the same model, while style and frontmatter analysis emit the Stylesheet artifact and template dependency metadata.compiler/cmd/goldar-compilerexposes compilation as a long-lived, newline-delimited JSON-RPC process and negotiates the protocol and artifact versions before work begins.packages/compilerowns the Node process client, exact declaration synchronization, imported template graph validation, component discovery, stylesheet transformation, and Vite modules.packages/corevalidates and renders View programs. It owns escaping, trusted HTML, dependency authentication, and instruction execution.packages/typed-handlebarscombines compiler mappings with a persistent TypeScript language server and maps completions, hover, navigation, and diagnostics back to.hbssource.packages/goldarassembles these private workspaces into the public package and selects the platform compiler executable.
The template-language reference is the canonical authoring contract. Proposals cannot extend the language until compiler, runtime, editor, and package tests make the behavior executable.
Artifact contract
One successful compile returns a recoverable TemplateDocument, ordered diagnostics, and:
| Output | Version | Consumer |
|---|---|---|
| Typecheck probe and mappings | v1 | TypeScript and editor tooling |
| View program | v3 | goldar/compiler-runtime and goldar/view |
| Stylesheet artifact | v1 | Vite stylesheet compilation |
| Template dependency metadata | Protocol-owned | Type sync, Vite, and View dependency slots |
The View program is omitted when any compiler error is present. The Typecheck probe and source document remain useful during incomplete editing. The Stylesheet artifact and dependency metadata are always present, including empty arrays for templates that have neither feature.
These are cross-language invariants:
- Every source and generated offset is a zero-based UTF-16 code-unit offset.
- Ranges are half-open; syntax ranges are non-empty while mappings may be zero-length cursor anchors.
- Diagnostics, mappings, capabilities, dependencies, styles, and instructions have deterministic source order.
- JSON collection fields serialize as arrays, including when empty; consumers do not handle
null. - Mapping kinds are a shared closed vocabulary verified from one fixture by Go and both TypeScript clients.
- Dynamic instruction IDs and lexical binding IDs are deterministic within a compile.
- Compiler errors suppress executable output instead of asking a consumer to guess what is safe.
- Standard output belongs exclusively to the wire protocol; human diagnostics belong on standard error.
Wire protocol
The executable accepts one JSON-RPC 2.0 object per line. Request IDs are integers. A line may be at most 16 MiB; exceeding that limit ends the process with a scanner error.
The lifecycle is:
initializenegotiates protocol v3 plus Typecheck v1, ViewProgram v3, and Stylesheet v1.goldar/compileTemplaterequiressourceand a non-emptysourceName. The top-level source name is authoritative and is copied into compilation options.shutdownreturns an empty result and closes the loop.
The process uses JSON-RPC errors -32700 for invalid JSON, -32600 for an invalid request,
-32601 for an unknown method, -32602 for invalid parameters or incompatible versions, and
-32002 for a request made before initialization.
Build transaction
Project synchronization is deliberately transactional:
- Find templates while ignoring generated, dependency, and VCS directories.
- Compile every template and gather compiler errors.
- Validate imported-template files and detect cycles.
- If any error exists, throw
TemplateTypeSyncErrorand leave generated declarations unchanged. - Otherwise, write changed declarations and remove only stale files bearing Goldar’s ownership banner.
Vite runs the same scan to discover styles and component tags. Server template modules import only compiled templates; browser component modules and CSS enter through the generated client module. This keeps server rendering independent of a DOM and makes browser cost explicit.
Version changes
A semantic artifact change is incomplete until every owner agrees. In one reviewable change:
- Update the Go wire type and emitter.
- Bump the matching version in
compiler/cmd/goldar-compiler. - Update
packages/compiler/src/protocol.tsand its version constant. - Update the runtime validator and model in
packages/corefor View-program changes. - Update typed Handlebars types and mappings when editor behavior changes.
- Update shared contract fixtures, fake compilers, package probes, and reference documentation.
- Build every platform artifact serially before running consumers that locate it.
Do not silently add an instruction, mapping kind, or optional interpretation under an existing schema version. Consumers reject mismatches intentionally.
Contributor validation
Use Go 1.26, Node.js 24 or newer, and npm 11. During compiler iteration:
npm run check:compiler
cd compiler && go test -race ./...
cd compiler && go test ./typedhandlebars -run '^$' -fuzz FuzzCompile -fuzztime=10s
npm run build:compiler
npm run build --workspace @goldar/compiler
npm test --workspace @goldar/compiler
npm test --workspace @goldar/typed-handlebars
Artifact writers must run serially. Before review, return to the repository root and run:
npm run check
npm run typecheck
npm test
npm run build
The public-package pack/install probe remains part of npm test --workspace goldar. A local Go
test or compiler build is not proof that packaged platform selection or an installed consumer works.