# Fieldtest — cycle 0106 — research-artifact document surface — 2026-07-03 **Role:** downstream consumer (methodology designer / campaign designer), public interface only (ledger C18/C20/C22/C25, glossary, CLI help + introspection, the fieldtests corpus shape). No `crates/` source read. Binary built from HEAD; referential tier exercised after `cargo build` in the scaffolded `demo_project/`. ## Fixtures (this directory) - `c0106_1_attempt1..3.json`, `c0106_1_partial.json`, `c0106_1_reformatted.json` — process doc: 3-round envelope discovery + canonicalization + empty-gate probe - `c0106_2_strategy.json` — SMA-cross op-script (content id `573262…`) - `c0106_2_campaign_attempt1..2.json`, `c0106_2_campaign_valid.json`, `c0106_2_campaign_partial.json`, `c0106_2_probe_{barestring,refnull,noref,prefixed}.json` - `c0106_4_{emptyaxis,floatinint,noinstr,backwardwin,badmetric,badcmp,process_identity}.json` - `demo_project/` — `aura new` scaffold + campaign/process docs + in-project store - `runs/{processes,campaigns}/…` — content-addressed store written by `register` ## Findings ### F2 [bug] `introspect --block std::process_ref` advertises `identity_id`, which the validator refuses The slot line prints `ref required, one of { content_id } | { identity_id }` while validation refuses an identity_id process ref (`process.ref: a process is referenced by content id in this version`, exit 1); the block header itself says "(content id)". The 0106 audit fixed the parallel `--unwired` hint but not this `--block` describe. Repro: `aura campaign introspect --block std::process_ref`. → debug (RED-pin content-id-only). ### F1 [friction] Document envelope not derivable from the introspection contract Process doc took 3 blind rounds (`stages` → wrong-kind refusal that does not name the `kind` key → `unknown field stages, expected one of … pipeline`). Campaign worse: block ids `std::data/std::strategy/std::process_ref/std::presentation` map to fields `data`/`strategies` (plural)/`process`/`presentation`, and the required `seed` appears in NO block (`missing field seed`). Introspection describes block slots but never the envelope composing them. → plan (envelope/skeleton introspection; reconcile block ids with field names). ### F3 [friction] content-id printed `content:`-prefixed, refs need the bare hash — silent referential break `process|campaign introspect --content-id` print `content:`; `graph introspect --content-id` prints bare. Pasting the prefixed form into a ref PASSES intrinsic validation (different id!) then fails referential resolution without the error naming the prefix as the cause. → plan (one display form across verbs; accept/strip the prefix in refs). ### F4 [friction] `--unwired` open-slot hints fire only when a ref is omitted, which `validate` fails The ref open-slot hints appear only with the `ref` key removed (then validate says `missing field ref`); placeholders `{}` / `null` give cryptic serde errors (`expected map with a single key`; `invalid type: null, expected string or map`) and `--unwired` reports `no open slots`. One draft file cannot both validate-so-far and report its open slots. → plan (treat `ref: {}`/`null` as the reported open slot). ### F5 [friction] A campaign's strategy ref cannot be driven to resolve from the public surface No verb computes a blueprint FILE's content id (`graph introspect --content-id` is op-list-only), no verb registers a standalone blueprint into the store (only sweep/mc/walkforward populate it), no verb lists a strategy's `param_space` (axis names/kinds undiscoverable). The ref stays unresolved unless a sweep already ran — but the sweep is what the campaign describes (see F7). → planner (blueprint register + file content-id + param-space listing; scope with the executor). ### F6 [doc-gap] No worked document example anywhere; `metric_vocabulary` unlisted by any verb Zero process/campaign JSON examples in docs/ or the corpus at test time. Block hints say "metric name (see metric_vocabulary)" but no verb lists it, and `unknown metric` does not enumerate valid names. → tighten docs (worked example per type; metric enumeration via introspect or in the refusal). ### F7 [spec_gap] No executor — a valid campaign has no run path (the pending executor decision) After registering a campaign whose process declares sweep → gate → walk_forward over a strategy + 9-point axis, the expected `aura campaign run ` does not exist; `aura run`/`sweep` take no campaign. The campaign+process pair is a complete declarative spec of machinery the engine already runs (sweep_family / optimize_deflated / walkforward_family); what exists is persisted, content-addressed, legible intent that nothing consumes. The trail ends at `runs/campaigns/.json`. → this run IS the intent-persistence re-test the executor decision waited on; scope the executor. ### F8 [working] Content-id canonicalization is exact and stable Reordered keys + reflowed whitespace + `0` vs `0.0` yield the identical content id; stored form is compact, declared-key-order, no trailing newline, and re-derives its id. → carry-on. ### F9 [working] Intrinsic validation is thorough, path-addressed, house-style Empty gate, unknown metric/cmp, empty axis, float-in-I64, empty instruments, backwards window, invalid-doc content-id refusal — all precise prose, exit codes usage=2 / invalid=1 / ok=0. Minor: the kind-mismatch error omits the axis path its siblings carry. → carry-on. ### F10 [working] Referential tier correct across the project boundary Outside: skip line names the search root. Inside without dylib: actionable build hint. Inside built: per-store diagnostics, progressive resolution as documents get registered. → carry-on. ## Verdict The shipped surface delivers standalone value: methodology and experiment intent are nameable, diffable (byte-exact content id surviving reformatting), and auditable (content-addressed, referentially checkable, honest diagnostics) — with no compile and no run. The shortfall concentrates in the authoring on-ramp (envelope invisible to introspection, no worked example, the `content:`-vs-bare id trap) and the terminal wall: the campaign+process pair fully specifies a sweep→gate→walk-forward the engine already runs, yet nothing consumes it. The single most valuable next capability is an executor (`aura campaign run ` driving the existing family machinery) — the one addition that turns persisted intent into a result and retroactively gives every id, store, axis, and gate its reason to exist. Counts: bug 1 (F2), friction 4 (F1/F3/F4/F5), doc-gap 1 (F6), spec-gap 1 (F7), working 3 (F8/F9/F10).