Scope: AI-agent-agnostic playbook for building applications with the Stoffel framework. This is not a maintainer guide for compiler, VM, protocol, or release engineering work. Dependency assumption: use current public crates.io releases by default, then the official GitHub repository at a full immutable revision when the needed change is not published. A local checkout is a separate, explicitly requested, nonportable framework-development workflow.
Use when
Use this playbook when a Stoffel app fails to init, check, build, run, test, execute locally, generate bindings, or connect through the SDK/network path.Goal
Diagnose app-level issues systematically and collect real evidence before reporting success.First commands
From the app root:Portability and provenance diagnosis
Capture provenance before changing code or dependencies:- app repository URL, commit, branch/tag if relevant, and clean/dirty state;
- framework repository URL, commit, and clean/dirty state if a framework checkout is in use;
- CLI installation source, resolved executable path, and reported version/build identity when available;
- SDK source (public package version or git URL and revision, or the exact intentional local path);
- committed lockfile path and hash, or why no lockfile applies;
- bytecode hash and generated binding/manifest hashes;
- immutable build/runtime image digest when containers are involved.
Cargo.toml files for [patch], [replace], path =, git revisions, and workspace-inherited dependencies. Inspect repository and applicable user/global .cargo/config and .cargo/config.toml files for source replacement, registries, aliases, target settings, and injected build flags. Record the resolved SDK package source from cargo metadata and compare it with the lockfile. Do not delete a patch or path dependency until you know whether it was intentional; do not call the result portable while it remains dependent on undeclared local state.
Reproduce the failure from a clean external app checkout, outside the framework repository, with only documented public CLI/SDK dependencies and the committed lockfile. The public dependency consumer proof must check/build, produce bytecode and bindings, and exercise the relevant client-facing path without framework workspace inheritance, source mounts, unpublished package caches, or dirty generated files. Framework workspace tests do not substitute for this proof.
If that external proof was not run or requires local framework state, classify the result explicitly as not clean-room tested. State why, instead of reporting a portability success.
Container and CI diagnosis
- Record the image digest, network mode, published ports, working directory, environment overrides, and every host-to-container mount.
- Inspect mounts for framework checkouts, host
target/directories, local SDK paths, package caches containing unpublished builds, stale generated bindings, and shadowed config/lockfiles. - Hash bytecode and bindings both outside and inside the container. Treat a mismatch as bundle mutation or a mount-selection failure.
- Remember that
localhost/127.0.0.1names the current network namespace. Record bind and advertised addresses separately, then test coordinator, mesh, and RPC reachability from the failing peer/client context. - In CI, make clean checkout, public dependency resolution, lockfile stability, artifact hash agreement, image digest capture, config validation, and real service/client smoke separate gates. Fail on unexpected path/patched dependencies or bundle drift.
- Report every gate as
passed,failed, orskipped. Every skip needs the exact reason, execution context, and impact; use not clean-room tested or deployment unverified where appropriate.
Config checklist
InspectStoffel.toml:
[package]exists.nameandversionare non-empty.package.nameuses only letters, numbers,-, and_.build.sourceis relative, inside the project, and either a.stflfile or source directory.build.target_diris a relative directory, not undersrc/, and not a file path.optimization_levelis0..3if present.[mpc].parties,[mpc].threshold, and[mpc].instance_idare unquoted positive whole numbers where present.- Byzantine validation holds: HoneyBadger needs at least
4 * threshold + 1parties. - Backend syntax is valid:
honeybadger,avss,avss:bls12_381,avss:bn254,avss:curve25519,avss:ed25519,avss:secp256k1,avss:p-256. curve/fieldis only used where a backend/curve combination supports it.
Input checklist
- Named function inputs use repeated
--input NAME=VALUE. - ClientStore inputs use repeated
--client-input SLOT=VALUE. - Repeating the same ClientStore slot appends values in order for
ClientStore.take_share(slot, index). - Do not combine multiple assignments in one flag.
- Named input names must match function parameters exactly.
- Client slots must be numeric.
- If using input files, extensions must be
.json,.csv, or.txt. - Named JSON inputs are an object like
{"a": 40, "b": 2}. - Client JSON inputs are an object keyed by numeric slot like
{"0": [40, 2]}. - Client CSV inputs require
slot,valueorclient_slot,valueheaders. - TXT input files use one
name=valueorslot=valueassignment per line; blank lines and#comments are ignored. - CLI values are integers, booleans, strings/JSON where accepted by file parsing, or
0x-prefixed bytes where supported.
Bytecode checklist
- Rebuild
.stflbafter source changes. - Regenerate typed bindings after bytecode changes.
- Explicit SDK backend/curve must match bytecode metadata. Prefer generated
ProgramManifestfor ClientStore apps. - Use
--program-infoor disassembly when diagnosing wrong entrypoint/function/client metadata. - If a source directory is configured, confirm the intended file was compiled; the CLI can compile multiple
.stflfiles.
Local MPC checklist
- Increase
--timeout-secsbefore declaring protocol failure. - Avoid concurrent local party meshes that collide on ports/processes.
- Verify whether the app uses named inputs or ClientStore inputs.
- For examples with a first-line
# run-args:header, copy those exact flags. - Include
--expected-output-clients Nfor programs that callMpcOutput.send_to_clientorShare.send_to_client.
Typed bindings checklist
- Bindings were generated from the same
.stflbloaded at runtime. - Rust code includes generated bindings after generation.
cargo checkwas run after regeneration.- If duplicate crate/output collision errors appear with path or git dependencies, pre-generate bindings or remove the duplicate SDK build-dependency.
Network/off-chain checklist
- Local smoke passes before network work.
- Network config is not project
Stoffel.toml. - Client slot exists in program metadata.
- Generated bindings came from the same
.stflb. - Coordinator address, node RPC addresses, timestamp, identity material, and expected certificates are provided.
- Network config validates server addresses, expected parties, expected clients, threshold, backend, and preprocessing.
- Bytecode hash, generated binding version, party configs, coordinator settings, node RPC addresses, and identity material are from the same deployment bundle.
- If live server startup is delegated to lower-layer tooling, capture the exact service command/supervisor logs instead of reporting SDK builder success as deployment success.
Minimal diagnosis report
When handing off a failure, include:- command run
- working directory
stoffel --help/version if relevant- app
Stoffel.tomlwith secrets removed - exact error output
- whether
stoffel status --verbosepassed - whether
stoffel checkpassed - whether bytecode was rebuilt
- whether typed bindings were regenerated
- exact
# run-args:header if using an example - network/off-chain config shape with secrets redacted if relevant
- bytecode hash and generated binding timestamp/hash for deployment failures
- labeled execution context and exact working directory
- app/framework repository URL, commit, and clean/dirty state
- CLI source/path, SDK source, lockfile path/hash, and applicable image digest
- relevant
cargo metadatapackage source plus any[patch],.cargosource replacement, local path, or workspace inheritance found - container mount map and bind/advertised addresses when applicable
- exit status, first actionable error, and location of complete unabridged output
- each check that passed, failed, or was skipped; include the reason and impact of every skip
- clean external consumer proof result, or the explicit classification not clean-room tested
Common pitfalls
- Do not “fix” app issues by editing framework internals unless the task is explicitly a framework bug report.
- Do not report success from a command that was not run.
- Do not leak private client inputs, tokens, identity material, or secrets into notes, logs, Obsidian, HackMD, or public issues.
- Do not store API tokens in
Stoffel.toml, app repos, Obsidian, or HackMD. - Do not call deployment done from
execute_local()output or SDK builder construction alone. - Do not mistake a host framework mount, package cache,
[patch],.cargosource replacement, or path dependency for public dependency portability. - Do not summarize a partial run as success: preserve the exact failure and list checks that never ran.