diff --git a/.github/actions/conformance/client.py b/.github/actions/conformance/client.py index 4f3a93978b..2d2acf9304 100644 --- a/.github/actions/conformance/client.py +++ b/.github/actions/conformance/client.py @@ -36,9 +36,10 @@ from urllib.parse import parse_qs, urlparse import httpx +import mcp_types as types +from mcp_types.version import MODERN_PROTOCOL_VERSIONS from pydantic import AnyUrl -from mcp import types from mcp.client.auth import OAuthClientProvider, TokenStorage from mcp.client.auth.extensions.client_credentials import ( ClientCredentialsOAuthProvider, @@ -49,7 +50,6 @@ from mcp.client.context import ClientRequestContext from mcp.client.streamable_http import streamable_http_client from mcp.shared.auth import AuthorizationCodeResult, OAuthClientInformationFull, OAuthClientMetadata, OAuthToken -from mcp.shared.version import MODERN_PROTOCOL_VERSIONS # Set up logging to stderr (stdout is for conformance test output) logging.basicConfig( diff --git a/.github/workflows/publish-pypi.yml b/.github/workflows/publish-pypi.yml index 1dc909b00e..d77820b1d1 100644 --- a/.github/workflows/publish-pypi.yml +++ b/.github/workflows/publish-pypi.yml @@ -27,7 +27,9 @@ jobs: run: uv python install 3.12 - name: Build - run: uv build + run: | + uv build --package mcp + uv build --package mcp-types - name: Upload artifacts uses: actions/upload-artifact@043fb46d1a93c77aae656e7c1c64a875d1fc6a0a # v7.0.1 diff --git a/README.v2.md b/README.v2.md index 6eb869a8a4..b9896d9412 100644 --- a/README.v2.md +++ b/README.v2.md @@ -419,10 +419,10 @@ For full control over tool responses including the `_meta` field (for passing da from typing import Annotated +from mcp_types import CallToolResult, TextContent from pydantic import BaseModel from mcp.server.mcpserver import MCPServer -from mcp.types import CallToolResult, TextContent mcp = MCPServer("CallToolResult Example") @@ -739,9 +739,10 @@ uv run completion-client import asyncio import os +from mcp_types import PromptReference, ResourceTemplateReference + from mcp import ClientSession, StdioServerParameters from mcp.client.stdio import stdio_client -from mcp.types import PromptReference, ResourceTemplateReference # Create server parameters for stdio connection server_params = StdioServerParameters( @@ -828,11 +829,11 @@ like OAuth flows, credential collection, or payment processing. import uuid +from mcp_types import ElicitRequestURLParams from pydantic import BaseModel, Field from mcp.server.mcpserver import Context, MCPServer from mcp.shared.exceptions import UrlElicitationRequiredError -from mcp.types import ElicitRequestURLParams mcp = MCPServer(name="Elicitation Example") @@ -937,8 +938,9 @@ Tools can interact with LLMs through sampling (generating text): ```python +from mcp_types import SamplingMessage, TextContent + from mcp.server.mcpserver import Context, MCPServer -from mcp.types import SamplingMessage, TextContent mcp = MCPServer(name="Sampling Example") @@ -1647,8 +1649,9 @@ from collections.abc import AsyncIterator from contextlib import asynccontextmanager from typing import TypedDict +import mcp_types as types + import mcp.server.stdio -from mcp import types from mcp.server import Server, ServerRequestContext @@ -1759,8 +1762,9 @@ uv run examples/snippets/servers/lowlevel/basic.py import asyncio +import mcp_types as types + import mcp.server.stdio -from mcp import types from mcp.server import Server, ServerRequestContext @@ -1836,8 +1840,9 @@ uv run examples/snippets/servers/lowlevel/structured_output.py import asyncio import json +import mcp_types as types + import mcp.server.stdio -from mcp import types from mcp.server import Server, ServerRequestContext @@ -1928,8 +1933,9 @@ uv run examples/snippets/servers/lowlevel/direct_call_tool_result.py import asyncio +import mcp_types as types + import mcp.server.stdio -from mcp import types from mcp.server import Server, ServerRequestContext @@ -1999,7 +2005,8 @@ For servers that need to handle large datasets, the low-level server provides pa ```python """Example of implementing pagination with the low-level MCP server.""" -from mcp import types +import mcp_types as types + from mcp.server import Server, ServerRequestContext # Sample data to paginate @@ -2045,9 +2052,10 @@ _Full example: [examples/snippets/servers/pagination_example.py](https://github. import asyncio +from mcp_types import PaginatedRequestParams, Resource + from mcp.client.session import ClientSession from mcp.client.stdio import StdioServerParameters, stdio_client -from mcp.types import PaginatedRequestParams, Resource async def list_all_resources() -> None: @@ -2107,7 +2115,9 @@ uv run client import asyncio import os -from mcp import ClientSession, StdioServerParameters, types +import mcp_types as types + +from mcp import ClientSession, StdioServerParameters from mcp.client.context import ClientRequestContext from mcp.client.stdio import stdio_client @@ -2417,7 +2427,9 @@ When calling tools through MCP, the `CallToolResult` object contains the tool's import asyncio -from mcp import ClientSession, StdioServerParameters, types +import mcp_types as types + +from mcp import ClientSession, StdioServerParameters from mcp.client.stdio import stdio_client diff --git a/docs/migration.md b/docs/migration.md index 1c965562d1..e977ce4a21 100644 --- a/docs/migration.md +++ b/docs/migration.md @@ -209,9 +209,38 @@ named `mcp.os.win32.utilities` (was `client.stdio.win32`). The WebSocket transport has been removed: `mcp.client.websocket.websocket_client`, `mcp.server.websocket.websocket_server`, and the `ws` optional dependency extra (`mcp[ws]`) no longer exist. WebSocket was never part of the MCP specification. Use the streamable HTTP transport instead (`mcp.client.streamable_http.streamable_http_client` on the client, `streamable_http_app()` on the server), which supports bidirectional communication with server-to-client streaming over standard HTTP. +### `mcp.types` moved to the `mcp-types` package + +The protocol wire types now live in a standalone distribution, `mcp-types`, imported as +`mcp_types`. It depends only on `pydantic`, so code that just needs to (de)serialize MCP +traffic can install it without the full SDK. The `mcp` package depends on `mcp-types` and +continues to re-export the type names at the top level, so `from mcp import Tool` is +unchanged. Only the `mcp.types` submodule and `mcp.shared.version` were removed. + +**Why:** keeping the wire types in their own package lets tooling and lightweight clients +depend on the protocol schema without pulling in `httpx`, `starlette`, `uvicorn`, and the +rest of the server/transport stack. + +**Before (v1):** + +```python +from mcp.types import Tool, CallToolResult +from mcp.shared.version import LATEST_PROTOCOL_VERSION +``` + +**After (v2):** + +```python +from mcp_types import Tool, CallToolResult +from mcp_types.version import LATEST_PROTOCOL_VERSION + +# Top-level re-exports are unchanged: +from mcp import Tool, CallToolResult +``` + ### Removed type aliases and classes -The following deprecated type aliases and classes have been removed from `mcp.types`: +The following deprecated type aliases and classes have been removed from `mcp_types`: | Removed | Replacement | |---------|-------------| @@ -231,13 +260,13 @@ from mcp.types import Content, ResourceReference, Cursor **After (v2):** ```python -from mcp.types import ContentBlock, ResourceTemplateReference +from mcp_types import ContentBlock, ResourceTemplateReference # Use `str` instead of `Cursor` for pagination cursors ``` ### Field names changed from camelCase to snake_case -All Pydantic model fields in `mcp.types` now use snake_case names for Python attribute access. The JSON wire format is unchanged — serialization still uses camelCase via Pydantic aliases. +All Pydantic model fields in `mcp_types` now use snake_case names for Python attribute access. The JSON wire format is unchanged — serialization still uses camelCase via Pydantic aliases. **Before (v1):** @@ -287,7 +316,7 @@ Results returned from server handlers are now validated against the negotiated p ### Client validates inbound traffic against the protocol schema -`ClientSession` now validates server requests, notifications, and results against the negotiated protocol version's schema before parsing them into `mcp.types` models. Spec-invalid server output that the previous monolith parse tolerated may now raise `pydantic.ValidationError` from `list_tools()`, `call_tool()`, and similar calls. `_meta` remains the sanctioned place for result extras (and `experimental` for capability extras). +`ClientSession` now validates server requests, notifications, and results against the negotiated protocol version's schema before parsing them into `mcp_types` models. Spec-invalid server output that the previous monolith parse tolerated may now raise `pydantic.ValidationError` from `list_tools()`, `call_tool()`, and similar calls. `_meta` remains the sanctioned place for result extras (and `experimental` for capability extras). ### `args` parameter removed from `ClientSessionGroup.call_tool()` @@ -326,7 +355,7 @@ result = await session.list_tools(cursor="next_page_token") **After (v2):** ```python -from mcp.types import PaginatedRequestParams +from mcp_types import PaginatedRequestParams result = await session.list_resources(params=PaginatedRequestParams(cursor="next_page_token")) result = await session.list_tools(params=PaginatedRequestParams(cursor="next_page_token")) @@ -415,7 +444,7 @@ raise McpError(ErrorData(code=INVALID_REQUEST, message="bad input")) ```python from mcp.shared.exceptions import MCPError -from mcp.types import INVALID_REQUEST +from mcp_types import INVALID_REQUEST raise MCPError(INVALID_REQUEST, "bad input") # or, if you already have an ErrorData: @@ -590,7 +619,7 @@ In v2, the lowlevel `Server` supports arbitrary request handlers directly via `a ```python from mcp.server import ServerRequestContext -from mcp.types import EmptyResult, SetLevelRequestParams, SubscribeRequestParams +from mcp_types import EmptyResult, SetLevelRequestParams, SubscribeRequestParams async def handle_set_logging_level(ctx: ServerRequestContext, params: SetLevelRequestParams) -> EmptyResult: @@ -663,7 +692,7 @@ actual_notification = notification.root **After (v2):** ```python -from mcp.types import client_request_adapter, server_notification_adapter +from mcp_types import client_request_adapter, server_notification_adapter # Using TypeAdapter.validate_python() request = client_request_adapter.validate_python(data) @@ -701,7 +730,7 @@ await session.send_request(PingRequest(), EmptyResult) | `ServerResult` | `server_result_adapter` | | `JSONRPCMessage` | `jsonrpc_message_adapter` | -All adapters are exported from `mcp.types`. +All adapters are exported from `mcp_types`. ### `RequestParams.Meta` replaced with `RequestParamsMeta` TypedDict @@ -881,7 +910,7 @@ resource = Resource(name="test", uri=AnyUrl("users/me")) # Would fail validatio **After (v2):** ```python -from mcp.types import Resource +from mcp_types import Resource # Plain strings accepted resource = Resource(name="test", uri="users/me") # Works @@ -1038,7 +1067,7 @@ async def handle_call_tool(name: str, arguments: dict): ```python from mcp.server import Server, ServerRequestContext -from mcp.types import ( +from mcp_types import ( CallToolRequestParams, CallToolResult, ListToolsResult, @@ -1087,13 +1116,13 @@ All handlers receive `ctx: ServerRequestContext` as the first argument. The seco | `@server.progress_notification()` | `on_progress` | `ProgressNotificationParams` | `None` | | — | `on_roots_list_changed` | `NotificationParams \| None` | `None` | -All `params` and return types are importable from `mcp.types`. +All `params` and return types are importable from `mcp_types`. **Notification handlers:** ```python from mcp.server import Server, ServerRequestContext -from mcp.types import ProgressNotificationParams +from mcp_types import ProgressNotificationParams async def handle_progress(ctx: ServerRequestContext, params: ProgressNotificationParams) -> None: @@ -1218,7 +1247,7 @@ async def handle_call_tool(name: str, arguments: dict): ```python from mcp.server import ServerRequestContext -from mcp.types import CallToolRequestParams, CallToolResult, TextContent +from mcp_types import CallToolRequestParams, CallToolResult, TextContent async def handle_call_tool(ctx: ServerRequestContext, params: CallToolRequestParams) -> CallToolResult: @@ -1290,7 +1319,7 @@ Behavior changes: ### Experimental Tasks support removed -Tasks (SEP-1686) have been removed from the MCP specification and are no longer part of this SDK. The `mcp.client.experimental`, `mcp.server.experimental`, `mcp.shared.experimental`, and `mcp.server.lowlevel.experimental` modules have been removed, along with the `experimental` properties on `ClientSession`, `ServerSession`, `Server`, and `ServerRequestContext`. The corresponding `Task*` types remain in `mcp.types` as types-only definitions. +Tasks (SEP-1686) have been removed from the MCP specification and are no longer part of this SDK. The `mcp.client.experimental`, `mcp.server.experimental`, `mcp.shared.experimental`, and `mcp.server.lowlevel.experimental` modules have been removed, along with the `experimental` properties on `ClientSession`, `ServerSession`, `Server`, and `ServerRequestContext`. The corresponding `Task*` types remain in `mcp_types` as types-only definitions. Tasks are expected to return as a separate MCP extension in a future release. @@ -1358,7 +1387,7 @@ In v1, MCP protocol types were configured with `extra="allow"`: unknown fields p In v2, MCP types silently ignore extra fields. Unknown constructor keyword arguments and unknown keys in wire data are dropped during validation — no error is raised, and the values do not round-trip: ```python -from mcp.types import CallToolRequestParams +from mcp_types import CallToolRequestParams params = CallToolRequestParams( name="my_tool", @@ -1404,7 +1433,7 @@ Under OIDC, omitting `application_type` defaults to `"web"`, which an authorizat ### 2025-11-25 and 2026-07-28 protocol fields modeled -`mcp.types` models the 2025-11-25 and 2026-07-28 protocol fields (e.g. `resultType`, `ttlMs`/`cacheScope` on cacheable results, `inputResponses`/`requestState` on retried requests), so inbound payloads carrying these keys parse into typed fields and round-trip. `ttlMs`/`cacheScope` default to `0`/`"private"` (immediately stale, not shared-cacheable); `resultType` defaults to `"complete"` on concrete results (`None` on `EmptyResult`); the server strips all of them from the wire at pre-2026 versions. +`mcp_types` models the 2025-11-25 and 2026-07-28 protocol fields (e.g. `resultType`, `ttlMs`/`cacheScope` on cacheable results, `inputResponses`/`requestState` on retried requests), so inbound payloads carrying these keys parse into typed fields and round-trip. `ttlMs`/`cacheScope` default to `0`/`"private"` (immediately stale, not shared-cacheable); `resultType` defaults to `"complete"` on concrete results (`None` on `EmptyResult`); the server strips all of them from the wire at pre-2026 versions. ### `streamable_http_app()` available on lowlevel Server @@ -1412,7 +1441,7 @@ The `streamable_http_app()` method is now available directly on the lowlevel `Se ```python from mcp.server import Server, ServerRequestContext -from mcp.types import ListToolsResult, PaginatedRequestParams +from mcp_types import ListToolsResult, PaginatedRequestParams async def handle_list_tools(ctx: ServerRequestContext, params: PaginatedRequestParams | None) -> ListToolsResult: diff --git a/docs/testing.md b/docs/testing.md index c1d263b763..fcbc3a8553 100644 --- a/docs/testing.md +++ b/docs/testing.md @@ -44,7 +44,7 @@ To run the below test, you'll need to install the following dependencies: import pytest from inline_snapshot import snapshot from mcp import Client -from mcp.types import CallToolResult, TextContent +from mcp_types import CallToolResult, TextContent from server import app diff --git a/examples/mcpserver/direct_call_tool_result_return.py b/examples/mcpserver/direct_call_tool_result_return.py index 44a316bc6b..c73e6164f5 100644 --- a/examples/mcpserver/direct_call_tool_result_return.py +++ b/examples/mcpserver/direct_call_tool_result_return.py @@ -2,10 +2,10 @@ from typing import Annotated +from mcp_types import CallToolResult, TextContent from pydantic import BaseModel from mcp.server.mcpserver import MCPServer -from mcp.types import CallToolResult, TextContent mcp = MCPServer("Echo Server") diff --git a/examples/servers/everything-server/mcp_everything_server/server.py b/examples/servers/everything-server/mcp_everything_server/server.py index b12290a6d8..c43b6735c3 100644 --- a/examples/servers/everything-server/mcp_everything_server/server.py +++ b/examples/servers/everything-server/mcp_everything_server/server.py @@ -15,7 +15,7 @@ from mcp.server.mcpserver.prompts.base import UserMessage from mcp.server.streamable_http import EventCallback, EventMessage, EventStore from mcp.shared.exceptions import MCPError -from mcp.types import ( +from mcp_types import ( AudioContent, Completion, CompletionArgument, @@ -33,7 +33,7 @@ TextResourceContents, UnsubscribeRequestParams, ) -from mcp.types.jsonrpc import MISSING_REQUIRED_CLIENT_CAPABILITY +from mcp_types.jsonrpc import MISSING_REQUIRED_CLIENT_CAPABILITY from pydantic import BaseModel, Field logger = logging.getLogger(__name__) diff --git a/examples/servers/simple-pagination/mcp_simple_pagination/server.py b/examples/servers/simple-pagination/mcp_simple_pagination/server.py index c94f2ac3d1..9aca87f730 100644 --- a/examples/servers/simple-pagination/mcp_simple_pagination/server.py +++ b/examples/servers/simple-pagination/mcp_simple_pagination/server.py @@ -8,7 +8,7 @@ import anyio import click -from mcp import types +import mcp_types as types from mcp.server import Server, ServerRequestContext T = TypeVar("T") diff --git a/examples/servers/simple-prompt/mcp_simple_prompt/server.py b/examples/servers/simple-prompt/mcp_simple_prompt/server.py index 74b71b3f38..31e3eb7d76 100644 --- a/examples/servers/simple-prompt/mcp_simple_prompt/server.py +++ b/examples/servers/simple-prompt/mcp_simple_prompt/server.py @@ -1,6 +1,6 @@ import anyio import click -from mcp import types +import mcp_types as types from mcp.server import Server, ServerRequestContext diff --git a/examples/servers/simple-resource/README.md b/examples/servers/simple-resource/README.md index 7fb2ab7cdc..1d8fb7c2aa 100644 --- a/examples/servers/simple-resource/README.md +++ b/examples/servers/simple-resource/README.md @@ -22,7 +22,7 @@ Using the MCP client, you can retrieve resources like this using the STDIO trans ```python import asyncio -from mcp.types import AnyUrl +from pydantic import AnyUrl from mcp.client.session import ClientSession from mcp.client.stdio import StdioServerParameters, stdio_client diff --git a/examples/servers/simple-resource/mcp_simple_resource/server.py b/examples/servers/simple-resource/mcp_simple_resource/server.py index 8d11054145..fe9dcfb709 100644 --- a/examples/servers/simple-resource/mcp_simple_resource/server.py +++ b/examples/servers/simple-resource/mcp_simple_resource/server.py @@ -2,7 +2,7 @@ import anyio import click -from mcp import types +import mcp_types as types from mcp.server import Server, ServerRequestContext SAMPLE_RESOURCES = { diff --git a/examples/servers/simple-streamablehttp-stateless/mcp_simple_streamablehttp_stateless/server.py b/examples/servers/simple-streamablehttp-stateless/mcp_simple_streamablehttp_stateless/server.py index feffb057eb..9df18cc6a2 100644 --- a/examples/servers/simple-streamablehttp-stateless/mcp_simple_streamablehttp_stateless/server.py +++ b/examples/servers/simple-streamablehttp-stateless/mcp_simple_streamablehttp_stateless/server.py @@ -2,8 +2,8 @@ import anyio import click +import mcp_types as types import uvicorn -from mcp import types from mcp.server import Server, ServerRequestContext from starlette.middleware.cors import CORSMiddleware diff --git a/examples/servers/simple-streamablehttp/mcp_simple_streamablehttp/event_store.py b/examples/servers/simple-streamablehttp/mcp_simple_streamablehttp/event_store.py index 3501fa47ce..c9369cfc2c 100644 --- a/examples/servers/simple-streamablehttp/mcp_simple_streamablehttp/event_store.py +++ b/examples/servers/simple-streamablehttp/mcp_simple_streamablehttp/event_store.py @@ -10,7 +10,7 @@ from uuid import uuid4 from mcp.server.streamable_http import EventCallback, EventId, EventMessage, EventStore, StreamId -from mcp.types import JSONRPCMessage +from mcp_types import JSONRPCMessage logger = logging.getLogger(__name__) diff --git a/examples/servers/simple-streamablehttp/mcp_simple_streamablehttp/server.py b/examples/servers/simple-streamablehttp/mcp_simple_streamablehttp/server.py index 9ab5b4d1f6..e650b35732 100644 --- a/examples/servers/simple-streamablehttp/mcp_simple_streamablehttp/server.py +++ b/examples/servers/simple-streamablehttp/mcp_simple_streamablehttp/server.py @@ -2,8 +2,8 @@ import anyio import click +import mcp_types as types import uvicorn -from mcp import types from mcp.server import Server, ServerRequestContext from starlette.middleware.cors import CORSMiddleware diff --git a/examples/servers/simple-tool/mcp_simple_tool/server.py b/examples/servers/simple-tool/mcp_simple_tool/server.py index 226058b955..b16249e068 100644 --- a/examples/servers/simple-tool/mcp_simple_tool/server.py +++ b/examples/servers/simple-tool/mcp_simple_tool/server.py @@ -1,6 +1,6 @@ import anyio import click -from mcp import types +import mcp_types as types from mcp.server import Server, ServerRequestContext from mcp.shared._httpx_utils import create_mcp_http_client diff --git a/examples/servers/sse-polling-demo/mcp_sse_polling_demo/event_store.py b/examples/servers/sse-polling-demo/mcp_sse_polling_demo/event_store.py index c77bddef36..e2cca4a2eb 100644 --- a/examples/servers/sse-polling-demo/mcp_sse_polling_demo/event_store.py +++ b/examples/servers/sse-polling-demo/mcp_sse_polling_demo/event_store.py @@ -10,7 +10,7 @@ from uuid import uuid4 from mcp.server.streamable_http import EventCallback, EventId, EventMessage, EventStore, StreamId -from mcp.types import JSONRPCMessage +from mcp_types import JSONRPCMessage logger = logging.getLogger(__name__) diff --git a/examples/servers/sse-polling-demo/mcp_sse_polling_demo/server.py b/examples/servers/sse-polling-demo/mcp_sse_polling_demo/server.py index 54ed960de3..7d2c60fa32 100644 --- a/examples/servers/sse-polling-demo/mcp_sse_polling_demo/server.py +++ b/examples/servers/sse-polling-demo/mcp_sse_polling_demo/server.py @@ -16,8 +16,8 @@ import anyio import click +import mcp_types as types import uvicorn -from mcp import types from mcp.server import Server, ServerRequestContext from .event_store import InMemoryEventStore diff --git a/examples/servers/structured-output-lowlevel/mcp_structured_output_lowlevel/__main__.py b/examples/servers/structured-output-lowlevel/mcp_structured_output_lowlevel/__main__.py index 95fb908540..393ff7a5a0 100644 --- a/examples/servers/structured-output-lowlevel/mcp_structured_output_lowlevel/__main__.py +++ b/examples/servers/structured-output-lowlevel/mcp_structured_output_lowlevel/__main__.py @@ -10,8 +10,9 @@ import random from datetime import datetime +import mcp_types as types + import mcp.server.stdio -from mcp import types from mcp.server import Server, ServerRequestContext diff --git a/examples/snippets/clients/completion_client.py b/examples/snippets/clients/completion_client.py index dc0c1b4f72..52957d97d8 100644 --- a/examples/snippets/clients/completion_client.py +++ b/examples/snippets/clients/completion_client.py @@ -5,9 +5,10 @@ import asyncio import os +from mcp_types import PromptReference, ResourceTemplateReference + from mcp import ClientSession, StdioServerParameters from mcp.client.stdio import stdio_client -from mcp.types import PromptReference, ResourceTemplateReference # Create server parameters for stdio connection server_params = StdioServerParameters( diff --git a/examples/snippets/clients/pagination_client.py b/examples/snippets/clients/pagination_client.py index b9b8c23ae7..00663ef038 100644 --- a/examples/snippets/clients/pagination_client.py +++ b/examples/snippets/clients/pagination_client.py @@ -2,9 +2,10 @@ import asyncio +from mcp_types import PaginatedRequestParams, Resource + from mcp.client.session import ClientSession from mcp.client.stdio import StdioServerParameters, stdio_client -from mcp.types import PaginatedRequestParams, Resource async def list_all_resources() -> None: diff --git a/examples/snippets/clients/parsing_tool_results.py b/examples/snippets/clients/parsing_tool_results.py index b166406774..f9aade41e3 100644 --- a/examples/snippets/clients/parsing_tool_results.py +++ b/examples/snippets/clients/parsing_tool_results.py @@ -2,7 +2,9 @@ import asyncio -from mcp import ClientSession, StdioServerParameters, types +import mcp_types as types + +from mcp import ClientSession, StdioServerParameters from mcp.client.stdio import stdio_client diff --git a/examples/snippets/clients/stdio_client.py b/examples/snippets/clients/stdio_client.py index 3f7c4b981b..6fff083853 100644 --- a/examples/snippets/clients/stdio_client.py +++ b/examples/snippets/clients/stdio_client.py @@ -5,7 +5,9 @@ import asyncio import os -from mcp import ClientSession, StdioServerParameters, types +import mcp_types as types + +from mcp import ClientSession, StdioServerParameters from mcp.client.context import ClientRequestContext from mcp.client.stdio import stdio_client diff --git a/examples/snippets/clients/url_elicitation_client.py b/examples/snippets/clients/url_elicitation_client.py index 2aecbeeee6..de962eb718 100644 --- a/examples/snippets/clients/url_elicitation_client.py +++ b/examples/snippets/clients/url_elicitation_client.py @@ -28,11 +28,13 @@ from typing import Any from urllib.parse import urlparse -from mcp import ClientSession, types +import mcp_types as types +from mcp_types import URL_ELICITATION_REQUIRED + +from mcp import ClientSession from mcp.client.context import ClientRequestContext from mcp.client.sse import sse_client from mcp.shared.exceptions import MCPError, UrlElicitationRequiredError -from mcp.types import URL_ELICITATION_REQUIRED async def handle_elicitation( diff --git a/examples/snippets/servers/completion.py b/examples/snippets/servers/completion.py index 47accffa3b..7fc2f20454 100644 --- a/examples/snippets/servers/completion.py +++ b/examples/snippets/servers/completion.py @@ -1,5 +1,4 @@ -from mcp.server.mcpserver import MCPServer -from mcp.types import ( +from mcp_types import ( Completion, CompletionArgument, CompletionContext, @@ -7,6 +6,8 @@ ResourceTemplateReference, ) +from mcp.server.mcpserver import MCPServer + mcp = MCPServer(name="Example") diff --git a/examples/snippets/servers/direct_call_tool_result.py b/examples/snippets/servers/direct_call_tool_result.py index 4c98c358ee..f3035338b3 100644 --- a/examples/snippets/servers/direct_call_tool_result.py +++ b/examples/snippets/servers/direct_call_tool_result.py @@ -2,10 +2,10 @@ from typing import Annotated +from mcp_types import CallToolResult, TextContent from pydantic import BaseModel from mcp.server.mcpserver import MCPServer -from mcp.types import CallToolResult, TextContent mcp = MCPServer("CallToolResult Example") diff --git a/examples/snippets/servers/elicitation.py b/examples/snippets/servers/elicitation.py index 79453f543e..97e847b510 100644 --- a/examples/snippets/servers/elicitation.py +++ b/examples/snippets/servers/elicitation.py @@ -7,11 +7,11 @@ import uuid +from mcp_types import ElicitRequestURLParams from pydantic import BaseModel, Field from mcp.server.mcpserver import Context, MCPServer from mcp.shared.exceptions import UrlElicitationRequiredError -from mcp.types import ElicitRequestURLParams mcp = MCPServer(name="Elicitation Example") diff --git a/examples/snippets/servers/lowlevel/basic.py b/examples/snippets/servers/lowlevel/basic.py index 81f40e9945..ff9b0a2c49 100644 --- a/examples/snippets/servers/lowlevel/basic.py +++ b/examples/snippets/servers/lowlevel/basic.py @@ -4,8 +4,9 @@ import asyncio +import mcp_types as types + import mcp.server.stdio -from mcp import types from mcp.server import Server, ServerRequestContext diff --git a/examples/snippets/servers/lowlevel/direct_call_tool_result.py b/examples/snippets/servers/lowlevel/direct_call_tool_result.py index 7e8fc4dcb3..4d6607d2ff 100644 --- a/examples/snippets/servers/lowlevel/direct_call_tool_result.py +++ b/examples/snippets/servers/lowlevel/direct_call_tool_result.py @@ -4,8 +4,9 @@ import asyncio +import mcp_types as types + import mcp.server.stdio -from mcp import types from mcp.server import Server, ServerRequestContext diff --git a/examples/snippets/servers/lowlevel/lifespan.py b/examples/snippets/servers/lowlevel/lifespan.py index bcd96c8935..46db9ecc07 100644 --- a/examples/snippets/servers/lowlevel/lifespan.py +++ b/examples/snippets/servers/lowlevel/lifespan.py @@ -6,8 +6,9 @@ from contextlib import asynccontextmanager from typing import TypedDict +import mcp_types as types + import mcp.server.stdio -from mcp import types from mcp.server import Server, ServerRequestContext diff --git a/examples/snippets/servers/lowlevel/structured_output.py b/examples/snippets/servers/lowlevel/structured_output.py index f93c8875fd..84e411ff55 100644 --- a/examples/snippets/servers/lowlevel/structured_output.py +++ b/examples/snippets/servers/lowlevel/structured_output.py @@ -5,8 +5,9 @@ import asyncio import json +import mcp_types as types + import mcp.server.stdio -from mcp import types from mcp.server import Server, ServerRequestContext diff --git a/examples/snippets/servers/pagination_example.py b/examples/snippets/servers/pagination_example.py index bcd0ffb106..4f7435acf6 100644 --- a/examples/snippets/servers/pagination_example.py +++ b/examples/snippets/servers/pagination_example.py @@ -1,6 +1,7 @@ """Example of implementing pagination with the low-level MCP server.""" -from mcp import types +import mcp_types as types + from mcp.server import Server, ServerRequestContext # Sample data to paginate diff --git a/examples/snippets/servers/sampling.py b/examples/snippets/servers/sampling.py index a3f6d5c7bd..83ec5066dd 100644 --- a/examples/snippets/servers/sampling.py +++ b/examples/snippets/servers/sampling.py @@ -1,5 +1,6 @@ +from mcp_types import SamplingMessage, TextContent + from mcp.server.mcpserver import Context, MCPServer -from mcp.types import SamplingMessage, TextContent mcp = MCPServer(name="Sampling Example") diff --git a/pyproject.toml b/pyproject.toml index a36d152dc4..830fc9963c 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -1,6 +1,6 @@ [project] name = "mcp" -dynamic = ["version"] +dynamic = ["version", "dependencies"] description = "Model Context Protocol SDK" readme = "README.v2.md" requires-python = ">=3.10" @@ -24,29 +24,6 @@ classifiers = [ "Programming Language :: Python :: 3.13", "Programming Language :: Python :: 3.14", ] -dependencies = [ - # anyio < 4.10 triggers a compile-time SyntaxWarning on Python 3.14 (PEP 765, - # "'return' in a 'finally' block"); for stdio servers it lands on the child's - # stderr (agronholm/anyio#816, fixed in 4.10). - "anyio>=4.10; python_version >= '3.14'", - "anyio>=4.9; python_version < '3.14'", - "httpx>=0.27.1,<1.0.0", - "httpx-sse>=0.4", - "pydantic>=2.12.0", - "starlette>=0.48.0; python_version >= '3.14'", - "starlette>=0.27; python_version < '3.14'", - "python-multipart>=0.0.9", - "sse-starlette>=3.0.0", - "pydantic-settings>=2.5.2", - "uvicorn>=0.31.1; sys_platform != 'emscripten'", - "jsonschema>=4.20.0", - "pywin32>=311; sys_platform == 'win32'", - "pyjwt[crypto]>=2.10.1", - "typing-extensions>=4.13.0", - "typing-inspection>=0.4.1", - "opentelemetry-api>=1.28.0", -] - [project.optional-dependencies] rich = ["rich>=13.9.4"] cli = ["typer>=0.16.0", "python-dotenv>=1.0.0"] @@ -118,6 +95,31 @@ vcs = "git" style = "pep440" bump = true +[tool.hatch.metadata.hooks.uv-dynamic-versioning] +dependencies = [ + # anyio < 4.10 triggers a compile-time SyntaxWarning on Python 3.14 (PEP 765, + # "'return' in a 'finally' block"); for stdio servers it lands on the child's + # stderr (agronholm/anyio#816, fixed in 4.10). + "anyio>=4.10; python_version >= '3.14'", + "anyio>=4.9; python_version < '3.14'", + "httpx>=0.27.1,<1.0.0", + "httpx-sse>=0.4", + "mcp-types=={{ version }}", + "pydantic>=2.12.0", + "starlette>=0.48.0; python_version >= '3.14'", + "starlette>=0.27; python_version < '3.14'", + "python-multipart>=0.0.9", + "sse-starlette>=3.0.0", + "pydantic-settings>=2.5.2", + "uvicorn>=0.31.1; sys_platform != 'emscripten'", + "jsonschema>=4.20.0", + "pywin32>=311; sys_platform == 'win32'", + "pyjwt[crypto]>=2.10.1", + "typing-extensions>=4.13.0", + "typing-inspection>=0.4.1", + "opentelemetry-api>=1.28.0", +] + [project.urls] Homepage = "https://modelcontextprotocol.io" Documentation = "https://py.sdk.modelcontextprotocol.io/v2/" @@ -131,6 +133,7 @@ packages = ["src/mcp"] typeCheckingMode = "strict" include = [ "src/mcp", + "src/mcp-types/mcp_types", "tests", "examples/servers", "examples/snippets", @@ -179,7 +182,7 @@ max-complexity = 24 # Default is 10 [tool.ruff.lint.per-file-ignores] "__init__.py" = ["F401"] # Generated by scripts/gen_surface_types.py: raw datamodel-codegen output (TID251 lifts the repo-wide RootModel ban for these generated validators). -"src/mcp/types/v*/__init__.py" = ["D212", "E501", "I001", "TID251", "UP007", "UP037"] +"src/mcp-types/mcp_types/v*/__init__.py" = ["D212", "E501", "I001", "TID251", "UP007", "UP037"] "tests/server/mcpserver/test_func_metadata.py" = ["E501"] "tests/shared/test_progress_notifications.py" = ["PLW0603"] @@ -191,10 +194,11 @@ max-returns = 13 # Default is 6 max-statements = 102 # Default is 50 [tool.uv.workspace] -members = ["examples/clients/*", "examples/servers/*", "examples/snippets"] +members = ["src/mcp-types", "examples/clients/*", "examples/servers/*", "examples/snippets"] [tool.uv.sources] mcp = { workspace = true } +mcp-types = { workspace = true } strict-no-cover = { git = "https://github.com/pydantic/strict-no-cover" } [tool.pytest.ini_options] @@ -241,7 +245,7 @@ MD059 = false # descriptive-link-text branch = true patch = ["subprocess"] concurrency = ["multiprocessing", "thread"] -source = ["src", "tests"] +source = ["src", "src/mcp-types/mcp_types", "tests"] omit = [ "src/mcp/client/__main__.py", "src/mcp/server/__main__.py", diff --git a/scripts/gen_surface_types.py b/scripts/gen_surface_types.py index bbc5993172..df99b33ebe 100644 --- a/scripts/gen_surface_types.py +++ b/scripts/gen_surface_types.py @@ -1,7 +1,7 @@ """Regenerate the per-version wire-shape surface packages from vendored schemas. Runs `datamodel-code-generator` over each `schema/PINNED.json` entry and -writes the result to `src/mcp/types/v/__init__.py` with only the +writes the result to `src/mcp-types/mcp_types/v/__init__.py` with only the fixes the raw output needs: a small JSON pre-patch for the known `number`-as-`integer` schema.json defect, a header, full URLs for the spec's site-absolute doc links, and per-version epilogue aliases. Run with @@ -23,7 +23,7 @@ REPO_ROOT = Path(__file__).resolve().parent.parent SCHEMA_DIR = REPO_ROOT / "schema" -TYPES_DIR = REPO_ROOT / "src" / "mcp" / "types" +TYPES_DIR = REPO_ROOT / "src" / "mcp-types" / "mcp_types" # schema.ts -> schema.json renders TypeScript `number` as JSON Schema # `integer` at these sites; patch the JSON before codegen so floats validate. @@ -142,7 +142,7 @@ def run_codegen(schema_path: Path, output_path: Path) -> None: "--output", str(output_path), "--output-model-type", "pydantic_v2.BaseModel", "--target-python-version", "3.10", - "--base-class", "mcp.types._wire_base.WireModel", + "--base-class", "mcp_types._wire_base.WireModel", "--snake-case-field", "--remove-special-field-name-prefix", "--use-annotated", "--use-field-description", "--use-schema-description", "--enum-field-as-literal", "all", diff --git a/src/mcp-types/README.md b/src/mcp-types/README.md new file mode 100644 index 0000000000..910a9e8f38 --- /dev/null +++ b/src/mcp-types/README.md @@ -0,0 +1,16 @@ +# MCP Types + +The wire types for the [Model Context Protocol](https://modelcontextprotocol.io). + +This package holds the protocol message models, JSON-RPC envelope types, per-version +surface validators, and the protocol-version registry. Its only runtime dependencies are +`pydantic` and `typing-extensions`, so it can be installed on its own when you need to +(de)serialize MCP traffic without pulling in the full `mcp` SDK. + +```python +from mcp_types import Tool, CallToolRequest +from mcp_types.version import LATEST_PROTOCOL_VERSION +``` + +The `mcp` package re-exports these names, so existing `from mcp import Tool` imports +keep working. diff --git a/src/mcp/types/__init__.py b/src/mcp-types/mcp_types/__init__.py similarity index 98% rename from src/mcp/types/__init__.py rename to src/mcp-types/mcp_types/__init__.py index 491047ae74..c90062e412 100644 --- a/src/mcp/types/__init__.py +++ b/src/mcp-types/mcp_types/__init__.py @@ -4,10 +4,8 @@ https://github.com/modelcontextprotocol/modelcontextprotocol/blob/main/schema/draft/schema.json """ -from mcp.shared.version import LATEST_PROTOCOL_VERSION - # Re-export everything from _types for backward compatibility -from mcp.types._types import ( +from mcp_types._types import ( CLIENT_CAPABILITIES_META_KEY, CLIENT_INFO_META_KEY, DEFAULT_NEGOTIATED_VERSION, @@ -198,7 +196,7 @@ ) # Re-export JSONRPC types -from mcp.types.jsonrpc import ( +from mcp_types.jsonrpc import ( CONNECTION_CLOSED, HEADER_MISMATCH, INTERNAL_ERROR, @@ -220,6 +218,7 @@ RequestId, jsonrpc_message_adapter, ) +from mcp_types.version import LATEST_PROTOCOL_VERSION __all__ = [ # Protocol version constants diff --git a/src/mcp/types/_types.py b/src/mcp-types/mcp_types/_types.py similarity index 99% rename from src/mcp/types/_types.py rename to src/mcp-types/mcp_types/_types.py index 7bdfc70603..7f50d02fe7 100644 --- a/src/mcp/types/_types.py +++ b/src/mcp-types/mcp_types/_types.py @@ -3,7 +3,7 @@ One model per protocol construct, carrying every field from every supported protocol version, so application code sees a single set of types regardless of the negotiated version. Per-field docstrings note version availability. The -`mcp.types.v*` surface packages carry the schema-exact wire shapes. +`mcp_types.v*` surface packages carry the schema-exact wire shapes. """ from __future__ import annotations @@ -21,7 +21,7 @@ from pydantic.alias_generators import to_camel from typing_extensions import NotRequired, Self, TypedDict -from mcp.types.jsonrpc import RequestId +from mcp_types.jsonrpc import RequestId DEFAULT_NEGOTIATED_VERSION: Final[str] = "2025-03-26" """The default negotiated version of the Model Context Protocol when no version is specified. @@ -122,7 +122,7 @@ class Request(MCPModel, Generic[RequestParamsT, MethodT]): """Base class for JSON-RPC requests. The JSON-RPC envelope (`jsonrpc`, `id`) is attached by the session layer - (see `mcp.types.jsonrpc`), not carried here. + (see `mcp_types.jsonrpc`), not carried here. """ method: MethodT @@ -2073,7 +2073,7 @@ def _require_one_field(self) -> Self: CallToolRequestParams.model_rebuild() # Top-level message unions: superset across all supported protocol versions. -# Per-version validity is recorded in `mcp.types.methods`, not enforced here. +# Per-version validity is recorded in `mcp_types.methods`, not enforced here. ClientRequest = ( PingRequest diff --git a/src/mcp/types/_wire_base.py b/src/mcp-types/mcp_types/_wire_base.py similarity index 79% rename from src/mcp/types/_wire_base.py rename to src/mcp-types/mcp_types/_wire_base.py index 2ce08c855a..8d7b09d7f3 100644 --- a/src/mcp/types/_wire_base.py +++ b/src/mcp-types/mcp_types/_wire_base.py @@ -1,4 +1,4 @@ -"""Shared pydantic base for the generated `mcp.types.v*` wire-shape packages.""" +"""Shared pydantic base for the generated `mcp_types.v*` wire-shape packages.""" from pydantic import BaseModel, ConfigDict diff --git a/src/mcp/types/jsonrpc.py b/src/mcp-types/mcp_types/jsonrpc.py similarity index 100% rename from src/mcp/types/jsonrpc.py rename to src/mcp-types/mcp_types/jsonrpc.py diff --git a/src/mcp/types/methods.py b/src/mcp-types/mcp_types/methods.py similarity index 99% rename from src/mcp/types/methods.py rename to src/mcp-types/mcp_types/methods.py index 10bded166d..5bc7c1ff96 100644 --- a/src/mcp/types/methods.py +++ b/src/mcp-types/mcp_types/methods.py @@ -1,12 +1,12 @@ """Per-version method maps and parse/serialize functions for MCP traffic. -This module is supported public API; the `mcp.types.v*` packages it draws on +This module is supported public API; the `mcp_types.v*` packages it draws on are internal validators and not for direct import. Surface maps key `(method, version)` to per-version wire types (key absence is the version gate; shape validation is per schema era, i.e. 2025-11-25 for every pre-2026 version and 2026-07-28 for 2026). Monolith maps key `method` to the -version-free `mcp.types` models user code receives.""" +version-free `mcp_types` models user code receives.""" from __future__ import annotations @@ -17,10 +17,10 @@ from pydantic import BaseModel, TypeAdapter -import mcp.types as types -import mcp.types.v2025_11_25 as v2025 -import mcp.types.v2026_07_28 as v2026 -from mcp.shared.version import KNOWN_PROTOCOL_VERSIONS +import mcp_types as types +import mcp_types.v2025_11_25 as v2025 +import mcp_types.v2026_07_28 as v2026 +from mcp_types.version import KNOWN_PROTOCOL_VERSIONS __all__ = [ "CLIENT_NOTIFICATIONS", diff --git a/src/mcp-types/mcp_types/py.typed b/src/mcp-types/mcp_types/py.typed new file mode 100644 index 0000000000..e69de29bb2 diff --git a/src/mcp/types/v2025_11_25/__init__.py b/src/mcp-types/mcp_types/v2025_11_25/__init__.py similarity index 99% rename from src/mcp/types/v2025_11_25/__init__.py rename to src/mcp-types/mcp_types/v2025_11_25/__init__.py index e70a0afa01..b639bf7af8 100644 --- a/src/mcp/types/v2025_11_25/__init__.py +++ b/src/mcp-types/mcp_types/v2025_11_25/__init__.py @@ -8,7 +8,7 @@ from typing import Annotated, Any, Literal -from mcp.types._wire_base import WireModel +from mcp_types._wire_base import WireModel from pydantic import ConfigDict, Field, RootModel diff --git a/src/mcp/types/v2026_07_28/__init__.py b/src/mcp-types/mcp_types/v2026_07_28/__init__.py similarity index 99% rename from src/mcp/types/v2026_07_28/__init__.py rename to src/mcp-types/mcp_types/v2026_07_28/__init__.py index c0b4d88929..9ab30a3469 100644 --- a/src/mcp/types/v2026_07_28/__init__.py +++ b/src/mcp-types/mcp_types/v2026_07_28/__init__.py @@ -8,7 +8,7 @@ from typing import Annotated, Any, Literal, Union -from mcp.types._wire_base import WireModel +from mcp_types._wire_base import WireModel from pydantic import ConfigDict, Field, RootModel diff --git a/src/mcp/shared/version.py b/src/mcp-types/mcp_types/version.py similarity index 100% rename from src/mcp/shared/version.py rename to src/mcp-types/mcp_types/version.py diff --git a/src/mcp-types/pyproject.toml b/src/mcp-types/pyproject.toml new file mode 100644 index 0000000000..1ae7bae809 --- /dev/null +++ b/src/mcp-types/pyproject.toml @@ -0,0 +1,54 @@ +[project] +name = "mcp-types" +dynamic = ["version"] +description = "Model Context Protocol wire types" +readme = "README.md" +requires-python = ">=3.10" +authors = [{ name = "Model Context Protocol a Series of LF Projects, LLC." }] +maintainers = [ + { name = "David Soria Parra", email = "davidsp@anthropic.com" }, + { name = "Marcelo Trylesinski", email = "marcelotryle@gmail.com" }, + { name = "Max Isbey", email = "maxisbey@anthropic.com" }, + { name = "Felix Weinberger", email = "fweinberger@anthropic.com" }, +] +keywords = ["mcp", "llm", "automation"] +license = { text = "MIT" } +classifiers = [ + "Development Status :: 3 - Alpha", + "Intended Audience :: Developers", + "License :: OSI Approved :: MIT License", + "Programming Language :: Python :: 3", + "Programming Language :: Python :: 3.10", + "Programming Language :: Python :: 3.11", + "Programming Language :: Python :: 3.12", + "Programming Language :: Python :: 3.13", + "Programming Language :: Python :: 3.14", +] +dependencies = [ + "pydantic>=2.12.0", + "typing-extensions>=4.13.0", +] + +[project.urls] +Homepage = "https://modelcontextprotocol.io" +Documentation = "https://py.sdk.modelcontextprotocol.io/v2/" +Repository = "https://github.com/modelcontextprotocol/python-sdk" +Issues = "https://github.com/modelcontextprotocol/python-sdk/issues" + +[build-system] +requires = ["hatchling", "uv-dynamic-versioning"] +build-backend = "hatchling.build" + +[tool.hatch.version] +source = "uv-dynamic-versioning" + +[tool.uv-dynamic-versioning] +vcs = "git" +style = "pep440" +bump = true + +[tool.hatch.build.targets.sdist.force-include] +"../../LICENSE" = "LICENSE" + +[tool.hatch.build.targets.wheel] +packages = ["mcp_types"] diff --git a/src/mcp/__init__.py b/src/mcp/__init__.py index 20cc64aac5..3988289f6b 100644 --- a/src/mcp/__init__.py +++ b/src/mcp/__init__.py @@ -1,11 +1,4 @@ -from .client.client import Client -from .client.session import ClientSession -from .client.session_group import ClientSessionGroup -from .client.stdio import StdioServerParameters, stdio_client -from .server.session import ServerSession -from .server.stdio import stdio_server -from .shared.exceptions import MCPDeprecationWarning, MCPError, UrlElicitationRequiredError -from .types import ( +from mcp_types import ( CallToolRequest, ClientCapabilities, ClientNotification, @@ -63,7 +56,15 @@ ToolUseContent, UnsubscribeRequest, ) -from .types import Role as SamplingRole +from mcp_types import Role as SamplingRole + +from .client.client import Client +from .client.session import ClientSession +from .client.session_group import ClientSessionGroup +from .client.stdio import StdioServerParameters, stdio_client +from .server.session import ServerSession +from .server.stdio import stdio_server +from .shared.exceptions import MCPDeprecationWarning, MCPError, UrlElicitationRequiredError __all__ = [ "CallToolRequest", diff --git a/src/mcp/client/__main__.py b/src/mcp/client/__main__.py index b9ec344226..5fa3ce109b 100644 --- a/src/mcp/client/__main__.py +++ b/src/mcp/client/__main__.py @@ -6,8 +6,8 @@ from urllib.parse import urlparse import anyio +import mcp_types as types -from mcp import types from mcp.client._transport import ReadStream, WriteStream from mcp.client.session import ClientSession from mcp.client.sse import sse_client diff --git a/src/mcp/client/_probe.py b/src/mcp/client/_probe.py index 1da4cfcbcb..39a5c52964 100644 --- a/src/mcp/client/_probe.py +++ b/src/mcp/client/_probe.py @@ -17,17 +17,17 @@ from typing import Any -from pydantic import ValidationError - -from mcp import types -from mcp.client.session import ClientSession -from mcp.shared.exceptions import MCPError -from mcp.shared.version import ( +import mcp_types as types +from mcp_types import UNSUPPORTED_PROTOCOL_VERSION +from mcp_types.version import ( HANDSHAKE_PROTOCOL_VERSIONS, LATEST_MODERN_VERSION, MODERN_PROTOCOL_VERSIONS, ) -from mcp.types import UNSUPPORTED_PROTOCOL_VERSION +from pydantic import ValidationError + +from mcp.client.session import ClientSession +from mcp.shared.exceptions import MCPError def _parse_supported(data: Any) -> list[str] | None: diff --git a/src/mcp/client/auth/oauth2.py b/src/mcp/client/auth/oauth2.py index f21231b924..aae4d20b0b 100644 --- a/src/mcp/client/auth/oauth2.py +++ b/src/mcp/client/auth/oauth2.py @@ -16,6 +16,7 @@ import anyio import httpx +from mcp_types.version import is_version_at_least from pydantic import BaseModel, Field, ValidationError from mcp.client.auth.exceptions import OAuthFlowError, OAuthTokenError @@ -54,7 +55,6 @@ resource_url_from_server_url, ) from mcp.shared.inbound import MCP_PROTOCOL_VERSION_HEADER -from mcp.shared.version import is_version_at_least logger = logging.getLogger(__name__) diff --git a/src/mcp/client/auth/utils.py b/src/mcp/client/auth/utils.py index 16f711dd45..d6b05e0667 100644 --- a/src/mcp/client/auth/utils.py +++ b/src/mcp/client/auth/utils.py @@ -2,6 +2,7 @@ from urllib.parse import urljoin, urlparse from httpx import Request, Response +from mcp_types import LATEST_PROTOCOL_VERSION from pydantic import AnyUrl, ValidationError from mcp.client.auth import OAuthFlowError, OAuthRegistrationError, OAuthTokenError @@ -13,7 +14,6 @@ ProtectedResourceMetadata, ) from mcp.shared.inbound import MCP_PROTOCOL_VERSION_HEADER -from mcp.types import LATEST_PROTOCOL_VERSION def extract_field_from_www_auth(response: Response, field_name: str) -> str | None: diff --git a/src/mcp/client/client.py b/src/mcp/client/client.py index 362042ba5e..308f28d1c2 100644 --- a/src/mcp/client/client.py +++ b/src/mcp/client/client.py @@ -8,23 +8,8 @@ from typing import Any, Literal, TypeVar, overload import anyio -from typing_extensions import deprecated - -from mcp import types -from mcp.client._memory import InMemoryTransport -from mcp.client._probe import negotiate_auto -from mcp.client._transport import Transport -from mcp.client.session import ClientSession, ElicitationFnT, ListRootsFnT, LoggingFnT, MessageHandlerFnT, SamplingFnT -from mcp.client.streamable_http import streamable_http_client -from mcp.server import Server -from mcp.server.mcpserver import MCPServer -from mcp.server.runner import modern_on_request -from mcp.shared.direct_dispatcher import create_direct_dispatcher_pair -from mcp.shared.dispatcher import Dispatcher, ProgressFnT -from mcp.shared.exceptions import MCPDeprecationWarning -from mcp.shared.jsonrpc_dispatcher import JSONRPCDispatcher -from mcp.shared.version import HANDSHAKE_PROTOCOL_VERSIONS, MODERN_PROTOCOL_VERSIONS -from mcp.types import ( +import mcp_types as types +from mcp_types import ( CallToolResult, CompleteResult, EmptyResult, @@ -44,6 +29,21 @@ ResourceTemplateReference, ServerCapabilities, ) +from mcp_types.version import HANDSHAKE_PROTOCOL_VERSIONS, MODERN_PROTOCOL_VERSIONS +from typing_extensions import deprecated + +from mcp.client._memory import InMemoryTransport +from mcp.client._probe import negotiate_auto +from mcp.client._transport import Transport +from mcp.client.session import ClientSession, ElicitationFnT, ListRootsFnT, LoggingFnT, MessageHandlerFnT, SamplingFnT +from mcp.client.streamable_http import streamable_http_client +from mcp.server import Server +from mcp.server.mcpserver import MCPServer +from mcp.server.runner import modern_on_request +from mcp.shared.direct_dispatcher import create_direct_dispatcher_pair +from mcp.shared.dispatcher import Dispatcher, ProgressFnT +from mcp.shared.exceptions import MCPDeprecationWarning +from mcp.shared.jsonrpc_dispatcher import JSONRPCDispatcher ConnectMode = Literal["legacy", "auto"] | str """``mode=`` value: ``"legacy"`` (initialize handshake), ``"auto"`` (discover, fall back to diff --git a/src/mcp/client/session.py b/src/mcp/client/session.py index 902cec80bc..591223250d 100644 --- a/src/mcp/client/session.py +++ b/src/mcp/client/session.py @@ -9,10 +9,27 @@ import anyio import anyio.abc import anyio.lowlevel +import mcp_types as types +from mcp_types import ( + CLIENT_CAPABILITIES_META_KEY, + CLIENT_INFO_META_KEY, + INTERNAL_ERROR, + METHOD_NOT_FOUND, + PROTOCOL_VERSION_META_KEY, + UNSUPPORTED_PROTOCOL_VERSION, + RequestId, + RequestParamsMeta, +) +from mcp_types import methods as _methods +from mcp_types.version import ( + HANDSHAKE_PROTOCOL_VERSIONS, + LATEST_HANDSHAKE_VERSION, + LATEST_MODERN_VERSION, + MODERN_PROTOCOL_VERSIONS, +) from pydantic import BaseModel, TypeAdapter, ValidationError from typing_extensions import Self, TypeVar, deprecated -from mcp import types from mcp.client._transport import ReadStream, WriteStream from mcp.shared._compat import resync_tracer from mcp.shared.dispatcher import CallOptions, DispatchContext, Dispatcher, ProgressFnT @@ -27,23 +44,6 @@ from mcp.shared.message import ClientMessageMetadata, SessionMessage from mcp.shared.session import RequestResponder from mcp.shared.transport_context import TransportContext -from mcp.shared.version import ( - HANDSHAKE_PROTOCOL_VERSIONS, - LATEST_HANDSHAKE_VERSION, - LATEST_MODERN_VERSION, - MODERN_PROTOCOL_VERSIONS, -) -from mcp.types import ( - CLIENT_CAPABILITIES_META_KEY, - CLIENT_INFO_META_KEY, - INTERNAL_ERROR, - METHOD_NOT_FOUND, - PROTOCOL_VERSION_META_KEY, - UNSUPPORTED_PROTOCOL_VERSION, - RequestId, - RequestParamsMeta, -) -from mcp.types import methods as _methods DEFAULT_CLIENT_INFO = types.Implementation(name="mcp", version="0.1.0") DISCOVER_TIMEOUT_SECONDS = 10.0 diff --git a/src/mcp/client/session_group.py b/src/mcp/client/session_group.py index 211733d6a3..40f0232594 100644 --- a/src/mcp/client/session_group.py +++ b/src/mcp/client/session_group.py @@ -15,11 +15,11 @@ import anyio import httpx +import mcp_types as types from pydantic import BaseModel, Field from typing_extensions import Self import mcp -from mcp import types from mcp.client.session import ElicitationFnT, ListRootsFnT, LoggingFnT, MessageHandlerFnT, SamplingFnT from mcp.client.sse import sse_client from mcp.client.stdio import StdioServerParameters diff --git a/src/mcp/client/sse.py b/src/mcp/client/sse.py index 6a2579f4c0..8b482932aa 100644 --- a/src/mcp/client/sse.py +++ b/src/mcp/client/sse.py @@ -6,10 +6,10 @@ import anyio import httpx +import mcp_types as types from anyio.abc import TaskStatus from httpx_sse import SSEError, aconnect_sse -from mcp import types from mcp.shared._compat import resync_tracer from mcp.shared._context_streams import create_context_streams from mcp.shared._httpx_utils import McpHttpClientFactory, create_mcp_http_client diff --git a/src/mcp/client/stdio.py b/src/mcp/client/stdio.py index baf7ad1ca1..3e03eef9ef 100644 --- a/src/mcp/client/stdio.py +++ b/src/mcp/client/stdio.py @@ -18,11 +18,11 @@ import anyio import anyio.lowlevel +import mcp_types as types from anyio.abc import AsyncResource, Process from anyio.streams.text import TextReceiveStream from pydantic import BaseModel, Field -from mcp import types from mcp.client._transport import TransportStreams from mcp.os.posix.utilities import terminate_posix_process_tree from mcp.os.win32.utilities import ( diff --git a/src/mcp/client/streamable_http.py b/src/mcp/client/streamable_http.py index 78a8614765..551bfa5f37 100644 --- a/src/mcp/client/streamable_http.py +++ b/src/mcp/client/streamable_http.py @@ -12,15 +12,7 @@ import httpx from anyio.abc import TaskGroup from httpx_sse import EventSource, ServerSentEvent, aconnect_sse -from pydantic import ValidationError - -from mcp.client._transport import TransportStreams -from mcp.shared._compat import resync_tracer -from mcp.shared._context_streams import ContextReceiveStream, ContextSendStream, create_context_streams -from mcp.shared._httpx_utils import create_mcp_http_client -from mcp.shared.inbound import MCP_PROTOCOL_VERSION_HEADER -from mcp.shared.message import ClientMessageMetadata, SessionMessage -from mcp.types import ( +from mcp_types import ( INTERNAL_ERROR, INVALID_REQUEST, METHOD_NOT_FOUND, @@ -34,6 +26,14 @@ RequestId, jsonrpc_message_adapter, ) +from pydantic import ValidationError + +from mcp.client._transport import TransportStreams +from mcp.shared._compat import resync_tracer +from mcp.shared._context_streams import ContextReceiveStream, ContextSendStream, create_context_streams +from mcp.shared._httpx_utils import create_mcp_http_client +from mcp.shared.inbound import MCP_PROTOCOL_VERSION_HEADER +from mcp.shared.message import ClientMessageMetadata, SessionMessage logger = logging.getLogger(__name__) diff --git a/src/mcp/server/_otel.py b/src/mcp/server/_otel.py index 37e9d28559..ff722eb903 100644 --- a/src/mcp/server/_otel.py +++ b/src/mcp/server/_otel.py @@ -2,13 +2,13 @@ from typing import Any +from mcp_types import INVALID_PARAMS, CallToolResult from opentelemetry.trace import SpanKind, StatusCode from pydantic import ValidationError from mcp.server.context import CallNext, HandlerResult, ServerMiddleware, ServerRequestContext from mcp.shared._otel import extract_trace_context, otel_span from mcp.shared.exceptions import MCPError -from mcp.types import INVALID_PARAMS, CallToolResult class OpenTelemetryMiddleware(ServerMiddleware[Any]): diff --git a/src/mcp/server/_streamable_http_modern.py b/src/mcp/server/_streamable_http_modern.py index d151bc259c..9a42d64dda 100644 --- a/src/mcp/server/_streamable_http_modern.py +++ b/src/mcp/server/_streamable_http_modern.py @@ -19,6 +19,18 @@ from typing import TYPE_CHECKING, Any, TypeVar import anyio +from mcp_types import ( + INTERNAL_ERROR, + INVALID_REQUEST, + PARSE_ERROR, + ClientCapabilities, + ErrorData, + Implementation, + JSONRPCError, + JSONRPCRequest, + JSONRPCResponse, + RequestId, +) from pydantic import BaseModel, ValidationError from starlette.requests import Request from starlette.responses import Response @@ -33,18 +45,6 @@ from mcp.shared.jsonrpc_dispatcher import handler_exception_to_error_data from mcp.shared.message import MessageMetadata, ServerMessageMetadata from mcp.shared.transport_context import TransportContext -from mcp.types import ( - INTERNAL_ERROR, - INVALID_REQUEST, - PARSE_ERROR, - ClientCapabilities, - ErrorData, - Implementation, - JSONRPCError, - JSONRPCRequest, - JSONRPCResponse, - RequestId, -) if TYPE_CHECKING: from mcp.server.lowlevel.server import Server diff --git a/src/mcp/server/connection.py b/src/mcp/server/connection.py index 933bd5c6b6..76917f8967 100644 --- a/src/mcp/server/connection.py +++ b/src/mcp/server/connection.py @@ -25,14 +25,7 @@ from typing import Any, TypeVar, overload import anyio -from pydantic import BaseModel -from typing_extensions import deprecated - -from mcp.shared.dispatcher import CallOptions, Outbound -from mcp.shared.exceptions import MCPDeprecationWarning, NoBackChannelError -from mcp.shared.peer import Meta, dump_params -from mcp.shared.version import LATEST_HANDSHAKE_VERSION -from mcp.types import ( +from mcp_types import ( ClientCapabilities, CreateMessageRequest, CreateMessageResult, @@ -47,7 +40,14 @@ PingRequest, Request, ) -from mcp.types import methods as _methods +from mcp_types import methods as _methods +from mcp_types.version import LATEST_HANDSHAKE_VERSION +from pydantic import BaseModel +from typing_extensions import deprecated + +from mcp.shared.dispatcher import CallOptions, Outbound +from mcp.shared.exceptions import MCPDeprecationWarning, NoBackChannelError +from mcp.shared.peer import Meta, dump_params __all__ = ["Connection"] diff --git a/src/mcp/server/context.py b/src/mcp/server/context.py index 0fcd7ba9ae..b5c356075a 100644 --- a/src/mcp/server/context.py +++ b/src/mcp/server/context.py @@ -2,6 +2,7 @@ from dataclasses import dataclass from typing import Any, Generic, Protocol +from mcp_types import LoggingLevel, RequestId, RequestParamsMeta from pydantic import BaseModel from typing_extensions import TypeVar, deprecated @@ -13,7 +14,6 @@ from mcp.shared.message import CloseSSEStreamCallback from mcp.shared.peer import Meta from mcp.shared.transport_context import TransportContext -from mcp.types import LoggingLevel, RequestId, RequestParamsMeta # Invariant: parametrizes a mutable dataclass field; dict default matches the default lifespan. LifespanContextT = TypeVar("LifespanContextT", default=dict[str, Any]) diff --git a/src/mcp/server/elicitation.py b/src/mcp/server/elicitation.py index a34708d38d..066d33a1be 100644 --- a/src/mcp/server/elicitation.py +++ b/src/mcp/server/elicitation.py @@ -4,15 +4,15 @@ from typing import Any, Generic, Literal, TypeVar +from mcp_types import RequestId + +# Internal surface package; imported as the gate's source of truth for spec-valid property schemas. +from mcp_types.v2025_11_25 import PrimitiveSchemaDefinition from pydantic import BaseModel, ValidationError from pydantic.json_schema import GenerateJsonSchema, JsonSchemaValue from pydantic_core import core_schema from mcp.server.session import ServerSession -from mcp.types import RequestId - -# Internal surface package; imported as the gate's source of truth for spec-valid property schemas. -from mcp.types.v2025_11_25 import PrimitiveSchemaDefinition ElicitSchemaModelT = TypeVar("ElicitSchemaModelT", bound=BaseModel) diff --git a/src/mcp/server/lowlevel/server.py b/src/mcp/server/lowlevel/server.py index 0e917aefd0..8ad945b6a8 100644 --- a/src/mcp/server/lowlevel/server.py +++ b/src/mcp/server/lowlevel/server.py @@ -43,6 +43,8 @@ async def main(): from importlib.metadata import version as importlib_version from typing import Any, Generic +import mcp_types as types +from mcp_types.version import MODERN_PROTOCOL_VERSIONS from pydantic import BaseModel from starlette.applications import Starlette from starlette.middleware import Middleware @@ -50,7 +52,6 @@ async def main(): from starlette.routing import Mount, Route from typing_extensions import TypeVar -from mcp import types from mcp.server.auth.middleware.auth_context import AuthContextMiddleware from mcp.server.auth.middleware.bearer_auth import BearerAuthBackend, RequireAuthMiddleware from mcp.server.auth.provider import OAuthAuthorizationServerProvider, TokenVerifier @@ -64,7 +65,6 @@ async def main(): from mcp.server.transport_security import TransportSecuritySettings from mcp.shared._stream_protocols import ReadStream, WriteStream from mcp.shared.message import SessionMessage -from mcp.shared.version import MODERN_PROTOCOL_VERSIONS logger = logging.getLogger(__name__) diff --git a/src/mcp/server/mcpserver/__init__.py b/src/mcp/server/mcpserver/__init__.py index 0857e38bd4..e36a7ae7d6 100644 --- a/src/mcp/server/mcpserver/__init__.py +++ b/src/mcp/server/mcpserver/__init__.py @@ -1,6 +1,6 @@ """MCPServer - A more ergonomic interface for MCP servers.""" -from mcp.types import Icon +from mcp_types import Icon from .context import Context from .server import MCPServer diff --git a/src/mcp/server/mcpserver/context.py b/src/mcp/server/mcpserver/context.py index 7856e32185..f703e760fb 100644 --- a/src/mcp/server/mcpserver/context.py +++ b/src/mcp/server/mcpserver/context.py @@ -3,6 +3,7 @@ from collections.abc import Iterable from typing import TYPE_CHECKING, Any, Generic +from mcp_types import LoggingLevel from pydantic import AnyUrl, BaseModel from typing_extensions import deprecated @@ -16,7 +17,6 @@ ) from mcp.server.lowlevel.helper_types import ReadResourceContents from mcp.shared.exceptions import MCPDeprecationWarning -from mcp.types import LoggingLevel if TYPE_CHECKING: from mcp.server.mcpserver.server import MCPServer diff --git a/src/mcp/server/mcpserver/prompts/base.py b/src/mcp/server/mcpserver/prompts/base.py index 2f778eb514..338cb1f870 100644 --- a/src/mcp/server/mcpserver/prompts/base.py +++ b/src/mcp/server/mcpserver/prompts/base.py @@ -8,12 +8,12 @@ import anyio.to_thread import pydantic_core +from mcp_types import ContentBlock, Icon, TextContent from pydantic import BaseModel, Field, TypeAdapter, validate_call from mcp.server.mcpserver.utilities.context_injection import find_context_parameter, inject_context from mcp.server.mcpserver.utilities.func_metadata import func_metadata from mcp.shared._callable_inspection import is_async_callable -from mcp.types import ContentBlock, Icon, TextContent if TYPE_CHECKING: from mcp.server.context import LifespanContextT, RequestT diff --git a/src/mcp/server/mcpserver/resources/base.py b/src/mcp/server/mcpserver/resources/base.py index d48e0695cb..f7bedf6cbe 100644 --- a/src/mcp/server/mcpserver/resources/base.py +++ b/src/mcp/server/mcpserver/resources/base.py @@ -3,6 +3,7 @@ import abc from typing import Any +from mcp_types import Annotations, Icon from pydantic import ( BaseModel, ConfigDict, @@ -11,8 +12,6 @@ field_validator, ) -from mcp.types import Annotations, Icon - class Resource(BaseModel, abc.ABC): """Base class for all resources.""" diff --git a/src/mcp/server/mcpserver/resources/resource_manager.py b/src/mcp/server/mcpserver/resources/resource_manager.py index cff41495e0..54f54549eb 100644 --- a/src/mcp/server/mcpserver/resources/resource_manager.py +++ b/src/mcp/server/mcpserver/resources/resource_manager.py @@ -5,13 +5,13 @@ from collections.abc import Callable from typing import TYPE_CHECKING, Any +from mcp_types import Annotations, Icon from pydantic import AnyUrl from mcp.server.mcpserver.exceptions import ResourceNotFoundError from mcp.server.mcpserver.resources.base import Resource from mcp.server.mcpserver.resources.templates import ResourceTemplate from mcp.server.mcpserver.utilities.logging import get_logger -from mcp.types import Annotations, Icon if TYPE_CHECKING: from mcp.server.context import LifespanContextT, RequestT diff --git a/src/mcp/server/mcpserver/resources/templates.py b/src/mcp/server/mcpserver/resources/templates.py index 0c5df425c9..72707a11ab 100644 --- a/src/mcp/server/mcpserver/resources/templates.py +++ b/src/mcp/server/mcpserver/resources/templates.py @@ -9,6 +9,7 @@ from urllib.parse import unquote import anyio.to_thread +from mcp_types import Annotations, Icon from pydantic import BaseModel, Field, validate_call from mcp.server.mcpserver.exceptions import ResourceError @@ -17,7 +18,6 @@ from mcp.server.mcpserver.utilities.func_metadata import func_metadata from mcp.server.mcpserver.utilities.logging import get_logger from mcp.shared._callable_inspection import is_async_callable -from mcp.types import Annotations, Icon logger = get_logger(__name__) diff --git a/src/mcp/server/mcpserver/resources/types.py b/src/mcp/server/mcpserver/resources/types.py index d9e472e362..a25213e7bf 100644 --- a/src/mcp/server/mcpserver/resources/types.py +++ b/src/mcp/server/mcpserver/resources/types.py @@ -12,11 +12,11 @@ import httpx import pydantic import pydantic_core +from mcp_types import Annotations, Icon from pydantic import Field, ValidationInfo, validate_call from mcp.server.mcpserver.resources.base import Resource from mcp.shared._callable_inspection import is_async_callable -from mcp.types import Annotations, Icon class TextResource(Resource): diff --git a/src/mcp/server/mcpserver/server.py b/src/mcp/server/mcpserver/server.py index 2064bd60cd..15308eefd7 100644 --- a/src/mcp/server/mcpserver/server.py +++ b/src/mcp/server/mcpserver/server.py @@ -11,6 +11,35 @@ import anyio import pydantic_core +from mcp_types import ( + INTERNAL_ERROR, + INVALID_PARAMS, + Annotations, + BlobResourceContents, + CallToolRequestParams, + CallToolResult, + CompleteRequestParams, + CompleteResult, + Completion, + GetPromptRequestParams, + GetPromptResult, + Icon, + ListPromptsResult, + ListResourcesResult, + ListResourceTemplatesResult, + ListToolsResult, + PaginatedRequestParams, + ReadResourceRequestParams, + ReadResourceResult, + TextContent, + TextResourceContents, + ToolAnnotations, +) +from mcp_types import Prompt as MCPPrompt +from mcp_types import PromptArgument as MCPPromptArgument +from mcp_types import Resource as MCPResource +from mcp_types import ResourceTemplate as MCPResourceTemplate +from mcp_types import Tool as MCPTool from pydantic.networks import AnyUrl from pydantic_settings import BaseSettings, SettingsConfigDict from starlette.applications import Starlette @@ -42,35 +71,6 @@ from mcp.server.streamable_http_manager import StreamableHTTPSessionManager from mcp.server.transport_security import TransportSecuritySettings from mcp.shared.exceptions import MCPError -from mcp.types import ( - INTERNAL_ERROR, - INVALID_PARAMS, - Annotations, - BlobResourceContents, - CallToolRequestParams, - CallToolResult, - CompleteRequestParams, - CompleteResult, - Completion, - GetPromptRequestParams, - GetPromptResult, - Icon, - ListPromptsResult, - ListResourcesResult, - ListResourceTemplatesResult, - ListToolsResult, - PaginatedRequestParams, - ReadResourceRequestParams, - ReadResourceResult, - TextContent, - TextResourceContents, - ToolAnnotations, -) -from mcp.types import Prompt as MCPPrompt -from mcp.types import PromptArgument as MCPPromptArgument -from mcp.types import Resource as MCPResource -from mcp.types import ResourceTemplate as MCPResourceTemplate -from mcp.types import Tool as MCPTool logger = get_logger(__name__) diff --git a/src/mcp/server/mcpserver/tools/base.py b/src/mcp/server/mcpserver/tools/base.py index 29894d7d1d..7eb87eed03 100644 --- a/src/mcp/server/mcpserver/tools/base.py +++ b/src/mcp/server/mcpserver/tools/base.py @@ -4,6 +4,7 @@ from functools import cached_property from typing import TYPE_CHECKING, Any +from mcp_types import Icon, ToolAnnotations from pydantic import BaseModel, Field from mcp.server.mcpserver.exceptions import ToolError @@ -12,7 +13,6 @@ from mcp.shared._callable_inspection import is_async_callable from mcp.shared.exceptions import MCPError from mcp.shared.tool_name_validation import validate_and_warn_tool_name -from mcp.types import Icon, ToolAnnotations if TYPE_CHECKING: from mcp.server.context import LifespanContextT, RequestT diff --git a/src/mcp/server/mcpserver/tools/tool_manager.py b/src/mcp/server/mcpserver/tools/tool_manager.py index eef4911f9e..9e7910ea93 100644 --- a/src/mcp/server/mcpserver/tools/tool_manager.py +++ b/src/mcp/server/mcpserver/tools/tool_manager.py @@ -3,10 +3,11 @@ from collections.abc import Callable from typing import TYPE_CHECKING, Any +from mcp_types import Icon, ToolAnnotations + from mcp.server.mcpserver.exceptions import ToolError from mcp.server.mcpserver.tools.base import Tool from mcp.server.mcpserver.utilities.logging import get_logger -from mcp.types import Icon, ToolAnnotations if TYPE_CHECKING: from mcp.server.context import LifespanContextT, RequestT diff --git a/src/mcp/server/mcpserver/utilities/func_metadata.py b/src/mcp/server/mcpserver/utilities/func_metadata.py index 6c553fbab9..d0c679c053 100644 --- a/src/mcp/server/mcpserver/utilities/func_metadata.py +++ b/src/mcp/server/mcpserver/utilities/func_metadata.py @@ -9,6 +9,7 @@ import anyio import anyio.to_thread import pydantic_core +from mcp_types import CallToolResult, ContentBlock, TextContent from pydantic import BaseModel, ConfigDict, Field, PydanticUserError, WithJsonSchema, create_model from pydantic.fields import FieldInfo from pydantic.json_schema import GenerateJsonSchema, JsonSchemaWarningKind @@ -24,7 +25,6 @@ from mcp.server.mcpserver.exceptions import InvalidSignature from mcp.server.mcpserver.utilities.logging import get_logger from mcp.server.mcpserver.utilities.types import Audio, Image -from mcp.types import CallToolResult, ContentBlock, TextContent logger = get_logger(__name__) diff --git a/src/mcp/server/mcpserver/utilities/types.py b/src/mcp/server/mcpserver/utilities/types.py index f092b245a8..63f94d4cc7 100644 --- a/src/mcp/server/mcpserver/utilities/types.py +++ b/src/mcp/server/mcpserver/utilities/types.py @@ -3,7 +3,7 @@ import base64 from pathlib import Path -from mcp.types import AudioContent, ImageContent +from mcp_types import AudioContent, ImageContent class Image: diff --git a/src/mcp/server/models.py b/src/mcp/server/models.py index 3861f42a7e..6b129165a1 100644 --- a/src/mcp/server/models.py +++ b/src/mcp/server/models.py @@ -2,10 +2,9 @@ and tools. """ +from mcp_types import Icon, ServerCapabilities from pydantic import BaseModel -from mcp.types import Icon, ServerCapabilities - class InitializationOptions(BaseModel): server_name: str diff --git a/src/mcp/server/runner.py b/src/mcp/server/runner.py index e71a8a6e7a..f75e2ca420 100644 --- a/src/mcp/server/runner.py +++ b/src/mcp/server/runner.py @@ -21,6 +21,22 @@ import anyio import anyio.abc +from mcp_types import ( + CLIENT_CAPABILITIES_META_KEY, + CLIENT_INFO_META_KEY, + INTERNAL_ERROR, + INVALID_PARAMS, + METHOD_NOT_FOUND, + PROTOCOL_VERSION_META_KEY, + ErrorData, + Implementation, + InitializeRequestParams, + InitializeResult, + RequestParams, + RequestParamsMeta, +) +from mcp_types import methods as _methods +from mcp_types.version import HANDSHAKE_PROTOCOL_VERSIONS, LATEST_HANDSHAKE_VERSION, LATEST_MODERN_VERSION from opentelemetry.trace import SpanKind, StatusCode from pydantic import BaseModel, ValidationError from typing_extensions import TypeVar @@ -36,22 +52,6 @@ from mcp.shared.jsonrpc_dispatcher import JSONRPCDispatcher from mcp.shared.message import ServerMessageMetadata, SessionMessage from mcp.shared.transport_context import TransportContext -from mcp.shared.version import HANDSHAKE_PROTOCOL_VERSIONS, LATEST_HANDSHAKE_VERSION, LATEST_MODERN_VERSION -from mcp.types import ( - CLIENT_CAPABILITIES_META_KEY, - CLIENT_INFO_META_KEY, - INTERNAL_ERROR, - INVALID_PARAMS, - METHOD_NOT_FOUND, - PROTOCOL_VERSION_META_KEY, - ErrorData, - Implementation, - InitializeRequestParams, - InitializeResult, - RequestParams, - RequestParamsMeta, -) -from mcp.types import methods as _methods if TYPE_CHECKING: from mcp.server.lowlevel.server import Server diff --git a/src/mcp/server/session.py b/src/mcp/server/session.py index aa84ad37b8..ca62fb9c8e 100644 --- a/src/mcp/server/session.py +++ b/src/mcp/server/session.py @@ -8,16 +8,16 @@ from typing import Any, TypeVar, overload +import mcp_types as types +from mcp_types import methods as _methods from pydantic import AnyUrl, BaseModel from typing_extensions import deprecated -from mcp import types from mcp.server.connection import Connection from mcp.server.validation import validate_sampling_tools, validate_tool_use_result_messages from mcp.shared.dispatcher import CallOptions, DispatchContext, ProgressFnT from mcp.shared.exceptions import MCPDeprecationWarning from mcp.shared.message import ServerMessageMetadata -from mcp.types import methods as _methods __all__ = ["ServerSession"] diff --git a/src/mcp/server/sse.py b/src/mcp/server/sse.py index 05e948332b..4d02fc4a73 100644 --- a/src/mcp/server/sse.py +++ b/src/mcp/server/sse.py @@ -43,13 +43,13 @@ async def handle_sse(request): from uuid import UUID, uuid4 import anyio +import mcp_types as types from pydantic import ValidationError from sse_starlette import EventSourceResponse from starlette.requests import Request from starlette.responses import Response from starlette.types import Receive, Scope, Send -from mcp import types from mcp.server.auth.middleware.bearer_auth import AuthenticatedUser, AuthorizationContext, authorization_context from mcp.server.transport_security import ( TransportSecurityMiddleware, diff --git a/src/mcp/server/stdio.py b/src/mcp/server/stdio.py index 5c1459dff6..876d256ddb 100644 --- a/src/mcp/server/stdio.py +++ b/src/mcp/server/stdio.py @@ -23,8 +23,8 @@ async def run_server(): import anyio import anyio.lowlevel +import mcp_types as types -from mcp import types from mcp.shared._context_streams import create_context_streams from mcp.shared.message import SessionMessage diff --git a/src/mcp/server/streamable_http.py b/src/mcp/server/streamable_http.py index aa682cbf2a..b6128d3e08 100644 --- a/src/mcp/server/streamable_http.py +++ b/src/mcp/server/streamable_http.py @@ -19,19 +19,7 @@ import anyio import pydantic_core from anyio.streams.memory import MemoryObjectReceiveStream, MemoryObjectSendStream -from pydantic import ValidationError -from sse_starlette import EventSourceResponse -from starlette.requests import Request -from starlette.responses import Response -from starlette.types import Receive, Scope, Send - -from mcp.server.transport_security import TransportSecurityMiddleware, TransportSecuritySettings -from mcp.shared._context_streams import ContextReceiveStream, ContextSendStream, create_context_streams -from mcp.shared._stream_protocols import ReadStream, WriteStream -from mcp.shared.inbound import MCP_PROTOCOL_VERSION_HEADER -from mcp.shared.message import ServerMessageMetadata, SessionMessage -from mcp.shared.version import is_version_at_least -from mcp.types import ( +from mcp_types import ( DEFAULT_NEGOTIATED_VERSION, INTERNAL_ERROR, INVALID_PARAMS, @@ -45,6 +33,18 @@ RequestId, jsonrpc_message_adapter, ) +from mcp_types.version import is_version_at_least +from pydantic import ValidationError +from sse_starlette import EventSourceResponse +from starlette.requests import Request +from starlette.responses import Response +from starlette.types import Receive, Scope, Send + +from mcp.server.transport_security import TransportSecurityMiddleware, TransportSecuritySettings +from mcp.shared._context_streams import ContextReceiveStream, ContextSendStream, create_context_streams +from mcp.shared._stream_protocols import ReadStream, WriteStream +from mcp.shared.inbound import MCP_PROTOCOL_VERSION_HEADER +from mcp.shared.message import ServerMessageMetadata, SessionMessage logger = logging.getLogger(__name__) diff --git a/src/mcp/server/streamable_http_manager.py b/src/mcp/server/streamable_http_manager.py index f9329f8564..578639853a 100644 --- a/src/mcp/server/streamable_http_manager.py +++ b/src/mcp/server/streamable_http_manager.py @@ -10,6 +10,8 @@ import anyio from anyio.abc import TaskStatus +from mcp_types import DEFAULT_NEGOTIATED_VERSION, INVALID_REQUEST, ErrorData, JSONRPCError +from mcp_types.version import HANDSHAKE_PROTOCOL_VERSIONS from starlette.requests import Request from starlette.responses import Response from starlette.types import Receive, Scope, Send @@ -28,8 +30,6 @@ from mcp.shared.inbound import MCP_PROTOCOL_VERSION_HEADER from mcp.shared.jsonrpc_dispatcher import JSONRPCDispatcher from mcp.shared.transport_context import TransportContext -from mcp.shared.version import HANDSHAKE_PROTOCOL_VERSIONS -from mcp.types import DEFAULT_NEGOTIATED_VERSION, INVALID_REQUEST, ErrorData, JSONRPCError if TYPE_CHECKING: from mcp.server.lowlevel.server import Server diff --git a/src/mcp/server/validation.py b/src/mcp/server/validation.py index 08f5754f1e..fd16beb957 100644 --- a/src/mcp/server/validation.py +++ b/src/mcp/server/validation.py @@ -3,8 +3,9 @@ This module provides validation logic for sampling and elicitation requests. """ +from mcp_types import INVALID_PARAMS, ClientCapabilities, SamplingMessage, Tool, ToolChoice + from mcp.shared.exceptions import MCPError -from mcp.types import INVALID_PARAMS, ClientCapabilities, SamplingMessage, Tool, ToolChoice def check_sampling_tools_capability(client_caps: ClientCapabilities | None) -> bool: diff --git a/src/mcp/shared/context.py b/src/mcp/shared/context.py index eef1fa3855..13c145be5b 100644 --- a/src/mcp/shared/context.py +++ b/src/mcp/shared/context.py @@ -13,11 +13,11 @@ from typing import Any, Generic import anyio +from mcp_types import RequestParamsMeta from typing_extensions import TypeVar from mcp.shared.dispatcher import CallOptions, DispatchContext from mcp.shared.transport_context import TransportContext -from mcp.types import RequestParamsMeta __all__ = ["BaseContext"] diff --git a/src/mcp/shared/direct_dispatcher.py b/src/mcp/shared/direct_dispatcher.py index 9268feffe1..fd3e69d493 100644 --- a/src/mcp/shared/direct_dispatcher.py +++ b/src/mcp/shared/direct_dispatcher.py @@ -24,6 +24,7 @@ import anyio import anyio.abc +from mcp_types import CONNECTION_CLOSED, INTERNAL_ERROR, INVALID_PARAMS, REQUEST_TIMEOUT, RequestId from pydantic import ValidationError from mcp.shared._compat import resync_tracer @@ -31,7 +32,6 @@ from mcp.shared.exceptions import MCPError, NoBackChannelError from mcp.shared.message import MessageMetadata from mcp.shared.transport_context import TransportContext -from mcp.types import CONNECTION_CLOSED, INTERNAL_ERROR, INVALID_PARAMS, REQUEST_TIMEOUT, RequestId logger = logging.getLogger(__name__) diff --git a/src/mcp/shared/dispatcher.py b/src/mcp/shared/dispatcher.py index 8b343f2555..eaefd3d1cb 100644 --- a/src/mcp/shared/dispatcher.py +++ b/src/mcp/shared/dispatcher.py @@ -21,10 +21,10 @@ import anyio import anyio.abc +from mcp_types import RequestId from mcp.shared.message import MessageMetadata from mcp.shared.transport_context import TransportContext -from mcp.types import RequestId __all__ = [ "CallOptions", diff --git a/src/mcp/shared/exceptions.py b/src/mcp/shared/exceptions.py index 7d17d59e13..d3acb12714 100644 --- a/src/mcp/shared/exceptions.py +++ b/src/mcp/shared/exceptions.py @@ -2,7 +2,7 @@ from typing import Any, cast -from mcp.types import INVALID_REQUEST, URL_ELICITATION_REQUIRED, ElicitRequestURLParams, ErrorData, JSONRPCError +from mcp_types import INVALID_REQUEST, URL_ELICITATION_REQUIRED, ElicitRequestURLParams, ErrorData, JSONRPCError class MCPDeprecationWarning(UserWarning): diff --git a/src/mcp/shared/inbound.py b/src/mcp/shared/inbound.py index fb4c765246..f54f125e7a 100644 --- a/src/mcp/shared/inbound.py +++ b/src/mcp/shared/inbound.py @@ -15,14 +15,13 @@ from types import MappingProxyType from typing import Any, Final -from mcp.shared.version import MODERN_PROTOCOL_VERSIONS -from mcp.types import ( +from mcp_types import ( CLIENT_CAPABILITIES_META_KEY, CLIENT_INFO_META_KEY, PROTOCOL_VERSION_META_KEY, UnsupportedProtocolVersionErrorData, ) -from mcp.types.jsonrpc import ( +from mcp_types.jsonrpc import ( HEADER_MISMATCH, INVALID_PARAMS, INVALID_REQUEST, @@ -31,6 +30,7 @@ PARSE_ERROR, UNSUPPORTED_PROTOCOL_VERSION, ) +from mcp_types.version import MODERN_PROTOCOL_VERSIONS __all__ = [ "ERROR_CODE_HTTP_STATUS", @@ -119,14 +119,14 @@ def classify_inbound_request( 1. ``params._meta`` is a mapping carrying every reserved envelope key (protocol version, client info, client capabilities) → else - :data:`~mcp.types.jsonrpc.INVALID_PARAMS`. + :data:`~mcp_types.jsonrpc.INVALID_PARAMS`. 2. When ``headers`` is given, its ``MCP-Protocol-Version`` entry equals the envelope's protocol version → else - :data:`~mcp.types.jsonrpc.HEADER_MISMATCH`. Runs before the + :data:`~mcp_types.jsonrpc.HEADER_MISMATCH`. Runs before the supported-version rung so a client that disagrees with itself is told so, rather than told the body's version is unsupported. 3. The envelope's protocol version is in ``supported_modern_versions`` → - else :data:`~mcp.types.jsonrpc.UNSUPPORTED_PROTOCOL_VERSION` with + else :data:`~mcp_types.jsonrpc.UNSUPPORTED_PROTOCOL_VERSION` with ``data = {"supported": [...], "requested": }``. Method existence is *not* a rung: kernel dispatch owns that decision so diff --git a/src/mcp/shared/jsonrpc_dispatcher.py b/src/mcp/shared/jsonrpc_dispatcher.py index 24f1d3593a..2e784e2c20 100644 --- a/src/mcp/shared/jsonrpc_dispatcher.py +++ b/src/mcp/shared/jsonrpc_dispatcher.py @@ -18,6 +18,20 @@ import anyio.abc import anyio.lowlevel from anyio.streams.memory import MemoryObjectReceiveStream, MemoryObjectSendStream +from mcp_types import ( + CONNECTION_CLOSED, + INTERNAL_ERROR, + INVALID_PARAMS, + REQUEST_TIMEOUT, + ErrorData, + JSONRPCError, + JSONRPCMessage, + JSONRPCNotification, + JSONRPCRequest, + JSONRPCResponse, + ProgressToken, + RequestId, +) from opentelemetry.trace import SpanKind from pydantic import ValidationError from typing_extensions import TypeVar @@ -34,20 +48,6 @@ SessionMessage, ) from mcp.shared.transport_context import TransportContext -from mcp.types import ( - CONNECTION_CLOSED, - INTERNAL_ERROR, - INVALID_PARAMS, - REQUEST_TIMEOUT, - ErrorData, - JSONRPCError, - JSONRPCMessage, - JSONRPCNotification, - JSONRPCRequest, - JSONRPCResponse, - ProgressToken, - RequestId, -) __all__ = ["JSONRPCDispatcher", "handler_exception_to_error_data"] diff --git a/src/mcp/shared/message.py b/src/mcp/shared/message.py index a0b6561151..236569fac2 100644 --- a/src/mcp/shared/message.py +++ b/src/mcp/shared/message.py @@ -8,7 +8,7 @@ from dataclasses import dataclass from typing import Any -from mcp.types import JSONRPCMessage, RequestId +from mcp_types import JSONRPCMessage, RequestId ResumptionToken = str diff --git a/src/mcp/shared/metadata_utils.py b/src/mcp/shared/metadata_utils.py index 6e4d33da0f..b646133477 100644 --- a/src/mcp/shared/metadata_utils.py +++ b/src/mcp/shared/metadata_utils.py @@ -4,7 +4,7 @@ human-readable names in user interfaces in a spec-compliant way. """ -from mcp.types import Implementation, Prompt, Resource, ResourceTemplate, Tool +from mcp_types import Implementation, Prompt, Resource, ResourceTemplate, Tool def get_display_name(obj: Tool | Resource | Prompt | ResourceTemplate | Implementation) -> str: diff --git a/src/mcp/shared/peer.py b/src/mcp/shared/peer.py index 2cf7b36823..ca59b56af6 100644 --- a/src/mcp/shared/peer.py +++ b/src/mcp/shared/peer.py @@ -12,12 +12,7 @@ from collections.abc import Mapping from typing import Any, cast, overload -from pydantic import BaseModel -from typing_extensions import deprecated - -from mcp.shared.dispatcher import CallOptions, Outbound -from mcp.shared.exceptions import MCPDeprecationWarning -from mcp.types import ( +from mcp_types import ( CreateMessageRequestParams, CreateMessageResult, CreateMessageResultWithTools, @@ -34,6 +29,11 @@ Tool, ToolChoice, ) +from pydantic import BaseModel +from typing_extensions import deprecated + +from mcp.shared.dispatcher import CallOptions, Outbound +from mcp.shared.exceptions import MCPDeprecationWarning __all__ = ["ClientPeer", "Meta"] diff --git a/src/mcp/shared/session.py b/src/mcp/shared/session.py index b4f0beedf1..f8f0a6d416 100644 --- a/src/mcp/shared/session.py +++ b/src/mcp/shared/session.py @@ -2,9 +2,10 @@ from typing import Generic, TypeVar +from mcp_types import RequestParamsMeta + from mcp.shared.dispatcher import ProgressFnT as ProgressFnT from mcp.shared.message import MessageMetadata -from mcp.types import RequestParamsMeta RequestId = str | int diff --git a/tests/client/conftest.py b/tests/client/conftest.py index 081e1d68ea..1fbee13c18 100644 --- a/tests/client/conftest.py +++ b/tests/client/conftest.py @@ -4,11 +4,11 @@ from unittest.mock import patch import pytest +from mcp_types import JSONRPCNotification, JSONRPCRequest import mcp.shared.memory from mcp.client._transport import WriteStream from mcp.shared.message import SessionMessage -from mcp.types import JSONRPCNotification, JSONRPCRequest class SpyMemoryObjectSendStream: diff --git a/tests/client/test_client.py b/tests/client/test_client.py index 792bdc8a7c..cc3ff4d968 100644 --- a/tests/client/test_client.py +++ b/tests/client/test_client.py @@ -8,20 +8,10 @@ from unittest.mock import patch import anyio +import mcp_types as types import pytest from inline_snapshot import snapshot - -from mcp import MCPError, types -from mcp.client._memory import InMemoryTransport -from mcp.client._transport import TransportStreams -from mcp.client.client import Client -from mcp.client.streamable_http import streamable_http_client -from mcp.server import Server, ServerRequestContext -from mcp.server.mcpserver import MCPServer -from mcp.shared.memory import MessageStream, create_client_server_memory_streams -from mcp.shared.message import SessionMessage -from mcp.shared.version import LATEST_HANDSHAKE_VERSION -from mcp.types import ( +from mcp_types import ( CallToolResult, EmptyResult, GetPromptResult, @@ -42,6 +32,17 @@ Tool, ToolsCapability, ) +from mcp_types.version import LATEST_HANDSHAKE_VERSION + +from mcp import MCPError +from mcp.client._memory import InMemoryTransport +from mcp.client._transport import TransportStreams +from mcp.client.client import Client +from mcp.client.streamable_http import streamable_http_client +from mcp.server import Server, ServerRequestContext +from mcp.server.mcpserver import MCPServer +from mcp.shared.memory import MessageStream, create_client_server_memory_streams +from mcp.shared.message import SessionMessage from tests.interaction._connect import BASE_URL, mounted_app pytestmark = pytest.mark.anyio diff --git a/tests/client/test_http_unicode.py b/tests/client/test_http_unicode.py index 585a142617..387fa4b48e 100644 --- a/tests/client/test_http_unicode.py +++ b/tests/client/test_http_unicode.py @@ -8,16 +8,16 @@ from contextlib import asynccontextmanager import httpx +import mcp_types as types import pytest +from mcp_types import TextContent, Tool from starlette.applications import Starlette from starlette.routing import Mount -from mcp import types from mcp.client.session import ClientSession from mcp.client.streamable_http import streamable_http_client from mcp.server import Server, ServerRequestContext from mcp.server.streamable_http_manager import StreamableHTTPSessionManager -from mcp.types import TextContent, Tool from tests.interaction.transports import StreamingASGITransport # The in-process app is mounted at this origin purely so URLs are well-formed; nothing listens here. diff --git a/tests/client/test_list_methods_cursor.py b/tests/client/test_list_methods_cursor.py index 30955d4308..043b630d5c 100644 --- a/tests/client/test_list_methods_cursor.py +++ b/tests/client/test_list_methods_cursor.py @@ -1,11 +1,12 @@ from collections.abc import Callable +import mcp_types as types import pytest +from mcp_types import ListToolsResult -from mcp import Client, types +from mcp import Client from mcp.server import Server, ServerRequestContext from mcp.server.mcpserver import MCPServer -from mcp.types import ListToolsResult from .conftest import StreamSpyCollection diff --git a/tests/client/test_list_roots_callback.py b/tests/client/test_list_roots_callback.py index 72119a8cfc..14ca1577d1 100644 --- a/tests/client/test_list_roots_callback.py +++ b/tests/client/test_list_roots_callback.py @@ -1,11 +1,11 @@ import pytest +from mcp_types import INVALID_REQUEST, ListRootsResult, Root, TextContent from pydantic import FileUrl from mcp import Client from mcp.client import ClientRequestContext from mcp.server.mcpserver import Context, MCPServer from mcp.shared.exceptions import MCPError -from mcp.types import INVALID_REQUEST, ListRootsResult, Root, TextContent @pytest.mark.anyio diff --git a/tests/client/test_logging_callback.py b/tests/client/test_logging_callback.py index 0b7e363a17..d62b7e19b3 100644 --- a/tests/client/test_logging_callback.py +++ b/tests/client/test_logging_callback.py @@ -1,15 +1,16 @@ from typing import Literal +import mcp_types as types import pytest - -from mcp import Client, types -from mcp.server.mcpserver import Context, MCPServer -from mcp.shared.session import RequestResponder -from mcp.types import ( +from mcp_types import ( LoggingMessageNotificationParams, TextContent, ) +from mcp import Client +from mcp.server.mcpserver import Context, MCPServer +from mcp.shared.session import RequestResponder + class LoggingCollector: def __init__(self): diff --git a/tests/client/test_notification_response.py b/tests/client/test_notification_response.py index bd85cd074a..418a6bc54b 100644 --- a/tests/client/test_notification_response.py +++ b/tests/client/test_notification_response.py @@ -7,16 +7,17 @@ import json import httpx +import mcp_types as types import pytest +from mcp_types import RootsListChangedNotification from starlette.applications import Starlette from starlette.requests import Request from starlette.responses import JSONResponse, Response from starlette.routing import Route -from mcp import ClientSession, MCPError, types +from mcp import ClientSession, MCPError from mcp.client.streamable_http import streamable_http_client from mcp.shared.session import RequestResponder -from mcp.types import RootsListChangedNotification pytestmark = pytest.mark.anyio diff --git a/tests/client/test_output_schema_validation.py b/tests/client/test_output_schema_validation.py index d78197b5c3..60f6fadc0f 100644 --- a/tests/client/test_output_schema_validation.py +++ b/tests/client/test_output_schema_validation.py @@ -2,10 +2,7 @@ from typing import Any import pytest - -from mcp import Client -from mcp.server import Server, ServerRequestContext -from mcp.types import ( +from mcp_types import ( CallToolRequestParams, CallToolResult, ListToolsResult, @@ -14,6 +11,9 @@ Tool, ) +from mcp import Client +from mcp.server import Server, ServerRequestContext + def _make_server( tools: list[Tool], diff --git a/tests/client/test_probe.py b/tests/client/test_probe.py index 95c3dbac23..34a347fa7d 100644 --- a/tests/client/test_probe.py +++ b/tests/client/test_probe.py @@ -17,18 +17,9 @@ import anyio import httpx +import mcp_types as types import pytest - -from mcp import types -from mcp.client._probe import _parse_supported, negotiate_auto -from mcp.client.session import ClientSession -from mcp.shared.exceptions import MCPError -from mcp.shared.version import ( - HANDSHAKE_PROTOCOL_VERSIONS, - LATEST_MODERN_VERSION, - MODERN_PROTOCOL_VERSIONS, -) -from mcp.types import ( +from mcp_types import ( INTERNAL_ERROR, INVALID_REQUEST, METHOD_NOT_FOUND, @@ -37,6 +28,15 @@ Implementation, ServerCapabilities, ) +from mcp_types.version import ( + HANDSHAKE_PROTOCOL_VERSIONS, + LATEST_MODERN_VERSION, + MODERN_PROTOCOL_VERSIONS, +) + +from mcp.client._probe import _parse_supported, negotiate_auto +from mcp.client.session import ClientSession +from mcp.shared.exceptions import MCPError pytestmark = pytest.mark.anyio diff --git a/tests/client/test_sampling_callback.py b/tests/client/test_sampling_callback.py index af255ee249..d9bfddaf27 100644 --- a/tests/client/test_sampling_callback.py +++ b/tests/client/test_sampling_callback.py @@ -1,10 +1,5 @@ import pytest - -from mcp import Client -from mcp.client import ClientRequestContext -from mcp.server.mcpserver import Context, MCPServer -from mcp.shared.exceptions import MCPError -from mcp.types import ( +from mcp_types import ( INVALID_REQUEST, CreateMessageRequestParams, CreateMessageResult, @@ -14,6 +9,11 @@ ToolUseContent, ) +from mcp import Client +from mcp.client import ClientRequestContext +from mcp.server.mcpserver import Context, MCPServer +from mcp.shared.exceptions import MCPError + @pytest.mark.anyio async def test_sampling_callback(): diff --git a/tests/client/test_session.py b/tests/client/test_session.py index f46d6e6069..b66ca1bbaa 100644 --- a/tests/client/test_session.py +++ b/tests/client/test_session.py @@ -7,21 +7,9 @@ import anyio import anyio.abc import anyio.streams.memory +import mcp_types as types import pytest -from pydantic import FileUrl, ValidationError - -from mcp import MCPError, types -from mcp.client import ClientRequestContext -from mcp.client.client import Client -from mcp.client.session import DEFAULT_CLIENT_INFO, ClientSession -from mcp.server import Server, ServerRequestContext -from mcp.shared.direct_dispatcher import create_direct_dispatcher_pair -from mcp.shared.dispatcher import CallOptions, DispatchContext, OnNotify, OnRequest -from mcp.shared.message import SessionMessage -from mcp.shared.session import RequestResponder -from mcp.shared.transport_context import TransportContext -from mcp.shared.version import HANDSHAKE_PROTOCOL_VERSIONS, LATEST_HANDSHAKE_VERSION -from mcp.types import ( +from mcp_types import ( CONNECTION_CLOSED, INTERNAL_ERROR, INVALID_PARAMS, @@ -44,6 +32,19 @@ client_notification_adapter, client_request_adapter, ) +from mcp_types.version import HANDSHAKE_PROTOCOL_VERSIONS, LATEST_HANDSHAKE_VERSION +from pydantic import FileUrl, ValidationError + +from mcp import MCPError +from mcp.client import ClientRequestContext +from mcp.client.client import Client +from mcp.client.session import DEFAULT_CLIENT_INFO, ClientSession +from mcp.server import Server, ServerRequestContext +from mcp.shared.direct_dispatcher import create_direct_dispatcher_pair +from mcp.shared.dispatcher import CallOptions, DispatchContext, OnNotify, OnRequest +from mcp.shared.message import SessionMessage +from mcp.shared.session import RequestResponder +from mcp.shared.transport_context import TransportContext _SendToClient = anyio.streams.memory.MemoryObjectSendStream[SessionMessage | Exception] _RecvFromClient = anyio.streams.memory.MemoryObjectReceiveStream[SessionMessage] diff --git a/tests/client/test_session_concurrency.py b/tests/client/test_session_concurrency.py index 512a876ee9..0a0ae62dde 100644 --- a/tests/client/test_session_concurrency.py +++ b/tests/client/test_session_concurrency.py @@ -3,11 +3,7 @@ import anyio import pytest from inline_snapshot import snapshot - -from mcp import Client -from mcp.client import ClientRequestContext -from mcp.server.mcpserver import Context, MCPServer -from mcp.types import ( +from mcp_types import ( CallToolResult, CreateMessageRequestParams, CreateMessageResult, @@ -15,6 +11,10 @@ TextContent, ) +from mcp import Client +from mcp.client import ClientRequestContext +from mcp.server.mcpserver import Context, MCPServer + pytestmark = pytest.mark.anyio diff --git a/tests/client/test_session_group.py b/tests/client/test_session_group.py index faa4281e3c..dae0766168 100644 --- a/tests/client/test_session_group.py +++ b/tests/client/test_session_group.py @@ -2,10 +2,10 @@ from unittest import mock import httpx +import mcp_types as types import pytest import mcp -from mcp import types from mcp.client.session_group import ( ClientSessionGroup, ClientSessionParameters, diff --git a/tests/client/test_stdio.py b/tests/client/test_stdio.py index f3cb88dc9c..0b0695378b 100644 --- a/tests/client/test_stdio.py +++ b/tests/client/test_stdio.py @@ -26,6 +26,7 @@ import trio import trio.testing from anyio.streams.memory import MemoryObjectReceiveStream +from mcp_types import CONNECTION_CLOSED, JSONRPCMessage, JSONRPCRequest, JSONRPCResponse from mcp.client import stdio from mcp.client._transport import ReadStream @@ -42,7 +43,6 @@ from mcp.os.win32.utilities import FallbackProcess from mcp.shared.exceptions import MCPError from mcp.shared.message import SessionMessage -from mcp.types import CONNECTION_CLOSED, JSONRPCMessage, JSONRPCRequest, JSONRPCResponse # --------------------------------------------------------------------------- # In-process fake of the spawned server process diff --git a/tests/client/test_streamable_http.py b/tests/client/test_streamable_http.py index 086694aae4..99ff6f03e5 100644 --- a/tests/client/test_streamable_http.py +++ b/tests/client/test_streamable_http.py @@ -13,11 +13,11 @@ import httpx import pytest from inline_snapshot import snapshot +from mcp_types import METHOD_NOT_FOUND, JSONRPCError, JSONRPCNotification, JSONRPCRequest, JSONRPCResponse from mcp.client.streamable_http import streamable_http_client from mcp.shared.inbound import MCP_PROTOCOL_VERSION_HEADER, encode_header_value from mcp.shared.message import ClientMessageMetadata, SessionMessage -from mcp.types import METHOD_NOT_FOUND, JSONRPCError, JSONRPCNotification, JSONRPCRequest, JSONRPCResponse @pytest.mark.parametrize( diff --git a/tests/client/transports/test_memory.py b/tests/client/transports/test_memory.py index da9b95f721..375fe972a6 100644 --- a/tests/client/transports/test_memory.py +++ b/tests/client/transports/test_memory.py @@ -6,14 +6,15 @@ import anyio import anyio.lowlevel +import mcp_types as types import pytest +from mcp_types import ListResourcesResult, Resource -from mcp import Client, types +from mcp import Client from mcp.client import _memory from mcp.client._memory import InMemoryTransport from mcp.server import Server, ServerRequestContext from mcp.server.mcpserver import MCPServer -from mcp.types import ListResourcesResult, Resource @pytest.fixture diff --git a/tests/interaction/README.md b/tests/interaction/README.md index 863be7d6c7..feb5ca5d15 100644 --- a/tests/interaction/README.md +++ b/tests/interaction/README.md @@ -24,7 +24,7 @@ flows — with a single subprocess test for stdio. rewrite preserved behaviour; a passing test that pins the wrong output exactly does. Known divergences are recorded as data on the requirement (see below), not worked around in the test. - **Spec-mandated assertions, not implementation quirks.** Error *codes* are asserted against - the constants in `mcp.types`; error *message strings* are pinned only where they are the + the constants in `mcp_types`; error *message strings* are pinned only where they are the SDK's own deliberate output. - **No sleeps, no real I/O.** Concurrency is coordinated with `anyio.Event`; every wait that could hang is bounded by `anyio.fail_after(5)`. The HTTP and OAuth tests drive the Starlette @@ -243,7 +243,7 @@ many requirements at once; if the assertions would be separate, write separate t |---|---| | the result of a transformation (arguments → output, exception → error result) | `result == snapshot(...)` of the full object, so any field the implementation adds or drops fails the test | | pass-through of an opaque value (`_meta`, cursors) | identity against the same variable that was sent — a snapshot of a pass-through value only matches the input because a human checked two literals correspond | -| an error | `pytest.raises(MCPError)` and a snapshot of `exc.value.error` when the message is the SDK's own; a plain `==` on `.code` against the `mcp.types` constant when it is not | +| an error | `pytest.raises(MCPError)` and a snapshot of `exc.value.error` when the message is the SDK's own; a plain `==` on `.code` against the `mcp_types` constant when it is not | | third-party output embedded in a result (validation messages) | the stable prefix only — never pin text that changes with a dependency upgrade | ### Notifications and concurrency diff --git a/tests/interaction/_connect.py b/tests/interaction/_connect.py index bb8e75ed43..05b2d2277b 100644 --- a/tests/interaction/_connect.py +++ b/tests/interaction/_connect.py @@ -14,6 +14,16 @@ import httpx from httpx_sse import ServerSentEvent, aconnect_sse +from mcp_types import ( + ClientCapabilities, + Implementation, + InitializeRequestParams, + JSONRPCMessage, + JSONRPCRequest, + JSONRPCResponse, + jsonrpc_message_adapter, +) +from mcp_types.version import LATEST_HANDSHAKE_VERSION, MODERN_PROTOCOL_VERSIONS from starlette.applications import Starlette from starlette.requests import Request from starlette.responses import Response @@ -31,16 +41,6 @@ from mcp.server.streamable_http import EventStore from mcp.server.streamable_http_manager import StreamableHTTPSessionManager from mcp.server.transport_security import TransportSecuritySettings -from mcp.shared.version import LATEST_HANDSHAKE_VERSION, MODERN_PROTOCOL_VERSIONS -from mcp.types import ( - ClientCapabilities, - Implementation, - InitializeRequestParams, - JSONRPCMessage, - JSONRPCRequest, - JSONRPCResponse, - jsonrpc_message_adapter, -) from tests.interaction.transports._bridge import StreamingASGITransport # The in-process app is mounted at this origin purely so URLs are well-formed; nothing listens here. diff --git a/tests/interaction/_helpers.py b/tests/interaction/_helpers.py index 54d41e1e7b..0641aeab97 100644 --- a/tests/interaction/_helpers.py +++ b/tests/interaction/_helpers.py @@ -9,12 +9,12 @@ from types import TracebackType import anyio +from mcp_types import ClientResult, ServerNotification, ServerRequest from typing_extensions import Self from mcp.client._transport import ReadStream, Transport, TransportStreams, WriteStream from mcp.shared.message import SessionMessage from mcp.shared.session import RequestResponder -from mcp.types import ClientResult, ServerNotification, ServerRequest # TODO: this union is the parameter type of every client message handler (MessageHandlerFnT), # but the SDK does not export a name for it -- writing a correctly-typed handler requires diff --git a/tests/interaction/_modern_vocab.py b/tests/interaction/_modern_vocab.py index 7531724ee3..2f69763419 100644 --- a/tests/interaction/_modern_vocab.py +++ b/tests/interaction/_modern_vocab.py @@ -18,8 +18,7 @@ from dataclasses import dataclass import httpx - -from mcp.types import JSONRPCMessage, jsonrpc_message_adapter +from mcp_types import JSONRPCMessage, jsonrpc_message_adapter #: Substrings that must not appear anywhere in a request body or JSON-RPC frame on a legacy #: exchange. Matching is by raw substring against the by-alias JSON serialisation, so a leaked diff --git a/tests/interaction/_requirements.py b/tests/interaction/_requirements.py index a2b4178054..50449c459a 100644 --- a/tests/interaction/_requirements.py +++ b/tests/interaction/_requirements.py @@ -38,8 +38,7 @@ from typing import Any, Literal, TypeVar import pytest - -from mcp.shared.version import KNOWN_PROTOCOL_VERSIONS +from mcp_types.version import KNOWN_PROTOCOL_VERSIONS SpecVersion = Literal["2025-11-25", "2026-07-28"] """A protocol version the suite parametrizes over. Both values are typed even though only one is diff --git a/tests/interaction/auth/test_authorize_token.py b/tests/interaction/auth/test_authorize_token.py index 62822ca804..d4eb591b59 100644 --- a/tests/interaction/auth/test_authorize_token.py +++ b/tests/interaction/auth/test_authorize_token.py @@ -20,15 +20,15 @@ from urllib.parse import parse_qsl, quote, urlsplit import anyio +import mcp_types as types import pytest from inline_snapshot import snapshot +from mcp_types import ListToolsResult, Tool from pydantic import AnyHttpUrl, AnyUrl -from mcp import types from mcp.client.auth import OAuthFlowError from mcp.server import Server, ServerRequestContext from mcp.shared.auth import OAuthClientInformationFull, OAuthMetadata -from mcp.types import ListToolsResult, Tool from tests.interaction._connect import BASE_URL from tests.interaction._requirements import requirement from tests.interaction.auth._harness import ( diff --git a/tests/interaction/auth/test_bearer.py b/tests/interaction/auth/test_bearer.py index 341a8e0db9..55029c9f43 100644 --- a/tests/interaction/auth/test_bearer.py +++ b/tests/interaction/auth/test_bearer.py @@ -13,10 +13,10 @@ import httpx import pytest from inline_snapshot import snapshot +from mcp_types import JSONRPCResponse from mcp.server import Server from mcp.server.auth.provider import AccessToken -from mcp.types import JSONRPCResponse from tests.interaction._connect import base_headers, initialize_body, mounted_app from tests.interaction._requirements import requirement from tests.interaction.auth._harness import StaticTokenVerifier, auth_settings diff --git a/tests/interaction/auth/test_discovery.py b/tests/interaction/auth/test_discovery.py index 5038fa8e65..1317fd19de 100644 --- a/tests/interaction/auth/test_discovery.py +++ b/tests/interaction/auth/test_discovery.py @@ -13,15 +13,15 @@ import json import anyio +import mcp_types as types import pytest from inline_snapshot import snapshot +from mcp_types import ListToolsResult, Tool from pydantic import AnyHttpUrl -from mcp import types from mcp.client.auth import OAuthFlowError, OAuthRegistrationError from mcp.server import Server, ServerRequestContext from mcp.shared.auth import OAuthMetadata, ProtectedResourceMetadata -from mcp.types import ListToolsResult, Tool from tests.interaction._connect import BASE_URL, mounted_app from tests.interaction._requirements import requirement from tests.interaction.auth._harness import ( diff --git a/tests/interaction/auth/test_flow.py b/tests/interaction/auth/test_flow.py index 96903ef910..e98735abf8 100644 --- a/tests/interaction/auth/test_flow.py +++ b/tests/interaction/auth/test_flow.py @@ -14,15 +14,15 @@ import anyio import httpx +import mcp_types as types import pytest from inline_snapshot import snapshot +from mcp_types import CallToolResult, ListToolsResult, TextContent, Tool from pydantic import AnyUrl -from mcp import types from mcp.server import Server, ServerRequestContext from mcp.server.auth.middleware.auth_context import get_access_token from mcp.shared.auth import OAuthClientInformationFull -from mcp.types import CallToolResult, ListToolsResult, TextContent, Tool from tests.interaction._connect import BASE_URL from tests.interaction._requirements import requirement from tests.interaction.auth._harness import ( diff --git a/tests/interaction/auth/test_lifecycle.py b/tests/interaction/auth/test_lifecycle.py index f2cf962a10..c810f8c449 100644 --- a/tests/interaction/auth/test_lifecycle.py +++ b/tests/interaction/auth/test_lifecycle.py @@ -11,15 +11,16 @@ from urllib.parse import parse_qsl, urlsplit import anyio +import mcp_types as types import pytest from inline_snapshot import snapshot +from mcp_types import INTERNAL_ERROR, ListToolsResult, Tool from pydantic import AnyHttpUrl, AnyUrl -from mcp import MCPError, types +from mcp import MCPError from mcp.client.auth.extensions.client_credentials import ClientCredentialsOAuthProvider, PrivateKeyJWTOAuthProvider from mcp.server import Server, ServerRequestContext from mcp.shared.auth import OAuthClientInformationFull, OAuthMetadata -from mcp.types import INTERNAL_ERROR, ListToolsResult, Tool from tests.interaction._connect import BASE_URL from tests.interaction._requirements import requirement from tests.interaction.auth._harness import ( diff --git a/tests/interaction/lowlevel/test_cancellation.py b/tests/interaction/lowlevel/test_cancellation.py index 6e6c2b6f60..247e1135a6 100644 --- a/tests/interaction/lowlevel/test_cancellation.py +++ b/tests/interaction/lowlevel/test_cancellation.py @@ -7,15 +7,10 @@ """ import anyio +import mcp_types as types import pytest from inline_snapshot import snapshot - -from mcp import MCPError, types -from mcp.client import ClientRequestContext, ClientSession -from mcp.server import Server, ServerRequestContext -from mcp.shared.memory import MessageStream, create_client_server_memory_streams -from mcp.shared.message import SessionMessage -from mcp.types import ( +from mcp_types import ( REQUEST_TIMEOUT, CallToolResult, EmptyResult, @@ -29,6 +24,12 @@ ServerCapabilities, TextContent, ) + +from mcp import MCPError +from mcp.client import ClientRequestContext, ClientSession +from mcp.server import Server, ServerRequestContext +from mcp.shared.memory import MessageStream, create_client_server_memory_streams +from mcp.shared.message import SessionMessage from tests.interaction._connect import Connect from tests.interaction._helpers import IncomingMessage from tests.interaction._requirements import requirement diff --git a/tests/interaction/lowlevel/test_client_connect.py b/tests/interaction/lowlevel/test_client_connect.py index 33c988e14e..69fd5c4e85 100644 --- a/tests/interaction/lowlevel/test_client_connect.py +++ b/tests/interaction/lowlevel/test_client_connect.py @@ -17,18 +17,9 @@ import anyio import httpx +import mcp_types as types import pytest - -from mcp import MCPError, types -from mcp.client._memory import InMemoryTransport -from mcp.client._transport import TransportStreams -from mcp.client.client import Client -from mcp.client.streamable_http import streamable_http_client -from mcp.server import Server, ServerRequestContext -from mcp.shared.memory import MessageStream, create_client_server_memory_streams -from mcp.shared.message import SessionMessage -from mcp.shared.version import LATEST_HANDSHAKE_VERSION, LATEST_MODERN_VERSION, MODERN_PROTOCOL_VERSIONS -from mcp.types import ( +from mcp_types import ( CLIENT_CAPABILITIES_META_KEY, CLIENT_INFO_META_KEY, INVALID_REQUEST, @@ -45,6 +36,16 @@ ServerCapabilities, ToolsCapability, ) +from mcp_types.version import LATEST_HANDSHAKE_VERSION, LATEST_MODERN_VERSION, MODERN_PROTOCOL_VERSIONS + +from mcp import MCPError +from mcp.client._memory import InMemoryTransport +from mcp.client._transport import TransportStreams +from mcp.client.client import Client +from mcp.client.streamable_http import streamable_http_client +from mcp.server import Server, ServerRequestContext +from mcp.shared.memory import MessageStream, create_client_server_memory_streams +from mcp.shared.message import SessionMessage from tests.interaction._connect import BASE_URL, Connect, mounted_app from tests.interaction._helpers import RecordingTransport from tests.interaction._requirements import requirement diff --git a/tests/interaction/lowlevel/test_completion.py b/tests/interaction/lowlevel/test_completion.py index 8478831f31..d75865a2f0 100644 --- a/tests/interaction/lowlevel/test_completion.py +++ b/tests/interaction/lowlevel/test_completion.py @@ -1,11 +1,9 @@ """Completion interactions against the low-level Server, driven through the public Client API.""" +import mcp_types as types import pytest from inline_snapshot import snapshot - -from mcp import MCPError, types -from mcp.server import Server, ServerRequestContext -from mcp.types import ( +from mcp_types import ( INVALID_PARAMS, METHOD_NOT_FOUND, CompleteResult, @@ -14,6 +12,9 @@ PromptReference, ResourceTemplateReference, ) + +from mcp import MCPError +from mcp.server import Server, ServerRequestContext from tests.interaction._connect import Connect from tests.interaction._requirements import requirement diff --git a/tests/interaction/lowlevel/test_elicitation.py b/tests/interaction/lowlevel/test_elicitation.py index 52adc3b1ef..b8393dd316 100644 --- a/tests/interaction/lowlevel/test_elicitation.py +++ b/tests/interaction/lowlevel/test_elicitation.py @@ -5,15 +5,10 @@ """ import anyio +import mcp_types as types import pytest from inline_snapshot import snapshot - -from mcp import MCPError, UrlElicitationRequiredError, types -from mcp.client import ClientRequestContext, ClientSession -from mcp.server import Server, ServerRequestContext -from mcp.shared.memory import MessageStream, create_client_server_memory_streams -from mcp.shared.message import SessionMessage -from mcp.types import ( +from mcp_types import ( CallToolResult, ElicitCompleteNotification, ElicitCompleteNotificationParams, @@ -31,6 +26,12 @@ ServerCapabilities, TextContent, ) + +from mcp import MCPError, UrlElicitationRequiredError +from mcp.client import ClientRequestContext, ClientSession +from mcp.server import Server, ServerRequestContext +from mcp.shared.memory import MessageStream, create_client_server_memory_streams +from mcp.shared.message import SessionMessage from tests.interaction._connect import Connect from tests.interaction._helpers import IncomingMessage from tests.interaction._requirements import requirement diff --git a/tests/interaction/lowlevel/test_flows.py b/tests/interaction/lowlevel/test_flows.py index 75b8aa61ea..77cf78888f 100644 --- a/tests/interaction/lowlevel/test_flows.py +++ b/tests/interaction/lowlevel/test_flows.py @@ -9,14 +9,10 @@ from collections.abc import Awaitable, Callable import anyio +import mcp_types as types import pytest from inline_snapshot import snapshot - -from mcp import MCPError, UrlElicitationRequiredError, types -from mcp.client import ClientRequestContext -from mcp.server import Server, ServerRequestContext -from mcp.server.session import ServerSession -from mcp.types import ( +from mcp_types import ( URL_ELICITATION_REQUIRED, CallToolResult, ElicitCompleteNotification, @@ -31,6 +27,11 @@ TextResourceContents, Tool, ) + +from mcp import MCPError, UrlElicitationRequiredError +from mcp.client import ClientRequestContext +from mcp.server import Server, ServerRequestContext +from mcp.server.session import ServerSession from tests.interaction._connect import Connect from tests.interaction._helpers import IncomingMessage from tests.interaction._requirements import requirement diff --git a/tests/interaction/lowlevel/test_initialize.py b/tests/interaction/lowlevel/test_initialize.py index d1f79c0cb7..29eb7297c9 100644 --- a/tests/interaction/lowlevel/test_initialize.py +++ b/tests/interaction/lowlevel/test_initialize.py @@ -8,16 +8,10 @@ """ import anyio +import mcp_types as types import pytest from inline_snapshot import snapshot - -from mcp import MCPError, types -from mcp.client import ClientRequestContext, ClientSession -from mcp.client._memory import InMemoryTransport -from mcp.server import Server, ServerRequestContext -from mcp.shared.memory import MessageStream, create_client_server_memory_streams -from mcp.shared.message import SessionMessage -from mcp.types import ( +from mcp_types import ( INVALID_PARAMS, CallToolResult, ClientCapabilities, @@ -40,6 +34,13 @@ TextContent, ToolsCapability, ) + +from mcp import MCPError +from mcp.client import ClientRequestContext, ClientSession +from mcp.client._memory import InMemoryTransport +from mcp.server import Server, ServerRequestContext +from mcp.shared.memory import MessageStream, create_client_server_memory_streams +from mcp.shared.message import SessionMessage from tests.interaction._connect import Connect from tests.interaction._requirements import requirement diff --git a/tests/interaction/lowlevel/test_list_changed.py b/tests/interaction/lowlevel/test_list_changed.py index a2f85eeacf..e7d497ba2d 100644 --- a/tests/interaction/lowlevel/test_list_changed.py +++ b/tests/interaction/lowlevel/test_list_changed.py @@ -15,18 +15,18 @@ """ import anyio +import mcp_types as types import pytest from inline_snapshot import snapshot - -from mcp import types -from mcp.server import Server, ServerRequestContext -from mcp.types import ( +from mcp_types import ( CallToolResult, PromptListChangedNotification, ResourceListChangedNotification, TextContent, ToolListChangedNotification, ) + +from mcp.server import Server, ServerRequestContext from tests.interaction._connect import Connect from tests.interaction._helpers import IncomingMessage from tests.interaction._requirements import requirement diff --git a/tests/interaction/lowlevel/test_logging.py b/tests/interaction/lowlevel/test_logging.py index 4b8c3ebb97..90af931cf2 100644 --- a/tests/interaction/lowlevel/test_logging.py +++ b/tests/interaction/lowlevel/test_logging.py @@ -5,12 +5,12 @@ streamable HTTP, so plain-list collection is deterministic on every transport leg. """ +import mcp_types as types import pytest from inline_snapshot import snapshot +from mcp_types import CallToolResult, EmptyResult, LoggingMessageNotificationParams, TextContent -from mcp import types from mcp.server import Server, ServerRequestContext -from mcp.types import CallToolResult, EmptyResult, LoggingMessageNotificationParams, TextContent from tests.interaction._connect import Connect from tests.interaction._requirements import requirement diff --git a/tests/interaction/lowlevel/test_meta.py b/tests/interaction/lowlevel/test_meta.py index a9e4f994d8..27cf25e30c 100644 --- a/tests/interaction/lowlevel/test_meta.py +++ b/tests/interaction/lowlevel/test_meta.py @@ -5,11 +5,11 @@ which also proves the SDK injected nothing alongside it. """ +import mcp_types as types import pytest +from mcp_types import CallToolResult, RequestParamsMeta, TextContent -from mcp import types from mcp.server import Server, ServerRequestContext -from mcp.types import CallToolResult, RequestParamsMeta, TextContent from tests.interaction._connect import Connect from tests.interaction._requirements import requirement diff --git a/tests/interaction/lowlevel/test_pagination.py b/tests/interaction/lowlevel/test_pagination.py index 77db90401e..01bc0a99bd 100644 --- a/tests/interaction/lowlevel/test_pagination.py +++ b/tests/interaction/lowlevel/test_pagination.py @@ -5,12 +5,10 @@ pagination scheme. """ +import mcp_types as types import pytest from inline_snapshot import snapshot - -from mcp import MCPError, types -from mcp.server import Server, ServerRequestContext -from mcp.types import ( +from mcp_types import ( INVALID_PARAMS, ListPromptsResult, ListResourcesResult, @@ -21,6 +19,9 @@ ResourceTemplate, Tool, ) + +from mcp import MCPError +from mcp.server import Server, ServerRequestContext from tests.interaction._connect import Connect from tests.interaction._requirements import requirement diff --git a/tests/interaction/lowlevel/test_ping.py b/tests/interaction/lowlevel/test_ping.py index e65bbe3ae3..4ccf800e2f 100644 --- a/tests/interaction/lowlevel/test_ping.py +++ b/tests/interaction/lowlevel/test_ping.py @@ -1,11 +1,11 @@ """Ping interactions against the low-level Server, driven through the public Client API.""" +import mcp_types as types import pytest from inline_snapshot import snapshot +from mcp_types import CallToolResult, EmptyResult, TextContent -from mcp import types from mcp.server import Server, ServerRequestContext -from mcp.types import CallToolResult, EmptyResult, TextContent from tests.interaction._connect import Connect from tests.interaction._requirements import requirement diff --git a/tests/interaction/lowlevel/test_progress.py b/tests/interaction/lowlevel/test_progress.py index 4fb2c7c224..b2e94bae36 100644 --- a/tests/interaction/lowlevel/test_progress.py +++ b/tests/interaction/lowlevel/test_progress.py @@ -10,14 +10,14 @@ """ import anyio +import mcp_types as types import pytest from inline_snapshot import snapshot +from mcp_types import CallToolResult, ProgressNotification, ProgressNotificationParams, ProgressToken, TextContent -from mcp import types from mcp.server import Server, ServerRequestContext from mcp.server.session import ServerSession from mcp.shared.session import ProgressFnT -from mcp.types import CallToolResult, ProgressNotification, ProgressNotificationParams, ProgressToken, TextContent from tests.interaction._connect import Connect from tests.interaction._helpers import IncomingMessage from tests.interaction._requirements import requirement diff --git a/tests/interaction/lowlevel/test_prompts.py b/tests/interaction/lowlevel/test_prompts.py index 868b82692c..eb19d4d60d 100644 --- a/tests/interaction/lowlevel/test_prompts.py +++ b/tests/interaction/lowlevel/test_prompts.py @@ -1,11 +1,9 @@ """Prompt interactions against the low-level Server, driven through the public Client API.""" +import mcp_types as types import pytest from inline_snapshot import snapshot - -from mcp import MCPError, types -from mcp.server import Server, ServerRequestContext -from mcp.types import ( +from mcp_types import ( INVALID_PARAMS, AudioContent, EmbeddedResource, @@ -20,6 +18,9 @@ TextContent, TextResourceContents, ) + +from mcp import MCPError +from mcp.server import Server, ServerRequestContext from tests.interaction._connect import Connect from tests.interaction._requirements import requirement diff --git a/tests/interaction/lowlevel/test_resources.py b/tests/interaction/lowlevel/test_resources.py index a5a4bdc14d..44ab33e64a 100644 --- a/tests/interaction/lowlevel/test_resources.py +++ b/tests/interaction/lowlevel/test_resources.py @@ -3,12 +3,10 @@ import base64 import anyio +import mcp_types as types import pytest from inline_snapshot import snapshot - -from mcp import MCPError, types -from mcp.server import Server, ServerRequestContext -from mcp.types import ( +from mcp_types import ( METHOD_NOT_FOUND, Annotations, BlobResourceContents, @@ -26,6 +24,9 @@ TextContent, TextResourceContents, ) + +from mcp import MCPError +from mcp.server import Server, ServerRequestContext from tests.interaction._connect import Connect from tests.interaction._helpers import IncomingMessage from tests.interaction._requirements import requirement diff --git a/tests/interaction/lowlevel/test_roots.py b/tests/interaction/lowlevel/test_roots.py index 391fc8ec61..5e38b8aab1 100644 --- a/tests/interaction/lowlevel/test_roots.py +++ b/tests/interaction/lowlevel/test_roots.py @@ -1,14 +1,15 @@ """Roots interactions against the low-level Server, driven through the public Client API.""" import anyio +import mcp_types as types import pytest from inline_snapshot import snapshot +from mcp_types import INTERNAL_ERROR, CallToolResult, ErrorData, ListRootsResult, Root, TextContent from pydantic import FileUrl -from mcp import MCPError, types +from mcp import MCPError from mcp.client import ClientRequestContext from mcp.server import Server, ServerRequestContext -from mcp.types import INTERNAL_ERROR, CallToolResult, ErrorData, ListRootsResult, Root, TextContent from tests.interaction._connect import Connect from tests.interaction._requirements import requirement diff --git a/tests/interaction/lowlevel/test_sampling.py b/tests/interaction/lowlevel/test_sampling.py index fb66c3ad81..4d2e888c49 100644 --- a/tests/interaction/lowlevel/test_sampling.py +++ b/tests/interaction/lowlevel/test_sampling.py @@ -5,14 +5,11 @@ round-trips what it received back to the test through its tool result. """ +import mcp_types as types import pydantic import pytest from inline_snapshot import snapshot - -from mcp import MCPError, types -from mcp.client import ClientRequestContext -from mcp.server import Server, ServerRequestContext -from mcp.types import ( +from mcp_types import ( AudioContent, CallToolResult, CreateMessageRequestParams, @@ -28,6 +25,10 @@ ToolResultContent, ToolUseContent, ) + +from mcp import MCPError +from mcp.client import ClientRequestContext +from mcp.server import Server, ServerRequestContext from tests.interaction._connect import Connect from tests.interaction._requirements import requirement diff --git a/tests/interaction/lowlevel/test_timeouts.py b/tests/interaction/lowlevel/test_timeouts.py index 044c055032..316c69245c 100644 --- a/tests/interaction/lowlevel/test_timeouts.py +++ b/tests/interaction/lowlevel/test_timeouts.py @@ -9,17 +9,18 @@ """ import anyio +import mcp_types as types import pytest from inline_snapshot import snapshot +from mcp_types import REQUEST_TIMEOUT, CallToolResult, ErrorData, JSONRPCNotification, TextContent from trio.testing import MockClock -from mcp import MCPError, types +from mcp import MCPError from mcp.client import ClientRequestContext from mcp.client._memory import InMemoryTransport from mcp.client.client import Client from mcp.server import Server, ServerRequestContext from mcp.shared.message import SessionMessage -from mcp.types import REQUEST_TIMEOUT, CallToolResult, ErrorData, JSONRPCNotification, TextContent from tests.interaction._helpers import RecordingTransport from tests.interaction._requirements import requirement diff --git a/tests/interaction/lowlevel/test_tools.py b/tests/interaction/lowlevel/test_tools.py index e8053fbaa7..861dd75e44 100644 --- a/tests/interaction/lowlevel/test_tools.py +++ b/tests/interaction/lowlevel/test_tools.py @@ -1,12 +1,10 @@ """Tool interactions against the low-level Server, driven through the public Client API.""" import anyio +import mcp_types as types import pytest from inline_snapshot import snapshot - -from mcp import MCPError, types -from mcp.server import Server, ServerRequestContext -from mcp.types import ( +from mcp_types import ( INVALID_PARAMS, AudioContent, CallToolResult, @@ -21,6 +19,9 @@ Tool, ToolAnnotations, ) + +from mcp import MCPError +from mcp.server import Server, ServerRequestContext from tests.interaction._connect import Connect from tests.interaction._requirements import requirement diff --git a/tests/interaction/lowlevel/test_wire.py b/tests/interaction/lowlevel/test_wire.py index d8f9a530bd..cddbfdfa5d 100644 --- a/tests/interaction/lowlevel/test_wire.py +++ b/tests/interaction/lowlevel/test_wire.py @@ -11,17 +11,10 @@ """ import anyio +import mcp_types as types import pytest from inline_snapshot import snapshot - -from mcp import MCPError, types -from mcp.client import ClientRequestContext, ClientSession -from mcp.client._memory import InMemoryTransport -from mcp.client.client import Client -from mcp.server import Server, ServerRequestContext -from mcp.shared.memory import create_client_server_memory_streams -from mcp.shared.message import SessionMessage -from mcp.types import ( +from mcp_types import ( CONNECTION_CLOSED, INVALID_PARAMS, CallToolRequest, @@ -36,6 +29,14 @@ ListRootsResult, TextContent, ) + +from mcp import MCPError +from mcp.client import ClientRequestContext, ClientSession +from mcp.client._memory import InMemoryTransport +from mcp.client.client import Client +from mcp.server import Server, ServerRequestContext +from mcp.shared.memory import create_client_server_memory_streams +from mcp.shared.message import SessionMessage from tests.interaction._helpers import RecordingTransport, _RecordingReadStream from tests.interaction._requirements import requirement diff --git a/tests/interaction/mcpserver/test_completion.py b/tests/interaction/mcpserver/test_completion.py index 30ff9613e3..7d3f164098 100644 --- a/tests/interaction/mcpserver/test_completion.py +++ b/tests/interaction/mcpserver/test_completion.py @@ -1,9 +1,7 @@ """Completion behaviour against MCPServer, driven through the public Client API.""" import pytest - -from mcp.server.mcpserver import MCPServer -from mcp.types import ( +from mcp_types import ( Completion, CompletionArgument, CompletionContext, @@ -11,6 +9,8 @@ PromptReference, ResourceTemplateReference, ) + +from mcp.server.mcpserver import MCPServer from tests.interaction._connect import Connect from tests.interaction._requirements import requirement diff --git a/tests/interaction/mcpserver/test_context.py b/tests/interaction/mcpserver/test_context.py index edbbc94467..27c0c70cc1 100644 --- a/tests/interaction/mcpserver/test_context.py +++ b/tests/interaction/mcpserver/test_context.py @@ -2,13 +2,7 @@ import pytest from inline_snapshot import snapshot -from pydantic import BaseModel - -from mcp import MCPError -from mcp.client import ClientRequestContext -from mcp.server.elicitation import AcceptedElicitation -from mcp.server.mcpserver import Context, MCPServer -from mcp.types import ( +from mcp_types import ( METHOD_NOT_FOUND, CallToolResult, ElicitRequestFormParams, @@ -20,6 +14,12 @@ LoggingMessageNotificationParams, TextContent, ) +from pydantic import BaseModel + +from mcp import MCPError +from mcp.client import ClientRequestContext +from mcp.server.elicitation import AcceptedElicitation +from mcp.server.mcpserver import Context, MCPServer from tests.interaction._connect import Connect from tests.interaction._helpers import IncomingMessage from tests.interaction._requirements import requirement diff --git a/tests/interaction/mcpserver/test_prompts.py b/tests/interaction/mcpserver/test_prompts.py index 2095f086d4..58c8b48c7f 100644 --- a/tests/interaction/mcpserver/test_prompts.py +++ b/tests/interaction/mcpserver/test_prompts.py @@ -2,10 +2,7 @@ import pytest from inline_snapshot import snapshot - -from mcp import MCPError -from mcp.server.mcpserver import MCPServer -from mcp.types import ( +from mcp_types import ( ErrorData, GetPromptResult, ListPromptsResult, @@ -14,6 +11,9 @@ PromptMessage, TextContent, ) + +from mcp import MCPError +from mcp.server.mcpserver import MCPServer from tests.interaction._connect import Connect from tests.interaction._requirements import requirement diff --git a/tests/interaction/mcpserver/test_resources.py b/tests/interaction/mcpserver/test_resources.py index d2be655b6b..d7fd996051 100644 --- a/tests/interaction/mcpserver/test_resources.py +++ b/tests/interaction/mcpserver/test_resources.py @@ -2,10 +2,7 @@ import pytest from inline_snapshot import snapshot - -from mcp import MCPError -from mcp.server.mcpserver import MCPServer -from mcp.types import ( +from mcp_types import ( ErrorData, ListResourcesResult, ListResourceTemplatesResult, @@ -14,6 +11,9 @@ ResourceTemplate, TextResourceContents, ) + +from mcp import MCPError +from mcp.server.mcpserver import MCPServer from tests.interaction._connect import Connect from tests.interaction._requirements import requirement diff --git a/tests/interaction/mcpserver/test_tools.py b/tests/interaction/mcpserver/test_tools.py index 1314d85587..a7791d7cda 100644 --- a/tests/interaction/mcpserver/test_tools.py +++ b/tests/interaction/mcpserver/test_tools.py @@ -5,13 +5,7 @@ import pytest from inline_snapshot import snapshot -from pydantic import BaseModel, Field - -from mcp import MCPError -from mcp.server.mcpserver import Context, MCPServer -from mcp.server.mcpserver.exceptions import ToolError -from mcp.shared.exceptions import UrlElicitationRequiredError -from mcp.types import ( +from mcp_types import ( URL_ELICITATION_REQUIRED, CallToolResult, ElicitRequestURLParams, @@ -20,6 +14,12 @@ LoggingMessageNotificationParams, TextContent, ) +from pydantic import BaseModel, Field + +from mcp import MCPError +from mcp.server.mcpserver import Context, MCPServer +from mcp.server.mcpserver.exceptions import ToolError +from mcp.shared.exceptions import UrlElicitationRequiredError from tests.interaction._connect import Connect from tests.interaction._helpers import IncomingMessage from tests.interaction._requirements import requirement diff --git a/tests/interaction/test_coverage.py b/tests/interaction/test_coverage.py index 26e697c3ba..f6df297345 100644 --- a/tests/interaction/test_coverage.py +++ b/tests/interaction/test_coverage.py @@ -14,9 +14,9 @@ from typing import cast import pytest +from mcp_types import LATEST_PROTOCOL_VERSION +from mcp_types.version import KNOWN_PROTOCOL_VERSIONS -from mcp.shared.version import KNOWN_PROTOCOL_VERSIONS -from mcp.types import LATEST_PROTOCOL_VERSION from tests.interaction._requirements import ( CONNECTABLE_TRANSPORTS, REQUIREMENTS, diff --git a/tests/interaction/transports/_event_store.py b/tests/interaction/transports/_event_store.py index 84d1a2646a..265c9a58f6 100644 --- a/tests/interaction/transports/_event_store.py +++ b/tests/interaction/transports/_event_store.py @@ -8,9 +8,9 @@ """ import anyio +from mcp_types import JSONRPCMessage from mcp.server.streamable_http import EventCallback, EventId, EventMessage, EventStore, StreamId -from mcp.types import JSONRPCMessage class SequencedEventStore(EventStore): diff --git a/tests/interaction/transports/_stdio_server.py b/tests/interaction/transports/_stdio_server.py index 0faf0c80ad..cc3dc3a8a1 100644 --- a/tests/interaction/transports/_stdio_server.py +++ b/tests/interaction/transports/_stdio_server.py @@ -11,11 +11,7 @@ import anyio import coverage - -from mcp.server import Server, ServerRequestContext -from mcp.server.stdio import stdio_server -from mcp.shared.exceptions import MCPDeprecationWarning -from mcp.types import ( +from mcp_types import ( CallToolRequestParams, CallToolResult, EmptyResult, @@ -26,6 +22,10 @@ Tool, ) +from mcp.server import Server, ServerRequestContext +from mcp.server.stdio import stdio_server +from mcp.shared.exceptions import MCPDeprecationWarning + async def list_tools(ctx: ServerRequestContext, params: PaginatedRequestParams | None) -> ListToolsResult: return ListToolsResult( diff --git a/tests/interaction/transports/test_client_transport_http.py b/tests/interaction/transports/test_client_transport_http.py index 173371d75d..5508d3e8f9 100644 --- a/tests/interaction/transports/test_client_transport_http.py +++ b/tests/interaction/transports/test_client_transport_http.py @@ -10,15 +10,16 @@ import anyio import httpx +import mcp_types as types import pytest from inline_snapshot import snapshot +from mcp_types import INVALID_REQUEST, CallToolResult, ErrorData, ListToolsResult, TextContent, Tool from starlette.types import Receive, Scope, Send -from mcp import MCPError, types +from mcp import MCPError from mcp.client.client import Client from mcp.client.streamable_http import streamable_http_client from mcp.server import Server, ServerRequestContext -from mcp.types import INVALID_REQUEST, CallToolResult, ErrorData, ListToolsResult, TextContent, Tool from tests.interaction._connect import BASE_URL, NO_DNS_REBINDING_PROTECTION, client_via_http, mounted_app from tests.interaction._requirements import requirement from tests.interaction.transports._bridge import StreamingASGITransport diff --git a/tests/interaction/transports/test_flows.py b/tests/interaction/transports/test_flows.py index e8081a7a1d..13979b3f1a 100644 --- a/tests/interaction/transports/test_flows.py +++ b/tests/interaction/transports/test_flows.py @@ -9,10 +9,10 @@ import httpx import pytest from inline_snapshot import snapshot +from mcp_types import CallToolResult, LoggingMessageNotificationParams, TextContent from mcp.client.session import LoggingFnT from mcp.server.mcpserver import Context, MCPServer -from mcp.types import CallToolResult, LoggingMessageNotificationParams, TextContent from tests.interaction._connect import client_via_http, connect_over_sse, mounted_app from tests.interaction._requirements import requirement diff --git a/tests/interaction/transports/test_hosting_http.py b/tests/interaction/transports/test_hosting_http.py index 5b5c7085b3..e17f2f18f8 100644 --- a/tests/interaction/transports/test_hosting_http.py +++ b/tests/interaction/transports/test_hosting_http.py @@ -11,11 +11,7 @@ from anyio.lowlevel import checkpoint from httpx_sse import ServerSentEvent, aconnect_sse from inline_snapshot import snapshot - -from mcp.server import Server, ServerRequestContext -from mcp.server.transport_security import TransportSecuritySettings -from mcp.shared.version import MODERN_PROTOCOL_VERSIONS -from mcp.types import ( +from mcp_types import ( CLIENT_CAPABILITIES_META_KEY, CLIENT_INFO_META_KEY, INVALID_PARAMS, @@ -36,6 +32,10 @@ SubscribeRequestParams, TextContent, ) +from mcp_types.version import MODERN_PROTOCOL_VERSIONS + +from mcp.server import Server, ServerRequestContext +from mcp.server.transport_security import TransportSecuritySettings from tests.interaction._connect import ( base_headers, initialize_body, diff --git a/tests/interaction/transports/test_hosting_http_modern.py b/tests/interaction/transports/test_hosting_http_modern.py index 52b20629e6..77ac850182 100644 --- a/tests/interaction/transports/test_hosting_http_modern.py +++ b/tests/interaction/transports/test_hosting_http_modern.py @@ -15,13 +15,7 @@ import httpx import pytest from inline_snapshot import snapshot - -from mcp import MCPError -from mcp.client.session import ClientSession -from mcp.client.streamable_http import streamable_http_client -from mcp.server import Server, ServerRequestContext -from mcp.shared.version import LATEST_MODERN_VERSION -from mcp.types import ( +from mcp_types import ( CLIENT_CAPABILITIES_META_KEY, INTERNAL_ERROR, INVALID_PARAMS, @@ -41,6 +35,12 @@ TextContent, Tool, ) +from mcp_types.version import LATEST_MODERN_VERSION + +from mcp import MCPError +from mcp.client.session import ClientSession +from mcp.client.streamable_http import streamable_http_client +from mcp.server import Server, ServerRequestContext from tests.interaction._connect import BASE_URL, base_headers, initialize_via_http, mounted_app from tests.interaction._requirements import requirement diff --git a/tests/interaction/transports/test_hosting_resume.py b/tests/interaction/transports/test_hosting_resume.py index 77ef087cd6..78492ccb7e 100644 --- a/tests/interaction/transports/test_hosting_resume.py +++ b/tests/interaction/transports/test_hosting_resume.py @@ -16,13 +16,7 @@ import pytest from httpx_sse import EventSource, ServerSentEvent from inline_snapshot import snapshot - -from mcp.client.session import ClientSession -from mcp.client.streamable_http import streamable_http_client -from mcp.server.mcpserver import Context, MCPServer -from mcp.shared.message import ClientMessageMetadata -from mcp.shared.version import LATEST_HANDSHAKE_VERSION -from mcp.types import ( +from mcp_types import ( CallToolRequest, CallToolRequestParams, CallToolResult, @@ -33,6 +27,12 @@ TextContent, jsonrpc_message_adapter, ) +from mcp_types.version import LATEST_HANDSHAKE_VERSION + +from mcp.client.session import ClientSession +from mcp.client.streamable_http import streamable_http_client +from mcp.server.mcpserver import Context, MCPServer +from mcp.shared.message import ClientMessageMetadata from tests.interaction._connect import ( BASE_URL, base_headers, diff --git a/tests/interaction/transports/test_hosting_session.py b/tests/interaction/transports/test_hosting_session.py index a926c3e8a2..1b41a4bee4 100644 --- a/tests/interaction/transports/test_hosting_session.py +++ b/tests/interaction/transports/test_hosting_session.py @@ -12,9 +12,9 @@ import httpx import pytest from inline_snapshot import snapshot +from mcp_types import JSONRPCResponse, ListToolsResult, PaginatedRequestParams, Tool from mcp.server import Server, ServerRequestContext -from mcp.types import JSONRPCResponse, ListToolsResult, PaginatedRequestParams, Tool from tests.interaction._connect import ( base_headers, client_via_http, diff --git a/tests/interaction/transports/test_legacy_wire.py b/tests/interaction/transports/test_legacy_wire.py index 99c614e1a6..d097ded692 100644 --- a/tests/interaction/transports/test_legacy_wire.py +++ b/tests/interaction/transports/test_legacy_wire.py @@ -10,12 +10,7 @@ import httpx import pytest from inline_snapshot import snapshot - -from mcp.client.client import Client -from mcp.client.streamable_http import streamable_http_client -from mcp.server import Server, ServerRequestContext -from mcp.shared.message import SessionMessage -from mcp.types import ( +from mcp_types import ( CallToolRequestParams, CallToolResult, ListToolsResult, @@ -23,6 +18,11 @@ TextContent, Tool, ) + +from mcp.client.client import Client +from mcp.client.streamable_http import streamable_http_client +from mcp.server import Server, ServerRequestContext +from mcp.shared.message import SessionMessage from tests.interaction._connect import BASE_URL, mounted_app from tests.interaction._helpers import RecordingTransport from tests.interaction._modern_vocab import RecordedExchange, assert_no_modern_vocabulary diff --git a/tests/interaction/transports/test_sse.py b/tests/interaction/transports/test_sse.py index 7a8cdcf7d2..6e492a35ba 100644 --- a/tests/interaction/transports/test_sse.py +++ b/tests/interaction/transports/test_sse.py @@ -13,11 +13,11 @@ import httpx import pytest from inline_snapshot import snapshot +from mcp_types import EmptyResult from mcp.client.client import Client from mcp.client.sse import sse_client from mcp.server import Server -from mcp.types import EmptyResult from tests.interaction._connect import BASE_URL, build_sse_app from tests.interaction._requirements import requirement from tests.interaction.transports._bridge import StreamingASGITransport diff --git a/tests/interaction/transports/test_stdio.py b/tests/interaction/transports/test_stdio.py index 9b7813f2d1..dbb7de3459 100644 --- a/tests/interaction/transports/test_stdio.py +++ b/tests/interaction/transports/test_stdio.py @@ -20,13 +20,7 @@ import anyio import pytest from inline_snapshot import snapshot - -from mcp.client import stdio -from mcp.client.client import Client -from mcp.client.stdio import StdioServerParameters, stdio_client -from mcp.server.stdio import stdio_server -from mcp.shared.message import SessionMessage -from mcp.types import ( +from mcp_types import ( CallToolResult, JSONRPCNotification, JSONRPCRequest, @@ -34,7 +28,13 @@ LoggingMessageNotificationParams, TextContent, ) -from mcp.types.jsonrpc import jsonrpc_message_adapter +from mcp_types.jsonrpc import jsonrpc_message_adapter + +from mcp.client import stdio +from mcp.client.client import Client +from mcp.client.stdio import StdioServerParameters, stdio_client +from mcp.server.stdio import stdio_server +from mcp.shared.message import SessionMessage from tests.interaction._connect import initialize_body from tests.interaction._requirements import requirement from tests.interaction.transports import _stdio_server diff --git a/tests/interaction/transports/test_streamable_http.py b/tests/interaction/transports/test_streamable_http.py index 79aace2639..779a46054a 100644 --- a/tests/interaction/transports/test_streamable_http.py +++ b/tests/interaction/transports/test_streamable_http.py @@ -10,13 +10,7 @@ import anyio import pytest from inline_snapshot import snapshot -from pydantic import BaseModel - -from mcp.client import ClientRequestContext -from mcp.server.elicitation import AcceptedElicitation -from mcp.server.mcpserver import Context, MCPServer -from mcp.shared.exceptions import MCPError -from mcp.types import ( +from mcp_types import ( INVALID_REQUEST, CallToolResult, ElicitRequestParams, @@ -27,6 +21,12 @@ ResourceUpdatedNotificationParams, TextContent, ) +from pydantic import BaseModel + +from mcp.client import ClientRequestContext +from mcp.server.elicitation import AcceptedElicitation +from mcp.server.mcpserver import Context, MCPServer +from mcp.shared.exceptions import MCPError from tests.interaction._connect import connect_over_streamable_http from tests.interaction._helpers import IncomingMessage from tests.interaction._requirements import requirement diff --git a/tests/issues/test_1338_icons_and_metadata.py b/tests/issues/test_1338_icons_and_metadata.py index a003f75b8b..b91f655872 100644 --- a/tests/issues/test_1338_icons_and_metadata.py +++ b/tests/issues/test_1338_icons_and_metadata.py @@ -1,9 +1,9 @@ """Test icon and metadata support (SEP-973).""" import pytest +from mcp_types import Icon from mcp.server.mcpserver import MCPServer -from mcp.types import Icon pytestmark = pytest.mark.anyio diff --git a/tests/issues/test_141_resource_templates.py b/tests/issues/test_141_resource_templates.py index f5c5081c3c..e955ab0afb 100644 --- a/tests/issues/test_141_resource_templates.py +++ b/tests/issues/test_141_resource_templates.py @@ -1,12 +1,12 @@ import pytest +from mcp_types import ( + ListResourceTemplatesResult, + TextResourceContents, +) from mcp import Client from mcp.server.mcpserver import MCPServer from mcp.server.mcpserver.exceptions import ResourceError -from mcp.types import ( - ListResourceTemplatesResult, - TextResourceContents, -) @pytest.mark.anyio diff --git a/tests/issues/test_152_resource_mime_type.py b/tests/issues/test_152_resource_mime_type.py index 851e89979f..d1e76f7b7d 100644 --- a/tests/issues/test_152_resource_mime_type.py +++ b/tests/issues/test_152_resource_mime_type.py @@ -1,11 +1,8 @@ import base64 +import mcp_types as types import pytest - -from mcp import Client, types -from mcp.server import Server, ServerRequestContext -from mcp.server.mcpserver import MCPServer -from mcp.types import ( +from mcp_types import ( BlobResourceContents, ListResourcesResult, PaginatedRequestParams, @@ -14,6 +11,10 @@ TextResourceContents, ) +from mcp import Client +from mcp.server import Server, ServerRequestContext +from mcp.server.mcpserver import MCPServer + pytestmark = pytest.mark.anyio diff --git a/tests/issues/test_1574_resource_uri_validation.py b/tests/issues/test_1574_resource_uri_validation.py index c677081282..856ecf0767 100644 --- a/tests/issues/test_1574_resource_uri_validation.py +++ b/tests/issues/test_1574_resource_uri_validation.py @@ -10,11 +10,9 @@ These tests verify the fix works end-to-end through the JSON-RPC protocol. """ +import mcp_types as types import pytest - -from mcp import Client, types -from mcp.server import Server, ServerRequestContext -from mcp.types import ( +from mcp_types import ( ListResourcesResult, PaginatedRequestParams, ReadResourceRequestParams, @@ -22,6 +20,9 @@ TextResourceContents, ) +from mcp import Client +from mcp.server import Server, ServerRequestContext + pytestmark = pytest.mark.anyio diff --git a/tests/issues/test_192_request_id.py b/tests/issues/test_192_request_id.py index 9f935ae088..bc2df01cd4 100644 --- a/tests/issues/test_192_request_id.py +++ b/tests/issues/test_192_request_id.py @@ -1,11 +1,6 @@ import anyio import pytest - -from mcp.server.lowlevel import NotificationOptions, Server -from mcp.server.models import InitializationOptions -from mcp.shared.message import SessionMessage -from mcp.shared.version import LATEST_HANDSHAKE_VERSION -from mcp.types import ( +from mcp_types import ( ClientCapabilities, Implementation, InitializeRequestParams, @@ -15,6 +10,11 @@ JSONRPCResponse, NotificationParams, ) +from mcp_types.version import LATEST_HANDSHAKE_VERSION + +from mcp.server.lowlevel import NotificationOptions, Server +from mcp.server.models import InitializationOptions +from mcp.shared.message import SessionMessage @pytest.mark.anyio diff --git a/tests/issues/test_342_base64_encoding.py b/tests/issues/test_342_base64_encoding.py index 2bccedf8d2..71d9df42d2 100644 --- a/tests/issues/test_342_base64_encoding.py +++ b/tests/issues/test_342_base64_encoding.py @@ -7,10 +7,10 @@ import base64 import pytest +from mcp_types import BlobResourceContents from mcp import Client from mcp.server.mcpserver import MCPServer -from mcp.types import BlobResourceContents pytestmark = pytest.mark.anyio diff --git a/tests/issues/test_552_windows_hang.py b/tests/issues/test_552_windows_hang.py index 82d4074e91..f4ec0d6878 100644 --- a/tests/issues/test_552_windows_hang.py +++ b/tests/issues/test_552_windows_hang.py @@ -6,11 +6,11 @@ import anyio import pytest +from mcp_types import InitializeResult +from mcp_types.version import LATEST_HANDSHAKE_VERSION from mcp import ClientSession, StdioServerParameters from mcp.client.stdio import stdio_client -from mcp.shared.version import LATEST_HANDSHAKE_VERSION -from mcp.types import InitializeResult @pytest.mark.skipif(sys.platform != "win32", reason="Windows-specific test") # pragma: no cover diff --git a/tests/issues/test_88_random_error.py b/tests/issues/test_88_random_error.py index b1c6a4f709..409ac96a2f 100644 --- a/tests/issues/test_88_random_error.py +++ b/tests/issues/test_88_random_error.py @@ -3,16 +3,11 @@ from pathlib import Path import anyio +import mcp_types as types import pytest from anyio.abc import TaskStatus from anyio.streams.memory import MemoryObjectReceiveStream, MemoryObjectSendStream - -from mcp import types -from mcp.client.session import ClientSession -from mcp.server import Server, ServerRequestContext -from mcp.shared.exceptions import MCPError -from mcp.shared.message import SessionMessage -from mcp.types import ( +from mcp_types import ( REQUEST_TIMEOUT, CallToolRequestParams, CallToolResult, @@ -21,6 +16,11 @@ TextContent, ) +from mcp.client.session import ClientSession +from mcp.server import Server, ServerRequestContext +from mcp.shared.exceptions import MCPError +from mcp.shared.message import SessionMessage + @pytest.mark.anyio async def test_notification_validation_error(tmp_path: Path): diff --git a/tests/server/lowlevel/test_server_discover.py b/tests/server/lowlevel/test_server_discover.py index ed26e7244d..1d036c2e7b 100644 --- a/tests/server/lowlevel/test_server_discover.py +++ b/tests/server/lowlevel/test_server_discover.py @@ -8,11 +8,11 @@ import importlib.metadata from typing import Any, cast +import mcp_types as types import pytest +from mcp_types.version import MODERN_PROTOCOL_VERSIONS -from mcp import types from mcp.server import Server, ServerRequestContext -from mcp.shared.version import MODERN_PROTOCOL_VERSIONS # `Server._handle_discover` ignores its `ctx` argument entirely (it derives the # result from server state), so a sentinel keeps the call site type-correct diff --git a/tests/server/lowlevel/test_server_listing.py b/tests/server/lowlevel/test_server_listing.py index 2c3d303a92..6c70bf5f29 100644 --- a/tests/server/lowlevel/test_server_listing.py +++ b/tests/server/lowlevel/test_server_listing.py @@ -1,10 +1,7 @@ """Basic tests for list_prompts, list_resources, and list_tools handlers without pagination.""" import pytest - -from mcp import Client -from mcp.server import Server, ServerRequestContext -from mcp.types import ( +from mcp_types import ( ListPromptsResult, ListResourcesResult, ListToolsResult, @@ -14,6 +11,9 @@ Tool, ) +from mcp import Client +from mcp.server import Server, ServerRequestContext + @pytest.mark.anyio async def test_list_prompts_basic() -> None: diff --git a/tests/server/lowlevel/test_server_pagination.py b/tests/server/lowlevel/test_server_pagination.py index a4627b316d..e875a11775 100644 --- a/tests/server/lowlevel/test_server_pagination.py +++ b/tests/server/lowlevel/test_server_pagination.py @@ -1,14 +1,14 @@ import pytest - -from mcp import Client -from mcp.server import Server, ServerRequestContext -from mcp.types import ( +from mcp_types import ( ListPromptsResult, ListResourcesResult, ListToolsResult, PaginatedRequestParams, ) +from mcp import Client +from mcp.server import Server, ServerRequestContext + @pytest.mark.anyio async def test_list_prompts_pagination() -> None: diff --git a/tests/server/mcpserver/prompts/test_base.py b/tests/server/mcpserver/prompts/test_base.py index d4e4e6b5a6..ef795777ea 100644 --- a/tests/server/mcpserver/prompts/test_base.py +++ b/tests/server/mcpserver/prompts/test_base.py @@ -2,10 +2,10 @@ from typing import Any import pytest +from mcp_types import EmbeddedResource, TextContent, TextResourceContents from mcp.server.mcpserver import Context from mcp.server.mcpserver.prompts.base import AssistantMessage, Message, Prompt, UserMessage -from mcp.types import EmbeddedResource, TextContent, TextResourceContents class TestRenderPrompt: diff --git a/tests/server/mcpserver/prompts/test_manager.py b/tests/server/mcpserver/prompts/test_manager.py index 99a03db565..2389d198be 100644 --- a/tests/server/mcpserver/prompts/test_manager.py +++ b/tests/server/mcpserver/prompts/test_manager.py @@ -1,9 +1,9 @@ import pytest +from mcp_types import TextContent from mcp.server.mcpserver import Context from mcp.server.mcpserver.prompts.base import Prompt, UserMessage from mcp.server.mcpserver.prompts.manager import PromptManager -from mcp.types import TextContent class TestPromptManager: diff --git a/tests/server/mcpserver/resources/test_resource_template.py b/tests/server/mcpserver/resources/test_resource_template.py index 0e8121b990..565afe81a7 100644 --- a/tests/server/mcpserver/resources/test_resource_template.py +++ b/tests/server/mcpserver/resources/test_resource_template.py @@ -3,12 +3,12 @@ from typing import Any import pytest +from mcp_types import Annotations from pydantic import BaseModel from mcp.server.mcpserver import Context, MCPServer from mcp.server.mcpserver.exceptions import ResourceError from mcp.server.mcpserver.resources import FunctionResource, ResourceTemplate -from mcp.types import Annotations class TestResourceTemplate: diff --git a/tests/server/mcpserver/resources/test_resources.py b/tests/server/mcpserver/resources/test_resources.py index 5d36beda85..744f483619 100644 --- a/tests/server/mcpserver/resources/test_resources.py +++ b/tests/server/mcpserver/resources/test_resources.py @@ -1,8 +1,8 @@ import pytest +from mcp_types import Annotations from mcp.server.mcpserver import MCPServer from mcp.server.mcpserver.resources import FunctionResource, Resource -from mcp.types import Annotations class TestResourceValidation: diff --git a/tests/server/mcpserver/test_elicitation.py b/tests/server/mcpserver/test_elicitation.py index 226d147195..bacb4dc9dd 100644 --- a/tests/server/mcpserver/test_elicitation.py +++ b/tests/server/mcpserver/test_elicitation.py @@ -2,14 +2,15 @@ from typing import Any, Literal +import mcp_types as types import pytest +from mcp_types import ElicitRequestParams, ElicitResult, TextContent from pydantic import BaseModel, Field -from mcp import Client, types +from mcp import Client from mcp.client import ClientRequestContext from mcp.client.session import ElicitationFnT from mcp.server.mcpserver import Context, MCPServer -from mcp.types import ElicitRequestParams, ElicitResult, TextContent # Shared schema for basic tests diff --git a/tests/server/mcpserver/test_func_metadata.py b/tests/server/mcpserver/test_func_metadata.py index 2763b3f503..0329f68365 100644 --- a/tests/server/mcpserver/test_func_metadata.py +++ b/tests/server/mcpserver/test_func_metadata.py @@ -10,11 +10,11 @@ import annotated_types import pytest from dirty_equals import IsPartialDict +from mcp_types import CallToolResult from pydantic import BaseModel, Field from mcp.server.mcpserver.exceptions import InvalidSignature from mcp.server.mcpserver.utilities.func_metadata import func_metadata -from mcp.types import CallToolResult class SomeInputModelA(BaseModel): diff --git a/tests/server/mcpserver/test_integration.py b/tests/server/mcpserver/test_integration.py index 904c8f873d..f6361f7574 100644 --- a/tests/server/mcpserver/test_integration.py +++ b/tests/server/mcpserver/test_integration.py @@ -13,22 +13,7 @@ import pytest from inline_snapshot import snapshot - -from examples.snippets.servers import ( - basic_prompt, - basic_resource, - basic_tool, - completion, - elicitation, - mcpserver_quickstart, - notifications, - sampling, - structured_output, - tool_progress, -) -from mcp.client import Client, ClientRequestContext -from mcp.shared.session import RequestResponder -from mcp.types import ( +from mcp_types import ( ClientResult, CreateMessageRequestParams, CreateMessageResult, @@ -51,6 +36,21 @@ ToolListChangedNotification, ) +from examples.snippets.servers import ( + basic_prompt, + basic_resource, + basic_tool, + completion, + elicitation, + mcpserver_quickstart, + notifications, + sampling, + structured_output, + tool_progress, +) +from mcp.client import Client, ClientRequestContext +from mcp.shared.session import RequestResponder + pytestmark = pytest.mark.anyio diff --git a/tests/server/mcpserver/test_server.py b/tests/server/mcpserver/test_server.py index 9b469e566a..4ea867480e 100644 --- a/tests/server/mcpserver/test_server.py +++ b/tests/server/mcpserver/test_server.py @@ -5,20 +5,7 @@ import pytest from inline_snapshot import snapshot -from pydantic import BaseModel -from starlette.applications import Starlette -from starlette.routing import Mount, Route - -from mcp.client import Client -from mcp.server.context import ServerRequestContext -from mcp.server.mcpserver import Context, MCPServer -from mcp.server.mcpserver.exceptions import ResourceNotFoundError, ToolError -from mcp.server.mcpserver.prompts.base import Message, UserMessage -from mcp.server.mcpserver.resources import FileResource, FunctionResource -from mcp.server.mcpserver.utilities.types import Audio, Image -from mcp.server.transport_security import TransportSecuritySettings -from mcp.shared.exceptions import MCPError -from mcp.types import ( +from mcp_types import ( INTERNAL_ERROR, INVALID_PARAMS, AudioContent, @@ -43,6 +30,19 @@ TextContent, TextResourceContents, ) +from pydantic import BaseModel +from starlette.applications import Starlette +from starlette.routing import Mount, Route + +from mcp.client import Client +from mcp.server.context import ServerRequestContext +from mcp.server.mcpserver import Context, MCPServer +from mcp.server.mcpserver.exceptions import ResourceNotFoundError, ToolError +from mcp.server.mcpserver.prompts.base import Message, UserMessage +from mcp.server.mcpserver.resources import FileResource, FunctionResource +from mcp.server.mcpserver.utilities.types import Audio, Image +from mcp.server.transport_security import TransportSecuritySettings +from mcp.shared.exceptions import MCPError pytestmark = pytest.mark.anyio diff --git a/tests/server/mcpserver/test_title.py b/tests/server/mcpserver/test_title.py index 9a3caf1b20..3e36f22579 100644 --- a/tests/server/mcpserver/test_title.py +++ b/tests/server/mcpserver/test_title.py @@ -1,12 +1,12 @@ """Integration tests for title field functionality.""" import pytest +from mcp_types import Prompt, Resource, ResourceTemplate, Tool, ToolAnnotations from mcp import Client from mcp.server.mcpserver import MCPServer from mcp.server.mcpserver.resources import FunctionResource from mcp.shared.metadata_utils import get_display_name -from mcp.types import Prompt, Resource, ResourceTemplate, Tool, ToolAnnotations @pytest.mark.anyio diff --git a/tests/server/mcpserver/test_tool_manager.py b/tests/server/mcpserver/test_tool_manager.py index 01b362fb50..221828c60a 100644 --- a/tests/server/mcpserver/test_tool_manager.py +++ b/tests/server/mcpserver/test_tool_manager.py @@ -4,6 +4,7 @@ from typing import Any, TypedDict import pytest +from mcp_types import CallToolResult, TextContent, ToolAnnotations from pydantic import BaseModel from mcp.server.context import LifespanContextT, RequestT @@ -11,7 +12,6 @@ from mcp.server.mcpserver.exceptions import ToolError from mcp.server.mcpserver.tools import Tool, ToolManager from mcp.server.mcpserver.utilities.func_metadata import ArgModelBase, FuncMetadata -from mcp.types import CallToolResult, TextContent, ToolAnnotations class TestAddTools: diff --git a/tests/server/mcpserver/test_url_elicitation.py b/tests/server/mcpserver/test_url_elicitation.py index 8446ed1bad..f2ce5e013c 100644 --- a/tests/server/mcpserver/test_url_elicitation.py +++ b/tests/server/mcpserver/test_url_elicitation.py @@ -1,14 +1,15 @@ """Test URL mode elicitation feature (SEP 1036).""" import anyio +import mcp_types as types import pytest +from mcp_types import ElicitRequestParams, ElicitResult, TextContent from pydantic import BaseModel, Field -from mcp import Client, types +from mcp import Client from mcp.client import ClientRequestContext from mcp.server.elicitation import CancelledElicitation, DeclinedElicitation, elicit_url from mcp.server.mcpserver import Context, MCPServer -from mcp.types import ElicitRequestParams, ElicitResult, TextContent @pytest.mark.anyio diff --git a/tests/server/mcpserver/test_url_elicitation_error_throw.py b/tests/server/mcpserver/test_url_elicitation_error_throw.py index 1f45fd60f0..29117e6936 100644 --- a/tests/server/mcpserver/test_url_elicitation_error_throw.py +++ b/tests/server/mcpserver/test_url_elicitation_error_throw.py @@ -1,9 +1,10 @@ """Test that UrlElicitationRequiredError is properly propagated as MCP error.""" +import mcp_types as types import pytest from inline_snapshot import snapshot -from mcp import Client, ErrorData, types +from mcp import Client, ErrorData from mcp.server.mcpserver import Context, MCPServer from mcp.shared.exceptions import MCPError, UrlElicitationRequiredError diff --git a/tests/server/mcpserver/tools/test_base.py b/tests/server/mcpserver/tools/test_base.py index 5e20f61ad3..0cb583028d 100644 --- a/tests/server/mcpserver/tools/test_base.py +++ b/tests/server/mcpserver/tools/test_base.py @@ -1,6 +1,7 @@ +import mcp_types as types import pytest -from mcp import Client, types +from mcp import Client from mcp.server.mcpserver import Context, MCPServer from mcp.server.mcpserver.tools.base import Tool from mcp.shared.exceptions import MCPError diff --git a/tests/server/test_cancel_handling.py b/tests/server/test_cancel_handling.py index 7c976cc2d9..3d32adb3c8 100644 --- a/tests/server/test_cancel_handling.py +++ b/tests/server/test_cancel_handling.py @@ -2,13 +2,7 @@ import anyio import pytest - -from mcp import Client -from mcp.server import Server, ServerRequestContext -from mcp.shared.exceptions import MCPError -from mcp.shared.message import SessionMessage -from mcp.shared.version import LATEST_HANDSHAKE_VERSION -from mcp.types import ( +from mcp_types import ( CallToolRequest, CallToolRequestParams, CallToolResult, @@ -24,6 +18,12 @@ TextContent, Tool, ) +from mcp_types.version import LATEST_HANDSHAKE_VERSION + +from mcp import Client +from mcp.server import Server, ServerRequestContext +from mcp.shared.exceptions import MCPError +from mcp.shared.message import SessionMessage @pytest.mark.anyio diff --git a/tests/server/test_completion_with_context.py b/tests/server/test_completion_with_context.py index 592af7c35a..79e4223ed4 100644 --- a/tests/server/test_completion_with_context.py +++ b/tests/server/test_completion_with_context.py @@ -1,10 +1,7 @@ """Tests for completion handler with context functionality.""" import pytest - -from mcp import Client -from mcp.server import Server, ServerRequestContext -from mcp.types import ( +from mcp_types import ( CompleteRequestParams, CompleteResult, Completion, @@ -12,6 +9,9 @@ ResourceTemplateReference, ) +from mcp import Client +from mcp.server import Server, ServerRequestContext + @pytest.mark.anyio async def test_completion_handler_receives_context(): diff --git a/tests/server/test_connection.py b/tests/server/test_connection.py index 3a09aa15d7..d448905a96 100644 --- a/tests/server/test_connection.py +++ b/tests/server/test_connection.py @@ -14,13 +14,7 @@ import anyio import pytest -from pydantic import BaseModel, ValidationError - -from mcp.server.connection import Connection -from mcp.shared.dispatcher import CallOptions -from mcp.shared.exceptions import NoBackChannelError -from mcp.shared.version import LATEST_HANDSHAKE_VERSION, LATEST_MODERN_VERSION -from mcp.types import ( +from mcp_types import ( LATEST_PROTOCOL_VERSION, ClientCapabilities, CreateMessageRequest, @@ -38,6 +32,12 @@ SamplingContextCapability, SamplingToolsCapability, ) +from mcp_types.version import LATEST_HANDSHAKE_VERSION, LATEST_MODERN_VERSION +from pydantic import BaseModel, ValidationError + +from mcp.server.connection import Connection +from mcp.shared.dispatcher import CallOptions +from mcp.shared.exceptions import NoBackChannelError _CLIENT_INFO = Implementation(name="t", version="0") diff --git a/tests/server/test_lifespan.py b/tests/server/test_lifespan.py index 0d87905042..4cfff47c39 100644 --- a/tests/server/test_lifespan.py +++ b/tests/server/test_lifespan.py @@ -5,14 +5,7 @@ import anyio import pytest -from pydantic import TypeAdapter - -from mcp.server import ServerRequestContext -from mcp.server.lowlevel.server import NotificationOptions, Server -from mcp.server.mcpserver import Context, MCPServer -from mcp.server.models import InitializationOptions -from mcp.shared.message import SessionMessage -from mcp.types import ( +from mcp_types import ( CallToolRequestParams, CallToolResult, ClientCapabilities, @@ -24,6 +17,13 @@ JSONRPCResponse, TextContent, ) +from pydantic import TypeAdapter + +from mcp.server import ServerRequestContext +from mcp.server.lowlevel.server import NotificationOptions, Server +from mcp.server.mcpserver import Context, MCPServer +from mcp.server.models import InitializationOptions +from mcp.shared.message import SessionMessage @pytest.mark.anyio diff --git a/tests/server/test_lowlevel_tool_annotations.py b/tests/server/test_lowlevel_tool_annotations.py index 705abdfe8c..f80ebd81ef 100644 --- a/tests/server/test_lowlevel_tool_annotations.py +++ b/tests/server/test_lowlevel_tool_annotations.py @@ -1,10 +1,10 @@ """Tests for tool annotations in low-level server.""" import pytest +from mcp_types import ListToolsResult, PaginatedRequestParams, Tool, ToolAnnotations from mcp import Client from mcp.server import Server, ServerRequestContext -from mcp.types import ListToolsResult, PaginatedRequestParams, Tool, ToolAnnotations @pytest.mark.anyio diff --git a/tests/server/test_otel.py b/tests/server/test_otel.py index 1da8567b32..0cf843eeff 100644 --- a/tests/server/test_otel.py +++ b/tests/server/test_otel.py @@ -5,15 +5,7 @@ import anyio import pytest -from opentelemetry.trace import SpanKind, StatusCode - -from mcp.server._otel import OpenTelemetryMiddleware -from mcp.server.context import CallNext -from mcp.server.lowlevel.server import Server -from mcp.server.runner import otel_middleware -from mcp.shared._otel import inject_trace_context -from mcp.shared.exceptions import MCPError -from mcp.types import ( +from mcp_types import ( INVALID_PARAMS, CallToolRequestParams, CallToolResult, @@ -24,6 +16,14 @@ PaginatedRequestParams, Tool, ) +from opentelemetry.trace import SpanKind, StatusCode + +from mcp.server._otel import OpenTelemetryMiddleware +from mcp.server.context import CallNext +from mcp.server.lowlevel.server import Server +from mcp.server.runner import otel_middleware +from mcp.shared._otel import inject_trace_context +from mcp.shared.exceptions import MCPError from .conftest import SpanCapture from .test_runner import Ctx, SrvT, connected_runner diff --git a/tests/server/test_read_resource.py b/tests/server/test_read_resource.py index 102a58d039..1ce8dac412 100644 --- a/tests/server/test_read_resource.py +++ b/tests/server/test_read_resource.py @@ -1,16 +1,16 @@ import base64 import pytest - -from mcp import Client -from mcp.server import Server, ServerRequestContext -from mcp.types import ( +from mcp_types import ( BlobResourceContents, ReadResourceRequestParams, ReadResourceResult, TextResourceContents, ) +from mcp import Client +from mcp.server import Server, ServerRequestContext + pytestmark = pytest.mark.anyio diff --git a/tests/server/test_runner.py b/tests/server/test_runner.py index 30c611066c..4d787dc5d7 100644 --- a/tests/server/test_runner.py +++ b/tests/server/test_runner.py @@ -16,6 +16,25 @@ import anyio import anyio.abc import pytest +from mcp_types import ( + INTERNAL_ERROR, + INVALID_PARAMS, + LATEST_PROTOCOL_VERSION, + METHOD_NOT_FOUND, + CallToolRequestParams, + ClientCapabilities, + ErrorData, + Implementation, + InitializeRequestParams, + ListToolsResult, + NotificationParams, + PaginatedRequestParams, + ProgressNotificationParams, + RequestParams, + SetLevelRequestParams, + Tool, +) +from mcp_types.version import LATEST_HANDSHAKE_VERSION, LATEST_MODERN_VERSION, OLDEST_SUPPORTED_VERSION from opentelemetry.trace import SpanKind, StatusCode import mcp.server.runner @@ -38,25 +57,6 @@ from mcp.shared.message import MessageMetadata from mcp.shared.peer import dump_params from mcp.shared.transport_context import TransportContext -from mcp.shared.version import LATEST_HANDSHAKE_VERSION, LATEST_MODERN_VERSION, OLDEST_SUPPORTED_VERSION -from mcp.types import ( - INTERNAL_ERROR, - INVALID_PARAMS, - LATEST_PROTOCOL_VERSION, - METHOD_NOT_FOUND, - CallToolRequestParams, - ClientCapabilities, - ErrorData, - Implementation, - InitializeRequestParams, - ListToolsResult, - NotificationParams, - PaginatedRequestParams, - ProgressNotificationParams, - RequestParams, - SetLevelRequestParams, - Tool, -) from ..shared.conftest import jsonrpc_pair from ..shared.test_dispatcher import Recorder, echo_handlers diff --git a/tests/server/test_session.py b/tests/server/test_session.py index ea57441dcc..25b8257eb2 100644 --- a/tests/server/test_session.py +++ b/tests/server/test_session.py @@ -9,21 +9,21 @@ from collections.abc import Mapping from typing import Any +import mcp_types as types import pytest +from mcp_types import ( + ClientCapabilities, + Implementation, + SamplingCapability, + SamplingToolsCapability, +) +from mcp_types.version import LATEST_HANDSHAKE_VERSION, LATEST_MODERN_VERSION from pydantic import ValidationError -from mcp import types from mcp.server.connection import Connection from mcp.server.session import ServerSession from mcp.shared.dispatcher import CallOptions from mcp.shared.message import ServerMessageMetadata -from mcp.shared.version import LATEST_HANDSHAKE_VERSION, LATEST_MODERN_VERSION -from mcp.types import ( - ClientCapabilities, - Implementation, - SamplingCapability, - SamplingToolsCapability, -) class StubOutbound: diff --git a/tests/server/test_sse_security.py b/tests/server/test_sse_security.py index e77bd5e2c2..ca16d33541 100644 --- a/tests/server/test_sse_security.py +++ b/tests/server/test_sse_security.py @@ -7,6 +7,7 @@ import httpx import pytest import sse_starlette.sse +from mcp_types import JSONRPCRequest, JSONRPCResponse from starlette.applications import Starlette from starlette.requests import Request from starlette.responses import Response @@ -20,7 +21,6 @@ from mcp.server.transport_security import TransportSecuritySettings from mcp.shared._stream_protocols import WriteStream from mcp.shared.message import SessionMessage -from mcp.types import JSONRPCRequest, JSONRPCResponse from tests.interaction.transports import StreamingASGITransport logger = logging.getLogger(__name__) diff --git a/tests/server/test_stateless_mode.py b/tests/server/test_stateless_mode.py index 7b252ef536..1124d69b71 100644 --- a/tests/server/test_stateless_mode.py +++ b/tests/server/test_stateless_mode.py @@ -10,14 +10,14 @@ from collections.abc import Mapping from typing import Any +import mcp_types as types import pytest +from mcp_types import LATEST_PROTOCOL_VERSION -from mcp import types from mcp.server.connection import Connection from mcp.server.session import ServerSession from mcp.shared.dispatcher import CallOptions from mcp.shared.exceptions import NoBackChannelError -from mcp.types import LATEST_PROTOCOL_VERSION class StubOutbound: diff --git a/tests/server/test_stdio.py b/tests/server/test_stdio.py index 054a157b3b..886bc51b54 100644 --- a/tests/server/test_stdio.py +++ b/tests/server/test_stdio.py @@ -7,11 +7,11 @@ import anyio import pytest +from mcp_types import JSONRPCMessage, JSONRPCRequest, JSONRPCResponse, jsonrpc_message_adapter from mcp.server.mcpserver import MCPServer from mcp.server.stdio import stdio_server from mcp.shared.message import SessionMessage -from mcp.types import JSONRPCMessage, JSONRPCRequest, JSONRPCResponse, jsonrpc_message_adapter @pytest.mark.anyio diff --git a/tests/server/test_streamable_http_manager.py b/tests/server/test_streamable_http_manager.py index d738c02cd0..0b3a280832 100644 --- a/tests/server/test_streamable_http_manager.py +++ b/tests/server/test_streamable_http_manager.py @@ -8,6 +8,7 @@ import anyio import httpx import pytest +from mcp_types import INVALID_REQUEST, ListToolsResult, PaginatedRequestParams from starlette.types import Message, Scope from mcp import Client @@ -17,7 +18,6 @@ from mcp.server.auth.provider import AccessToken from mcp.server.streamable_http import MCP_SESSION_ID_HEADER, StreamableHTTPServerTransport from mcp.server.streamable_http_manager import StreamableHTTPSessionManager -from mcp.types import INVALID_REQUEST, ListToolsResult, PaginatedRequestParams @pytest.mark.anyio diff --git a/tests/server/test_streamable_http_modern.py b/tests/server/test_streamable_http_modern.py index 7b655bdd6f..08b9401078 100644 --- a/tests/server/test_streamable_http_modern.py +++ b/tests/server/test_streamable_http_modern.py @@ -12,20 +12,7 @@ import anyio import httpx import pytest -from starlette.types import Receive, Scope, Send - -from mcp.server import Server, ServerRequestContext, runner -from mcp.server._streamable_http_modern import ( - _SingleExchangeDispatchContext, - _to_jsonrpc_response, - handle_modern_request, -) -from mcp.server.transport_security import TransportSecuritySettings -from mcp.shared.exceptions import MCPError, NoBackChannelError -from mcp.shared.inbound import MCP_PROTOCOL_VERSION_HEADER -from mcp.shared.transport_context import TransportContext -from mcp.shared.version import LATEST_MODERN_VERSION -from mcp.types import ( +from mcp_types import ( CLIENT_CAPABILITIES_META_KEY, CLIENT_INFO_META_KEY, INTERNAL_ERROR, @@ -41,6 +28,19 @@ PaginatedRequestParams, Tool, ) +from mcp_types.version import LATEST_MODERN_VERSION +from starlette.types import Receive, Scope, Send + +from mcp.server import Server, ServerRequestContext, runner +from mcp.server._streamable_http_modern import ( + _SingleExchangeDispatchContext, + _to_jsonrpc_response, + handle_modern_request, +) +from mcp.server.transport_security import TransportSecuritySettings +from mcp.shared.exceptions import MCPError, NoBackChannelError +from mcp.shared.inbound import MCP_PROTOCOL_VERSION_HEADER +from mcp.shared.transport_context import TransportContext pytestmark = pytest.mark.anyio diff --git a/tests/server/test_streamable_http_router.py b/tests/server/test_streamable_http_router.py index 4f6286c4de..3086dca990 100644 --- a/tests/server/test_streamable_http_router.py +++ b/tests/server/test_streamable_http_router.py @@ -2,6 +2,7 @@ import anyio import pytest +from mcp_types import JSONRPCMessage, JSONRPCResponse from starlette.types import Message, Scope from mcp.server.streamable_http import ( @@ -14,7 +15,6 @@ StreamId, ) from mcp.shared.message import SessionMessage -from mcp.types import JSONRPCMessage, JSONRPCResponse class _PrimingFailingStore(EventStore): diff --git a/tests/server/test_validation.py b/tests/server/test_validation.py index 19f4eb1088..8015c34dde 100644 --- a/tests/server/test_validation.py +++ b/tests/server/test_validation.py @@ -1,14 +1,7 @@ """Tests for server validation functions.""" import pytest - -from mcp.server.validation import ( - check_sampling_tools_capability, - validate_sampling_tools, - validate_tool_use_result_messages, -) -from mcp.shared.exceptions import MCPError -from mcp.types import ( +from mcp_types import ( ClientCapabilities, SamplingCapability, SamplingMessage, @@ -20,6 +13,13 @@ ToolUseContent, ) +from mcp.server.validation import ( + check_sampling_tools_capability, + validate_sampling_tools, + validate_tool_use_result_messages, +) +from mcp.shared.exceptions import MCPError + # Tests for check_sampling_tools_capability function diff --git a/tests/shared/test_dispatcher.py b/tests/shared/test_dispatcher.py index 3a699e97dd..1f82083379 100644 --- a/tests/shared/test_dispatcher.py +++ b/tests/shared/test_dispatcher.py @@ -12,13 +12,7 @@ import anyio import pytest - -from mcp.shared._compat import resync_tracer -from mcp.shared.direct_dispatcher import DirectDispatcher, create_direct_dispatcher_pair -from mcp.shared.dispatcher import DispatchContext, Dispatcher, OnNotify, OnRequest, Outbound -from mcp.shared.exceptions import MCPError -from mcp.shared.transport_context import TransportContext -from mcp.types import ( +from mcp_types import ( CONNECTION_CLOSED, INTERNAL_ERROR, INVALID_PARAMS, @@ -28,6 +22,12 @@ Tool, ) +from mcp.shared._compat import resync_tracer +from mcp.shared.direct_dispatcher import DirectDispatcher, create_direct_dispatcher_pair +from mcp.shared.dispatcher import DispatchContext, Dispatcher, OnNotify, OnRequest, Outbound +from mcp.shared.exceptions import MCPError +from mcp.shared.transport_context import TransportContext + from .conftest import PairFactory, direct_pair diff --git a/tests/shared/test_exceptions.py b/tests/shared/test_exceptions.py index c6b5750928..9da4f606d3 100644 --- a/tests/shared/test_exceptions.py +++ b/tests/shared/test_exceptions.py @@ -1,9 +1,9 @@ """Tests for MCP exception classes.""" import pytest +from mcp_types import URL_ELICITATION_REQUIRED, ElicitRequestURLParams, ErrorData, JSONRPCError from mcp.shared.exceptions import MCPError, UrlElicitationRequiredError -from mcp.types import URL_ELICITATION_REQUIRED, ElicitRequestURLParams, ErrorData, JSONRPCError def test_url_elicitation_required_error_create_with_single_elicitation() -> None: diff --git a/tests/shared/test_inbound.py b/tests/shared/test_inbound.py index a8e275a4fa..150cea6c2b 100644 --- a/tests/shared/test_inbound.py +++ b/tests/shared/test_inbound.py @@ -9,21 +9,12 @@ from typing import Any import pytest - -from mcp.shared.inbound import ( - ERROR_CODE_HTTP_STATUS, - MCP_PROTOCOL_VERSION_HEADER, - InboundLadderRejection, - InboundModernRoute, - classify_inbound_request, -) -from mcp.shared.version import LATEST_HANDSHAKE_VERSION, LATEST_MODERN_VERSION, MODERN_PROTOCOL_VERSIONS -from mcp.types import ( +from mcp_types import ( CLIENT_CAPABILITIES_META_KEY, CLIENT_INFO_META_KEY, PROTOCOL_VERSION_META_KEY, ) -from mcp.types.jsonrpc import ( +from mcp_types.jsonrpc import ( HEADER_MISMATCH, INVALID_PARAMS, INVALID_REQUEST, @@ -32,6 +23,15 @@ PARSE_ERROR, UNSUPPORTED_PROTOCOL_VERSION, ) +from mcp_types.version import LATEST_HANDSHAKE_VERSION, LATEST_MODERN_VERSION, MODERN_PROTOCOL_VERSIONS + +from mcp.shared.inbound import ( + ERROR_CODE_HTTP_STATUS, + MCP_PROTOCOL_VERSION_HEADER, + InboundLadderRejection, + InboundModernRoute, + classify_inbound_request, +) CLIENT_INFO = {"name": "t", "version": "0"} CLIENT_CAPS: dict[str, Any] = {} diff --git a/tests/shared/test_jsonrpc_dispatcher.py b/tests/shared/test_jsonrpc_dispatcher.py index 1acbb363c0..82d16bc4b9 100644 --- a/tests/shared/test_jsonrpc_dispatcher.py +++ b/tests/shared/test_jsonrpc_dispatcher.py @@ -10,24 +10,7 @@ import anyio import anyio.lowlevel import pytest -from trio.testing import MockClock - -from mcp import Client -from mcp.server import Server, ServerRequestContext -from mcp.shared._compat import resync_tracer -from mcp.shared._context_streams import ContextReceiveStream, ContextSendStream -from mcp.shared.dispatcher import CallOptions, DispatchContext -from mcp.shared.exceptions import MCPError, NoBackChannelError -from mcp.shared.jsonrpc_dispatcher import ( # pyright: ignore[reportPrivateUsage] - JSONRPCDispatcher, - _coerce_id, - _OutboundPlan, - _Pending, - _plan_outbound, -) -from mcp.shared.message import ClientMessageMetadata, MessageMetadata, ServerMessageMetadata, SessionMessage -from mcp.shared.transport_context import TransportContext -from mcp.types import ( +from mcp_types import ( CONNECTION_CLOSED, INTERNAL_ERROR, INVALID_PARAMS, @@ -45,6 +28,23 @@ RequestId, Tool, ) +from trio.testing import MockClock + +from mcp import Client +from mcp.server import Server, ServerRequestContext +from mcp.shared._compat import resync_tracer +from mcp.shared._context_streams import ContextReceiveStream, ContextSendStream +from mcp.shared.dispatcher import CallOptions, DispatchContext +from mcp.shared.exceptions import MCPError, NoBackChannelError +from mcp.shared.jsonrpc_dispatcher import ( # pyright: ignore[reportPrivateUsage] + JSONRPCDispatcher, + _coerce_id, + _OutboundPlan, + _Pending, + _plan_outbound, +) +from mcp.shared.message import ClientMessageMetadata, MessageMetadata, ServerMessageMetadata, SessionMessage +from mcp.shared.transport_context import TransportContext from .conftest import jsonrpc_pair from .test_dispatcher import Recorder, echo_handlers, running_pair diff --git a/tests/shared/test_otel.py b/tests/shared/test_otel.py index ab45576137..3c5be30269 100644 --- a/tests/shared/test_otel.py +++ b/tests/shared/test_otel.py @@ -1,9 +1,9 @@ from __future__ import annotations +import mcp_types as types import pytest from logfire.testing import CaptureLogfire -from mcp import types from mcp.client.client import Client from mcp.server.mcpserver import MCPServer diff --git a/tests/shared/test_peer.py b/tests/shared/test_peer.py index 89e931b3b1..2fc92e2c8b 100644 --- a/tests/shared/test_peer.py +++ b/tests/shared/test_peer.py @@ -10,12 +10,7 @@ import anyio import pytest - -from mcp.shared.dispatcher import DispatchContext -from mcp.shared.exceptions import MCPDeprecationWarning -from mcp.shared.peer import ClientPeer, dump_params -from mcp.shared.transport_context import TransportContext -from mcp.types import ( +from mcp_types import ( CreateMessageResult, CreateMessageResultWithTools, ElicitResult, @@ -25,6 +20,11 @@ Tool, ) +from mcp.shared.dispatcher import DispatchContext +from mcp.shared.exceptions import MCPDeprecationWarning +from mcp.shared.peer import ClientPeer, dump_params +from mcp.shared.transport_context import TransportContext + from .conftest import direct_pair from .test_dispatcher import running_pair diff --git a/tests/shared/test_sse.py b/tests/shared/test_sse.py index 675a4acb16..6427fb21a6 100644 --- a/tests/shared/test_sse.py +++ b/tests/shared/test_sse.py @@ -8,24 +8,11 @@ import anyio import httpx +import mcp_types as types import pytest from httpx_sse import ServerSentEvent from inline_snapshot import snapshot -from starlette.applications import Starlette -from starlette.requests import Request -from starlette.responses import Response -from starlette.routing import Mount, Route - -import mcp.client.sse -from mcp import types -from mcp.client.session import ClientSession -from mcp.client.sse import _extract_session_id_from_endpoint, sse_client -from mcp.server import Server, ServerRequestContext -from mcp.server.sse import SseServerTransport -from mcp.server.transport_security import TransportSecuritySettings -from mcp.shared._httpx_utils import McpHttpClientFactory -from mcp.shared.exceptions import MCPError -from mcp.types import ( +from mcp_types import ( CallToolRequestParams, CallToolResult, EmptyResult, @@ -41,6 +28,19 @@ TextResourceContents, Tool, ) +from starlette.applications import Starlette +from starlette.requests import Request +from starlette.responses import Response +from starlette.routing import Mount, Route + +import mcp.client.sse +from mcp.client.session import ClientSession +from mcp.client.sse import _extract_session_id_from_endpoint, sse_client +from mcp.server import Server, ServerRequestContext +from mcp.server.sse import SseServerTransport +from mcp.server.transport_security import TransportSecuritySettings +from mcp.shared._httpx_utils import McpHttpClientFactory +from mcp.shared.exceptions import MCPError from tests.interaction.transports import StreamingASGITransport SERVER_NAME = "test_server_for_SSE" diff --git a/tests/shared/test_streamable_http.py b/tests/shared/test_streamable_http.py index 5360e56ff6..cbce222eca 100644 --- a/tests/shared/test_streamable_http.py +++ b/tests/shared/test_streamable_http.py @@ -17,15 +17,32 @@ import anyio import httpx +import mcp_types as types import pytest from anyio.streams.memory import MemoryObjectReceiveStream, MemoryObjectSendStream from httpx_sse import ServerSentEvent +from mcp_types import ( + DEFAULT_NEGOTIATED_VERSION, + INVALID_PARAMS, + INVALID_REQUEST, + CallToolRequestParams, + CallToolResult, + InitializeResult, + JSONRPCRequest, + ListToolsResult, + PaginatedRequestParams, + ReadResourceRequestParams, + ReadResourceResult, + TextContent, + TextResourceContents, + Tool, +) from starlette.applications import Starlette from starlette.requests import Request from starlette.routing import Mount from starlette.types import Message, Scope -from mcp import MCPError, types +from mcp import MCPError from mcp.client import ClientRequestContext from mcp.client.session import ClientSession from mcp.client.streamable_http import StreamableHTTPTransport, streamable_http_client @@ -48,22 +65,6 @@ from mcp.shared._context_streams import create_context_streams from mcp.shared.message import ClientMessageMetadata, ServerMessageMetadata, SessionMessage from mcp.shared.session import RequestResponder -from mcp.types import ( - DEFAULT_NEGOTIATED_VERSION, - INVALID_PARAMS, - INVALID_REQUEST, - CallToolRequestParams, - CallToolResult, - InitializeResult, - JSONRPCRequest, - ListToolsResult, - PaginatedRequestParams, - ReadResourceRequestParams, - ReadResourceResult, - TextContent, - TextResourceContents, - Tool, -) from tests.interaction.transports import StreamingASGITransport # Test constants diff --git a/tests/shared/test_version.py b/tests/shared/test_version.py index 595bb03bc0..b61f551ca7 100644 --- a/tests/shared/test_version.py +++ b/tests/shared/test_version.py @@ -1,8 +1,7 @@ """Tests for the protocol-version registry and comparison helpers.""" import pytest - -from mcp.shared.version import ( +from mcp_types.version import ( HANDSHAKE_PROTOCOL_VERSIONS, KNOWN_PROTOCOL_VERSIONS, MODERN_PROTOCOL_VERSIONS, diff --git a/tests/test_examples.py b/tests/test_examples.py index af40fb9b99..ae35767f7c 100644 --- a/tests/test_examples.py +++ b/tests/test_examples.py @@ -9,10 +9,10 @@ import pytest from inline_snapshot import snapshot +from mcp_types import CallToolResult, TextContent, TextResourceContents from pytest_examples import CodeExample, EvalExample, find_examples from mcp import Client -from mcp.types import CallToolResult, TextContent, TextResourceContents @pytest.mark.anyio diff --git a/tests/test_types.py b/tests/test_types.py index dffbc918dc..c32ade2957 100644 --- a/tests/test_types.py +++ b/tests/test_types.py @@ -2,9 +2,7 @@ import pytest from inline_snapshot import snapshot -from pydantic import ValidationError - -from mcp.types import ( +from mcp_types import ( LATEST_PROTOCOL_VERSION, CallToolResult, ClientCapabilities, @@ -38,6 +36,7 @@ client_request_adapter, jsonrpc_message_adapter, ) +from pydantic import ValidationError @pytest.mark.anyio diff --git a/tests/transports/stdio/test_windows.py b/tests/transports/stdio/test_windows.py index 0e7ad092c7..656fc8124d 100644 --- a/tests/transports/stdio/test_windows.py +++ b/tests/transports/stdio/test_windows.py @@ -19,11 +19,11 @@ import anyio import anyio.abc import pytest +from mcp_types import JSONRPCRequest, JSONRPCResponse from mcp.client.stdio import StdioServerParameters, stdio_client from mcp.os.win32.utilities import FallbackProcess from mcp.shared.message import SessionMessage -from mcp.types import JSONRPCRequest, JSONRPCResponse from tests.transports.stdio._liveness import ( accept_alive, assert_stream_closed, diff --git a/tests/types/test_methods.py b/tests/types/test_methods.py index c6d6823d72..ab72aa389f 100644 --- a/tests/types/test_methods.py +++ b/tests/types/test_methods.py @@ -1,20 +1,19 @@ -"""Tests for the wire-method maps and two-step parse functions in `mcp.types.methods`.""" +"""Tests for the wire-method maps and two-step parse functions in `mcp_types.methods`.""" import importlib.util from collections.abc import Mapping from types import MappingProxyType, UnionType from typing import Any, get_args +import mcp_types as types +import mcp_types.v2025_11_25 as v2025 +import mcp_types.v2026_07_28 as v2026 import pydantic import pytest +from mcp_types import methods +from mcp_types.version import KNOWN_PROTOCOL_VERSIONS from pydantic import BaseModel -import mcp.types as types -import mcp.types.v2025_11_25 as v2025 -import mcp.types.v2026_07_28 as v2026 -from mcp.shared.version import KNOWN_PROTOCOL_VERSIONS -from mcp.types import methods - # Transcribed from each schema's ClientRequest/ServerRequest/ClientNotification/ # ServerNotification unions, minus the tasks/* family (extensions register those). EXPECTED_METHODS: dict[str, dict[str, frozenset[str]]] = { @@ -298,11 +297,11 @@ # Pre-2026 versions share the 2025-11-25 surface package. PACKAGE_BY_VERSION = { - "2024-11-05": "mcp.types.v2025_11_25", - "2025-03-26": "mcp.types.v2025_11_25", - "2025-06-18": "mcp.types.v2025_11_25", - "2025-11-25": "mcp.types.v2025_11_25", - "2026-07-28": "mcp.types.v2026_07_28", + "2024-11-05": "mcp_types.v2025_11_25", + "2025-03-26": "mcp_types.v2025_11_25", + "2025-06-18": "mcp_types.v2025_11_25", + "2025-11-25": "mcp_types.v2025_11_25", + "2026-07-28": "mcp_types.v2026_07_28", } # The three reserved `params._meta` entries the 2026 surface requires on every request. @@ -920,7 +919,7 @@ def test_serialize_server_result_raises_key_error_for_an_absent_row_and_value_er def test_importing_the_module_builds_no_adapters_and_identical_rows_share_one(): # Execute a fresh copy so the cache assertion is order-independent. - spec = importlib.util.find_spec("mcp.types.methods") + spec = importlib.util.find_spec("mcp_types.methods") assert spec is not None and spec.loader is not None fresh = importlib.util.module_from_spec(spec) spec.loader.exec_module(fresh) diff --git a/tests/types/test_parity.py b/tests/types/test_parity.py index e5d305cf95..8a06073acd 100644 --- a/tests/types/test_parity.py +++ b/tests/types/test_parity.py @@ -1,21 +1,20 @@ -"""Assert every per-version surface model's wire fields are a subset of its `mcp.types` superset counterpart.""" +"""Assert every per-version surface model's wire fields are a subset of its `mcp_types` superset counterpart.""" from __future__ import annotations import inspect from types import ModuleType +import mcp_types as monolith +import mcp_types._types as _types +import mcp_types.v2025_11_25 as v2025_11_25 +import mcp_types.v2026_07_28 as v2026_07_28 import pytest from pydantic import BaseModel -import mcp.types as monolith -import mcp.types._types as _types -import mcp.types.v2025_11_25 as v2025_11_25 -import mcp.types.v2026_07_28 as v2026_07_28 - SURFACES: tuple[ModuleType, ...] = (v2025_11_25, v2026_07_28) -# Envelope fields the monolith models on `mcp.types.jsonrpc` instead of on each request/notification. +# Envelope fields the monolith models on `mcp_types.jsonrpc` instead of on each request/notification. ENVELOPE_FIELDS: frozenset[str] = frozenset({"jsonrpc", "id"}) # Surface classes whose monolith counterpart has a different name (key: "."). @@ -186,7 +185,7 @@ def test_monolith_is_superset_of_surface_fields( assert not missing, f"{qualname}: monolith {mono_cls.__name__} missing wire fields {sorted(missing)}" -# Monolith model classes intentionally kept out of `mcp.types.__all__`. +# Monolith model classes intentionally kept out of `mcp_types.__all__`. PRIVATE_MONOLITH_MODELS: frozenset[str] = frozenset( { "MCPModel", # internal base; users subclass the concrete spec types instead @@ -205,7 +204,7 @@ def test_every_public_monolith_model_is_exported_from_mcp_types() -> None: and obj.__module__ == _types.__name__ } missing = defined - set(monolith.__all__) - PRIVATE_MONOLITH_MODELS - assert not missing, f"_types models not in mcp.types.__all__: {sorted(missing)}" + assert not missing, f"_types models not in mcp_types.__all__: {sorted(missing)}" def test_every_surface_class_is_accounted_for() -> None: diff --git a/tests/types/test_wire_frames.py b/tests/types/test_wire_frames.py index a48180634d..40c5dd54fc 100644 --- a/tests/types/test_wire_frames.py +++ b/tests/types/test_wire_frames.py @@ -3,9 +3,7 @@ from typing import Any from inline_snapshot import snapshot -from pydantic import BaseModel - -from mcp.types import ( +from mcp_types import ( METHOD_NOT_FOUND, CallToolRequest, CallToolRequestParams, @@ -24,6 +22,7 @@ TextContent, Tool, ) +from pydantic import BaseModel def _body(model: BaseModel) -> dict[str, Any]: diff --git a/uv.lock b/uv.lock index 7970d1cc2d..b6dbdd9e0a 100644 --- a/uv.lock +++ b/uv.lock @@ -23,6 +23,7 @@ members = [ "mcp-sse-polling-client", "mcp-sse-polling-demo", "mcp-structured-output-lowlevel", + "mcp-types", ] build-constraints = [ { name = "dunamai", specifier = "==1.26.1" }, @@ -909,6 +910,7 @@ dependencies = [ { name = "httpx" }, { name = "httpx-sse" }, { name = "jsonschema" }, + { name = "mcp-types" }, { name = "opentelemetry-api" }, { name = "pydantic" }, { name = "pydantic-settings" }, @@ -969,6 +971,7 @@ requires-dist = [ { name = "httpx", specifier = ">=0.27.1,<1.0.0" }, { name = "httpx-sse", specifier = ">=0.4" }, { name = "jsonschema", specifier = ">=4.20.0" }, + { name = "mcp-types", editable = "src/mcp-types" }, { name = "opentelemetry-api", specifier = ">=1.28.0" }, { name = "pydantic", specifier = ">=2.12.0" }, { name = "pydantic-settings", specifier = ">=2.5.2" }, @@ -1448,6 +1451,20 @@ dependencies = [ [package.metadata] requires-dist = [{ name = "mcp", editable = "." }] +[[package]] +name = "mcp-types" +source = { editable = "src/mcp-types" } +dependencies = [ + { name = "pydantic" }, + { name = "typing-extensions" }, +] + +[package.metadata] +requires-dist = [ + { name = "pydantic", specifier = ">=2.12.0" }, + { name = "typing-extensions", specifier = ">=4.13.0" }, +] + [[package]] name = "mdurl" version = "0.1.2"