nexu-io/open-design · error
vela login failed to start: ${result.error.message}
Error message
vela login failed to start: ${result.error.message} What it means
Raised by waitForImmediateLoginFailure() when the vela login child emitted an 'error' event within the LOGIN_STARTUP_GRACE_MS window — i.e. the process failed to spawn or failed very early. result.error.message carries the underlying spawn error (ENOENT, EACCES, EAGAIN).
Source
Thrown at apps/daemon/src/integrations/vela.ts:1083
capture: VelaLoginActivationCapture,
terminal: Promise<VelaLoginChildTerminal>,
): Promise<void> {
const result = await Promise.race<
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 anView on GitHub (pinned to 5be4028344)
Solutions
- Inspect result.error.message: ENOENT → install vela or set VELA_BIN; EACCES → chmod +x the binary; EAGAIN → lower fd/memory pressure.
- Ensure the amr agent def resolves a real selectedPath via resolveAgentLaunch.
- If using the IPv4 proxy fallback path, the caller may still retry through it — make sure the fallback is enabled.
Example fix
// before
await waitForImmediateLoginFailure(capture, terminal);
// after
try {
await waitForImmediateLoginFailure(capture, terminal);
} catch (err) {
if (/ENOENT|EACCES/.test(String(err))) {
// surface 'install vela or configure VELA_BIN' to the user, no retry
}
throw err;
} Defensive patterns
Strategy: try-catch
Validate before calling
function isVelaBinPresent(bin = process.env.VELA_BIN): boolean {
if (!bin) return false;
try {
// cheap existence check; real exec check happens at spawn
return fs.statSync(bin).isFile();
} catch {
return false;
}
} Type guard
function isSpawnFailureMessage(err: unknown): boolean {
return err instanceof Error && err.message.startsWith('vela login failed to start:');
}
function underlyingErrno(err: unknown): string | null {
const m = err instanceof Error ? err.message.match(/\b(ENOENT|EACCES|EAGAIN)\b/) : null;
return m ? m[1] : null;
} Try / catch
try {
await waitForImmediateLoginFailure(capture, terminal);
} catch (err) {
const errno = underlyingErrno(err);
if (errno === 'ENOENT' || errno === 'EACCES') {
// permanent — surface 'install vela or configure VELA_BIN', do not retry
}
throw err;
} Prevention
- Ensure VELA_BIN resolves to an existing, executable binary before starting login.
- Keep the amr agent runtime resolver able to find vela on PATH.
- Distinguish permanent spawn errors (ENOENT/EACCES) from retriable ones.
When it happens
Trigger: Spawn errors before the grace timer elapses: binary missing (ENOENT), not executable (EACCES), or OS resource limits (EAGAIN). The direct login attempt fails before it can print a device-auth activation URL.
Common situations: VELA_BIN points at a non-existent path; vela not on PATH; binary exists but lacks execute permission; /tmp or process env in a broken state; packaged daemon lost access to the bundled binary.
Related errors
- vela login exited before authentication completed (code ${re
- 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/788588785e041476.
Report an issue: GitHub.