Problem
No public API enumerates the tools loaded into a session — built-ins merged with MCP-discovered tools from SessionConfig.mcpServers. Closest existing surfaces don't cover it:
client.rpc.tools.list({ model? }) is server-scoped — built-ins only, no session-loaded MCP tools.
session.rpc.mcp.list() returns server connection status (name, status, error?, source?), not tools or counts per server.
session.mcp_servers_loaded event fires once on session startup but carries the same server-status-only payload — no tool list.
session.mcp_server_status_changed carries { serverName, status } only.
session.tools_updated event payload is just { model: string }.
A session can report mcp.status: "connected" and still expose zero tools (wrong CLI flags, version mismatch, schema error) — there's no SDK-side way to detect this.
Why it's needed
- Operational visibility. Confirm before the first turn that an MCP server actually contributed the expected tools, not just that its process started.
- Diagnostic UIs. Surface per-server tool counts to operators of BYOK / multi-MCP deployments.
- Test assertions. Verify a given MCP wiring exposes the expected tool set without spawning a parallel
tools/list probe.
- Parity with prior MCP clients. Other MCP integrations (e.g.
@ai-sdk/mcp) expose discovered tools as an enumerable map; consumers migrating to copilot-sdk lose this.
Contribution scope
api.schema.json ships from the closed @github/copilot npm package (the public github/copilot-cli repo is just the installer). The server-side RPC handler must live in the internal CLI — external contributors can only touch SDK bindings/wrappers in this repo, not the underlying RPC implementation.
Proposed solution
Add a session-scoped tools.list RPC, mirroring the existing client.rpc.tools.list() but reflecting per-session config:
// in createSessionRpc:
tools: {
list: async (): Promise<SessionToolsListResult> =>
connection.sendRequest("session.tools.list", { sessionId }),
handlePendingToolCall: /* unchanged */,
}
export interface SessionToolsListResult {
tools: Tool[]; // namespacedName populated for MCP tools (e.g. "playwright/browser_navigate")
}
Returns built-ins (post-excludedTools/availableTools filtering) + MCP-contributed tools. Consistent with existing session.rpc.{mcp,skills,plugins,extensions}.list() shape. Parity in Python/Go/.NET per CONTRIBUTING.
A leaner alternative: enrich McpServer with toolCount?: number and/or tools?: string[]. Less consistent with the existing pattern but lighter.
Related
Environment
@github/copilot-sdk@0.3.0
Problem
No public API enumerates the tools loaded into a session — built-ins merged with MCP-discovered tools from
SessionConfig.mcpServers. Closest existing surfaces don't cover it:client.rpc.tools.list({ model? })is server-scoped — built-ins only, no session-loaded MCP tools.session.rpc.mcp.list()returns server connection status (name,status,error?,source?), not tools or counts per server.session.mcp_servers_loadedevent fires once on session startup but carries the same server-status-only payload — no tool list.session.mcp_server_status_changedcarries{ serverName, status }only.session.tools_updatedevent payload is just{ model: string }.A session can report
mcp.status: "connected"and still expose zero tools (wrong CLI flags, version mismatch, schema error) — there's no SDK-side way to detect this.Why it's needed
tools/listprobe.@ai-sdk/mcp) expose discovered tools as an enumerable map; consumers migrating to copilot-sdk lose this.Contribution scope
api.schema.jsonships from the closed@github/copilotnpm package (the publicgithub/copilot-clirepo is just the installer). The server-side RPC handler must live in the internal CLI — external contributors can only touch SDK bindings/wrappers in this repo, not the underlying RPC implementation.Proposed solution
Add a session-scoped
tools.listRPC, mirroring the existingclient.rpc.tools.list()but reflecting per-session config:Returns built-ins (post-
excludedTools/availableToolsfiltering) + MCP-contributed tools. Consistent with existingsession.rpc.{mcp,skills,plugins,extensions}.list()shape. Parity in Python/Go/.NET per CONTRIBUTING.A leaner alternative: enrich
McpServerwithtoolCount?: numberand/ortools?: string[]. Less consistent with the existing pattern but lighter.Related
Environment
@github/copilot-sdk@0.3.0