stablyai/orca · error

SSH connection is not available. Please reconnect and try ag

Error message

SSH connection is not available. Please reconnect and try again.

What it means

Thrown by registerRequiredSshWorktreeCreateRoots when getActiveMultiplexer(connectionId) returns a falsy value, meaning there is no live SSH mux (the multiplexed control connection) for the given connectionId. The 'required' variant exists because registering worktree-create roots on the remote host is mandatory for that flow to function, unlike the softer best-effort registration that just returns early. The error surfaces that the SSH session the caller believes is live has actually gone away.

Source

Thrown at src/main/ipc/ssh-worktree-create-root-registration.ts:47

export async function registerOptionalSshWorktreeCreateRoots(
  connectionId: string,
  rootPaths: string[]
): Promise<void> {
  const mux = getActiveMultiplexer(connectionId)
  if (!mux) {
    return
  }
  await registerSshWorktreeCreateRoots(mux, rootPaths)
}

export async function registerRequiredSshWorktreeCreateRoots(
  connectionId: string,
  rootPaths: string[]
): Promise<void> {
  const mux = getActiveMultiplexer(connectionId)
  if (!mux) {
    throw new Error(SSH_CONNECTION_UNAVAILABLE_MESSAGE)
  }
  await registerSshWorktreeCreateRoots(mux, rootPaths)
}

View on GitHub (pinned to 1136503c6a)

Solutions

  1. Reconnect the SSH target, then retry the worktree-create-root registration so a fresh mux is available.
  2. Guard the caller: check getActiveMultiplexer(connectionId) returns truthy before invoking the required variant, and skip or queue if not.
  3. Ensure this call is sequenced after a successful connect completes (await the connect promise) rather than fired speculatively.

Example fix

// before
await registerRequiredSshWorktreeCreateRoots(connectionId, rootPaths)
// after
if (getActiveMultiplexer(connectionId)) {
  await registerRequiredSshWorktreeCreateRoots(connectionId, rootPaths)
} else {
  await reconnectTarget(connectionId)
  await registerRequiredSshWorktreeCreateRoots(connectionId, rootPaths)
}
Defensive patterns

Strategy: validation

Validate before calling

if (!getActiveMultiplexer(connectionId)) {
  await reconnectTarget(connectionId)
}
await registerRequiredSshWorktreeCreateRoots(connectionId, rootPaths)

Type guard

function hasActiveMux(connectionId: string): boolean {
  return getActiveMultiplexer(connectionId) !== undefined && !getActiveMultiplexer(connectionId)?.isDisposed()
}

Try / catch

try {
  await registerRequiredSshWorktreeCreateRoots(connectionId, rootPaths)
} catch (e) {
  if (/SSH connection is not available/.test((e as Error).message)) {
    await reconnectTarget(connectionId)
    await registerRequiredSshWorktreeCreateRoots(connectionId, rootPaths)
  } else throw e
}

Prevention

When it happens

Trigger: registerRequiredSshWorktreeCreateRoots(connectionId, rootPaths) is called for a connectionId whose mux was disposed, never connected, or torn down after a relay disconnect/reconnect cycle. Typical during automated flows (post-connect setup) that race with a concurrent disconnect.

Common situations: A reconnect finished (mux replaced/disposed) while a deferred setup task still holds the old connectionId. The user disconnected an SSH target mid-operation. A stale connectionId was persisted and replayed on startup before the session re-established.

Related errors


AI-assisted analysis of stablyai/orca@1136503c6a (2026-08-12). Data as JSON: /api/errors/f643481379db45d4. Report an issue: GitHub.