SPB Git

Repository Public Research preview

Commit

P0: node sync/replica/pull/poll scripts, frozen environment (uv.lock, requirements-frozen.txt), sha256 of the 2025 final files before any Stage D run

Items: infrastructure (plan P0). Nodes: M3U96b data home; replicas on M3U96a, M4M64a/b/c, M5M36, M2U64, m4mm, m4mn.

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Simon-Pierre Boucher committed · Nov 6, 2026 parent 4f3e89a
11 changed files +2,212 −0 Browse files
added requirements-frozen.txt +54 −0
@@ -0,0 +1,54 @@
1 +anyio==4.16.0
2 +arch==8.0.0
3 +certifi==2026.10.23
4 +cloudpickle==3.1.2
5 +contourpy==1.4.0
6 +cycler==0.12.1
7 +duckdb==2.0.0
8 +exchange-calendars==4.13.2
9 +filelock==4.2.7
10 +fonttools==4.68.0
11 +formulaic==1.2.2
12 +fsspec==2026.9.0
13 +h11==0.16.0
14 +httpcore==1.0.9
15 +httpx==0.28.1
16 +idna==3.20
17 +iniconfig==2.3.1
18 +interface-meta==2.0.1
19 +jinja2==3.1.6
20 +joblib==1.6.0
21 +kiwisolver==1.5.1
22 +korean-lunar-calendar==0.4.0
23 +lightgbm==4.7.0
24 +markupsafe==3.0.4
25 +matplotlib==3.11.2
26 +mpmath==1.3.0
27 +narwhals==2.28.0
28 +networkx==3.7
29 +numpy==2.5.4
30 +packaging==26.3
31 +pandas==3.1.0
32 +patsy==1.0.3
33 +pillow==13.0.0
34 +pluggy==1.7.0
35 +polars==2.1.0
36 +polars-runtime-32==2.1.0
37 +pyarrow==26.0.0
38 +pygments==2.21.0
39 +pyluach==2.3.0
40 +pyparsing==3.3.3
41 +pytest==9.2.0
42 +python-dateutil==4.0.0
43 +pyyaml==6.0.3
44 +scikit-learn==1.9.1
45 +scipy==1.18.1
46 +setuptools==84.2.1
47 +statsmodels==0.15.0
48 +sympy==1.14.0
49 +threadpoolctl==3.7.0
50 +toolz==1.2.0
51 +torch==2.15.0
52 +typing-extensions==4.16.0
53 +tzdata==2026.6
54 +wrapt==2.5.2
added results/metrics/final/checksums_pre_review.txt +39 −0
@@ -0,0 +1,39 @@
1 +c4dace7b33ceea6cd2f5d79622ee7be5346ce489e0413105e767d709534e9018 per_origin_elastic_net_final_heldout.npz
2 +4ba5c0735369c311d085acc3b7669e51048dd940c984b5b68090b3206946268f per_origin_elastic_net_final.npz
3 +5de93c14815a35ece6aa64c4c2be4d5e3321c0fca408a33f985aef771200fe99 per_origin_ewma_final_heldout.npz
4 +d4c5b8a50d7e2fe98e9e89caea07dac1291cd6b8bbe972112bf88083639f1e0a per_origin_ewma_final.npz
5 +5f429507337ebf13c7f685d21101386d2511271cd013fffc6bea4c224ba83e59 per_origin_garch_t_final_heldout.npz
6 +20d1e3ffba4724715a87f19bcf00ff91c1c506ed280e5c8f73bc8425c145db47 per_origin_garch_t_final.npz
7 +9c24e1888942d17168eb7c3d2e96a43332d1f0b843f6eb616652d7ab48cbaf99 per_origin_har_rv_final_heldout.npz
8 +703b924bde95374e3c7bf3065cc156165bd92973a678f8bac7ce3479f911a193 per_origin_har_rv_final.npz
9 +edfe3cbd039d652718fad1cb4bf2c55004ea5c2b1fb3e6612fd70d109414dee9 per_origin_lightgbm_final_heldout.npz
10 +f6e7b7fbba8a8d1a752275d1718f83b21a3bd8457337891968c9c75e068927a1 per_origin_lightgbm_final.npz
11 +04ea1f7b429de40da8a75499c2b948d9dad0026f57f025ca7511a08d9fe3c104 per_origin_mlp_final_heldout.npz
12 +0405c8bcb3d025c621c9bddbd2d5d882a7645194a7ab4bd7c588274a147db3e9 per_origin_mlp_final.npz
13 +294b9404681d658bcf06a21ae9144970d33f326a35efbcb023d514eaaecc3aab per_origin_mrpt_base_final_heldout.npz
14 +2702e0024221226c14d1453a6b106b2382fd72c88d9e65810411b1bd86739fcc per_origin_mrpt_base_final.npz
15 +a2e60839dbf0b4aeb94649541e1095e25f812fa534092a663987e5943773cc17 per_origin_mrpt_small_1m_only_final_heldout.npz
16 +5be02bb1b2d1ae8b33697c0dd87673fe896f8fdc77d69b28c2d839d8cfc204b7 per_origin_mrpt_small_1m_only_final.npz
17 +0a07ba06d5ee25f803c94b25646a2851f6fc48b3cd5d41ad04993f9d1c924509 per_origin_mrpt_small_final_heldout.npz
18 +40dd61bd825d5b68d932ca1433c43fc4dd39a8cde015bf32b0294ccc5a7aec89 per_origin_mrpt_small_final.npz
19 +549bf054ed510f7ca0e4698a416e3a015b726a11c0f3a671b607e738b79179b7 per_origin_naive_rw_final_heldout.npz
20 +0339e86e1f0cb470674e8ec1905638b0ddd34ee90c826dcf756c777cf74ea780 per_origin_naive_rw_final.npz
21 +407aa937c585f404c9cf18f986f4f5fe1d7f39dd8835efad6444d077b16e5f35 per_origin_ridge_final_heldout.npz
22 +6483e978da4bf96448932f88dcd85e7efdfb4a3436972689856e62e69e17b38e per_origin_ridge_final.npz
23 +273ed5c7284394d608d63f2bcf0f72e4938847174b20d81ffbc3bee72790b045 per_origin_seasonal_vol_final_heldout.npz
24 +17110bcc6a2e49e2118fbbd58048e90266225d3626fee190376ed1861dba5d14 per_origin_seasonal_vol_final.npz
25 +a95a71700791b07efba1e3f76d383dc08e09b5f8bf664f2918480120f4217cdf per_origin_tcn_final_heldout.npz
26 +77456bcc0ebbdd24cbdb8d695a3f0d0c5e1c50804b4208962d0d410540c9a405 per_origin_tcn_final.npz
27 +df9e3b3f4daf1d698b8dc33cdf1b413911a77404fbf2ba4cd1e11221ffbf85ca pred_mlp_final_heldout.npz
28 +d55f5d70964fef1f5d6c23466cdaf7c043d077ca757b638ba4b488577910bb01 pred_mlp_final.npz
29 +b2d6a866a8c8f9bd3ba8b56c74ed6145168635cbd291bc02da8822e1f44808b0 pred_mrpt_base_final_heldout.npz
30 +db981b930bdae56b438330eeb9559cc6330c52e1be32965de98207765fb4b22b pred_mrpt_base_final.npz
31 +7bfc8f86d0cda50ea9a0545fff6555ff8988176dcc17eeb1bd61f28eea5b8bd5 pred_mrpt_small_1m_only_final_heldout.npz
32 +b27fdf2d405db88e1a4ed417169b63181d191b714268a2a28d9dbfedd35a861a pred_mrpt_small_1m_only_final.npz
33 +b3f83d989a51649763cc49be725f5cfa4826a18301ee5ea12de7c1969645bad4 pred_mrpt_small_final_heldout.npz
34 +6812501aec81999febbfe43b814490afe7f5e8722c60d3bd1690f43ac56baefe pred_mrpt_small_final.npz
35 +7b41c741b660abf0380b2c57041afef9fef0ac53069b9bed18ff927ea075c702 pred_tcn_final_heldout.npz
36 +61a85c6380006444e7283b8e72af07cfa5c36d210bc850ba0c8d3c85b06fa0e5 pred_tcn_final.npz
37 +c78a4e2c340aeba1eeab8d2cd5b0a818c019dfb98b150031b5e50234e574da2b leaderboard_final_heldout.csv
38 +f1959468cc63663c4647893b4bfbe6f7d9581ac2e7d3b3657efbdce4e50e359c leaderboard_final.csv
39 +# recorded 2026-11-06T04:46:08Z on m3u96b before any Stage D run
added scripts/review/launch_node.sh +13 −0
@@ -0,0 +1,13 @@
1 +#!/bin/bash
2 +# Review: sync the worktree code to a node (optionally waiting for an input-push log to finish) and launch its batch
3 +# chain detached through scripts/node_run.sh. Usage: launch_node.sh <alias> <batch-name> [wait-log]
4 +set -e
5 +WT="$(cd "$(dirname "$0")/../.." && pwd)"
6 +NODE="${1:?alias}"; BATCH="${2:?batch}"; WAITLOG="$3"
7 +if [ -n "$WAITLOG" ]; then
8 + for i in $(seq 1 360); do grep -q "done" "$WAITLOG" 2>/dev/null && break; sleep 10; done
9 + grep -q "done" "$WAITLOG" || { echo "[launch_node] $NODE: input push did not finish"; exit 1; }
10 +fi
11 +bash "$WT/scripts/review/sync_node.sh" "$NODE" > /dev/null
12 +ssh "$NODE" "cd ~/wp41_uqo && scripts/node_run.sh $BATCH 'bash scripts/review/batch_$BATCH.sh'"
13 +echo "[launch_node] $NODE $BATCH launched $(date +%H:%M)"
added scripts/review/ledger.sh +16 −0
@@ -0,0 +1,16 @@
1 +#!/bin/bash
2 +# Run one review job and append a ledger line to results/metrics/review_runs.jsonl (node, chip, command, wall-clock, exit).
3 +# Usage: scripts/review/ledger.sh <job-name> <command...>
4 +cd ~/wp41_uqo || exit 1
5 +name="$1"; shift
6 +mkdir -p results/metrics
7 +start=$(date -u +%FT%TZ); t0=$(date +%s)
8 +echo "[ledger] $(hostname) $name START $start :: $*"
9 +bash -c "$*"; rc=$?
10 +t1=$(date +%s)
11 +chip=$(sysctl -n machdep.cpu.brand_string 2>/dev/null)
12 +sha=$(cat scripts/*.py src/chronos_x/*.py src/chronos_x/*/*.py 2>/dev/null | shasum -a 256 | cut -c1-16)
13 +printf '{"node": "%s", "chip": "%s", "job": "%s", "command": %s, "start": "%s", "end": "%s", "wall_s": %d, "exit": %d, "code_sha256_16": "%s", "config_env": {"WP41_NUM_WORKERS": "%s", "OMP_NUM_THREADS": "%s"}}\n' \
14 + "$(hostname)" "$chip" "$name" "$(printf '%s' "$*" | python3 -c 'import json,sys; print(json.dumps(sys.stdin.read()))')" "$start" "$(date -u +%FT%TZ)" $((t1 - t0)) $rc "$sha" "$WP41_NUM_WORKERS" "$OMP_NUM_THREADS" >> results/metrics/review_runs.jsonl
15 +echo "[ledger] $(hostname) $name END exit=$rc wall=$((t1 - t0))s"
16 +exit $rc
added scripts/review/poll.sh +15 −0
@@ -0,0 +1,15 @@
1 +#!/bin/bash
2 +# Review: one poll of every node's review jobs. Usage: scripts/review/poll.sh [alias ...]
3 +NODES="${*:-M3U96b M3U96a M4M64a M4M64b M4M64c M5M36 M2U64 m4mm m4mn}"
4 +for n in $NODES; do
5 + ssh -o ConnectTimeout=15 -o BatchMode=yes "$n" bash -s 2>&1 <<'REMOTE'
6 +cd ~/wp41_uqo 2>/dev/null || exit 0
7 +echo "== $(hostname) $(date +%H:%M) load=$(sysctl -n vm.loadavg) free=$(df -g ~ | tail -1 | awk '{print $4}')G"
8 +shopt -s nullglob
9 +for f in results/logs/N*.exit results/logs/review_*.exit; do echo " EXIT $(basename $f) = $(cat $f)"; done
10 +for f in results/logs/N*.out results/logs/review_*.out; do echo " $(basename $f): $(tail -n1 $f | cut -c1-150)"; done
11 +now=$(date +%s)
12 +for l in $(ls -t results/metrics/*/*/train_log.jsonl results/metrics/*/*/copula/train_log.jsonl 2>/dev/null | head -3); do
13 + age=$(( now - $(stat -f %m $l) )); echo " $l age=${age}s $(grep -E '"event": "(train|val)"' $l | tail -n1 | cut -c1-170)"; done
14 +REMOTE
15 +done
added scripts/review/pull_node.sh +13 −0
@@ -0,0 +1,13 @@
1 +#!/bin/bash
2 +# Review: pull aggregated results (CSV/JSON/txt <= 20 MB; never origins_*.csv, *.npz, *.pt, *.pkl, *.parquet) from the
3 +# data home M3U96b into the worktree's results/metrics/ and results/logs (run logs). Usage: scripts/review/pull_node.sh [alias]
4 +set -e
5 +WT="$(cd "$(dirname "$0")/../.." && pwd)"
6 +NODE="${1:-M3U96b}"
7 +rsync -rlt --max-size=20m --exclude 'origins_*.csv' --exclude '*.npz' --exclude '*.pt' --exclude '*.pkl' --exclude '*.parquet' \
8 + --exclude '*.tmp' --exclude 'val_samples_*' --exclude '__pycache__' \
9 + "$NODE:~/wp41_uqo/results/metrics/" "$WT/results/metrics/"
10 +mkdir -p "$WT/results/logs"
11 +rsync -rlt --max-size=20m --include '*/' --include 'N*.out' --include 'N*.exit' --include '*.exit' --include 'provenance_*.jsonl' --include 'review_*.out' --exclude '*' \
12 + "$NODE:~/wp41_uqo/results/logs/" "$WT/results/logs/"
13 +echo "[pull_node] done from $NODE"
added scripts/review/push_inputs.sh +19 −0
@@ -0,0 +1,19 @@
1 +#!/bin/bash
2 +# Review P0: copy the per-package result inputs from the data home M3U96b to a replica over the LAN (node-to-node rsync
3 +# through the forwarded agent). Usage: scripts/review/push_inputs.sh <lan-ip> <seeds|budget_small|budget_1m|p1_main_final|p1_ablations>
4 +set -e
5 +IP="${1:?lan-ip}"; KIND="${2:?kind}"
6 +R='rsync -a -e "ssh -o StrictHostKeyChecking=no"'
7 +case "$KIND" in
8 + seeds)
9 + ssh -A M3U96b "cd ~/wp41_uqo/results/metrics && ssh -o StrictHostKeyChecking=no $IP 'mkdir -p ~/wp41_uqo/results/metrics/main' && $R main/origins_test.csv main/per_origin_naive_rw_test.npz $IP:~/wp41_uqo/results/metrics/main/";;
10 + budget_small|budget_1m)
11 + twin=mrpt_small; [ "$KIND" = budget_1m ] && twin=mrpt_small_1m_only
12 + ssh -A M3U96b "cd ~/wp41_uqo/results/metrics && ssh -o StrictHostKeyChecking=no $IP 'mkdir -p ~/wp41_uqo/results/metrics/main/$twin ~/wp41_uqo/results/metrics/ablations' && $R main/origins_test.csv main/per_origin_naive_rw_test.npz $IP:~/wp41_uqo/results/metrics/main/ && $R main/$twin/last.pt main/$twin/train_summary.json $IP:~/wp41_uqo/results/metrics/main/$twin/ && $R ablations/origins_test.csv $IP:~/wp41_uqo/results/metrics/ablations/";;
13 + p1_main_final)
14 + ssh -A M3U96b "cd ~/wp41_uqo/results/metrics && ssh -o StrictHostKeyChecking=no $IP 'mkdir -p ~/wp41_uqo/results/metrics/main ~/wp41_uqo/results/metrics/final' && $R --include='per_origin_*' --include='origins_*.csv' --include='summary_*' --include='run_meta_*' --include='leaderboard_*' --include='compare_*' --include='pairwise_*' --exclude='*' main/ $IP:~/wp41_uqo/results/metrics/main/ && $R --include='per_origin_*' --include='origins_*.csv' --include='summary_*' --include='run_meta_*' --include='leaderboard_*' --include='compare_*' --include='pairwise_*' --exclude='*' final/ $IP:~/wp41_uqo/results/metrics/final/";;
15 + p1_ablations)
16 + ssh -A M3U96b "cd ~/wp41_uqo/results/metrics && ssh -o StrictHostKeyChecking=no $IP 'mkdir -p ~/wp41_uqo/results/metrics/main ~/wp41_uqo/results/metrics/ablations' && $R --include='per_origin_*' --include='origins_test.csv' --include='summary_*' --include='run_meta_*' --include='leaderboard_*' --include='compare_*' --include='pairwise_*' --include='path_scores_*' --include='pred_mrpt_small_copula_test.npz' --exclude='*' ablations/ $IP:~/wp41_uqo/results/metrics/ablations/ && $R main/pred_mrpt_small_test.npz main/origins_test.csv $IP:~/wp41_uqo/results/metrics/main/";;
17 + *) echo "unknown kind $KIND"; exit 1;;
18 +esac
19 +echo "[push_inputs] $IP $KIND done"
added scripts/review/replicate_node.sh +22 −0
@@ -0,0 +1,22 @@
1 +#!/bin/bash
2 +# Review P0: make a replica of the code + environment (+ grids for GPU nodes and m4mn) on one cluster node.
3 +# Usage: scripts/review/replicate_node.sh <alias> <lan-ip> [--grids] [--inputs "<rsync source list on M3U96b>"]
4 +# Run from the laptop with agent forwarding (ssh -A is configured); node-to-node rsync goes M3U96b -> <lan-ip> over the LAN.
5 +set -e
6 +WT="$(cd "$(dirname "$0")/../.." && pwd)"
7 +NODE="${1:?alias}"; IP="${2:?lan-ip}"; shift 2
8 +UV=$(ssh "$NODE" 'for u in /opt/homebrew/bin/uv $HOME/.local/bin/uv $HOME/.cargo/bin/uv /usr/local/bin/uv; do [ -x "$u" ] && echo "$u" && break; done')
9 +[ -n "$UV" ] || { echo "no uv on $NODE"; exit 1; }
10 +echo "[replicate] $NODE ($IP): code"
11 +bash "$WT/scripts/review/sync_node.sh" "$NODE" >/dev/null
12 +echo "[replicate] $NODE: venv (frozen requirements from M3U96b)"
13 +ssh "$NODE" "cd ~/wp41_uqo && ( [ -x .venv/bin/python ] || $UV venv -q -p 3.12 .venv ) && $UV pip install -q -p .venv/bin/python -r requirements-frozen.txt && $UV pip install -q -p .venv/bin/python --no-deps -e . && .venv/bin/python -c 'import torch, lightgbm, numpy, scipy; print(\"torch\", torch.__version__, \"mps\", torch.backends.mps.is_available(), \"lightgbm\", lightgbm.__version__, \"numpy\", numpy.__version__, \"scipy\", scipy.__version__)'"
14 +for arg in "$@"; do
15 + case "$arg" in
16 + --grids)
17 + echo "[replicate] $NODE: grids + instruments from M3U96b over the LAN"
18 + ssh -A M3U96b "mkdir -p /tmp && rsync -a -e 'ssh -o StrictHostKeyChecking=no' --rsync-path='mkdir -p ~/wp41-cache/grids/2018-01-02_2025-12-31 ~/wp41-cache/instruments && rsync' ~/wp41-cache/grids/2018-01-02_2025-12-31/ $IP:~/wp41-cache/grids/2018-01-02_2025-12-31/ && rsync -a -e 'ssh -o StrictHostKeyChecking=no' ~/wp41-cache/instruments/ $IP:~/wp41-cache/instruments/"
19 + ssh "$NODE" 'echo "grids: $(ls ~/wp41-cache/grids/2018-01-02_2025-12-31 | wc -l) dirs, $(du -sh ~/wp41-cache/grids | cut -f1)"';;
20 + esac
21 +done
22 +ssh "$NODE" "cd ~/wp41_uqo && ulimit -n 65536 && OMP_NUM_THREADS=4 .venv/bin/python -m pytest -q tests/unit tests/numerical tests/leakage 2>&1 | tail -2; df -g ~ | tail -1 | awk '{print \"free GiB:\", \$4}'"
added scripts/review/smoke_review.sh +37 −0
@@ -0,0 +1,37 @@
1 +#!/bin/bash
2 +# Review smoke test on license-free synthetic bars: exercises the Stage D code paths (stratified validation subset,
3 +# baseline artefacts, copula head retrain with --copula-only, cluster-t/daily-DM/MCS/stress-contrast inference,
4 +# glob_set/shuffle_mode ablation options). ~5 min on a Mac Studio. Writes results/metrics/synthetic_review/ (deleted at the end).
5 +set -e
6 +cd "$(dirname "$0")/../.."
7 +PY=.venv/bin/python; [ -x "$PY" ] || PY=python3
8 +export PYTORCH_ENABLE_MPS_FALLBACK=1 OMP_NUM_THREADS=4
9 +CACHE=/tmp/wp41_syn_cache; rm -rf $CACHE; export WP41_CACHE=$CACHE
10 +$PY scripts/make_synthetic.py --cache $CACHE --n 4 --end 2024-05-31
11 +CFG=/tmp/wp41_synthetic_review.yaml
12 +sed -e "s#cache: data/synthetic/cache#cache: $CACHE#" -e "s/name: synthetic_smoke/name: synthetic_review/" \
13 + -e "s/eval_batch_size: 64}/eval_batch_size: 64, val_subset: 300}/" configs/synthetic_smoke.yaml > $CFG
14 +cat >> $CFG <<'YAML'
15 + - {name: mrpt_tiny_redglob, preset: tiny, kwargs: {regime: none}, feature_set: full, glob_set: reduced}
16 + - {name: mrpt_tiny_shuffled_pv, preset: tiny, kwargs: {}, feature_set: full, shuffle_minutes: true, shuffle_minutes_eval: true, shuffle_mode: price_volume}
17 +YAML
18 +$PY scripts/run_experiment.py --config $CFG --exp-name synthetic_review
19 +OUT=results/metrics/synthetic_review
20 +ls $OUT/pred_har_rv_test.npz $OUT/pred_lightgbm_test.npz $OUT/baseline_models.pkl $OUT/nu_hat.json $OUT/baselines_meta_test.json
21 +grep -c '"event": "val_subset"' $OUT/mrpt_tiny/train_log.jsonl
22 +$PY scripts/pairwise.py --exp synthetic_review --tag test --pairs mrpt_tiny:har_rv,mrpt_tiny:naive_rw,mrpt_tiny_copula:mrpt_tiny_copula_indep,mrpt_tiny_redglob:mrpt_tiny,mrpt_tiny_shuffled_pv:mrpt_tiny --universe data/manifests/universe_synthetic.json --mcs --stride 30
23 +ls $OUT/pairwise_test.csv $OUT/mcs_test.csv $OUT/stress_contrast_test.csv $OUT/pairwise_families.json
24 +$PY scripts/run_experiment.py --config $CFG --exp-name synthetic_review --stage neural --copula-only --only-models mrpt_tiny_copula
25 +ls $OUT/mrpt_tiny_copula/copula_orig $OUT/mrpt_tiny_copula/copula/train_log.jsonl $OUT/path_scores_mrpt_tiny_copula_test.json $OUT/per_origin_mrpt_tiny_copula_test_v1orig.npz
26 +grep '"event": "val"' $OUT/mrpt_tiny_copula/copula/train_log.jsonl | tail -3
27 +$PY scripts/run_experiment.py --config $CFG --exp-name synthetic_review --stage tables
28 +WP41_LEGACY_BASELINES=1 $PY scripts/run_experiment.py --config $CFG --exp-name synthetic_review_legacy --stage baselines
29 +$PY scripts/run_experiment.py --config $CFG --exp-name synthetic_review_legacy --stage tables
30 +$PY - <<'PY'
31 +import pandas as pd
32 +a = pd.read_csv("results/metrics/synthetic_review/leaderboard_test.csv"); b = pd.read_csv("results/metrics/synthetic_review_legacy/leaderboard_test.csv")
33 +m = a.merge(b, on=["model", "H"], suffixes=("_new", "_legacy"))
34 +print(m[m.model.isin(["har_rv", "ridge", "lightgbm"])][["model", "H", "crps_new", "crps_legacy", "cov_50_new", "cov_50_legacy"]].to_string(index=False))
35 +PY
36 +rm -rf results/metrics/synthetic_review results/metrics/synthetic_review_legacy $CACHE
37 +echo "[smoke_review] OK"
added scripts/review/sync_node.sh +25 −0
@@ -0,0 +1,25 @@
1 +#!/bin/bash
2 +# Review P0: push the worktree code (never results/, never the laptop checkout) to a node's ~/wp41_uqo and check it.
3 +# Usage: scripts/review/sync_node.sh <alias> [--install] [--test]
4 +set -e
5 +WT="$(cd "$(dirname "$0")/../.." && pwd)"
6 +NODE="${1:?alias}"; shift || true
7 +UV=$(ssh "$NODE" 'for u in /opt/homebrew/bin/uv $HOME/.local/bin/uv $HOME/.cargo/bin/uv /usr/local/bin/uv; do [ -x "$u" ] && echo "$u" && break; done')
8 +[ -n "$UV" ] || { echo "no uv on $NODE"; exit 1; }
9 +ssh "$NODE" 'mkdir -p ~/wp41_uqo/results/logs ~/wp41_uqo/results/metrics'
10 +for sub in scripts src configs tests data/manifests; do
11 + rsync -rlc --delete --exclude __pycache__ --exclude '.pytest_cache' "$WT/$sub/" "$NODE:~/wp41_uqo/$sub/"
12 +done
13 +rsync -rlc "$WT/pyproject.toml" "$WT/Makefile" "$WT/CLAUDE.md" "$WT/README.md" "$NODE:~/wp41_uqo/"
14 +[ -f "$WT/uv.lock" ] && rsync -rlc "$WT/uv.lock" "$NODE:~/wp41_uqo/"
15 +[ -f "$WT/requirements-frozen.txt" ] && rsync -rlc "$WT/requirements-frozen.txt" "$NODE:~/wp41_uqo/"
16 +for arg in "$@"; do
17 + case "$arg" in
18 + --install) ssh "$NODE" "cd ~/wp41_uqo && $UV pip install -q -p .venv/bin/python --no-deps -e . && .venv/bin/python -c 'import chronos_x, torch; print(\"chronos_x ok, torch\", torch.__version__, \"mps\", torch.backends.mps.is_available())'";;
19 + --test) ssh "$NODE" "cd ~/wp41_uqo && ulimit -n 65536 && OMP_NUM_THREADS=4 .venv/bin/python -m pytest -q tests/unit tests/numerical tests/leakage 2>&1 | tail -3";;
20 + esac
21 +done
22 +echo "[sync_node] dry-run differences (should be empty):"
23 +for sub in scripts src configs tests data/manifests; do
24 + rsync -rlcn --delete --exclude __pycache__ --exclude '.pytest_cache' --out-format='%n' "$WT/$sub/" "$NODE:~/wp41_uqo/$sub/" | grep -v '/$' || true
25 +done
added uv.lock +1959 −0
Large diff (1,960 lines) is not loaded by default to keep the page fast.Load diff
Menu

Theme