fix(ui): show real last-active time for inactive sessions, not TUI load time#1560
fix(ui): show real last-active time for inactive sessions, not TUI load time#1560borng wants to merge 1 commit into
Conversation
…ad time The session detail pane's "last active" line read GetLastActivityTime(), which returns the tmux tracker's lastChangeTime. That field is seeded with time.Now() when the tracker is lazily created on TUI load, and — unlike its guarded sibling LastObservedActivity() — GetLastActivityTime() ignores realActivityConfirmed. For sessions that never confirm real activity (error/idle/stopped panes), the value stays at the load-time seed, so the detail pane showed the most recent TUI load instead of when the session was actually last used. Reloading the TUI reseeded it, making the time jump. The web UI was unaffected because it serves the persisted last_accessed. GetLastActivityTime() also feeds OpenCode session-rotation windows, so its semantics must not change. Add a display-only DisplayLastActivityTime() that consults confirmed activity, then falls back to the persisted LastAccessedAt (matching the web), then CreatedAt. Point the detail pane at it. Tests: - TestDisplayLastActivityTime_NoConfirmedActivity_UsesLastAccessed (regression) - TestDisplayLastActivityTime_NoAccess_FallsBackToCreated - TestDisplayLastActivityTime_AllZero_ReturnsZeroNotLoadTime Created by gregb and his home-grown crew of builders 🦜 🤖
|
No actionable comments were generated in the recent review. 🎉 ℹ️ Recent review info⚙️ Run configurationConfiguration used: Path: .coderabbit.yaml Review profile: CHILL Plan: Pro Plus Run ID: 📒 Files selected for processing (3)
📝 WalkthroughWalkthroughAdds a new ChangesDisplay Last Activity Time
Estimated code review effort: 2 (Simple) | ~10 minutes Possibly related PRs
Suggested reviewers: PoemA rabbit checks the session's clock, 🚥 Pre-merge checks | ✅ 6 | ❌ 1❌ Failed checks (1 warning)
✅ Passed checks (6 passed)
✨ Finishing Touches🧪 Generate unit tests (beta)
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
|
Let me know if you need any updates... my patch has been working great the past week |
Summary
The TUI session detail pane's "⏱ last active" line shows the most recent TUI load time for sessions that aren't actively running (error / idle / stopped), instead of when the session was actually last used. Reloading the TUI makes the timestamp jump to the new load time. The web UI is correct because it serves the persisted
last_accessed.Root cause
renderPreviewPanereadsInstance.GetLastActivityTime(), which returns the tmux tracker'slastChangeTime(internal/tmux/tmux.go:3737). That field is seeded withtime.Now()when the tracker is lazily created on TUI load (ensureStateTrackerLocked,internal/tmux/tmux.go:1255). Unlike its siblingLastObservedActivity(),GetLastActivityTime()does not checkrealActivityConfirmed. For a session that never confirms real activity (no spinner / busy indicator — i.e. a static error/idle/stopped pane), the value stays at that load-time seed, and the intendedCreatedAtfallback inInstance.GetLastActivityTime()is dead code because the seed is never zero.Fix
GetLastActivityTime()is left untouched because it also feeds the OpenCode session-rotation activity windows (internal/session/instance.go:1915, :4579) and its "recent-activity" semantics must not change.Instead, add a display-only
Instance.DisplayLastActivityTime():LastObservedActivity(), which correctly guards onrealActivityConfirmed), elseLastAccessedAt(matches what the web serves), elseCreatedAt(renders as "unknown" when also zero — an honest blank, never a fabricated time).The detail pane now calls
DisplayLastActivityTime(). Net:+82 / −2across 3 files, no behavior change to any existing path.Works retroactively
This is a pure display-path change reading already-persisted data — no migration/backfill. The buggy value was in-memory tracker state, never persisted, so every existing session picks up the corrected display immediately. Verified against a real DB of 195 error sessions: 174 have a real
last_accessed(now match the web exactly); the rest fall back to created-date or "unknown".Tests
TestDisplayLastActivityTime_NoConfirmedActivity_UsesLastAccessed— regression pin (no confirmed activity ⇒LastAccessedAt, and asserts the result is not ~now).TestDisplayLastActivityTime_NoAccess_FallsBackToCreatedTestDisplayLastActivityTime_AllZero_ReturnsZeroNotLoadTimego build ./...,go vet ./internal/session/ ./internal/ui/, the session package suite, and the mandatedTestPersistence_gate all pass (the soleTestPersistence_TmuxDiesWithoutUserScopefailure is pre-existing/environmental — it needs a real fake-login tmux server and fails identically on unmodifiedmain).Notes for reviewers
DisplayLastActivityTimeprefers confirmed activity overLastAccessedAt. For the reported case (error sessions) these are identical. They diverge only for a non-running session that showed a spinner earlier in the same TUI session — where "last active" is arguably more correct than "last accessed". Happy to drop step 1 and strictly mirror the web (LastAccessedAt → CreatedAt) if you prefer.pickBadgeTime) uses a separate formula and already guards viaLastObservedActivity, so it never leaked load-time and is unchanged; it may now differ slightly from the detail-pane value for some sessions.tests/eval/case was added. Flagging in case you want one for the render path.Summary by CodeRabbit
Bug Fixes
Tests