use async_trait::async_trait;
use rust_mcp_sdk::{
error::SdkResult,
mcp_client::{client_runtime, ClientHandler, McpClientOptions, ToMcpClientHandler},
schema::*,
task_store::InMemoryTaskStore,
*,
};
use std::sync::Arc;
pub struct MyClientHandler;
#[async_trait]
impl ClientHandler for MyClientHandler {
}
#[tokio::main]
async fn main() -> SdkResult<()> {
let client_details: InitializeRequestParams = InitializeRequestParams {
capabilities: ClientCapabilities::default(),
client_info: Implementation {
name: "simple-rust-mcp-client".into(),
version: "0.1.0".into(),
description: None,
icons: vec![],
title: None,
website_url: None,
},
protocol_version: ProtocolVersion::V2025_11_25.into(),
meta: None,
};
let transport = StdioTransport::create_with_server_launch(
"npx",
vec![
"-y".to_string(),
"@modelcontextprotocol/server-everything@latest".to_string(),
],
None,
TransportOptions::default(),
)?;
let handler = MyClientHandler {};
let client = client_runtime::create_client(McpClientOptions {
client_details,
transport,
handler: handler.to_mcp_client_handler(),
task_store: Some(Arc::new(InMemoryTaskStore::new(None))), server_task_store: Some(Arc::new(InMemoryTaskStore::new(None))),
message_observer: None,
});
client.clone().start().await?;
let server_version = client.server_version().unwrap();
let tools = client.request_tool_list(None).await?.tools;
println!(
"List of tools for {}@{}",
server_version.name, server_version.version
);
tools.iter().enumerate().for_each(|(tool_index, tool)| {
println!(
" {}. {} : {}",
tool_index + 1,
tool.name,
tool.description.clone().unwrap_or_default()
);
});
println!("Call \"add\" tool with 100 and 28 ...");
let params = serde_json::json!({"a": 100,"b": 28})
.as_object()
.unwrap()
.clone();
let request = CallToolRequestParams {
name: "add".to_string(),
arguments: Some(params),
meta: None,
task: None,
};
let result = client.request_tool_call(request).await?;
println!(
"{}",
result.content.first().unwrap().as_text_content()?.text
);
client.shut_down().await?;
Ok(())
}