fastmcp 2.1.0__tar.gz → 2.1.1__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {fastmcp-2.1.0 → fastmcp-2.1.1}/.github/workflows/run-tests.yml +1 -1
- {fastmcp-2.1.0 → fastmcp-2.1.1}/PKG-INFO +72 -52
- {fastmcp-2.1.0 → fastmcp-2.1.1}/README.md +70 -50
- fastmcp-2.1.1/docs/clients/overview.mdx +252 -0
- fastmcp-2.1.1/docs/clients/transports.mdx +241 -0
- fastmcp-2.1.1/docs/docs.json +74 -0
- fastmcp-2.1.1/docs/getting-started/installation.mdx +62 -0
- fastmcp-2.1.1/docs/getting-started/quickstart.mdx +127 -0
- fastmcp-2.1.1/docs/getting-started/welcome.mdx +59 -0
- fastmcp-2.1.1/docs/patterns/composition.mdx +186 -0
- fastmcp-2.1.1/docs/patterns/decorating-methods.mdx +201 -0
- fastmcp-2.1.1/docs/patterns/fastapi.mdx +114 -0
- fastmcp-2.1.1/docs/patterns/openapi.mdx +174 -0
- fastmcp-2.1.1/docs/patterns/proxying.mdx +109 -0
- fastmcp-2.1.1/docs/servers/context.mdx +281 -0
- fastmcp-2.1.1/docs/servers/fastmcp.mdx +302 -0
- fastmcp-2.1.1/docs/servers/prompts.mdx +229 -0
- fastmcp-2.1.1/docs/servers/resources.mdx +252 -0
- fastmcp-2.1.1/docs/servers/resources_backup.mdx +270 -0
- fastmcp-2.1.1/docs/servers/tools.mdx +335 -0
- fastmcp-2.1.1/docs/style.css +13 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/examples/mount_example.py +4 -2
- fastmcp-2.1.1/examples/smart_home/pyproject.toml +19 -0
- fastmcp-2.1.1/examples/smart_home/src/smart_home/__init__.py +3 -0
- fastmcp-2.1.1/examples/smart_home/src/smart_home/__main__.py +9 -0
- fastmcp-2.1.1/examples/smart_home/src/smart_home/hub.py +35 -0
- fastmcp-2.1.1/examples/smart_home/src/smart_home/lights/hue_utils.py +34 -0
- fastmcp-2.1.1/examples/smart_home/src/smart_home/lights/server.py +292 -0
- fastmcp-2.1.1/examples/smart_home/src/smart_home/settings.py +12 -0
- fastmcp-2.1.1/examples/smart_home/uv.lock +657 -0
- fastmcp-2.1.1/justfile +9 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/pyproject.toml +2 -1
- {fastmcp-2.1.0 → fastmcp-2.1.1}/src/fastmcp/cli/cli.py +2 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/src/fastmcp/client/transports.py +22 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/src/fastmcp/exceptions.py +4 -0
- fastmcp-2.1.1/src/fastmcp/prompts/__init__.py +4 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/src/fastmcp/prompts/prompt.py +6 -16
- {fastmcp-2.1.0 → fastmcp-2.1.1}/src/fastmcp/prompts/prompt_manager.py +2 -1
- {fastmcp-2.1.0 → fastmcp-2.1.1}/src/fastmcp/resources/resource_manager.py +89 -5
- {fastmcp-2.1.0 → fastmcp-2.1.1}/src/fastmcp/server/context.py +1 -1
- {fastmcp-2.1.0 → fastmcp-2.1.1}/src/fastmcp/server/proxy.py +4 -4
- {fastmcp-2.1.0 → fastmcp-2.1.1}/src/fastmcp/server/server.py +156 -73
- {fastmcp-2.1.0 → fastmcp-2.1.1}/src/fastmcp/tools/tool.py +4 -1
- fastmcp-2.1.1/src/fastmcp/utilities/decorators.py +101 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/src/fastmcp/utilities/func_metadata.py +4 -1
- fastmcp-2.1.1/src/fastmcp/utilities/openapi.py +1176 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/tests/prompts/test_base.py +3 -3
- {fastmcp-2.1.0 → fastmcp-2.1.1}/tests/prompts/test_prompt_manager.py +2 -1
- fastmcp-2.1.1/tests/resources/__init__.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/tests/resources/test_resource_manager.py +2 -1
- fastmcp-2.1.1/tests/server/__init__.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/tests/server/test_file_server.py +4 -4
- {fastmcp-2.1.0 → fastmcp-2.1.1}/tests/server/test_openapi.py +8 -8
- {fastmcp-2.1.0 → fastmcp-2.1.1}/tests/server/test_proxy.py +22 -14
- {fastmcp-2.1.0 → fastmcp-2.1.1}/tests/server/test_server.py +535 -18
- fastmcp-2.1.1/tests/tools/__init__.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/tests/utilities/openapi/test_openapi.py +329 -0
- fastmcp-2.1.1/tests/utilities/test_decorated_function.py +222 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/uv.lock +43 -43
- fastmcp-2.1.0/src/fastmcp/prompts/__init__.py +0 -4
- fastmcp-2.1.0/src/fastmcp/utilities/openapi.py +0 -797
- {fastmcp-2.1.0 → fastmcp-2.1.1}/.cursor/rules/core-mcp-objects.mdc +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/.github/release.yml +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/.github/workflows/publish.yml +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/.github/workflows/run-static.yml +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/.gitignore +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/.pre-commit-config.yaml +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/LICENSE +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/Windows_Notes.md +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/docs/assets/demo-inspector.png +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/examples/complex_inputs.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/examples/desktop.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/examples/echo.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/examples/memory.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/examples/readme-quickstart.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/examples/sampling.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/examples/screenshot.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/examples/simple_echo.py +0 -0
- fastmcp-2.1.0/src/fastmcp/py.typed → fastmcp-2.1.1/examples/smart_home/README.md +0 -0
- {fastmcp-2.1.0/tests → fastmcp-2.1.1/examples/smart_home/src/smart_home/lights}/__init__.py +0 -0
- fastmcp-2.1.0/tests/prompts/__init__.py → fastmcp-2.1.1/examples/smart_home/src/smart_home/py.typed +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/examples/text_me.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/src/fastmcp/__init__.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/src/fastmcp/cli/__init__.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/src/fastmcp/cli/claude.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/src/fastmcp/client/__init__.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/src/fastmcp/client/base.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/src/fastmcp/client/client.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/src/fastmcp/client/roots.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/src/fastmcp/client/sampling.py +0 -0
- fastmcp-2.1.0/tests/resources/__init__.py → fastmcp-2.1.1/src/fastmcp/py.typed +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/src/fastmcp/resources/__init__.py +1 -1
- {fastmcp-2.1.0 → fastmcp-2.1.1}/src/fastmcp/resources/resource.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/src/fastmcp/resources/template.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/src/fastmcp/resources/types.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/src/fastmcp/server/__init__.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/src/fastmcp/server/openapi.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/src/fastmcp/settings.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/src/fastmcp/tools/__init__.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/src/fastmcp/tools/tool_manager.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/src/fastmcp/utilities/__init__.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/src/fastmcp/utilities/logging.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/src/fastmcp/utilities/types.py +0 -0
- {fastmcp-2.1.0/tests/server → fastmcp-2.1.1/tests}/__init__.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/tests/client/__init__.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/tests/client/test_client.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/tests/client/test_roots.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/tests/client/test_sampling.py +0 -0
- {fastmcp-2.1.0/tests/tools → fastmcp-2.1.1/tests/prompts}/__init__.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/tests/resources/test_file_resources.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/tests/resources/test_function_resources.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/tests/resources/test_resource_template.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/tests/resources/test_resources.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/tests/server/test_lifespan.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/tests/server/test_mount.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/tests/server/test_run_server.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/tests/server/test_servers/fastmcp_server.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/tests/server/test_servers/sse.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/tests/server/test_servers/stdio.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/tests/tools/test_tool_manager.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/tests/utilities/__init__.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/tests/utilities/openapi/__init__.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/tests/utilities/openapi/conftest.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/tests/utilities/openapi/test_openapi_advanced.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/tests/utilities/openapi/test_openapi_fastapi.py +0 -0
- {fastmcp-2.1.0 → fastmcp-2.1.1}/tests/utilities/test_func_metadata.py +0 -0
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: fastmcp
|
|
3
|
-
Version: 2.1.
|
|
4
|
-
Summary:
|
|
3
|
+
Version: 2.1.1
|
|
4
|
+
Summary: The fast, Pythonic way to build MCP servers.
|
|
5
5
|
Author: Jeremiah Lowin
|
|
6
6
|
License: Apache-2.0
|
|
7
7
|
License-File: LICENSE
|
|
@@ -19,15 +19,16 @@ Description-Content-Type: text/markdown
|
|
|
19
19
|
|
|
20
20
|
<!-- omit in toc -->
|
|
21
21
|
# FastMCP v2 🚀
|
|
22
|
-
<strong>The fast, Pythonic way to build MCP servers.</strong>
|
|
22
|
+
<strong>The fast, Pythonic way to build MCP servers and clients.</strong>
|
|
23
23
|
|
|
24
|
+
[](https://gofastmcp.com)
|
|
24
25
|
[](https://pypi.org/project/fastmcp)
|
|
25
26
|
[](https://github.com/jlowin/fastmcp/actions/workflows/run-tests.yml)
|
|
26
27
|
[](https://github.com/jlowin/fastmcp/blob/main/LICENSE)
|
|
27
28
|
|
|
28
29
|
</div>
|
|
29
30
|
|
|
30
|
-
[Model Context Protocol (MCP)](https://modelcontextprotocol.io)
|
|
31
|
+
The [Model Context Protocol (MCP)](https://modelcontextprotocol.io) is a new, standardized way to provide context and tools to your LLMs, and FastMCP makes building MCP servers and clients simple and intuitive. Create tools, expose resources, define prompts, and connect components with clean, Pythonic code.
|
|
31
32
|
|
|
32
33
|
```python
|
|
33
34
|
# server.py
|
|
@@ -44,48 +45,27 @@ if __name__ == "__main__":
|
|
|
44
45
|
mcp.run()
|
|
45
46
|
```
|
|
46
47
|
|
|
47
|
-
Run it locally for testing:
|
|
48
|
-
```bash
|
|
49
|
-
fastmcp dev server.py
|
|
50
|
-
```
|
|
51
48
|
|
|
52
|
-
|
|
49
|
+
Run the server locally:
|
|
53
50
|
```bash
|
|
54
|
-
fastmcp
|
|
51
|
+
fastmcp run server.py
|
|
55
52
|
```
|
|
56
53
|
|
|
57
54
|
FastMCP handles the complex protocol details and server management, letting you focus on building great tools and applications. It's designed to feel natural to Python developers.
|
|
58
55
|
|
|
59
|
-
## Key Features:
|
|
60
|
-
|
|
61
|
-
* **Simple Server Creation:** Build MCP servers with minimal boilerplate using intuitive decorators (`@tool`, `@resource`, `@prompt`).
|
|
62
|
-
* **Proxy MCP Servers:** Create proxy servers to expose existing MCP servers or clients with modifications, or convert between transport protocols (e.g., expose a Stdio server via SSE for web access).
|
|
63
|
-
* **Compose MCP Servers:** Compose complex applications by mounting multiple FastMCP servers together.
|
|
64
|
-
* **API Generation:** Automatically create MCP servers from existing **OpenAPI specifications** or **FastAPI applications**.
|
|
65
|
-
* **Powerful Clients:** Programmatically interact with *any* MCP server, regardless of how it was built.
|
|
66
|
-
* **LLM Sampling:** Request completions from client LLMs directly within your MCP tools.
|
|
67
|
-
* **Pythonic Interface:** Designed with familiar Python patterns like decorators and type hints.
|
|
68
|
-
* **Context Injection:** Easily access core MCP capabilities like sampling, logging, and progress reporting within your functions.
|
|
69
|
-
|
|
70
|
-
---
|
|
71
|
-
|
|
72
|
-
### What's New in v2?
|
|
73
|
-
|
|
74
|
-
FastMCP 1.0 made it so easy to build MCP servers that it's now part of the [official Model Context Protocol Python SDK](https://github.com/modelcontextprotocol/python-sdk)! For basic use cases, you can use the upstream version by importing `mcp.server.fastmcp.FastMCP` (or installing `fastmcp=1.0`).
|
|
75
|
-
|
|
76
|
-
Based on how the MCP ecosystem is evolving, FastMCP 2.0 builds on that foundation to introduce a variety of new features (and more experimental ideas). It adds advanced features like proxying and composing MCP servers, as well as automatically generating them from OpenAPI specs or FastAPI objects. FastMCP 2.0 also introduces new client-side functionality like LLM sampling.
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
---
|
|
80
56
|
|
|
81
57
|
<!-- omit in toc -->
|
|
82
58
|
## Table of Contents
|
|
83
59
|
|
|
84
|
-
- [Key Features:](#key-features)
|
|
85
|
-
- [What's New in v2?](#whats-new-in-v2)
|
|
86
|
-
- [Installation](#installation)
|
|
87
|
-
- [Quickstart](#quickstart)
|
|
88
60
|
- [What is MCP?](#what-is-mcp)
|
|
61
|
+
- [Why FastMCP?](#why-fastmcp)
|
|
62
|
+
- [Key Features](#key-features)
|
|
63
|
+
- [Servers](#servers)
|
|
64
|
+
- [Clients](#clients)
|
|
65
|
+
- [What's New in v2?](#whats-new-in-v2)
|
|
66
|
+
- [Documentation](#documentation)
|
|
67
|
+
- [Installation](#installation)
|
|
68
|
+
- [Quickstart](#quickstart)
|
|
89
69
|
- [Core Concepts](#core-concepts)
|
|
90
70
|
- [The `FastMCP` Server](#the-fastmcp-server)
|
|
91
71
|
- [Tools](#tools)
|
|
@@ -115,7 +95,62 @@ Based on how the MCP ecosystem is evolving, FastMCP 2.0 builds on that foundatio
|
|
|
115
95
|
- [Formatting \& Linting](#formatting--linting)
|
|
116
96
|
- [Pull Requests](#pull-requests)
|
|
117
97
|
|
|
118
|
-
|
|
98
|
+
|
|
99
|
+
## What is MCP?
|
|
100
|
+
|
|
101
|
+
The [Model Context Protocol (MCP)](https://modelcontextprotocol.io) lets you build servers that expose data and functionality to LLM applications in a secure, standardized way. Think of it like a web API, but specifically designed for LLM interactions. MCP servers can:
|
|
102
|
+
|
|
103
|
+
- Expose data through **Resources** (think GET endpoints; load info into context)
|
|
104
|
+
- Provide functionality through **Tools** (think POST/PUT endpoints; execute actions)
|
|
105
|
+
- Define interaction patterns through **Prompts** (reusable templates)
|
|
106
|
+
- And more!
|
|
107
|
+
|
|
108
|
+
FastMCP provides a high-level, Pythonic interface for building and interacting with these servers.
|
|
109
|
+
|
|
110
|
+
## Why FastMCP?
|
|
111
|
+
|
|
112
|
+
The MCP protocol is powerful but implementing it involves a lot of boilerplate - server setup, protocol handlers, content types, error management. FastMCP handles all the complex protocol details and server management, so you can focus on building great tools. It’s designed to be high-level and Pythonic; in most cases, decorating a function is all you need.
|
|
113
|
+
|
|
114
|
+
FastMCP aims to be:
|
|
115
|
+
|
|
116
|
+
|
|
117
|
+
🚀 **Fast:** High-level interface means less code and faster development
|
|
118
|
+
|
|
119
|
+
🍀 **Simple:** Build MCP servers with minimal boilerplate
|
|
120
|
+
|
|
121
|
+
🐍 **Pythonic:** Feels natural to Python developers
|
|
122
|
+
|
|
123
|
+
🔍 **Complete:** FastMCP aims to provide a full implementation of the core MCP specification for both servers and clients
|
|
124
|
+
|
|
125
|
+
## Key Features
|
|
126
|
+
|
|
127
|
+
### Servers
|
|
128
|
+
- **Create** servers with minimal boilerplate using intuitive decorators
|
|
129
|
+
- **Proxy** existing servers to modify configuration or transport
|
|
130
|
+
- **Compose** servers by into complex applications
|
|
131
|
+
- **Generate** servers from OpenAPI specs or FastAPI objects
|
|
132
|
+
|
|
133
|
+
### Clients
|
|
134
|
+
- **Interact** with MCP servers programmatically
|
|
135
|
+
- **Connect** to any MCP server using any transport
|
|
136
|
+
- **Test** your servers without manual intervention
|
|
137
|
+
- **Innovate** with core MCP capabilities like LLM sampling
|
|
138
|
+
|
|
139
|
+
|
|
140
|
+
## What's New in v2?
|
|
141
|
+
|
|
142
|
+
FastMCP 1.0 made it so easy to build MCP servers that it's now part of the [official Model Context Protocol Python SDK](https://github.com/modelcontextprotocol/python-sdk)! For basic use cases, you can use the upstream version by importing `mcp.server.fastmcp.FastMCP` (or installing `fastmcp=1.0`).
|
|
143
|
+
|
|
144
|
+
Based on how the MCP ecosystem is evolving, FastMCP 2.0 builds on that foundation to introduce a variety of new features (and more experimental ideas). It adds advanced features like proxying and composing MCP servers, as well as automatically generating them from OpenAPI specs or FastAPI objects. FastMCP 2.0 also introduces new client-side functionality like LLM sampling.
|
|
145
|
+
|
|
146
|
+
|
|
147
|
+
## Documentation
|
|
148
|
+
|
|
149
|
+
📚 FastMCP's documentation is available at [gofastmcp.com](https://gofastmcp.com).
|
|
150
|
+
|
|
151
|
+
---
|
|
152
|
+
|
|
153
|
+
### Installation
|
|
119
154
|
|
|
120
155
|
We strongly recommend installing FastMCP with [uv](https://docs.astral.sh/uv/), as it is required for deploying servers via the CLI:
|
|
121
156
|
|
|
@@ -134,7 +169,7 @@ cd fastmcp
|
|
|
134
169
|
uv sync
|
|
135
170
|
```
|
|
136
171
|
|
|
137
|
-
|
|
172
|
+
### Quickstart
|
|
138
173
|
|
|
139
174
|
Let's create a simple MCP server that exposes a calculator tool and some data:
|
|
140
175
|
|
|
@@ -163,23 +198,8 @@ You can install this server in [Claude Desktop](https://claude.ai/download) and
|
|
|
163
198
|
fastmcp install server.py
|
|
164
199
|
```
|
|
165
200
|
|
|
166
|
-
Alternatively, you can test it with the MCP Inspector:
|
|
167
|
-
```bash
|
|
168
|
-
fastmcp dev server.py
|
|
169
|
-
```
|
|
170
|
-
|
|
171
201
|

|
|
172
202
|
|
|
173
|
-
## What is MCP?
|
|
174
|
-
|
|
175
|
-
The [Model Context Protocol (MCP)](https://modelcontextprotocol.io) lets you build servers that expose data and functionality to LLM applications in a secure, standardized way. Think of it like a web API, but specifically designed for LLM interactions. MCP servers can:
|
|
176
|
-
|
|
177
|
-
- Expose data through **Resources** (think GET endpoints; load info into context)
|
|
178
|
-
- Provide functionality through **Tools** (think POST/PUT endpoints; execute actions)
|
|
179
|
-
- Define interaction patterns through **Prompts** (reusable templates)
|
|
180
|
-
- And more!
|
|
181
|
-
|
|
182
|
-
FastMCP provides a high-level, Pythonic interface for building and interacting with these servers.
|
|
183
203
|
|
|
184
204
|
## Core Concepts
|
|
185
205
|
|
|
@@ -2,15 +2,16 @@
|
|
|
2
2
|
|
|
3
3
|
<!-- omit in toc -->
|
|
4
4
|
# FastMCP v2 🚀
|
|
5
|
-
<strong>The fast, Pythonic way to build MCP servers.</strong>
|
|
5
|
+
<strong>The fast, Pythonic way to build MCP servers and clients.</strong>
|
|
6
6
|
|
|
7
|
+
[](https://gofastmcp.com)
|
|
7
8
|
[](https://pypi.org/project/fastmcp)
|
|
8
9
|
[](https://github.com/jlowin/fastmcp/actions/workflows/run-tests.yml)
|
|
9
10
|
[](https://github.com/jlowin/fastmcp/blob/main/LICENSE)
|
|
10
11
|
|
|
11
12
|
</div>
|
|
12
13
|
|
|
13
|
-
[Model Context Protocol (MCP)](https://modelcontextprotocol.io)
|
|
14
|
+
The [Model Context Protocol (MCP)](https://modelcontextprotocol.io) is a new, standardized way to provide context and tools to your LLMs, and FastMCP makes building MCP servers and clients simple and intuitive. Create tools, expose resources, define prompts, and connect components with clean, Pythonic code.
|
|
14
15
|
|
|
15
16
|
```python
|
|
16
17
|
# server.py
|
|
@@ -27,48 +28,27 @@ if __name__ == "__main__":
|
|
|
27
28
|
mcp.run()
|
|
28
29
|
```
|
|
29
30
|
|
|
30
|
-
Run it locally for testing:
|
|
31
|
-
```bash
|
|
32
|
-
fastmcp dev server.py
|
|
33
|
-
```
|
|
34
31
|
|
|
35
|
-
|
|
32
|
+
Run the server locally:
|
|
36
33
|
```bash
|
|
37
|
-
fastmcp
|
|
34
|
+
fastmcp run server.py
|
|
38
35
|
```
|
|
39
36
|
|
|
40
37
|
FastMCP handles the complex protocol details and server management, letting you focus on building great tools and applications. It's designed to feel natural to Python developers.
|
|
41
38
|
|
|
42
|
-
## Key Features:
|
|
43
|
-
|
|
44
|
-
* **Simple Server Creation:** Build MCP servers with minimal boilerplate using intuitive decorators (`@tool`, `@resource`, `@prompt`).
|
|
45
|
-
* **Proxy MCP Servers:** Create proxy servers to expose existing MCP servers or clients with modifications, or convert between transport protocols (e.g., expose a Stdio server via SSE for web access).
|
|
46
|
-
* **Compose MCP Servers:** Compose complex applications by mounting multiple FastMCP servers together.
|
|
47
|
-
* **API Generation:** Automatically create MCP servers from existing **OpenAPI specifications** or **FastAPI applications**.
|
|
48
|
-
* **Powerful Clients:** Programmatically interact with *any* MCP server, regardless of how it was built.
|
|
49
|
-
* **LLM Sampling:** Request completions from client LLMs directly within your MCP tools.
|
|
50
|
-
* **Pythonic Interface:** Designed with familiar Python patterns like decorators and type hints.
|
|
51
|
-
* **Context Injection:** Easily access core MCP capabilities like sampling, logging, and progress reporting within your functions.
|
|
52
|
-
|
|
53
|
-
---
|
|
54
|
-
|
|
55
|
-
### What's New in v2?
|
|
56
|
-
|
|
57
|
-
FastMCP 1.0 made it so easy to build MCP servers that it's now part of the [official Model Context Protocol Python SDK](https://github.com/modelcontextprotocol/python-sdk)! For basic use cases, you can use the upstream version by importing `mcp.server.fastmcp.FastMCP` (or installing `fastmcp=1.0`).
|
|
58
|
-
|
|
59
|
-
Based on how the MCP ecosystem is evolving, FastMCP 2.0 builds on that foundation to introduce a variety of new features (and more experimental ideas). It adds advanced features like proxying and composing MCP servers, as well as automatically generating them from OpenAPI specs or FastAPI objects. FastMCP 2.0 also introduces new client-side functionality like LLM sampling.
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
---
|
|
63
39
|
|
|
64
40
|
<!-- omit in toc -->
|
|
65
41
|
## Table of Contents
|
|
66
42
|
|
|
67
|
-
- [Key Features:](#key-features)
|
|
68
|
-
- [What's New in v2?](#whats-new-in-v2)
|
|
69
|
-
- [Installation](#installation)
|
|
70
|
-
- [Quickstart](#quickstart)
|
|
71
43
|
- [What is MCP?](#what-is-mcp)
|
|
44
|
+
- [Why FastMCP?](#why-fastmcp)
|
|
45
|
+
- [Key Features](#key-features)
|
|
46
|
+
- [Servers](#servers)
|
|
47
|
+
- [Clients](#clients)
|
|
48
|
+
- [What's New in v2?](#whats-new-in-v2)
|
|
49
|
+
- [Documentation](#documentation)
|
|
50
|
+
- [Installation](#installation)
|
|
51
|
+
- [Quickstart](#quickstart)
|
|
72
52
|
- [Core Concepts](#core-concepts)
|
|
73
53
|
- [The `FastMCP` Server](#the-fastmcp-server)
|
|
74
54
|
- [Tools](#tools)
|
|
@@ -98,7 +78,62 @@ Based on how the MCP ecosystem is evolving, FastMCP 2.0 builds on that foundatio
|
|
|
98
78
|
- [Formatting \& Linting](#formatting--linting)
|
|
99
79
|
- [Pull Requests](#pull-requests)
|
|
100
80
|
|
|
101
|
-
|
|
81
|
+
|
|
82
|
+
## What is MCP?
|
|
83
|
+
|
|
84
|
+
The [Model Context Protocol (MCP)](https://modelcontextprotocol.io) lets you build servers that expose data and functionality to LLM applications in a secure, standardized way. Think of it like a web API, but specifically designed for LLM interactions. MCP servers can:
|
|
85
|
+
|
|
86
|
+
- Expose data through **Resources** (think GET endpoints; load info into context)
|
|
87
|
+
- Provide functionality through **Tools** (think POST/PUT endpoints; execute actions)
|
|
88
|
+
- Define interaction patterns through **Prompts** (reusable templates)
|
|
89
|
+
- And more!
|
|
90
|
+
|
|
91
|
+
FastMCP provides a high-level, Pythonic interface for building and interacting with these servers.
|
|
92
|
+
|
|
93
|
+
## Why FastMCP?
|
|
94
|
+
|
|
95
|
+
The MCP protocol is powerful but implementing it involves a lot of boilerplate - server setup, protocol handlers, content types, error management. FastMCP handles all the complex protocol details and server management, so you can focus on building great tools. It’s designed to be high-level and Pythonic; in most cases, decorating a function is all you need.
|
|
96
|
+
|
|
97
|
+
FastMCP aims to be:
|
|
98
|
+
|
|
99
|
+
|
|
100
|
+
🚀 **Fast:** High-level interface means less code and faster development
|
|
101
|
+
|
|
102
|
+
🍀 **Simple:** Build MCP servers with minimal boilerplate
|
|
103
|
+
|
|
104
|
+
🐍 **Pythonic:** Feels natural to Python developers
|
|
105
|
+
|
|
106
|
+
🔍 **Complete:** FastMCP aims to provide a full implementation of the core MCP specification for both servers and clients
|
|
107
|
+
|
|
108
|
+
## Key Features
|
|
109
|
+
|
|
110
|
+
### Servers
|
|
111
|
+
- **Create** servers with minimal boilerplate using intuitive decorators
|
|
112
|
+
- **Proxy** existing servers to modify configuration or transport
|
|
113
|
+
- **Compose** servers by into complex applications
|
|
114
|
+
- **Generate** servers from OpenAPI specs or FastAPI objects
|
|
115
|
+
|
|
116
|
+
### Clients
|
|
117
|
+
- **Interact** with MCP servers programmatically
|
|
118
|
+
- **Connect** to any MCP server using any transport
|
|
119
|
+
- **Test** your servers without manual intervention
|
|
120
|
+
- **Innovate** with core MCP capabilities like LLM sampling
|
|
121
|
+
|
|
122
|
+
|
|
123
|
+
## What's New in v2?
|
|
124
|
+
|
|
125
|
+
FastMCP 1.0 made it so easy to build MCP servers that it's now part of the [official Model Context Protocol Python SDK](https://github.com/modelcontextprotocol/python-sdk)! For basic use cases, you can use the upstream version by importing `mcp.server.fastmcp.FastMCP` (or installing `fastmcp=1.0`).
|
|
126
|
+
|
|
127
|
+
Based on how the MCP ecosystem is evolving, FastMCP 2.0 builds on that foundation to introduce a variety of new features (and more experimental ideas). It adds advanced features like proxying and composing MCP servers, as well as automatically generating them from OpenAPI specs or FastAPI objects. FastMCP 2.0 also introduces new client-side functionality like LLM sampling.
|
|
128
|
+
|
|
129
|
+
|
|
130
|
+
## Documentation
|
|
131
|
+
|
|
132
|
+
📚 FastMCP's documentation is available at [gofastmcp.com](https://gofastmcp.com).
|
|
133
|
+
|
|
134
|
+
---
|
|
135
|
+
|
|
136
|
+
### Installation
|
|
102
137
|
|
|
103
138
|
We strongly recommend installing FastMCP with [uv](https://docs.astral.sh/uv/), as it is required for deploying servers via the CLI:
|
|
104
139
|
|
|
@@ -117,7 +152,7 @@ cd fastmcp
|
|
|
117
152
|
uv sync
|
|
118
153
|
```
|
|
119
154
|
|
|
120
|
-
|
|
155
|
+
### Quickstart
|
|
121
156
|
|
|
122
157
|
Let's create a simple MCP server that exposes a calculator tool and some data:
|
|
123
158
|
|
|
@@ -146,23 +181,8 @@ You can install this server in [Claude Desktop](https://claude.ai/download) and
|
|
|
146
181
|
fastmcp install server.py
|
|
147
182
|
```
|
|
148
183
|
|
|
149
|
-
Alternatively, you can test it with the MCP Inspector:
|
|
150
|
-
```bash
|
|
151
|
-
fastmcp dev server.py
|
|
152
|
-
```
|
|
153
|
-
|
|
154
184
|

|
|
155
185
|
|
|
156
|
-
## What is MCP?
|
|
157
|
-
|
|
158
|
-
The [Model Context Protocol (MCP)](https://modelcontextprotocol.io) lets you build servers that expose data and functionality to LLM applications in a secure, standardized way. Think of it like a web API, but specifically designed for LLM interactions. MCP servers can:
|
|
159
|
-
|
|
160
|
-
- Expose data through **Resources** (think GET endpoints; load info into context)
|
|
161
|
-
- Provide functionality through **Tools** (think POST/PUT endpoints; execute actions)
|
|
162
|
-
- Define interaction patterns through **Prompts** (reusable templates)
|
|
163
|
-
- And more!
|
|
164
|
-
|
|
165
|
-
FastMCP provides a high-level, Pythonic interface for building and interacting with these servers.
|
|
166
186
|
|
|
167
187
|
## Core Concepts
|
|
168
188
|
|
|
@@ -0,0 +1,252 @@
|
|
|
1
|
+
---
|
|
2
|
+
title: Client Overview
|
|
3
|
+
sidebarTitle: Overview
|
|
4
|
+
description: Learn how to use the FastMCP Client to interact with MCP servers.
|
|
5
|
+
icon: user-robot
|
|
6
|
+
---
|
|
7
|
+
|
|
8
|
+
The `fastmcp.Client` provides a high-level, asynchronous interface for interacting with any Model Context Protocol (MCP) server, whether it's built with FastMCP or another implementation. It simplifies communication by handling protocol details and connection management.
|
|
9
|
+
|
|
10
|
+
## FastMCP Client
|
|
11
|
+
|
|
12
|
+
The FastMCP Client architecture separates the protocol logic (`Client`) from the connection mechanism (`Transport`).
|
|
13
|
+
|
|
14
|
+
- **`Client`**: Handles sending MCP requests (like `tools/call`, `resources/read`), receiving responses, and managing callbacks.
|
|
15
|
+
- **`Transport`**: Responsible for establishing and maintaining the connection to the server (e.g., via WebSockets, SSE, Stdio, or in-memory).
|
|
16
|
+
|
|
17
|
+
|
|
18
|
+
### Transports
|
|
19
|
+
|
|
20
|
+
Clients must be initialized with a `transport`. You can either provide an already instantiated transport object, or provide a transport source and let FastMCP attempt to infer the correct transport to use.
|
|
21
|
+
|
|
22
|
+
The following inference rules are used to determine the appropriate `ClientTransport` based on the input type:
|
|
23
|
+
|
|
24
|
+
1. **`ClientTransport` Instance**: If you provide an already instantiated transport object, it's used directly.
|
|
25
|
+
2. **`FastMCP` Instance**: Creates a `FastMCPTransport` for efficient in-memory communication (ideal for testing).
|
|
26
|
+
3. **`Path` or `str` pointing to an existing file**:
|
|
27
|
+
* If it ends with `.py`: Creates a `PythonStdioTransport` to run the script using `python`.
|
|
28
|
+
* If it ends with `.js`: Creates a `NodeStdioTransport` to run the script using `node`.
|
|
29
|
+
4. **`AnyUrl` or `str` pointing to a URL**:
|
|
30
|
+
* If it starts with `http://` or `https://`: Creates an `SSETransport`.
|
|
31
|
+
* If it starts with `ws://` or `wss://`: Creates a `WSTransport`.
|
|
32
|
+
5. **Other**: Raises a `ValueError` if the type cannot be inferred.
|
|
33
|
+
|
|
34
|
+
```python
|
|
35
|
+
import asyncio
|
|
36
|
+
from fastmcp import Client, FastMCP
|
|
37
|
+
|
|
38
|
+
# Example transports (more details in Transports page)
|
|
39
|
+
server_instance = FastMCP(name="TestServer") # In-memory server
|
|
40
|
+
sse_url = "http://localhost:8000/sse" # SSE server URL
|
|
41
|
+
ws_url = "ws://localhost:9000" # WebSocket server URL
|
|
42
|
+
server_script = "my_mcp_server.py" # Path to a Python server file
|
|
43
|
+
|
|
44
|
+
# Client automatically infers the transport type
|
|
45
|
+
client_in_memory = Client(server_instance)
|
|
46
|
+
client_sse = Client(sse_url)
|
|
47
|
+
client_ws = Client(ws_url)
|
|
48
|
+
client_stdio = Client(server_script)
|
|
49
|
+
|
|
50
|
+
print(client_in_memory.transport)
|
|
51
|
+
print(client_sse.transport)
|
|
52
|
+
print(client_ws.transport)
|
|
53
|
+
print(client_stdio.transport)
|
|
54
|
+
|
|
55
|
+
# Expected Output (types may vary slightly based on environment):
|
|
56
|
+
# <FastMCP(server='TestServer')>
|
|
57
|
+
# <SSE(url='http://localhost:8000/sse')>
|
|
58
|
+
# <WebSocket(url='ws://localhost:9000')>
|
|
59
|
+
# <PythonStdioTransport(command='python', args=['/path/to/your/my_mcp_server.py'])>
|
|
60
|
+
```
|
|
61
|
+
<Tip>
|
|
62
|
+
For more control over connection details (like headers for SSE, environment variables for Stdio), you can instantiate the specific `ClientTransport` class yourself and pass it to the `Client`. See the [Transports](/clients/transports) page for details.
|
|
63
|
+
</Tip>
|
|
64
|
+
|
|
65
|
+
## Client Usage
|
|
66
|
+
|
|
67
|
+
### Connection Lifecycle
|
|
68
|
+
|
|
69
|
+
The client operates asynchronously and must be used within an `async with` block. This context manager handles establishing the connection, initializing the MCP session, and cleaning up resources upon exit.
|
|
70
|
+
|
|
71
|
+
```python
|
|
72
|
+
import asyncio
|
|
73
|
+
from fastmcp import Client
|
|
74
|
+
|
|
75
|
+
client = Client("my_mcp_server.py") # Assumes my_mcp_server.py exists
|
|
76
|
+
|
|
77
|
+
async def main():
|
|
78
|
+
# Connection is established here
|
|
79
|
+
async with client:
|
|
80
|
+
print(f"Client connected: {client.is_connected()}")
|
|
81
|
+
|
|
82
|
+
# Make MCP calls within the context
|
|
83
|
+
tools = await client.list_tools()
|
|
84
|
+
print(f"Available tools: {tools}")
|
|
85
|
+
|
|
86
|
+
if any(tool.name == "greet" for tool in tools):
|
|
87
|
+
result = await client.call_tool("greet", {"name": "World"})
|
|
88
|
+
print(f"Greet result: {result}")
|
|
89
|
+
|
|
90
|
+
# Connection is closed automatically here
|
|
91
|
+
print(f"Client connected: {client.is_connected()}")
|
|
92
|
+
|
|
93
|
+
if __name__ == "__main__":
|
|
94
|
+
asyncio.run(main())
|
|
95
|
+
```
|
|
96
|
+
|
|
97
|
+
You can make multiple calls to the server within the same `async with` block using the established session.
|
|
98
|
+
|
|
99
|
+
### Client Methods
|
|
100
|
+
|
|
101
|
+
The `Client` provides methods corresponding to standard MCP requests:
|
|
102
|
+
|
|
103
|
+
#### Tool Operations
|
|
104
|
+
|
|
105
|
+
* **`list_tools()`**: Retrieves a list of tools available on the server.
|
|
106
|
+
```python
|
|
107
|
+
tools = await client.list_tools()
|
|
108
|
+
# tools -> list[mcp.types.Tool]
|
|
109
|
+
```
|
|
110
|
+
* **`call_tool(name: str, arguments: dict[str, Any] | None = None)`**: Executes a tool on the server.
|
|
111
|
+
```python
|
|
112
|
+
result = await client.call_tool("add", {"a": 5, "b": 3})
|
|
113
|
+
# result -> list[mcp.types.TextContent | mcp.types.ImageContent | ...]
|
|
114
|
+
print(result[0].text) # Assuming TextContent, e.g., '8'
|
|
115
|
+
```
|
|
116
|
+
* Arguments are passed as a dictionary. FastMCP servers automatically handle JSON string parsing for complex types if needed.
|
|
117
|
+
* Returns a list of content objects (usually `TextContent` or `ImageContent`).
|
|
118
|
+
|
|
119
|
+
#### Resource Operations
|
|
120
|
+
|
|
121
|
+
* **`list_resources()`**: Retrieves a list of static resources.
|
|
122
|
+
```python
|
|
123
|
+
resources = await client.list_resources()
|
|
124
|
+
# resources -> list[mcp.types.Resource]
|
|
125
|
+
```
|
|
126
|
+
* **`list_resource_templates()`**: Retrieves a list of resource templates.
|
|
127
|
+
```python
|
|
128
|
+
templates = await client.list_resource_templates()
|
|
129
|
+
# templates -> list[mcp.types.ResourceTemplate]
|
|
130
|
+
```
|
|
131
|
+
* **`read_resource(uri: str | AnyUrl)`**: Reads the content of a resource or a resolved template.
|
|
132
|
+
```python
|
|
133
|
+
# Read a static resource
|
|
134
|
+
readme_content = await client.read_resource("file:///path/to/README.md")
|
|
135
|
+
# readme_content -> list[mcp.types.TextResourceContents | mcp.types.BlobResourceContents]
|
|
136
|
+
print(readme_content[0].text) # Assuming text
|
|
137
|
+
|
|
138
|
+
# Read a resource generated from a template
|
|
139
|
+
weather_content = await client.read_resource("data://weather/london")
|
|
140
|
+
print(weather_content[0].text) # Assuming text JSON
|
|
141
|
+
```
|
|
142
|
+
|
|
143
|
+
#### Prompt Operations
|
|
144
|
+
|
|
145
|
+
* **`list_prompts()`**: Retrieves available prompt templates.
|
|
146
|
+
* **`get_prompt(name: str, arguments: dict[str, Any] | None = None)`**: Retrieves a rendered prompt message list.
|
|
147
|
+
|
|
148
|
+
### Callbacks
|
|
149
|
+
|
|
150
|
+
MCP allows servers to make requests *back* to the client for certain capabilities. The `Client` constructor accepts callback functions to handle these server requests:
|
|
151
|
+
|
|
152
|
+
#### Roots
|
|
153
|
+
|
|
154
|
+
* **`roots: RootsList | RootsHandler | None`**: Provides the server with a list of root directories the client grants access to. This can be a static list or a function that dynamically determines roots.
|
|
155
|
+
```python
|
|
156
|
+
from pathlib import Path
|
|
157
|
+
from fastmcp.client.roots import RootsHandler, RootsList
|
|
158
|
+
from mcp.shared.context import RequestContext # For type hint
|
|
159
|
+
|
|
160
|
+
# Option 1: Static list
|
|
161
|
+
static_roots: RootsList = [str(Path.home() / "Documents")]
|
|
162
|
+
|
|
163
|
+
# Option 2: Dynamic function
|
|
164
|
+
def dynamic_roots_handler(context: RequestContext) -> RootsList:
|
|
165
|
+
# Logic to determine accessible roots based on context
|
|
166
|
+
print(f"Server requested roots (Request ID: {context.request_id})")
|
|
167
|
+
return [str(Path.home() / "Downloads")]
|
|
168
|
+
|
|
169
|
+
client_with_roots = Client(
|
|
170
|
+
"my_server.py",
|
|
171
|
+
roots=dynamic_roots_handler # or roots=static_roots
|
|
172
|
+
)
|
|
173
|
+
|
|
174
|
+
# Tell the server the roots might have changed (if needed)
|
|
175
|
+
# async with client_with_roots:
|
|
176
|
+
# await client_with_roots.send_roots_list_changed()
|
|
177
|
+
```
|
|
178
|
+
See `fastmcp.client.roots` for helpers.
|
|
179
|
+
|
|
180
|
+
#### LLM Sampling
|
|
181
|
+
|
|
182
|
+
* **`sampling_handler: SamplingHandler | None`**: Handles `sampling/createMessage` requests from the server. This callback receives messages from the server and should return an LLM completion.
|
|
183
|
+
```python
|
|
184
|
+
from fastmcp.client.sampling import SamplingHandler, MessageResult
|
|
185
|
+
from mcp.types import SamplingMessage, SamplingParams, TextContent
|
|
186
|
+
from mcp.shared.context import RequestContext # For type hint
|
|
187
|
+
|
|
188
|
+
async def my_llm_handler(
|
|
189
|
+
messages: list[SamplingMessage],
|
|
190
|
+
params: SamplingParams,
|
|
191
|
+
context: RequestContext
|
|
192
|
+
) -> str | MessageResult:
|
|
193
|
+
print(f"Server requested sampling (Request ID: {context.request_id})")
|
|
194
|
+
# In a real scenario, call your LLM API here
|
|
195
|
+
last_user_message = next((m for m in reversed(messages) if m.role == 'user'), None)
|
|
196
|
+
prompt = last_user_message.content.text if last_user_message and isinstance(last_user_message.content, TextContent) else "Default prompt"
|
|
197
|
+
|
|
198
|
+
# Simulate LLM response
|
|
199
|
+
response_text = f"LLM processed: {prompt[:50]}..."
|
|
200
|
+
# Return simple string (becomes TextContent) or a MessageResult object
|
|
201
|
+
return response_text
|
|
202
|
+
|
|
203
|
+
client_with_sampling = Client(
|
|
204
|
+
"my_server.py",
|
|
205
|
+
sampling_handler=my_llm_handler
|
|
206
|
+
)
|
|
207
|
+
```
|
|
208
|
+
See `fastmcp.client.sampling` for helpers.
|
|
209
|
+
|
|
210
|
+
#### Logging
|
|
211
|
+
|
|
212
|
+
* **`log_handler: LoggingFnT | None`**: Receives log messages sent from the server (`ctx.info`, `ctx.error`, etc.).
|
|
213
|
+
```python
|
|
214
|
+
from mcp.client.session import LoggingFnT, LogLevel
|
|
215
|
+
|
|
216
|
+
def my_log_handler(level: LogLevel, message: str, logger_name: str | None):
|
|
217
|
+
print(f"[Server Log - {level.upper()}] {logger_name or 'default'}: {message}")
|
|
218
|
+
|
|
219
|
+
client_with_logging = Client(
|
|
220
|
+
"my_server.py",
|
|
221
|
+
log_handler=my_log_handler
|
|
222
|
+
)
|
|
223
|
+
```
|
|
224
|
+
|
|
225
|
+
|
|
226
|
+
### Error Handling
|
|
227
|
+
|
|
228
|
+
When a `call_tool` request results in an error on the server (e.g., the tool function raised an exception), the `client.call_tool()` method will raise a `fastmcp.client.ClientError`.
|
|
229
|
+
|
|
230
|
+
```python
|
|
231
|
+
async def safe_call_tool():
|
|
232
|
+
async with client:
|
|
233
|
+
try:
|
|
234
|
+
# Assume 'divide' tool exists and might raise ZeroDivisionError
|
|
235
|
+
result = await client.call_tool("divide", {"a": 10, "b": 0})
|
|
236
|
+
print(f"Result: {result}")
|
|
237
|
+
except ClientError as e:
|
|
238
|
+
print(f"Tool call failed: {e}")
|
|
239
|
+
except ConnectionError as e:
|
|
240
|
+
print(f"Connection failed: {e}")
|
|
241
|
+
except Exception as e:
|
|
242
|
+
print(f"An unexpected error occurred: {e}")
|
|
243
|
+
|
|
244
|
+
# Example Output if division by zero occurs:
|
|
245
|
+
# Tool call failed: Division by zero is not allowed.
|
|
246
|
+
```
|
|
247
|
+
|
|
248
|
+
Other errors, like connection failures, will raise standard Python exceptions (e.g., `ConnectionError`, `TimeoutError`).
|
|
249
|
+
|
|
250
|
+
<Tip>
|
|
251
|
+
The client transport often has its own error-handling mechanisms, so you can not always trap errors like those raised by `call_tool` outside of the `async with` block. Instead, you can call `call_tools(..., return_raw_result=True)` to get the raw result object and handle errors yourself by checking its `isError` attribute.
|
|
252
|
+
</Tip>
|