Kommo + Customer.io: триггерные email-последовательности из воронки продаж
Customer.io — платформа поведенческого email-маркетинга с Track API на Basic Auth. Без интеграции с Kommo маркетолог вручную добавляет контакты в Customer.io, менеджер не знает, открыл ли клиент письмо перед звонком, а отписка клиента не обновляет поля в CRM. С интеграцией смена этапа воронки в Kommo запускает Customer.io-кампанию автоматически — и каждое взаимодействие с письмом отражается в таймлайне сделки.
Что даёт связка Kommo + Customer.io
Без интеграции:
— Маркетолог ведёт список Customer.io вручную — с задержкой 1–3 дня от смены статуса в CRM
— Менеджер не знает, получил ли клиент welcome-письмо перед первым звонком
— Клиент отписался в Customer.io -> Kommo об этом не знает, менеджер снова пишет
— Email-последовательности и CRM-пайплайн живут в разных системах без связи
С интеграцией:
— Won в Kommo -> Customer.io: identify + событие deal_won -> onboarding-кампания запущена
— email.opened -> Note в Kommo: «Клиент открыл письмо (тема)»
— email.clicked -> Note: «Клик по ссылке в письме»
— email.unsubscribed -> кастомное поле email_status = unsubscribed + задача менеджеру
— email.bounced -> задача проверить email контакта
Что синхронизируется
Kommo -> Customer.io:
— Email, имя, телефон контакта -> Customer profile в Customer.io
— Тариф, сегмент из кастомных полей -> Customer attributes для персонализации писем
— Смена этапа воронки -> event -> триггер кампании
— ID сделки -> Customer attribute kommo_deal_id для обратной трассировки
Customer.io -> Kommo:
— email.opened -> Note в сделку
— email.clicked -> Note со ссылкой по которой кликнул
— email.unsubscribed -> поле + задача
— email.bounced -> поле + задача на проверку email
— email.converted (если настроен goal) -> Note «Конверсия из письма»
Архитектура
Kommo Webhook: сделка перешла в этап «Онбординг»
↓ Backend
1. GET /api/v4/leads/{id} + contacts
-> email, имя, тариф из кастомных полей
2. Customer.io Track API: PUT /api/v1/customers/{email}
-> первичная идентификация с атрибутами
3. Customer.io Track API: POST /api/v1/customers/{email}/events
-> event: 'onboarding_started', properties: {plan, deal_id}
-> запускает кампанию с trigger: event = 'onboarding_started'
4. Kommo: POST /leads/{deal_id}/notes
-> «Onboarding email-кампания запущена в Customer.io»
Customer.io Reporting Webhook: email.clicked
↓ Backend
1. Из payload: customer_id (email), subject, link_url, timestamp
2. Найти deal_id по email -> kommo_deal_id в Customer.io или по контакту Kommo
3. Kommo: POST /leads/{deal_id}/notes
Customer.io Reporting Webhook: email.unsubscribed
↓ Backend
1. customer_id, timestamp
2. Найти deal_id
3. Kommo: PATCH /leads/{deal_id} -> email_status = unsubscribed
4. Kommo: POST /tasks -> «Клиент отписался - уточнить предпочтения»
Customer.io Track API: ключевые запросы
Base URL Track API: https://track.customer.io/api/v1/. Аутентификация: Basic Auth, username = site_id, password = api_key. Оба значения берутся из Customer.io: Settings -> API Credentials.
Идентификация пользователя:
import requests
from requests.auth import HTTPBasicAuth
CIO_SITE_ID = 'your_site_id'
CIO_API_KEY = 'your_api_key'
CIO_AUTH = HTTPBasicAuth(CIO_SITE_ID, CIO_API_KEY)
CIO_TRACK_URL = 'https://track.customer.io/api/v1'
def identify_customer(email: str, attributes: dict) -> None:
# Создать или обновить профиль в Customer.io
resp = requests.put(
f'{CIO_TRACK_URL}/customers/{email}',
auth=CIO_AUTH,
json=attributes
)
resp.raise_for_status()
Отправить событие:
def track_event(email: str, event_name: str, data: dict = None) -> None:
# Отправить событие для триггера кампании
resp = requests.post(
f'{CIO_TRACK_URL}/customers/{email}/events',
auth=CIO_AUTH,
json={'name': event_name, 'data': data or {}}
)
resp.raise_for_status()
def on_deal_won(lead: dict, contact: dict):
email = get_contact_email(contact)
plan = get_custom_field(lead, field_id=PLAN_FIELD_ID)
identify_customer(email, {
'first_name': contact['name'].split()[0],
'plan': plan,
'kommo_deal_id': lead['id'],
'deal_amount': lead.get('price', 0)
})
track_event(email, 'deal_won', {'plan': plan, 'deal_id': lead['id']})
Маппинг событий Kommo -> Customer.io:
STAGE_EVENT_MAP = {
'12345678': 'demo_scheduled',
'12345679': 'demo_completed',
'12345680': 'proposal_sent',
'12345681': 'deal_won',
}
def on_stage_change(lead_id: int, new_status_id: int):
event_name = STAGE_EVENT_MAP.get(str(new_status_id))
if not event_name:
return
lead = get_kommo_lead(lead_id)
contact = get_kommo_contact(lead_id)
email = get_contact_email(contact)
track_event(email, event_name, {'deal_id': lead_id})
Обработка Customer.io Reporting Webhook:
from flask import Flask, request
app = Flask(__name__)
@app.route('/webhooks/customerio', methods=['POST'])
def customerio_webhook():
payload = request.json
event_type = payload.get('event_type')
customer_id = payload.get('data', {}).get('customer_id')
deal_id = find_kommo_deal_by_email(customer_id)
if not deal_id:
return '', 200
if event_type == 'email_opened':
subject = payload.get('data', {}).get('subject', '')
create_kommo_note(deal_id, f'Customer.io: открыл письмо - {subject}')
elif event_type == 'email_clicked':
link = payload.get('data', {}).get('href', '')
subject = payload.get('data', {}).get('subject', '')
create_kommo_note(deal_id, f'Customer.io: кликнул в письме {subject} -> {link}')
elif event_type == 'email_unsubscribed':
update_kommo_deal(deal_id, {'email_status': 'unsubscribed'})
create_kommo_task(deal_id,
'Клиент отписался от рассылки Customer.io - уточнить предпочтения')
elif event_type == 'email_bounced':
bounce_type = payload.get('data', {}).get('type', '')
update_kommo_deal(deal_id, {'email_status': f'bounced_{bounce_type}'})
create_kommo_task(deal_id,
f'Email недоставлен (bounce: {bounce_type}) - проверить адрес')
return '', 200
Настройка Reporting Webhook в Customer.io: Settings -> Integrations -> Reporting Webhooks -> Add Endpoint. Выбрать события: email_opened, email_clicked, email_unsubscribed, email_bounced, email_converted. Customer.io подписывает payload через HMAC-SHA256, заголовок X-CIO-Signature для верификации.
EU-инстанс: если аккаунт на EU-серверах — Track API URL: https://track-eu.customer.io/api/v1. Проверить в настройках: Settings -> Account -> Data Region.
Персонализация писем через атрибуты Kommo
Customer.io позволяет использовать атрибуты клиента в шаблонах письма через Liquid: {{ customer.plan }}, {{ customer.first_name }}. Данные из Kommo передаются при identify_customer:
identify_customer(email, {
'first_name': 'John',
'plan': 'Pro',
'company': 'Acme Inc',
'deal_amount': 1500,
'account_manager': 'Sarah'
})
Это даёт персонализацию писем без дополнительных усилий — все переменные из CRM уже в профиле.
Реальный кейс
B2B SaaS (US, 50–70 новых клиентов в месяц, Kommo + Customer.io + Stripe, onboarding-кампания из 7 писем):
- До: маркетолог добавлял новых клиентов в Customer.io вручную раз в день по выгрузке из Kommo. Первое письмо уходило с задержкой 24–48 часов от момента Won. Отписки не попадали в CRM.
- После: Won -> Customer.io -> первое письмо за 3 минуты. Персонализация по тарифу и имени. При клике на ссылку документации — Note в Kommo, менеджер видит активность клиента.
- Дополнительно: если клиент не открыл ни одного письма за 5 дней — триггер
onboarding_inactive-> задача CSM-у на ручной аутрич.
Для кого актуально
- SaaS-компании с активным email-онбордингом (welcome-серии, обучающие кампании)
- Продажи через воронку Kommo, маркетинг через Customer.io
- Менеджер должен видеть email-активность клиента перед звонком
- 30+ новых клиентов в месяц — ручная синхронизация становится нерентабельной
Часто задаваемые вопросы
Customer.io API — Basic Auth или Bearer token?
Track API (для identify и событий) использует Basic Auth: site_id как username, api_key как password. App API (для управления кампаниями, сегментами) использует Bearer token. Для серверной интеграции с Kommo нужен Track API — Basic Auth.
Как настроить Reporting Webhook в Customer.io?
Settings -> Integrations -> Reporting Webhooks -> Add Endpoint. Указать URL вашего сервера, выбрать события. Customer.io подписывает каждый запрос через HMAC-SHA256 (X-CIO-Signature). Проверяйте подпись на сервере перед обработкой.
Customer.io vs Mailchimp для интеграции с Kommo?
Mailchimp ориентирован на списочные кампании. Customer.io — на поведенческие триггеры: событие в CRM -> кампания. Если нужен onboarding по этапам воронки, последовательности на основе действий в продукте — Customer.io. Если массовые рассылки по сегментам — Mailchimp.
Что делать если контакт уже есть в Customer.io до интеграции?
PUT /customers/{email} — idempotent: если профиль существует — обновит атрибуты, если нет — создаст. Атрибуты мерджатся, не перезаписываются полностью.
Как передавать данные из кастомных полей Kommo в Customer.io?
Через identify_customer передаётся произвольный словарь атрибутов. Для каждого нужного кастомного поля Kommo сделайте маппинг field_id -> имя атрибута Customer.io. Атрибуты сразу доступны в Liquid-шаблонах писем.
Итого
- Customer.io Track API: Basic Auth (site_id:api_key), Base URL
https://track.customer.io/api/v1/ - Identify:
PUT /customers/{email}с атрибутами из Kommo - Track event:
POST /customers/{email}/eventsпри смене этапа - Reporting Webhook:
email_opened/clicked/unsubscribed/bounced-> Notes и задачи в Kommo - EU-инстанс:
https://track-eu.customer.io/api/v1 - Типовой срок разработки — 1–2 недели
Если вы используете Customer.io и Kommo и хотите замкнуть воронку продаж с email-маркетингом — опишите ваши этапы и кампании. Exceltic.dev настроит маппинг событий и обработку отписок в CRM.