Hmbown/CodeWhale · warning
MCP configuration changed; reload it before retrying this…
Error message
MCP configuration changed; reload it before retrying this server
What it means
The retry endpoint checks pool.config_matches(&config) after the enabled check. If the fresh config differs from the pool's snapshot, retry is refused and this error is recorded as the outcome, mirroring the connect endpoint's stale-pool guard but phrased for retries.
Solutions
- Reload the MCP configuration via the Runtime API reload endpoint (or restart the Runtime API), then retry the server.
- Diff the on-disk MCP config against the pool's snapshot to identify what changed unintentionally.
- Sequence automation: config edit -> reload -> retry, never config edit -> retry.
Example fix
// before
POST /mcp/retry {"server": "github"} // -> stale config error
// after
POST /mcp/reload
POST /mcp/retry {"server": "github"} Defensive patterns
Strategy: retry
Validate before calling
let pool_hash = fetch_pool_config_hash().await?;
if pool_hash != hash_of(&fetch_mcp_config().await?) {
call_mcp_reload().await?;
} Try / catch
match outcome.error {
Some(e) if e.contains("configuration changed") => {
client.reload_mcp_config().await?;
client.mcp_retry(name).await?;
}
other => handle(other),
} Prevention
- Reload MCP config immediately after edits, before any retry
- Serialize config edits through a single automation step that reloads
- Verify server state via the listing endpoint before retry loops
When it happens
Trigger: Calling the MCP retry endpoint while the MCP configuration has been edited since the pool was loaded, so config_matches returns false; the per-server name in the request is enabled but the pool is stale.
Common situations: Adding a new server or changing env/args in the MCP config and immediately hitting retry without reload; CI or automation rewriting mcp config between calls.
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
- MCP configuration changed; reload it before connecting this…
- computer_observation_required
- MCP configuration changed while connecting
- MCP server ' ' is disabled
- Reviewed source is unavailable; refresh the import preview
AI-assisted analysis of Hmbown/CodeWhale@73e0f67d83 (2026-09-22).
Data as JSON: /api/errors/143da2c3c7f3c6da.
Report an issue: GitHub.
Appendix: source
Thrown at crates/tui/src/runtime_api.rs:4683
/// return the actual result without replacing healthy sibling connections.
async fn reconnect_mcp_server(
State(state): State<RuntimeApiState>,
Path(name): Path<String>,
) -> Result<Json<McpServerActionReceipt>, ApiError> {
let (config, _) = mcp_management_config(&state)?;
if !config.servers.contains_key(&name) {
return Err(ApiError::not_found(format!(
"MCP server '{name}' not found"
)));
}
let handle = mcp_pool_handle(&state, true)
.await?
.ok_or_else(|| ApiError::internal("MCP pool unavailable"))?;
let mut pool = handle.lock().await;
let error = if !config.servers[&name].is_enabled() {
Some(anyhow::anyhow!("MCP server '{name}' is disabled"))
} else if !pool.config_matches(&config) {
Some(anyhow::anyhow!(
"MCP configuration changed; reload it before retrying this server"
))
} else {
pool.retry_connection(&name).await.err()
};
let connection = mcp_connection_outcome(&pool, &name, error.as_ref());
Ok(Json(McpServerActionReceipt {
revision: None,
name,
action: if error.is_none() {
"reconnected"
} else {
"reconnect_failed"
},
ok: error.is_none() && connection.connected,
connection: Some(connection),
}))
}View on GitHub (pinned to 73e0f67d83)