Operations — running and reproducing the WP42 laboratory
Prerequisites (controller)
- macOS laptop with Claude Code ≥ 2.1.316 (
claude --version), Python 3.12 venv in the repo (uv venv -p 3.12 .venv && uv pip install -p .venv/bin/python pandas numpy openpyxl python-docx python-pptx reportlab matplotlib statsmodels scipy flask pypdf playwright polars pyarrow duckdb xlsxwriter jinja2 markdown pillow jsonschema lifelines pytest), LibreOffice (brew install --cask libreoffice, used to recalculate workbook formulas before evaluation), LaTeX (latexmk). - API key file
~/Desktop/Cluster/secrets/wp42/.envcontainingANTHROPIC_API_KEY=…(mode 600). Never commit it. - Hidden oracles in
~/wp42-oracles/<TASK_ID>/(regenerate withbenchmark/scenarios/<TASK_ID>/generate.py --seed <seed> --oracle-root ~/wp42-oracles; seeds are inbenchmark/taxonomy/registry.csv). After regeneration, the validators' evaluator fixes (version 1.1) must be re-applied from~/wp42-oracles/<TASK_ID>/validation/diffs ifevaluate.pyis overwritten — generate.py does not write evaluate.py.
Prerequisites (executor nodes)
For each node in src/wp42/config.py NODES: passwordless SSH alias, Claude Code installed (claude --version, 2.1.314 in the pilot), ~/wp42/.env (API key, mode 600), ~/wp42/venv (same packages as the controller + playwright install chromium), LibreOffice in /Applications, python -m wp42.cli sync-tools to copy the portal package to ~/wp42/tools/wp42.
Commands
export PYTHONPATH=src
.venv/bin/python -m pytest -q tests # harness unit tests
.venv/bin/python scripts/freeze.py --tasks ACC-01 … RES-01 # freeze manifest (hashes) before a stage
.venv/bin/python scripts/verify_freeze.py # exit 1 and list if anything changed
.venv/bin/python -m wp42.cli assign --tasks … --arms A0 A1 A2 A3 A4 --reps 2 --seed 4242 --model claude-opus-5-5 --stage pilot
.venv/bin/python -m wp42.cli run --where "stage='pilot' AND status='assigned'" --parallel 12 # Ctrl-C = graceful stop
.venv/bin/python -m wp42.cli status | ledger
.venv/bin/python -m wp42.cli evaluate --where "status='collected'" # (re)evaluate + judge
.venv/bin/python -m wp42.cli reset-run --run-ids <id> # infra error → rerun (log an amendment)
.venv/bin/python -m wp42.cli kill-all # emergency shutdown on every node
.venv/bin/python -m wp42.cli export --tag pilot # data/validated/*.parquet|csv
.venv/bin/python analysis/econometrics/estimate.py --tag pilot # tables + analysis/derived/estimates_pilot.json
.venv/bin/python analysis/figures/make_figures.py --tag pilot # vector figures
.venv/bin/python -m wp42.dashboard --serve 8642 # private dashboardWhere things are
- Raw, immutable:
data/raw/wp42.sqlite(store),data/raw/runs/<run_id>/raw_stream.jsonl(+raw_stream_recovery.jsonl,out/,collection.json,receipt.json,judgments.json). - Validated:
data/validated/runs_<tag>.parquet(one row per run with every metric),judgments_<tag>,receipts_<tag>,events_<tag>. - Protocol:
protocol/preregistration/{PREREGISTRATION.md,freeze_manifest.json},protocol/amendments.csv,protocol/ethics/,protocol/power_analysis/. - Scenario validation reports:
~/wp42-oracles/<TASK_ID>/validation/report.md(outside the repo; summarised in the manuscript appendix).
Known gotchas
timeout does not exist on macOS; claude -p waits 3 s for stdin unless < /dev/null; resume costs are cumulative in total_cost_usd; GUI Apple Events time out over SSH (TCC); a stray /tmp/bisect.py on the laptop shadows the stdlib when Python runs with cwd=/tmp; openpyxl workbooks carry no cached values (hence LibreOffice recalculation on the controller); zsh does not word-split $VAR (list task ids explicitly).