@modelcontextprotocol/server-everything 2025.9.25 → 2025.12.18

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.
package/README.md CHANGED
@@ -196,7 +196,7 @@ Add the configuration to your user-level MCP configuration file. Open the Comman
196
196
  **Method 2: Workspace Configuration**
197
197
  Alternatively, you can add the configuration to a file called `.vscode/mcp.json` in your workspace. This will allow you to share the configuration with others.
198
198
 
199
- > For more details about MCP configuration in VS Code, see the [official VS Code MCP documentation](https://code.visualstudio.com/docs/copilot/mcp).
199
+ > For more details about MCP configuration in VS Code, see the [official VS Code MCP documentation](https://code.visualstudio.com/docs/copilot/customization/mcp-servers).
200
200
 
201
201
  #### NPX
202
202
 
@@ -1,15 +1,14 @@
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, 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");
11
- const ToolInputSchema = ToolSchema.shape.inputSchema;
12
- const ToolOutputSchema = ToolSchema.shape.outputSchema;
13
12
  /* Input schemas for tools implemented in this server */
14
13
  const EchoSchema = z.object({
15
14
  message: z.string().describe("Message to echo"),
@@ -83,6 +82,9 @@ const StructuredContentSchema = {
83
82
  .describe("Humidity percentage"),
84
83
  })
85
84
  };
85
+ const ZipResourcesInputSchema = z.object({
86
+ 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"),
87
+ });
86
88
  var ToolName;
87
89
  (function (ToolName) {
88
90
  ToolName["ECHO"] = "echo";
@@ -96,6 +98,7 @@ var ToolName;
96
98
  ToolName["ELICITATION"] = "startElicitation";
97
99
  ToolName["GET_RESOURCE_LINKS"] = "getResourceLinks";
98
100
  ToolName["STRUCTURED_CONTENT"] = "structuredContent";
101
+ ToolName["ZIP_RESOURCES"] = "zip";
99
102
  ToolName["LIST_ROOTS"] = "listRoots";
100
103
  })(ToolName || (ToolName = {}));
101
104
  var PromptName;
@@ -167,7 +170,7 @@ export const createServer = () => {
167
170
  }
168
171
  };
169
172
  // Helper method to request sampling from client
170
- const requestSampling = async (context, uri, maxTokens = 100) => {
173
+ const requestSampling = async (context, uri, maxTokens = 100, sendRequest) => {
171
174
  const request = {
172
175
  method: "sampling/createMessage",
173
176
  params: {
@@ -186,17 +189,7 @@ export const createServer = () => {
186
189
  includeContext: "thisServer",
187
190
  },
188
191
  };
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());
192
+ return await sendRequest(request, CreateMessageResultSchema);
200
193
  };
201
194
  const ALL_RESOURCES = Array.from({ length: 100 }, (_, i) => {
202
195
  const uri = `test://static/resource/${i + 1}`;
@@ -263,11 +256,9 @@ export const createServer = () => {
263
256
  }
264
257
  throw new Error(`Unknown resource: ${uri}`);
265
258
  });
266
- server.setRequestHandler(SubscribeRequestSchema, async (request) => {
259
+ server.setRequestHandler(SubscribeRequestSchema, async (request, extra) => {
267
260
  const { uri } = request.params;
268
261
  subscriptions.add(uri);
269
- // Request sampling from client when someone subscribes
270
- await requestSampling("A new subscription was started", uri);
271
262
  return {};
272
263
  });
273
264
  server.setRequestHandler(UnsubscribeRequestSchema, async (request) => {
@@ -435,6 +426,11 @@ export const createServer = () => {
435
426
  inputSchema: zodToJsonSchema(StructuredContentSchema.input),
436
427
  outputSchema: zodToJsonSchema(StructuredContentSchema.output),
437
428
  },
429
+ {
430
+ name: ToolName.ZIP_RESOURCES,
431
+ 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.",
432
+ inputSchema: zodToJsonSchema(ZipResourcesInputSchema),
433
+ }
438
434
  ];
439
435
  if (clientCapabilities.roots)
440
436
  tools.push({
@@ -445,7 +441,7 @@ export const createServer = () => {
445
441
  if (clientCapabilities.elicitation)
446
442
  tools.push({
447
443
  name: ToolName.ELICITATION,
448
- description: "Demonstrates the Elicitation feature by asking the user to provide information about their favorite color, number, and pets.",
444
+ description: "Elicitation test tool that demonstrates how to request user input with various field types (string, boolean, email, uri, date, integer, number, enum)",
449
445
  inputSchema: zodToJsonSchema(ElicitationSchema),
450
446
  });
451
447
  return { tools };
@@ -510,10 +506,10 @@ export const createServer = () => {
510
506
  if (name === ToolName.SAMPLE_LLM) {
511
507
  const validatedArgs = SampleLLMSchema.parse(args);
512
508
  const { prompt, maxTokens } = validatedArgs;
513
- const result = await requestSampling(prompt, ToolName.SAMPLE_LLM, maxTokens);
509
+ const result = await requestSampling(prompt, ToolName.SAMPLE_LLM, maxTokens, extra.sendRequest);
514
510
  return {
515
511
  content: [
516
- { type: "text", text: `LLM sampling result: ${result.content.text}` },
512
+ { type: "text", text: `LLM sampling result: ${Array.isArray(result.content) ? result.content.map(c => c.type === "text" ? c.text : JSON.stringify(c)).join("") : (result.content.type === "text" ? result.content.text : JSON.stringify(result.content))}` },
517
513
  ],
518
514
  };
519
515
  }
@@ -612,36 +608,155 @@ export const createServer = () => {
612
608
  }
613
609
  if (name === ToolName.ELICITATION) {
614
610
  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'
611
+ const elicitationResult = await extra.sendRequest({
612
+ method: 'elicitation/create',
613
+ params: {
614
+ message: 'Please provide inputs for the following fields:',
615
+ requestedSchema: {
616
+ type: 'object',
617
+ properties: {
618
+ name: {
619
+ title: 'String',
620
+ type: 'string',
621
+ description: 'Your full, legal name',
622
+ },
623
+ check: {
624
+ title: 'Boolean',
625
+ type: 'boolean',
626
+ description: 'Agree to the terms and conditions',
627
+ },
628
+ firstLine: {
629
+ title: 'String with default',
630
+ type: 'string',
631
+ description: 'Favorite first line of a story',
632
+ default: 'It was a dark and stormy night.',
633
+ },
634
+ email: {
635
+ title: 'String with email format',
636
+ type: 'string',
637
+ format: 'email',
638
+ description: 'Your email address (will be verified, and never shared with anyone else)',
639
+ },
640
+ homepage: {
641
+ type: 'string',
642
+ format: 'uri',
643
+ title: 'String with uri format',
644
+ description: 'Portfolio / personal website',
645
+ },
646
+ birthdate: {
647
+ title: 'String with date format',
648
+ type: 'string',
649
+ format: 'date',
650
+ description: 'Your date of birth',
651
+ },
652
+ integer: {
653
+ title: 'Integer',
654
+ type: 'integer',
655
+ description: 'Your favorite integer (do not give us your phone number, pin, or other sensitive info)',
656
+ minimum: 1,
657
+ maximum: 100,
658
+ default: 42,
659
+ },
660
+ number: {
661
+ title: 'Number in range 1-1000',
662
+ type: 'number',
663
+ description: 'Favorite number (there are no wrong answers)',
664
+ minimum: 0,
665
+ maximum: 1000,
666
+ default: 3.14,
667
+ },
668
+ untitledSingleSelectEnum: {
669
+ type: 'string',
670
+ title: 'Untitled Single Select Enum',
671
+ description: 'Choose your favorite friend',
672
+ enum: ['Monica', 'Rachel', 'Joey', 'Chandler', 'Ross', 'Phoebe'],
673
+ default: 'Monica'
674
+ },
675
+ untitledMultipleSelectEnum: {
676
+ type: 'array',
677
+ title: 'Untitled Multiple Select Enum',
678
+ description: 'Choose your favorite instruments',
679
+ minItems: 1,
680
+ maxItems: 3,
681
+ items: { type: 'string', enum: ['Guitar', 'Piano', 'Violin', 'Drums', 'Bass'] },
682
+ default: ['Guitar']
683
+ },
684
+ titledSingleSelectEnum: {
685
+ type: 'string',
686
+ title: 'Titled Single Select Enum',
687
+ description: 'Choose your favorite hero',
688
+ oneOf: [
689
+ { const: 'hero-1', title: 'Superman' },
690
+ { const: 'hero-2', title: 'Green Lantern' },
691
+ { const: 'hero-3', title: 'Wonder Woman' }
692
+ ],
693
+ default: 'hero-1'
694
+ },
695
+ titledMultipleSelectEnum: {
696
+ type: 'array',
697
+ title: 'Titled Multiple Select Enum',
698
+ description: 'Choose your favorite types of fish',
699
+ minItems: 1,
700
+ maxItems: 3,
701
+ items: {
702
+ anyOf: [
703
+ { const: 'fish-1', title: 'Tuna' },
704
+ { const: 'fish-2', title: 'Salmon' },
705
+ { const: 'fish-3', title: 'Trout' }
706
+ ]
707
+ },
708
+ default: ['fish-1']
709
+ },
710
+ legacyTitledEnum: {
711
+ type: 'string',
712
+ title: 'Legacy Titled Single Select Enum',
713
+ description: 'Choose your favorite type of pet',
714
+ enum: ['pet-1', 'pet-2', 'pet-3', 'pet-4', 'pet-5'],
715
+ enumNames: ['Cats', 'Dogs', 'Birds', 'Fish', 'Reptiles'],
716
+ default: 'pet-1',
717
+ }
718
+ },
719
+ required: ['name'],
624
720
  },
625
- }
626
- });
721
+ },
722
+ }, ElicitResultSchema, { timeout: 10 * 60 * 1000 /* 10 minutes */ });
627
723
  // Handle different response actions
628
724
  const content = [];
629
725
  if (elicitationResult.action === 'accept' && elicitationResult.content) {
630
726
  content.push({
631
727
  type: "text",
632
- text: `✅ User provided their favorite things!`,
728
+ text: `✅ User provided the requested information!`,
633
729
  });
634
730
  // Only access elicitationResult.content when action is accept
635
- const { color, number, pets } = elicitationResult.content;
731
+ const userData = elicitationResult.content;
732
+ const lines = [];
733
+ if (userData.name)
734
+ lines.push(`- Name: ${userData.name}`);
735
+ if (userData.check !== undefined)
736
+ lines.push(`- Agreed to terms: ${userData.check}`);
737
+ if (userData.color)
738
+ lines.push(`- Favorite Color: ${userData.color}`);
739
+ if (userData.email)
740
+ lines.push(`- Email: ${userData.email}`);
741
+ if (userData.homepage)
742
+ lines.push(`- Homepage: ${userData.homepage}`);
743
+ if (userData.birthdate)
744
+ lines.push(`- Birthdate: ${userData.birthdate}`);
745
+ if (userData.integer !== undefined)
746
+ lines.push(`- Favorite Integer: ${userData.integer}`);
747
+ if (userData.number !== undefined)
748
+ lines.push(`- Favorite Number: ${userData.number}`);
749
+ if (userData.petType)
750
+ lines.push(`- Pet Type: ${userData.petType}`);
636
751
  content.push({
637
752
  type: "text",
638
- text: `Their favorites are:\n- Color: ${color || 'not specified'}\n- Number: ${number || 'not specified'}\n- Pets: ${pets || 'not specified'}`,
753
+ text: `User inputs:\n${lines.join('\n')}`,
639
754
  });
640
755
  }
641
756
  else if (elicitationResult.action === 'decline') {
642
757
  content.push({
643
758
  type: "text",
644
- text: `❌ User declined to provide their favorite things.`,
759
+ text: `❌ User declined to provide the requested information.`,
645
760
  });
646
761
  }
647
762
  else if (elicitationResult.action === 'cancel') {
@@ -698,6 +813,33 @@ export const createServer = () => {
698
813
  structuredContent: weather
699
814
  };
700
815
  }
816
+ if (name === ToolName.ZIP_RESOURCES) {
817
+ const { files } = ZipResourcesInputSchema.parse(args);
818
+ const zip = new JSZip();
819
+ for (const [fileName, fileUrl] of Object.entries(files)) {
820
+ try {
821
+ const response = await fetch(fileUrl);
822
+ if (!response.ok) {
823
+ throw new Error(`Failed to fetch ${fileUrl}: ${response.statusText}`);
824
+ }
825
+ const arrayBuffer = await response.arrayBuffer();
826
+ zip.file(fileName, arrayBuffer);
827
+ }
828
+ catch (error) {
829
+ throw new Error(`Error fetching file ${fileUrl}: ${error instanceof Error ? error.message : String(error)}`);
830
+ }
831
+ }
832
+ const uri = `data:application/zip;base64,${await zip.generateAsync({ type: "base64" })}`;
833
+ return {
834
+ content: [
835
+ {
836
+ type: "resource_link",
837
+ mimeType: "application/zip",
838
+ uri,
839
+ },
840
+ ],
841
+ };
842
+ }
701
843
  if (name === ToolName.LIST_ROOTS) {
702
844
  ListRootsSchema.parse(args);
703
845
  if (!clientSupportsRoots) {
package/dist/stdio.js CHANGED
@@ -5,13 +5,16 @@ console.error('Starting default (STDIO) server...');
5
5
  async function main() {
6
6
  const transport = new StdioServerTransport();
7
7
  const { server, cleanup, startNotificationIntervals } = createServer();
8
+ // Cleanup when client disconnects
9
+ server.onclose = async () => {
10
+ await cleanup();
11
+ process.exit(0);
12
+ };
8
13
  await server.connect(transport);
9
14
  startNotificationIntervals();
10
15
  // Cleanup on exit
11
16
  process.on("SIGINT", async () => {
12
- await cleanup();
13
17
  await server.close();
14
- process.exit(0);
15
18
  });
16
19
  }
17
20
  main().catch((error) => {
package/package.json CHANGED
@@ -1,11 +1,16 @@
1
1
  {
2
2
  "name": "@modelcontextprotocol/server-everything",
3
- "version": "2025.9.25",
3
+ "version": "2025.12.18",
4
4
  "description": "MCP server that exercises all the features of the MCP protocol",
5
5
  "license": "MIT",
6
+ "mcpName": "io.github.modelcontextprotocol/server-everything",
6
7
  "author": "Anthropic, PBC (https://anthropic.com)",
7
8
  "homepage": "https://modelcontextprotocol.io",
8
9
  "bugs": "https://github.com/modelcontextprotocol/servers/issues",
10
+ "repository": {
11
+ "type": "git",
12
+ "url": "https://github.com/modelcontextprotocol/servers.git"
13
+ },
9
14
  "type": "module",
10
15
  "bin": {
11
16
  "mcp-server-everything": "dist/index.js"
@@ -22,15 +27,16 @@
22
27
  "start:streamableHttp": "node dist/streamableHttp.js"
23
28
  },
24
29
  "dependencies": {
25
- "@modelcontextprotocol/sdk": "^1.18.0",
30
+ "@modelcontextprotocol/sdk": "^1.24.0",
26
31
  "cors": "^2.8.5",
27
- "express": "^4.21.1",
28
- "zod": "^3.23.8",
32
+ "express": "^5.2.1",
33
+ "jszip": "^3.10.1",
34
+ "zod": "^3.25.0",
29
35
  "zod-to-json-schema": "^3.23.5"
30
36
  },
31
37
  "devDependencies": {
32
38
  "@types/cors": "^2.8.19",
33
- "@types/express": "^5.0.0",
39
+ "@types/express": "^5.0.6",
34
40
  "shx": "^0.3.4",
35
41
  "typescript": "^5.6.2"
36
42
  }