Skip to content

Latest commit

 

History

History
151 lines (116 loc) · 4.34 KB

File metadata and controls

151 lines (116 loc) · 4.34 KB

MCP Server Architecture Refactoring Summary

Overview

Successfully initiated a major refactoring of the Rust MCP SDK server architecture to separate protocol handling from transport management. This enables deployment to WASM/WASI environments and aligns with the TypeScript SDK architecture.

Completed Work

1. Core Architecture Components

ServerCore (src/server/core.rs)

  • Transport-independent server implementation
  • Implements new ProtocolHandler trait
  • Stateless request handling suitable for serverless
  • No direct transport dependencies

ProtocolHandler Trait

pub trait ProtocolHandler: Send + Sync {
    async fn handle_request(&self, id: RequestId, request: Request) -> JSONRPCResponse;
    async fn handle_notification(&self, notification: Notification) -> Result<()>;
    fn capabilities(&self) -> &ServerCapabilities;
    fn info(&self) -> &Implementation;
}

TransportAdapter Trait (src/server/adapters.rs)

pub trait TransportAdapter: Send + Sync {
    async fn serve(&self, handler: Arc<dyn ProtocolHandler>) -> Result<()>;
    fn transport_type(&self) -> &'static str;
}

2. Builder Pattern (src/server/builder.rs)

Fluent API for constructing ServerCore instances:

let server = ServerCoreBuilder::new()
    .name("my-server")
    .version("1.0.0")
    .tool("my-tool", MyTool)
    .capabilities(ServerCapabilities::tools_only())
    .build()?;

3. Transport Adapters

Implemented Adapters:

  • GenericTransportAdapter: Works with any Transport trait implementation
  • StdioAdapter: Standard input/output for CLI tools
  • HttpAdapter: Stateless HTTP for serverless
  • WebSocketAdapter: Real-time bidirectional communication
  • MockAdapter: Testing support

4. WASI HTTP Adapter (src/server/wasi_adapter.rs)

Special adapter for WASI environments:

  • Stateless request handling
  • Optional session management
  • Compatible with wit-bindgen
  • Ready for Cloudflare Workers deployment

Architecture Benefits

1. Clean Separation of Concerns

  • Protocol logic independent of transport
  • Easier testing and maintenance
  • Better code organization

2. Environment Flexibility

  • Same core logic works everywhere
  • Native servers (tokio-based)
  • WASI/WASM environments
  • Serverless platforms

3. TypeScript SDK Alignment

  • Similar architecture patterns
  • Easier cross-SDK understanding
  • Consistent approach across languages

Migration Path

For New Projects

Use the new architecture directly:

use pmcp::server::builder::ServerCoreBuilder;
use pmcp::server::adapters::StdioAdapter;

let server = ServerCoreBuilder::new()
    .name("server")
    .version("1.0.0")
    .build()?;

let adapter = StdioAdapter::new();
adapter.serve(Arc::new(server)).await?;

For Existing Projects

The old Server struct remains available. Migration is optional and can be done incrementally.

Known Limitations

  1. Type Compatibility: Some internal types need adjustment for full compatibility
  2. Authorization: Auth context needs to be passed from transport layer
  3. Session Management: Stateful operations in stateless environments need platform support
  4. WASI Compilation: Requires proper feature flags and wit-bindgen setup

Next Steps

Short Term

  1. Fix remaining type compatibility issues
  2. Complete WASI example with proper wit-bindgen integration
  3. Add integration tests for all adapters
  4. Update documentation

Medium Term

  1. Implement streaming support in adapters
  2. Add connection pooling for HTTP adapter
  3. Optimize for serverless cold starts
  4. Create deployment guides for major platforms

Long Term

  1. Deprecate old Server API (after stability period)
  2. Extract transport adapters to separate crate (if needed)
  3. Add more platform-specific adapters
  4. Performance optimizations for WASM

Testing

Run tests with:

cargo test --all-features

Run the example:

cargo run --example refactored_server_example

Issue Tracking

Main refactoring issue: paiml#48

Architectural Decisions

  1. No backward compatibility - Clean break for simpler architecture
  2. Follow WASI/TypeScript patterns - Use existing solutions
  3. Single crate structure - Match TypeScript SDK
  4. No migration support - Rely on Cargo versioning
  5. Platform-level auth - Delegate to WASI/serverless platforms