Skip to content

Add /idle endpoint for hosting platform idle tracking#13169

Open
isabelizimm wants to merge 2 commits intomainfrom
feature/idle-tracking-endpoint
Open

Add /idle endpoint for hosting platform idle tracking#13169
isabelizimm wants to merge 2 commits intomainfrom
feature/idle-tracking-endpoint

Conversation

@isabelizimm
Copy link
Copy Markdown
Contributor

Opening duplicate PR based off these instructions

BELOW COPIED FROM #13146


Summary

Adds a /idle HTTP endpoint on the Positron server/REH build that Posit Cloud can query to determine how long the user has been idle.

Architecture

The existing IUserActivityService keeps track of DOM events (e.g. keydown, mousedown, touchstart. A new browser-side workbench contribution, PositronIdleReporterContribution, registers a callback to watch activity changes, upon which it forwards timestamps to a new IPC channel every 30s. A new service, PositronIdleTrackingService, keeps the most recent timestamp monotonically and exposes the result via the HTTP endpoint.

Response format

GET /idle?tkn=<connection-token>

{
  "seconds_idle": 142,
  "last_activity_epoch_ms": 1718900000000
}

Behavior notes

Since timestamps are sent every 30 seconds, the idle time may be reported up to 30s even while Positron is in use.

Opening a tab counts as activity for ~60-70s. IUserActivityService initializes isActive = true on construction, treating the act of opening the window as an implicit activity signal (see the service's own comment). The bundled DomActivityTracker then verifies continued activity via DOM events: after 2 poll intervals (~60s) with no keydown/mousedown/touchstart, plus a 10s debounce, it flips to isActive = false.

In practice: if a user opens a tab and walks away without interacting, seconds_idle will report 0 for approximately 60-70 seconds before it begins to climb. This is expected and acceptable for session-management use cases where idle timeouts are on the order of minutes or hours, but it's worth noting for any consumer that expects sub-minute precision.

Release Notes

New Features

  • N/A (internal server/REH feature; no user-visible change)

Bug Fixes

  • N/A

QA Notes

@:sessions

This feature only activates in the server/REH build and requires Linux (license manager is Linux-only).

Automated tests

```bash
./scripts/test.sh --run src/vs/platform/positronIdleTracking/test/node/positronIdleTrackingService.test.ts
./scripts/test.sh --run src/vs/platform/positronIdleTracking/test/common/positronIdleTrackingIpc.test.ts
```

Manual verification (Linux only)

  1. Build and start the server:
    ```bash
    npm run build-start && npm run build-check
    ./scripts/code-server.sh --connection-token test-token --license-key-file /path/to/license.lic
    ```
  2. Open the URL printed by the server in a browser.
  3. Wait ~10s, then query `/idle`:
    ```bash
    curl -s "http://localhost:/idle?tkn=test-token" | jq .
    ```
  4. Verify:
    • `seconds_idle` near 0 when interacting
    • `seconds_idle` oscillates between 0 and ~30s when actively interacting (heartbeat interval)
    • `seconds_idle` grows unboundedly when the user stops interacting (after the ~60-70s grace period described above)
    • HTTP 403 when `?tkn=` is missing or wrong

🤖 Generated with Claude Code

mslynch and others added 2 commits April 22, 2026 10:36
Adds a /idle HTTP endpoint on the Positron server/REH build that hosting
platforms (e.g. Posit Cloud) can query to determine how long the user has
been idle. The response includes seconds_idle, last_activity_epoch_ms,
and connected_clients.

Activity signals originate from the existing IUserActivityService in the
browser (DOM events: keydown, mousedown, touchstart). A new browser-side
workbench contribution forwards activity timestamps to the server via a
dedicated IPC channel. A new node-side service aggregates timestamps
across connected clients (taking the most recent) and exposes the
resulting idle info via the HTTP endpoint.

Includes unit tests for the service and IPC channel pair.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Replace the per-client Map<string, number> with a single monotonic
lastActivityEpochMs. Drop the connectedClients field from the response,
the clientId parameter from reportActivity, and the removeClient method.

Rationale: the core signal (max activity timestamp across all clients)
is naturally preserved by monotonic updates. Per-client tracking added
complexity without meaningful benefit for Posit Cloud's use case.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
@github-actions
Copy link
Copy Markdown

E2E Tests 🚀
This PR will run tests tagged with: @:critical @:sessions

readme  valid tags

@isabelizimm
Copy link
Copy Markdown
Contributor Author

isabelizimm commented Apr 23, 2026

Copying comments from other PR:

@jmcphers : This checks user activity but not kernel activity; i.e. if you start a long-running computation and close the browser tab, your session will quickly begin reporting as idle even though Python or R are still doing work. Is that intended behavior for this endpoint?

@mslynch : Yes - we're planning on calling the Kallichore API as well for that.

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.

2 participants