Skip to main content
← Back to list
01Issue
BugOpenSwamp CLIPublic
AssigneesNone

Relationships

#1899 swamp serve panics on successful OAuth device-flow completion (Deno HTTP invariant)

Opened by sntxrr · 8/28/2026

Summary

Completing an OAuth device-flow login against swamp serve reliably panics the process. The panic is a Rust-level abort inside Deno's HTTP layer, so there is no JS stack and no graceful shutdown — the whole server dies.

Reproduced 2 out of 2 attempts, minutes apart, on the same build.

Environment

  • swamp 20260828.202201.0-sha.2a5bcb89
  • swamp serve --auth-mode oauth --oauth-provider https://<INTERNAL_HOST> --dashboard --host 0.0.0.0
  • Login initiated from the --dashboard web UI (device flow), approved in the upstream IdP
  • Self-hosted authorization server (an OIDC shim in front of Authentik)
  • Running in Docker; restart: unless-stopped is what brings it back

What happens

The device flow succeeds server-side, and then the process aborts:

system │ Device grant started for provider "https://<INTERNAL_HOST>"
system │ Minted OAuth server token "oauth-<REDACTED>" for "user:<USERNAME>"
system │ Stored OAuth access token for "oauth-<REDACTED>"
system │ OAuth device flow completed for "user:<USERNAME>"

thread 'main' (1) panicked at ext/http/service.rs:794:5:
HTTP state error: Expected to be last strong reference
note: run with `RUST_BACKTRACE=1` environment variable to display a backtrace

The token is minted and stored, but the response never reaches the browser — the process is gone before it is delivered. The container's restart count incremented on both occasions.

Reproduction

  1. Run swamp serve --auth-mode oauth --oauth-provider <non-swamp-club server> --dashboard
  2. Open /dashboard and click the login button
  3. Approve the device code at the IdP
  4. Serve panics within a few seconds of approval

Impact

  • OAuth login via the dashboard cannot complete. Succeeding is what kills it, so there is no way through by retrying.
  • Because it is a process-level abort, everything else the instance owns goes with it. On this deployment that includes the scheduler, so every cron trigger is interrupted and re-registered on restart (~40 s outage per login attempt).
  • The client sees no error at all — see the companion report on the dashboard's device-poll error handling, which renders every failure as an indefinite "Waiting for you to approve...".

Notes toward a cause

Offered as observation, not diagnosis — the panic is in Deno, not swamp:

  • src/serve/device_auth_handler.ts builds an ordinary jsonResponse(200, ...) and returns it; nothing in the handler itself looks unusual.
  • packages/dashboard/src/views/Login.tsx:164 polls POST /auth/device/token on a bare setInterval with no AbortController and no in-flight guard. A poll that is still open when the next one fires — likely around the slow upstream token exchange — leaves overlapping requests on the same connection. Expected to be last strong reference is consistent with a request's HTTP state being dropped while another reference is still live.
  • Worth checking whether the CLI path (swamp auth server-login), which polls differently, is affected too. Not tested here.

Suggested mitigations

Independent of the underlying Deno issue, either of these would reduce blast radius:

  • Guard the poll client-side: skip a tick while a request is in flight, and abort the previous request before issuing a new one.
  • Catch the panic boundary so a single request cannot take down a server that may also be running scheduled workflows.
02Bog Flow
OPENTRIAGEDIN PROGRESSSHIPPED

Open

8/28/2026, 10:50:08 PM

No activity in this phase yet.

03Sludge Pulse

Sign in to post a ripple.