2. Multi-image Docker architecture - Created role-specific Dockerfiles:
- agent-base.Dockerfile (shared foundation)
- agent-pm.Dockerfile, agent-dev-be.Dockerfile, agent-dev-fe.Dockerfile
- agent-qa-be.Dockerfile, agent-qa-fe.Dockerfile, agent-doc.Dockerfile, agent-ux.Dockerfile
3. Orchestrator updates - roboco/runtime/orchestrator.py:
- Added AGENT_IMAGES mapping and get_agent_image() function
- Updated _ensure_agent_image() to build base + specialized images
- Updated _spawn_container() to use role-specific image
- Made _generate_mcp_config() role-aware (though kept notify for all since they need to receive)
/roboco/roboco/mcp/message_server.py:
- Renamed _get_or_create_session → _get_active_session
- Removed auto-creation of sessions - now returns error instead
- Added helpful error guidance when no session exists:
"NO_ACTIVE_SESSION"
"No active session in this channel. Sessions are created by PMs for tasks."
Guidance:
1. Include task_id in your message call if working on a task (routes to task's session)
2. If no task session exists, ask your PM to create one using roboco_session_create_for_tasks
3. All work communication should happen within task sessions
What This Enforces
1. Only PMs can create sessions using roboco_session_create_for_tasks (already enforced by can_create_tasks())
2. Agents MUST provide task_id when sending messages to route to the task's session
3. If no session exists → agents get clear guidance instead of auto-creating chaos
4. No more "Session 750c51e7" with 0-1 messages - sessions will be intentionally created and managed
Major feature: Sessions are now linked to tasks with smart routing and context loading, ensuring agents have proper discussion context.
## Session-Task Relationship (Many-to-Many)
- Added SessionTaskTable junction table linking sessions to tasks
- Sessions can link to multiple tasks, tasks can have multiple sessions
- is_primary flag marks the main discussion session for a task
- relationship_type: discussion, planning, review, retrospective
- Subtasks auto-inherit parent task's session
## BACKLOG Status + Activation Flow
- Tasks now created with BACKLOG status (not PENDING)
- PMs must create session BEFORE activating task
- roboco_task_activate() transitions BACKLOG → PENDING
- Prevents race condition where dev starts before session exists
- Flow: CREATE (backlog) → SESSION → ACTIVATE (pending) → spawn
## Session Scopes
- SessionScope enum: initiative, cell, task
- initiative: Cross-cell coordination (Main PM, #dev-all)
- cell: Cell-specific work (Cell PM default)
- task: Individual task execution (dev level)
- Enables future smart context loading by scope
## Message Routing to Task Sessions
- When task_id provided in roboco_message_send(), routes to task's primary session instead of channel's active session
- New API endpoint: GET /sessions/for-task/{task_id}
- TaskResponse now includes linked sessions array
## Dev Session Access
- New tool: roboco_session_history_for_task(task_id)
- Devs can now see their task's discussion history
- Messages tagged with task_id for filtering
## Communication Guidelines
- Added "When to Post / When NOT to Post" to all 9 agent blueprints
- Devs/QA/Doc should use task tools for status, journal for reasoning
- Sessions reserved for coordination that needs response
- Reduces noise: no "Starting work" or "Made progress" chat messages
Files changed:
- DB: SessionTaskTable, SessionScope column
- Services: messaging.py (linking), task.py (activation)
- MCP: 5 new session tools, message routing update
- API: session-task endpoints, TaskResponse sessions
- Blueprints: All 13 updated with session/activation workflow
- Add X-Agent-Team header to all MCP servers (journal, task, message, notify)
The permission system uses (role, team) tuple for channel access lookup.
Without team, lookup returned empty list causing "Channel not found" errors.
- Standardize header case to X-Agent-ID (uppercase) matching frontend
- Reorder journal routes: /me/* endpoints now defined before /{agent_id}/*
FastAPI was matching /me/entries as /{agent_id}/entries with agent_id="me"
causing "Agent not found: me" errors
- Fix journal search returning empty results:
- optimal.py: Pass chunk.metadata to SearchResult instead of empty dict
- journal.py: Read entry_id from result.metadata instead of parsing contentfix(mcp): resolve agent authentication and journal routing issues
- Add X-Agent-Team header to all MCP servers (journal, task, message, notify)
The permission system uses (role, team) tuple for channel access lookup.
Without team, lookup returned empty list causing "Channel not found" errors.
- Standardize header case to X-Agent-ID (uppercase) matching frontend
- Reorder journal routes: /me/* endpoints now defined before /{agent_id}/*
FastAPI was matching /me/entries as /{agent_id}/entries with agent_id="me"
causing "Agent not found: me" errors
- Fix journal search returning empty results:
- optimal.py: Pass chunk.metadata to SearchResult instead of empty dict
- journal.py: Read entry_id from result.metadata instead of parsing content