{"id":"f02caa79-3da2-42e3-9b25-0f871b6a874f","slug":"atmofab","kind":"skill","name":"atmofab","summary":"","owner":"seiya","repoUrl":"https://github.com/seiya/atmofab","license":"BSD-2-Clause","licenseTier":"permissive","trust":"community","stars":0,"match":null,"fewStars":true,"format":"skill","createdAt":"2025-10-31T09:25:03.000Z","addedAt":"2026-10-21T22:11:02.790Z","logoUrl":"https://avatars.githubusercontent.com/u/710079?v=4","linkOnly":false,"collection":null,"skillPath":null,"categories":["writing"],"tags":[],"runtime":"binary","local":true,"cloudCapable":false,"cloudCapability":"unknown","cloudReadyOnPlatform":false,"needsApiKey":false,"reviewed":false,"syncedAt":"2026-10-22T19:28:04.294Z","sample":false,"url":"https://conduits.dev/tools/atmofab","language":"Python","transports":["stdio"],"install":{},"requirements":{"env":[],"upstreamMayCharge":false},"tools":null,"readme":"# atmofab\n\n`atmofab` generates, validates, and certifies weather and climate compute kernels from natural-language specifications.\n\n`controlled_spec.md` (physics and algorithm definition), `tests.md` (verification profile), and `deps.yaml` (dependency declaration) are authored by humans and are the canonical source. Every phase after them is executed by a deterministic conductor (`tools/workflow_conductor.py`), which fulfils the `orchestration agent` role: it launches each judgment-bearing `substep` as one isolated `substep agent` (an `LLM` leaf) under a fixed input/output contract, runs the deterministic gates and the build itself in its own process, and performs every build, execution, lint, and syntax check through the build-runtime library (`tools/build_runtime.py`).\n\n## Scope\n\n- Generate the `model` (physics computation) and the `runner` (execution and judgment coordination) for a computation task defined by a `spec`, targeting `CPU` and `GPU` hardware. The material certified in this tree is Fortran on `CPU`. A second target profile, CUDA C++ on `GPU` (`spec/targets/`), builds its harness, and reaches `Validate` only at an execution site with a GPU that the operator's `sites.yaml` names ([issue #293](https://github.com/seiya/atmofab/issues/293); `docs/ORCHESTRATION.md` §Execution sites).\n- Manage specifications under four `spec_kind` values: `problem` (integration scenario), `component` (reusable operation), `profile` (component selection policy), and `infrastructure` (the shared runner harness, one node per `(language, hardware)` target).\n- Keep the physics definition separated from execution optimization. `spec.ir.yaml` carries physics-affecting structure in its `case` / `algorithm` / `io_contract` sections and names no implementation target; execution discretion is held in the target profile (`spec/targets/<target_id>.yaml`) and in the generated bundle's lowering plan (`docs/IMPL_PLAN_SPEC.md`).\n- Judge each `node` from its own execution evidence, and aggregate the judgment across its dependency closure.\n\n## Workflow\n\nThe core workflow is five phases. Each phase produces exactly one kind of primary artifact. `docs/WORKFLOW.md` is the entry point of the contract, and `docs/workflow/WORKFLOW_CORE.md` is the canonical source for the common invariants and the per-phase I/O contract.\n\n| # | phase | role | primary artifact |\n|---|-------|------|------------------|\n| 0 | Spec | manual authoring of the natural-language specification | `controlled_spec.md` / `tests.md` / `deps.yaml` (a `profile` has no `tests.md`) |\n| 1 | Compile | natural-language specification → structured IR | `spec.ir.yaml` |\n| 2 | Generate | IR → source code | `source/<source_id>/` |\n| 3 | Build | source → binary (deterministic) | `binary/<binary_id>/bin/` |\n| 4 | Validate | execution and pass/fail judgment | `verdict.json` / `aggregate_verdict.json` |\n\n`Tune` (implementation-variant exploration) and `Promote` (publication to `releases/`) are optional flows outside the core workflow. Neither is implemented: their contracts are deferred (`docs/WORKFLOW.md` §Optional flows), and no `spec` in this tree carries an official release.\n\nFrom `Generate` onward, `spec.ir.yaml` is the sole generation and verification contract; reading `controlled_spec.md` is forbidden except at `Generate.verify`, which reads it as a secondary requirement-fidelity cross-check.\n\nEach phase runs an ordered substep sequence, and there are three launch shapes. An `LLM` substep runs as one `pure-function leaf`: the host inlines a closed context into the prompt, the model returns one JSON document, and the host validates and writes it — the leaf holds no tools, no shell and no write authority. A deterministic substep runs in the conductor's own process. The two producing substeps, `Compile.generate` and `Generate.generate`, may instead run as a `workshop leaf` when the substep's `llm.yaml` entry says `leaf: workshop` (`claude_cli` only, [issue #534](https://github.com/seiya/atmofab/issues/534)): an agent that edits a host-seeded work tree outside the checkout — on `Generate.generate` asking the host to derive, compile, lint, syntax-check and run its bundle, on `Compile.generate` writing the whole IR and asking the host to check it as `Compile.static` will — after which the host snapshots the tree into the same document contract as the pure producer's and runs the same gates; every judging leaf stays pure (`docs/ORCHESTRATION.md` §workshop leaf). The agentic leaf of the pre-Z4 design ([issue #171](https://github.com/seiya/atmofab/issues/171)), which ran in the checkout with tools and a hook layer around it, is retired, and a node with no bundle shape fails closed rather than falling back to one.\n\n| phase | substeps | `LLM` substeps |\n|---|---|---|\n| Compile | `generate` → `static` → `verify` | `generate`, `verify` |\n| Generate | `generate` → `gate` → `verify` | `generate`, `verify` |\n| Build | none (a single step) | none |\n| Validate | `pre_judge` → `execute` → `judge` → `post_judge` | `judge` |\n\nThe deterministic `Compile.static` and `Generate.gate` substeps route a violation back to the phase's `generate` substep, so the `verify` leaf is reached only on a deterministically-clean artifact. `Validate.pre_judge` blocks execution when the dependency DAG is not ready, and `Validate.post_judge` classifies the severity of a violation found after the judge returns.\n\n## Running a workflow\n\nThe host prerequisites — the CLI tools, the Python packages, the target `spec`'s toolchain and `static lint` tool, the sandbox runtime, and the provider credentials — are one list in [docs/RUNBOOK.md](docs/RUNBOOK.md) §0-1, which also carries the SUPPORTED VERSION RANGE of the `static lint` tool (a build outside it is refused at launch, because the rule set the `Generate.gate` applies is measured against that range), pointers to the backend documents that carry the install lines, and the reason code each absence is refused with. Every one of them is refused before the first `LLM` leaf is launched. This paragraph used to be a second list, and it was the longer of the two while the one an operator setting up a machine reads was the shorter (issue #109).\n\nCreate the leaf-`LLM` configuration once. It selects the provider, model, and reasoning effort of each `LLM` leaf, and is the only thing that says what a leaf launches: no flag overrides its contents, and `--llm-config` only selects which file is read. It is gitignored.\n\n```bash\ncp docs/examples/llm_claude.example.yaml llm.yaml\n```\n\nEvery `LLM` leaf is a billed provider call. One node spends at least five of them per full `Compile` → `Validate` pass — more when a phase re-rolls — a `--with-deps` closure spends them per node, and a leaf that dies on a provider quota terminalizes the run unless `--wait-usage-reset` is passed.\n\nStart a run:\n\n```bash\npython3 tools/run_workflow.py <spec_ref> <until_phase> --target <target_id> [--llm-config <path>]\n\n# the dependency closure of one problem node, then the node itself\npython3 tools/run_workflow.py spec/problem/dynamics/advection_diffusion/advdiff1d_linear validate --with-deps --target fortran_cpu\n```\n\n`<spec_ref>` is the `spec` directory of the target node and `<until_phase>` is one of `compile` / `generate` / `build` / `validate`. `--llm-config` defaults to `./llm.yaml`; a missing default stops the run with `llm_config_default_missing` rather than being filled in. `python3 tools/run_workflow.py --help` is canonical for the full option set (`docs/CLI_REFERENCE.md` §Information-acquisition policy); the options a first run needs are:\n\n| option | effect |\n|---|---|\n| `--target` | the target profile `spec/targets/<target_id>.yaml` the run builds for; required while more than one is declared (`docs/RUNBOOK.md` §1-3) |\n| `--with-deps` | resolve the transitive dependency closure and run each not-yet-ready dependency node bottom-up before the target |\n| `--resume` | continue the latest (or `--orchestration-id`) orchestration from its checkpoint, recovering `spec_ref` / `until_phase` / the launched configuration |\n| `--mode` | `dev` (default): a `major` / `critical` verify finding terminalizes the run. `prod`: it is routed to the diagnostician, which decides how far back to recover |\n| `--wait-usage-reset` | sleep out a provider usage limit in place and re-launch the dead substep, instead of terminalizing (bounded; opt-in per invocation) |\n| `--rederive PHASE[,PHASE]` | run the named phase(s) of the target although they are certified; the previous output stays eligible, and later phases re-derive only if the forced phase changed its output (`docs/RUNBOOK.md` §Updating a shared dependency spec) |\n| `--jobs N` | with `--with-deps`: run up to N dependency nodes whose own dependencies are ready at once, each as a child driver process; the explicit parallel-execution instruction the workflow invariants require (default 1 = sequential; `docs/RUNBOOK.md` §Parallel closure) |\n\n`docs/RUNBOOK.md` is the canonical operational procedure: preflight requirements per backend, the minimal loop, the failure-to-phase routing table, and the recovery procedures.\n\n## Build runtime\n\nThe conductor calls the build-runtime library `tools/build_runtime.py` in-process for every `compile`, `run`, `quality check`, `static lint`, and `syntax check`; no leaf imports it (a `Generate.generate` `workshop leaf` reaches five of its operations only through the host-served wrapper, which composes every argument), and one-off `gcc` / `clang` / `gfortran` builds are forbidden. Its entry points, the validation each applies, and the `command_log.jsonl` record each writes are specified in `docs/BUILD_RUNTIME.md`.\n\n## Artifacts\n\nTrial artifacts are confined to `workspace/`, and a write outside it fails the phase. `docs/GLOSSARY.md` defines the identifiers below (`node_key_safe`, `ir_id`, `pipeline_id`, `source_id`, `binary_id`, `run_id`).\n\n```text\nworkspace/ir/<node_key_safe>/<ir_id>/                        spec.ir.yaml, ir_meta.json, dependency_graph.json\nworkspace/pipelines/<node_key_safe>/<target_id>/<pipeline_id>/ lineage.json\n  source/<source_id>/                                        Generate output\n  binary/<binary_id>/                                        Build output\n  runs/<run_id>/<node_key_safe>/                             Validate output and raw evidence\nworkspace/orchestrations/<orchestration_id>/                 orchestration_meta.json, agent_graph.json, agent_runs.jsonl\n```\n\n`Validate` emits `diagnostics.json`, `perf.json`, `verdict.json`, `aggregate_verdict.json`, `summary.json`, and `semantic_review.json` per `run_id`. Promoted official-version artifacts live under `releases/<spec_kind>/<domain>/<family>/<spec_id>/<target_id>/<release_id>/`. `docs/WORKSPACE_LAYOUT.md` is the canonical layout source.\n\nThe driver prints the run's event stream on stdout (`--stdout-format human`, or `jsonl` for a caller that parses it) and mirrors it to `workspace/orchestrations/<orchestration_id>/run_logs/`. A run's terminal state is `orchestration_meta.json#status`; the node's physics judgment, including its dependencies, is `aggregate_verdict.json`.\n\n## Repository layout\n\n```text\ndocs/         workflow contracts, phase specifications, runbook, glossary\nspec/         source specs (problem / component / profile / infrastructure) and the registry\nskills/       execution procedures (SKILL.md) for the flows an operator runs\ntools/        workflow driver, conductor, orchestration runtime, gates, validators, tests\n.claude/      the operator's own interactive session: settings, and the development skills\nreleases/     the component registry, and the promoted official artifacts of the Promote flow (none yet)\nworkspace/    trial artifacts\n```\n\n## In-tree specifications\n\n| spec_kind | spec_id |\n|---|---|\n| `problem` | `advdiff1d_linear`, `shallow_water2d`, `shallow_water2d_channel` |\n| `component` | `dynamics_advdiff_flux_1d_upwind_center2`, `dynamics_advection_diffusion_boundary_1d_periodic_copy`, `dynamics_advection_diffusion_time_update_1d_euler1`, `dynamics_shallow_water_flux_2d_rusanov_p0`, `dynamics_shallow_water_boundary_2d_periodic_copy`, `dynamics_shallow_water_time_update_2d_ssprk2`, `dynamics_shallow_water_boundary_2d_channel_mirror`, `dynamics_shallow_water_source_2d_coriolis`, `dynamics_shallow_water_time_update_2d_rk4`, `dynamics_shallow_water_reconstruction_2d_muscl_mc`, `dynamics_shallow_water_flux_2d_rusanov`, `dynamics_shallow_water_source_2d_tc4_forcing` |\n| `profile` | `dynamics_advdiff_profile_1d_upwind_center2_euler1`, `dynamics_shallow_water_profile_2d_rusanov_p0_ssprk2`, `dynamics_shallow_water_profile_2d_channel_p0_rk4`, `dynamics_shallow_water_profile_2d_channel_p1_rk4` |\n| `infrastructure` | `harness_fortran_cpu`, `harness_cpp_gpu`, `harness_fortran_cpu_mpi` |\n\n`spec/registry/spec_catalog.yaml` is the registry of record for placement and state.\n\n## Tests\n\nFull suite (the default):\n\n```bash\npython3 -m pytest tools/tests/ -q\n```\n\nFast local loop, deselecting the wall-clock-bound `slow` tests:\n\n```bash\npython3 -m pytest tools/tests/ -q -m \"not slow\"\n```\n\n`pytest.ini` registers the `slow` marker, sets `-p no:randomly`, and points `testpaths` at\n`tools/tests` so a bare `pytest` at the repository root runs the suite. The marker is\nopt-out because nothing else runs the full set: deselecting it by default would leave the\nleaf deadline / abandon / teardown guards executed by nobody.\n\nThe review instrument under `.claude/skills/` — `atmofab-review-loop/scripts/mutation_check.py` —\ncarries its tests beside it in `scripts/tests/`. Its skill states the command that runs them\n(`.claude/skills/atmofab-review-loop/SKILL.md`), because no command in this section collects\nthem — measured at `dfeb73dc`: `pytest tools/tests/` and a bare `pytest` each collect 6266, and\nthat directory holds 52 tests. (A second instrument, `measure_claude_tool.py`, measured the\nleaf tools that went in issue #171, and was deleted in issue #445.)\n\n**That command gets none of the guards `tools/tests/conftest.py` installs** for the suite's\nown directory: not the environment strip, not the private-root redirect, not\nthe secret-root refusal, and `--keep-operator-env` is an unrecognized argument there. Nothing\nis known to bite — neither the instrument's tests nor the script read an `ATMOFAB_*` name,\n`CODEX_HOME` or `CLAUDE_CONFIG_DIR` — and no `conftest.py` is placed beside them, so an\ninstrument test that ever does need a guard has to say so itself.\n\n**The suite ignores your `ATMOFAB_*`, `CODEX_HOME` and `CLAUDE_CONFIG_DIR` environment\nvariables** (issue #84). They are per-run knobs that `tools/run_workflow.py` sets in every\nnode's environment, so the shell most likely to have them exported is one used for this\nrepository's own work — and a suite that inherits them answers a question about the machine\ninstead of about the code. Measured at `165c26f`: exporting every such name the tree\nreads took a clean run of 5280 passed to 181 failed, none of the failures belonging to any\nchange. (That commit predates the rename, so spell the names `METDSL_*` to re-take it —\n`docs/GLOSSARY.md` §13.) Every run says which names it removed. To run against a knob you\nset on purpose, pass `--keep-operator-env`; expect failures that belong to the knob. `tools/tests/conftest.py`\nand `tools/tests/suite_env_guard.py` are canonical.\n\n## Documentation entry points\n\n| document | content |\n|---|---|\n| `docs/WORKFLOW.md` | workflow entry point; `docs/workflow/WORKFLOW_CORE.md` and `docs/workflow/phases/` hold the contracts |\n| `docs/SPEC.md` | overall policy, `spec` management requirements, registry requirements |\n| `docs/RUNBOOK.md` | operational procedure, preflight, recovery |\n| `docs/ORCHESTRATION.md` | orchestration design and contract, including the `pure-function leaf` every judging LLM substep runs as and the `workshop leaf` |\n| `docs/AGENT_SKILLS.md` | phase-to-`SKILL` mapping |\n| `docs/GLOSSARY.md` | canonical terminology and artifact definitions |\n| `docs/BACKEND_BOUNDARY.md` | where knowledge of a concrete target-stack technology may live, and which `axis` selects it |\n| `AGENTS.md` | conventions every agent working in this repository follows |\n| `TODO.md` | incomplete tasks aggregated across the repository |\n\n## License\n\nBSD 2-Clause. See `LICENSE`.\n"}