ADR-0003. Render official HKD PDFs with Typst
| Field | Value |
|---|---|
| Status | Accepted |
| Date | 2026-03-30 |
| Deciders | ledger-team |
| Supersedes | — |
Context
- HKD ledgers are official government forms with strict layout: precise headers, signature blocks, Vietnamese number/date conventions, multi-page tables, and portrait/landscape variants per form.
- The same validated data must also produce an editable XLSX (handled separately by ExcelJS).
- We need pixel-stable, print-ready PDFs that designers can iterate on without recompiling the service.
Decision
We will render PDFs with Typst via @myriaddreamin/typst-ts-node-compiler. Templates live as .typ source in resources/templates/ (6 forms + shared common.typ); the PdfGeneratorService lazy-initializes a single NodeCompiler, injects the validated data as a shadow file (data.json), and renders. Each consumer instance has its own service instance, so the fixed shadow-file path is not shared concurrently. Standalone previews/ files allow typst compile for layout debugging without the full pipeline.
Consequences
| Pros | Cons |
|---|---|
| Markup-driven, version-controlled templates; fast iteration | New language for the team vs HTML/CSS |
| Native multi-page tables, precise typography, font embedding | Compiler is a native dependency; needs bundled fonts |
Shared common.typ macros keep 6 forms consistent | Shadow-file isolation relies on one-service-per-consumer assumption |
--root . previews enable quick visual checks | A compile error requires replacing the compiler instance |
Alternatives Considered
| Option | Pros | Cons | Why rejected |
|---|---|---|---|
| Headless Chromium (HTML→PDF) | Familiar HTML/CSS | Heavy runtime, fragile pagination, large memory | Too heavy for batch render; pagination control poor |
| LaTeX | Excellent typography | Heavyweight toolchain, slow, hard to template from JSON | Operationally awkward |
| PDF library (pdf-lib / PDFKit) | Pure JS | Manual layout for complex multi-page tables | Too low-level for official multi-form layouts |
References
ledger/src/services/generators/pdf-generator.service.tsledger/resources/templates/(common.typ,s1a-hkd.typ..s2e-hkd.typ)- HKD Templates