import uuid from datetime import datetime from typing import Literal from pydantic import AliasChoices, BaseModel, ConfigDict, Field, computed_field ExecutionState = Literal["manual", "queued", "scheduled", "launching", "paused", "completed", "cancelled"] LaunchMode = Literal["manual", "queued", "scheduled", "immediate"] ConcurrencyMode = Literal["sequential", "parallel"] LaunchRequestStatus = Literal["requested", "accepted", "completed", "cancelled"] class ExecutionIntentUpdate(BaseModel): execution_state: ExecutionState | None = None launch_mode: LaunchMode | None = None concurrency_mode: ConcurrencyMode | None = None queue_rank: int | None = None execution_group: str | None = None scheduled_for: datetime | None = None class ExecutionIntentRead(BaseModel): workplan_id: uuid.UUID @computed_field # type: ignore[prop-decorator] @property def workstream_id(self) -> uuid.UUID: return self.workplan_id execution_state: ExecutionState launch_mode: LaunchMode concurrency_mode: ConcurrencyMode queue_rank: int | None = None execution_group: str | None = None scheduled_for: datetime | None = None class WorkplanQueueItem(BaseModel): workplan_id: uuid.UUID slug: str title: str status: str repo_id: uuid.UUID | None = None planning_priority: str | None = None planning_order: int | None = None execution_state: ExecutionState launch_mode: LaunchMode concurrency_mode: ConcurrencyMode queue_rank: int | None = None execution_group: str | None = None scheduled_for: datetime | None = None eligible: bool blocked_by_workplan_ids: list[uuid.UUID] = Field(default_factory=list) @computed_field # type: ignore[prop-decorator] @property def blocked_by_workstream_ids(self) -> list[uuid.UUID]: return self.blocked_by_workplan_ids blocked_by_task_ids: list[uuid.UUID] = Field(default_factory=list) sort_key: list[str | int] = Field(default_factory=list) class LaunchRequestCreate(BaseModel): workplan_id: uuid.UUID = Field(validation_alias=AliasChoices("workplan_id", "workstream_id")) requested_by: str = "dashboard" requested_actor: str | None = None launch_mode: LaunchMode = "queued" concurrency_mode: ConcurrencyMode = "sequential" priority: str | None = None repo_id: uuid.UUID | None = None branch_preference: str | None = None immediate_pickup: bool = False notes: str | None = None request_metadata: dict = Field(default_factory=dict) class LaunchRequestRead(BaseModel): model_config = ConfigDict(from_attributes=True) id: uuid.UUID workplan_id: uuid.UUID requested_by: str requested_actor: str | None = None launch_mode: LaunchMode @computed_field # type: ignore[prop-decorator] @property def workstream_id(self) -> uuid.UUID: return self.workplan_id concurrency_mode: ConcurrencyMode priority: str | None = None repo_id: uuid.UUID | None = None branch_preference: str | None = None immediate_pickup: bool status: LaunchRequestStatus notes: str | None = None request_metadata: dict = Field(default_factory=dict) created_at: datetime updated_at: datetime class ExecutionSemantics(BaseModel): execution_states: dict[str, str] launch_modes: dict[str, str] concurrency_modes: dict[str, str] state_hub_responsibility: list[str] activity_core_responsibility: list[str]