1# Compiler rebuild comparison
2
3The `compiler-rebuild` suite measures 25 public SchemaParser operations with the
4interpreter, selective JIT and generated AOT modules. Nineteen cases also run
5against `z.compile(schema, { strict: true })`; eleven representative cases run
6against Valibot and Zod with `{ jitless: true }`. The fixture families name the
7execution mode. Cases
8cover simple and nested Structs, Arrays, tuples, Records, transformed Record
9keys, anyOf/oneOf Unions, transformations, middleware, recursive and suspended
10schemas, Declarations, construction,
11and successful and failing validation.
12
13The Effect tuple has a trailing element after its rest element, Zod compilation
14does not support recursive schemas or `z.xor`, and Zod has no equivalent
15decoding middleware. Those four cases intentionally have no Zod fixture. Zod
16compilation only accelerates forward parsing, so the encode case measures its
17documented runtime fallback. Zod parsing stands in for Effect construction
18because Zod has no separate constructor operation. Valibot parsing with defaults
19is used for the same comparison.
20
21```sh
22pnpm runtimeperf-compare compiler-rebuild --base schema-compiler
23pnpm runtimeperf-compare compiler-rebuild --base main --family interpreted
24pnpm runtimeperf compiler-rebuild
25```
26
27The first command compares the current working tree with the archived compiler
28branch. The second isolates changes to interpreted parsing against main. Schema
29and parser construction are outside the steady-state measurements. AOT fixtures
30generate their version-specific module in a separate process before loading it.
31
32The standard paired harness records five alternating rounds, validates every
33fixture before and after measurement, uses a common batch within each pair, and
34reports bootstrap confidence intervals. Cross-mode rankings are descriptive;
35the paired base/head comparison is the regression evidence.
36
37## Retained heap and first use
38
39For a current cross-library comparison of retained heap, V8 code memory, peak
40RSS and preparation CPU, run:
41
42```sh
43node packages/effect/runtimeperf/suites/compiler-rebuild/run-resources.mts \
44 tmp/schema-compiler-resources.json 5 100,500
45node packages/effect/runtimeperf/suites/compiler-rebuild/report-resources.mts \
46 tmp/schema-compiler-resources.json
47```
48
49Each sample runs in a fresh process. The report calculates median per-schema
50slopes between 100 and 500 distinct schemas, which removes fixed module and
51lazy initialization costs. Fixture inputs are released before retained-memory
52measurement. Preparation CPU includes adapter creation and first use; AOT also
53includes loading and installing the generated module. AOT source generation is
54reported separately because it runs at build time. Hot synchronous CPU is
55already represented by the normal runtime measurements.
56
57The older Effect-only probe below remains available for comparisons with its
58existing archived results.
59
60The standalone cost probe accepts a checkout root, mode, operation, shape and
61schema count. Run several fresh processes per combination and alternate the
62checkout order. Supported modes are `interpreted`, `jit` and `aot`; operations
63are `decode`, `invalid`, `is` and `make`; shapes are `struct`, `array`, `transform`
64and `default`.
65
66```sh
67node --expose-gc packages/effect/runtimeperf/suites/compiler-rebuild/costs.mts heap "$PWD" jit decode struct 500
68node --expose-gc packages/effect/runtimeperf/suites/compiler-rebuild/costs.mts cold "$PWD" jit decode struct 500
69```
70
71Heap measurements exclude schema construction and module imports, and retain
72both schema objects and public parser functions. They include operation setup
73and first use. Forced GC removes transient parse output and issues. The AOT
74generator runs in a separate process, so its retained heap is not attributed to
75the runtime application.
76
77First-use measurements include constructing a fresh schema, installing its
78compiler when requested, creating a public parser and calling it. They exclude
79module imports and AOT source generation. Repeated shapes can benefit from V8's
80source cache, so this is not process startup latency. Treat these timing probes
81as exploratory, separately from the paired throughput results.