# cross-agent-watch **Purpose.** Long-running watcher that fires desktop notifications when new cross-agent messages land in any project's `inbox/from-agents/` directory. This is the primary cold-start mechanism: messages get noticed even when no Claude session is active. ## Usage ``` cross-agent-watch [--projects-glob ] [--log ] ``` No args required. Defaults: - Watches `~/projects/*/inbox/from-agents/` (matches every project with the cross-agent-comms convention). - Logs each event to `~/.local/state/cross-agent-comms/watch.log`. ### Flags | Flag | Default | Purpose | |---|---|---| | `--projects-glob ` | `~/projects/*/inbox/from-agents/` | Override which directories to watch. Useful for testing on a single project. | | `--log ` | `~/.local/state/cross-agent-comms/watch.log` | Override log location. Set to `/dev/null` to disable logging. | | `--quiet` | off | Suppress stdout output. Notifications still fire. | | `--no-notify` | off | Skip `notify` calls. Useful for testing the watcher loop without spamming notifications. | ## Behavior 1. Resolves the projects-glob to a concrete list of directories at startup. New projects added to `~/projects/` after startup are NOT picked up — restart the watcher to re-resolve. 2. Runs `inotifywait -m -e create,moved_to --format '%w%f'` against each watched directory. 3. For each event, calls `notify info "Cross-agent message" ": "`. 4. Appends an event line to the log: `\t\t`. ## Event filtering - Watches `create` AND `moved_to` events. The `moved_to` part is critical for the atomic-write convention (`mktemp` + `mv` produces a `moved_to`, not a `create`). - Files starting with `.tmp.` are ignored — they're staging files from in-progress writes that should never produce a notification. ## Installation ### Option A — tmux pane (personal, easy) Run in a tmux pane that survives session disconnects: ``` tmux new -d -s cross-agent-watch 'cross-agent-watch' ``` ### Option B — systemd user service (production) Provided files: - `~/.config/systemd/user/cross-agent-watch.service` - `~/.config/systemd/user/cross-agent-watch.path` Enable with: ``` systemctl --user enable --now cross-agent-watch.path ``` The path unit triggers the service unit on filesystem changes; the service unit re-execs `cross-agent-watch` if it dies. Survives reboot. ## Failure modes | Symptom | Likely cause | Fix | |---|---|---| | No notifications fire on new files | inotifywait not running, or glob resolved to zero dirs | Check `cross-agent-watch --projects-glob ... --quiet` exits non-zero immediately. Log shows `"resolved 0 directories"`. | | Notifications fire on `.tmp.` files | Filter regression | Verify `inotifywait` events show the `.tmp.` files; if so check this script's filter logic. | | Some files missed under rapid bursts | inotify queue overflow | Increase `fs.inotify.max_queued_events` sysctl. Default 16384 is usually fine. | | Permission denied on a watched dir | Directory perms wrong | `chmod 700 ` and confirm owner. | ## HALT awareness Checks `~/.config/cross-agent-comms/HALT` on each iteration (each inotifywait event fired). If HALT exists, the watcher continues running but **suppresses the `notify` call**. The event is still logged, with `(suppressed by HALT)` appended: ``` 2026-04-27T04:42:00-05:00 career 20260427T094200Z-from-homelab-test.org (suppressed by HALT) ``` Logged-but-suppressed events are useful for the operator to see what would have fired during the halt window — helpful for diagnosing whatever caused the halt. When HALT clears, suppression stops; subsequent events fire normally. Backlog events that arrived during halt are NOT replayed — they get picked up via cold-start handling (status CLI, agent startup check, or the next agent poll once polling resumes). If the HALT file exists but is unreadable, fail-closed (suppress) — safer than fail-open. See `cross-agent-halt.md` for the full halt mechanism. ## Examples ```bash # Watch all projects, log everything, fire notifications cross-agent-watch # Test against a single project, no notifications, verbose cross-agent-watch \ --projects-glob "$HOME/projects/work/inbox/from-agents/" \ --no-notify # Production-style: quiet stdout, log only cross-agent-watch --quiet ``` ## See also - `cross-agent-status` — point-in-time snapshot of pending messages. - `cross-agent-send` — counterpart writer. - `cross-agent-comms.org` — protocol spec.