Open
Conversation
|
@modelcontextprotocol/client
@modelcontextprotocol/server
@modelcontextprotocol/express
@modelcontextprotocol/fastify
@modelcontextprotocol/hono
@modelcontextprotocol/node
commit: |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Adds a pair of self-contained examples showing how to author MCP tools, resources, and prompts as decorated methods on a class, in both decorator dialects TypeScript supports.
Motivation and Context
Follow-up to #116 ("Declarative, high-level MCP server API"). That thread evolved into a discussion of class-based
@Tool/@Resource/@Promptdecorators as an alternative to the function-basedMcpServerAPI. The issue was closed as not planned — decorators in TS/JS only work on class methods, so shipping them in the SDK would impose an OO style on everyone — with the position that this pattern is straightforward for users to build themselves on top of the existing SDK. These examples are the reference implementation of exactly that: copy-paste-friendly proof that the pattern works end-to-end, with no SDK changes required.The SDK's
McpServerAPI is function-based: you call.tool(),.resource(),.prompt()at registration time. That works well, but a recurring question from users is "can I group related handlers onto a class and register them declaratively?" — the answer is yes, with a small amount of decorator plumbing and no new SDK dependency.These examples show the full pattern end-to-end so users can copy ~60 lines into their own project:
@McpTool/@McpResource/@McpResourceTemplate/@McpPromptmethod decoratorsregisterClass(server, instance)helper that reflects over the class and wires each decorated method intoMcpServerTool,Prompt,Resource,ResourceTemplateType) viaOmit<…, identity>, so any spec-level field (icons, annotations,_meta, …) is automatically supported without touching the exampleBecause
experimentalDecoratorsis project-wide in TypeScript, covering both dialects requires a second tsconfig — which is itself useful to document.How Has This Been Tested?
pnpm tsx src/legacyClassDecoratorsExample.ts(uses the package's existingexperimentalDecorators: truetsconfig).pnpm tsx --tsconfig=tsconfig.standard-decorators.json src/classDecoratorsExample.ts.pnpm --filter @modelcontextprotocol/server-examples typechecknow runstsgoagainst both tsconfigs, so the standard-decorators file is type-checked in CI.Breaking Changes
None. These are additive example files; no SDK code changes.
Types of changes
Checklist
Additional context
Background references
experimentalDecorators.classDecoratorsExample.ts.Design notes
(target, propertyKey, descriptor)vs(value, context)) and howregisterClassretrieves the collected metadata. This makes them easy to diff if you're porting one codebase to the other.reflect-metadata. The legacy version stashes arrays on the prototype; the standard version uses Stage-3's built-incontext.metadataobject.Symbol.metadatapolyfill is guarded (??=) so it is a no-op on Node 22+.