"""Pydantic schemas for session branches and fork points.""" from __future__ import annotations from typing import Any from uuid import UUID from datetime import datetime from pydantic import BaseModel, Field class BranchCreate(BaseModel): label: str = Field(..., max_length=200) status: str = "untried" class BranchUpdate(BaseModel): status: str = Field(..., pattern="^(active|dead_end|solved|untried|revived)$") status_reason: str | None = None class BranchResponse(BaseModel): id: UUID session_id: UUID parent_branch_id: UUID | None fork_point_step_id: UUID | None branch_order: int label: str status: str status_reason: str | None status_changed_at: datetime | None context_summary: dict[str, Any] | None evidence_from_branch_id: UUID | None evidence_description: str | None step_count: int = 0 created_at: datetime updated_at: datetime model_config = {"from_attributes": True} class BranchTreeResponse(BaseModel): branches: list[BranchResponse] active_branch_id: UUID | None class ForkOption(BaseModel): label: str = Field(..., max_length=200) description: str = Field(..., max_length=500) class ForkCreateRequest(BaseModel): fork_reason: str = Field(..., min_length=5, max_length=2000) options: list[ForkOption] = Field(..., min_length=2, max_length=10) class ForkPointResponse(BaseModel): id: UUID session_id: UUID parent_branch_id: UUID trigger_step_id: UUID | None fork_reason: str options: list[dict[str, Any]] created_at: datetime model_config = {"from_attributes": True} class BranchSwitchResponse(BaseModel): active_branch_id: UUID branch: BranchResponse conversation_messages: list[dict[str, Any]] class ReviveRequest(BaseModel): evidence_from_branch_id: UUID evidence_description: str = Field(..., min_length=5, max_length=2000) class BranchMessageRequest(BaseModel): message: str = Field(..., min_length=1, max_length=8000) upload_ids: list[UUID] = Field(default_factory=list, max_length=10) class BranchMessageResponse(BaseModel): content: str branch_id: UUID step_id: UUID | None = None