βββββββ βββββββ βββ ββββββββββββββββββββββββββββ ββββββ βββββββ ββββββββββββββββββββ βββββββββββββββββββββββββββββββββββββββββββββ βββ ββββββββββββββββββ ββββββ ββββββββ βββ ββββββββββββββββ βββ ββββββββββββββββββ ββββββ ββββββββ βββ ββββββββββββββββ ββββββββββββ ββββββ βββββββββββββββββββ βββ βββ ββββββ βββ βββββββ βββ ββββββ βββββββββββββββββββ βββ βββ ββββββ βββ
Orkestar is unstable and under active development. Use at your own risk.
Run your coding agents from one terminal, and keep them running when you close it.
Orkestar is a background daemon that owns your agent sessions, and a terminal UI that attaches to it. Because the daemon owns the processes, closing the UI, dropping a connection or restarting your editor does not stop the work. Reopen it and you are back exactly where you were.
No account, no server, no browser. One static binary.
- Work survives the UI. A daemon owns every pseudoterminal, screen and agent process. Clients are disposable and any number can watch the same session.
- Nested split panes. Tile shells, agents, diffs and editors up to sixteen panes, with drag-resizable dividers, a zoom toggle and per-pane input.
- A live file viewer. A tree of the workspace on the right edge that follows files as agents create and delete them.
- Review and edit in place. A pull-request style diff pane, and an editor with syntax highlighting for around three hundred languages.
- Real agent integration. Lifecycle events, native permission prompts answered from the sidebar, and explicit session resume, through each CLI's own hook or plugin mechanism and without touching your global config.
- Tasks with worktrees. Units of work with dependencies, an assignee, their own Git worktree and an optional reviewer-agent gate before they can close.
- Durable state. SQLite keeps workspaces, tasks, artifacts and session metadata across daemon restarts.
On macOS or Linux:
curl -fsSL https://raw.githubusercontent.com/LibreCollab/orkestar/main/install.sh | shThe installer verifies the release checksum before unpacking anything, installs
to /usr/local/bin when that is writable and ~/.local/bin otherwise, and
tells you if that directory is not on your PATH rather than editing your
shell profile. Set ORKESTAR_INSTALL_DIR to choose somewhere else.
With Homebrew:
brew install librecollab/tap/orkestarIf you installed from the older martintrifunov/tap, brew update moves you to
librecollab/tap. Run brew trust --formula librecollab/tap/orkestar once so
Homebrew will load the formula by its short name for brew upgrade.
With mise, which reads the same GitHub releases:
mise use -g ubi:LibreCollab/orkestarInstall the latest x64 or ARM64 release from PowerShell, on Windows 10 1809+ or Windows 11:
irm https://raw.githubusercontent.com/LibreCollab/orkestar/main/install.ps1 | iexThe installer verifies the release checksum, places orkestar.exe in
%LOCALAPPDATA%\Programs\orkestar, and adds that directory to your user PATH.
Run the same command again to upgrade, once any running daemon can be stopped.
Use Windows Terminal; shell panes prefer PowerShell 7, falling back to Windows
PowerShell.
Agent CLIs must be installed separately. Claude Code, Codex and OpenCode are supported with full lifecycle awareness; Cursor and Grok run in a pane but do not yet report when they are waiting for you, because neither CLI's hook contract has been verified. See validation.
Build from source with Go 1.27 or newer on macOS, Linux or Windows:
git clone https://github.com/LibreCollab/orkestar
cd orkestar
go build -o ./orkestar ./cmd/orkestarOn Windows, use ./build.ps1 to build or ./build.ps1 -Task Install to install.
Check the build with orkestar --version.
Install the agent CLIs you want to drive: claude, codex or opencode.
Orkestar works without them, as a persistent terminal multiplexer.
Run it from the project you want to work in:
./orkestarIt starts a daemon if one is not already running. Press a to launch an agent
or n for a shell. Press q to leave; the agent keeps working. Start Orkestar
again and press Enter on the session to reattach.
The UI needs a terminal of at least 50 Γ 16 cells.
A sidebar on the left lists workspaces, sessions, tasks, agents and pending permission requests. The rest of the window is a tree of panes. An optional file viewer mirrors the sidebar on the right.
| Key | Action |
|---|---|
a / n |
Launch an agent / open a shell |
Tab |
Next section |
β β |
Move the selection |
Enter |
Open the selected session or agent |
f |
Show or hide the file viewer |
u |
Resume an inactive agent |
i |
Interrupt an agent's current turn |
E |
Explain why an agent is in its state |
X |
Stop what is selected, or clear it once finished |
y / x |
Allow or deny a pending permission request |
r |
Refresh |
q |
Quit the UI |
Stopping something still running asks for a second X, because it ends work the
daemon is holding for you. Clearing a finished entry is immediate.
Press and release Ctrl+b, then the action key. Each action needs its own
prefix, so ordinary letters still reach the agent you are typing to.
| Key | Action |
|---|---|
v / s |
Split: new shell beside / below the focused pane |
o or F6 |
Focus the next pane |
z |
Zoom the focused pane to fill the area, and back |
p |
Swap the focused pane with the next |
m |
Move the focused pane beside a neighbour: then an arrow |
l |
Portable layouts: save, apply, delete |
| arrows | Move the enclosing split's divider, repeatable |
d / e |
Review changes / open a file |
f |
Show or hide the file viewer |
[ |
Scrollback, 2,000 lines |
, |
Editor settings |
t |
Claim input after another client disconnected |
q / x |
Close the pane / discard an unsaved editor |
The arrows repeat: the prefix stays armed so a divider can be moved with
several presses, until Esc or any other key. Opening a file from the viewer
puts the editor below the focused pane, at full width.
Splits nest: Ctrl+b s then Ctrl+b v gives three panes, not a rearranged two.
Panes are labelled in their border, dividers can be dragged, and closing a pane
leaves its process running. Click any pane to focus it. When the window is too
small for every split, the focused pane fills the space and F6 still cycles
the hidden ones.
Shift+Enter is forwarded as a modified Enter; plain Enter submits. Your outer
terminal must distinguish those keys (Kitty keyboard protocol or CSI-u). If it
sends both as carriage return, configure Shift+Enter to send ESC [ 13 ; 2 u, or
use the agent's alternate newline binding such as Alt+Enter or Ctrl+j.
Orkestar cannot recover a modifier the outer terminal did not send.
Select the Tasks section with Tab, then c creates one.
| Key | Action |
|---|---|
c |
Create a task |
d |
Its diff and the latest reviewer verdict |
m / x |
Mark it done / cancel it |
w |
Create or remove its Git worktree |
t |
Assign it to the highlighted agent |
T |
Apply a workflow template |
A task carries a status, optional dependencies, an assignee and its own Git
worktree, so an agent can change files without disturbing your checkout. Tasks
are created with automatic review on: the daemon runs a reviewer agent and
requires approval before the task can close. Press Ctrl+R in the create prompt
to opt out, and Ctrl+D to pick the tasks this one waits on.
Ctrl+b , then m manages saved SSH machines: add a profile, enable or
disable one, or remove it. Every enabled machine's agents appear in one
sidebar with a machine column, and a remote agent's row is driven in place β
interrupt, stop, resume, explain, or Enter to move there and open its pane.
orkestar --remote user@host attaches a single machine without saving a
profile. Nothing listens on a network and no credential is stored; the
transport and authentication are ssh.
Ctrl+b d opens a pull-request style review of the workspace or task worktree,
with changed-file selection, colored hunks and old and new line numbers.
Ctrl+b e finds or creates a file.
The built-in editor handles UTF-8 files up to 1 MiB with mouse selection, undo and redo, search, clipboard access and conflict-checked saves that never overwrite a change an agent made underneath you. It highlights around three hundred languages in Orkestar's own palette, lexing in the background so typing never waits. Vim, Nano and custom editor commands run as real daemon-owned terminals instead.
Ctrl+b f shows a file tree of the workspace on the right edge. It is hidden by
default and reads nothing until opened. While open it follows the workspace, so
files an agent writes appear on their own.
Settings live in orkestar/tui.json inside your OS configuration directory, or
at ORKESTAR_TUI_CONFIG. The settings panel (Ctrl+b, comma) shows the path.
{
"editor": "custom",
"command": ["nvim", "-c", "set mouse=a"],
"max_panes": 16,
"syntax": true,
"sidebar": {
"task": "{status} {title}",
"agent": "{adapter} {state} on {task} [{machine}]",
"session": "{state} {command}"
}
}Sidebar rows are templates with {token} placeholders. Tasks have
status, title, id, branch, worktree, assignee, depends and
review; agents have adapter, state, machine, task, id, attention
and terminal; sessions have state, command, id and directory. An
unknown token is reported when the interface starts.
ORKESTAR_RUNTIME_DIR relocates the daemon socket and database.
The daemon is the authority for state and process ownership. It holds each pseudoterminal, one terminal screen per session with bounded scrollback, and the agent adapters. Clients speak a versioned local protocol over a Unix socket (Windows: a private named pipe) and render frames the daemon sends them; they never own a managed process. Several clients can watch one session, but only one holds input at a time.
Claude Code, Codex and OpenCode launch interactively through a pseudoterminal. OpenCode also has a managed HTTP mode used by the reviewer workflow. Lifecycle signals and permission prompts arrive through invocation-local hooks or a plugin, so no global agent configuration is edited and no native trust or approval decision is bypassed. Codex may ask you to review Orkestar's five command hooks the first time you launch it; declining leaves the terminal fully working, with less lifecycle detail.
Metadata is written to SQLite after each mutation. A write that fails leaves
the change live in memory, keeps retrying in the background, and makes
orkestar status say metadata is not durable until it succeeds. An agent that
stays in one working state without a lifecycle change past
ORKESTAR_AGENT_WATCHDOG (30 minutes by default, 0 disables) is flagged in
the sidebar, the way a crash is.
For the boundaries and the reasoning behind them, see the architecture and the decision records.
orkestar --version show application version
orkestar start the UI
orkestar status show daemon state
orkestar reset [--yes] clear all daemon state
orkestar daemon serve | stop
orkestar workspace create [directory]
orkestar terminal start <workspace-id> -- <cmd> run a command in a PTY
orkestar terminal attach | stop | remove <terminal-id>
orkestar agent list | launch <workspace-id> <adapter>
orkestar agent resume | stop | remove | interrupt <agent-id>
orkestar task create | list | status | assign | worktree | diff
orkestar mcp serve orchestration MCP server
orkestar reset clears everything the daemon holds: every session and agent,
stopped or running, along with tasks, artifacts, workspaces and leases. It is
the way to empty a sidebar that has filled up with finished sessions, which
daemon stop does not do, because that ends the processes but keeps the records
so they can be resumed.
It previews by default and changes nothing until you pass --yes:
$ orkestar reset
A reset stops and clears everything the daemon is holding:
sessions 3 (2 still running)
agents 1 (1 still running)
tasks 1
...
Nothing has changed. Run 'orkestar reset --yes' to go ahead.Nothing on disk is deleted. Task worktrees are left where they are and listed
so you can remove any you no longer want with git worktree remove. The new daemon loads its registered
agent adapters as configuration. To clear
a single session instead, use orkestar terminal remove or press X in the
sidebar.
orkestar reset --yes handles shutdown itself: it waits for the running daemon
and its final metadata write to finish, starts the current binary to clear the
saved records, then stops that daemon too. This also works with older daemons
that do not implement system.reset. The next launch starts a fresh daemon.
Previewing with orkestar reset never stops a running daemon.
Rebuilding alone does not replace a running daemon. A confirmed reset now does that as part of clearing its state. Metadata survives a restart; terminal screens and scrollback are held in memory and do not.
go test ./...
go vet ./...
go test -race ./...Every push and pull request runs the same checks on macOS and Linux, after a formatting check, plus a cross-build of every supported target. The suite needs no network and no installed agent CLIs: it starts real daemons on temporary sockets and drives real pseudoterminals with fixture commands.
Two scripts exercise installed CLIs against an isolated temporary daemon, never
your running one. scripts/smoke-agents.py checks each one starts and
reattaches without submitting a prompt. scripts/live-agents.py drives an
authenticated CLI through a real turn, permission allow and deny, interrupt and
resume; it spends tokens, so run it deliberately.
docs/validation.md records what has actually been
exercised.
- Architecture
- Panes and editing
- Validation
- Releases
- Roadmap
- Decision records
- Agent guide, for contributors and coding agents
The daemon, protocol, pseudoterminal ownership, persistence, panes, review, editing, tasks and the three agent adapters are implemented and tested. Authenticated live model turns across every installed CLI, and the MCP client registry that game-engine work depends on, are the next milestones. The roadmap tracks what is done and what is not.
Released under the MIT License.