ACP: session/new blocks for 192s on a single unresponsive MCP server (no bounded MCP startup budget)
Nessuno ha ancora preso questa issue.
- Lingua principale
- Shell
- Stelle
- 11.2k
- Fork
- 1.9k
- Merge medio
- 14h 16m
- PR unite (30g)
- 6
Descrizione
Describe the bug
In ACP mode (--acp), the session/new response is blocked until every
configured MCP server has finished connecting. A single unresponsive HTTP MCP
server therefore delays session creation by 192 seconds — three connection
attempts at roughly 59 s each — instead of failing fast and starting the session
without that server.
There is no bounded budget on this. An ACP client cannot distinguish "still
starting" from "wedged", so it either waits minutes or times out and kills a
process that was going to succeed.
Affected version
GitHub Copilot CLI 1.0.82-1
Windows 10/11 x64, WinGet install.
Steps to reproduce
Fully deterministic. Reproduces every time.
- Create an MCP endpoint that accepts the connection and never replies —
this stands in for any MCP server that is wedged or slow to start:
// stall-server.js
const http = require('http')
http.createServer((req) => {
console.log(`received ${req.method} ${req.url} -- deliberately not responding`)
}).listen(39217, '127.0.0.1', () => console.log('listening on 127.0.0.1:39217'))
node stall-server.js
- Point an MCP config at it:
{
"mcpServers": {
"stalled": { "type": "http", "url": "http://127.0.0.1:39217/mcp", "tools": ["*"] }
}
}
- Start Copilot in ACP mode with that config:
copilot --no-auto-update --log-dir ./logs --acp --additional-mcp-config @mcp.json
- Over stdio, send
initialize, thensession/new, and time the response:
{"jsonrpc":"2.0","id":1,"method":"initialize","params":{"protocolVersion":1,"clientCapabilities":{"fs":{"readTextFile":false,"writeTextFile":false}}}}
{"jsonrpc":"2.0","id":2,"method":"session/new","params":{"cwd":"<abs path>","mcpServers":[]}}
Actual behavior
initialize returns in ~1 s. session/new takes 192 s:
RUN stall2: OK initialize 1078ms session/new 192355ms sid=3a0719b1-...
The log shows the retry ladder — three attempts, each burning a ~59 s
connection timeout, each followed by a server/discover timeout and a legacy
initialize retry:
23:10:14.946 Workspace initialized: 3a0719b1-... (checkpoints: 0)
23:10:15.224 mcp discover_and_start_root: full replace_host path
23:10:15.752 mcp graph load: reload_with_config {"force":false}
23:10:18.747 mcp discover_and_start_root: incremental reconcile path
23:10:19.874 [WARNING] server/discover timed out; retrying with legacy initialize
23:11:18.876 Transient MCP connection failure {"server_name":"stalled",...}
23:11:18.876 Retrying connection to HTTP server stalled (attempt 2/3) after 500ms
23:11:20.392 [WARNING] server/discover timed out; retrying with legacy initialize
23:12:19.386 Transient MCP connection failure {"server_name":"stalled",...}
23:12:19.386 Retrying connection to HTTP server stalled (attempt 3/3) after 1000ms
23:12:21.395 [WARNING] server/discover timed out; retrying with legacy initialize
Two details that make this hard to diagnose from the client side:
- The wait is silent. Between
connected to 127.0.0.1:39217and the
Transient MCP connection failure59 s later, nothing is logged at all. The
log simply appears to stop, which reads like a freeze rather than a retry. session/newhas already succeeded internally.Workspace initialized
is logged 3 minutes before the client gets its reply, so the session exists
the whole time the client is blocked waiting for it.
Expected behavior
One of:
- A bounded overall budget for MCP startup during
session/new, after which
the session is returned and unreachable servers are reported as degraded; or - MCP connection established asynchronously, so
session/newreturns promptly
and servers become available as they connect.
Either way, an unreachable MCP server should degrade tool availability, not
delay session creation by minutes.
Baseline for comparison
Same client, same workspace, same machine:
| MCP configuration | session/new |
|---|---|
| none | 5.6 s |
| 2 reachable public HTTP servers | ~5 s (10/10 runs) |
| 1 unresponsive HTTP server | 192.4 s |
Impact
Any ACP client with a startup timeout under ~3 minutes will kill a Copilot
process that was going to succeed. Because the connection wait is silent, the
resulting logs make it look like Copilot froze during MCP graph initialization,
which sends people looking in the wrong place. It also means one flaky or
slow-starting MCP server degrades session startup for the whole session, rather
than just its own tools.
Related observation (may be a separate issue)
Separately, and not reproduced deterministically, I have twice seen ACP
startup stop at mcp graph load: reload_with_config with no subsequent
connection attempt logged at all, on a workspace using locally-hosted MCP
servers. Unlike the case above, no connecting to line ever follows. Retrying
the same request minutes later succeeded, so it appears to be a race rather than
a configuration problem. I am mentioning it only as possible context — I cannot
currently reproduce it on demand and it may well be unrelated to the timeout
issue reported here.
Additional context
Possibly related, in the same startup-reconciliation area:
- #4636 — MCP servers from
--additional-mcp-configremoved during startup reconciliation - #4392 — Post-authentication MCP client rebuild leaves orphaned stdio MCP server processes
Full logs for the reproduction available on request.
Guida per i contributori
Apri la guida per i contributori
Come iniziare
- Leggi tutta la issue e poi la guida ai contributi del progetto.
- Commenta sulla issue per dire che te ne occupi tu — evita che due persone facciano lo stesso lavoro.
- Fai un fork del repository e lavora su un branch.
- Apri una pull request che faccia riferimento al numero della issue.
Direzione di ricerca
Inizia eseguendo la riproduzione fornita stall-server.js con copilot --acp e cronometra initialize rispetto a session/new; usa la sequenza dei log di timeout e retry di MCP come riferimento. Traccia il punto di ingresso ACP di session/new e il percorso di avvio/riconciliazione di MCP, quindi verifica che un server che non risponde non blocchi più la creazione della sessione oltre un budget limitato e che il server degradato venga segnalato.
Scritto dal modello di indicizzazione a partire dal testo della issue.
Valutazione
- Stack tecnologico
- nodejs
- Ambito
- api, cli
- Tipo di issue
- Bug
- Difficoltà
- 4/5
- Tempo stimato
- 3-5 giorni
- Stato di attività
- Attiva
- Chiarezza
- Abbastanza chiara
- Idoneità per principianti
- 48/100