# Inspect the minimal single-provider hank
## Use this fixture for a first useful hank
A **hank** is the configuration for a unit of work; a **codon** is one sealed agent task in its sequence. This page walks through the smallest useful hank: one codon, one provider key (`ANTHROPIC_API_KEY`), and one output file. By the end you will have read every file in the fixture, validated the configuration, run it headless, watched it fail safely without a key, and checked the evidence a good run leaves behind.
We follow one successful path and one authentication-failure capture, pausing at each field in `hank.json` to explain what it controls. If you would rather begin with a guided validate, run, break, and resume walkthrough, start with [start/quickstart](/0.10.0/files/start/quickstart) and come back here when you want the fixture itself explained.
## Find the pieces before you run
Work from the `minimal-single-provider/` directory. Before running anything, look at what the fixture ships: the configuration, the prompt, the input data, a README, and a set of captured expected outputs you can compare your own run against.

Find the pieces before you run
Diagram as text
```text
minimal-single-provider/
├── hank.json
├── prompts/
│ └── summarize.md
├── data/
│ └── notes.txt
├── expected/
│ ├── MANIFEST.md
│ ├── receipt.json
│ ├── validate-output.txt
│ ├── run-transcript.txt
│ ├── final-events.txt
│ ├── fail-no-key.txt
│ └── summary-example.md
└── README.md
```
The input, `data/notes.txt`, is fictional meeting material. It names the Calloway vendor decision, Devon as owner, and a Friday-the-12th deadline, and it carries a training-fixture watermark so it cannot be mistaken for real data:
```text
FICTIONAL TRAINING FIXTURE — invented content for documentation testing.
Meeting notes, Tuesday.
Attendees: Mara, Devon, Sam.
We compared the two vendor quotes for the packaging line refit.
Decision: go with the Calloway quote (lower total, includes installation).
Devon owns the purchase order and vendor follow-up.
Deadline: PO issued by Friday the 12th.
Sam raised spare-parts stocking; parked for next week.
```
The `expected/` directory holds captures from one complete live execution. Its manifest dates the set to 2026-09-06, identifies hankweave\@0.10.0, and records a tracked codon cost of `$0.01394590`. The capture set uses normalized placeholders for changing execution values, while `final-events.txt` retains some per-run process and session fields; diff-clean recapture therefore depends on the normalizer covering those fields too. The manifest marks the execution as actual service output. Note what is absent: there is no committed `out/` directory, because `out/summary.md` is created by the run command below.
```text
# Capture manifest
- Captured: 2026-09-06T05:52:24.303456+00:00 · runtime: hankweave@0.10.0
- actual_service_output: true
- Scope: one complete live execution
- Raw execution (path normalized): ~/.hankweave-executions/minimal/1788673917095-hvhh-c5c378
- Complete codons: 1/1
- Tracked codon cost: $0.01394590 (provider health checks and sentinel calls are separate)
- Input scope: notes only
```
## Read what hank.json controls
The configuration is a single file. Its `hank` array holds one codon, and the `$schema` URL pins this fixture to the 0.10.0 schema rather than the `@latest` spelling used by the initialization fixture.
```json
{
"$schema": "https://unpkg.com/hankweave@0.10.0/schemas/hank.schema.json",
"meta": {
"name": "Minimal single provider",
"version": "1.0.0",
"description": "The smallest useful hank: one codon, one provider key, one output file. The quickstart's fixture."
},
"hank": [
{
"id": "summarize-notes",
"name": "Summarize the notes",
"model": "haiku",
"continuationMode": "fresh",
"promptFile": "./prompts/summarize.md",
"checkpointedFiles": ["summary.md"],
"outputFiles": [ { "copy": ["summary.md"] } ]
}
]
}
```
The optional `meta` block carries a name, version, and description; it has no runtime effect. The `summarize-notes` codon declares `id`, `name`, `model`, and `continuationMode`, plus its prompt, checkpointed file, and output copy. Each of those fields does something specific:
`haiku` is a registry shortcut. When authentication fails, the capture prints its runtime-resolved display name: `Claude Haiku 4.5 (latest) (anthropic/claude-haiku-4-5)`. That is a registry resolution result, not a pinned artifact string. Bare shortcuts such as `haiku`, `sonnet`, and `opus` are valid only when the registry defines them; use a full `pi//` or provider-prefixed slug for another model. See [model resolution](/0.10.0/files/reference/model-resolution) for the resolution phases.
`continuationMode: "fresh"` starts the codon in a new agent session. `checkpointedFiles: ["summary.md"]` makes that file watched, streamed to the client, and sealed into the git-based checkpoint store after the codon. `outputFiles: [{"copy": ["summary.md"]}]` copies it from the execution directory to the output directory when `-o` is configured. See [concepts/codons](/0.10.0/files/concepts/codons), [concepts/checkpoints](/0.10.0/files/concepts/checkpoints), [reference/hank-json](/0.10.0/files/reference/hank-json), and [operate/runbook](/0.10.0/files/operate/runbook) for those mechanics.
> **VersionNote:** In 0.10.0, `promptFile` must be a relative POSIX path inside the directory containing `hank.json`. Absolute paths, `..` escapes, and symlinks are rejected when the hank loads. See [reference/hank-json](/0.10.0/files/reference/hank-json).
Equally important is what this hank does not declare: no `budget`, `onFailure`, rig setup, sentinels, or `requirements.env`. Its failure policy therefore uses the default `abort`, and the remaining behavior comes from defaults. Because it declares no `requirements.env`, a missing `ANTHROPIC_API_KEY` is caught by the startup self-test, as the expected-failure capture shows below. See [authentication and models](/0.10.0/files/operate/authentication-and-models).
## Keep the data path in mind
The prompt is the other half of the codon. It asks the agent to read `notes.txt` from `read_only_data_source` in its working directory, then write `summary.md` with one sentence and exactly three bullets: one decision, one owner, and one deadline. The prompt preserves the deadline wording from the notes and forbids inferring a month, year, calendar date, or other detail the notes do not give. The file must stay under 15 lines.
```text
# Summarize the meeting notes
Read the file `notes.txt` inside the `read_only_data_source` directory in your current working directory (use shell commands like `cat` — the directory may be a symlink).
Write `summary.md` in the current working directory containing:
1. A one-sentence summary of what the meeting decided.
2. Exactly three bullet points: one decision, one owner, one deadline — taken from the notes.
Keep the deadline's wording from the notes. Do not infer a month, year, calendar date, or other detail that the notes do not give.
Nothing else. Keep it under 15 lines.
```
One detail in that prompt deserves attention. The data-path positional mounts at `agentRoot/read_only_data_source`, regardless of the source directory's name. Here the source is `data/`, and the startup capture reports `Source → data`; use the mounted path in the prompt rather than depending on the source name.
This is the cheapest first run the fixture set offers: one mechanical summarization task on the cheapest model tier, one key, and one sealed output. It is the small version of the shape used by [quote-template-unification](/0.10.0/files/examples/quote-template-unification) at production scale.
## Validate, run, and break safely
Enter the `minimal-single-provider/` directory – the directory containing `hank.json` – before running these commands. The shown `bunx` launcher invokes the package's Node entry point, so use Node `>=22.19.0`; Bun/bunx is the package launcher here. If you use npm instead, substitute `npx` once for `bunx` in each command. Set `ANTHROPIC_API_KEY` for the successful run: a local Claude Code login alone is not the default direct-Anthropic credential for this fixture.
### Validate before the run
Run the checked validation command from the fixture root:
```sh
bunx hankweave@0.10.0 hank.json data/ --validate
```
The single `.json` positional is the hank path; the other positional is the data path. The command grammar belongs to [reference/cli](/0.10.0/files/reference/cli). At 0.10.0, validation initializes the registry with provider health checks disabled. It performs local SDK-import, credential-presence, catalog, configuration, and harness checks, but does not execute codons or make a model-generation self-test. Do not treat validation as a proof of provider connectivity or as a universal offline/no-write guarantee; runtime startup separately performs provider health checks, which can be billable and are outside the tracked codon total.
**Check-it:** the command prints `✓ Configuration is valid!` and the `GOOD TO RUN!` box with `1 codons • 1 prompts • 0 system prompts • 0 rigs • 1 checkpoints`. The full captured output looks like this:
```text
╭────────────────────────────────────────────────────────────────────╮
│ Hankweave v0.10.0 │
│ darwin arm64 • node v23.8.0 │
╰────────────────────────────────────────────────────────────────────╯
Calculating data signature for validation...
> Validating configuration: /fixtures/minimal-single-provider/hank.json
Data source: /fixtures/minimal-single-provider/data
Execution path: ~/.hankweave-executions/validation-
✓ Configuration is valid!
╭──────────────────────────────────────────────────────────────────────────────╮
│ Minimal single provider v1.0.0 │
│ 1 codon • 0 loops │
╰──────────────────────────────────────────────────────────────────────────────╯
└─ [1] summarize-notes (Summarize the notes)
model: haiku │ mode: fresh │ prompts: 1 (13 lines)
checkpointedGlobs: 1
╭─ GOOD TO RUN! ─────────────────────────────────────────────────────╮
│ 1 codons • 1 prompts • 0 system prompts • 0 rigs • 1 checkpoints │
╰────────────────────────────────────────────────────────────────────╯
Run it: hankweave hank.json
Environment Variables:
From System (HANKWEAVE_ prefixed):
- CAPTURE_VERSION: 0.10.0
- TELEMETRY: 0
exit=0
```
### Run a fresh headless execution
With validation passing, run without the terminal interface, force a fresh execution, and copy the result to `out/`:
```sh
bunx hankweave@0.10.0 hank.json data/ --headless --start-new -o out
```
`--headless` runs without the terminal interface. `--start-new` (also `-n`) starts a fresh execution and does not resume one. `-o out` copies the output under the fixture root. The runtime creates a managed execution directory at `~/.hankweave-executions//` and prints its path. The codon's working directory is that execution's `agentRoot`, where the mounted data appears as `read_only_data_source`.
Without `-o`, `summary.md` remains only in `~/.hankweave-executions//agentRoot/`; there is no default results directory. See [operate/runbook](/0.10.0/files/operate/runbook) for output-directory behavior.
**Check-it:** after this command, `out/summary.md` exists under the fixture root and the capture contains the `Hankweave Server Started` box and `Running in headless mode on port `:
```text
╭────────────────────────────────────────────────────────────────────╮
│ Hankweave v0.10.0 │
│ darwin arm64 • node v23.8.0 │
╰────────────────────────────────────────────────────────────────────╯
Created new execution directory: ~/.hankweave-executions/
New execution:
Source → data
Exec → ~/.hankweave-executions/
SDKs → Claude node_modules ✓
╭──────────────────────────────────────────────────────────────────────────────╮
│ Minimal single provider v1.0.0 │
│ 1 codon • 0 loops │
╰──────────────────────────────────────────────────────────────────────────────╯
└─ [1] summarize-notes (Summarize the notes)
model: haiku │ mode: fresh │ prompts: 1 (13 lines)
checkpointedGlobs: 1
══════════════════════════════════════════════════
Hankweave Server Started
WebSocket: ws://localhost:
══════════════════════════════════════════════════
Running in headless mode on port
➜ Listening on: http://localhost:/ (all interfaces)
exit=0
```
### Break authentication before a codon runs
To exercise the named failure fixture, unset the key and run the same minimal hank command:
```sh
env -u ANTHROPIC_API_KEY bunx hankweave@0.10.0 hank.json data/ --headless --start-new -o out
```
Startup creates the execution directory, then its self-test fails before the codon runs. The diagnostic prints the resolved model name and an installed `hankweave@0.10.0` bundle path in its stack trace – not a source checkout.
**Check-it:** the expected-failure capture says `No authentication found (set ANTHROPIC_API_KEY)` and `Server startup failed!`:
```text
╭────────────────────────────────────────────────────────────────────╮
│ Hankweave v0.10.0 │
│ darwin arm64 • node v23.8.0 │
╰────────────────────────────────────────────────────────────────────╯
Created new execution directory: ~/.hankweave-executions/
New execution:
Source → data
Exec → ~/.hankweave-executions/
SDKs → Claude node_modules ✓
[] [ERROR] Self-test completed: FAILED
[] [ERROR] Self-test FAILED: Some checks failed
[] [ERROR] - authentication: ✗ No authentication found (set ANTHROPIC_API_KEY)
[ERROR] Server startup failed!
Error message: Self-test failed for 1 model(s):
- Claude Haiku 4.5 (latest) (anthropic/claude-haiku-4-5): Some checks failed
• authentication: No authentication found (set ANTHROPIC_API_KEY)
Stack trace:
Error: Self-test failed for 1 model(s):
- Claude Haiku 4.5 (latest) (anthropic/claude-haiku-4-5): Some checks failed
• authentication: No authentication found (set ANTHROPIC_API_KEY)
at eU (file:///build/runtime/0.10.0/node_modules/hankweave/dist/index.js:260:5401)
at async Egt (file:///build/runtime/0.10.0/node_modules/hankweave/dist/index.js:842:647)
at async file:///build/runtime/0.10.0/node_modules/hankweave/dist/index.js:843:754
exit=1
```
> **Pitfall:** After a successful run, rerunning **without** `--start-new` reports `Resuming execution in:` and reuses the newest managed execution for the same data signature. If it is already `RunCompleted`, the server starts, prints `Shutting down server: all codons completed`, and exits 0 without running new work. The command above includes `--start-new` to create a new managed execution. If `out/summary.md` already exists, a repeated output copy can also hit output-collision renaming, such as `file.txt -> file_1_.txt`; pass `--overwrite-output` when that is intended.
### Check the completion evidence
After a successful run, inspect the normalized event capture. It records `RunStarted`, `CodonStarted`, the codon transitions `preparing → starting → initializing → running`, cost and assistant-message updates, `CodonFinalCostSet`, a completed `CheckpointCreated`, the codon transition `running → completed` with exit code 0, one successful `codon.completed`, and `RunCompleted`. The initializing transition records the agent log path.
**Check-it:** the capture contains `CheckpointCreated`, one successful `codon.completed`, and `RunCompleted`:
```text
{"id": "", "timestamp": "", "type": "state.transition", "data": {"transitionType": "RunStarted", "runId": "", "transition": {"type": "RunStarted", "data": {"runId": "", "runFolder": "~/.hankweave-executions//.hankweave/runs/", "gitBranch": "run-", "startingConditions": {"type": "fresh"}, "serverPid": 50024}}, "resultingState": {"currentRunId": "", "runCount": 1, "totalCost":"", "currentRunCost":""}}}
{"id": "", "timestamp": "", "type": "state.transition", "data": {"transitionType": "CodonStarted", "runId": "", "codonId": "summarize-notes", "transition": {"type": "CodonStarted", "data": {"runId": "", "codonId": "summarize-notes"}}, "resultingState": {"currentRunId": "", "runCount": 1, "totalCost":"", "currentRunCost":""}}}
{"id": "", "timestamp": "", "type": "state.transition", "data": {"transitionType": "CodonTransitioned", "runId": "", "codonId": "summarize-notes", "transition": {"type": "CodonTransitioned", "data": {"runId": "", "codonId": "summarize-notes", "from": "preparing", "to": "starting", "metadata": {}}}, "resultingState": {"currentRunId": "", "runCount": 1, "totalCost":"", "currentRunCost":""}}}
{"id": "", "timestamp": "", "type": "state.transition", "data": {"transitionType": "CodonTransitioned", "runId": "", "codonId": "summarize-notes", "transition": {"type": "CodonTransitioned", "data": {"runId": "", "codonId": "summarize-notes", "from": "starting", "to": "initializing", "metadata": {"claudePid": 962109, "claudeLogPath": ".hankweave/runs//summarize-notes-claude.log"}}}, "resultingState": {"currentRunId": "", "runCount": 1, "totalCost":"", "currentRunCost":""}}}
{"id": "", "timestamp": "", "type": "state.transition", "data": {"transitionType": "CodonTransitioned", "runId": "", "codonId": "summarize-notes", "transition": {"type": "CodonTransitioned", "data": {"runId": "", "codonId": "summarize-notes", "from": "initializing", "to": "running", "metadata": {"claudeSessionId": "be7a1143-f289-4e61-9346-9c3bf0dc8ed2"}}}, "resultingState": {"currentRunId": "", "runCount": 1, "totalCost":"", "currentRunCost":""}}}
{"id": "", "timestamp": "", "type": "state.transition", "data": {"transitionType": "CostsIncremented", "runId": "", "codonId": "summarize-notes", "transition": {"type": "CostsIncremented", "data": {"runId": "", "codonId": "summarize-notes", "costDelta":"", "tokensDelta": {"inputTokens":"", "outputTokens":"", "cacheCreationTokens":"", "cacheReadTokens":""}}}, "resultingState": {"currentRunId": "", "runCount": 1, "totalCost":"", "currentRunCost":""}}}
{"id": "", "timestamp": "", "type": "state.transition", "data": {"transitionType": "AssistantMessageCountUpdated", "runId": "", "codonId": "summarize-notes", "transition": {"type": "AssistantMessageCountUpdated", "data": {"runId": "", "codonId": "summarize-notes", "newCount":""}}, "resultingState": {"currentRunId": "", "runCount": 1, "totalCost":"", "currentRunCost":""}}}
{"id": "", "timestamp": "", "type": "state.transition", "data": {"transitionType": "CostsIncremented", "runId": "", "codonId": "summarize-notes", "transition": {"type": "CostsIncremented", "data": {"runId": "", "codonId": "summarize-notes", "costDelta":"", "tokensDelta": {"inputTokens":"", "outputTokens":"", "cacheCreationTokens":"", "cacheReadTokens":""}}}, "resultingState": {"currentRunId": "", "runCount": 1, "totalCost":"", "currentRunCost":""}}}
{"id": "", "timestamp": "", "type": "state.transition", "data": {"transitionType": "AssistantMessageCountUpdated", "runId": "", "codonId": "summarize-notes", "transition": {"type": "AssistantMessageCountUpdated", "data": {"runId": "", "codonId": "summarize-notes", "newCount":""}}, "resultingState": {"currentRunId": "", "runCount": 1, "totalCost":"", "currentRunCost":""}}}
{"id": "", "timestamp": "", "type": "state.transition", "data": {"transitionType": "CostsIncremented", "runId": "", "codonId": "summarize-notes", "transition": {"type": "CostsIncremented", "data": {"runId": "", "codonId": "summarize-notes", "costDelta":"", "tokensDelta": {"inputTokens":"", "outputTokens":"", "cacheCreationTokens":"", "cacheReadTokens":""}}}, "resultingState": {"currentRunId": "", "runCount": 1, "totalCost":"", "currentRunCost":""}}}
{"id": "", "timestamp": "", "type": "state.transition", "data": {"transitionType": "AssistantMessageCountUpdated", "runId": "", "codonId": "summarize-notes", "transition": {"type": "AssistantMessageCountUpdated", "data": {"runId": "", "codonId": "summarize-notes", "newCount":""}}, "resultingState": {"currentRunId": "", "runCount": 1, "totalCost":"", "currentRunCost":""}}}
{"id": "", "timestamp": "", "type": "state.transition", "data": {"transitionType": "CostsIncremented", "runId": "", "codonId": "summarize-notes", "transition": {"type": "CostsIncremented", "data": {"runId": "", "codonId": "summarize-notes", "costDelta":"", "tokensDelta": {"inputTokens":"", "outputTokens":"", "cacheCreationTokens":"", "cacheReadTokens":""}}}, "resultingState": {"currentRunId": "", "runCount": 1, "totalCost":"", "currentRunCost":""}}}
{"id": "", "timestamp": "", "type": "state.transition", "data": {"transitionType": "AssistantMessageCountUpdated", "runId": "", "codonId": "summarize-notes", "transition": {"type": "AssistantMessageCountUpdated", "data": {"runId": "", "codonId": "summarize-notes", "newCount":""}}, "resultingState": {"currentRunId": "", "runCount": 1, "totalCost":"", "currentRunCost":""}}}
{"id": "", "timestamp": "", "type": "state.transition", "data": {"transitionType": "CostsIncremented", "runId": "", "codonId": "summarize-notes", "transition": {"type": "CostsIncremented", "data": {"runId": "", "codonId": "summarize-notes", "costDelta":"", "tokensDelta": {"inputTokens":"", "outputTokens":"", "cacheCreationTokens":"", "cacheReadTokens":""}}}, "resultingState": {"currentRunId": "", "runCount": 1, "totalCost":"", "currentRunCost":""}}}
{"id": "", "timestamp": "", "type": "state.transition", "data": {"transitionType": "AssistantMessageCountUpdated", "runId": "", "codonId": "summarize-notes", "transition": {"type": "AssistantMessageCountUpdated", "data": {"runId": "", "codonId": "summarize-notes", "newCount":""}}, "resultingState": {"currentRunId": "", "runCount": 1, "totalCost":"", "currentRunCost":""}}}
{"id": "", "timestamp": "", "type": "state.transition", "data": {"transitionType": "CostsIncremented", "runId": "", "codonId": "summarize-notes", "transition": {"type": "CostsIncremented", "data": {"runId": "", "codonId": "summarize-notes", "costDelta":"", "tokensDelta": {"inputTokens":"", "outputTokens":"", "cacheCreationTokens":"", "cacheReadTokens":""}}}, "resultingState": {"currentRunId": "", "runCount": 1, "totalCost":"", "currentRunCost":""}}}
{"id": "", "timestamp": "", "type": "state.transition", "data": {"transitionType": "AssistantMessageCountUpdated", "runId": "", "codonId": "summarize-notes", "transition": {"type": "AssistantMessageCountUpdated", "data": {"runId": "", "codonId": "summarize-notes", "newCount":""}}, "resultingState": {"currentRunId": "", "runCount": 1, "totalCost":"", "currentRunCost":""}}}
{"id": "", "timestamp": "", "type": "state.transition", "data": {"transitionType": "CodonFinalCostSet", "runId": "", "codonId": "summarize-notes", "transition": {"type": "CodonFinalCostSet", "data": {"runId": "", "codonId": "summarize-notes", "finalCost":"", "finalTokens": {"inputTokens":"", "outputTokens":"", "cacheCreationTokens":"", "cacheReadTokens":""}}}, "resultingState": {"currentRunId": "", "runCount": 1, "totalCost":"", "currentRunCost":""}}}
{"id": "", "timestamp": "", "type": "state.transition", "data": {"transitionType": "CheckpointCreated", "runId": "", "codonId": "summarize-notes", "transition": {"type": "CheckpointCreated", "data": {"runId": "", "codonId": "summarize-notes", "checkpointType": "completed", "sha": "", "branch": "run-"}}, "resultingState": {"currentRunId": "", "runCount": 1, "totalCost":"", "currentRunCost":""}}}
{"id": "", "timestamp": "", "type": "state.transition", "data": {"transitionType": "CodonTransitioned", "runId": "", "codonId": "summarize-notes", "transition": {"type": "CodonTransitioned", "data": {"runId": "", "codonId": "summarize-notes", "from": "running", "to": "completed", "metadata": {"exitCode": 0, "resultMessageReceived": true, "checkpointSha": "", "contextExceeded": false, "extensionCount": 0}}}, "resultingState": {"currentRunId": "", "runCount": 1, "totalCost":"", "currentRunCost":""}}}
{"id": "", "timestamp": "", "type": "codon.completed", "data": {"codonId": "summarize-notes", "success": true, "cost":"", "duration":"", "exitStatus": {"type": "success"}}}
{"id": "", "timestamp": "", "type": "state.transition", "data": {"transitionType": "RunCompleted", "runId": "", "transition": {"type": "RunCompleted", "data": {"runId": ""}}, "resultingState": {"currentRunId": null, "runCount": 1, "totalCost":"", "currentRunCost":""}}}
```
## Recognize a good run's evidence
Each capture above answers a different question about the run, so read them as a set. Validation ends with `✓ Configuration is valid!`, a one-codon structure box, the `GOOD TO RUN!` counts, a `Run it:` line, and an environment report. Its execution path is a synthetic validation path, not a real directory. The captured report is labeled `From System (HANKWEAVE_ prefixed)` and shows that scope rather than the whole machine environment; its captured values include `CAPTURE_VERSION: 0.10.0` and `TELEMETRY: 0`.
The run capture supplies the version banner, the `New execution` block with `Source → data`, the managed execution path, and the `Hankweave Server Started` box. `--headless` removes the terminal interface, but the runtime still starts this local server and reports its WebSocket (the local client connection); it shuts down after all codons complete. The event capture shows the completed checkpoint, successful codon completion, and `RunCompleted`. Its initializing metadata gives the agent log path as `.hankweave/runs//summarize-notes-claude.log`.
Finally, compare your summary with this captured codon output:
```markdown
# Meeting Summary
The team decided to proceed with the Calloway vendor quote for the packaging line refit based on lower total cost and included installation.
- **Decision:** Go with the Calloway quote for packaging line refit
- **Owner:** Devon
- **Deadline:** PO issued by Friday the 12th
```
Model output is stochastic, so another run can differ in wording. Treat the contract as the shape – one sentence and three bullets taken from the notes – not identical output bytes.
## Measure the run cost
The full run cost measured `$0.01394590` on 2026-09-06 against the published `hankweave@0.10.0` artifact with the `haiku` model. Treat this as a dated capture, not an estimate. Provider health checks and sentinel calls are tracked separately from the codon cost.
The hank has no budget caps. The operator-level ceilings are `--max-cost` and `--max-time`; the runtime parses them, but they are absent from the shipped `--help`. See [reference/cli](/0.10.0/files/reference/cli) for that parity note.
## How the example captures were recorded
The published transcripts come from this fixture directory against the pinned runtime: the validation and headless commands above are rerun, then `expected/` is recaptured. The corpus records a passed recapture transaction for this minimal fixture and a verification step. Its normalizer masks changing execution values. The maintenance scripts are not shipped in the fixture corpus; you do not need them to run the example.
The maintenance capture transaction reports a successful live minimal run, an explicit no-key refusal, and preserved expected bytes.
## Adapt one piece at a time
To make this example your own, change either `prompts/summarize.md` or `data/notes.txt`, then run with `--start-new`. Changing the data directory changes the data hash; use [operate/runbook](/0.10.0/files/operate/runbook) for the distinction between resuming and starting fresh.
For a Gemini version, swap the single `model` field to a spelling such as `pi/google/gemini-2.5-flash` and use `GEMINI_API_KEY`. Generate it from this same fixture rather than hand-forking it; [start/quickstart](/0.10.0/files/start/quickstart) owns that provider variant.
When this shape is no longer enough, add a codon `budget`, a second codon, or a sentinel. Follow [concepts/budgets](/0.10.0/files/concepts/budgets), [concepts/codons](/0.10.0/files/concepts/codons), or [concepts/sentinels](/0.10.0/files/concepts/sentinels) for those mechanics. For the full-sized version of this shape, continue to [quote-template-unification](/0.10.0/files/examples/quote-template-unification).