Take a data product from nothing (or an existing dataset that needs a new variable) all the way to published, by running each stage of the pipeline in its own sub-agent. This doc is written for the agent that coordinates that work.
You, the reader, are the coordinator. You do not do the stage work yourself — you sequence it, spawn a sub-agent per stage, and drive to completion.
- New dataset — full integration. The Implement stage follows implementation_guide.md.
- Add a variable to an existing dataset — the Implement and Backfill stages follow add_new_variable.md and are smaller. Explore collapses to inspecting one recent source file for the variable, and Checkpoint A collapses to confirming the variable's name, level, and attrs.
The stages are otherwise the same; Validate and Publish are shared.
- Hold only thread state: the mode, the current stage, the human's scope decisions, and the artifact locations (report path, PR, store URL, report URL). Push every heavy step into a per-stage sub-agent (the Agent tool) and act on its compact return — keep the sub-agent's raw output (plot images, file dumps, long logs) out of your own context.
- One stage at a time, gated. Advance only when the stage's done-check passes. On failure, loop within the stage (bounded) — do not skip ahead or escalate on the first miss.
- Two human checkpoints are hard gates. Stop, surface what's needed, and wait for an answer. Never cross a checkpoint on your own.
- Long-running work (a Kubernetes backfill, a ~1–2 h virtual
run-all) — launch it detached with a monitor and don't block; see the long-runs note in validation.md §1. - Multiple datasets in one run. A run often produces several related datasets — forecast + analysis, early + late, virtual + materialized. Implement them all in a single shared Implement agent (they share source exploration, config, and utilities); Backfill and Validate then run per dataset, and Publish can batch them into one STAC PR.
- Drive to completion. After each sub-agent returns and each checkpoint is answered, proceed to the next stage automatically until Publish is done or you are blocked on a human.
- Goal: know exactly what source data exists, how it's structured, and how to access it.
- Sub-agent: follow source_data_exploration_guide.md and produce its filled-in template. New-dataset mode does the full archive search; add-variable mode only inspects a recent source file for the variable (add_new_variable.md, step 1a).
- Output: an exploration report (a markdown file — keep the path).
- Done: every claim in the report is verified against real source files, with gaps noted rather than guessed.
Present the exploration findings and settle the scope with the human. Always align on the exact provider, model, and variant(s) to produce — including whether this run creates several related datasets (see "Multiple datasets in one run" above) — and on the variable set for each (usually all available variables for a virtual dataset, a common subset for a materialized one). Beyond that, raise the non-obvious questions that surfaced while mapping the source data onto a datacube in our conventions — the decisions the exploration can't settle on its own (an awkwardly-structured or intermittently-available variable, an irregular level set, a coordinate that doesn't map cleanly, a choice between combining or splitting sources). Use judgement about what's worth asking rather than running a fixed checklist. In add-variable mode this collapses to confirming the variable's name, level, and attrs. Record what's decided — it drives every later stage.
- Goal: reviewed code that reads the source data and writes the dataset, with tests.
- Sub-agent(s):
- New dataset: one agent implements every variant in this run, following implementation_guide.md (init → register →
TemplateConfig→RegionJob→DynamicalDataset→ integration test with snapshot values). - Add variable: follow add_new_variable.md.
- Then a code-review sub-agent focused on correctness, simplicity, and the future maintainer — drive to the simplest maintainable end state (the
/code-reviewskill, or a general-purpose agent).
- New dataset: one agent implements every variant in this run, following implementation_guide.md (init → register →
- Output: a PR (code + regenerated
templates/latest.zarr+ tests). A human reviews and merges it — the backfill runs frommain. - Done:
ruff format,ruff check,ty check, and the dataset's tests are green, and the PR is merged tomain.
- Goal: a populated store.
- Sub-agent: follow backfill.md. New dataset: create the bucket, then a
create-new-storebackfill. Add variable: anoverwrite-chunks-and-metadatabackfill filtered to the new variable. - If the dataset already has an active operational update cronjob, do not suspend it — that would delay the production pipeline. Instead run the backfill between update fires so an update publish doesn't fail the backfill's finalize (see backfill.md and parallel_processing.md).
- New dataset: its cron jobs ship suspended (
suspend=True). Once this backfill completes, open a PR removing that so operational updates start keeping the store current — the targeted re-backfills in the Validate stage then follow the between-update-fires rule above. - Output: the store URL, with data written.
- Done: the backfill job succeeded and the expected data is present.
- Goal: a reviewed, ready-to-publish dataset and a draft validation report.
- Sub-agent: follow validation.md — run
run-all, review every plot (a many-variable dataset uses the §3f batched sub-agent process), and investigate-and-verify every anomaly. Fix issues found, run a targeted re-backfill of only the affected variables/positions, and re-validate. Iterate until### For further reviewis empty, then rewrite the summary for an external audience and upload a draft (upload, no--publish). - Add variable: run the full
run-all(not-v-filtered) and carry the current published report's approved## Summaryforward, updating only the new variable's pieces rather than rewriting it — see validation.md §5c′. - Output: the draft report URL.
- Done: draft uploaded,
### For further reviewempty, summary reworded for external readers.
Share the draft report URL (including after your own fix-and-re-validate passes). The human reviews it. Never run upload --publish while ### For further review is non-empty or unapproved. Once the user approves, publish the report to the stable path immediately (upload --publish; see validation.md §5) — it becomes visible on dynamical.org when the STAC change in the next stage triggers a site deploy.
- The dataset catalog on dynamical.org is built from the STAC catalog (
https://stac.dynamical.org/catalog.json), maintained indynamical-org/dynamical-stac. It is the source of truth — you never edit the website; you update the STAC and the site reflects it on its next deploy (which also surfaces the validation report published at Checkpoint B). Regenerate the committed STAC output and open a PR tomainin dynamical-stac:A new dataset first needs an entry added to./scripts/generate # opens each Zarr store; picks up new datasets and variables git add stac/ # commit the regenerated collection.json
src/catalog.py; adding a variable to an existing dataset needs only the regenerate (the generator reads variables from the store). When the run produced several datasets, publish them all in one STAC PR. - Done: the STAC PR is merged to
main.
Placeholder — this process is in flux (Source Coop, Earthmover Marketplace, AWS Open Data, and others). Leave it to a human for now.