ChatGPTNextWeb/NextChat · warning · Error

Server ${clientId} not found

Error message

Server ${clientId} not found

What it means

Thrown at app/mcp/actions.ts:201 inside pauseMcpServer when currentConfig.mcpServers[clientId] is undefined — i.e. the clientId passed in does not exist in the persisted MCP config file. The function reads the config from disk (getMcpConfigFromFile), looks up the server entry, and refuses to pause a server it cannot find.

Source

Thrown at app/mcp/actions.ts:201

    // 只有新服务器或状态为 active 的服务器才初始化
    if (isNewServer || config.status === "active") {
      await initializeSingleClient(clientId, config);
    }

    return newConfig;
  } catch (error) {
    logger.error(`Failed to add server [${clientId}]: ${error}`);
    throw error;
  }
}

// 暂停服务器
export async function pauseMcpServer(clientId: string) {
  try {
    const currentConfig = await getMcpConfigFromFile();
    const serverConfig = currentConfig.mcpServers[clientId];
    if (!serverConfig) {
      throw new Error(`Server ${clientId} not found`);
    }

    // 先更新配置
    const newConfig: McpConfigData = {
      ...currentConfig,
      mcpServers: {
        ...currentConfig.mcpServers,
        [clientId]: {
          ...serverConfig,
          status: "paused",
        },
      },
    };
    await updateMcpConfig(newConfig);

    // 然后关闭客户端
    const client = clientsMap.get(clientId);
    if (client?.client) {

View on GitHub (pinned to defdcdb55d)

Solutions

  1. Refresh the server list from getMcpConfigFromFile() before invoking pause and drop the call if the id is gone.
  2. Verify the clientId exists in config.mcpServers before calling pauseMcpServer.
  3. If the config file was lost, re-add the server via addMcpServer before pausing.
  4. Treat 'not found' as a non-fatal no-op in the caller rather than an uncaught throw.

Example fix

// before
pauseMcpServer(staleId).catch(console.error);

// after
const config = await getMcpConfigFromFile();
if (config.mcpServers[staleId]) {
  await pauseMcpServer(staleId);
} else {
  showToast(`Server ${staleId} no longer exists`);
}
Defensive patterns

Strategy: validation

Validate before calling

import { getMcpConfigFromFile } from "@/app/mcp/actions";

async function serverExists(clientId: string): Promise<boolean> {
  const config = await getMcpConfigFromFile();
  return Boolean(config.mcpServers[clientId]);
}

if (await serverExists(id)) {
  await pauseMcpServer(id);
}

Type guard

function isServerInConfig(
  config: McpConfigData,
  clientId: string,
): config is McpConfigData & { mcpServers: Record<string, ServerConfig> } {
  return Boolean(config.mcpServers[clientId]);
}

Try / catch

try {
  await pauseMcpServer(id);
} catch (e) {
  if (e instanceof Error && /not found/.test(e.message)) {
    showToast(`Server ${id} no longer exists`);
  } else {
    throw e;
  }
}

Prevention

When it happens

Trigger: Calling pauseMcpServer(clientId) where clientId was never added, was already removed (removeMcpServer deleted the key), or where the config file on disk was hand-edited and the entry deleted between the UI listing and the pause click.

Common situations: Stale UI state: the server list was rendered, then the config changed (removed by another tab, external edit, or a restart that reset to defaults) before the user clicked pause; a typo or programmatic caller passing a wrong id; the config file does not exist and getMcpConfigFromFile fell back to DEFAULT_MCP_CONFIG which has no servers.

Related errors


AI-assisted analysis of ChatGPTNextWeb/NextChat@defdcdb55d (2026-08-12). Data as JSON: /api/errors/0073746601da0b88. Report an issue: GitHub.