Files
claudetools/api/services/coord_component_service.py
Mike Swanson 63975284f4 feat: agent coordination system (workflows, locks, components, messages)
Adds /api/coord/* endpoints for real-time cross-session coordination:
- coord_workflows: named units of work per project
- coord_work_items: tasks within workflows with dependency chains
- coord_session_locks: exclusive resource locks with auto-expiry (TTL)
- coord_component_states: live component state per project (upsert)
- coord_messages: cross-session messaging and broadcasts
- /api/coord/status: cross-project snapshot endpoint

Replaces PROJECT_STATE.md as the coordination layer for Claude sessions.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-05-12 08:25:33 -07:00

64 lines
2.0 KiB
Python

"""Service layer for CoordComponentState."""
from typing import Optional
from fastapi import HTTPException, status
from sqlalchemy.dialects.mysql import insert
from sqlalchemy.orm import Session
from api.models.coord_component_state import CoordComponentState
from api.schemas.coord_component_state import CoordComponentStateUpsert
def get_component_states(
db: Session,
project_key: Optional[str] = None,
) -> list[CoordComponentState]:
"""Return all component states, optionally filtered by project."""
q = db.query(CoordComponentState)
if project_key:
q = q.filter(CoordComponentState.project_key == project_key)
return q.order_by(CoordComponentState.project_key, CoordComponentState.component).all()
def upsert_component_state(
db: Session,
project_key: str,
component: str,
data: CoordComponentStateUpsert,
) -> CoordComponentState:
"""Insert or update a component state using MariaDB ON DUPLICATE KEY UPDATE."""
try:
stmt = insert(CoordComponentState).values(
project_key=project_key,
component=component,
state=data.state,
version=data.version,
notes=data.notes,
updated_by=data.updated_by,
)
stmt = stmt.on_duplicate_key_update(
state=stmt.inserted.state,
version=stmt.inserted.version,
notes=stmt.inserted.notes,
updated_by=stmt.inserted.updated_by,
)
db.execute(stmt)
db.commit()
record = (
db.query(CoordComponentState)
.filter(
CoordComponentState.project_key == project_key,
CoordComponentState.component == component,
)
.first()
)
return record
except Exception as e:
db.rollback()
raise HTTPException(
status_code=status.HTTP_500_INTERNAL_SERVER_ERROR,
detail=f"Failed to upsert component state: {e}"
)