Release exp-v0.52.176: start profile list-cache TTL after row build (#6846) (#6847)

* fix(profiles): start list cache TTL after row build

Slow row builds currently consume the cache TTL before the result is stored.
Timestamp the cache at completion so every successful build receives the full TTL.

Refs #5364

Assisted-by: Hermes Agent:gpt-5.6-sol
Assisted-by: Codex:gpt-5.6-luna

* Release exp-v0.52.176: start profile list-cache TTL after row build (#6846)

---------

Co-authored-by: starship-s <45587122+starship-s@users.noreply.github.com>
Co-authored-by: nesquena-hermes <nesquena-hermes@users.noreply.github.com>
This commit is contained in:
authored and GitHub committed 2026-08-07 22:40:22 -07:00
1 parent fcef6ba1af
commit 5e5a41e79f
3 files changed
+27 -1

No files matched your search

@@ -301,6 +301,30 @@ class TestListProfilesSingleFlight:
assert len(results) == n_threads
assert all(r and r[0]["name"] == "default" for r in results)
def test_slow_build_gets_full_cache_ttl(self, mod, monkeypatch):
build_calls = []
clock = [0.0]
def _slow_build():
build_calls.append(1)
clock[0] += 0.08
return [{"name": "default", "path": "/x"}]
with (
patch.object(time, "time", side_effect=lambda: clock[0]),
patch.object(mod, "_is_isolated_profile_mode", return_value=False),
patch.object(mod, "get_active_profile_name", return_value="default"),
patch.object(mod, "_build_profile_rows_fast", side_effect=_slow_build),
):
monkeypatch.setattr(mod, "_LIST_PROFILES_CACHE_TTL", 0.05)
mod._LIST_PROFILES_CACHE = None
mod.list_profiles_api()
mod.list_profiles_api()
assert len(build_calls) == 1, (
"cache age must start after a slow build completes, not before it starts"
)
# ---------------------------------------------------------------------------
# 4. #4783 contract preserved: the cheap mtime probe still runs on every call