Skip to main content
Glama
implement.py4.77 kB
"""Implementation phase handler.""" import re from typing import Any from fastmcp.server.context import Context from pathfinder_mcp.handlers.base import BaseHandler from pathfinder_mcp.state import Phase class ImplementHandler(BaseHandler): """Handler for implementation phase operations.""" phase = Phase.IMPLEMENT async def execute( # noqa: C901 self, session_id: str, phase_number: int | None = None, ctx: Context | None = None, **kwargs: Any, ) -> dict[str, Any]: """Execute implementation phase. Args: session_id: Session ID phase_number: Specific phase to execute (or next uncompleted) ctx: FastMCP context for elicitation Returns: Phase details and tasks """ # Validate phase (must be PLAN or IMPLEMENT) error = self.validate_phase(session_id, [Phase.PLAN, Phase.IMPLEMENT]) if error: return error # Load plan plan_content = self.artifact_writer.read_artifact(session_id, "plan.md") if not plan_content: return {"error": "Plan not found", "code": "MISSING_PLAN"} # Extract phases phases = self._extract_phases(plan_content) if not phases: return {"error": "No phases in plan", "code": "NO_PHASES"} # Find target phase if phase_number is not None: target = next((p for p in phases if p["number"] == phase_number), None) if not target: return { "error": f"Phase {phase_number} not found", "code": "PHASE_NOT_FOUND", "available_phases": [p["number"] for p in phases], } else: target = next((p for p in phases if not p["completed"]), None) if not target: return { "session_id": session_id, "status": "all_phases_completed", "message": "All phases complete!", } # Elicit confirmation if transitioning state = self.get_session(session_id) if state and state.is_plan and ctx is not None: try: result = await ctx.elicit( f"Begin Phase {target['number']}: {target['title']}?", response_type=["yes", "no"], ) if result.action != "accept" or result.data == "no": return { "session_id": session_id, "phase": "plan", "message": "Implementation cancelled.", "cancelled": True, } except Exception: pass # Transition if needed if state and state.is_plan: new_state = state.transition_to(Phase.IMPLEMENT) self.set_session(session_id, new_state) # Update progress progress = f"\n## Phase {target['number']}: {target['title']}\n\n" progress += "**Status**: In Progress\n\n### Tasks\n" for task in target["tasks"]: status = "x" if task["done"] else " " progress += f"- [{status}] {task['text']}\n" self.artifact_writer.write_progress(session_id, progress) self.context_monitor.add_message(progress) return { "session_id": session_id, "phase": "implement", "executing_phase": { "number": target["number"], "title": target["title"], "tasks": target["tasks"], }, "total_phases": len(phases), "completed_phases": sum(1 for p in phases if p["completed"]), "context": self.get_context_status(), "message": f"Executing Phase {target['number']}.", } def _extract_phases(self, plan_content: str) -> list[dict[str, Any]]: """Extract phase sections from plan.""" phases: list[dict[str, Any]] = [] pattern = ( r"## Phase (\d+):?\s*([^\n]*)\n(.*?)(?=## Phase \d+|## Implementation|$)" ) for match in re.findall(pattern, plan_content, re.DOTALL): num = int(match[0]) title = match[1].strip() content = match[2].strip() tasks = re.findall(r"- \[([ x])\] (.+)", content) phases.append( { "number": num, "title": title, "tasks": [{"done": t[0] == "x", "text": t[1]} for t in tasks], "completed": all(t[0] == "x" for t in tasks) if tasks else False, } ) return phases

Latest Blog Posts

MCP directory API

We provide all the information about MCP servers via our MCP API.

curl -X GET 'https://glama.ai/api/mcp/v1/servers/jamesctucker/pathfinder-mcp'

If you have feedback or need assistance with the MCP directory API, please join our Discord server