Two-way sync: the PC now publishes its own manual workouts so the phone can see
them for the shared budget. Reverses the old "the PC never pushes" invariant.
- _manual_push.py (new): a small crdt-sync store of PC-originated manuals
(manual_sync_log.json, next to workout_log.json). record_pc_manual() appends
the form's entry (wrapped as the shared kind/date payload under a stable
manual: id, monotonic HLC); push_pc_manuals() runs one sync_log tick to
devices/pc/log.json. Best-effort: no token, empty store, or a 403 from a
read-only token is swallowed so the local form still works.
- _manual_workout_dialog.py: record the manual locally on form save (fast, both
hosts) — published on the next lock startup.
- screen_lock.py: push_pc_manuals() runs in the startup sync step (also retries
any manual a previous push failed to publish).
- Updated the now-false "PC only ever reads, never pushes" docstrings in
_workout_sync.py and _constants.py; noted the contents:write PAT requirement.
A PC-pushed record round-trips through the same ingestion decoder, so it is
ingestable by any device. Full suite green at 100% coverage.
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01PM3auNTifaVgcXWDizZrjH