Workflow может сам вызывать API вашей CRM. Шаг Внешний вызов отправляет запрос, а выпадающий список в форме Запросить данные берёт варианты из вашего API.
Подключение
Адрес и ключ вашего API хранятся в подключении: откройте Настройки, раздел Подключения к API. Шаг workflow ссылается на подключение и указывает только путь, поэтому ключ в workflow не попадает.
| Поле | Что задаёт |
|---|---|
| Базовый адрес | Полный адрес с http:// или https://, например https://crm.example.com/api/v1 |
| Авторизация | Один из способов ниже |
| Заголовки | До 20 заголовков, которые уходят с каждым запросом |
| Способ | Что приходит на ваш сервер |
|---|---|
| Без авторизации | Ничего |
| Bearer-токен | Authorization: Bearer <токен> |
| Логин и пароль (Basic) | Authorization: Basic <base64(логин:пароль)> |
| Ключ в заголовке | <имя заголовка>: <ключ>, имя задаётся в подключении |
Ключ хранится в зашифрованном виде. При редактировании подключения поле ключа пустое.
Путь шага добавляется к базовому адресу. Если путь выходит за базовый адрес (../, //host,
полный адрес с другим доменом), запрос не уходит. Адрес с логином и паролем
(https://user:pass@…) тоже отклоняется.
Шаг можно настроить и без подключения, с полным адресом. Тогда авторизацию задайте заголовком в самом шаге.
Запрос
Метод и адрес
Методы: GET, POST, PUT, PATCH, DELETE. У GET и DELETE тела нет.
В пути и в поле Параметры адреса можно использовать переменные: /accounts/$contact.custom.crm_id.
Значения кодируются для адреса. Если у переменной нет значения, в адресе остаётся её имя,
например $contact.custom.crm_id.
Заголовки
| Заголовок | Когда есть |
|---|---|
| Заголовки подключения | Всегда |
| Заголовки шага | Если заданы в шаге. Значения могут содержать переменные. Одноимённый заголовок шага заменяет заголовок подключения |
| Авторизация | Если у подключения есть ключ. Заменяет одноимённый заголовок из настроек |
Idempotency-Key |
Всегда, если шаг не задал свой заголовок с этим именем. Значение описано в разделе Повторы и Idempotency-Key |
Accept: application/json, text/plain, */* |
Если шаг не задал свой Accept |
Content-Type |
Если есть тело и шаг не задал свой. Значение зависит от вида тела |
Content-Length |
Если есть тело |
Polygram не задаёт User-Agent.
Чтобы CRM знала, какой сотрудник запустил workflow, добавьте в шаг заголовок со значением
$me.id, например X-Snippex-User-Id: $me.id. Доступны также $me.name и $me.email.
Если workflow запущен без сотрудника, например входящим сообщением, в заголовке останется
текст $me.id.
Заголовок, в значении которого есть перевод строки, отклоняется до отправки.
Тело
| Вид тела в шаге | Content-Type |
Что приходит |
|---|---|---|
| Поля | application/json |
JSON-объект из полей, см. ниже |
| Вручную (JSON) | application/json |
JSON, который написал автор workflow. Значения переменных экранируются для JSON |
| Форма | application/x-www-form-urlencoded |
a=1&b=2, значения кодируются для адреса |
| Текст | text/plain; charset=utf-8 |
Текст как есть |
| Без тела | нет | Тела нет |
Вид Поля собирает JSON из пар имя и значение:
- имя через точку создаёт вложенный объект: из
client.phoneполучится{"client": {"phone": "…"}}; - тип поля определяет JSON-тип значения.
| Тип | JSON | Правило |
|---|---|---|
| Текст | строка | Значение как есть |
| Число | число | Пробелы убираются, запятая считается точкой: из 1 500,5 получится 1500.5. Пустое значение даёт null. Если значение не число, запрос не уходит |
| Да/нет | true / false |
true, 1, да, yes дают true. false, 0, нет, no и пустое значение дают false. С другим значением запрос не уходит |
| Как есть | любой | Значение разбирается как JSON. Если значение состоит из одной переменной ($vars.order), уходит её значение, и объект остаётся объектом |
Переменная без значения даёт в поле null.
Пример. Поля шага:
| Имя | Значение | Тип |
|---|---|---|
login |
$vars.login |
Текст |
client.name |
$contact.name |
Текст |
client.phone |
$contact.phone |
Текст |
tariff_id |
$vars.tariff |
Число |
trial |
да |
Да/нет |
Тело запроса:
{
"login": "ivan.petrov",
"client": { "name": "Иван Петров", "phone": "+7 700 000 00 00" },
"tariff_id": 3,
"trial": true
}
Таймауты и размер ответа
- Polygram ждёт ответа 15 секунд. Автор workflow может поставить от 1 до 60 секунд в поле Ждать ответа, сек в разделе Надёжность.
- Варианты для выпадающего списка Polygram ждёт 10 секунд и не повторяет запрос.
- Ответ больше 1 МБ Polygram обрывает и считает ошибкой. Такой запрос не повторяется.
Повторы и Idempotency-Key
Polygram повторяет запрос, если:
- ответа нет из-за сетевой ошибки или вышло время ожидания;
- пришёл ответ
429; - пришёл ответ
500или выше.
Остальные коды, в том числе 4xx и 3xx, не повторяются.
По умолчанию Polygram делает 2 повтора: всего до 3 запросов. Автор workflow может
поставить от 0 до 3 в поле Повторов при сбое в разделе Надёжность. Перед повторами
Polygram ждёт 1, 3 и 9 секунд. Если в ответе 429 или 5xx есть заголовок Retry-After
в секундах, пауза берётся из него, но не больше 10 секунд. Дату в Retry-After Polygram не учитывает.
Если время ожидания вышло, ваш сервер мог уже обработать запрос. Повтор придёт с тем же
Idempotency-Key. Проверяйте этот заголовок и на повтор возвращайте результат первого запроса,
тогда запись не создастся дважды.
| Откуда запрос | Idempotency-Key |
|---|---|
| Шаг с включённым Выполнять один раз | Ключ операции после подстановки переменных, например crm_account:9b1c… |
| Обычный шаг | <id запуска>:<id шага>. Ключ тот же, если упавший запуск повторили из журнала |
| Кнопка Пробный запрос в редакторе | test:<время в миллисекундах>, каждый раз новый |
| Варианты выпадающего списка | form-options:<id формы>:<ключ поля> |
У однократной операции ключ не меняется и после ошибки: следующий запуск придёт с тем же
Idempotency-Key. Если вы запоминаете ответы по этому ключу, не запоминайте ответы с ошибкой,
иначе повтор получит ту же ошибку.
Пробный запрос в редакторе workflow отправляет на ваш сервер настоящий запрос, один раз и без повторов. В карточку клиента он ничего не пишет.
Редиректы
Polygram не переходит по редиректам и считает ответ 3xx ошибкой шага. Указывайте в подключении
адрес, который отвечает сразу.
Адреса внутренней сети
Polygram отправляет запрос только на публичный адрес. Перед отправкой он узнаёт IP домена и не отправляет запрос, если это:
localhost;- адреса
10.0.0.0/8,127.0.0.0/8,172.16.0.0/12,192.168.0.0/16,169.254.0.0/16,100.64.0.0/10,0.0.0.0/8,192.0.0.0/16,198.18.0.0/15,224.0.0.0и выше; - IPv6
::,::1, адреса наfcиfd, адреса отfe8доfef.
Соединение идёт на тот IP, который Polygram проверил. Такой запрос не повторяется.
Поддерживаются только http и https.
Успех и ошибка
Успехом считается ответ с кодом 2xx. Всё остальное считается ошибкой: другой код, отсутствие
ответа, запрос, который не удалось собрать.
Тело ответа разбирается как JSON, если в Content-Type есть json или тело начинается
с { или [. Иначе оно остаётся текстом. Что Polygram сохраняет из ответа, описано
в статье Ответы: что Polygram сохраняет.
У шага три выхода:
| Выход | Когда |
|---|---|
| Успех | Ответ 2xx |
| Ошибка | Ответ не 2xx или ответа нет |
| Уже выполнено | Однократная операция уже была, запрос не отправлялся |
Если к выходу Ошибка ничего не подключено, workflow на ошибке останавливается.
Как отдать ошибку, чтобы её понял сотрудник
При ошибке Polygram пишет в переменную $vars.http_error текст:
Внешний сервис ответил <код>: <тело ответа>
Тело берётся как есть, первые 500 символов, JSON не разбирается. Например, ответ
{"error":"Логин занят"} даст текст Внешний сервис ответил 409: {"error":"Логин занят"}.
Если ответа нет, в переменной будет описание сбоя, например Нет ответа за 15 с.
Сотрудник видит этот текст:
- в уведомлении, если автор workflow вставил
$vars.http_errorв шаг Уведомить сотрудника на выходе Ошибка; - в ленте диалога, если выход Ошибка не подключён и workflow остановился. В ленте будет
Workflow «…» не выполнен — <текст>, первые 300 символов; - в окне шага Показать сотруднику, если workflow остановился до него.
Поэтому на ошибку отвечайте кодом 4xx и короткой понятной сотруднику фразой на русском,
например с Content-Type: text/plain:
HTTP/1.1 409 Conflict
Content-Type: text/plain; charset=utf-8
Логин ivan.petrov уже занят
Код последнего ответа хранится в $vars.http_status, по нему workflow может ветвиться.
После успешного ответа $vars.http_error пуст.
Однократные операции
Шаг с включённым Выполнять один раз отправляет запрос один раз на каждый ключ операции.
Ключ задаётся шаблоном с переменными, например crm_account:$contact.id, и для одного клиента
он одинаковый во всех запусках.
- Перед запросом Polygram отмечает операцию как начатую. Если второй запуск с тем же ключом начнётся, пока первый не закончился, он не отправит запрос и пойдёт по выходу Ошибка.
- Выполненной операция считается только после успеха. После ошибки следующий запуск отправит
запрос снова, с тем же
Idempotency-Key. - Если операция уже выполнена, запрос не уходит, и workflow идёт по выходу Уже выполнено,
а если он не подключён, по выходу Успех. Переменные
$vars, сохранённые из первого ответа, восстанавливаются. - Если ключ не собрался из-за переменной без значения, запрос не уходит, и workflow идёт по выходу Ошибка.
Сотрудник сбрасывает отметку в карточке клиента, раздел Внешние операции. После сброса workflow выполнит операцию заново.
Если ваш сервер принял запрос, а ответ до Polygram не дошёл, операция остаётся начатой.
Следующий запуск получит ошибку Операция с этим ключом уже выполняется…. Проверьте результат
у себя и попросите сотрудника сбросить операцию.
Журнал
Каждый запрос и ответ записываются в журнал запуска workflow. Журнал видят сотрудники
с доступом к workflow. Значения заголовков Authorization, Cookie, X-…-Key, X-…-Token
заменяются на ***. Тело запроса в журнале обрезается до 2000 символов, тело ответа до 4000.