К основному содержанию
скилл CX Codex

agmsg — скилл для Claude Code: обмен сообщениями между агентами

Скилл для переписки между агентами через SQLite: Claude, Codex, Gemini CLI и другие обмениваются сообщениями без сети и демона.

Установить в Claude Code · Через Skills CLI (Vercel) Все способы и платформы ↓
npx skills add fujibee/agmsg --skill agmsg -a claude-code
Открыть на GitHub

Что делает agmsg

agmsg даёт агентам общий канал связи. База SQLite, реестр команд и рабочее состояние лежат в ~/.agents/skills/agmsg/. Никакой сети и никаких зависимостей, кроме bash и sqlite3. Демон не нужен, но есть необязательный agmsgd — локальная резидентная служба.

Скилл настоятельно советует не трогать конфиги, базу и данные команды руками, а пользоваться только скриптами. Отдельного register.sh нет: чтобы войти в команду, вызывается join.sh. Все скрипты — Bash, поэтому запускать их нужно через bash, а не через PowerShell или cmd. Если оболочка по умолчанию не Bash, команду оборачивают в bash -lc '...'. Пути к базе вручную не собирают, для переноса хранилища есть AGMSG_STORAGE_PATH.

Есть и подводный камень: у части агентских CLI уже есть собственный способ переписки между сессиями на одной машине. Пока проект на agmsg, такие сообщения идут мимо истории и экспорта команды, не доходят до участника на другой машине и не отмечаются прочитанными. Это повод проверить, не расходится ли переписка по двум каналам.

Какие задачи решает

  • передать сообщение от сессии Claude к сессии Codex
  • собрать общую историю переписки агентов команды
  • связать агентов на разных машинах через remote sync
  • отметить прочитанное и продвинуть курсор у получателя
  • подключить агента другого CLI к той же команде

Примеры запросов агенту

  • /agmsg
  • /agmsg send alice привет, посмотри задачу
  • /agmsg history

Как установить agmsg

1Через Skills CLI (Vercel)

npx skills add fujibee/agmsg --skill agmsg -a claude-code

2Вручную: положить файлы

~/.claude/skills/agmsg/SKILL.md

Папка скилла целиком; для одного проекта — .claude/skills/agmsg/

По шагам, с командами для каждой платформы: Как установить скилл в Claude Code: пять способов

Вопросы о agmsg

Как установить agmsg в Claude?

Через маркетплейс плагинов: сначала npx skills add fujibee/agmsg --skill agmsg -a claude-code, затем файл скилла оказывается по пути ~/.claude/skills/agmsg/SKILL.md. После этого при первом вызове скилл сам выполняет bootstrap: создаёт дерево ~/.agents/skills/agmsg/, если его ещё нет.

Что делает agmsg?

Передаёт сообщения между агентами через локальную базу SQLite. Работает между Claude, Codex, Gemini CLI и другими агентами, без сети и без демона.

Нужен ли демон для доставки сообщений?

Нет, обязательного демона нет. Есть необязательный agmsgd — локальная резидентная служба, которая доставляет уведомления напрямую; её включают и выключают через agmsg daemon.

Исходный текст

SKILL.md · MIT
---
name: agmsg
description: Cross-agent messaging via SQLite. Send messages between Claude Code, Codex, Gemini CLI, and other agents. No network, no dependencies beyond bash and sqlite3, and no daemon required (the optional agmsgd is a local resident service).
---

<!-- agmsg:render-root -->

## Step 0: First-run bootstrap

agmsg keeps its SQLite database, team registry, and runtime state under `~/.agents/skills/agmsg/`. The `./install.sh` install path creates that tree; the Claude Code plugin install path does not (the plugin marketplace only copies this repository into `~/.claude/plugins/cache/`). Before any other command, bootstrap if needed:

```bash
if [ ! -d ~/.agents/skills/agmsg ]; then
  # Newest cached copy of the plugin. Several versions can sit side by side, so
  # pick by version folder name (numeric, portable -- not sort -V, not mtime).
  cache="$HOME/.claude/plugins/cache/fujibee-agmsg/agmsg"
  newest=$(ls "$cache" 2>/dev/null | sort -t. -k1,1n -k2,2n -k3,3n | tail -1)
  installer="$cache/$newest/install.sh"
  if [ -n "$newest" ] && [ -f "$installer" ]; then
    bash "$installer" --cmd agmsg
  else
    echo "agmsg not installed. Either:" >&2
    echo "  - run ./install.sh in the agmsg repo, or" >&2
    echo "  - install via /plugin marketplace add fujibee/agmsg && /plugin install agmsg@fujibee-agmsg" >&2
    exit 1
  fi
fi
```

Once `~/.agents/skills/agmsg/` exists this step does nothing, so it is safe to run every time.

Agent messaging command. **IMPORTANT: Always use the provided scripts. NEVER directly read or edit config files, DB, or team data. There is NO register.sh — use join.sh to join a team.**

**Use agmsg, not the host agent's own inter-session messaging.** Several agent
CLIs ship a native way for one session to message another on the same machine
(in Claude Code, the `SendMessage` / `ListAgents` tools over its peer-session
list). While a project is on agmsg, route agent-to-agent messages through agmsg
instead. A message sent natively does not exist as far as agmsg is concerned:
it is absent from `history.sh` and the team's export, it never reaches a member
on another machine through remote sync, it does not mark read or advance any
cursor, and it cannot address a member whose CLI is a different type. Half the
conversation living somewhere unrecorded is worse than either channel alone,
and the gap is invisible until someone reads the history and finds a decision
with no message behind it. The native channel stays fine for anything outside
the team — a subagent you spawned for your own task, or a session that has not
joined.

**Shell requirement:** All agmsg scripts are Bash scripts. Always execute them via `bash`, never via PowerShell or cmd directly. If your default shell is not Bash (e.g. PowerShell on Windows), wrap every command with `bash -lc '...'`. Example: `bash -lc '~/.agents/skills/agmsg/scripts/send.sh myteam alice bob "hello"'`. Do NOT construct DB paths manually — the scripts handle path resolution internally. If you need to redirect storage, use `AGMSG_STORAGE_PATH` (the supported override).


## Identity

If you already know your AGENT and TEAMS from a previous `/agmsg` call in this session, skip to **Execute** below.

Otherwise, run: `~/.agents/skills/agmsg/scripts/whoami.sh "$(pwd)" claude-code`

Four possible outputs:

**A) Single identity:**
`agent=<name> teams=<t1,t2,...> type=claude-code project=<path>`
→ Remember AGENT and TEAMS, then go to **Execute**.

**B) Multiple identities:**
`multiple=true agents=<n1,n2,...> teams=<t1,t2,...> type=claude-code project=<path>`
→ Ask the user which agent name to use for this session, then go to **Execute**.

**C) Not in a team:**
`not_joined=true available_teams=<t1,t2,...>` (or `available_teams=none`)
→ Show the user the available teams from the output, then:

  Before first-time setup, inspect the user's request. If they ask to join, import, or bring in a team that already exists on a server, do not call `join.sh`. Go directly to `remote pull` under Execute. First run `~/.agents/skills/agmsg/scripts/team-list.sh --json --scope all`; if a same-named local team has `binding_state` `none` or `disconnected`, stop and ask the user how to proceed. After pull succeeds, return to Identity setup so the user can register a new local agent in the pulled team.

  > **First-time setup required.**
  > Joining a team so this agent can send and receive messages.
  > - **Team name**: a group of agents that can message each other (available: <list from output>)
  > - **Agent name**: this agent's identity within the team

  1. Ask: "Enter a team name (joins existing or creates new)". If that name is not in `available_teams` and `~/.agents/skills/agmsg/scripts/team-list.sh --json --scope all` shows a team whose `binding_state` is not `none`, do not create it yet: ask whether to create a new local team or bring in the team of that name from a server (`remote pull`; after it succeeds, return to Identity setup). With no such team, create it locally without mentioning remote.
  2. If the team name given already appears in `available_teams`, run `~/.agents/skills/agmsg/scripts/team.sh <team>` to see the current roster (name, type, project) and note the names already in use. Look for a naming convention already in play (e.g. a shared base name with role and number suffixes (`<base>-<role><n>`), or names derived from the team name) and, when one exists, propose 2-3 unused names that extend it; otherwise propose 2-3 short, distinctive identity names (not a bare tool-type label like `codex`/`cc`). Either way, names must not collide with the roster. Then ask: "Enter a name for this agent (suggestions: <name1>, <name2>, <name3> — or type your own)". For a brand-new team, skip the roster check and just ask: "Enter a name for this agent".
  3. **You MUST use join.sh** — run: `~/.agents/skills/agmsg/scripts/join.sh <team> <agent_name> claude-code "$(pwd)"`
  4. Show the result and explain:

  > **Joined!** You can now use `/agmsg` to check and send messages.
  > - `/agmsg` — check inbox
  > - `/agmsg send <agent> <message>` — send a message
  > - `/agmsg team` — list team members
  > - `/agmsg history` — message history

<!-- agmsg:render-overlay claude-code -->
  5. **REQUIRED — Do NOT skip this step.** Choose how incoming messages reach this agent. Show this screen every time (a new join, a new seat added by someone already using agmsg, and when the mode is changed). First run `~/.agents/skills/agmsg/scripts/agmsg daemon offer claude-code`; it only reads and prints one line:
     - `agmsgd=available`: ask the user to pick one, in this order:
       1. `agmsgd` — notices delivered directly by a background service (recommended). Choosing it registers a background service that starts at login; `agmsg daemon disable` stops and removes it. Empty input means this one.
       2. `monitor (legacy)` — the Claude Code Monitor tool streams the inbox (the `monitor` mode value).
       3. `turn`, 4. `both`, 5. `off` — as before.
     - `agmsgd=on`: do not ask which to use. Say "agmsgd is on: notices are delivered directly" and ask only whether to keep using it or switch to `monitor (legacy)`.
     - `agmsgd=not-running reason=...`: agmsgd is turned on but is not running, so do not say notices are delivered directly. Say so with the reason and ask whether to start it (`agmsg delivery agmsgd` starts it) or switch to `monitor (legacy)`.
     - `agmsgd=unavailable reason=...`: do not offer agmsgd; say the reason in one line, then ask for `monitor (legacy)`, `turn`, `both`, or `off` (empty input means `monitor`).

     To apply the choice, run `~/.agents/skills/agmsg/scripts/agmsg delivery <choice> --type claude-code --project "$(pwd)"` with `<choice>` = `agmsgd`, `monitor`, `turn`, `both` or `off` (`monitor (legacy)` is the value `monitor`) and show its output and follow the printed `AGMSG-DIRECTIVE` block:
     - `agmsgd` turns the background service on (`daemon enable`) and leaves the project on `monitor` as the fallback for a seat whose destination is not confirmed yet. If it fails, say so and offer the other choices.
     - Keep using agmsgd (it is on or turned on but not running): run `agmsg delivery agmsgd` the same way; it also records that this project uses agmsgd.
     - `monitor (legacy)` (and `turn`, `both`, `off`) is a real opt-out: the CLI records that this project does not use agmsgd, so agmsgd stops delivering here and the project keeps the old path. agmsgd stays on for the install's other projects; when it says so, pass on its line that `agmsg daemon disable` turns agmsgd off for all of them.

  6. Then check inbox for the newly joined team.

**D) Suggestions for reuse:**
`suggest=true agents=<n1,n2,...> teams=<t1,t2,...> type=claude-code project=<path> available_teams=<t1,t2,...>`
→ No exact registration exists for this project, but there are same-type agent names registered elsewhere.

  1. Show the suggested agent names to the user.
  2. Ask whether to reuse one of those names or choose a new one.
  3. Ask for the team name to join (existing or new). If that name is not in `available_teams` and `~/.agents/skills/agmsg/scripts/team-list.sh --json --scope all` shows a team whose `binding_state` is not `none`, do not create it yet: ask whether to create a new local team or bring in the team of that name from a server (`remote pull`; after it succeeds, return to Identity setup). With no such team, create it locally without mentioning remote. If the team is in `available_teams`, run `~/.agents/skills/agmsg/scripts/team.sh <team>` and check that the agent name you are about to use (reused or new) is not already in its roster.
  4. Run: `~/.agents/skills/agmsg/scripts/join.sh <team> <agent_name> claude-code "$(pwd)"`
  5. Then continue with the normal post-join flow above.

## Execute

**Only use scripts in `~/.agents/skills/agmsg/scripts/` — do not read or modify files under `teams/` or `db/` directly.** Treat the storage layout as internal: never construct a database path or invoke `sqlite3` directly. The scripts resolve the active store, including `AGMSG_STORAGE_PATH` overrides.

**Terminal/pane self-awareness.** Asked about this session's own terminal, pane, or driver — or before using `arrange`, `peek`, or `poke` below — run `where.sh` (see the "where" argument below) first and answer from its `terminal=`/`capabilities=` fields. Never infer the driver from environment variables or a `grep`/`ps` guess: that is how a session under a real driver ends up reporting a false negative about its own placement, or claiming a capability or a whole driver does not exist when it does (#1171). Each driver's own operational detail lives in `~/.agents/skills/agmsg/scripts/drivers/terminals/<terminal>/README.md`, named by `where.sh`'s own `terminal=` field — never guessed at from a remembered syntax.

Asked about a *teammate's* placement or status, or what can be done to one, that is `team.sh <team>`'s question (see the "team" argument below), not something to infer from a stale memory of their last known pane. Act on a teammate with `peek.sh`/`poke.sh`/`arrange.sh <team> <name>` directly rather than guessing reachability first — its exit code says whether it worked and, if not, why (see the "peek"/"poke"/"arrange" arguments below).

**If no arguments provided (DEFAULT action — always do this when the command is invoked without arguments):**
1. **IMMEDIATELY** run inbox check for each TEAM: `~/.agents/skills/agmsg/scripts/inbox.sh $TEAM $AGENT`
2. Do NOT ask the user what to do — just run the inbox check.
3. If there are messages, read and respond appropriately. To reply:
   `~/.agents/skills/agmsg/scripts/send.sh $TEAM $AGENT <to_agent> "<message>"`

**Ensure monitor is running first.** In `monitor` or `both` mode, keep one persistent `watch.sh` task for this session. Switch that watcher when `actas` changes the active role.

If asked, in ordinary language and in either English or Japanese, to re-arm this session's own agmsg monitor (no fixed trigger word — read the request as it is phrased): invoke Monitor with the standard command and description for this seat, and say nothing else.

If asked to re-arm every Claude Code seat in the team together (not just this session's own — no dedicated command for this, do it through poke: #1321): run `~/.agents/skills/agmsg/scripts/team.sh <team> --json`, select the rows whose `type` is `claude-code` and whose `delivery` is `monitor` or `both`, deduplicated by member name. Whole team — never narrow this to your own project. For each selected seat, in turn with a gap of a few seconds between seats (poking them all at once starts every seat's model turn in the same instant and risks rate limits): write a one-line message asking that seat to re-arm its own agmsg monitor — phrase it in whoever asked's own words, or something equivalent — to a file, then `~/.agents/skills/agmsg/scripts/poke.sh <team> <seat> --retries 5 --retry-delay 2 --backoff exponential --body-file <path>`. A seat whose input box was still busy after every retry (poke exits 14) could not be reached this way; name it in your report rather than silently skipping it.

Claude Code commands may need permission and sandbox allowlists for `~/.agents/skills/agmsg/scripts/` and its writable `db/`, `teams/`, and `run/` directories.

**Permission prompts.** Every command here runs through the Bash tool, so each call is gated by the permission system until the script directory is allowlisted. Without this the user is asked to confirm essentially every `agmsg` call. Add to `~/.claude/settings.json` (or project-level `.claude/settings.local.json`):

```json
{
  "permissions": {
    "allow": [
      "Bash(~/.agents/skills/agmsg/scripts/*)",
      "Bash(/Users/<you>/.agents/skills/agmsg/scripts/*)",
      "Bash(bash ~/.agents/skills/agmsg/scripts/*)",
      "Bash(bash /Users/<you>/.agents/skills/agmsg/scripts/*)"
    ]
  }
}
```

Four entries are needed because a rule matches the command string as written, and these scripts are invoked both as `~/...` and as an absolute path, with or without an explicit `bash` prefix. Replace `/Users/<you>` with the user's home directory.

**Sandbox compatibility.** When Claude Code's sandbox is enabled, `watch.sh` (monitor mode) runs inside the sandbox and needs to write pidfiles and SQLite WAL files under `~/.agents/skills/agmsg/`. If monitor mode fails with write/permission errors there, add an allowlist entry to `~/.claude/settings.json` (or project-level `.claude/settings.local.json`):

```json
{
  "sandbox": {
    "filesystem": {
      "allowWrite": [
        "~/.agents/skills/agmsg/"
      ]
    }
  }
}
```

The allowlist does not enable sandboxing by itself. Use `/sandbox` in Claude Code to choose a sandbox mode, or add `"enabled": true` alongside `"filesystem"` under `"sandbox"` to configure it in settings. The allowlist has no effect until sandboxing is enabled.

If argument is "history":
1. Run: `~/.agents/skills/agmsg/scripts/history.sh $TEAM $AGENT`

If argument starts with "team list" (e.g. "team list", "team list --json", "team list --scope project"):
1. Run: `~/.agents/skills/agmsg/scripts/team-list.sh <the rest of the args after "team list", unchanged>`
2. This is a distinct command from bare "team" below — check for "team list" FIRST so "list" is never mistaken for a team name.

If argument is "team" or "team --json":
1. For each TEAM, run: `~/.agents/skills/agmsg/scripts/team.sh $TEAM [--json]`, preserving the option when present. `--json` returns every observed field.
2. This is read-only. It reports each member's identity cells and whether they are consistent — including a member that does not answer at all — but writes nothing and pokes no one. A seat that is wrong or unresponsive is not something this command, or any other, repairs from the outside: typing into another seat's session to fix it is exactly the mistake that used to happen here, and it is gone on purpose, not replaced by another form of the same thing. A member repairs its own identity cells by running `fix` (below), from itself. A seat that cannot or will not do that gets despawned and restarted, or a person takes it — not patched over from another pane.

If argument starts with "send" (e.g. "send misaki check the server"):
1. Parse target agent and message from the arguments
2. Determine which team the target agent belongs to, then run:
   `~/.agents/skills/agmsg/scripts/send.sh $TEAM $AGENT <to_agent> "<message>"`

If argument is "config":
1. Run: `~/.agents/skills/agmsg/scripts/config.sh show`
2. Show the output to the user.

If argument starts with "config set" (e.g. "config set delivery.turn.check_interval 30"):
1. Parse key and value from the arguments.
2. Run: `~/.agents/skills/agmsg/scripts/config.sh set <key> <value>`

If argument is "version":
1. Run: `~/.agents/skills/agmsg/scripts/version.sh`
2. Show the output — the installed version (git-describe provenance recorded at install time).

If asked to update or upgrade agmsg:
1. Say "Downloading the agmsg update…" before running `npx agmsg@latest install --update` — add `--cmd <name>` when this machine has more than one agmsg install. It keeps the database and team configs and replaces the scripts.
2. This session still has the old skill loaded. Re-read the updated installation's `SKILL.md`, read the new version's section of its `CHANGELOG.md`, and tell the user what changed and which settings it recommends. The update output gives the real file paths and version.
3. Tell the user to restart running agent sessions so they pick up the new scripts.

If argument is "where" (e.g. asked to report this session's own pane or placement):
1. Run: `~/.agents/skills/agmsg/scripts/where.sh`
2. Report exactly what it prints. Do not try to answer this by naming a terminal yourself or running any terminal-specific command directly — this call already asked every driver on this session's behalf.
3. `resolved=true placement=<terminal>:<id>` is a known pane; `resolved=true placement=none` is a GENUINE negative (this session's own terminal confirmed it has no addressable pane). `resolved=false` means placement could NOT be determined — `reason` names which terminal(s) were asked and why. Never report a `resolved=false` answer as "no pane" or "not attached to a pane"; those are different answers to different questions, and the difference is the entire point of this command (#1171).
4. `where.sh`'s output also carries `capabilities=<list>` (#1082) — that resolved terminal's own manifest, space-separated, verbatim. Before using `arrange`, `peek`, or `poke` below, check that the verb is in this list; if it is not, report it as unavailable for this terminal (name the terminal) rather than attempting it and finding out from an exit code. If it IS listed, read that terminal's own file — `~/.agents/skills/agmsg/scripts/drivers/terminals/<terminal>/README.md` — before reporting a peek/poke/arrange failure: exit-code meanings differ by driver, and that file, not this one, is where they live.


If argument starts with "actas" followed by an agent name (e.g. "actas alice"):
1. Parse the new role name. If none was given (e.g. bare "actas", or the user asks you to suggest one), run `~/.agents/skills/agmsg/scripts/team.sh <team>` for each TEAM to see the current roster. Look for a naming convention already in play (e.g. a shared base name with role and number suffixes (`<base>-<role><n>`), or names derived from the team name) and, when one exists, propose 2-3 unused names that extend it; otherwise propose 2-3 short, distinctive identity names (not a bare tool-type label). Either way, names must not collide with the roster. Ask the user to pick one or type their own before continuing.
2. Run `~/.agents/skills/agmsg/scripts/identities.sh "$(pwd)" claude-code` to see whether the role is already registered for this (project, type).
3. If the name does not appear in the output, join under the existing team. Read TEAMS from the in-session whoami state (it may be a single team or comma-separated). For a single team, run `~/.agents/skills/agmsg/scripts/join.sh <team> <name> claude-code "$(pwd)"`. For multiple teams, ask the user which team to join the new role into, then run join.sh for that team.
4. **Pre-flight claim** the actas exclusivity lock so this role isn't already owned by another live session: `~/.agents/skills/agmsg/scripts/actas-claim.sh "$(pwd)" claude-code <name> "$CLAUDE_CODE_SESSION_ID"`. Read the `status=` line of the output:
    - `status=ok ...`: proceed to step 5.
    - `status=held team=<team> owner=<sid>`: another live session currently owns `<name>` in `<team>`. Tell the user: "Cannot actas as `<name>` — it is held by session `<sid>` in team `<team>`. Run `/agmsg drop <name>` in that session first, then retry." Then abort — do NOT touch the running Monitor.
    - `status=not_registered`: shouldn't happen if step 3 ran; treat as an error.
5. **Switch receive too — exclusive role mode.**
   a. Find this session's agmsg watch Monitor task: a task in TaskList whose description begins with "agmsg inbox stream", or the task_id returned by a Monitor call you made earlier in this conversation. Not every environment lists Monitor tasks in TaskList, so an empty list does not mean none is running.
   b. **If you have such a task_id**: TaskStop it.
   c. **If you have none** (typical when /agmsg actas runs as the first command of a fresh session — SessionStart hasn't fired the Monitor directive yet, or you're invoking actas before the agent acted on it): skip TaskStop. Do NOT attempt TaskStop with a guessed or empty task_id — it will fail with "Invalid tool parameters" and confuse the flow. Starting a new watcher for this session in step d replaces any previous one.
   d. **If the step 4 output had a `delivery=native` line**: agmsgd now delivers to this session directly, so start no Monitor and skip the rest of this step. Otherwise run `~/.agents/skills/agmsg/scripts/delivery.sh status claude-code "$(pwd)"` and read its **first line**.
      - **`mode: monitor` or `mode: both`**: invoke a fresh Monitor, regardless of whether step b or c applied:
        - command: `~/.agents/skills/agmsg/scripts/watch.sh $CLAUDE_CODE_SESSION_ID "$(pwd)" claude-code <name> --max-seconds=1750`
        - description: `agmsg inbox stream (acting as <name>)`
        - persistent: true
        - timeout_ms: 1800000

        This watch renews itself. A little before the 30-minute cap it prints one line on its own and exits: on `agmsg watch: re-arm - ...`, invoke Monitor again with exactly the command and description that line names (persistent: true, timeout_ms: 1800000), silently — no message to the user, no "re-armed", no acknowledgement, no summary, since announcing it every 30 minutes wastes tokens for no benefit; on `agmsg watch: stopping - ...`, do not re-arm it. If the watch is instead killed at the cap and no such line arrived (an agmsg install from before this), re-arm it only when the expiry notification says it delivered something.
      - **`mode: turn`**: leave it stopped, silently. `has_st=1` is the one case `delivery.sh` can actually confirm was a deliberate choice — someone configured turn-based delivery for this project — so `actas` starting nothing here needs no explanation.
      - **`mode: off (no agmsg delivery hooks installed for this project)`**: leave it stopped (`actas` must not start automatic delivery a project wasn't configured for), but **do not treat this as silently deliberate**. `delivery.sh` cannot tell whether someone ran `mode off` here or this project was simply never configured — both leave the exact same settings file (#687 review round 3). **Tell the user** — e.g. "agmsg delivery hooks are not installed for this project; automatic delivery remains stopped. Run `/agmsg mode <choice>` if you want to configure it." Keep it matter-of-fact, not a warning. Do not report `actas` as complete without saying this.
      - **`mode: off (unrecognized: ...)`**: leave it stopped too (same rule — do not guess a mode), but this is a stronger case than the no-hooks-installed one above: `delivery.sh` could not even find or read a settings file for this project, most often because the working directory does not match how the project was actually registered. **Tell the user explicitly** — e.g. "agmsg could not find a delivery configuration for this project at `<path from the message>` — delivery is stopped, but this may mean the project isn't registered here rather than that it was deliberately turned off. Check the path, or run `/agmsg mode <choice>` to configure it explicitly." Do not report `actas` as complete without saying this — a silent stop here is indistinguishable from the other off cases and is what let this go unnoticed before (#687).
   The 4th argument to `watch.sh` restricts the subscription to messages addressed to `<name>` only — other roles' inbound messages stop reaching this session until another `actas` or session end.
6. Set the session's active FROM to `<name>` — use `<name>` in every `send.sh` call for the rest of this session.
7. Tell the user: "Now acting as `<name>`. Sends use `<name>` as from; receive restricted to `<name>` only."
8. **Only if this session was NOT launched via `spawn`** — check the environment variable `AGMSG_SPAWNED` (e.g. `printenv AGMSG_SPAWNED`): `spawn` exports `AGMSG_SPAWNED=1` and already named the session `<team>-<agent>` via `-n`, so when it is set, **skip this tip entirely**. When it is UNSET (a human typed `claude` then actas'd, so the session has no convention name), additionally suggest to the user: "Tip: rename this session to `<team>-<name>` with `/rename <team>-<name>` so it's easy to find in the `/resume` picker and stays labeled after a restart." `/rename` is a user-typed slash command — you cannot invoke it yourself, so only suggest it.
9. **Confirm the Monitor actually attached** — only when step 5d invoked a fresh Monitor (`mode: monitor` or `mode: both`): confirm the Monitor call from step 5d started (it returned a task id rather than an error). TaskList may list this task, but not every environment does (the desktop app's Code tab runs the Monitor and delivers its events without listing it), so a task missing from TaskList is not a failure: judge by the Monitor call starting and its events arriving. The background-task footer is not a reliable check either. If the Monitor call failed, retry the invocation from step 5d once. If it still fails after the retry, tell the user `actas` completed but delivery could not be confirmed as attached, and do not describe delivery as active.
If argument starts with "drop" followed by an agent name (e.g. "drop alice"):
1. Parse the role name.
2. Run `~/.agents/skills/agmsg/scripts/reset.sh "$(pwd)" claude-code <name> "$CLAUDE_CODE_SESSION_ID"` to remove only that role's registration for this project. If the role has no other registrations left, reset.sh also drops it from the team config. The 4th argument releases any actas exclusivity locks this session held on the role so peers can pick it up immediately (see #62).
3. If the session's active FROM was `<name>`, clear that state. Then:
   a. Find this session's agmsg watch Monitor task: a task in TaskList whose description begins with "agmsg inbox stream", or the task_id returned by a Monitor call you made earlier in this conversation. An empty TaskList does not mean none is running.
   b. **If you have such a task_id**: TaskStop it.
   c. **If you have none**: skip TaskStop. Do NOT attempt TaskStop with a guessed or empty task_id.
   d. Run `~/.agents/skills/agmsg/scripts/delivery.sh status claude-code "$(pwd)"` and read its **first line**.
      - **`mode: monitor` or `mode: both`**: invoke a fresh Monitor with the default subscription (no `actas` name filter — receives every (team, agent) pair currently registered for this project that isn't held by another session):
        - command: `~/.agents/skills/agmsg/scripts/watch.sh $CLAUDE_CODE_SESSION_ID "$(pwd)" claude-code --max-seconds=1750`
        - description: `agmsg inbox stream`
        - persistent: true
        - timeout_ms: 1800000

        This watch renews itself. A little before the 30-minute cap it prints one line on its own and exits: on `agmsg watch: re-arm - ...`, invoke Monitor again with exactly the command and description that line names (persistent: true, timeout_ms: 1800000), silently — no message to the user, no "re-armed", no acknowledgement, no summary, since announcing it every 30 minutes wastes tokens for no benefit; on `agmsg watch: stopping - ...`, do not re-arm it. If the watch is instead killed at the cap and no such line arrived (an agmsg install from before this), re-arm it only when the expiry notification says it delivered something.
      - **`mode: turn`**: leave it stopped, silently — the one case `delivery.sh` can confirm was deliberate.
      - **`mode: off (no agmsg delivery hooks installed for this project)`**: leave it stopped, but say so — same reasoning as the `actas` step this mirrors: this state is indistinguishable from "never configured" (#687 review round 3), so do not report it as deliberate. Do not report the drop as complete without mentioning it.
      - **`mode: off (unrecognized: ...)`**: leave it stopped, but say so with the stronger diagnostic — same reasoning as the `actas` step this mirrors (#687). Do not report the drop as complete without mentioning it.
4. Tell the user: "Dropped role `<name>` from this project."
If argument starts with "spawn" (e.g. "spawn codex reviewer", "spawn claude-code alice --window"):
1. Parse `<type>` (a spawnable agent type), `<name>`, and any options (`--boot-prompt <text>`, `--project <path>`, `--team <team>`, `--window`, `--split h|v`, `--terminal <template>`, `--no-wait`, `--ready-timeout <secs>`, `--model <id>`, `--fresh`).
2. Run: `~/.agents/skills/agmsg/scripts/spawn.sh <type> <name> --project "$(pwd)" [options]`
   - `spawn.sh` pre-joins `<name>...

© fujibee · MIT · fujibee/agmsg

Похожие скиллы

Все скиллы по теме «Настройка агента: память, контекст, субагенты» →
agentica-infrastructure parcadei Справочник по API инфраструктуры Agentica: 11 классов паттернов координации агентов, примитивы консенсуса и схема базы отслеживания. Пригодится, когда строишь мультиагентный воркфлоу и нужны точные сигнатуры конструкторов. CX Codex +1 475установок openclaw-config adisinghstudent Скилл помогает управлять конфигурацией бота OpenClaw, диагностировать каналы связи и находить сбои в шлюзе или сессиях. CX Codex +1 2 800установок mcp-hub claude-office-skills Скилл подключает агента к каталогу MCP-серверов: файловые системы, базы данных, API и обработка документов. Пригодится, когда агенту нужно выйти за пределы проекта. CX Codex +1 4 600установок agent-orchestration OrchestKit Скилл с паттернами автономных циклов, координации нескольких агентов и мультисценарных прогонов. Пригодится, когда строите агентные пайплайны и выбираете фреймворк. CX Codex +1 1 400установок hive-mind-advanced ruvnet Система координации множественных агентов с королевой-координатором, консенсусными механизмами и общей памятью. Подходит для сложных проектов, где нужно распределить задачи между специализированными агентами. CX Codex +1 1 100установок daily-news-report sickn33 Скилл собирает свежие статьи с заранее заданных источников, фильтрует по качеству и генерирует ежедневный отчёт в Markdown. Пригодится, если нужно отслеживать релизы, исследования и новости из техсообщества без ручного сёрфинга. CX Codex +1 1 000установок

Спонсоры проекта

Компании, которые помогают держать аналитику открытой