# CRITICAL IMPLEMENTATION INSTRUCTIONS FOR MCP-PY3REPL
## šØ URGENT: READ THIS FIRST - DO NOT SKIP šØ
**STOP! Before you write ANY code, you MUST:**
1. Read this ENTIRE file first
2. Re-read the PROHIBITIONS section
3. Re-read the MANDATORY PATTERNS section
4. Create PROGRESS.md and add: `- [ ] Read CLAUDE.md completely`
5. Check that box only after reading everything
**If you skip this file, the implementation WILL FAIL.**
This project implements an MCP server for Python REPL functionality. The implementation is **EXTREMELY SPECIFIC** about certain patterns and requirements. Failure to follow these instructions will result in a non-functional MCP server.
## š“ CHECKPOINT: Did you read the above? If not, STOP and read it. š“
## ā ABSOLUTE PROHIBITIONS - NEVER DO THESE ā
### FROM IMPLEMENTATION_PLAN.md - THESE ARE NON-NEGOTIABLE:
1. **DO NOT** modify the test_project structure AFTER creating it - it's a reference implementation
2. **DO NOT** assume imports work without activating venv first
3. **DO NOT** use relative imports in tool implementations
4. **DO NOT** forget to make all tool handlers async
5. **DO NOT** raise exceptions in tool handlers - return ErrorData instead
6. **DO NOT** forget to validate file paths are within project directory
7. **DO NOT** forget to handle async/await properly in all tools
### ADDITIONAL CRITICAL PROHIBITIONS:
8. **DO NOT** skip creating the test_project - IT MUST BE CREATED as specified in IMPLEMENTATION_PLAN.md
9. **DO NOT** use old pydantic v1 imports - here's what changed in v2:
- ā `from pydantic import BaseSettings` ā ā
`from pydantic_settings import BaseSettings`
- ā `from pydantic import BaseModel, Field, validator` ā ā
`from pydantic import BaseModel, Field, field_validator`
- ā `@validator('field_name')` ā ā
`@field_validator('field_name')`
- ā `Config` class inside model ā ā
`model_config = ConfigDict(...)`
10. **DO NOT** forget to use `uv add "mcp[server]"` - the quotes and [server] are REQUIRED
11. **DO NOT** implement synchronous code execution - everything must properly handle async
12. **DO NOT** mix tool implementation code with test code
## šØ CRITICAL CLARIFICATION ABOUT TEST PROJECT šØ
**YES, YOU MUST CREATE THE TEST PROJECT!** The test_project is NOT optional. Here's what you need to understand:
1. **CREATE IT**: You must create the complete test_project structure as specified in IMPLEMENTATION_PLAN.md
2. **COMPLETE IT**: It needs all the files - models, API endpoints, config, database setup, tests
3. **INITIALIZE IT**: Run `uv venv` and `uv sync` in the test_project directory
4. **DON'T MODIFY IT LATER**: Once created and working, treat it as read-only for testing the MCP server
The test_project structure from IMPLEMENTATION_PLAN.md:
```
tests/test_project/
āāā pyproject.toml # You CREATE this with all dependencies
āāā .env # You CREATE this with test values
āāā .env.example # You CREATE this template
āāā alembic.ini # You CREATE this for migrations
āāā alembic/
ā āāā env.py # You CREATE this
ā āāā versions/ # You CREATE migration files
āāā app/
ā āāā main.py # You CREATE the FastAPI app
ā āāā config.py # You CREATE pydantic Settings
ā āāā database.py # You CREATE SQLModel setup
ā āāā models/
ā ā āāā user.py # You CREATE User model
ā ā āāā post.py # You CREATE Post model
ā ā āāā __init__.py
ā āāā api/
ā ā āāā users.py # You CREATE user endpoints
ā ā āāā posts.py # You CREATE post endpoints
ā ā āāā __init__.py
ā āāā services/
ā āāā rabbitmq.py # You CREATE mock service
ā āāā __init__.py
āāā tests/
ā āāā conftest.py # You CREATE pytest fixtures
ā āāā test_models.py # You CREATE model tests
ā āāā test_api.py # You CREATE API tests
ā āāā test_database.py # You CREATE database tests
ā āāā test_services.py # You CREATE service tests
āāā test.db # Gets created by SQLite
```
## ā
MANDATORY IMPLEMENTATION PATTERNS ā
### 1. EVERY MCP Tool MUST Follow This EXACT Pattern:
```python
from mcp import Tool
from mcp.types import TextContent, ToolResponse, ErrorData
@server.tool()
async def tool_name(param1: str, param2: int | None = None) -> ToolResponse:
"""Tool description for MCP discovery"""
try:
# Implementation
result = await some_operation(param1, param2)
return ToolResponse(
content=[TextContent(text=str(result))],
metadata={"extra_info": "value"}
)
except Exception as e:
return ToolResponse(
error=ErrorData(
code="ERROR_CODE",
message=str(e)
)
)
```
### 2. Virtual Environment Activation MUST Use This Code:
```python
import sys
from pathlib import Path
def activate_venv(project_dir: Path):
venv_path = project_dir / ".venv"
if venv_path.exists():
# Update sys.path
site_packages = venv_path / "lib" / f"python{sys.version_info.major}.{sys.version_info.minor}" / "site-packages"
if site_packages.exists():
sys.path.insert(0, str(site_packages))
# Update sys.prefix
sys.prefix = str(venv_path)
# Add venv bin to PATH
import os
venv_bin = venv_path / "bin"
os.environ["PATH"] = f"{venv_bin}:{os.environ.get('PATH', '')}"
# Update sys.executable
python_exe = venv_bin / "python"
if python_exe.exists():
sys.executable = str(python_exe)
```
### 4. Subprocess Execution Pattern:
```python
# IMPORTANT: subprocess.run is SYNCHRONOUS - do NOT await it!
import subprocess
async def run_command(cmd: list[str], cwd: Path) -> dict:
# This is correct - subprocess.run is sync
result = subprocess.run(
cmd,
cwd=cwd,
capture_output=True,
text=True
)
# Process the result
return {
"stdout": result.stdout,
"stderr": result.stderr,
"returncode": result.returncode
}
```
### 3. Path Validation MUST Be Done Like This:
```python
requested_path = Path(file_path).resolve()
project_root = Path.cwd()
if not requested_path.is_relative_to(project_root):
raise ValueError("Path outside project")
```
## š IMPLEMENTATION CHECKLIST - FOLLOW IN ORDER
### Phase 1: Main Project Setup
1. Create PROGRESS.md to track implementation progress
2. Run `uv init` in the project root
3. Run `uv add "mcp[server]"` - YES WITH QUOTES
4. Add all other dependencies: `uv add pydantic python-dotenv rich`
5. Add dev dependencies: `uv add --dev pytest pytest-asyncio black ruff`
6. Create the src/mcp_py3repl/ directory structure
### Phase 2: Create Test Project (YES, CREATE IT!)
1. Create tests/test_project/ directory
2. Create the test project's pyproject.toml with ALL its dependencies
3. Create ALL the app files (models, API, config, etc.)
4. Create the test files
5. Initialize the test project:
```bash
cd tests/test_project
uv venv
uv sync
```
**CRITICAL VENV CLARIFICATION**:
- The MCP server project has its own `.venv` at the project root
- The test_project has its own `.venv` at `tests/test_project/.venv`
- These are COMPLETELY SEPARATE - don't confuse them!
- When writing MCP server code, you're using the root .venv
- When the MCP server executes code in test_project, it activates test_project's .venv
- NEVER manually activate test_project's venv while developing the MCP server
### Phase 3: Core Implementation
1. Start with models.py - define all Pydantic models
2. Implement session_manager.py with proper venv activation
3. Implement code_executor.py with output capture
4. Create server.py with proper MCP server initialization
5. Add each tool handler ONE AT A TIME and test it
## š TESTING REQUIREMENTS
### ā” TEST IMMEDIATELY AFTER IMPLEMENTING EACH TOOL ā”
**DO NOT** implement all tools and then test. You MUST follow this pattern:
1. **Implement ONE tool**
2. **Write a unit test for that tool using the test_project**
3. **Test that tool IMMEDIATELY**
4. **Fix any issues**
5. **Only then move to the next tool**
### Testing Strategy:
- **MCP Server Testing**: Will be tested manually by the user - no need for comprehensive MCP server tests yet
- **Tool Unit Tests**: REQUIRED - each tool needs unit tests based on the test_project
- **Test Location**: Create tests/test_mcp_tools.py with unit tests for each tool
### Example Unit Test Pattern:
```python
# tests/test_mcp_tools.py
import pytest
from pathlib import Path
from mcp_py3repl.server import python_execute, session_create
@pytest.mark.asyncio
async def test_python_execute():
# Create session in test_project
session_response = await session_create(
session_name="test",
working_directory=str(Path(__file__).parent / "test_project")
)
session_id = session_response.content[0].text # Extract session ID
# Test code execution
result = await python_execute(
code="from app.models.user import User; print('imported')",
session_id=session_id
)
assert "imported" in result.content[0].text
assert result.error is None
```
### Integration Testing with test_project:
1. Ensure test_project is fully created and initialized
2. Test MCP tools against the test_project
3. Verify you can:
- Load test_project's .env file
- Import test_project's models
- Run test_project's tests
- Format test_project's code
## šØ COMMON FAILURE MODES TO AVOID
1. **Import Errors**: Always activate venv before trying to import project modules
2. **Async Errors**: subprocess.run is SYNC - don't await it
3. **MCP Protocol Errors**: ToolResponse MUST have either content or error, not both
4. **Path Errors**: Always use absolute paths internally, resolve them early
5. **Environment Variable Errors**: Load .env files AFTER changing to project directory
6. **Test Project Errors**: The test_project MUST be a complete, working FastAPI project
7. **Venv Confusion**: Don't mix up the MCP server's .venv with test_project's .venv - they're separate!
## š” HELPFUL IMPLEMENTATION TIPS
1. **Start Small**: Implement `session_create` and `python_execute` first
2. **Log Everything**: Use the logger to debug issues
3. **Test Continuously**: Don't implement all tools then test - test each one
4. **MCP Package Documentation**: Google "mcp python package" or check PyPI/ReadTheDocs for the mcp package documentation to understand protocol details
5. **Use Type Hints**: They help catch errors early
6. **Test Project First**: Get the test_project working standalone before testing MCP tools on it
## š PROJECT PHILOSOPHY REMINDER
This MCP server is **stack-aware but structure-agnostic**. It should:
- Detect project structure automatically
- Work with any Python project layout
- Not impose its own structure
- Adapt to the user's project
The test_project demonstrates ONE possible structure but the MCP server should work with ANY structure.
## šØ IMPLEMENTATION ASSUMPTIONS
1. **Session Persistence**: Sessions do NOT persist across server restarts - each server start begins fresh
2. **Error Handling**: Error codes and messages should be encapsulated for easy refactoring later. Use consistent patterns like:
- `EXECUTION_ERROR` for code execution failures
- `SESSION_ERROR` for session management issues
- `PACKAGE_ERROR` for package management failures
- `FILE_ERROR` for file operations
- `ENV_ERROR` for environment variable issues
3. **Progress Tracking**: Create and maintain PROGRESS.md with concise checkboxes and minimal notes
4. **MCP Documentation**: Use Google/PyPI/ReadTheDocs to find mcp package documentation as needed
## šÆ SUCCESS CRITERIA
You have succeeded when:
1. All tools from README.md are implemented
2. The test_project EXISTS and can be fully operated through MCP tools
3. Sessions are isolated and persistent
4. Package management works with uv
5. Environment variables are loaded and set correctly
6. Code formatting and linting work
7. Tests can be run through the MCP interface
## FINAL REMINDERS
1. **CREATE THE TEST PROJECT** - It won't appear magically
2. The MCP protocol is very specific about response formats
3. When in doubt, check the mcp package documentation
4. Use structured error responses, not exceptions
5. Test each tool as you implement it
6. **DOCUMENT PROGRESS** - Update PROGRESS.md as you work with checkboxes and minimal notes
**NOW GO BUILD THIS CORRECTLY - INCLUDING THE TEST PROJECT!**
---
## š BEFORE YOU START CODING
**MANDATORY FIRST STEPS:**
1. Create PROGRESS.md with this EXACT content:
```markdown
# Implementation Progress
## Pre-Implementation Checklist
- [ ] Read CLAUDE.md completely
- [ ] Read IMPLEMENTATION_PLAN.md completely
- [ ] Understood the two-venv setup
- [ ] Understood MCP tool pattern
- [ ] Will test each tool immediately after implementing
## Phase 1: Main Project Setup
- [ ] Created PROGRESS.md (this file)
- [ ] Run uv init
- [ ] Run uv add "mcp[server]" (with quotes!)
- [ ] Add dependencies
- [ ] Create directory structure
[Continue with phases from IMPLEMENTATION_PLAN.md]
```
2. **CHECK THE BOXES** as you complete each item
3. **REFER BACK** to CLAUDE.md every time you implement a new tool
4. **COPY-PASTE** the patterns from CLAUDE.md - don't try to recreate them from memory
Remember: This file (CLAUDE.md) is your BIBLE for this implementation. When in doubt, check CLAUDE.md!