Skip to content

Commit 6f852a1

Browse files
committed
Merge remote-tracking branch 'upstream/main' into request-auth-info
2 parents c4381b8 + 56b0427 commit 6f852a1

19 files changed

+5074
-102
lines changed

Diff for: README.md

+62
Original file line numberDiff line numberDiff line change
@@ -380,6 +380,68 @@ server.tool(
380380

381381
## Advanced Usage
382382

383+
### Dynamic Servers
384+
385+
If you want to offer an initial set of tools/prompts/resources, but later add additional ones based on user action or external state change, you can add/update/remove them _after_ the Server is connected. This will automatically emit the corresponding `listChanged` notificaions:
386+
387+
```ts
388+
import { McpServer } from "@modelcontextprotocol/sdk/server/mcp.js";
389+
import { z } from "zod";
390+
391+
const server = new McpServer({
392+
name: "Dynamic Example",
393+
version: "1.0.0"
394+
});
395+
396+
const listMessageTool = server.tool(
397+
"listMessages",
398+
{ channel: z.string() },
399+
async ({ channel }) => ({
400+
content: [{ type: "text", text: await listMessages(channel) }]
401+
})
402+
);
403+
404+
const putMessageTool = server.tool(
405+
"putMessage",
406+
{ channel: z.string(), message: z.string() },
407+
async ({ channel, message }) => ({
408+
content: [{ type: "text", text: await putMessage(channel, string) }]
409+
})
410+
);
411+
// Until we upgrade auth, `putMessage` is disabled (won't show up in listTools)
412+
putMessageTool.disable()
413+
414+
const upgradeAuthTool = server.tool(
415+
"upgradeAuth",
416+
{ permission: z.enum(["write', vadmin"])},
417+
// Any mutations here will automatically emit `listChanged` notifications
418+
async ({ permission }) => {
419+
const { ok, err, previous } = await upgradeAuthAndStoreToken(permission)
420+
if (!ok) return {content: [{ type: "text", text: `Error: ${err}` }]}
421+
422+
// If we previously had read-only access, 'putMessage' is now available
423+
if (previous === "read") {
424+
putMessageTool.enable()
425+
}
426+
427+
if (permission === 'write') {
428+
// If we've just upgraded to 'write' permissions, we can still call 'upgradeAuth'
429+
// but can only upgrade to 'admin'.
430+
upgradeAuthTool.update({
431+
paramSchema: { permission: z.enum(["admin"]) }, // change validation rules
432+
})
433+
} else {
434+
// If we're now an admin, we no longer have anywhere to upgrade to, so fully remove that tool
435+
upgradeAuthTool.remove()
436+
}
437+
}
438+
)
439+
440+
// Connect as normal
441+
const transport = new StdioServerTransport();
442+
await server.connect(transport);
443+
```
444+
383445
### Low-Level Server
384446

385447
For more control, you can use the low-level Server class directly:

Diff for: package.json

+1-1
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
{
22
"name": "@modelcontextprotocol/sdk",
3-
"version": "1.9.0",
3+
"version": "1.10.0",
44
"description": "Model Context Protocol implementation for TypeScript",
55
"license": "MIT",
66
"author": "Anthropic, PBC (https://anthropic.com)",

Diff for: src/client/index.test.ts

+3
Original file line numberDiff line numberDiff line change
@@ -66,6 +66,9 @@ test("should initialize with matching protocol version", async () => {
6666
protocolVersion: LATEST_PROTOCOL_VERSION,
6767
}),
6868
}),
69+
expect.objectContaining({
70+
relatedRequestId: undefined,
71+
}),
6972
);
7073

7174
// Should have the instructions returned

0 commit comments

Comments
 (0)