GitHub - nikhilshinday/workforest

2 min read Original article ↗

workforest

A Rust terminal UI inspired by the layout of conductor.build, wired to real git repositories and worktrees.

Install

Prereqs:

  • Rust (stable) + Cargo
  • git
  • Optional: gitui (for the Diff panel hotkey d)

Install from GitHub (recommended)

cargo install --git https://github.com/nikhilshinday/workforest --locked --bin workforest
workforest

Install from a local checkout

git clone https://github.com/nikhilshinday/workforest
cd workforest
cargo install --path . --locked --bin workforest
workforest

Run (dev)

Self-test (non-interactive)

macOS app bundle (opens Terminal.app)

This is still a terminal UI, but you can build a clickable .app that opens Terminal.app and runs workforest.

./scripts/build-macos-app.sh
open dist/Workforest.app

Usage

  • A to add a repo (mount / clone / init)
  • a on a repo to create a new worktree (city-named, next to the repo under <repo>-worktrees/<city>)

Keys

  • F6: cycle focus (Sidebar / Terminal / Diff)
  • Tab / Shift+Tab: cycle focus (outside Terminal)
  • Sidebar: / or j/k, Enter selects worktree, Space toggles repo, a adds worktree (on repo), x unmount/remove, X delete repo, R refresh
  • Sidebar: n rename a worktree based on current diff (picks a city, renames branch + moves dir)
  • Terminal: F2 new terminal, F3 close, F7/F8 prev/next (other keys go to the shell)
  • Terminal: F4 rename current terminal
  • Terminal: Shift+PageUp/PageDown scrollback, Shift+End back to live
  • Diff: d open gitui, r refresh
  • Panels: F9 / F10 collapse sidebar / diff, Ctrl+F9/F10 widen, Shift+F9/F10 narrow
  • Mouse: click sidebar rows/tabs, wheel scroll (terminal scrollback), drag dividers to resize
  • F1 help, Ctrl+Q quit (q/Esc also quit outside Terminal)

Harness notifications (Codex + Claude)

Workforest marks a terminal tab with when the terminal emits a bell (BEL, \a). You can configure Codex TUI and Claude Code to emit a bell when they finish a turn or need attention.

Auto-configure (user-scoped)

Options:

  • --dry-run prints changes without writing
  • --print prints minimal snippets only
  • --codex / --claude configure just one

Manual snippets

Codex (~/.codex/config.toml):

[tui]
notifications = ["agent-turn-complete", "approval-requested"]
notification_method = "bel"

Claude Code (~/.claude/settings.json):

{
  "hooks": {
    "Stop": [{ "matcher": "*", "hooks": [{ "type": "command", "command": "printf '\\a'" }] }],
    "PermissionRequest": [{ "matcher": "*", "hooks": [{ "type": "command", "command": "printf '\\a'" }] }],
    "Notification": [{ "matcher": "permission_prompt|elicitation_dialog", "hooks": [{ "type": "command", "command": "printf '\\a'" }] }]
  }
}