The loop
One loop, four steps, two places where it stops and asks you. This is the operational loop — one turn of the bigger meta-loop, and the part that runs on a daily cron today.
Each step reads and writes plain files in your repo. A daily runner (systemix loop, usually on a cron) moves things forward; you make every actual decision.
Propose
When the loop is idle — nothing running — or a fresh learning just landed, the daily runner queues an experiment-proposal card in .systemix/queue.json. The card carries:
- a suggested id and the goal it serves
- a draft hypothesis built from the newest entries in
LEARNINGS.md(the notebook seeds the next idea) - the learnings it cites, so you can check its reasoning
The runner never creates the experiment file. You accept a proposal by running /init-experiment (it reads the card and prefills the wizard) or systemix experiment new <id> — or you dismiss it, and the runner won't re-propose the same bet.
Build
/init-experiment (or /systemix-init on a fresh repo) writes experiments/<id>.mdx: the bet in one sentence, who it's for, what change ships, and the one number that will prove it. /write-variants drafts the copy or code for the change; /measure wires the event that counts.
Measure
The runner pulls real numbers from PostHog into the experiment file — every day, on its own. Each pass re-reads the file fresh, does exactly one thing, writes it back, and stops on an explicit state:
| Stop | Meaning |
|---|---|
decision-ready | A close-proposal card is queued — you close, never the runner |
blocked:not-measured | No posthog-event yet — run /measure |
blocked:not-wired | No PostHog credentials — run /connect-signal |
waiting:insufficient-evidence | The signal is still too weak — it tries again tomorrow |
Evaluation is variant-vs-control when an A/B split is live, or this window vs the previous one when the experiment ships to everyone.
Learn
When the evidence clears your thresholds, you get a card recommending promote, iterate, or kill — with the numbers that back it. You close it with /close-experiment, and one line is appended to experiments/LEARNINGS.md:
- **2026-07-04 · Bolder CTA lifted calls 24%** — confidence 0.85 · from
[hero-cta-2026-06], decision: promote. Review by: 2026-10-02. Used by: —That file is the loop's memory. The next proposal cites it, and when a new experiment builds on an old learning, the old line gets a Used by: backlink — you can see which lessons are actually load-bearing.
Why separate skills
Each skill is a separate agent run with a clean context — not one long session. The experiment file is the handoff: the next skill reads it cold, does one thing, writes back. State lives in files, not in a chat that fills up and forgets. See Why files & loops.
The cards
Everything the loop wants from you arrives as a card in .systemix/queue.json, visible on /config: proposals to start, recommendations to close, and any suggested change to the loop's own skills or rules. One decision per card. Skill and rule changes are never applied without your approval, whatever the autonomy setting.
The three doors
The same files are readable and writable from three entry points:
| Door | How |
|---|---|
| Claude Code skills | /init-experiment, /measure, /close-experiment, … |
| CLI | systemix experiment new | list | measure | close | learnings · systemix loop |
| MCP | experiment_new, experiment_list, experiment_measure, experiment_close |
Any agent that speaks MCP can drive the loop — not just Claude Code.