github/copilot-sdk · error · RuntimeError
Timeout waiting for CLI server to start
Error message
Timeout waiting for CLI server to start
What it means
RuntimeError raised when the TCP port-wait step times out: the CLI process is alive but never printed a 'listening on port N' announcement within the allowed window. The library converts the TimeoutError into this message.
Solutions
- Increase the CLI startup timeout in the client configuration if available
- Confirm the CLI version prints 'listening on port <n>' (upgrade/downgrade to a compatible version)
- Check system resources (CPU, disk, antivirus) that may delay process startup
- Enable debug logging to see the lines the CLI actually emits while waiting
Example fix
// before client = CopilotClient() # default timeout too short on slow CI // after client = CopilotClient(cli_start_timeout=120) # allow more startup time
Defensive patterns
Strategy: try-catch
Try / catch
try:
await client.start()
except RuntimeError as e:
if "Timeout waiting for CLI server to start" in str(e):
raise StartupTimeout("CLI did not announce a port in time") from e Prevention
- Configure a generous startup timeout on slow machines/CI
- Keep antivirus from scanning the CLI binary on every launch
- Pin compatible CLI versions (log-line format drift causes hangs)
- Enable SDK debug logging during onboarding to observe startup lines
When it happens
Trigger: CLI is slow to start (cold start, slow disk/AV scan), prints the announcement in an unexpected format, or hangs at startup so read_port() never matches the port regex before the deadline.
Common situations: Slow machines or containers with heavy startup latency; antivirus delaying binary launch; CLI versions whose log line format changed; resource-starved CI runners.
Understand the failure class
Background: Request timed out: what client-side request timeouts mean across libraries (Request timed out, TIMED_OUT, APITimeoutError) — this error's family across 39 libraries.
- Timeouts: ETIMEDOUT, deadlines, and hung requests — what actually expires when a request times out.
Related errors
- Process not started or stdout not available
- CLI process exited before announcing port
- Timeout waiting for CLI to announce port
- str(e)
- {process exit error from _get_process_exit_error()}
AI-assisted analysis of github/copilot-sdk@cd8cf15dc3 (2026-09-09).
Data as JSON: /api/errors/724ed1960484aa4c.
Report an issue: GitHub.
Appendix: source
Thrown at python/copilot/client.py:4496
line_str = line.decode() if isinstance(line, bytes) else line
logger.debug("[CLI] %s", line_str.rstrip())
match = re.search(r"listening on port (\d+)", line_str, re.IGNORECASE)
if match:
self._runtime_port = int(match.group(1))
return
try:
port_wait_start = time.perf_counter()
await asyncio.wait_for(read_port(), timeout=10.0)
log_timing(
logger,
logging.DEBUG,
"CopilotClient._start_cli_server TCP port wait complete",
port_wait_start,
port=self._runtime_port,
)
except TimeoutError:
raise RuntimeError("Timeout waiting for CLI server to start")
async def _start_inprocess_ffi(self) -> None:
"""Host the runtime in-process via the native FFI library.
Loads the native runtime library and opens the FFI JSON-RPC connection.
Raises:
RuntimeError: If the native library is missing or startup fails.
"""
assert isinstance(self._connection, InProcessRuntimeConnection)
runtime_path = self._inprocess_runtime_path
assert runtime_path is not None # resolved in __init__
logger.info(
"CopilotClient._start_inprocess_ffi hosting Copilot runtime in-process",
extra={"runtime_path": runtime_path, "runtime_path_source": self._cli_path_source},
)
View on GitHub (pinned to cd8cf15dc3)