Skip to content
~/case-studies/agentbar

AgentBar

One menu bar item for all your AI coding agents — live status plus remote Allow/Deny, built on nothing but files.

Solo — concept, Swift/AppKit, hook protocol, design2026Open source (MIT) · v1.4.0
SwiftAppKitmacOSNode.js hooksClaude Code hooksCodex notifyHomebrew

AgentBar is a lightweight, native macOS menu bar app that shows the live state of your AI coding sessions — Claude Code with full fidelity today, Codex, GitHub Copilot and Google Antigravity in the same bar. Each agent gets its own animated mascot (Clawd the crab walks the bar while Claude works), and the bar always surfaces the session that needs you most.

The headline feature is remote Allow/Deny: when Claude Code asks for permission, the exact request appears right in the menu — allow once, always allow, or deny, without switching to the terminal. Underneath, the architecture is deliberately boring: tiny hook scripts write one JSON file per session, the app watches a folder and renders. No sockets, no daemons, no network.

4
AI agents in one menu bar item
0
sockets, daemons, network calls — just files
1 line
to install — curl or Homebrew
10 min
before an unanswered prompt falls back to the terminal

the problem

Running coding agents in parallel has a characteristic failure mode, and it isn't the agent getting something wrong — it's the agent silently waiting. A session in a background terminal hits a permission prompt and blocks. You find out twenty minutes later, when you switch tabs and realize nothing has happened since the last time you looked. Multiply that by three or four concurrent sessions across different agents, and babysitting terminals becomes the actual job.

The existing answers don't scale: per-agent notifier apps (one more menu bar item each), notification spam you learn to ignore, or just alt-tabbing on a timer. What I wanted was one glanceable spot that always shows the session that needs me most — and, for the most common interruption of all, the permission prompt, the ability to answer right there without leaving whatever I was doing.

how it works

The whole system is files. Tiny Node.js hook scripts write one JSON file per session to ~/.agentbar/state.d/; the app watches that folder and renders. Claude Code reports with full fidelity (prompt, tool use, permission, stop, session lifecycle), Codex reports turn-complete via its notify hook. Copilot and Antigravity have no public event API yet — they're launchable from the menu and their mascots are ready for the day one appears.

Permission approvals are two more folders of the same protocol: the blocking PermissionRequest hook writes the request into requests.d/, the app writes the decision into answers.d/, the hook unblocks. When the bar shows more than it can say, priority decides: permission outranks working, working outranks idle. Every live session gets a menu row with project name, git branch and state — click it to jump to its app or terminal.

$the-protocol
claude hooks ──┐  one JSON per session
codex notify ──┴─▶ ~/.agentbar/state.d/  ──watch──▶ menu bar
permission ask ──▶ requests.d/ ─▶ ✓ Allow / ✕ Deny ─▶ answers.d/
                   (no sockets, no daemons, no network — just files)

remote allow/deny

When a Claude Code session asks for permission, the request appears under the yellow needs approval row: exactly what's requested — e.g. Bash: git push origin main, full input in the tooltip — plus an inline button strip. ✓ Allow once, ✓ Always (only when Claude Code itself suggests a rule, shown as readable text like Bash(git push:*), never raw JSON), ✕ Deny, or hand the prompt back to the terminal or the Claude desktop app. Decisions return through Claude Code's own PermissionRequest hook, so the terminal prompt never even appears.

The design constraint that shaped all of it: the app must never become a hostage. If AgentBar isn't running, quits mid-wait, or you simply ignore the request for ten minutes, the prompt shows in the terminal exactly as it would have without AgentBar. Fail-open by construction — every failure mode was enumerated and each one ends at the ordinary terminal prompt. Codex and Copilot have no decision hooks, so their rows offer a clearly-labeled best effort instead: focus the session's terminal and press the approval key, gated behind macOS's Accessibility permission.

engineering decisions

AgentBar is a clean-room rewrite of an earlier single-agent notifier concept, rebuilt around one bet: the simplest possible transport wins. State is plain JSON files in watched folders — the whole protocol is debuggable with ls and cat, survives crashes on either side, and adding an agent means adding a script that writes a file.

  • A question is not an approval: when Claude asks something (AskUserQuestion — option pickers, plan questions), the session shows a blue dot with the question text instead of a false amber “needs approval”. Different urgency, different color.
  • Single writer per fact: v1.2.1 fixed sessions stuck on “needs approval” — a legacy notification hook could land late and overwrite fresh state with a stale flag. Permission state is now written by exactly one script; the racing hook was removed and old registrations are cleaned up on launch.
  • Idempotent install: first launch merges hook entries into ~/.claude/settings.json preserving whatever is already there, and touches ~/.codex/config.toml only if no notify line exists. Reinstalling is always safe.
  • Mascots as sprite frames rendered natively in AppKit — Clawd the crab for Claude, each agent with its own mark — plus a monochrome System mode that matches the menu bar, with rotating thinking verbs while an agent works.
  • Nothing else: no dock icon, no windows, no countdown timers, no sounds. One process, tiny footprint.

status & what's next

AgentBar is open source under MIT, at v1.4.0 — five releases shipped on day one, from the first multi-agent bar through remote Allow/Deny, the inline approval strip, a race fix and the question state. It installs with a one-line curl, a Homebrew cask, or by pasting the install command into your coding agent and letting it do the work. Hook mapping is documented as a spec — claude-code-states.md records which Claude Code events map to which states, including what's deliberately ignored and why.

Next levers: a notarized build (the app is ad-hoc signed today, so a manual download triggers Gatekeeper's warning), and live status for Copilot and Antigravity the moment either ships a public event API — the bar, the protocol and the mascots are already waiting.

$try-it-in-60-seconds
# one line — downloads the latest release, installs the hooks
curl -fsSL https://raw.githubusercontent.com/michalstrnadel/AgentBar/main/Scripts/install.sh | bash

# or via Homebrew
brew install --cask michalstrnadel/tap/agentbar

# then open a NEW Claude Code session and watch the bar