Fix MCP server telemetry and update graphiti-core to v0.23.0 (#1057)
* Fix MCP server telemetry and update graphiti-core to v0.23.0 - Regenerate uv.lock in Docker builds to ensure posthog dependency is included - Update graphiti-core version to 0.23.0 across all configurations - Fix Python 3.11 compatibility for Pydantic TypedDict import - Add FalkorDB Browser UI access information to startup logs 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude <noreply@anthropic.com> * Add typing-extensions as explicit dependency Required for Python 3.11 compatibility with Pydantic 2.11.7, which mandates typing_extensions.TypedDict on Python < 3.12. 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude <noreply@anthropic.com> * Use built-in TypedDict from typing module Python 3.10+ includes TypedDict in the standard library. Removed typing-extensions dependency as it's unnecessary. 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude <noreply@anthropic.com> * Revert to typing_extensions.TypedDict for Pydantic compatibility Pydantic requires typing_extensions.TypedDict on Python < 3.12. Docker container uses Python 3.11, so this is necessary. 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude <noreply@anthropic.com> * Add Ruff linter rule to prevent typing.TypedDict usage Adds banned-api configuration to both main and MCP server pyproject.toml files to enforce typing_extensions.TypedDict usage, required for Pydantic compatibility on Python < 3.12. Also includes Ruff auto-formatting changes to quote styles. 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude <noreply@anthropic.com> * Bump MCP server version to 1.0.1 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude <noreply@anthropic.com> --------- Co-authored-by: Claude <noreply@anthropic.com>
This commit is contained in:
parent
d01e3c5df9
commit
d97c248551
8 changed files with 59 additions and 33 deletions
|
|
@ -33,16 +33,20 @@ ENV UV_COMPILE_BYTECODE=1 \
|
||||||
WORKDIR /app/mcp
|
WORKDIR /app/mcp
|
||||||
|
|
||||||
# Accept graphiti-core version as build argument
|
# Accept graphiti-core version as build argument
|
||||||
ARG GRAPHITI_CORE_VERSION=0.22.0
|
ARG GRAPHITI_CORE_VERSION=0.23.0
|
||||||
|
|
||||||
# Copy project files for dependency installation
|
# Copy project files for dependency installation
|
||||||
COPY pyproject.toml uv.lock ./
|
COPY pyproject.toml uv.lock ./
|
||||||
|
|
||||||
# Remove the local path override for graphiti-core in Docker builds
|
# Remove the local path override for graphiti-core in Docker builds
|
||||||
|
# and regenerate lock file to match the PyPI version
|
||||||
RUN sed -i '/\[tool\.uv\.sources\]/,/graphiti-core/d' pyproject.toml && \
|
RUN sed -i '/\[tool\.uv\.sources\]/,/graphiti-core/d' pyproject.toml && \
|
||||||
if [ -n "${GRAPHITI_CORE_VERSION}" ]; then \
|
if [ -n "${GRAPHITI_CORE_VERSION}" ]; then \
|
||||||
sed -i "s/graphiti-core\[falkordb\]>=0\.16\.0/graphiti-core[falkordb]==${GRAPHITI_CORE_VERSION}/" pyproject.toml; \
|
sed -i "s/graphiti-core\[falkordb\]>=0\.23\.0/graphiti-core[falkordb]==${GRAPHITI_CORE_VERSION}/" pyproject.toml; \
|
||||||
fi
|
fi && \
|
||||||
|
echo "Regenerating lock file for PyPI graphiti-core..." && \
|
||||||
|
rm -f uv.lock && \
|
||||||
|
uv lock
|
||||||
|
|
||||||
# Install Python dependencies
|
# Install Python dependencies
|
||||||
RUN --mount=type=cache,target=/root/.cache/uv \
|
RUN --mount=type=cache,target=/root/.cache/uv \
|
||||||
|
|
|
||||||
|
|
@ -28,15 +28,19 @@ ENV UV_COMPILE_BYTECODE=1 \
|
||||||
WORKDIR /app/mcp
|
WORKDIR /app/mcp
|
||||||
|
|
||||||
# Accept graphiti-core version as build argument
|
# Accept graphiti-core version as build argument
|
||||||
ARG GRAPHITI_CORE_VERSION=0.22.0
|
ARG GRAPHITI_CORE_VERSION=0.23.0
|
||||||
|
|
||||||
# Copy project files for dependency installation
|
# Copy project files for dependency installation
|
||||||
COPY pyproject.toml uv.lock ./
|
COPY pyproject.toml uv.lock ./
|
||||||
|
|
||||||
# Remove the local path override for graphiti-core in Docker builds
|
# Remove the local path override for graphiti-core in Docker builds
|
||||||
# Install with BOTH neo4j and falkordb extras for maximum flexibility
|
# Install with BOTH neo4j and falkordb extras for maximum flexibility
|
||||||
|
# and regenerate lock file to match the PyPI version
|
||||||
RUN sed -i '/\[tool\.uv\.sources\]/,/graphiti-core/d' pyproject.toml && \
|
RUN sed -i '/\[tool\.uv\.sources\]/,/graphiti-core/d' pyproject.toml && \
|
||||||
sed -i "s/graphiti-core\[falkordb\]>=0\.16\.0/graphiti-core[neo4j,falkordb]==${GRAPHITI_CORE_VERSION}/" pyproject.toml
|
sed -i "s/graphiti-core\[falkordb\]>=0\.23\.0/graphiti-core[neo4j,falkordb]==${GRAPHITI_CORE_VERSION}/" pyproject.toml && \
|
||||||
|
echo "Regenerating lock file for PyPI graphiti-core..." && \
|
||||||
|
rm -f uv.lock && \
|
||||||
|
uv lock
|
||||||
|
|
||||||
# Install Python dependencies
|
# Install Python dependencies
|
||||||
RUN --mount=type=cache,target=/root/.cache/uv \
|
RUN --mount=type=cache,target=/root/.cache/uv \
|
||||||
|
|
|
||||||
|
|
@ -5,7 +5,7 @@ services:
|
||||||
context: ..
|
context: ..
|
||||||
dockerfile: docker/Dockerfile
|
dockerfile: docker/Dockerfile
|
||||||
args:
|
args:
|
||||||
GRAPHITI_CORE_VERSION: ${GRAPHITI_CORE_VERSION:-0.22.0}
|
GRAPHITI_CORE_VERSION: ${GRAPHITI_CORE_VERSION:-0.23.0}
|
||||||
MCP_SERVER_VERSION: ${MCP_SERVER_VERSION:-1.0.0}
|
MCP_SERVER_VERSION: ${MCP_SERVER_VERSION:-1.0.0}
|
||||||
BUILD_DATE: ${BUILD_DATE:-}
|
BUILD_DATE: ${BUILD_DATE:-}
|
||||||
VCS_REF: ${VCS_REF:-}
|
VCS_REF: ${VCS_REF:-}
|
||||||
|
|
|
||||||
|
|
@ -1,15 +1,16 @@
|
||||||
[project]
|
[project]
|
||||||
name = "mcp-server"
|
name = "mcp-server"
|
||||||
version = "1.0.0"
|
version = "1.0.1"
|
||||||
description = "Graphiti MCP Server"
|
description = "Graphiti MCP Server"
|
||||||
readme = "README.md"
|
readme = "README.md"
|
||||||
requires-python = ">=3.10,<4"
|
requires-python = ">=3.10,<4"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"mcp>=1.9.4",
|
"mcp>=1.9.4",
|
||||||
"openai>=1.91.0",
|
"openai>=1.91.0",
|
||||||
"graphiti-core[falkordb]>=0.16.0",
|
"graphiti-core[falkordb]>=0.23.0",
|
||||||
"pydantic-settings>=2.0.0",
|
"pydantic-settings>=2.0.0",
|
||||||
"pyyaml>=6.0",
|
"pyyaml>=6.0",
|
||||||
|
"typing-extensions>=4.0.0",
|
||||||
]
|
]
|
||||||
|
|
||||||
[project.optional-dependencies]
|
[project.optional-dependencies]
|
||||||
|
|
@ -24,7 +25,7 @@ providers = [
|
||||||
"sentence-transformers>=2.0.0",
|
"sentence-transformers>=2.0.0",
|
||||||
]
|
]
|
||||||
dev = [
|
dev = [
|
||||||
"graphiti-core>=0.16.0",
|
"graphiti-core>=0.23.0",
|
||||||
"httpx>=0.28.1",
|
"httpx>=0.28.1",
|
||||||
"mcp>=1.9.4",
|
"mcp>=1.9.4",
|
||||||
"pyright>=1.1.404",
|
"pyright>=1.1.404",
|
||||||
|
|
@ -58,6 +59,10 @@ select = [
|
||||||
]
|
]
|
||||||
ignore = ["E501"]
|
ignore = ["E501"]
|
||||||
|
|
||||||
|
[tool.ruff.lint.flake8-tidy-imports.banned-api]
|
||||||
|
# Required by Pydantic on Python < 3.12
|
||||||
|
"typing.TypedDict".msg = "Use typing_extensions.TypedDict instead."
|
||||||
|
|
||||||
[tool.ruff.format]
|
[tool.ruff.format]
|
||||||
quote-style = "single"
|
quote-style = "single"
|
||||||
indent-style = "space"
|
indent-style = "space"
|
||||||
|
|
|
||||||
|
|
@ -245,35 +245,35 @@ class GraphitiService:
|
||||||
db_provider = self.config.database.provider
|
db_provider = self.config.database.provider
|
||||||
if db_provider.lower() == 'falkordb':
|
if db_provider.lower() == 'falkordb':
|
||||||
raise RuntimeError(
|
raise RuntimeError(
|
||||||
f"\n{'='*70}\n"
|
f'\n{"=" * 70}\n'
|
||||||
f"Database Connection Error: FalkorDB is not running\n"
|
f'Database Connection Error: FalkorDB is not running\n'
|
||||||
f"{'='*70}\n\n"
|
f'{"=" * 70}\n\n'
|
||||||
f"FalkorDB at {db_config['host']}:{db_config['port']} is not accessible.\n\n"
|
f'FalkorDB at {db_config["host"]}:{db_config["port"]} is not accessible.\n\n'
|
||||||
f"To start FalkorDB:\n"
|
f'To start FalkorDB:\n'
|
||||||
f" - Using Docker Compose: cd mcp_server && docker compose up\n"
|
f' - Using Docker Compose: cd mcp_server && docker compose up\n'
|
||||||
f" - Or run FalkorDB manually: docker run -p 6379:6379 falkordb/falkordb\n\n"
|
f' - Or run FalkorDB manually: docker run -p 6379:6379 falkordb/falkordb\n\n'
|
||||||
f"{'='*70}\n"
|
f'{"=" * 70}\n'
|
||||||
) from db_error
|
) from db_error
|
||||||
elif db_provider.lower() == 'neo4j':
|
elif db_provider.lower() == 'neo4j':
|
||||||
raise RuntimeError(
|
raise RuntimeError(
|
||||||
f"\n{'='*70}\n"
|
f'\n{"=" * 70}\n'
|
||||||
f"Database Connection Error: Neo4j is not running\n"
|
f'Database Connection Error: Neo4j is not running\n'
|
||||||
f"{'='*70}\n\n"
|
f'{"=" * 70}\n\n'
|
||||||
f"Neo4j at {db_config.get('uri', 'unknown')} is not accessible.\n\n"
|
f'Neo4j at {db_config.get("uri", "unknown")} is not accessible.\n\n'
|
||||||
f"To start Neo4j:\n"
|
f'To start Neo4j:\n'
|
||||||
f" - Using Docker Compose: cd mcp_server && docker compose -f docker/docker-compose-neo4j.yml up\n"
|
f' - Using Docker Compose: cd mcp_server && docker compose -f docker/docker-compose-neo4j.yml up\n'
|
||||||
f" - Or install Neo4j Desktop from: https://neo4j.com/download/\n"
|
f' - Or install Neo4j Desktop from: https://neo4j.com/download/\n'
|
||||||
f" - Or run Neo4j manually: docker run -p 7474:7474 -p 7687:7687 neo4j:latest\n\n"
|
f' - Or run Neo4j manually: docker run -p 7474:7474 -p 7687:7687 neo4j:latest\n\n'
|
||||||
f"{'='*70}\n"
|
f'{"=" * 70}\n'
|
||||||
) from db_error
|
) from db_error
|
||||||
else:
|
else:
|
||||||
raise RuntimeError(
|
raise RuntimeError(
|
||||||
f"\n{'='*70}\n"
|
f'\n{"=" * 70}\n'
|
||||||
f"Database Connection Error: {db_provider} is not running\n"
|
f'Database Connection Error: {db_provider} is not running\n'
|
||||||
f"{'='*70}\n\n"
|
f'{"=" * 70}\n\n'
|
||||||
f"{db_provider} at {db_config.get('uri', 'unknown')} is not accessible.\n\n"
|
f'{db_provider} at {db_config.get("uri", "unknown")} is not accessible.\n\n'
|
||||||
f"Please ensure {db_provider} is running and accessible.\n\n"
|
f'Please ensure {db_provider} is running and accessible.\n\n'
|
||||||
f"{'='*70}\n"
|
f'{"=" * 70}\n'
|
||||||
) from db_error
|
) from db_error
|
||||||
# Re-raise other errors
|
# Re-raise other errors
|
||||||
raise
|
raise
|
||||||
|
|
@ -931,6 +931,11 @@ async def run_mcp_server():
|
||||||
logger.info(f' Base URL: http://{display_host}:{mcp.settings.port}/')
|
logger.info(f' Base URL: http://{display_host}:{mcp.settings.port}/')
|
||||||
logger.info(f' MCP Endpoint: http://{display_host}:{mcp.settings.port}/mcp/')
|
logger.info(f' MCP Endpoint: http://{display_host}:{mcp.settings.port}/mcp/')
|
||||||
logger.info(' Transport: HTTP (streamable)')
|
logger.info(' Transport: HTTP (streamable)')
|
||||||
|
|
||||||
|
# Show FalkorDB Browser UI access if enabled
|
||||||
|
if os.environ.get('BROWSER', '1') == '1':
|
||||||
|
logger.info(f' FalkorDB Browser UI: http://{display_host}:3000/')
|
||||||
|
|
||||||
logger.info('=' * 60)
|
logger.info('=' * 60)
|
||||||
logger.info('For MCP clients, connect to the /mcp/ endpoint above')
|
logger.info('For MCP clients, connect to the /mcp/ endpoint above')
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -1,6 +1,8 @@
|
||||||
"""Response type definitions for Graphiti MCP Server."""
|
"""Response type definitions for Graphiti MCP Server."""
|
||||||
|
|
||||||
from typing import Any, TypedDict
|
from typing import Any
|
||||||
|
|
||||||
|
from typing_extensions import TypedDict
|
||||||
|
|
||||||
|
|
||||||
class ErrorResponse(TypedDict):
|
class ErrorResponse(TypedDict):
|
||||||
|
|
|
||||||
2
mcp_server/uv.lock
generated
2
mcp_server/uv.lock
generated
|
|
@ -1082,6 +1082,7 @@ dependencies = [
|
||||||
{ name = "openai" },
|
{ name = "openai" },
|
||||||
{ name = "pydantic-settings" },
|
{ name = "pydantic-settings" },
|
||||||
{ name = "pyyaml" },
|
{ name = "pyyaml" },
|
||||||
|
{ name = "typing-extensions" },
|
||||||
]
|
]
|
||||||
|
|
||||||
[package.optional-dependencies]
|
[package.optional-dependencies]
|
||||||
|
|
@ -1132,6 +1133,7 @@ requires-dist = [
|
||||||
{ name = "pyyaml", specifier = ">=6.0" },
|
{ name = "pyyaml", specifier = ">=6.0" },
|
||||||
{ name = "ruff", marker = "extra == 'dev'", specifier = ">=0.7.1" },
|
{ name = "ruff", marker = "extra == 'dev'", specifier = ">=0.7.1" },
|
||||||
{ name = "sentence-transformers", marker = "extra == 'providers'", specifier = ">=2.0.0" },
|
{ name = "sentence-transformers", marker = "extra == 'providers'", specifier = ">=2.0.0" },
|
||||||
|
{ name = "typing-extensions", specifier = ">=4.0.0" },
|
||||||
{ name = "voyageai", marker = "extra == 'providers'", specifier = ">=0.2.3" },
|
{ name = "voyageai", marker = "extra == 'providers'", specifier = ">=0.2.3" },
|
||||||
]
|
]
|
||||||
provides-extras = ["azure", "providers", "dev"]
|
provides-extras = ["azure", "providers", "dev"]
|
||||||
|
|
|
||||||
|
|
@ -90,6 +90,10 @@ select = [
|
||||||
]
|
]
|
||||||
ignore = ["E501"]
|
ignore = ["E501"]
|
||||||
|
|
||||||
|
[tool.ruff.lint.flake8-tidy-imports.banned-api]
|
||||||
|
# Required by Pydantic on Python < 3.12
|
||||||
|
"typing.TypedDict".msg = "Use typing_extensions.TypedDict instead."
|
||||||
|
|
||||||
[tool.ruff.format]
|
[tool.ruff.format]
|
||||||
quote-style = "single"
|
quote-style = "single"
|
||||||
indent-style = "space"
|
indent-style = "space"
|
||||||
|
|
|
||||||
Loading…
Add table
Reference in a new issue