diff --git a/NEXT_SESSION_PROMPT.md b/NEXT_SESSION_PROMPT.md index 69964072..416aff36 100644 --- a/NEXT_SESSION_PROMPT.md +++ b/NEXT_SESSION_PROMPT.md @@ -1,23 +1,122 @@ -# Next session: shell splits, tests first +# Next session: three explicit asks, then keep splitting > **Paste this whole file into a fresh Claude session opened in `~/testsAndMisc`.** > It is self-contained. Do not go looking for the previous session's context. -## Where things stand +Over-cap: **37 → 24** (20 shell, 2 kotlin, 1 dart, 1 markdown — this file). +17 commits pushed. **Python is done**: every `.py` is under the cap at 100% +line+branch coverage where the gate measures it. -Over-cap: **37 → 25** (21 shell, 2 kotlin, 1 dart, 1 markdown — the markdown is -this file). 15 commits, `0cf487b..HEAD`, all pushed. +The user has given three direct instructions. Do them in this order, each as +its own commit. They are already decided — do **not** re-litigate them. -**Python is done.** Every `.py` in the repo is under the cap, at 100% line and -branch coverage where the gate measures it. The remaining work is shell, plus -three files in other languages. +--- -## Tooling built last session — use it, don't rebuild it +## 1. Fix the `_VENDOR_KW` Intel bug -Two scripts do the mechanical half. Both were validated before use; don't -re-derive them. +`python_pkg/vscode_optimizer/_hardware.py:22`: -**`meta/scripts/extract_shell_functions.py`** moves functions into a library: +```python +_VENDOR_KW = {"nvidia": "NVIDIA", "amd": "AMD", "ati": "AMD", "intel": "Intel"} +``` + +`_detect_gpu` does `for kw, vendor in _VENDOR_KW.items(): if kw in low:`. +Every real `lspci` display line contains **"VGA comp*ati*ble controller"**, so +`"ati"` matches unconditionally and `"intel"` is unreachable. **Intel iGPUs are +reported as AMD**, which switches on the GPU-accelerated terminal and AMD-only +Electron flags. This machine is unaffected only because `"nvidia"` is checked +first. + +**Do:** + +- Fix it so vendor detection keys on the device description rather than the + whole line — the text after the last `:` is already extracted into + `hw.gpu_model` one line above. Match against that, not `low`. +- Delete the `strict=True` xfail `test_detect_gpu_should_recognise_an_intel_igpu` + in `python_pkg/vscode_optimizer/tests/test_gpu_disk.py` and make it a normal + passing test. **The xfail is `strict=True`, so a fix without removing the + marker fails the suite** — that is deliberate. +- The parametrised `test_detect_gpu_maps_each_vendor_keyword` currently + _characterises_ the bug: two of its cases assert `"AMD"` for an Intel line and + for an unknown vendor. Update both to the correct expectations. +- Verify with a real run: `python3 -m python_pkg.vscode_optimizer --dry-run` + must still detect this machine's RTX 3090 as NVIDIA and propose the same + **18 changes**. Then confirm the repo gate: bare `pytest` (memory-capped) + at 100%. + +## 2. Split the `phone_focus_mode` scripts anyway + +The user has accepted the deployment risk. **This does not mean skip the copy +lists** — it means proceed with the splits, doing them correctly. + +`deploy.sh` has **two** hardcoded per-file lists and never deploys `lib/`: + +- an `adb_cmd push "$DEPLOY_DIR/" "/data/local/tmp/focus_stage/"` (~line 381) +- an `adb_root "cp /data/local/tmp/focus_stage/ $REMOTE_DIR/"` (~line 497) + +**Every new sibling must be added to BOTH, in the same commit.** Missing the +push leaves the copy pointing at a file that was never staged. Use a **sibling +file** beside the entry script, never a `lib/` member — these scripts source +`"$SCRIPT_DIR/.sh"` and `lib/` does not exist on the phone. + +`tether_enforcer.sh` was done last session and is the worked example — read that +commit before starting. + +Targets, cheapest first, with what can verify each: + +| file | lines | verifiable by | +| -------------------- | ----- | ------------------------------------------------------------------------------------ | +| `dns_enforcer.sh` | 325 | `lib/tests/test_dns_enforcer.sh` — **runnable** | +| `phone_backup.sh` | 333 | no test; not in deploy.sh's lists at all | +| `curfew_enforcer.sh` | 367 | no test | +| `hosts_enforcer.sh` | 421 | no test | +| `lib/monitor.sh` | 449 | `lib/tests/test_monitor.sh` — **runnable**; already a lib, not deployed by deploy.sh | +| `focus_daemon.sh` | 543 | no test | +| `config.sh` | 571 | **`python_pkg/focus_policy/loader.py` parses it** — see below | +| `deploy.sh` | 835 | not deployed itself; entry+`lib/` IS safe here | +| `focus_ctl.sh` | 1091 | no test | + +Start with `dns_enforcer.sh` and `lib/monitor.sh`: both have real test scripts, +so you can prove the split the way `tether_enforcer` was proved (run the test +before and after; the count must match exactly). + +**`config.sh` is special.** `python_pkg/focus_policy/loader.py` is a +mini-interpreter that parses it as the live source of truth. Splitting it breaks +that loader unless the parser follows. `focus_policy` has 100% tests that will +catch it — run them. Plan the two changes together, or do `config.sh` last. + +## 3. Restructure the three parked files + +Last session parked these because a verbatim function move cannot get them under +the cap. The user has authorised restructuring. **Restructuring means the +verbatim harness no longer applies, so each one needs a test or a real run +instead** — say plainly which you used. + +- **`install_plagiarism_tools.sh` (534, only 3 tiny functions).** ~500 lines of + top-level code. Wrap coherent stages in functions, then move those. This is + the most mechanical of the three; do it first. +- **`libre_translate.sh` (488, 18 funcs).** After the clean seams are taken, + `parse_args` (111 lines), `write_env_file`, `detect_container_user` and `main` + all assign **and** read the same configuration globals. Four attempts were + spent relocating them; that does not work. Restructure `parse_args` — e.g. + split the case body into per-flag helpers, or move the whole config-globals + cluster into one lib that owns both writes and reads. +- **`diagnose_pacman_hook_stall.sh` (493, 15 funcs).** Same shape: `run_one` + writes `LAST_ELAPSED`, `main` reads it. Also emits **SC2153** + (`PACMAN_BIN` vs `PACMAN_PID`) once split — that is a real shellcheck finding + to resolve, not to suppress. + +--- + +## Tooling — use it, don't rebuild it + +**`meta/scripts/extract_shell_functions.py`** — moves functions into a library. +Walks brace-by-brace and lifts only function blocks. **Never slice by line +range**: these scripts interleave top-level commands between function +definitions, and a range slice sweeps those into the library where they run at +source time and out of order. It refuses to guess when there is no `set -e` +anchor (as in the `#!/system/bin/sh` phone scripts) — place the source line by +hand there, after the existing `. "$SCRIPT_DIR/config.sh"`. ```bash python3 meta/scripts/extract_shell_functions.py