FastMCP Tests
Running Tests
Test Organization
Our test organization mirrors thesrc/
directory structure, creating a predictable mapping between code and tests. When you’re working on src/fastmcp/server/auth.py
, you’ll find its tests in tests/server/test_auth.py
. In rare cases tests are split further - for example, the OpenAPI tests are so comprehensive they’re split across multiple files.
Test Markers
We use pytest markers to categorize tests that require special resources or take longer to run:Writing Tests
Test Requirements
Following these practices creates maintainable, debuggable test suites that serve as both documentation and regression protection.Single Behavior Per Test
Each test should verify exactly one behavior. When it fails, you need to know immediately what broke. A test that checks five things gives you five potential failure points to investigate. A test that checks one thing points directly to the problem.Self-Contained Setup
Every test must create its own setup. Tests should be runnable in any order, in parallel, or in isolation. When a test fails, you should be able to run just that test to reproduce the issue.Clear Intent
Test names and assertions should make the verified behavior obvious. A developer reading your test should understand what feature it validates and how that feature should behave.Using Fixtures
Use fixtures to create reusable data, server configurations, or other resources for your tests. Note that you should not open FastMCP clients in your fixtures as it can create hard-to-diagnose issues with event loops.Effective Assertions
Assertions should be specific and provide context on failure. When a test fails during CI, the assertion message should tell you exactly what went wrong.Inline Snapshots
FastMCP usesinline-snapshot
for testing complex data structures. On first run of pytest --inline-snapshot=create
with an empty snapshot()
, pytest will auto-populate the expected value. To update snapshots after intentional changes, run pytest --inline-snapshot=fix
. This is particularly useful for testing JSON schemas and API responses.
In-Memory Testing
FastMCP uses in-memory transport for testing, where servers and clients communicate directly. The majority of functionality can be tested in a deterministic fashion this way. We use more complex setups only when testing transports themselves. The in-memory transport runs the real MCP protocol implementation without network overhead. Instead of deploying your server or managing network connections, you pass your server instance directly to the client. Everything runs in the same Python process - you can set breakpoints anywhere and step through with your debugger.Mocking External Dependencies
FastMCP servers are standard Python objects, so you can mock external dependencies using your preferred approach:Testing Network Transports
While in-memory testing covers most unit testing needs, you’ll occasionally need to test actual network transports. Use therun_server_in_process
utility to spawn a server in a separate process for testing:
run_server_in_process
utility handles server lifecycle, port allocation, and cleanup automatically. This pattern is essential for testing transport-specific behavior like timeouts, headers, and authentication. Note that FastMCP often uses the client_process
marker to isolate tests that spawn processes, as they can create contention in CI.
Documentation Testing
Documentation requires the same validation as code. Thejust docs
command launches a local Mintlify server that renders your documentation exactly as users will see it: