Arbor
Run agentic coding workflows in a fully native desktop app for Git worktrees, terminals, and diffs.
Install / Use
/learn @penso/ArborREADME
Arbor
Arbor is a fully native app for agentic coding built with Rust and GPUI. It gives you one place to manage repositories, issue-driven worktrees, embedded terminals, managed processes, diffs, PR context, AI coding agent activity, and a shared daemon that also powers Arbor's web UI, CLI, and MCP server.
Why Arbor
- Fully native desktop app, UI and terminal stack included, optimized for long-running local workflows
- One daemon-backed model for the desktop app, web UI, CLI, and MCP server
- Built for parallel coding sessions across local repos, issue queues, and remote outposts
Core Capabilities
Repositories, Worktrees, and Issues
- List, create, and delete worktrees across multiple repositories
- Create managed worktrees directly from GitHub or GitLab issues
- Preview sanitized worktree names, branch names, and target paths before creation
- Repo-local branch naming rules via
[branch]inarbor.toml - Delete confirmation with unpushed commit detection
- Optional branch cleanup on worktree deletion
- Worktree navigation history (back/forward)
- Last git activity timestamp per worktree
- Automatic issue linking to existing branches and open PRs / MRs
Embedded Terminal, Processes, and Tasks
- Built-in PTY terminal with truecolor and
xterm-256colorsupport - Multiple terminal tabs per worktree
- Experimental embedded
libghostty-vtengine behind a compile-time feature flag, used by default when available - Persistent daemon-based sessions (survive app restarts)
- Session attach/detach and signals (interrupt/terminate/kill)
- Managed processes from both
Procfileandarbor.toml - Process restart state, memory metrics, and terminal-session linkage
- Scheduled
[[tasks]]fromarbor.toml, with optional Claude or Codex triggers - Bell-aware terminal activity and completion notifications
Diff, PR, and Review Context
- Side-by-side diff display with addition/deletion line counts
- Changed file listing per worktree
- File tree browsing with directory expand/collapse
- Multi-tab diff sessions
- PR summary and detail cards in the changes pane
- Native inline PR comment actions and review-comment refresh support
Agent Chat
- Interactive chat sessions with ACP agents (Claude, Codex, Pi, Gemini, and more via acpx)
- OpenAI-compatible provider support: Ollama, LM Studio, OpenRouter, OpenAI, and any
/v1/chat/completionsendpoint - Streaming responses via SSE for OpenAI-compatible providers and JSONL for ACP agents
- Automatic model discovery: probes
/v1/modelsat startup for configured providers - Model selector with per-provider sections and distinct icons (ACP vs API)
- Provider configuration via
~/.config/arbor/config.toml[[providers]]sections - Session persistence across daemon restarts
- Token usage tracking and display
AI Agent Visibility
- Detects running coding agents: Claude Code, Codex, OpenCode
- Working/waiting state indicators with color-coded dots
- Real-time updates over WebSocket streaming in both the desktop and web UI
- Legacy session compatibility and targeted clear events for long-lived daemon sessions
Remote Daemon and Companion Binaries
arbor-httpdserves the remote daemon API and bundled web UIarbor-cliexposes daemon-backed health, repo, worktree, terminal, process, and task commands- Dedicated
arbor-mcpbinary backed by Arbor's daemon API - Structured MCP tools for repositories, worktrees, terminals, processes, tasks, and agent activity
- MCP resources for daemon snapshots and prompts for common Arbor workflows
- Supports
ARBOR_DAEMON_URLandARBOR_DAEMON_AUTH_TOKENfor remote authenticated daemons - Create and manage remote worktrees over SSH
- Multi-host configuration with custom ports and identity files
- Mosh support for better connectivity
- Remote terminal sessions via
arbor-httpd - Outpost status tracking (available, unreachable, provisioning)
- Optional Symphony runtime endpoints when the feature is enabled
UI and Config
- Automatic PR detection and linking per worktree
- Git actions in the UI: commit, push
- Three-pane layout across
arbor-guiandarbor-web-ui - Command palette coverage for actions, repos, worktrees, issues, presets, and task templates
- Resizable panes, collapsible sidebar, desktop notifications
- 38 themes shared between the desktop app and web UI, with live sync when switching themes
- Branch-aware window titles and daemon / rate-limit status polish
- TOML config at
~/.config/arbor/config.tomlwith hot reload
Install
Homebrew (macOS)
brew install penso/arbor/arbor
Prebuilt Binaries
Download the latest build from Releases.
Release bundles ship the desktop app plus arbor-httpd, arbor-mcp, and arbor-cli.
Quick Start from Source
git clone https://github.com/penso/arbor
cd arbor
just run
To run the MCP server against a local dev daemon:
just run-mcp
Documentation
The live docs site is available at penso.github.io/arbor/docs.
The in-repo mdBook sources live under docs/src, and you can build them locally with:
just docs-build
Crates
| Crate | Description |
|-------|-------------|
| arbor-benchmarks | CodSpeed and local benchmark targets |
| arbor-cli | CLI for Arbor's daemon API (arbor-cli binary) |
| arbor-daemon-client | Typed client and shared API DTOs for arbor-httpd |
| arbor-core | Worktree primitives, change detection, agent hooks |
| arbor-gui | GPUI desktop app (arbor binary) |
| arbor-httpd | Remote HTTP daemon (arbor-httpd binary) |
| arbor-mcp | MCP server exposing Arbor via stdio (arbor-mcp binary) |
| arbor-mosh | Mosh transport for remote outposts |
| arbor-ssh | SSH transport for remote outposts |
| arbor-symphony | Optional workflow orchestration runtime |
| arbor-terminal-emulator | Embedded terminal engine glue and Ghostty integration |
| arbor-web-ui | TypeScript dashboard assets + helper crate |
Repo Config
Repo-local behavior is configured with <repo>/arbor.toml.
Arbor currently reads repo presets, managed processes, worktree scripts, scheduled tasks, branch naming rules, agent defaults, and notification routing from that file.
Example:
[[presets]]
name = "Review"
icon = "R"
command = "codex --prompt-file .arbor/tasks/review.md"
[[processes]]
name = "web"
command = "npm run dev"
working_dir = "app"
auto_start = true
auto_restart = true
restart_delay_ms = 2000
[scripts]
setup = ["cp .env.example .env"]
teardown = ["rm -f .env"]
[branch]
prefix_mode = "github-user"
[agent]
default_preset = "codex"
auto_checkpoint = true
[notifications]
desktop = true
events = ["agent_started", "agent_finished", "agent_error"]
webhook_urls = ["https://example.com/hook"]
[[tasks]]
name = "triage-prs"
schedule = "0 */30 * * * * *"
command = "./scripts/triage-prs"
enabled = true
[tasks.trigger]
on_exit_code = 0
on_stdout = true
agent = "codex"
prompt_template = "Review this output and prepare a follow-up plan:\n\n{stdout}"
Task templates for the command palette default to <repo>/.arbor/tasks/*.md.
CLI
Arbor also ships arbor-cli for daemon-backed scripting:
cargo run -p arbor-cli -- health
cargo run -p arbor-cli -- worktrees list --json
cargo run -p arbor-cli -- processes list --json
cargo run -p arbor-cli -- tasks list --json
MCP
Arbor ships a dedicated arbor-mcp binary from the arbor-mcp crate. The stdio server is enabled by the crate's default stdio-server feature and talks to arbor-httpd, so the daemon must be reachable first.
Enable it in a normal build:
cargo build -p arbor-mcp
Environment variables:
ARBOR_DAEMON_URLoverrides the daemon base URL. Default:http://127.0.0.1:8787ARBOR_DAEMON_AUTH_TOKENsends a bearer token for remote authenticated daemons
Remote access:
- On the daemon host, set
[daemon] auth_token = "your-secret"in~/.config/arbor/config.toml. - Start
arbor-httpd. When an auth token is configured, Arbor binds remotely by default on0.0.0.0:8787unlessARBOR_HTTPD_BINDoverrides it. - Point
arbor-mcpat that daemon withARBOR_DAEMON_URL=http://HOST:8787. - Pass the same secret with
ARBOR_DAEMON_AUTH_TOKEN=your-secret.
Loopback requests are allowed without a token. Non-loopback requests require Authorization: Bearer <token>.
Example client config:
{
"mcpServers": {
"arbor": {
"command": "/path/to/arbor-mcp",
"env": {
"ARBOR_DAEMON_URL": "http://127.0.0.1:8787"
}
}
}
}
The arbor-mcp binary is feature-gated. To disable the stdio server binary in a build, use:
cargo build -p arbor-mcp --no-default-features
See docs/mcp.md for the full MCP setup guide.
Building from Source
Prerequisites
- Rust nightly — the project uses
nightly-2025-11-30(install via [rustup](https://ru
