6.5 KiB
6.5 KiB
Relationship Events LLD
This document defines backend-driven state propagation and how WS notifications mirror those changes to the UI. Clients do not emit these events.
Core Rules
- Session state changes drive task state changes.
- Agentctl lifecycle changes drive session state changes, which then drive task state changes.
- Task state changes may move columns, but only between In Progress and Review for now.
All state propagation happens server-side on internal events. WebSocket events are outbound mirrors for UI synchronization.
1) Session State -> Task State
Trigger (backend only)
events.TaskSessionStateChanged(internal event bus)
Flow
- Resolve
task_idfromsession_id. - Map
TaskSessionState -> TaskState(table below). - If task state changes, call
taskSvc.UpdateTaskState(taskID, newState). - Emit
events.TaskStateChangedand WStask.state_changed. - Emit WS
session.state_changedfor clients.
Mapping Table
| TaskSessionState | TaskState | Board Column |
|---|---|---|
| CREATED | SCHEDULING | In Progress (if any) |
| STARTING | SCHEDULING | In Progress (if any) |
| RUNNING | IN_PROGRESS | In Progress |
| WAITING_FOR_INPUT | REVIEW | Review |
| COMPLETED | REVIEW | Review |
| ERROR | ERROR | (no auto-move) |
| CANCELLED | CANCELLED | (no auto-move) |
Notes:
WAITING_FOR_INPUT -> REVIEWandCOMPLETED -> REVIEWare the default paths. If a board has no Review column, keep task in its current column.- If the mapped task state equals current task state, do nothing.
2) Agentctl State -> Session State -> Task State
Triggers (backend only)
events.AgentctlStartingevents.AgentctlReadyevents.AgentctlError
Agentctl -> Session Mapping
| Agentctl Event | Session State |
|---|---|
| AgentctlStarting | STARTING |
| AgentctlReady | RUNNING |
| AgentctlError | FAILED |
Flow
- On Agentctl event, update session state in DB.
- Emit
events.TaskSessionStateChanged(which triggers session->task mapping). - Emit WS
session.agentctl_*andsession.state_changed.
3) Task State -> Column Move
Trigger (backend only)
events.TaskStateChanged
Policy (for now)
- Only move tasks between In Progress and Review.
- Do not auto-move for other states.
Flow
- When task state changes:
- If new state is
IN_PROGRESS, move to column mapped to In Progress (if exists). - If new state is
REVIEW, move to column mapped to Review (if exists).
- If new state is
- If column lookup fails or column already matches, do nothing.
- Emit
events.TaskUpdatedand WStask.updatedwith newcolumn_id.
WebSocket Notifications (Outbound Only)
session.state_changedsession.agentctl_startingsession.agentctl_readysession.agentctl_errortask.state_changedtask.updated
Clients should treat these as read-only state mirrors.
E2E Flow (Client-Initiated)
| Edge Trigger (Client) | Backend Action | Internal Event(s) | WS Notification(s) |
|---|---|---|---|
POST /api/v1/tasks (start_agent: true) |
Create task + create session + start agentctl | task.created, task_session.created | task.created, session.agentctl_starting |
POST /api/v1/tasks (start_agent: false) |
Create task + create session (idle) | task.created, task_session.created | task.created |
message.add (session message) |
Persist message + prompt agent via ACP | message.added | session.message.added |
task.state (manual update) |
Update task state | task.state_changed | task.state_changed, task.updated (column move) |
task.session.resume |
Resume session + start agentctl | task_session.state_changed | session.agentctl_starting, session.state_changed |
Notes:
- Column move only occurs for
IN_PROGRESS/REVIEWtransitions.
E2E Flow (Agent / agentctl-Initiated)
| Edge Trigger (Agent/agentctl) | Backend Action | Internal Event(s) | WS Notification(s) |
|---|---|---|---|
| Agentctl starting | Update session state → STARTING | task_session.state_changed | session.agentctl_starting, session.state_changed |
| Agentctl ready | Update session state → RUNNING | task_session.state_changed | session.agentctl_ready, session.state_changed |
| Agentctl error | Update session state → ERROR | task_session.state_changed | session.agentctl_error, session.state_changed |
| ACP content/progress | Create/append message chunks | message.added / message.updated | session.message.added / session.message.updated |
| ACP input_required | Create message (requests_input=true) | message.added | session.message.added + session.waiting_for_input |
| Git status stream update | Update session git status | git.status.updated | session.git.status |
| Workspace file change stream | Update session file activity | workspace.file.changed | session.workspace.file.changes |
| Shell output stream | Append shell output | shell.output | session.shell.output |