Две темы «второго уровня»: как устроен современный Jaeger v2 под капотом и как строится приём через Kafka — схема для крупных систем, где нельзя терять трейсы при сбоях.
Jaeger v2: Collector как основа
Jaeger v2 — это дистрибуция OTel Collector: стандартные компоненты OTel + компоненты
Jaeger (хранилище, query, сэмплинг). Один бинарник jaeger, конфиг — YAML в OTel-стиле:
# jaeger-v2-config.yaml (упрощённо)
extensions:
jaeger_storage:
backends:
es_default:
elasticsearch:
server_urls: http://elasticsearch:9200
index_prefix: jaeger
jaeger_query:
storage:
traces: es_default
receivers:
otlp:
protocols:
grpc: {}
http: {}
processors:
batch: {}
service:
extensions: [jaeger_storage, jaeger_query]
pipelines:
traces:
receivers: [otlp]
processors: [batch]
exporters: [jaeger_storage_exporter]
- Приём — OTLP (всё остальное — совместимость);
- Query/UI — порт 16686, как раньше;
- Любые процессоры Collector доступны в том же пайплайне: это и есть главная выгода — tail sampling, фильтры и маршрутизация «в одном флаконе» с бэкендом.
Зачем Kafka в цепочке трейсов
Прямая схема «Collector → хранилище» уязвима: остановка записи в ES/Cassandra = потеря входящих трейсов (буферы конечны). Kafka добавляет буфер с диском и развязку скоростей:
SDK ─► OTel Collector (agent) ─► Kafka topic "traces" ─► ingester ─► Jaeger storage (ES/Cassandra)
└► Jaeger query/UI
- Пик нагрузки не теряется: если хранилище отстаёт, спаны копятся в топике;
- Несколько потребителей: в Jaeger пишем, параллельно — аналитический пайплайн (spanmetrics, ML-обучение) из того же топика;
- Отказоустойчивость записи: acks/репликация Kafka дают гарантию доставки до журнала.
Как это реализовано
- Collector: exporter
kafka— пишет спаны (прототип OTLP) в топик; - v1: компонент
jaeger-ingester— читал топик и писал в хранилище; - v2: Collector-приёмник
kafkaв составе той же дистрибуции + exporter в jaeger_storage — та же схема, но единым бинарником и конфигом; - Партиционирование: по trace ID — сохраняется порядок спанов внутри трейса, нагрузка распределяется по партициям.
Цена Kafka-схемы
- Ещё один кластер в эксплуатации (если нет общего);
- Двойная запись (Kafka + хранилище) — задержка появления трейса в UI растёт (секунды);
- Настройка retention топика: должны переживать самый длинный сбой записи в хранилище.
💡 Практический порог: до ~10–20 тыс. трейсов/сек прямая схема с нормальным кластером хранилища обычно справляется. Kafka — когда объёмы больше или требование «не терять трейсы при плановых рестартах хранилища» непреложно.
Практика
- Соберите схему с Kafka в docker-compose: Collector (kafka exporter) → single-broker Kafka → Collector (kafka receiver) → Jaeger. Найдите свои трейсы в UI.
- Остановите «записывающий» Collector на 2 минуты под нагрузкой, поднимите: убедитесь, что трейсы доезжают из буфера Kafka.
- Сравните задержку появления трейса в UI: прямая схема против Kafka-схемы.
Мини-квиз
1. Что нового в архитектуре v2? — Jaeger — дистрибуция OTel Collector: единый бинарник, OTel-конфиг, OTLP как основной протокол.
2. Почему партиционирование по trace ID? — Спаны одного трейса идут в одну партицию: порядок и консистентное чтение.
3. Главная причина ставить Kafka? — Гарантированный буфер между приёмом и хранилищем + параллельные потребители.