The Hermes Kanban system provides a structured interface for both AI agents and human users to coordinate complex, multi-step tasks. While the core logic resides in a shared SQLite database, the system exposes two primary interaction layers: a tool-calling interface for agents to manage their own lifecycles and an interactive web dashboard for human oversight and manual board manipulation.
Agents interact with the Kanban board through the kanban_tools module. These tools are dynamically registered into the agent's schema based on the execution context tools/kanban_tools.py1-28
The visibility of Kanban tools is strictly controlled to prevent task-scoped workers from interfering with global board state:
HERMES_KANBAN_TASK environment variable is set (indicating a dispatcher-spawned worker), the agent sees lifecycle tools (kanban_complete, kanban_block, kanban_heartbeat, kanban_comment, kanban_create, kanban_link, kanban_attach, kanban_attach_url, kanban_attachments) but is denied access to routing tools (kanban_list, kanban_unblock) tools/kanban_tools.py92-108 tests/tools/test_kanban_tools.py43-63kanban toolset in its configuration tools/kanban_tools.py52-62 and is not currently running as a spawned worker, it gains access to the full suite, including routing and enumeration tools tools/kanban_tools.py111-124 tests/tools/test_kanban_tools.py122-145hermes chat session without the kanban toolset enabled sees zero Kanban tools tools/kanban_tools.py92-102 tests/tools/test_kanban_tools.py22-40delegate_task child contexts to prevent unintended side effects and maintain clear ownership of tasks tools/kanban_tools.py75-89| Tool Name | Purpose | Implementation |
|---|---|---|
kanban_show | Retrieves full task details, comments, and run history. | _handle_show tools/kanban_tools.py177-183 |
kanban_complete | Marks the current task as done and provides a result summary. | _handle_complete tools/kanban_tools.py255-270 |
kanban_block | Transitions task to blocked and requests human intervention. | _handle_block tools/kanban_tools.py280-295 |
kanban_heartbeat | Manually refreshes the claim_expires TTL for long-running tasks. | _handle_heartbeat tools/kanban_tools.py310-320 |
kanban_list | Enumerates tasks across the board with filtering. | _handle_list tools/kanban_tools.py440-455 |
kanban_create | Creates a new task on the board. | _handle_create tools/kanban_tools.py330-345 |
kanban_link | Establishes a parent-child dependency between tasks. | _handle_link tools/kanban_tools.py360-375 |
kanban_unblock | Moves a blocked task back to ready or todo. | _handle_unblock tools/kanban_tools.py390-405 |
kanban_attach | Attaches a file to a task. | _handle_attach tools/kanban_tools.py470-485 |
kanban_attach_url | Attaches a URL to a task. | _handle_attach_url tools/kanban_tools.py500-515 |
kanban_attachments | Lists attachments for a task. | _handle_attachments tools/kanban_tools.py530-545 |
Sources: tools/kanban_tools.py1-162 tests/tools/test_kanban_tools.py21-144
The Kanban Dashboard is implemented as a plugin for the Hermes Web UI. It provides a real-time, drag-and-drop interface for task management.
plugin_api.py)The backend is a FastAPI-powered REST and WebSocket service mounted at /api/plugins/kanban/ plugins/kanban/dashboard/plugin_api.py1-7
_resolve_board plugins/kanban/dashboard/plugin_api.py97-116 It also supports creating and patching boards, including setting default_workdir tests/plugins/test_kanban_dashboard_plugin.py141-205/events) that tails the append-only task_events table on a poll interval, allowing the UI to reflect changes made by background workers or CLI commands immediately plugins/kanban/dashboard/plugin_api.py10-12hermes_cli.web_server._ws_auth_ok via the _ws_upgrade_authorized helper plugins/kanban/dashboard/plugin_api.py64-81dist/index.js)The frontend is a React-based SPA that uses the Hermes Plugin SDK for UI components plugins/kanban/dashboard/dist/index.js12-25
triage, todo, ready, etc.) to visual columns using COLUMN_ORDER plugins/kanban/dashboard/dist/index.js89-102kanban_diagnostics layer plugins/kanban/dashboard/dist/index.js117-130useI18n hook and tx() helper for localization, with English fallbacks plugins/kanban/dashboard/dist/index.js48-69style.css to define column layouts, status dots, progress pills, and lane-based grouping, ensuring theme compatibility by referencing CSS variables plugins/kanban/dashboard/dist/style.css1-218Sources: plugins/kanban/dashboard/plugin_api.py1-152 plugins/kanban/dashboard/dist/index.js1-162 tests/plugins/test_kanban_dashboard_plugin.py67-193 plugins/kanban/dashboard/dist/style.css1-218
Coordination between workers and orchestrators is governed by the kanban_db state machine and the dispatcher loop.
This diagram illustrates how Natural Language intents from agents are translated into Code Entities and Database state.
Diagram: Intent to Execution Flow
Sources: tools/kanban_tools.py255-270 hermes_cli/kanban_db.py55-68 plugins/kanban/dashboard/plugin_api.py10-12
Two specialized skills facilitate complex coordination:
kanban-worker: Designed for agents assigned to a specific task. It focuses on using kanban_complete and kanban_block to signal state changes back to the board website/docs/user-guide/features/kanban.md17-18kanban-orchestrator: Designed for "manager" agents. It uses kanban_list to find ready tasks and kanban_create to decompose high-level goals into linked sub-tasks tools/kanban_tools.py111-124The following diagram maps the status transitions enforced by kanban_db and observed by the kanban_tools.
Diagram: Task Lifecycle Transitions
Sources: hermes_cli/kanban_db.py101-112 tools/kanban_tools.py280-320
The system includes a diagnostic layer (kanban_diagnostics.py) that identifies actionable distress signals for tasks hermes_cli/kanban_diagnostics.py1-28
Diagnostics are stateless, read-only rules that analyze task history and events to find failure modes:
blocked or running (without heartbeat) for too long hermes_cli/kanban_diagnostics.py1-12triage to break the loop hermes_cli/kanban_db.py131-134Each diagnostic provides one or more DiagnosticAction objects, which the dashboard renders as recovery buttons:
reclaim: Resets the claim_lock to allow another worker to pick up a crashed task hermes_cli/kanban_diagnostics.py59-60unblock: Force-transitions a task back to ready status hermes_cli/kanban_diagnostics.py61-62cli_hint: Provides a shell command for the human operator to fix environment or auth issues hermes_cli/kanban_diagnostics.py63-64Sources: hermes_cli/kanban_diagnostics.py1-117 plugins/kanban/dashboard/dist/index.js117-130 hermes_cli/kanban_db.py131-134
The system uses SQLite's WAL (Write-Ahead Logging) mode to allow the dashboard and agents to read the board without blocking the dispatcher's write transactions hermes_cli/kanban_db.py61-68 Write operations use BEGIN IMMEDIATE and Compare-and-Swap (CAS) logic on the status and claim_lock columns to ensure that two dispatchers or agents cannot claim the same task simultaneously hermes_cli/kanban_db.py61-65 Cross-process initialization locks are handled differently on Windows using byte-range locks to prevent deadlocks tests/hermes_cli/test_kanban_db.py81-107
A unique feature of kanban_tools is the automatic activity bridge. When an agent performs any action (like a terminal command or file write), the system optionally "touches" the Kanban heartbeat tools/kanban_tools.py108-120 This prevents the dispatcher from reclaiming a task while the agent is still actively working but hasn't explicitly called kanban_heartbeat.
The Kanban system leverages contextvars.ContextVar for session-scoped context variables, replacing older os.environ-based state. This ensures that concurrent messages processed by the gateway do not interfere with each other's session data, as each asyncio task gets its own copy of the context variables gateway/session_context.py10-22 This is crucial for correct routing of background task notifications and tool calls gateway/session_context.py10-22
Sources: hermes_cli/kanban_db.py61-68 tools/kanban_tools.py108-120 tests/hermes_cli/test_kanban_db.py45-54 tests/hermes_cli/test_kanban_db.py81-107 gateway/session_context.py10-22
Refresh this wiki
This wiki was recently refreshed. Please wait 4 days to refresh again.