Expand description
MCP client configuration and optional independent server support. MCP client construction and independently owned server lifecycle.
McpClientConfig selects stdio or Streamable HTTP plus naming and interaction
policy. Construction is passive; crate::Toolset::mcp connects. The optional
mcp-server feature adds a server whose consuming shutdown settles serving
work while the caller retains separate toolset shutdown authority.
§Invoke an explicitly configured service
This example requires a running Streamable HTTP server at the configured URL,
with an echo tool accepting {"text":"hello"} and returning that text.
MCP invocation arguments must be JSON objects. Supply any
required authentication through the explicit header map. Namespaces affect public
selection; they do not rename the native tool. Never infer a server endpoint from
a Toolset. A request timeout bounds calls, not a whole application scenario.
use std::time::Duration;
use tools_kit::{Toolset, ToolsetBackend, ToolHandlerBackend, ToolError};
use tools_kit::declaration::ToolName;
use tools_kit::execution::{ToolContent, ToolHandlerInput, ToolHandlerOutput, ToolInvocation};
use tools_kit::mcp::{McpClientConfig, McpConnectionConfig};
let config = McpClientConfig::new(McpConnectionConfig::StreamableHttp {
endpoint: "http://127.0.0.1:8000/mcp".parse().unwrap(),
headers: Default::default(),
}).with_request_timeout(Duration::from_secs(30))?;
let tools = Toolset::mcp(config).await?;
let work = async {
let name = ToolName::new("echo")?;
let inventory = tools.list_tools().await?;
assert!(inventory.iter().any(|info| info.name == name));
let mut handler = tools.tool_handler(name).await?;
let output = handler.step(ToolHandlerInput::Invoke(ToolInvocation {
call_id: Some("owned-call".into()), arguments: serde_json::json!({"text":"hello"}),
})).await?;
let ToolHandlerOutput::Completed(result) = output else {
return Err(ToolError::Protocol { message: "configured echo unexpectedly interacted".into() });
};
assert!(!result.is_error);
assert!(matches!(result.content.as_slice(), [ToolContent::Text { text, .. }] if text == "hello"));
Ok::<(), ToolError>(())
}.await;
let cleanup = tools.shutdown().await;
work?;
cleanup?;With mcp-server, the McpServer type’s complete example starts a separately
owned loopback server, invokes it through a client, then settles the client,
server, and underlying Toolset in that order. Without that feature only client
construction is available. A server does not own the caller’s underlying source.
Structs§
- McpClient
Config - Validated MCP client Toolset configuration.
Configuration construction does not connect or spawn a process;
crate::Toolset::mcpperforms that work. Discovered names may be namespaced without exposing native routing. - McpServer
- Independently owned MCP server serving any concrete
ToolsetBackend. - McpServer
Config - Validated independent MCP server configuration.
Available with the
mcp-serverfeature. Constructing this value does not bind a socket.
Enums§
- McpConnection
Config - Connection to one MCP server.
- McpServer
Interaction Policy - Policy for resolving interactions while serving a Toolset over MCP.