mirror of
https://github.com/kuhyx/wake-alarm.git
synced 2026-11-10 19:27:02 +01:00
On 2026-09-19 the phone was powered off after the bathroom tag and nothing on the PC noticed: every finished session was published and nothing read it. Now wake-alarm distils the phone's morning into an HMAC-signed ~/.local/state/wake_alarm/morning_session.json (wake-alarm-session.timer, 07:00-11:00 every 2 min) that screen-locker and leetcode-guard read to defer their locks -- provisionally until min(start + 90 min, 09:30) while the session is live, until 11:00 once it completed inside that cutoff, and not at all for a session finished later (the phone switched on at noon completes the legs then; that must un-lock nothing). The phone publishes the session at start as well as at finish (current_session, cleared with the finish stamp), so the PC can tell "started, not finished" from "never started". A required 1-5 energy tap joins the weigh-in and ships as latest_energy with a PC reader mirroring _weight (the shared half is _field_reader). Also fixes the vmbox harness, red since the 2026-09-11 home-tidy: the guest tree lives at ~/wake-alarm, and the INSTALL-OK grep matched vm's echo of the command line. Takes Flutter 3.47.5. Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01Tp54ewdXRLaimUuT8LgYyn
53 lines
2.0 KiB
Python
53 lines
2.0 KiB
Python
"""Shared fixtures keeping the wake_alarm suite off the real machine.
|
|
|
|
Two hazards are left now that the PC no longer owns a lock screen, audio or
|
|
an inhibitor:
|
|
|
|
* ``_state`` signs its records with gatelock's HMAC key, and the real key is
|
|
root-owned but *world-readable*. An unpatched run would sign test entries
|
|
with the **production** key on this machine and with none at all anywhere
|
|
else, so the suite would pass here and behave differently in CI.
|
|
* ``WAKE_STATE_FILE`` is a real path inside the repo, and ``_trigger`` now
|
|
*writes* it. The trigger tests never redirected it, because until the
|
|
once-per-day latch moved into the trigger nothing on that path wrote
|
|
anything. Redirecting it here rather than per-file is deliberate: a
|
|
per-file redirect is exactly the kind that gets forgotten when a new writer
|
|
appears, and the failure is silent -- a green suite that quietly stamped
|
|
the live state file.
|
|
"""
|
|
|
|
from __future__ import annotations
|
|
|
|
from typing import TYPE_CHECKING
|
|
from unittest.mock import patch
|
|
|
|
import freedays
|
|
import pytest
|
|
|
|
if TYPE_CHECKING:
|
|
from collections.abc import Generator
|
|
from pathlib import Path
|
|
|
|
|
|
@pytest.fixture(autouse=True)
|
|
def _hermetic(tmp_path: Path) -> Generator[None]:
|
|
"""Keep signing keys and state writes inside ``tmp_path``."""
|
|
key_file = tmp_path / "hmac.key"
|
|
key_file.write_bytes(b"0" * 32)
|
|
with (
|
|
patch("gatelock.log_integrity.DEFAULT_HMAC_KEY_FILE", key_file),
|
|
patch("wake_alarm._state.WAKE_STATE_FILE", tmp_path / "wake_state.json"),
|
|
patch(
|
|
"wake_alarm._session.MORNING_SESSION_FILE",
|
|
tmp_path / "morning_session.json",
|
|
),
|
|
# The shared free-day pool lives under ~/.local/share, outside every
|
|
# path above. Without this, a real free day on the developer's
|
|
# machine would silence the alarm in every trigger test here.
|
|
patch(
|
|
"freedays._api.resolve_paths",
|
|
lambda paths: paths or freedays.Paths.under(tmp_path / "freedays"),
|
|
),
|
|
):
|
|
yield
|