Read a `mcpServers` block, skipping any entry that fails to normalize.
(filePath: string)
| 182 | |
| 183 | /** Read a `mcpServers` block, skipping any entry that fails to normalize. */ |
| 184 | function readMcpServers(filePath: string): Record<string, McpServerConfig> { |
| 185 | const json = readJson(filePath); |
| 186 | if (!json) return {}; |
| 187 | const block = json.mcpServers; |
| 188 | if (!isPlainObject(block)) return {}; |
| 189 | const out: Record<string, McpServerConfig> = {}; |
| 190 | for (const [name, raw] of Object.entries(block)) { |
| 191 | if (!/^[A-Za-z0-9_-]+$/.test(name)) continue; |
| 192 | const config = normalizeExternalServer(raw); |
| 193 | if (config) out[name] = config; |
| 194 | } |
| 195 | return out; |
| 196 | } |
| 197 | |
| 198 | /** Pull the user-scope MCP servers Claude Code stores at the top level of |
| 199 | * `~/.claude.json`. This is where `claude mcp add -s user …` writes — the |
no test coverage detected