Spaces:
Running
Running
Jeremiah Lowin commited on
Commit ·
c7184ac
1
Parent(s): ad3a4c4
Move components to own file; add resource
Browse files
docs/getting-started/installation.mdx
CHANGED
|
@@ -72,7 +72,7 @@ For users concerned about stability in production environments, we recommend pin
|
|
| 72 |
|
| 73 |
Whenever possible, FastMCP will issue deprecation warnings when users attempt to use APIs that are either deprecated or destined for future removal. These warnings will be maintained for at least 1 minor version release, and may be maintained longer.
|
| 74 |
|
| 75 |
-
Note that the "public API" includes the
|
| 76 |
|
| 77 |
## Installing for Development
|
| 78 |
|
|
|
|
| 72 |
|
| 73 |
Whenever possible, FastMCP will issue deprecation warnings when users attempt to use APIs that are either deprecated or destined for future removal. These warnings will be maintained for at least 1 minor version release, and may be maintained longer.
|
| 74 |
|
| 75 |
+
Note that the "public API" includes the public functionality of the `FastMCP` server, core FastMCP components like `Tool`, `Prompt`, `Resource`, and `ResourceTemplate`, and their respective public methods. It does not include private methods, utilities, or objects that are stored as private attributes, as we do not expect users to rely on those implementation details.
|
| 76 |
|
| 77 |
## Installing for Development
|
| 78 |
|
src/fastmcp/prompts/prompt.py
CHANGED
|
@@ -15,11 +15,11 @@ from pydantic import Field, TypeAdapter, validate_call
|
|
| 15 |
|
| 16 |
from fastmcp.exceptions import PromptError
|
| 17 |
from fastmcp.server.dependencies import get_context
|
|
|
|
| 18 |
from fastmcp.utilities.json_schema import compress_schema
|
| 19 |
from fastmcp.utilities.logging import get_logger
|
| 20 |
from fastmcp.utilities.types import (
|
| 21 |
FastMCPBaseModel,
|
| 22 |
-
FastMCPComponent,
|
| 23 |
find_kwarg_by_type,
|
| 24 |
get_cached_typeadapter,
|
| 25 |
)
|
|
|
|
| 15 |
|
| 16 |
from fastmcp.exceptions import PromptError
|
| 17 |
from fastmcp.server.dependencies import get_context
|
| 18 |
+
from fastmcp.utilities.components import FastMCPComponent
|
| 19 |
from fastmcp.utilities.json_schema import compress_schema
|
| 20 |
from fastmcp.utilities.logging import get_logger
|
| 21 |
from fastmcp.utilities.types import (
|
| 22 |
FastMCPBaseModel,
|
|
|
|
| 23 |
find_kwarg_by_type,
|
| 24 |
get_cached_typeadapter,
|
| 25 |
)
|
src/fastmcp/resources/resource.py
CHANGED
|
@@ -11,7 +11,6 @@ import pydantic_core
|
|
| 11 |
from mcp.types import Resource as MCPResource
|
| 12 |
from pydantic import (
|
| 13 |
AnyUrl,
|
| 14 |
-
BeforeValidator,
|
| 15 |
ConfigDict,
|
| 16 |
Field,
|
| 17 |
UrlConstraints,
|
|
@@ -20,9 +19,8 @@ from pydantic import (
|
|
| 20 |
)
|
| 21 |
|
| 22 |
from fastmcp.server.dependencies import get_context
|
|
|
|
| 23 |
from fastmcp.utilities.types import (
|
| 24 |
-
FastMCPBaseModel,
|
| 25 |
-
_convert_set_default_none,
|
| 26 |
find_kwarg_by_type,
|
| 27 |
)
|
| 28 |
|
|
@@ -30,7 +28,7 @@ if TYPE_CHECKING:
|
|
| 30 |
pass
|
| 31 |
|
| 32 |
|
| 33 |
-
class Resource(
|
| 34 |
"""Base class for all resources."""
|
| 35 |
|
| 36 |
model_config = ConfigDict(validate_default=True)
|
|
@@ -38,13 +36,6 @@ class Resource(FastMCPBaseModel, abc.ABC):
|
|
| 38 |
uri: Annotated[AnyUrl, UrlConstraints(host_required=False)] = Field(
|
| 39 |
default=..., description="URI of the resource"
|
| 40 |
)
|
| 41 |
-
name: str | None = Field(default=None, description="Name of the resource")
|
| 42 |
-
description: str | None = Field(
|
| 43 |
-
default=None, description="Description of the resource"
|
| 44 |
-
)
|
| 45 |
-
tags: Annotated[set[str], BeforeValidator(_convert_set_default_none)] = Field(
|
| 46 |
-
default_factory=set, description="Tags for the resource"
|
| 47 |
-
)
|
| 48 |
mime_type: str = Field(
|
| 49 |
default="text/plain",
|
| 50 |
description="MIME type of the resource content",
|
|
|
|
| 11 |
from mcp.types import Resource as MCPResource
|
| 12 |
from pydantic import (
|
| 13 |
AnyUrl,
|
|
|
|
| 14 |
ConfigDict,
|
| 15 |
Field,
|
| 16 |
UrlConstraints,
|
|
|
|
| 19 |
)
|
| 20 |
|
| 21 |
from fastmcp.server.dependencies import get_context
|
| 22 |
+
from fastmcp.utilities.components import FastMCPComponent
|
| 23 |
from fastmcp.utilities.types import (
|
|
|
|
|
|
|
| 24 |
find_kwarg_by_type,
|
| 25 |
)
|
| 26 |
|
|
|
|
| 28 |
pass
|
| 29 |
|
| 30 |
|
| 31 |
+
class Resource(FastMCPComponent, abc.ABC):
|
| 32 |
"""Base class for all resources."""
|
| 33 |
|
| 34 |
model_config = ConfigDict(validate_default=True)
|
|
|
|
| 36 |
uri: Annotated[AnyUrl, UrlConstraints(host_required=False)] = Field(
|
| 37 |
default=..., description="URI of the resource"
|
| 38 |
)
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 39 |
mime_type: str = Field(
|
| 40 |
default="text/plain",
|
| 41 |
description="MIME type of the resource content",
|
src/fastmcp/resources/template.py
CHANGED
|
@@ -17,9 +17,9 @@ from pydantic import (
|
|
| 17 |
|
| 18 |
from fastmcp.resources.types import Resource
|
| 19 |
from fastmcp.server.dependencies import get_context
|
|
|
|
| 20 |
from fastmcp.utilities.json_schema import compress_schema
|
| 21 |
from fastmcp.utilities.types import (
|
| 22 |
-
FastMCPComponent,
|
| 23 |
find_kwarg_by_type,
|
| 24 |
get_cached_typeadapter,
|
| 25 |
)
|
|
|
|
| 17 |
|
| 18 |
from fastmcp.resources.types import Resource
|
| 19 |
from fastmcp.server.dependencies import get_context
|
| 20 |
+
from fastmcp.utilities.components import FastMCPComponent
|
| 21 |
from fastmcp.utilities.json_schema import compress_schema
|
| 22 |
from fastmcp.utilities.types import (
|
|
|
|
| 23 |
find_kwarg_by_type,
|
| 24 |
get_cached_typeadapter,
|
| 25 |
)
|
src/fastmcp/tools/tool.py
CHANGED
|
@@ -14,10 +14,10 @@ from pydantic import Field
|
|
| 14 |
|
| 15 |
import fastmcp
|
| 16 |
from fastmcp.server.dependencies import get_context
|
|
|
|
| 17 |
from fastmcp.utilities.json_schema import compress_schema
|
| 18 |
from fastmcp.utilities.logging import get_logger
|
| 19 |
from fastmcp.utilities.types import (
|
| 20 |
-
FastMCPComponent,
|
| 21 |
Image,
|
| 22 |
find_kwarg_by_type,
|
| 23 |
get_cached_typeadapter,
|
|
|
|
| 14 |
|
| 15 |
import fastmcp
|
| 16 |
from fastmcp.server.dependencies import get_context
|
| 17 |
+
from fastmcp.utilities.components import FastMCPComponent
|
| 18 |
from fastmcp.utilities.json_schema import compress_schema
|
| 19 |
from fastmcp.utilities.logging import get_logger
|
| 20 |
from fastmcp.utilities.types import (
|
|
|
|
| 21 |
Image,
|
| 22 |
find_kwarg_by_type,
|
| 23 |
get_cached_typeadapter,
|
src/fastmcp/utilities/components.py
ADDED
|
@@ -0,0 +1,39 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
from collections.abc import Sequence
|
| 2 |
+
from typing import Annotated, TypeVar
|
| 3 |
+
|
| 4 |
+
from pydantic import BeforeValidator, Field
|
| 5 |
+
|
| 6 |
+
from fastmcp.utilities.types import FastMCPBaseModel
|
| 7 |
+
|
| 8 |
+
T = TypeVar("T")
|
| 9 |
+
|
| 10 |
+
|
| 11 |
+
def _convert_set_default_none(maybe_set: set[T] | Sequence[T] | None) -> set[T]:
|
| 12 |
+
"""Convert a sequence to a set, defaulting to an empty set if None."""
|
| 13 |
+
if maybe_set is None:
|
| 14 |
+
return set()
|
| 15 |
+
if isinstance(maybe_set, set):
|
| 16 |
+
return maybe_set
|
| 17 |
+
return set(maybe_set)
|
| 18 |
+
|
| 19 |
+
|
| 20 |
+
class FastMCPComponent(FastMCPBaseModel):
|
| 21 |
+
"""Base class for FastMCP tools, prompts, resources, and resource templates."""
|
| 22 |
+
|
| 23 |
+
name: str = Field(
|
| 24 |
+
description="The name of the component.",
|
| 25 |
+
)
|
| 26 |
+
description: str | None = Field(
|
| 27 |
+
default=None,
|
| 28 |
+
description="The description of the component.",
|
| 29 |
+
)
|
| 30 |
+
tags: Annotated[set[str], BeforeValidator(_convert_set_default_none)] = Field(
|
| 31 |
+
default_factory=set,
|
| 32 |
+
description="Tags for the component.",
|
| 33 |
+
)
|
| 34 |
+
|
| 35 |
+
def __eq__(self, other: object) -> bool:
|
| 36 |
+
if type(self) is not type(other):
|
| 37 |
+
return False
|
| 38 |
+
assert isinstance(other, type(self))
|
| 39 |
+
return self.model_dump() == other.model_dump()
|
src/fastmcp/utilities/types.py
CHANGED
|
@@ -2,55 +2,24 @@
|
|
| 2 |
|
| 3 |
import base64
|
| 4 |
import inspect
|
| 5 |
-
from collections.abc import Callable
|
| 6 |
from functools import lru_cache
|
| 7 |
from pathlib import Path
|
| 8 |
from types import UnionType
|
| 9 |
from typing import Annotated, TypeVar, Union, get_args, get_origin
|
| 10 |
|
| 11 |
from mcp.types import ImageContent
|
| 12 |
-
from pydantic import BaseModel,
|
| 13 |
|
| 14 |
T = TypeVar("T")
|
| 15 |
|
| 16 |
|
| 17 |
-
def _convert_set_default_none(maybe_set: set[T] | Sequence[T] | None) -> set[T]:
|
| 18 |
-
"""Convert a sequence to a set, defaulting to an empty set if None."""
|
| 19 |
-
if maybe_set is None:
|
| 20 |
-
return set()
|
| 21 |
-
if isinstance(maybe_set, set):
|
| 22 |
-
return maybe_set
|
| 23 |
-
return set(maybe_set)
|
| 24 |
-
|
| 25 |
-
|
| 26 |
class FastMCPBaseModel(BaseModel):
|
| 27 |
"""Base model for FastMCP models."""
|
| 28 |
|
| 29 |
model_config = ConfigDict(extra="forbid")
|
| 30 |
|
| 31 |
|
| 32 |
-
class FastMCPComponent(FastMCPBaseModel):
|
| 33 |
-
"""Base class for FastMCP tools, prompts, resources, and resource templates."""
|
| 34 |
-
|
| 35 |
-
name: str = Field(
|
| 36 |
-
description="The name of the component.",
|
| 37 |
-
)
|
| 38 |
-
description: str | None = Field(
|
| 39 |
-
default=None,
|
| 40 |
-
description="The description of the component.",
|
| 41 |
-
)
|
| 42 |
-
tags: Annotated[set[str], BeforeValidator(_convert_set_default_none)] = Field(
|
| 43 |
-
default_factory=set,
|
| 44 |
-
description="Tags for the component.",
|
| 45 |
-
)
|
| 46 |
-
|
| 47 |
-
def __eq__(self, other: object) -> bool:
|
| 48 |
-
if type(self) is not type(other):
|
| 49 |
-
return False
|
| 50 |
-
assert isinstance(other, type(self))
|
| 51 |
-
return self.model_dump() == other.model_dump()
|
| 52 |
-
|
| 53 |
-
|
| 54 |
@lru_cache(maxsize=5000)
|
| 55 |
def get_cached_typeadapter(cls: T) -> TypeAdapter[T]:
|
| 56 |
"""
|
|
|
|
| 2 |
|
| 3 |
import base64
|
| 4 |
import inspect
|
| 5 |
+
from collections.abc import Callable
|
| 6 |
from functools import lru_cache
|
| 7 |
from pathlib import Path
|
| 8 |
from types import UnionType
|
| 9 |
from typing import Annotated, TypeVar, Union, get_args, get_origin
|
| 10 |
|
| 11 |
from mcp.types import ImageContent
|
| 12 |
+
from pydantic import BaseModel, ConfigDict, TypeAdapter
|
| 13 |
|
| 14 |
T = TypeVar("T")
|
| 15 |
|
| 16 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 17 |
class FastMCPBaseModel(BaseModel):
|
| 18 |
"""Base model for FastMCP models."""
|
| 19 |
|
| 20 |
model_config = ConfigDict(extra="forbid")
|
| 21 |
|
| 22 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 23 |
@lru_cache(maxsize=5000)
|
| 24 |
def get_cached_typeadapter(cls: T) -> TypeAdapter[T]:
|
| 25 |
"""
|