Mainstream messaging
Signal
Signal — це завантажуваний плагін каналу (@openclaw/signal). Gateway взаємодіє із signal-cli через HTTP: або з нативним демоном (JSON-RPC + SSE), або з контейнером bbernhard/signal-cli-rest-api (REST + WebSocket). OpenClaw не містить вбудованої libsignal.
Модель номерів (спочатку прочитайте це)
- Gateway підключається до пристрою Signal: облікового запису
signal-cli. - Якщо запустити бота у вашому особистому обліковому записі Signal, він ігноруватиме ваші власні повідомлення (захист від зациклення).
- Щоб реалізувати сценарій «я пишу боту, а він відповідає», використовуйте окремий номер бота.
Встановлення
openclaw plugins install @openclaw/signalДля специфікацій плагінів без префікса спочатку виконується спроба встановлення з ClawHub, а потім резервна спроба з npm. Щоб примусово вибрати джерело, використовуйте openclaw plugins install clawhub:@openclaw/signal або npm:@openclaw/signal. Команда plugins install реєструє та вмикає плагін; окремий крок enable не потрібен. Загальні правила встановлення наведено в розділі Плагіни.
Швидке налаштування
Виберіть номер
Використовуйте для бота окремий номер Signal (рекомендовано).
Встановіть плагін
openclaw plugins install @openclaw/signalЗапустіть кероване налаштування
openclaw channels addМайстер визначає, чи доступний signal-cli у PATH, а якщо ні — пропонує його встановити: завантажує офіційну нативну збірку GraalVM для Linux x86-64 або встановлює через Homebrew на macOS та інших архітектурах. Потім він запитує номер бота та шлях до signal-cli.
Прив’яжіть або зареєструйте обліковий запис
Перевірте та створіть пару
openclaw gateway call channels.status --params '{"probe":true}'Надішліть перше приватне повідомлення та схваліть створення пари: openclaw pairing approve signal <CODE>.
Мінімальна конфігурація:
{ channels: { signal: { enabled: true, account: "+15551234567", cliPath: "signal-cli", dmPolicy: "pairing", allowFrom: ["+15557654321"], }, },}| Поле | Опис |
|---|---|
account |
Номер телефону бота у форматі E.164 (+15551234567) |
cliPath |
Шлях до signal-cli (signal-cli, якщо він доступний у PATH) |
configPath |
Каталог конфігурації signal-cli, переданий як --config |
dmPolicy |
Політика доступу до приватних повідомлень (рекомендовано pairing) |
allowFrom |
Номери телефонів або значення uuid:<id>, яким дозволено надсилати приватні повідомлення |
Підтримка кількох облікових записів: використовуйте channels.signal.accounts із конфігурацією для кожного облікового запису та необов’язковим name. Спільний шаблон описано в розділі Канали з кількома обліковими записами.
Що це таке
- Детермінізована маршрутизація: відповіді завжди повертаються до Signal.
- Приватні повідомлення використовують основний сеанс агента; групи ізольовані (
agent:<agentId>:signal:group:<groupId>). - За замовчуванням Signal може записувати зміни конфігурації, ініційовані командою
/config set|unset(потрібноcommands.config: true). Щоб вимкнути це, установітьchannels.signal.configWrites: false.
Шлях налаштування A: прив’язування наявного облікового запису Signal (QR-код)
- Установіть
signal-cli(JVM або нативну збірку) чи дозвольтеopenclaw channels addустановити його. - Прив’яжіть обліковий запис бота:
signal-cli link -n "OpenClaw", потім відскануйте QR-код у Signal. - Налаштуйте Signal і запустіть Gateway.
Шлях налаштування B: реєстрація окремого номера бота (SMS, Linux)
Використовуйте цей спосіб для окремого номера бота замість прив’язування наявного облікового запису застосунку Signal. Наведений нижче процес перевірено на Ubuntu 24.
- Отримайте номер, який може приймати SMS (або голосовий виклик для перевірки стаціонарних номерів). Окремий номер бота дає змогу уникнути конфліктів облікового запису або сеансу.
- Установіть
signal-cliна хості Gateway:
VERSION=$(curl -Ls -o /dev/null -w %{url_effective} https://github.com/AsamK/signal-cli/releases/latest | sed -e 's/^.*\/v//')curl -L -O "https://github.com/AsamK/signal-cli/releases/download/v${VERSION}/signal-cli-${VERSION}-Linux-native.tar.gz"sudo tar xf "signal-cli-${VERSION}-Linux-native.tar.gz" -C /optsudo ln -sf /opt/signal-cli /usr/local/bin/signal-cli --versionЯкщо ви використовуєте збірку JVM (signal-cli-${VERSION}.tar.gz), спочатку встановіть JRE. Регулярно оновлюйте signal-cli: розробники зазначають, що старі випуски можуть перестати працювати через зміни серверних API Signal.
- Зареєструйте та підтвердьте номер:
signal-cli -a +<BOT_PHONE_NUMBER> registerЯкщо потрібна captcha (для виконання цього кроку необхідний доступ до браузера):
- Відкрийте
https://signalcaptchas.org/registration/generate.html. - Пройдіть captcha та скопіюйте цільове посилання
signalcaptcha://...з "Open Signal". - За можливості запускайте команду з тієї самої зовнішньої IP-адреси, що й сеанс браузера (строк дії токенів captcha швидко спливає).
- Негайно зареєструйте та підтвердьте номер:
signal-cli -a +<BOT_PHONE_NUMBER> register --captcha '<SIGNALCAPTCHA_URL>'signal-cli -a +<BOT_PHONE_NUMBER> verify <VERIFICATION_CODE>- Налаштуйте OpenClaw, перезапустіть Gateway і перевірте канал:
# Якщо Gateway запущено як користувацьку службу systemd:systemctl --user restart openclaw-gateway.service # Потім виконайте перевірку:openclaw doctoropenclaw channels status --probe- Створіть пару з відправником приватних повідомлень:
- Надішліть будь-яке повідомлення на номер бота.
- Схваліть на сервері:
openclaw pairing approve signal <PAIRING_CODE>. - Збережіть номер бота як контакт у телефоні, щоб уникнути позначки "Unknown contact".
Посилання на першоджерела:
- README
signal-cli:https://github.com/AsamK/signal-cli - Процес captcha:
https://github.com/AsamK/signal-cli/wiki/Registration-with-captcha - Процес прив’язування:
https://github.com/AsamK/signal-cli/wiki/Linking-other-devices-(Provisioning)
Режим зовнішнього демона (httpUrl)
Щоб самостійно керувати signal-cli (повільний холодний запуск JVM, ініціалізація контейнера, спільні ресурси процесора), запустіть демон окремо та спрямуйте OpenClaw до нього:
{ channels: { signal: { httpUrl: "http://127.0.0.1:8080", autoStart: false, }, },}У цьому разі автоматичний запуск і очікування OpenClaw під час запуску пропускаються. Для повільного автоматичного запуску задайте channels.signal.startupTimeoutMs.
Режим контейнера (bbernhard/signal-cli-rest-api)
Замість нативного запуску signal-cli використовуйте Docker-контейнер bbernhard/signal-cli-rest-api, який надає доступ до signal-cli через інтерфейс REST + WebSocket.
Вимоги:
- Для отримання повідомлень у реальному часі контейнер має працювати з
MODE=json-rpc. - Зареєструйте або прив’яжіть свій обліковий запис Signal усередині контейнера, перш ніж підключати OpenClaw.
Приклад служби docker-compose.yml:
signal-cli: image: bbernhard/signal-cli-rest-api:latest environment: MODE: json-rpc ports: - "8080:8080" volumes: - signal-cli-data:/home/.local/share/signal-cliКонфігурація OpenClaw:
{ channels: { signal: { enabled: true, account: "+15551234567", httpUrl: "http://signal-cli:8080", autoStart: false, apiMode: "container", // або "auto" для автоматичного визначення }, },}apiMode визначає, який протокол використовує OpenClaw:
| Значення | Поведінка |
|---|---|
"auto" |
(За замовчуванням) Перевіряє обидва транспорти; потоковий режим перевіряє отримання через WebSocket контейнера |
"native" |
Примусово використовує нативний signal-cli (JSON-RPC на /api/v1/rpc, SSE на /api/v1/events) |
"container" |
Примусово використовує контейнер bbernhard (REST на /v2/send, WebSocket на /v1/receive/{account}) |
Коли apiMode має значення "auto", OpenClaw кешує визначений режим на 30 секунд для кожної URL-адреси демона, щоб уникнути повторних перевірок (нативний режим має пріоритет, якщо обидва транспорти справні). Отримання через контейнер вибирається для потокового режиму лише після оновлення з’єднання /v1/receive/{account} до WebSocket, для чого потрібно MODE=json-rpc.
Режим контейнера підтримує ті самі операції Signal, що й нативний режим, якщо контейнер надає відповідні API: надсилання, отримання, вкладення, індикатори набору тексту, підтвердження прочитання та перегляду, реакції, групи й форматований текст. OpenClaw перетворює нативні RPC-виклики Signal на корисні навантаження REST контейнера, зокрема ідентифікатори груп group.{base64(internal_id)} і text_mode: "styled" для форматованого тексту.
Примітки щодо експлуатації:
- Використовуйте
autoStart: falseу режимі контейнера; OpenClaw не повинен запускати нативний демон, коли вибраноapiMode: "container". - Для отримання повідомлень використовуйте
MODE=json-rpc. ЗаMODE=normalендпоінт/v1/aboutможе виглядати справним, але/v1/receive/{account}не оновить з’єднання до WebSocket, тому OpenClaw не вибере потокове отримання через контейнер у режиміauto. - Установіть
apiMode: "container", колиhttpUrlвказує на REST API bbernhard,"native"— коли він вказує на JSON-RPC/SSE нативногоsignal-cli, і"auto"— коли розгортання може відрізнятися. - Завантаження вкладень у режимі контейнера підпорядковується тим самим обмеженням розміру медіаданих у байтах, що й нативний режим. Завеликі відповіді відхиляються до повної буферизації, якщо сервер надсилає
Content-Length, а в інших випадках — під час потокового передавання.
Керування доступом (приватні повідомлення та групи)
Приватні повідомлення:
- За замовчуванням:
channels.signal.dmPolicy = "pairing". - Невідомі відправники отримують код створення пари; повідомлення ігноруються до схвалення (строк дії кодів спливає через 1 годину).
- Схвалюйте за допомогою
openclaw pairing list signalіopenclaw pairing approve signal <CODE>. - Створення пари — стандартний обмін токенами для приватних повідомлень Signal. Докладніше: Створення пари
- Відправники лише з UUID (із
sourceUuid) зберігаються якuuid:<id>уchannels.signal.allowFrom.
Групи:
channels.signal.groupPolicy = open | allowlist | disabled.channels.signal.groupAllowFromвизначає, які групи або відправники можуть ініціювати відповіді в групах, коли встановленоallowlist; значеннями можуть бути ідентифікатори груп Signal (необроблені,group:<id>абоsignal:group:<id>), номери телефонів відправників, значенняuuid:<id>або*.channels.signal.groups["<group-id>" | "*"]може перевизначати поведінку групи за допомогоюrequireMention,toolsіtoolsBySender.- Використовуйте
channels.signal.accounts.<id>.groupsдля перевизначень на рівні облікового запису в конфігураціях із кількома обліковими записами. - Додавання групи до списку дозволених через
groupAllowFromсаме по собі не вимикає вимогу згадування. Явно налаштований записchannels.signal.groups["<group-id>"]обробляє кожне повідомлення групи, якщо явно не встановленоrequireMention: true. - Примітка щодо виконання: якщо
channels.signalповністю відсутній, середовище виконання використовує резервне значенняgroupPolicy="allowlist"для перевірок груп (навіть якщо встановленоchannels.defaults.groupPolicy).
Як це працює (поведінка)
- Нативний режим:
signal-cliпрацює як демон; Gateway читає події через SSE. - Режим контейнера: Gateway надсилає дані через REST API та отримує їх через WebSocket.
- Вхідні повідомлення нормалізуються у спільний конверт каналу.
- Відповіді завжди маршрутизуються назад до того самого номера або групи.
- Відповіді на вхідні повідомлення містять нативні метадані цитування Signal, якщо серверна частина приймає позначку часу та автора вхідного повідомлення; якщо метадані цитування відсутні або відхилені, OpenClaw надсилає відповідь як звичайне повідомлення.
- Налаштуйте використання нативного цитування через
channels.signal.replyToMode = off | first | all | batchedабоchannels.signal.replyToModeByChatType.direct/groupдля перевизначень за типом чату. Значення на рівні облікового запису вchannels.signal.accounts.<id>мають пріоритет.
Медіафайли та обмеження
- Вихідний текст розбивається на фрагменти відповідно до
channels.signal.textChunkLimit(типове значення — 4000). - Необов’язкове розбиття за новими рядками: установіть
channels.signal.chunkMode="newline", щоб перед розбиттям за довжиною розділяти текст за порожніми рядками (межами абзаців). - Вкладення підтримуються (отримуються з
signal-cliу форматі base64). - Для вкладень із голосовими повідомленнями використовується ім’я файлу від
signal-cliяк резервне джерело MIME-типу, якщоcontentTypeвідсутній, тому транскрибування аудіо все одно може розпізнати голосові нотатки AAC. - Типове обмеження медіафайлів:
channels.signal.mediaMaxMb(типове значення — 8). - Використовуйте
channels.signal.ignoreAttachments, щоб не завантажувати медіафайли. - Контекст історії групи використовує
channels.signal.historyLimit(абоchannels.signal.accounts.*.historyLimit) із резервним переходом доmessages.groupChat.historyLimit. Установіть0, щоб вимкнути цю функцію (типове значення — 50).
Індикатори введення та сповіщення про прочитання
- Індикатори введення: OpenClaw надсилає сигнали введення через
signal-cli sendTypingі поновлює їх, поки формується відповідь. - Сповіщення про прочитання: коли
channels.signal.sendReadReceiptsмає значення true, OpenClaw пересилає сповіщення про прочитання для дозволених приватних повідомлень. signal-cliне надає сповіщень про прочитання для груп.
Реакції стану життєвого циклу
Установіть messages.statusReactions.enabled: true, щоб Signal показував спільний життєвий цикл реакцій «у черзі»/«обмірковування»/«інструмент»/Compaction/«завершено»/«помилка» для вхідних звернень. Signal використовує часову позначку вхідного повідомлення як ціль реакції; групові реакції надсилаються з ідентифікатором групи Signal, а автором цілі вказується початковий відправник.
Для реакцій стану також потрібна реакція-підтвердження та відповідне значення messages.ackReactionScope (direct, group-all, group-mentions або all). Установіть channels.signal.reactionLevel: "off", щоб вимкнути реакції стану Signal.
messages.removeAckAfterReply: true видаляє остаточну реакцію стану після налаштованого часу утримання. Інакше Signal відновлює початкову реакцію-підтвердження після остаточного стану завершення або помилки.
Реакції (інструмент повідомлень)
Використовуйте message action=react із channel=signal.
- Цілі: E.164 або UUID відправника (використовуйте
uuid:<id>із результату сполучення; також працює UUID без префікса). messageId— це часова позначка Signal для повідомлення, на яке ви реагуєте.- Для групових реакцій потрібен
targetAuthorабоtargetAuthorUuid.
message action=react channel=signal target=uuid:123e4567-e89b-12d3-a456-426614174000 messageId=1737630212345 emoji=🔥message action=react channel=signal target=+15551234567 messageId=1737630212345 emoji=🔥 remove=truemessage action=react channel=signal target=signal:group:<groupId> targetAuthor=uuid:<sender-uuid> messageId=1737630212345 emoji=✅Конфігурація:
channels.signal.actions.reactions: увімкнути або вимкнути дії з реакціями (типове значення — true).channels.signal.reactionLevel:off | ack | minimal | extensive(типове значення —minimal).off/ackвимикає реакції агента (інструмент повідомленьreactповертає помилки).minimal/extensiveвмикає реакції агента та задає рівень рекомендацій.
- Перевизначення для окремих облікових записів:
channels.signal.accounts.<id>.actions.reactions,channels.signal.accounts.<id>.reactionLevel.
Реакції схвалення
Запити на схвалення виконання команд і плагінів у Signal використовують блоки маршрутизації верхнього рівня approvals.exec і approvals.plugin. У Signal немає блоку channels.signal.execApprovals.
👍схвалює один раз.👎відхиляє.- Використовуйте
/approve <id> allow-always, якщо запит передбачає постійне схвалення.
Обробка реакцій схвалення потребує явно вказаних осіб, уповноважених схвалювати в Signal, у channels.signal.allowFrom, channels.signal.defaultTo або у відповідних полях рівня облікового запису. Прямі запити на схвалення виконання команд у тому самому чаті можуть і без явно вказаних уповноважених осіб приховувати дубльований локальний резервний варіант /approve; для групових схвалень без уповноважених осіб локальний резервний варіант залишається видимим.
Цілі доставки (CLI/Cron)
- Приватні повідомлення:
signal:+15551234567(або звичайний номер E.164). - Приватні повідомлення за UUID:
uuid:<id>(або UUID без префікса). - Групи:
signal:group:<groupId>. - Імена користувачів:
username:<name>(якщо підтримується вашим обліковим записом Signal).
Псевдоніми
Налаштуйте псевдоніми для сталих назв цілей Signal, які використовуються повторно. Псевдоніми існують лише в конфігурації OpenClaw; вони не створюють і не редагують контакти Signal.
{ channels: { signal: { aliases: { me: "+15557654321", jane: "uuid:123e4567-e89b-12d3-a456-426614174000", ops: "group:<groupId>", }, defaultTo: "signal:me", }, },}Використовуйте псевдоніми всюди, де приймаються цілі доставки Signal:
openclaw message send --channel signal --target signal:ops --message "Deployment is complete"Псевдоніми окремого облікового запису успадковують псевдоніми верхнього рівня та можуть додавати або перевизначати назви:
{ channels: { signal: { aliases: { me: "+15557654321", }, accounts: { work: { aliases: { ops: "group:<workGroupId>", }, }, }, }, },}openclaw directory peers list --channel signal і openclaw directory groups list --channel signal виводять налаштовані псевдоніми. Каталог Signal базується на конфігурації; він не опитує контакти Signal у реальному часі та не змінює обліковий запис Signal.
Усунення несправностей
Спочатку виконайте цю послідовність:
openclaw statusopenclaw gateway statusopenclaw logs --followopenclaw doctoropenclaw channels status --probeПотім за потреби перевірте стан сполучення приватних повідомлень:
openclaw pairing list signalПоширені помилки:
- Демон доступний, але відповідей немає: перевірте налаштування облікового запису та демона (
httpUrl,account), а також режим отримання. - Приватні повідомлення ігноруються: відправник очікує схвалення сполучення.
- Групові повідомлення ігноруються: обмеження за відправником або згадкою в групі блокують доставку.
- Помилки перевірки конфігурації після редагування: виконайте
openclaw doctor --fix. - Signal відсутній у діагностиці: переконайтеся, що встановлено
channels.signal.enabled: true.
Додаткові перевірки:
openclaw pairing list signalpgrep -af signal-cligrep -i "signal" "/tmp/openclaw/openclaw-$(date +%Y-%m-%d).log" | tail -20Процес діагностики описано в розділі Усунення несправностей каналів.
Примітки щодо безпеки
signal-cliзберігає ключі облікового запису локально (зазвичай у~/.local/share/signal-cli/data/).- Перед міграцією або повторним розгортанням сервера створіть резервну копію стану облікового запису Signal.
- Залишайте
channels.signal.dmPolicy: "pairing", якщо вам явно не потрібен ширший доступ до приватних повідомлень. - SMS-перевірка потрібна лише для реєстрації або відновлення, але втрата контролю над номером чи обліковим записом може ускладнити повторну реєстрацію.
Довідник із конфігурації (Signal)
Повна конфігурація: Конфігурація
Параметри постачальника:
channels.signal.enabled: увімкнути або вимкнути запуск каналу.channels.signal.apiMode:auto | native | container(типове значення — auto). Див. Контейнерний режим.channels.signal.account: номер E.164 облікового запису бота.channels.signal.cliPath: шлях доsignal-cli.channels.signal.configPath: необов’язковий каталогsignal-cli --config.channels.signal.httpUrl: повна URL-адреса демона (перевизначає хост і порт).channels.signal.httpHost,channels.signal.httpPort: прив’язка демона (типове значення —127.0.0.1:8080).channels.signal.autoStart: автоматично запускати демон (типове значення — true, якщоhttpUrlне задано).channels.signal.startupTimeoutMs: граничний час очікування запуску в мс (мінімум 1000, максимум 120000; типове значення — 30000).channels.signal.receiveMode:on-start | manual.channels.signal.ignoreAttachments: не завантажувати вкладення.channels.signal.ignoreStories: ігнорувати історії від демона.channels.signal.sendReadReceipts: пересилати сповіщення про прочитання.channels.signal.dmPolicy:pairing | allowlist | open | disabled(типове значення — pairing).channels.signal.allowFrom: список дозволених відправників приватних повідомлень (E.164 абоuuid:<id>). Дляopenпотрібно"*". Signal не має імен користувачів; використовуйте ідентифікатори телефону або UUID.channels.signal.aliases: псевдоніми OpenClaw для цілей доставки приватних або групових повідомлень.channels.signal.groupPolicy:open | allowlist | disabled(типове значення — allowlist).channels.signal.groupAllowFrom: список дозволених для груп; приймає ідентифікатори груп Signal (без префікса,group:<id>абоsignal:group:<id>), номери E.164 відправників або значенняuuid:<id>.channels.signal.groups: перевизначення для окремих груп, ключами яких є ідентифікатори груп Signal (або"*"). Підтримувані поля:requireMention,tools,toolsBySender.channels.signal.accounts.<id>.groups: версіяchannels.signal.groupsдля окремого облікового запису в конфігураціях із кількома обліковими записами.channels.signal.accounts.<id>.aliases: псевдоніми окремого облікового запису, об’єднані з псевдонімами верхнього рівня.channels.signal.replyToMode: режим вбудованого цитування відповіді,off | first | all | batched(типове значення —all).channels.signal.replyToModeByChatType.direct,channels.signal.replyToModeByChatType.group: перевизначення вбудованого цитування відповіді для окремих типів чатів.channels.signal.accounts.<id>.replyToMode,channels.signal.accounts.<id>.replyToModeByChatType.direct,channels.signal.accounts.<id>.replyToModeByChatType.group: перевизначення цитування відповіді для окремих облікових записів.channels.signal.historyLimit: максимальна кількість групових повідомлень, які включаються до контексту (0 вимикає).channels.signal.dmHistoryLimit: обмеження історії приватних повідомлень у зверненнях користувача. Перевизначення для окремих користувачів:channels.signal.dms["<phone_or_uuid>"].historyLimit.channels.signal.textChunkLimit: розмір вихідного фрагмента в символах (типове значення — 4000).channels.signal.chunkMode:length(типове значення) абоnewline, щоб перед розбиттям за довжиною розділяти текст за порожніми рядками (межами абзаців).channels.signal.mediaMaxMb: обмеження розміру вхідних і вихідних медіафайлів у МБ (типове значення — 8).channels.signal.reactionLevel:off | ack | minimal | extensive(типове значення —minimal). Див. Реакції.channels.signal.reactionNotifications:off | own | all | allowlist(типове значення —own) — визначає, коли агент отримує сповіщення про вхідні реакції інших користувачів.channels.signal.reactionAllowlist: відправники, реакції яких сповіщають агента, колиreactionNotifications: "allowlist".channels.signal.blockStreaming,channels.signal.blockStreamingCoalesce: спільні для каналів засоби керування потоковою передачею в блоковому режимі. Див. Потокова передача.
Пов’язані глобальні параметри:
agents.list[].groupChat.mentionPatterns(Signal не підтримує вбудовані згадки).messages.groupChat.mentionPatterns(глобальний резервний варіант).messages.responsePrefix.
Пов’язані матеріали
- Огляд каналів — усі підтримувані канали
- Сполучення — автентифікація приватних повідомлень і процес сполучення
- Групи — поведінка групових чатів і обмеження за згадками
- Маршрутизація каналів — маршрутизація сеансів для повідомлень
- Безпека — модель доступу та посилення захисту