Files
lanspread/FOLLOW_UP_2.md
T
ddidderr be196f9e4b refactor: type game availability state
Game::availability used string labels that were carried through persisted
library data, protocol summaries, and the Tauri-facing game payload. That
allowed invalid states to exist and required legacy summary conversion code to
defensively map strings back into protocol availability values.

Move Availability to lanspread-db and re-export it from lanspread-proto so the
persisted Game type and wire GameSummary type share one serde enum. The JSON
spelling stays Ready, Downloading, or LocalOnly, so the serialized shape does
not change for current library indexes or peer payloads.

Add typed helpers for sentinel-derived download state. Game::set_downloaded
keeps downloaded and Ready/LocalOnly in lockstep and intentionally collapses
non-ready local state, including Downloading, back to LocalOnly. That matches
the current local-summary contract where active operations are suppressed
instead of advertised as Downloading. Game::normalized_availability keeps the
legacy Game-to-summary path from publishing an inconsistent Ready value when
downloaded is false.

Update the follow-up status note so typed availability is no longer listed as
open work.

Test Plan:
- just fmt
- just test
- just clippy
- just build

Refs: none
2026-05-16 11:49:01 +02:00

55 lines
3.3 KiB
Markdown

# Follow-up Plan #2
State of FOLLOW_UP_PLAN.md after two implementation rounds. Items here are
what's still open, plus notes for follow-up items completed after this file was
created.
## Context for next time
Branch `p2p-codex-muenchhausen` has uncommitted work that completes the bulk of FOLLOW_UP_PLAN.md (52 tests pass via `just test`). Specifically these items in the original plan are **done** and shouldn't be re-opened: #1, #2, #3, #4, #5, #6, #7, #8, #9, #15, #17, #20, plus parts of #12 (update success, version-ini begin/rollback, multi-eti sorted order, corrupt + mismatched-id intent JSON).
The OperationGuard ordering fix in `handlers.rs` is the structurally most important change: install/update/uninstall now drop the guard _before_ the finish event and `refresh_local_game`, so peers see settled state in the next announcement instead of waiting for a scan tick. Tests `*_refreshes_settled_state_after_guard_release` pin this.
## Completed after this file was created
- Tauri-side `active_operations` reconciliation: `PeerEvent::LocalGamesUpdated`
now carries an authoritative active-operation snapshot, the Tauri bridge
replaces its UI operation map from that snapshot, and the React game-list
merge uses the snapshot to clear stale download/install/update/uninstall
spinners even when a begin/finish/fail event was missed.
- Install-recovery matrix: `recovery_covers_install_matrix_rows` now covers the
ten named Installing / Updating / Uninstalling rows from PLAN.md, including
markerless reserved directories while an intent proves ownership.
- Update rollback on commit-rename failure:
`update_commit_rename_failure_restores_previous_local` forces a post-extract
commit conflict without production hooks and verifies backup restore.
- Uninstall delete-failure restore:
`uninstall_delete_failure_restores_backup` covers the rollback path on Unix,
where directory permissions can force recursive delete failure without hooks.
- Installed-only → Ready rescan:
`rescan_promotes_installed_only_game_to_ready_when_sentinel_appears` pins the
cached-index transition after a user adds `version.ini` to a local-only root.
- Scanner gating dispatch: local monitor tests now cover active-operation event
drops, burst collapse, fallback sideload pickup, and non-catalog roots leaving
no library entry or delta.
- Serve gating dispatch: stream tests now cover `GetGame` response gates and
the shared full-file/chunk transfer gate for non-catalog, active-operation,
missing-sentinel, and local-path cases.
- TempDir test helper: peer tests now share `test_support::TempDir` instead of
carrying per-module copies.
- Typed availability: `lanspread-db::Game::availability` now uses the shared
serde enum, with `lanspread-proto` re-exporting it for wire summaries. The
JSON spelling stays `"Ready" | "Downloading" | "LocalOnly"`.
## Still open
### Code hygiene
#### 10. `save_library_index` non-atomic
`local_games.rs:141-148` writes without temp+rename. Corrupt index → next scan rebuilds, so blast radius is small. Match the intent-log atomic pattern if touching that module.
#### 11. Split `download.rs` (1162 lines, growing)
Mixes chunk planning, retry orchestration, version-sentinel transaction, in-memory buffer, and the main loop. Future split into `download/{transaction,chunks,orchestrator}.rs`. Pure cosmetic.