coleam00/Archon · info · DeviceFlowError
aborted
aborted
Error message
Device flow polling was aborted
What it means
pollDeviceFlow loops until the user authorizes the device. Before each sleep it checks opts.signal; if the caller aborted the poll, it throws DeviceFlowError with code 'aborted' so callers can distinguish intentional cancellation from auth failure.
Source
Thrown at packages/core/src/github-auth/device-flow.ts:117
const defaultSleep = (ms: number): Promise<void> => new Promise(resolve => setTimeout(resolve, ms));
/**
* Step 2: poll until the user authorizes. Handles `authorization_pending`
* (keep waiting) and `slow_down` (back off using the server-supplied interval).
* Any other `error` is terminal and thrown as a DeviceFlowError.
*/
export async function pollDeviceFlow(
clientId: string,
deviceCode: string,
intervalSeconds: number,
opts: PollOptions = {}
): Promise<DeviceAccessToken> {
const sleep = opts.sleep ?? defaultSleep;
let interval = Math.max(1, intervalSeconds);
for (;;) {
if (opts.signal?.aborted) {
throw new DeviceFlowError('aborted', 'Device flow polling was aborted');
}
await sleep(interval * 1000);
const result = await pollDeviceFlowOnce(clientId, deviceCode);
if (result.status === 'authorized') return result.token;
if (result.status === 'pending') continue;
if (result.status === 'slow_down') {
// Honor the server's new interval, else keep the current. Floor at 1s so a
// malformed `interval: 0` can't turn this into a busy loop.
interval = Math.max(1, result.interval);
continue;
}
throw new DeviceFlowError(result.code);
}
}
/** Result of a single (non-blocking) device-flow poll. */
export type PollOnceResult =
| { status: 'pending' }View on GitHub (pinned to 0773b97458)
Solutions
- Treat code 'aborted' as an expected cancellation, not an auth failure — return to the login prompt
- Only abort when you actually intend to cancel; pass signal: undefined otherwise
- Wrap the poll in try/catch that special-cases aborted and restarts the device flow on demand
Example fix
// before
const token = await pollDeviceFlow(clientId, data, 5, { signal });
// after
try {
const token = await pollDeviceFlow(clientId, data, 5, { signal });
} catch (e) {
if (e instanceof DeviceFlowError && e.code === 'aborted') return null;
throw e;
} Defensive patterns
Strategy: try-catch
Try / catch
try { return await pollDeviceFlow(clientId, deviceCode, interval, { signal }); } catch (e) { if (e instanceof DeviceFlowError && e.code === 'aborted') return null; throw e; } Prevention
- Always special-case the 'aborted' code as normal control flow
- Wire user-cancel and shutdown signals into the AbortController you pass, so abort is intentional
When it happens
Trigger: Calling pollDeviceFlow with an AbortSignal and aborting it (e.g. user cancels login, UI timeout, shutdown) while polling is still pending.
Common situations: User closes the browser before entering the code; CLI cancelled with Ctrl-C mapped to an AbortController; server shutting down mid-login; application-level login timeout.
Related errors
- Login cancelled
- ${data.error}
- ${result.code}
- Provider '${provider}' does not support subscription login.
- Vendor '${vendor}' (Pi backend) has no env-based OAuth deliv
AI-assisted analysis of coleam00/Archon@0773b97458 (2026-09-01).
Data as JSON: /api/errors/68fe915029d63735.
Report an issue: GitHub.