# RustMCP
[](https://crates.io/crates/rustmcp)
[](https://docs.rs/rustmcp)
[](https://github.com/zhangyi/rustmcp-rs/blob/main/LICENSE)
A Rust implementation of the Model Context Protocol (MCP) for building AI agent tools.
## Overview
RustMCP is a Rust library that implements the Model Context Protocol (MCP), which allows AI models to interact with tools, resources, and prompts in a standardized way. This implementation provides:
- Tool management and execution
- Resource handling
- Prompt management
- Full MCP protocol implementation (HTTP and WebSocket)
- Easy integration with Axum web framework
## Features
- **Tool System**: Register and execute tools with parameter support
- **Resource Management**: Handle various types of resources
- **Prompt Management**: Manage and serve prompts for AI models
- **MCP Protocol**: Full implementation of the MCP specification
- **Web Integration**: Built-in HTTP and WebSocket API using Axum
- **Extensible**: Easy to extend with custom tools, resources, and prompts
## Installation
Add this to your `Cargo.toml`:
```toml
[dependencies]
rustmcp = "0.1"
```
## Basic Usage
```rust
use rustmcp::{RustMCP, FunctionTool};
use std::collections::HashMap;
#[tokio::main]
async fn main() {
// Create a RustMCP instance
let mut rustmcp = RustMCP::new();
// Define a simple tool function
fn greet_tool(args: Option<HashMap<String, serde_json::Value>>) -> Result<serde_json::Value, String> {
let name = args
.and_then(|map| map.get("name").cloned())
.unwrap_or(serde_json::Value::String("World".to_string()));
let greeting = format!("Hello, {}!", name.as_str().unwrap_or("World"));
Ok(serde_json::Value::String(greeting))
}
// Create and register the tool
let greet_function_tool = FunctionTool::from_function(
greet_tool,
Some("greet".to_string()),
Some("Greets a person by name".to_string()),
Some(vec!["greeting".to_string()]),
None,
None,
);
rustmcp.add_tool(greet_function_tool);
// Test calling the tool
let mut args = HashMap::new();
args.insert("name".to_string(), serde_json::Value::String("RustMCP".to_string()));
match rustmcp.mcp_call_tool("greet".to_string(), Some(args)).await {
Ok(result) => println!("Tool result: {}", result.as_str().unwrap_or("Unknown")),
Err(e) => println!("Error calling tool: {}", e),
}
}
```
## Server Example
RustMCP includes a built-in web server implementation that supports both HTTP and WebSocket connections. Here's a complete example:
```rust
use rustmcp::{RustMCP, FunctionTool, FunctionResource, FunctionPrompt, create_app};
use serde_json::Value;
use std::collections::HashMap;
#[tokio::main]
async fn main() {
// Create RustMCP instance
let mut rustmcp = RustMCP::new();
// Add a sample tool
let echo_tool = FunctionTool::from_function(
|_args: Option<HashMap<String, Value>>| -> Result<Value, String> {
let message = _args
.as_ref()
.and_then(|m| m.get("message"))
.and_then(|v| v.as_str())
.unwrap_or("Hello, World!");
Ok(Value::String(message.to_string()))
},
Some("echo".to_string()),
Some("Echoes back the provided message".to_string()),
Some(vec!["utility".to_string()]),
Some(serde_json::json!({
"type": "object",
"properties": {
"message": {
"type": "string",
"description": "The message to echo"
}
},
"required": ["message"]
})),
None,
None,
);
rustmcp.add_tool(echo_tool);
// Add a sample resource
let hello_resource = FunctionResource::from_function(
|| -> Result<Value, String> {
Ok(Value::String("Hello from resource!".to_string()))
},
"resource://hello".to_string(),
Some("hello".to_string()),
Some("A simple hello resource".to_string()),
Some("text/plain".to_string()),
Some(vec!["example".to_string()]),
None,
None,
);
rustmcp.add_resource(hello_resource);
// Add a sample prompt
let greeting_prompt = FunctionPrompt::from_function(
|_args: Option<HashMap<String, Value>>| -> Result<Vec<rustmcp::PromptMessage>, String> {
let name = _args
.as_ref()
.and_then(|m| m.get("name"))
.and_then(|v| v.as_str())
.unwrap_or("World");
Ok(vec![rustmcp::PromptMessage {
role: "user".to_string(),
content: format!("Hello, {}!", name),
}])
},
Some("greeting".to_string()),
Some("A simple greeting prompt".to_string()),
Some(vec!["example".to_string()]),
None,
);
rustmcp.add_prompt(greeting_prompt);
// Create and start the server
let app = create_app(rustmcp);
println!("Starting RustMCP server on port 3001...");
println!("HTTP endpoints available at http://localhost:3001");
println!("WebSocket endpoint available at ws://localhost:3001/mcp/ws");
println!("MCP JSON-RPC endpoint available at http://localhost:3001/mcp");
let listener = tokio::net::TcpListener::bind("0.0.0.0:3001").await.unwrap();
axum::serve(listener, app).await.unwrap();
}
```
## API Endpoints
The server provides the following endpoints:
- `GET /` - Health check endpoint
- `GET /mcp/tools` - List all tools
- `GET /mcp/resources` - List all resources
- `GET /mcp/prompts` - List all prompts
- `POST /mcp/call-tool` - Call a specific tool
- `POST /mcp` - MCP JSON-RPC endpoint (for full MCP protocol)
- `GET /mcp/ws` - WebSocket endpoint (for full MCP protocol)
## Documentation
- [API Documentation](https://docs.rs/rustmcp)
- [Examples](https://github.com/yourusername/rustmcp-rs/tree/main/examples)
## License
Licensed under either of:
- Apache License, Version 2.0 ([LICENSE-APACHE](LICENSE-APACHE) or http://www.apache.org/licenses/LICENSE-2.0)
- MIT license ([LICENSE-MIT](LICENSE-MIT) or http://opensource.org/licenses/MIT)
at your option.
## Contribution
Unless you explicitly state otherwise, any contribution intentionally submitted for inclusion in the work by you, as defined in the Apache-2.0 license, shall be dual licensed as above, without any additional terms or conditions.