littleguys is a small, free, open-source Mac and Windows app for talking to your AI agents, WhatsApp-style: OpenClaw, Hermes, Claude Code, Codex and any ACP agent, on every machine, are contacts with their own chats, and a little guy in the menu bar (or taskbar) shows who needs you. See it in action at littleguys.dev, or watch the 51-second intro.
brew install herval/tap/littleguysOr grab the .dmg from Releases. It needs macOS 13 or later, runs on Apple silicon and Intel, and updates itself.
- Chats: a WhatsApp-style window where each agent is a contact (a "little guy"). The sidebar lists every guy as a card; clicking one opens their threads. It has streaming replies, tool-call chips, attachments, and approve/deny for commands.
- Menu bar: the menu-bar sprite shows what your guys are up to: idle, working, new replies, needs you, or offline.
- Popover: clicking the guy opens a dropdown listing every guy with a live status ring, a last-message preview and quick reply.
- Routines: cron jobs with friendly schedules, run-now and run history. Results land in a thread.
For OpenClaw it's a UX layer over your existing ~/.openclaw, not a separate install. New guys use the workspaces OpenClaw gives each agent, and the UI links to their folder. With no OpenClaw on the Mac yet, littleguys can install and set it up for you.
Each saved bot uses one of four adapters (src-tauri/src/runtime/), and each adapter declares what it can do so the UI hides the rest:
| Runtime | How littleguys talks to it | Guys | Routines | Approvals |
|---|---|---|---|---|
| OpenClaw | Gateway WebSocket protocol v4 | Agents | Native cron | ✓ |
| Hermes Agent | Local hermes serve backend (JSON-RPC over WebSocket), or a remote API server (API_SERVER_KEY) |
Profiles | Native cron | ✓ |
| ACP agents: Claude Code, Codex, Gemini CLI, Goose, OpenCode, ZeroClaw… | Agent Client Protocol over stdio, or WebSocket for goose serve and similar |
One per agent | Run by littleguys while it's open | ✓ |
| Claude Code | Every session on this Mac, terminal or background: claude agents, their transcripts, and hooks from the littleguys plugin. New threads and routine runs are background sessions (claude --bg) |
One | Run by littleguys while it's open | Background sessions |
Every adapter speaks the same OpenClaw-shaped calls and events, documented in runtime/mod.rs, so the rest of the app doesn't care what's behind a guy. ACP agents can be added in one click from the ACP registry. Bots without a scheduler get routines from runtime/scheduler.rs.
littleguys can be connected to several OpenClaw gateways at once, and every gateway's guys show up together:
- Default gateway: the one your OpenClaw config points at is always there. That's local (
gateway.mode: "local") or remote (gateway.remote.url). - Adding more: use Settings → Add gateway. It finds gateways on your tailnet (Tailscale peers answering
/health, typically via Tailscale Serve) and on your LAN (Bonjour_openclaw-gw._tcp). You can also type an address such asstudio.tailnet.ts.netor192.168.1.20:18789. - Storage: added gateways are saved in littleguys' own data dir (
~/Library/Application Support/ai.littleguys.app/gateways.json). Tokens are kept in a 0600 file next to it, and only for the first connection. After the gateway approves this Mac, littleguys uses its own device token. - Labels: with more than one gateway, guys are labeled with where they live ("Fox · studio"). The popover groups them by gateway, and a quiet banner flags any gateway that needs approval or a token.
- Local gateway: loopback connections are approved automatically.
- Remote gateway: littleguys shows the exact approval command. On the gateway host, run
openclaw devices approve <requestId>once. littleguys then stores the per-device token the gateway issues, so you won't need to approve it again. - Unreadable credential: if your config keeps the gateway token in OpenClaw's secret store, littleguys asks you to paste it once.
- No working gateway on this Mac: the Doctor screen detects why and fixes it:
- OpenClaw not installed → installs it with the official installer
- CLI older than your data →
openclaw update - Service stopped →
openclaw gateway install/start - Never set up → non-interactive
openclaw onboardwith the provider you pick
littleguys for iPhone pairs with this Mac and reaches every bot on it (OpenClaw, Hermes, Claude Code, ACP agents), so your guys come along without each one being reachable from the phone:
- Pairing: Settings → Phones → Pair mobile app shows a QR code. Scan it from the iPhone app's Pair with your Mac. The code works once, for 10 minutes; Copy link pastes it on the phone through Universal Clipboard.
- Where it works: on the same Wi-Fi as this Mac, or anywhere when both are on Tailscale. The phone finds the Mac again on its own (Bonjour
_littleguys._tcp, then the addresses from the code). - Notifications: replies, routines and approvals reach the phone as pushes through littleguys-relay, sealed so the relay can't read them, and not while the app is open on the phone.
- What a paired phone can do: everything littleguys can here: chat, OK commands, edit guys and routines. Remove a phone in Settings → Phones to cut it off at once.
- Security: each session is end-to-end encrypted (Noise IK) with keys that never leave the two devices. Nothing listens until a phone is paired or a code is showing; "Let paired phones connect" turns it off. The wire format is docs/BRIDGE-PROTOCOL.md.
Yes. littleguys speaks the Agent Client Protocol, so Codex, Gemini CLI, GitHub Copilot CLI and the other agents in the ACP registry are a click away (Goose, OpenCode and others that ship as a download, once they're installed), each a contact with its own chats. It starts the agent itself, in the folder you pick, or connects to an ACP server over WebSocket. It's listed on the protocol's clients page. More: littleguys.dev/acp.
Yes, since version 0.2. Add a bot → Claude Code installs a small littleguys plugin in Claude Code, and from then on every session on this Mac, in a terminal or in the background, is a thread you can follow live and reply to. A terminal session gets your reply with the next prompt you type there; its permission prompts stay in the terminal. Codex and other ACP agents are different: littleguys starts those itself, so a Codex session running in a terminal doesn't show up. More: littleguys.dev/claude-code.
littleguys. Every OpenClaw agent, on this Mac or on a gateway on another machine, is a contact you chat with, and the commands an agent wants to run come to you to allow once, always allow or deny. It lists the gateways it finds on your tailnet and LAN, or you type an address; each gateway approves this Mac once. It doesn't run agents itself: it's a front end for the OpenClaw you already run. For voice wake, the Canvas panel or usage and cost in the menu bar, use OpenClaw's own macOS app. More: littleguys.dev/openclaw.
Yes, littleguys. Each Hermes profile is a contact, and its sessions are threads, including the ones you started in the CLI or from a messaging app; you allow or deny the commands Hermes asks about. It connects to hermes serve on this Mac or to the Hermes API server on another machine. Hermes Desktop is the full workspace, with git review, a terminal, a file browser and voice. littleguys is the small chat app that also holds your OpenClaw, Claude Code and Codex agents. More: littleguys.dev/hermes.
No. littleguys works with Hermes Agent, Claude Code and any ACP agent without OpenClaw. If OpenClaw isn't on your Mac, the first screen offers to install it; skip that with Add a gateway, and pick Hermes, Claude Code or Agents (ACP).
Yes: several OpenClaw gateways at once, found on your tailnet and LAN, Hermes API servers, and ACP agents served over WebSocket, such as goose serve. With more than one machine, each guy is labeled with where it lives.
Those are full apps built around one kind of agent each, and they do more: voice, terminals, git review, usage and cost tracking. littleguys does less on purpose: it's one small chat app for all of your agents, with nothing to configure. The comparison has the details, with a source for each.
No. littleguys talks straight to your agents, on this Mac or over your own network. The only other things it fetches are its own updates, from GitHub, and the ACP registry's list of agents when you add one. Phone notifications go through littleguys-relay, sealed so the relay can't read them.
The install script does it in one go. It installs whatever's missing (the Command Line Tools, Rust, and Node and pnpm if you don't have them), builds main in ~/.littleguys and puts the app in /Applications. Run it again to update.
curl -fsSL https://raw.githubusercontent.com/herval/littleguys/main/install.sh | bashBy hand, you need Rust (stable), Node 22+ and pnpm. Xcode isn't required; the Command Line Tools are enough.
make install # dependencies, plus the Apple silicon and Intel Rust targets
make run # app + hot-reloading UI
make mock # UI only, in a browser, with a mock gateway (fixtures)
# ?phase=pairing|offline|no-config previews the Doctor screens
make build # universal littleguys.app + .dmg in src-tauri/target/universal-apple-darwin/release/bundle/
make install-app # build the .app for this Mac only (faster, no LTO) and put it in /Applications
make test # Rust testsRun make to see every command.
export OPENCLAW_STATE_DIR=/tmp/lgtest OPENCLAW_GATEWAY_PORT=19789 OPENCLAW_GATEWAY_TOKEN=test
openclaw gateway run --port 19789 --allow-unconfigured --auth token --token test --bind loopback &
make run # app talks to the test gateway
cd src-tauri && cargo run --example gw_probe -- agents.list # raw RPC probe (PROBE_URL=… for any gateway)
cd src-tauri && cargo run --example discover # what "Add gateway" would findThe phone bridge has a stand-in Mac and a stand-in phone:
cd src-tauri && cargo run --example bridge_demo # pretend bots; prints a pairing link
cd src-tauri && cargo run --example bridge_probe -- pair '<link>' # then: bots | call <bot> <method> [json] | eventslittleguys also builds on Windows 10 and 11 (x64). You need Rust (stable, the MSVC toolchain, with Visual Studio's C++ build tools), Node 22+ and pnpm; WebView2 comes with Windows. There's no make there, so use pnpm and cargo directly:
pnpm install
pnpm tauri dev # app + hot-reloading UI
pnpm tauri build --bundles nsis # installer in src-tauri\target\release\bundle\nsis\
cd src-tauri; cargo test # Rust testsOn Windows the little guy lives in the taskbar's notification area, Claude Code's hooks reach littleguys on a local port that only answers with a secret (macOS uses a Unix socket), and OpenClaw installs with its PowerShell installer. Every push to main runs .github/workflows/windows.yml, which runs the tests on Windows and keeps an unsigned installer in the run's artifacts.
Pushing a v* tag runs .github/workflows/release.yml. It builds the universal app, signs it with a Developer ID and notarizes it, then builds the Windows installer. It then publishes the .dmg, the -setup.exe and their signed update bundles to GitHub Releases, along with the latest.json the in-app updater reads (src-tauri/src/updater.rs), and bumps the cask in herval/homebrew-tap.
The workflow's credentials live in the repo's GitHub secrets. make release-secrets sets them up once: it gets a Developer ID certificate from Apple (keeping the key in your login keychain), checks an app-specific password for notarization, stores the updater key and adds a deploy key to the tap. To cut a release, set the version in src-tauri/tauri.conf.json, commit, and push a matching tag:
git tag v0.1.1 && git push origin main v0.1.1src-tauri/ Rust core — owns the gateway connection so the menu bar and
gateway/client.rs notifications work with every window closed (and so the
gateway/identity.rs gateway's browser-origin allowlist never applies)
openclaw/config.rs reads ~/.openclaw/openclaw.json (JSON5) → endpoint + credential
gateways.rs saved gateways, address normalization, Tailscale/Bonjour discovery
hub.rs one GatewayClient per saved gateway (add / rename / disable / remove)
runtime/ OpenClaw, Hermes and ACP adapters behind one interface
openclaw/runtime.rs finds the CLI, the gateway service's state (launchd, or `openclaw gateway status`), /health
doctor.rs install / update / start / onboard
activity.rs per-gateway roster (guys + threads + running + approvals) → tray mood, notifications
bridge/ paired iPhones: pairing, the Noise session, every bot passed through (BRIDGE-PROTOCOL.md)
tray.rs animated template sprite (frames from scripts/gen-icons.mjs)
updater.rs self-update from GitHub releases, restarts when idle
windows.rs popover (vibrancy or Acrylic, anchored to the tray) + main window
platform.rs what differs on Windows: PATH and programs, private files, the computer's name
src/ React + Tailwind
lib/gateway.ts typed RPC wrappers (types from @openclaw/gateway-protocol)
stores/ zustand: app (status, roster, selection), chat (transcripts + live runs)
popover/ main/ the two windows
- Protocol: the gateway speaks WebSocket protocol v4. The handshake signs a v3 payload with an Ed25519 device key.
src-tauri/tests/device-auth-fixture.jsonis generated from OpenClaw's own implementation with a fixed throwaway key (node scripts/device-auth-fixture.mjs), andcargo testchecks the Rust signer against it. - Webview bridge: webviews call
gw_call(gateway, method, params)and receive every gateway event asgw:event {gateway, event, payload}. The Rust core also publishesgw:status(per gateway) andlg:roster(all gateways). In the UI, guys are identified asgatewayId/agentIdand threads asgatewayId|sessionKey, since agent ids likemainrepeat across gateways.
- Clicking a notification doesn't jump to the thread yet. Notifications go through
tauri-plugin-notification, which has no click callbacks on macOS. - Windows builds aren't code-signed yet, so SmartScreen warns the first time the installer runs. Linux isn't supported yet.
- "Their own browser" is soft enforcement. OpenClaw has no per-agent browser binding, so a guy gets a named managed Chrome profile plus an
AGENTS.mdinstruction to use it.
