Skip to content

Add session status display to System Status tab and fix stale-session detection#685

Draft
SimonHeybrock wants to merge 7 commits intomulti-sessionfrom
multi-session-status
Draft

Add session status display to System Status tab and fix stale-session detection#685
SimonHeybrock wants to merge 7 commits intomulti-sessionfrom
multi-session-status

Conversation

@SimonHeybrock
Copy link
Member

@SimonHeybrock SimonHeybrock commented Feb 2, 2026

Summary

  • Add "Dashboard Sessions" widget showing all active browser sessions with status indicators (You/Active/Stale)
  • Implement browser heartbeat detection using ReactiveHTML to reliably detect disconnected browsers
  • Show stale status for sessions without heartbeats for >15 seconds, providing visual feedback before the 60-second cleanup timeout

Example

System status tab with 3 sessions (one stale)

Key changes

New widgets:

  • HeartbeatWidget: ReactiveHTML component that sends periodic heartbeats from browser to server via bidirectional param sync
  • SessionStatusWidget: Displays list of active sessions with status badges and heartbeat times
  • SystemStatusWidget: Combines session status and backend worker status into unified System Status tab

Session tracking improvements:

  • SessionRegistry gains get_seconds_since_heartbeat() and update subscriber support
  • SessionUpdater uses HeartbeatWidget instead of fragile button-click approach for browser liveness detection
  • Polling-based refresh (every 2s) instead of background thread notifications to avoid Panel context issues

Test plan

  • Unit tests for all new widgets and registry methods (985 tests passing)
  • Manual: Open multiple browser tabs, verify all show in session list
  • Manual: Close a tab, verify it shows as "Stale" within ~15 seconds
  • Manual: Verify stale sessions are cleaned up after 60 seconds

🤖 Generated with Claude Code

SimonHeybrock and others added 5 commits February 2, 2026 10:34
Rename "Backend Status" tab to "System Status" and add a new section
showing active dashboard sessions. The current session is highlighted
with a "You" badge and sorted first.

Changes:
- Add subscriber mechanism to SessionRegistry (mirrors ServiceRegistry)
- Create SessionStatusWidget showing active sessions with heartbeat info
- Create SystemStatusWidget combining session and backend status
- Update PlotGridTabs and ReductionApp to use new combined widget

Prompt: This branch adds multi-session support (see SessionRegistry). I would
be useful if the UI had info about the active (or stale) sessions. Please
investigate how we could do this. I am thinking we could use the "Backend
Status" tab - rename it an move backend status to a section, adding a new
section with session info.

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
When a browser tab is refreshed, Panel's on_session_destroyed callback
may not fire reliably. This leaves the old session showing as "Active"
until the 60-second cleanup timeout.

Fix by:
- Adding "Stale" status (red badge) for sessions without heartbeats for
  >5 seconds, providing immediate visual feedback
- Adding periodic refresh of session status display via SessionUpdater
  to keep heartbeat times and stale indicators current
- Including stale count in the summary line

Prompt: I see a problem: This status page now indicates that when refreshing
the page it leads to sessions that are still marked as "active". Is the
browser not ending the session properly?

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
The previous approach used a Button with jscallback triggered by an HTML
script that searched for the button by text content. This was fragile:
- Panel 1.x Shadow DOM makes document.querySelectorAll unreliable
- Hidden buttons (visible=False) may not render properly
- Finding buttons by textContent is brittle

Replace with ReactiveHTML's _scripts['render'] pattern, which runs
JavaScript automatically when the component loads. The HeartbeatWidget
increments a counter every 5 seconds; Panel's bidirectional sync updates
the Python parameter, allowing detection of browser disconnection.

Key implementation notes from Panel issue #4925:
- Use += 1, not ++ (increment operators break param sync)
- Include 'remove' script to clearInterval and prevent memory leaks

Also adjust stale threshold from 5s to 15s to allow for network delay
(heartbeats arrive every 5s, so 15s = 3 missed heartbeats).

Prompt: Need your help finding out how to properly identify stale session
with panel. See recent commit and uncommitted changes for failed attempts.
Do some research and think. Let us not just try random things.

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
The widget was subscribing to session registry notifications via
register_update_subscriber(), but these notifications can come from
a background thread (cleanup_stale_sessions in the update loop).
Calling refresh() from a background thread causes pn.io.hold() to
not batch updates properly, leading to flicker.

The periodic refresh via SessionUpdater.register_custom_handler()
already updates the display every 500ms within the correct Panel
session context. Remove the redundant subscription and rely solely
on polling.

Prompt: The "Dashboard Sessions" widget (or the entire System Status tab?)
seem to not sync updates of individual subwidgets (like time info). Are we
missing a pn.io.hold()?

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
The widget was refreshing every 500ms (the SessionUpdater polling rate),
but the heartbeat time display only needs to update every few seconds.
Add a 2-second minimum interval between refreshes to reduce unnecessary
UI updates.

Prompt: The update every 500ms is too "busy". While we need this frequency
in other parts, here we do not want it.

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
@SimonHeybrock SimonHeybrock changed the title Add session status display to System Status tab Add session status display to System Status tab and fix stale-session detection Feb 2, 2026
SimonHeybrock and others added 2 commits February 2, 2026 12:37
The register_update_subscriber mechanism was removed from
SessionStatusWidget in favor of polling. Remove the now-unused
subscriber infrastructure from SessionRegistry:

- register_update_subscriber method
- _notify_update method
- _update_subscribers list
- Related tests

Prompt: Is register_update_subscriber in SessionRegistry unused?

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
@SimonHeybrock SimonHeybrock marked this pull request as draft February 6, 2026 07:37
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant