nexu-io/open-design · error
vela login exited before authentication completed (code ${re
Error message
vela login exited before authentication completed (code ${result.code ?? 'null'}, signal ${result.signal ?? 'null'}) What it means
Raised by waitForImmediateLoginFailure() when the direct vela login child exited within the grace window (no 'error' event) but never printed an activation URL. The message prefers captured stderr/stdout detail; the generic form embeds exit code and signal so the operator can tell a clean exit (code 0) from a signal kill.
Source
Thrown at apps/daemon/src/integrations/vela.ts:1087
VelaLoginChildTerminal | { kind: 'running' }
>([
terminal,
new Promise<{ kind: 'running' }>((resolve) => {
const timer = setTimeout(
() => resolve({ kind: 'running' }),
LOGIN_STARTUP_GRACE_MS,
);
timer.unref?.();
}),
]);
if (result.kind === 'running') return;
if (result.kind === 'error') {
throw new Error(`vela login failed to start: ${result.error.message}`);
}
if (capture.activation.activationUrl) return;
const detail = (capture.stderr || capture.stdout).trim();
throw new Error(
detail ||
`vela login exited before authentication completed (code ${result.code ?? 'null'}, signal ${result.signal ?? 'null'})`,
);
}
// Wait for the direct `vela login` attempt to either print its device-auth
// activation URL (healthy — the direct path works even on the transparent-proxy
// networks this fix targets, just possibly slowly) or exit/error BEFORE printing
// it (a real failure the caller can retry through the IPv4 proxy). Crucially, a
// merely slow-but-still-running direct login is NOT killed: once the grace
// elapses we simply stop blocking the request and let it keep running (the UI
// polls /status). Killing a slow-healthy direct login and re-routing it through
// the proxy is exactly the regression this avoids — on a corporate transparent
// proxy the proxy hop loses the client IP and the upstream 502s. Only an
// explicit pre-activation exit/error triggers the proxy fallback.
async function waitForLoginActivationSteadyState(
capture: VelaLoginActivationCapture,
graceMs: number,View on GitHub (pinned to 5be4028344)
Solutions
- Read the captured stderr/stdout first — when present it identifies the real cause (unknown flag, expired session, etc.).
- Re-run with a vela binary version matching the daemon's expected flags; or route through the IPv4 proxy fallback.
- If signal is SIGKILL, investigate OOM / sandbox policy; if exit code is 2/64, check flag compatibility.
Example fix
// before
throw new Error(`vela login exited before authentication completed (code ${result.code ?? 'null'}, signal ${result.signal ?? 'null'})`);
// after (always surface captured detail for the operator)
const detail = (capture.stderr || capture.stdout).trim();
throw new Error(
detail || `vela login exited before authentication completed (code ${result.code ?? 'null'}, signal ${result.signal ?? 'null'})`,
); Defensive patterns
Strategy: try-catch
Type guard
function isLoginExitedBeforeAuth(err: unknown): boolean {
return err instanceof Error
&& /vela login exited before authentication completed/.test(err.message);
}
function extractExitCodeSignal(err: unknown): { code: string | null; signal: string | null } | null {
const m = err instanceof Error
? err.message.match(/code (\S+), signal (\S+)\)\s*$/)
: null;
return m ? { code: m[1], signal: m[2] } : null;
} Try / catch
try {
await waitForImmediateLoginFailure(capture, terminal);
} catch (err) {
const info = extractExitCodeSignal(err);
if (info && info.signal !== 'null') {
// external kill — do not auto-retry; investigate sandbox/OOM
}
throw err;
} Prevention
- Always read capture.stderr/stdout first — the generic message only fires when they are empty.
- Match the vela binary version to the flags the daemon expects.
- Use the IPv4 proxy fallback when the direct path keeps exiting early.
When it happens
Trigger: vela login runs, fails fast, and exits with a non-zero code (or is killed by a signal) before printing the device-auth URL. Capture has no activationUrl, so the generic message fires when stderr/stdout are empty.
Common situations: vela login prints help and exits because of an unknown flag in this binary version; vela self-updates and exits; sandbox/network policy kills the child (SIGTERM/SIGKILL); vela exits 0 but stdout buffering hid the URL.
Understand the failure class
- Authentication and authorization failures — expired tokens, bad credentials, and missing scopes.
Related errors
- vela login failed to start: ${result.error.message}
- vela login exited before device authorization started (code
- failed to spawn vela login
- vela login already running
- vela login attempt is no longer active
AI-assisted analysis of nexu-io/open-design@5be4028344 (2026-08-12).
Data as JSON: /api/errors/a0a5cd8ee058c91b.
Report an issue: GitHub.