by ogulcancelik
agent multiplexer that lives in your terminal.
# Add to your Claude Code skills
git clone https://github.com/ogulcancelik/herdrLast scanned: 5/10/2026
{
"issues": [],
"status": "PASSED",
"scannedAt": "2026-05-10T06:33:05.628Z",
"semgrepRan": false,
"npmAuditRan": true,
"pipAuditRan": true
}herdr is an open-source ai agents skill for AI coding assistants such as Claude Code, Codex CLI, and ChatGPT, built by ogulcancelik. agent multiplexer that lives in your terminal. It has 12,301 GitHub stars.
Yes. herdr passed SkillsLLM's automated security scan — a dependency vulnerability audit plus prompt-injection heuristics — with no high-severity issues. You can read the full report in the Security Report section on this page.
Clone the repository with "git clone https://github.com/ogulcancelik/herdr" and add it to your Claude Code skills directory (see the Installation section above). herdr ships a SKILL.md manifest, so compatible agents can discover and load it automatically.
herdr is primarily written in Rust. It is open-source under ogulcancelik on GitHub, so you can review or fork the full source.
Yes. SkillsLLM lists many other AI Agents skills you can browse and compare side by side. Open the AI Agents category from the badge at the top of this page, or use the Related Skills and comparison links further down to weigh herdr against similar tools.
No comments yet. Be the first to share your thoughts!
before using this skill, check that HERDR_ENV=1. if it is not set to 1, say you are not running inside a herdr-managed pane and stop. do not inspect or control the focused herdr pane from outside herdr.
you are running inside herdr, a terminal-native agent multiplexer. herdr gives you workspaces, tabs, and panes — each pane is a real terminal with its own shell, agent, server, or log stream — and you can control all of it from the cli.
this means you can:
the herdr binary is available in your PATH. its workspace, tab, pane, and wait commands talk to the running herdr instance over a local unix socket.
if you need the raw protocol or full api reference, read the socket api docs.
workspaces are project contexts. each workspace has one or more tabs. unless manually renamed, a workspace's label follows the first tab's root pane — usually the repo name, otherwise the root pane's current folder name.
tabs are subcontexts inside a workspace. each tab has one or more panes.
panes are terminal splits inside a tab. each pane runs its own process — a shell, an agent, a server, anything.
agent status is detected automatically by herdr. the api exposes one public field for it:
agent_status — idle, working, blocked, done, unknowndone means the agent finished, but you have not looked at that finished pane yet.
plain shells still exist as panes, but herdr's sidebar agent section intentionally focuses on detected agents rather than listing every shell.
ids — workspace ids look like 1, 2. tab ids look like 1:1, 1:2, 2:1. pane ids look like 1-1, 1-2, 2-1. these are compact public ids for the current live session.
important: ids can compact when tabs, panes, or workspaces are closed. do not treat them as durable ids. re-read ids from workspace list, tab list, pane list, or create/split responses when you need a current id. do not guess that an older 1-3 is still the same pane later.
see what panes exist and which one is focused:
herdr pane list
the focused pane is yours. other panes are your neighbors.
list workspaces:
herdr workspace list
list tabs in the current workspace:
herdr tab list --workspace 1
create a new tab:
herdr tab create --workspace 1
without --label, the new tab keeps the default numbered tab name.
create and name it in one step:
herdr tab create --workspace 1 --label "logs"
rename it:
herdr tab rename 1:2 "logs"
focus it:
herdr tab focus 1:2
close it:
herdr tab close 1:2
see what is on another pane's screen:
herdr pane read 1-1 --source recent --lines 50
--source visible = current viewport--source recent = recent scrollback as rendered in the pane--source recent-unwrapped = recent terminal text with soft wraps joined back togethersplit your pane to the right and keep focus on your current pane:
herdr pane split 1-2 --direction right --no-focus
that prints json with the new pane nested at result.pane.pane_id. parse that value, then run a command in that pane:
NEW_PANE=$(herdr pane split 1-2 --direction right --no-focus | python3 -c 'import sys,json; print(json.load(sys.stdin)["result"]["pane"]["pane_id"])')
herdr pane run "$NEW_PANE" "npm run dev"
split downward instead:
herdr pane split 1-2 --direction down --no-focus
block until specific text appears in a pane. useful for waiting on servers, builds, and tests.
for --source recent, matching uses unwrapped recent terminal text, so pane width and soft wrapping do not break matches. pane read --source recent still shows the pane as rendered. if you want to inspect the same transcript that the waiter matches, use pane read --source recent-unwrapped.
herdr wait output 1-3 --match "ready on port 3000" --timeout 30000
with regex:
herdr wait output 1-3 --match "server.*ready" --regex --timeout 30000
if it times out, exit code is 1.
block until another agent reaches a specific status:
herdr wait agent-status 1-1 --status done --timeout 60000
use this when you want the same done / idle distinction the UI shows.
send text without pressing Enter:
herdr pane send-text 1-1 "hello from claude"
press Enter or other keys:
herdr pane send-keys 1-1 Enter
pane run sends the text and then a real Enter key in one request:
herdr pane run 1-1 "echo hello"
create a new workspace:
herdr workspace create --cwd /path/to/project
without --label, the new workspace keeps the default cwd-based name.
create and name one in one step:
herdr workspace create --cwd /path/to/project --label "api server"
create one without focusing it:
herdr workspace create --no-focus
focus a workspace:
herdr workspace focus 2
rename:
herdr workspace rename 1 "api server"
close:
herdr workspace close 2
herdr pane close 1-3
NEW_PANE=$(herdr pane split 1-2 --direction right --no-focus | python3 -c 'import sys,json; print(json.load(sys.stdin)["result"]["pane"]["pane_id"])')
herdr pane run "$NEW_PANE" "npm run dev"
herdr wait output "$NEW_PANE" --match "ready" --timeout 30000
herdr pane read "$NEW_PANE" --source recent --lines 20
herdr pane split 1-2 --direction down --no-focus
herdr pane run 1-3 "cargo test"
herdr wait output 1-3 --match "test result" --timeout 60000
herdr pane read 1-3 --source recent --lines 30
herdr pane list
herdr pane read 1-1 --source recent --lines 80
use this pattern when you need to coordinate with a sibling pane:
# inspect what is already there
herdr pane read 1-3 --source recent --lines 40
# wait only for the next output you expect
herdr wait output 1-3 --match "ready" --timeout 30000
# if you need to inspect the same transcript the waiter matched,
# read the unwrapped recent text directly
herdr pane read 1-3 --source recent-unwrapped --lines 40
herdr pane split 1-2 --direction right --no-focus
herdr pane run 1-3 "claude"
herdr wait output 1-3 --match ">" --timeout 15000
herdr pane run 1-3 "review the test coverage in src/api/"
herdr wait agent-status 1-1 --status done --timeout 120000
herdr pane read 1-1 --source recent --lines 100
workspace list, workspace create, tab list, tab create, tab get, tab focus, tab rename, tab close, pane list, pane get, pane split, wait output, and wait agent-status print json on success.pane read prints text, not json.pane read --format ansi or pane read --ansi returns a rendered ANSI snapshot for TUI feedback loops.pane read --source recent-unwrapped is useful when you want to inspect the same unwrapped transcript that wait output --source recent matches against.pane send-text, pane send-keys, and pane run print nothing on success.workspace create, tab create, and pane split responses when you need new ids. workspace create returns result.workspace, result.tab, and result.root_pane. tab create returns result.tab and result.root_pane. for pane split, the new pane id is at result.pane.pane_id.pane read for current output that already exists. use wait output for future output you expect next.--no-focus on split, tab create, and workspace create keeps your current terminal context focused.--label, workspace create keeps cwd-based naming and tab create keeps numbered naming.--label on tab create and workspace create applies the custom name immediately.HERDR_ENV environment variable is set to 1.https://github.com/user-attachments/assets/043ec09f-4bdd-41d5-aee0-8fda6b83e267
run all your coding agents in one terminal. see who's blocked, working, or done at a glance.
run your agents where they already run; your machine, a server, anywhere you can ssh. each one gets its own real terminal, not an app's imitation of one, so even full-screen TUIs render right. click, drag, and split panes into workspaces and tabs, and watch each agent go blocked, working, done. close the laptop and nothing dies; reattach from another terminal, or from your phone over ssh. one local rust binary, not an app: no gui, no electron, no mac-only wrapper, no account, no telemetry. (if you've used tmux: it's that, rebuilt for agents.)
| tmux | gui managers | herdr | |
|---|---|---|---|
| persistent sessions | ✓ | — | ✓ |
| detach / reattach | ✓ | — | ✓ |
| runs anywhere, over ssh | ✓ | — | ✓ |
| panes, tabs, workspaces | ✓ | ✓ | ✓ |
| agent awareness | — | ✓ | ✓ |
| lives in your terminal | ✓ | — | ✓ |
| real terminal views | ✓ | — | ✓ |
| mouse-native | — | ✓ | ✓ |
| lightweight binary | ✓ | — | ✓ |
| agents can orchestrate | ? | ? | ✓ |
tmux gives you persistence and panes, but it was built before agents existed. it has no idea which pane is blocked, working, or done; you can bolt a bell character and per-harness hooks onto it, but you wire each one yourself and still have no shared view of the fleet. the gui agent managers (conductor, cmux, emdash) do show agent state, so call that table stakes. the difference is everything around it. they are apps, often mac-only and closed, that redraw the terminal inside a wrapper. herdr is a single binary that runs in the terminal you already use, anywhere you can ssh, and shows each agent's real screen on a server that keeps it alive when you disconnect. see the full comparison with tmux, zellij, cmux, warp, conductor, and more.
curl -fsSL https://herdr.dev/install.sh | sh
windows preview beta:
powershell -ExecutionPolicy Bypass -c "irm https://herdr.dev/install.ps1 | iex"
also available with brew install herdr, mise use -g herdr, nix run github:ogulcancelik/herdr, or as a stable Linux/macOS binary from releases.
herdr update upgrades an installer-managed install; Homebrew, mise, and Nix update through their own package managers. channel, preview, restart, and restore details are in the install docs.
herdr
herdr starts or attaches to a background server and opens a workspace. run an agent in the pane.
herdr is mouse-native, so clicking and dragging panes, tabs, and split borders gets you everywhere without a single keybinding. for the keyboard, ctrl+b is the prefix: press it, release, then press the action key, so ctrl+b then c makes a tab. one reserved key keeps herdr out of your shell's way.
ctrl+b then shift+n for a new workspacectrl+b then v or minus to split panesctrl+b then c for a new tabctrl+b then w to switch workspacesctrl+b then q to detach; agents keep running, run herdr again to reattachpress ctrl+b then ? for every binding. the keyboard guide explains the prefix model and how to go prefix-free; the full keymap, copy mode, and config syntax live in the configuration docs.
run herdr on a VPS and reach it from your local terminal. herdr --remote makes your local terminal the client of the remote server, so pasting images into your agents keeps working, the thing plain ssh + tmux breaks.
herdr --remote workbox
herdr --remote ssh://you@yourserver:2222
see the persistence and remote docs for named sessions, keepalives, direct attach, and handoff.
detection works out of the box with process-name matching plus terminal-output heuristics.
| agent | idle / done | working | blocked |
|---|---|---|---|
| pi | ✓ | ✓ | partial |
| claude code | ✓ | ✓ | ✓ |
| codex | ✓ | ✓ | ✓ |
| droid | ✓ | ✓ | ✓ |
| amp | ✓ | ✓ | ✓ |
| opencode | ✓ | ✓ | ✓ |
| grok cli | ✓ | ✓ | ✓ |
| hermes agent | ✓ | ✓ | ✓ |
| kilo code cli | ✓ | ✓ | ✓ |
| devin cli | ✓ | ✓ | ✓ |
| cursor agent | ✓ | ✓ | ✓ |
| antigravity cli | ✓ | ✓ | ✓ |
| kimi code cli | ✓ | ✓ | ✓ |
| github copilot cli | ✓ | ✓ | ✓ |
| qodercli | ✓ | ✓ | ✓ |
| kiro cli | ✓ | ✓ | — |
detected but not fully tested: gemini cli, cline. any other agent still works; herdr runs it as a terminal multiplexer, and custom integrations can report labels and state over the socket api.
official integrations add native session restore, and some report semantic state directly. install one with herdr integration install <agent>, available for pi, omp, claude, codex, copilot, devin, droid, kimi, opencode, kilo, hermes, qodercli, and cursor. see the integrations docs.
the local Unix socket lets agents create workspaces, split or zoom panes, spawn helpers, read output, and subscribe to state changes instead of polling. install the reusable skill with:
npx skills add ogulcancelik/herdr --skill herdr -g
start with the agent skill docs, socket API docs, and SKILL.md.
SKILL.md: reusable agent skillif you are an ai agent helping with this repository, read AGENTS.md before making changes and read CONTRIBUTING.md before opening issues or PRs.
git clone https://github.com/ogulcancelik/herdr
cd herdr
cargo build --release
./target/release/herdr
just test # unit tests
just check # formatting, tests, and maintenance checks
herdr is built full-time, in the open, with no revenue behind it. sponsoring directly funds development, stability, and the path to a real agent runtime.
→ become a sponsor · enterprise / partnership: hey@herdr.dev · see SPONSORS.md for tiers. thank you 🐑
Herdr is dual-licensed:
Contact: hey@herdr.dev