@modelcontextprotocol/server-everything 2025.9.25 → 2025.11.25

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (2) hide show
  1. package/dist/everything.js +134 -33
  2. package/package.json +3 -2
@@ -1,10 +1,11 @@
1
1
  import { Server } from "@modelcontextprotocol/sdk/server/index.js";
2
- import { CallToolRequestSchema, CompleteRequestSchema, CreateMessageResultSchema, GetPromptRequestSchema, ListPromptsRequestSchema, ListResourcesRequestSchema, ListResourceTemplatesRequestSchema, ListToolsRequestSchema, ReadResourceRequestSchema, RootsListChangedNotificationSchema, SubscribeRequestSchema, ToolSchema, UnsubscribeRequestSchema } from "@modelcontextprotocol/sdk/types.js";
2
+ import { CallToolRequestSchema, CompleteRequestSchema, CreateMessageResultSchema, ElicitResultSchema, GetPromptRequestSchema, ListPromptsRequestSchema, ListResourcesRequestSchema, ListResourceTemplatesRequestSchema, ListToolsRequestSchema, ReadResourceRequestSchema, RootsListChangedNotificationSchema, SubscribeRequestSchema, ToolSchema, UnsubscribeRequestSchema } from "@modelcontextprotocol/sdk/types.js";
3
3
  import { z } from "zod";
4
4
  import { zodToJsonSchema } from "zod-to-json-schema";
5
5
  import { readFileSync } from "fs";
6
6
  import { fileURLToPath } from "url";
7
7
  import { dirname, join } from "path";
8
+ import JSZip from "jszip";
8
9
  const __filename = fileURLToPath(import.meta.url);
9
10
  const __dirname = dirname(__filename);
10
11
  const instructions = readFileSync(join(__dirname, "instructions.md"), "utf-8");
@@ -83,6 +84,9 @@ const StructuredContentSchema = {
83
84
  .describe("Humidity percentage"),
84
85
  })
85
86
  };
87
+ const ZipResourcesInputSchema = z.object({
88
+ files: z.record(z.string().url().describe("URL of the file to include in the zip")).describe("Mapping of file names to URLs to include in the zip"),
89
+ });
86
90
  var ToolName;
87
91
  (function (ToolName) {
88
92
  ToolName["ECHO"] = "echo";
@@ -96,6 +100,7 @@ var ToolName;
96
100
  ToolName["ELICITATION"] = "startElicitation";
97
101
  ToolName["GET_RESOURCE_LINKS"] = "getResourceLinks";
98
102
  ToolName["STRUCTURED_CONTENT"] = "structuredContent";
103
+ ToolName["ZIP_RESOURCES"] = "zip";
99
104
  ToolName["LIST_ROOTS"] = "listRoots";
100
105
  })(ToolName || (ToolName = {}));
101
106
  var PromptName;
@@ -167,7 +172,7 @@ export const createServer = () => {
167
172
  }
168
173
  };
169
174
  // Helper method to request sampling from client
170
- const requestSampling = async (context, uri, maxTokens = 100) => {
175
+ const requestSampling = async (context, uri, maxTokens = 100, sendRequest) => {
171
176
  const request = {
172
177
  method: "sampling/createMessage",
173
178
  params: {
@@ -186,17 +191,7 @@ export const createServer = () => {
186
191
  includeContext: "thisServer",
187
192
  },
188
193
  };
189
- return await server.request(request, CreateMessageResultSchema);
190
- };
191
- const requestElicitation = async (message, requestedSchema) => {
192
- const request = {
193
- method: 'elicitation/create',
194
- params: {
195
- message,
196
- requestedSchema
197
- }
198
- };
199
- return await server.request(request, z.any());
194
+ return await sendRequest(request, CreateMessageResultSchema);
200
195
  };
201
196
  const ALL_RESOURCES = Array.from({ length: 100 }, (_, i) => {
202
197
  const uri = `test://static/resource/${i + 1}`;
@@ -263,11 +258,9 @@ export const createServer = () => {
263
258
  }
264
259
  throw new Error(`Unknown resource: ${uri}`);
265
260
  });
266
- server.setRequestHandler(SubscribeRequestSchema, async (request) => {
261
+ server.setRequestHandler(SubscribeRequestSchema, async (request, extra) => {
267
262
  const { uri } = request.params;
268
263
  subscriptions.add(uri);
269
- // Request sampling from client when someone subscribes
270
- await requestSampling("A new subscription was started", uri);
271
264
  return {};
272
265
  });
273
266
  server.setRequestHandler(UnsubscribeRequestSchema, async (request) => {
@@ -435,6 +428,11 @@ export const createServer = () => {
435
428
  inputSchema: zodToJsonSchema(StructuredContentSchema.input),
436
429
  outputSchema: zodToJsonSchema(StructuredContentSchema.output),
437
430
  },
431
+ {
432
+ name: ToolName.ZIP_RESOURCES,
433
+ description: "Compresses the provided resource files (mapping of name to URI, which can be a data URI) to a zip file, which it returns as a data URI resource link.",
434
+ inputSchema: zodToJsonSchema(ZipResourcesInputSchema),
435
+ }
438
436
  ];
439
437
  if (clientCapabilities.roots)
440
438
  tools.push({
@@ -445,7 +443,7 @@ export const createServer = () => {
445
443
  if (clientCapabilities.elicitation)
446
444
  tools.push({
447
445
  name: ToolName.ELICITATION,
448
- description: "Demonstrates the Elicitation feature by asking the user to provide information about their favorite color, number, and pets.",
446
+ description: "Elicitation test tool that demonstrates how to request user input with various field types (string, boolean, email, uri, date, integer, number, enum)",
449
447
  inputSchema: zodToJsonSchema(ElicitationSchema),
450
448
  });
451
449
  return { tools };
@@ -510,7 +508,7 @@ export const createServer = () => {
510
508
  if (name === ToolName.SAMPLE_LLM) {
511
509
  const validatedArgs = SampleLLMSchema.parse(args);
512
510
  const { prompt, maxTokens } = validatedArgs;
513
- const result = await requestSampling(prompt, ToolName.SAMPLE_LLM, maxTokens);
511
+ const result = await requestSampling(prompt, ToolName.SAMPLE_LLM, maxTokens, extra.sendRequest);
514
512
  return {
515
513
  content: [
516
514
  { type: "text", text: `LLM sampling result: ${result.content.text}` },
@@ -612,36 +610,112 @@ export const createServer = () => {
612
610
  }
613
611
  if (name === ToolName.ELICITATION) {
614
612
  ElicitationSchema.parse(args);
615
- const elicitationResult = await requestElicitation('What are your favorite things?', {
616
- type: 'object',
617
- properties: {
618
- color: { type: 'string', description: 'Favorite color' },
619
- number: { type: 'integer', description: 'Favorite number', minimum: 1, maximum: 100 },
620
- pets: {
621
- type: 'string',
622
- enum: ['cats', 'dogs', 'birds', 'fish', 'reptiles'],
623
- description: 'Favorite pets'
613
+ const elicitationResult = await extra.sendRequest({
614
+ method: 'elicitation/create',
615
+ params: {
616
+ message: 'Please provide inputs for the following fields:',
617
+ requestedSchema: {
618
+ type: 'object',
619
+ properties: {
620
+ name: {
621
+ title: 'Full Name',
622
+ type: 'string',
623
+ description: 'Your full, legal name',
624
+ },
625
+ check: {
626
+ title: 'Agree to terms',
627
+ type: 'boolean',
628
+ description: 'A boolean check',
629
+ },
630
+ color: {
631
+ title: 'Favorite Color',
632
+ type: 'string',
633
+ description: 'Favorite color (open text)',
634
+ default: 'blue',
635
+ },
636
+ email: {
637
+ title: 'Email Address',
638
+ type: 'string',
639
+ format: 'email',
640
+ description: 'Your email address (will be verified, and never shared with anyone else)',
641
+ },
642
+ homepage: {
643
+ type: 'string',
644
+ format: 'uri',
645
+ description: 'Homepage / personal site',
646
+ },
647
+ birthdate: {
648
+ title: 'Birthdate',
649
+ type: 'string',
650
+ format: 'date',
651
+ description: 'Your date of birth (will never be shared with anyone else)',
652
+ },
653
+ integer: {
654
+ title: 'Favorite Integer',
655
+ type: 'integer',
656
+ description: 'Your favorite integer (do not give us your phone number, pin, or other sensitive info)',
657
+ minimum: 1,
658
+ maximum: 100,
659
+ default: 42,
660
+ },
661
+ number: {
662
+ title: 'Favorite Number',
663
+ type: 'number',
664
+ description: 'Favorite number (there are no wrong answers)',
665
+ minimum: 0,
666
+ maximum: 1000,
667
+ default: 3.14,
668
+ },
669
+ petType: {
670
+ title: 'Pet type',
671
+ type: 'string',
672
+ enum: ['cats', 'dogs', 'birds', 'fish', 'reptiles'],
673
+ enumNames: ['Cats', 'Dogs', 'Birds', 'Fish', 'Reptiles'],
674
+ default: 'dogs',
675
+ description: 'Your favorite pet type',
676
+ },
677
+ },
678
+ required: ['name'],
624
679
  },
625
- }
626
- });
680
+ },
681
+ }, ElicitResultSchema, { timeout: 10 * 60 * 1000 /* 10 minutes */ });
627
682
  // Handle different response actions
628
683
  const content = [];
629
684
  if (elicitationResult.action === 'accept' && elicitationResult.content) {
630
685
  content.push({
631
686
  type: "text",
632
- text: `✅ User provided their favorite things!`,
687
+ text: `✅ User provided the requested information!`,
633
688
  });
634
689
  // Only access elicitationResult.content when action is accept
635
- const { color, number, pets } = elicitationResult.content;
690
+ const userData = elicitationResult.content;
691
+ const lines = [];
692
+ if (userData.name)
693
+ lines.push(`- Name: ${userData.name}`);
694
+ if (userData.check !== undefined)
695
+ lines.push(`- Agreed to terms: ${userData.check}`);
696
+ if (userData.color)
697
+ lines.push(`- Favorite Color: ${userData.color}`);
698
+ if (userData.email)
699
+ lines.push(`- Email: ${userData.email}`);
700
+ if (userData.homepage)
701
+ lines.push(`- Homepage: ${userData.homepage}`);
702
+ if (userData.birthdate)
703
+ lines.push(`- Birthdate: ${userData.birthdate}`);
704
+ if (userData.integer !== undefined)
705
+ lines.push(`- Favorite Integer: ${userData.integer}`);
706
+ if (userData.number !== undefined)
707
+ lines.push(`- Favorite Number: ${userData.number}`);
708
+ if (userData.petType)
709
+ lines.push(`- Pet Type: ${userData.petType}`);
636
710
  content.push({
637
711
  type: "text",
638
- text: `Their favorites are:\n- Color: ${color || 'not specified'}\n- Number: ${number || 'not specified'}\n- Pets: ${pets || 'not specified'}`,
712
+ text: `User inputs:\n${lines.join('\n')}`,
639
713
  });
640
714
  }
641
715
  else if (elicitationResult.action === 'decline') {
642
716
  content.push({
643
717
  type: "text",
644
- text: `❌ User declined to provide their favorite things.`,
718
+ text: `❌ User declined to provide the requested information.`,
645
719
  });
646
720
  }
647
721
  else if (elicitationResult.action === 'cancel') {
@@ -698,6 +772,33 @@ export const createServer = () => {
698
772
  structuredContent: weather
699
773
  };
700
774
  }
775
+ if (name === ToolName.ZIP_RESOURCES) {
776
+ const { files } = ZipResourcesInputSchema.parse(args);
777
+ const zip = new JSZip();
778
+ for (const [fileName, fileUrl] of Object.entries(files)) {
779
+ try {
780
+ const response = await fetch(fileUrl);
781
+ if (!response.ok) {
782
+ throw new Error(`Failed to fetch ${fileUrl}: ${response.statusText}`);
783
+ }
784
+ const arrayBuffer = await response.arrayBuffer();
785
+ zip.file(fileName, arrayBuffer);
786
+ }
787
+ catch (error) {
788
+ throw new Error(`Error fetching file ${fileUrl}: ${error instanceof Error ? error.message : String(error)}`);
789
+ }
790
+ }
791
+ const uri = `data:application/zip;base64,${await zip.generateAsync({ type: "base64" })}`;
792
+ return {
793
+ content: [
794
+ {
795
+ type: "resource_link",
796
+ mimeType: "application/zip",
797
+ uri,
798
+ },
799
+ ],
800
+ };
801
+ }
701
802
  if (name === ToolName.LIST_ROOTS) {
702
803
  ListRootsSchema.parse(args);
703
804
  if (!clientSupportsRoots) {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@modelcontextprotocol/server-everything",
3
- "version": "2025.9.25",
3
+ "version": "2025.11.25",
4
4
  "description": "MCP server that exercises all the features of the MCP protocol",
5
5
  "license": "MIT",
6
6
  "author": "Anthropic, PBC (https://anthropic.com)",
@@ -22,9 +22,10 @@
22
22
  "start:streamableHttp": "node dist/streamableHttp.js"
23
23
  },
24
24
  "dependencies": {
25
- "@modelcontextprotocol/sdk": "^1.18.0",
25
+ "@modelcontextprotocol/sdk": "^1.19.1",
26
26
  "cors": "^2.8.5",
27
27
  "express": "^4.21.1",
28
+ "jszip": "^3.10.1",
28
29
  "zod": "^3.23.8",
29
30
  "zod-to-json-schema": "^3.23.5"
30
31
  },