tests/test-persist-score-history.sh passes or fails depending on the wall clock, because the afterhours push hook leaks into its temp fixtures.
Observed
Run during a v1.99.2 release check, Monday 2026-08-17 13:30 local:
=== Results ===
Passed: 2
Failed: 3
Same command, same tree, one env var changed:
$ AFTERHOURS_SKIP=1 ./tests/test-persist-score-history.sh
=== Results ===
Passed: 5
Failed: 0
The failure output names the cause directly:
afterhours: push blocked (currently 13:30 Mon)
allowed: weekdays before 08:00 or after 17:00, or any time on weekends
override: AFTERHOURS_SKIP=1 git push
error: failed to push some refs to '/var/folders/.../persist-score-history.Sv8GaY/remote.git'
The fixture creates a throwaway bare repo in $TMPDIR and pushes to it. The maintainer's afterhours hook is installed at a scope that applies to that push too, so three assertions fail against a fixture remote that has nothing to do with working hours.
Why this matters more than a flaky test
The suite is green on CI and red locally for a reason that has nothing to do with the code. Whoever runs the suite before a release on a weekday afternoon sees 3 failures and has to decide whether they are real — a decision that costs a cycle every time and eventually gets answered with a reflexive "probably environmental," which is how a genuine regression gets waved through.
It also inverts what the test is for. Two of the five assertions concern push behaviour under a declining hook (persist exits once on hook-declined push), so the suite deliberately exercises hook interaction. Having an unrelated real hook fire on top of that makes the passing assertions less trustworthy, not just the failing ones.
Direction
The fixture should be isolated from the ambient hook environment rather than the runner exporting AFTERHOURS_SKIP=1 — an override in the runner would also suppress the hook in the two assertions that are supposed to observe a declining hook, turning a real check into a tautology. Isolating the fixture's git config/hook path keeps those assertions meaningful while removing the wall-clock dependency.
Also worth checking while in here
The run stopped at Failed: 3 but the tail shows only assertions, no timing guard. Sibling e2e suites in the same list (tests/e2e/run-simulation.sh, tests/e2e/test-eval-prompt-regression.sh) make live model calls against the maintainer's subscription and hang indefinitely without an API key — the first was observed spawning a full claude --print build task during what was supposed to be a local release check. That is a separate defect from this one, but the same root question applies to both: a local suite run should not depend on ambient credentials, ambient hooks, or the time of day.
tests/test-persist-score-history.shpasses or fails depending on the wall clock, because the afterhours push hook leaks into its temp fixtures.Observed
Run during a v1.99.2 release check, Monday 2026-08-17 13:30 local:
Same command, same tree, one env var changed:
The failure output names the cause directly:
The fixture creates a throwaway bare repo in
$TMPDIRand pushes to it. The maintainer's afterhours hook is installed at a scope that applies to that push too, so three assertions fail against a fixture remote that has nothing to do with working hours.Why this matters more than a flaky test
The suite is green on CI and red locally for a reason that has nothing to do with the code. Whoever runs the suite before a release on a weekday afternoon sees 3 failures and has to decide whether they are real — a decision that costs a cycle every time and eventually gets answered with a reflexive "probably environmental," which is how a genuine regression gets waved through.
It also inverts what the test is for. Two of the five assertions concern push behaviour under a declining hook (
persist exits once on hook-declined push), so the suite deliberately exercises hook interaction. Having an unrelated real hook fire on top of that makes the passing assertions less trustworthy, not just the failing ones.Direction
The fixture should be isolated from the ambient hook environment rather than the runner exporting
AFTERHOURS_SKIP=1— an override in the runner would also suppress the hook in the two assertions that are supposed to observe a declining hook, turning a real check into a tautology. Isolating the fixture's git config/hook path keeps those assertions meaningful while removing the wall-clock dependency.Also worth checking while in here
The run stopped at
Failed: 3but the tail shows only assertions, no timing guard. Sibling e2e suites in the same list (tests/e2e/run-simulation.sh,tests/e2e/test-eval-prompt-regression.sh) make live model calls against the maintainer's subscription and hang indefinitely without an API key — the first was observed spawning a fullclaude --printbuild task during what was supposed to be a local release check. That is a separate defect from this one, but the same root question applies to both: a local suite run should not depend on ambient credentials, ambient hooks, or the time of day.