Этот сценарий отправляет карточку контакта WhatsApp с sendContact в 24-часовое окно обслуживания после назначения водителя или курьера на заказ.
Пример шаблона
Контакт курьера для этой доставки указан в карточке ниже.
Когда использовать
Применяйте этот сценарий, когда логистика назначает водителя или курьера для активной доставки, а покупателю нужен номер телефона этого человека без необходимости копировать цифры из текстового ответа. Это подходит для команд, занимающихся доставкой на последнем этапе, которые обмениваются контактами с функцией «нажми и сохрани» в активной сессии заказа, и операторов автопарка, передающих назначенного курьера, чтобы клиент мог напрямую позвонить через WhatsApp.
Меньше ошибок при наборе номера
sendContact отправляет vCard с именем курьера и номером телефона в формате E.164, чтобы клиент мог нажать и сохранить или позвонить, вместо того чтобы набирать цифры, которые часто вводятся неправильно в чате.
Меньше повторных обращений с вопросом «номер водителя?»
Вводная строка и контактная карточка приходят в той же открытой сессии WhatsApp, что и заказ, поэтому покупатель получает прямой доступ к телефону без открытия электронной почты или повторного звонка в службу поддержки.
Не передавайте код вручную
Когда логистика назначает курьера, ваш бэкенд загружает отображаемое имя и телефон из контракта интеграции, и sendContact запускается автоматически в активной сессии.
Контакт остаётся в теме заказа
Тело короткого сообщения указывает на карту ниже, поэтому данные о курьере остаются в чате доставки, который клиент уже использует, вместо отдельной SMS или переписки по email.
Как это работает
Триггер
Логистика назначает водителя или курьера для доставки.
event · triggered
Событие захвата
Ваш сервер загружает имя и номер телефона курьера.
phone: "+…"
Собрать и отправить
sendContact отправляет визитку в активную сессию.
POST/send_contact
Доставлено
Клиент сохраняет курьера или вызывает его через WhatsApp.
#!/usr/bin/env bash
set -euo pipefail
# === Configuration (replace "___" placeholders) ===
API_BASE_URL="https://api.1msg.io" # production 1MSG API base URL
CHANNEL_ID="___" # channel ID from 1MSG dashboard
API_TOKEN="___" # channel JWT token (Bearer)
# === Test data ===
TEST_PHONE="___" # client phone in international format
PHONE_NORM="$(printf '%s' "$TEST_PHONE" | tr -cd '0-9')"
URL="${API_BASE_URL%/}/${CHANNEL_ID}/sendContact"
# specialist display name (code_contract)
# specialist phone in E.164 format
read -r -d '' PAYLOAD <<JSON || true
{
"phone": "${PHONE_NORM}",
"contacts": [
{
"name": { "formatted_name": "Иван Курьер", "first_name": "Иван Курьер" },
"phones": [{ "phone": "+998901234567", "type": "CELL" }]
}
]
}
JSON
RESPONSE="$(curl -s -w '\n%{http_code}' -X POST "$URL" \
-H "Content-Type: application/json" \
-H "Authorization: Bearer ${API_TOKEN}" \
-d "$PAYLOAD")"
HTTP_CODE="$(printf '%s' "$RESPONSE" | tail -n1)"
BODY="$(printf '%s' "$RESPONSE" | sed '$d')"
case "$BODY" in
*'"sent":true'*) ok=1 ;;
*) ok=0 ;;
esac
if [ "$HTTP_CODE" -ge 200 ] && [ "$HTTP_CODE" -lt 300 ] && [ "$ok" -eq 1 ]; then
echo "Message sent to client."
else
echo "$BODY" >&2
exit 1
fi
Статус ответа и доставки
HTTP 2xx и JSON "sent": true означают, что 1MSG принял сообщение для отправки — это не значит, что оно уже достигло телефона клиента. Сохраните id поле (выглядит как wamid.…), чтобы сопоставлять уведомления о доставке.
Принято для отправки — ещёне доставлено на телефон клиента
id
Храните это. Обратные вызовы доставки и hookInfo привязаны к этому ключу
Delivery itself arrives later, as a separate callback. Register a webhook (POST …/webhook) and 1MSG POSTs status updates to your HTTPS endpoint in a top-level hooks[] payload.
200 OKВебхук статуса доставки — данные, которые вы получаете
sent, delivered, read — или статус ошибки, если подходит
id
Соотносит обратный вызов с idвозвращаемым значением вызова send
timestamp
Секунды Unix как строка
Если вы предпочитаете не получать обратные вызовы, GET {base}/{channel}/hookInfo?messageId=<id>вместо этого используйте опрос. На практике доставка часто завершается в считанные секунды — но контракт API этого не гарантирует, поэтому никогда не блокируйте поток в ожидании этого.
Распространённые ошибки
Статус
Ответ
Причина
200
Message was not sent: empty body
No body in the request.
200
Message was not sent: provide chatId, phone, bsuid, or username
No recipient the channel could resolve.
200
wrong file
The media could not be fetched or uploaded — not a reachable URL, not valid base64.
403
access denied
The token is wrong, or belongs to a different channel than the URL.
200
Message was not sent: filename
sendFile called without a filename, so the media has no extension to send.
ЧАСТО ЗАДАВАЕМЫЕ ВОПРОСЫ (FAQ)
Нет — в этом случае используется сеансовое сообщение в рамках 24-часового окна для общения с клиентом.