github/copilot-sdk · error · RuntimeError
Client is not connected. Call start() first.
Error message
Client is not connected. Call start() first.
What it means
This RuntimeError is thrown by the `rpc` property of CopilotClient when the internal `_rpc` handle has not been initialized. The client only creates `_rpc` during `start()` (or `connect()`), so accessing server-scoped RPC methods before the transport is up is an invalid state. The library throws early instead of returning None to prevent confusing downstream attribute errors.
Solutions
- Call `await client.start()` before accessing `client.rpc`.
- Check `client._state` / wrap usage in `async with CopilotClient(...) as client:` so lifecycle is managed automatically.
- If the client was stopped, create a new CopilotClient instance instead of reusing it.
- Inspect logs from the failed start() if start() was called but the state is 'error'.
Example fix
// before client = CopilotClient(...) result = await client.rpc.listModels() // after client = CopilotClient(...) await client.start() result = await client.rpc.listModels()
Defensive patterns
Strategy: try-catch
Validate before calling
if not hasattr(client, "rpc") or client._rpc is None:
await client.start() Type guard
def is_connected(client) -> bool:
return getattr(client, "_rpc", None) is not None Try / catch
try:
rpc = client.rpc
except RuntimeError as e:
if "not connected" in str(e):
await client.start()
rpc = client.rpc
else:
raise Prevention
- Always manage the client with `async with CopilotClient(...) as client:`
- Call start() immediately after construction and before any RPC access
- Never reuse a client after stop()/context exit — create a new one
- Check connection state before RPC calls in long-lived services
When it happens
Trigger: Accessing `client.rpc` (or any property built on it) before calling `await client.start()`, after `stop()`/`force_stop()` has torn the connection down, or after a failed `start()` left the client in the 'error' state.
Common situations: Forgetting to await start() in async code; calling RPC methods in a script that stopped the client earlier; reusing a client object after context-manager exit (`async with` block ended); a start() failure caught and ignored, then RPC attempted anyway.
Understand the failure class
Background: "Invalid state transition" errors: "status must be X, actually Y", "already rejected/charging/uninstalled", "cannot ... while running" — what they mean when a library rejects your call — this error's family across 31 libraries.
Related errors
- Client not connected; call start() first
- Client not connected. Call start() first.
- Session is not connected — RPC client is unavailable
- LLM inference response used after RPC connection closed
- Unknown session
AI-assisted analysis of github/copilot-sdk@cd8cf15dc3 (2026-09-09).
Data as JSON: /api/errors/e72ab8a185c8fe18.
Report an issue: GitHub.
Appendix: source
Thrown at python/copilot/client.py:1826
if runtime_path is None:
raise RuntimeError(
f"In-process runtime library not found next to '{explicit_cli}'."
)
self._cli_path_source = "environment"
self._inprocess_cli_entrypoint = explicit_cli
return runtime_path
from ._cli_download import ensure_runtime_wrapper
wrapper_path = Path(ensure_runtime_wrapper())
self._cli_path_source = "downloaded"
return str(wrapper_path.with_name("runtime.node"))
@property
def rpc(self) -> ServerRpc:
"""Typed server-scoped RPC methods."""
if self._rpc is None:
raise RuntimeError("Client is not connected. Call start() first.")
return self._rpc
@property
def runtime_port(self) -> int | None:
"""TCP port the runtime is listening on, when using TCP transport.
Useful for multi-client scenarios where a second client needs to connect
to the same runtime. Only available after :meth:`start` completes and
only when not using stdio transport.
"""
return self._runtime_port
def _parse_cli_url(self, url: str) -> tuple[str, int]:
"""
Parse CLI URL into host and port.
Supports formats: "host:port", "[ipv6]:port", "http://host:port",
"https://host:port", or just "port".View on GitHub (pinned to cd8cf15dc3)