A kanban-style issue tracker with TUI, REST + WebSocket API, CLI, and MCP server. Meta-package.
Project description
Kanbaroo
A kanban-style issue tracker with a TUI, REST + WebSocket API, CLI, and MCP server. Designed to be useful standalone, and to integrate with trusty-cage for AI-driven workflows.
Status: Phase 2 complete. Single-user, terminal + web + AI.
What it does
Kanbaroo exposes the same data through five surfaces:
- TUI (Textual) for terminal-centric humans: workspace list, kanban board, story detail, fuzzy search, audit feed.
- Web UI (React SPA, served by the API at
/ui): workspace list, kanban board with drag-to-transition, story detail, comments, tags, live WebSocket updates, keyboard shortcuts. - CLI (Typer + Rich): scriptable access to every resource, JSON output for pipelines.
- REST + WebSocket API (FastAPI): the source of truth. WebSocket feeds live change events; REST is always authoritative.
- MCP server: lets AI agents (outer Claude in particular) read and write the board through the Model Context Protocol.
The data model is intentionally Jira-shaped but simpler. Workspaces contain optional Epics which contain Stories. Stories carry comments, tags, typed linkages, priority, and a standard kanban lifecycle. Every mutation is attributed to a human, claude, or system actor and recorded in an immutable audit log.
Architecture
flowchart TB
subgraph clients["Clients"]
TUI["TUI<br/>(Textual)"]
CLI["CLI<br/>(Typer + Rich)"]
MCP["MCP Server<br/>(mcp SDK)"]
WEB["Web UI<br/>(React SPA)"]
end
subgraph server["Kanbaroo Server"]
REST["FastAPI<br/>REST endpoints"]
WS["WebSocket<br/>event stream"]
CORE["kanbaroo-core<br/>(business logic)"]
end
subgraph storage["Storage"]
DB[("SQLite (local)<br/>Postgres (cloud)")]
end
subgraph external["External Consumers"]
DUCK["DuckDB / Snowflake<br/>(read-only)"]
GHA["GitHub Actions<br/>(read-only scripts)"]
end
TUI -->|HTTP + WS| REST
TUI -->|HTTP + WS| WS
CLI -->|HTTP| REST
MCP -->|HTTP| REST
WEB -->|HTTP + WS| REST
REST --> CORE
WS --> CORE
CORE --> DB
DB -.->|direct read| DUCK
DB -.->|direct read| GHA
style DUCK stroke-dasharray: 5 5
style GHA stroke-dasharray: 5 5
Installation
Requires Python 3.12 or newer.
# Everything (server + TUI + CLI + MCP)
pip install 'kanbaroo[all]'
# Or pick and choose:
pip install kanbaroo-api # Just the server (no web UI)
pip install 'kanbaroo-api[web]' # Server + bundled web UI at /ui
pip install kanbaroo-cli # CLI only (pulls in core)
pip install kanbaroo-tui # TUI only
pip install kanbaroo-mcp # MCP server only
Contributors working from a checkout should use the uv workspace instead:
uv sync --all-packages --dev
Quickstart
For a human walking up cold, all the way from install to a running board:
# 1. Install
pip install 'kanbaroo[all]'
# 2. Initialize config dir, apply migrations, mint your first token
kb init
# 3. Start the server (docker compose under the hood)
kb server start
# 4. Create your first workspace
kb workspace create --key KAN --name "My Work"
# 5. File a story
kb story create --workspace KAN --title "First task"
# 6. In another terminal, open the TUI on the board
kanbaroo-tui
Press ? on any TUI screen for the keybinding cheatsheet. Press / from the workspace list or board for fuzzy search. a opens the global audit feed.
Configuration
Kanbaroo reads settings from $KANBAROO_CONFIG_DIR/config.toml (default ~/.kanbaroo/config.toml), which kb init creates for you. Environment variables override the TOML values when set.
| Variable | Consumed by | Default / note |
|---|---|---|
KANBAROO_DATABASE_URL |
core, api, kb init, kb backup |
Required for the API to start. Docker supplies sqlite:////data/kanbaroo.db inside the container. |
KANBAROO_API_URL |
cli, tui, mcp | Overrides api_url in config.toml. Example: http://localhost:8080. |
KANBAROO_TOKEN |
cli, tui | Bearer token for API auth. Overrides token in config.toml. |
KANBAROO_MCP_TOKEN |
mcp | MCP-specific token; falls back to KANBAROO_TOKEN. |
KANBAROO_CONFIG_DIR |
cli, tui, mcp, kb init |
Override for the config directory. Default: ~/.kanbaroo. |
KANBAROO_WORKSPACE |
cli | Default workspace key so you can omit --workspace on every command. Example: KAN. |
KANBAROO_API_HOST |
api server | Uvicorn bind host. Default: 0.0.0.0. |
KANBAROO_API_PORT |
api server | Uvicorn bind port. Default: 8080. |
KANBAROO_COMPOSE_FILE |
kb server |
Path to a non-default docker-compose.yml (useful for CI). |
KANBAROO_MCP_LOG_LEVEL |
mcp | INFO by default; DEBUG for verbose MCP logs. |
For a long-lived single-user setup with per-project token attribution, host-bind-mounted SQLite, and nightly snapshots, see docs/deployment-dogfood.md. The fastest path to wire a single project up to a running Kanbaroo server is kb project init, which creates the workspace, mints a per-project claude token, and writes a project-root .mcp.json in one shot.
Web UI
The kanbaroo-web package ships a Vite + React SPA that kanbaroo-api serves at /ui. Once the API is running, visit http://localhost:8080/ui in a browser.
First-boot inside the container
kb server start runs docker compose up -d; the API runs inside the kanbaroo-api container with its SQLite DB on a named volume. The volume is blank on first boot, so migrations and the initial token have to happen inside the container:
# Bring the stack up
kb server start
# Apply migrations
docker compose exec -e KANBAROO_DATABASE_URL="sqlite:////data/kanbaroo.db" \
kanbaroo-api \
uv run --no-dev alembic -c /app/packages/kanbaroo-core/alembic.ini upgrade head
# Mint the first token (print it once; save it)
docker compose exec -e KANBAROO_DATABASE_URL="sqlite:////data/kanbaroo.db" \
kanbaroo-api \
uv run --no-dev kb init
Copy the kbr_ token that kb init prints and paste it into the /ui login form. The token is stored in browser localStorage under kanbaroo.token; press "Log out" to clear it.
You can also mint additional tokens later with kb token create --actor-type human --actor-id you --name "web" (inside the container, same docker compose exec wrapper).
Shipped in v0.2.0:
- Workspace list with inline create.
- Kanban board with drag-to-transition, illegal-move rejection, optimistic updates.
- Story detail: markdown description, metadata, comments (with one-level replies), tags, audit trail.
- Live updates via the existing
/api/v1/eventsWebSocket. - Story creation modal (
non the board). - In-board search (
/on the board; matches on human id prefix and title substring). - Keyboard shortcuts:
nnew story,/search,eedit story,?shortcut help,Escapeclose modal / clear search / exit edit mode.
The release wheel auto-includes the built bundle, so pipx install --include-deps 'kanbaroo[all]' picks up the UI. Node 20+ is only required at build time for maintainers publishing a new release.
Developing the web UI
make web-build # Build the SPA into packages/kanbaroo-web/src/kanbaroo_web/dist/
make web-dev # Vite dev server on :5173, proxies /api and /api/v1/events to :8080
make web-test # vitest, single-shot
MCP setup
Let an AI agent drive Kanbaroo through the Model Context Protocol. The MCP server is a thin translator between the MCP tool protocol and the Kanbaroo REST API; every mutation routes through the API and is attributed to the MCP token's actor.
First create a dedicated claude-typed token so AI mutations are audited correctly:
kb token create --actor-type claude --actor-id outer-claude --name "claude"
Copy the plaintext that kb token create prints into KANBAROO_MCP_TOKEN in your shell, then add this to Claude's mcpServers block:
{
"mcpServers": {
"kanbaroo": {
"command": "kanbaroo-mcp",
"args": ["--api-url", "http://localhost:8080", "--token-env", "KANBAROO_MCP_TOKEN"]
}
}
}
See docs/mcp-setup.md for the full walkthrough, the smoke test, and the tool reference.
Docs
docs/spec.md: authoritative design intent. Start here if you want the why.docs/api-reference.md: generated REST API reference.docs/mcp-setup.md: MCP setup guide for AI agents.docs/future-skill-draft.md: draft workflow skill for AI agents using Kanbaroo via MCP.CLAUDE.md: guidance for Claude Code when working in this repo.CHANGELOG.md: release notes.
Development
This is a uv workspace monorepo with six packages in packages/ (kanbaroo-core, -api, -cli, -tui, -mcp, -web) and a top-level meta-package with an [all] extra. Before committing anything:
uv run ruff format .
uv run ruff check --fix .
uv run mypy packages/
uv run pytest
License
MIT. See LICENSE.
Project details
Release history Release notifications | RSS feed
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file kanbaroo-0.3.0.tar.gz.
File metadata
- Download URL: kanbaroo-0.3.0.tar.gz
- Upload date:
- Size: 696.5 kB
- Tags: Source
- Uploaded using Trusted Publishing? No
- Uploaded via: uv/0.11.7 {"installer":{"name":"uv","version":"0.11.7","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"macOS","version":null,"id":null,"libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":null}
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
4226d3b649a642f4c877c88330e7a81709ebe03a2f731a1eccc204fec414f3e5
|
|
| MD5 |
c48df4b4cbfe311fac049bb4c434f7b9
|
|
| BLAKE2b-256 |
664cb07e80ae8e9fe24e167d538149fed69dff1074acf9e67f6c7c77107ca786
|
File details
Details for the file kanbaroo-0.3.0-py3-none-any.whl.
File metadata
- Download URL: kanbaroo-0.3.0-py3-none-any.whl
- Upload date:
- Size: 6.1 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? No
- Uploaded via: uv/0.11.7 {"installer":{"name":"uv","version":"0.11.7","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"macOS","version":null,"id":null,"libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":null}
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
746944faf93dda275a87324767f71e1ed7c17d03dd6ae29832080ad54caa537a
|
|
| MD5 |
2d3eabcd58dd3d1f3478fddc84484bc3
|
|
| BLAKE2b-256 |
23770aa49c06186dc67a0a00732b4937598c05ef48edd34f722f84326b394036
|