1# WP38 — reproducible pipeline (run from the project root; requires the authorised snapshot in data/raw/, see data/raw/README.md)2PY := .venv/bin/python3.PHONY: all env ingest clean match validate external features models robust tables figures paper test lit45all: ingest clean match validate categories features models robust tables figures paper67env:8 uv venv --python 3.12 .venv && uv pip install --python $(PY) -e .910ingest:11 $(PY) -m src.ingest.load_snapshot1213external: # re-download public covariates and geography (manifest in data/external/)14 $(PY) -m src.ingest.external1516clean:17 $(PY) -m src.clean.listings && $(PY) -m src.clean.siblings && $(PY) -m src.clean.listings && $(PY) -m src.clean.stores && $(PY) -m src.reports.data_dictionary1819match:20 $(PY) -m src.features.match_products2122categories: # A-002 classifier (needs cached labels in data/processed/; API keys only to regenerate)23 $(PY) -m src.features.category_model embed && $(PY) -m src.features.category_model train2425validate: # LLM annotations need OPENAI_API_KEY / ANTHROPIC_API_KEY in .env; labels are kept in data/processed/*.csv (never overwritten)26 $(PY) -m src.validation.category_audit report && $(PY) -m src.validation.match_validation report && $(PY) -m src.reports.phase2_audit2728features:29 $(PY) -m src.features.region_category && $(PY) -m src.features.diversity3031models:32 $(PY) -m src.models.h1_raa && $(PY) -m src.models.h2_scale && $(PY) -m src.models.h3_longtail && $(PY) -m src.models.h4_dynamics \33 && $(PY) -m src.models.h5_hedonic && $(PY) -m src.models.h7_complexity && $(PY) -m src.models.qdaci && $(PY) -m src.models.summary $${WP38_LABEL:-rule}3435robust:36 $(PY) -m src.validation.robustness && $(PY) -m src.validation.external_validation3738tables figures:39 $(PY) -m src.reports.make_tables && $(PY) -m src.reports.make_figures4041paper:42 cd paper && latexmk -pdf -interaction=nonstopmode main.tex4344test:45 $(PY) -m pytest -q4647lit:48 $(PY) -m src.literature.verify_refs && $(PY) -m src.literature.make_bib49