TypeScript quickstart
Go from an empty directory to generated, typechecked, and tested TypeScript.
This tutorial builds the starter greet function that jaunt init creates. The
private spec is parsed without being executed. Application code imports an ordinary
TypeScript facade, and the emitted JavaScript has no Jaunt runtime dependency.
The TypeScript target is alpha. It requires Jaunt 1.7 or later and installs its
project-local worker separately as @usejaunt/ts@next. Alpha artifact formats can
change; the upgrade notes explain the deterministic
migration path.
1. Check the prerequisites
You need:
- Python 3.12 or later and
uv - Node 20 through 24
- the OpenAI Codex CLI, authenticated with
codex login
Jaunt uses codex exec for build and test. sync, status, and check do not
call a model.
2. Scaffold the project
mkdir jaunt-ts-quickstart
cd jaunt-ts-quickstart
uvx jaunt init --language ts
npm init -y
npm pkg set type=module
npm install -D @usejaunt/ts@next 'typescript@^5.9' vitest fast-check @types/node
codex loginjaunt init does not edit package.json; it prints the package commands you still
need to run. It creates a version-2 jaunt.toml with one TypeScript target:
version = 2
[target.ts]
source_roots = ["src"]
test_roots = ["tests"]
projects = ["tsconfig.json"]
test_projects = ["tsconfig.test.json"]
tool_owner = "."
generated_dir = "__generated__"
test_runner = "vitest"
fast_check_runs = 50tool_owner names the package that directly owns @usejaunt/ts and TypeScript.
Jaunt uses that compiler rather than a global installation. The scaffold also writes
separate production and test tsconfig files and excludes private Jaunt inputs from
both emit paths.
3. Read the starter spec
The generated src/index.jaunt.ts is a private static input:
import * as jaunt from "@usejaunt/ts/spec";
jaunt.magicModule();
/** Return a friendly greeting for `name`, including the name verbatim. */
export function greet(name: string): string {
return jaunt.magic();
}Production code never imports this file. It imports the committed facade instead:
export * from "./index.context.js";
export * from "./__generated__/index.js";The .js specifiers are intentional for NodeNext projects. TypeScript resolves them
to source .ts files, and the emitted JavaScript keeps valid runtime paths. Jaunt
also supports private .jaunt.tsx specs when the owning project supplies its normal
JSX configuration and runtime.
4. Sync the typed boundary
Run the model-free synchronization step before the first build:
uvx jaunt sync --language ts
npx tsc -p tsconfig.json --noEmit
uvx jaunt status --language tssync renders the API mirror and a typed throwing placeholder. Your editor and
compiler can resolve greet, while status still reports the implementation as
unbuilt.
src/
index.jaunt.ts
index.context.ts
index.ts
__generated__/
index.api.ts
index.ts
index.jaunt.jsonindex.api.ts, the implementation, and index.jaunt.json are machine-owned. Commit
them, but change the spec and regenerate instead of editing them.
5. Build and run
uvx jaunt build --language ts
npx tsc -p tsconfig.json
node --input-type=module -e \
'import("./dist/index.js").then(({ greet }) => console.log(greet("Ada")))'The build asks Codex for an implementation, checks it against the project-local compiler in an in-memory overlay, then writes the validated files as one transaction. The last command runs ordinary emitted JavaScript.
6. Generate and run the test
The scaffold includes test intent in tests/index.jaunt-test.ts:
import * as jaunt from "@usejaunt/ts/spec";
import { greet } from "../src/index.jaunt.js";
jaunt.magicModule();
/** `greet("Ada")` includes "Ada" and reads as a friendly greeting. */
export function greetExample(): void {
jaunt.testSpec({ targets: [greet] });
}Generate the Vitest battery, run it, and finish with the offline drift gate:
uvx jaunt test --language ts
uvx jaunt check --language tstest calls the model only when the battery needs generation. A fresh battery is
still typechecked and run on later calls. check never calls the model; it verifies
the committed implementation, mirrors, sidecars, and Vitest batteries.
7. Commit the result
Commit the authored spec and test intent, jaunt.toml, both tsconfig files, the
package manifest and lockfile, the public facade, JAUNT_LOG, and the generated
artifacts. Keep .jaunt/ ignored.
In a mixed Python and TypeScript workspace, use version 2 with both [target.py] and
[target.ts]. Plain commands cover both targets; --language py and --language ts
narrow a run. See the TypeScript target guide
for project references, pnpm workspaces, classes, contract mode, and current alpha
limits.
Where to next
TypeScript target guide
The full authoring model, workspace routing, classes, contracts, security boundary, and alpha limits.
Configuration
Every target.ts setting and the version-2 Python/TypeScript layout.
Gate it in CI
Install the project-local toolchain and run the model-free check in GitHub Actions.
Runnable examples
Start with slugify, then move to project references or the full JWT example.