#16031 · @BYK · opened Mar 4, 2026 at 5:55 PM UTC · last updated Mar 21, 2026 at 10:24 AM UTC
fix: unarchive session on touch, stop cache eviction on archive
Score breakdown
Impact
Clarity
Urgency
Ease Of Review
Guidelines
Readiness
Size
Trust
Traction
Summary
This PR addresses a critical bug where archived sessions become unusable and lose all displayed data upon user interaction. It implements a two-part fix, ensuring that interacting with an archived session unarchives it and preserves its cached data in the frontend. The solution includes changes to both backend session logic and frontend event handling.
Description
Issue for this PR
Closes #16030
Type of change
- [x] Bug fix
- [ ] New feature
- [ ] Refactor / code improvement
- [ ] Documentation
What does this PR do?
Fixes two related bugs that occur when interacting with an archived session:
Problem: When you navigate to an archived session and send a prompt, Session.touch() publishes a session.updated SSE event with time.archived still set. The frontend event-reducer sees this and unconditionally removes the session from the store and wipes all cached data (messages, parts, diffs, todos, permissions, questions, session_status). This causes the "Unable to retrieve session" toast and makes all messages disappear.
Fix (2 parts):
-
Backend —
Session.touch()now clearstime_archived(session/index.ts): When a session is touched (during prompting),time_archivedis set tonull. This means the published SSE event hastime.archived = undefined(falsy), so the event-reducer treats it as a normal update — the session gets upserted back into the sidebar list instead of removed. This is the correct behavior: interacting with an archived session should unarchive it. -
Frontend — Remove
cleanupSessionCaches()from archived branch (event-reducer.ts): Defense in depth. Thesession.updatedhandler still removes archived sessions from the sidebar list and decrementssessionTotal, but no longer wipes cached message/part/diff/todo/permission/question/status data. Archive is reversible — the user can navigate back at any time — and caches are harmless to keep. Memory is reclaimed naturally by store trimming.session.deletedstill cleans caches since deletion is permanent.
How did you verify your code works?
- Backend test: new test in
session.test.tsverifiestouch()on an archived session clearstime_archivedand publishes an event witharchived: undefined - Frontend test: updated
event-reducer.test.ts— the archive test now asserts that caches are preserved (session removed from list, sessionTotal decremented, but message/part/diff/todo/permission/question/status all still defined) - All existing tests pass (15 tests across both files)
Checklist
- [x] I have tested my changes locally
- [x] I have not included unrelated changes in this PR
Linked Issues
#16030 Archived session loses messages and becomes inaccessible when interacted with
View issueComments
No comments.
Changed Files
packages/app/src/components/dialog-connect-provider.tsx
+1−1packages/app/src/components/dialog-custom-provider.tsx
+1−1packages/app/src/context/global-sync/event-reducer.test.ts
+9−8packages/app/src/context/global-sync/event-reducer.ts
+1−1packages/opencode/src/cli/cmd/tui/component/dialog-provider.tsx
+1−1packages/opencode/src/session/index.ts
+1−1packages/opencode/test/session/session.test.ts
+33−0