fix(cache): honor entry expiry in CacheManager.exists() memory fallback
Summary
- The in-memory branch of
CacheManager.exists()(frontend/lib/cache.ts) returned!!entrywithout checkingexpiresAt. - Both
get()andgetAndRemoveIfMatch()already drop expired entries, soexists()could report a key as present whileget()returnsnullfor the same key — an inconsistent contract. - A caller that uses
exists()as a gate (e.g.isAutocompleteCacheExistsinlib/actions/autocomplete/cache.ts) would treat a stale entry as live and skip refreshing it. - Fix mirrors the expiry check in
get(): delete the expired entry and returnfalse. The Redis branch is unchanged (server-side TTL already handles expiry). - Exported
CacheManagerso the in-memory contract can be unit-tested without a Redis server, and added regression tests.
// before
const entry = this.memoryCache.get(key);
return !!entry;
// after
const entry = this.memoryCache.get(key);
if (!entry) return false;
if (entry.expiresAt && entry.expiresAt < Date.now()) {
this.memoryCache.delete(key);
return false;
}
return true;
Verification
pnpm test
# tests 117 # pass 117 # fail 0
New tests: tests/cache-exists-expiry.test.ts (expired -> false and agrees with get(); live -> true).
[!NOTE]
Low Risk
Small, localized cache contract fix with tests; no auth or data-model changes, and Redis behavior is untouched.
Overview
Aligns the in-memory CacheManager.exists() path with get() by treating past-expiresAt entries as absent: delete the stale entry and return false, instead of reporting presence from a non-expired check. Redis exists() is unchanged (TTL still handled server-side).
CacheManager is now exported so the in-memory path can be unit-tested without Redis. New tests in cache-exists-expiry.test.ts cover expired vs live keys and that exists() matches get().
This fixes callers such as isAutocompleteCacheExists that gate refresh on exists()—they could previously see a key as live while get() returned null when REDIS_URL is unset (dev/local memory cache).
Reviewed by Cursor Bugbot for commit c6d8fb9a02cbb501086e7f163f196c4a4ab7287b. Bugbot is set up for automated code reviews on this repo. Configure here.