Контроль отправки¶
media.push.supervisor
Sapsan может активно отправлять поток дальше: на CDN и стриминговые площадки по RTMP, на другой сервер по SRT или RIST, в сеть по UDP (мультикаст/юникаст). У потока может быть несколько пушей одновременно.
Переподключение¶
Собственной политики повторов у пушера нет — его переподнимает стрим. Раз в пять секунд стрим сверяет работающие отправки с конфигурацией и заменяет умершего пушера новым; счётчик reconnects считает именно такие замены. Поэтому отправка на недоступный адресат не «сдаётся» и не требует ручного перезапуска: она будет подниматься, пока пуш включён.
Что реконнектом не считается:
- правка настройки пуша — пушер тоже перезапускается, но это решение оператора, а не отказ канала;
- выключение и включение (
enabled: false) — выключение не удаление: настройка и накопленные счётчики остаются, отправки нет.
Выключение и удаление¶
Выключенный пуш остаётся в конфигурации со своим именем: статистика показывает его со статусом «выключен», счётчики заморожены на последних значениях, включение продолжает счёт с них же. Удаление ключа удаляет и статистику: счётчики привязаны к имени.
Мониторинг¶
У каждого пуша своя статистика — адресат, статус, причина отказа, скорость, байты, ошибки, реконнекты. Разбор полей, серии Prometheus и рецепты алертинга — на странице Статистика.
Что дальше¶
Статистика пушей¶
Отправка наружу считается отдельно от приёма и по каждому пушу: ключ статистики — пара «имя стрима, имя пуша», та же, что и в конфигурации. Один стрим может уходить на пять адресатов, и «стрим отдаёт 40 Мбит/с» не отвечает на вопрос, доходит ли он до конкретного из них.
Опция «статистика пушей»
Витрина пушей — отдельная лицензионная опция. Она режет только каналы отдачи: секцию pushes и плоские push_* в Admin API, серии stream_push_* в скрейпе ноды и во встроенном Prometheus-сервере. Сам сбор не останавливается, и в телеметрию Retroview счётчики уходят всегда — разбор в Retroview доступен и без опции.
Секция pushes¶
GET /streamer/api-v4/streams/stats/{name} (и элемент списка GET /streamer/api-v4/streams/stats) несёт объект по имени пуша:
"pushes": {
"cdn-main": {
"status": "running",
"proto": "udp",
"url": "udp://127.0.0.1:5500",
"opened_at": "2026-08-13T11:17:53Z",
"bitrate_kbit": 2113.4,
"bytes_total": 19053048,
"datagrams_total": 14478
},
"youtube": {
"status": "error",
"proto": "rtmp",
"url": "rtmp://198.51.100.7/live/secret-key",
"error": "rtmp connect failed: timeout after 5s",
"reconnects_total": 22
},
"backup-dc": {"status": "disabled", "proto": "srt", "url": "srt://203.0.113.10:9000"}
}
| Поле | Что означает | Как использовать |
|---|---|---|
status |
running, error или disabled |
не running дольше N минут — алерт; disabled штатен, это выключенный оператором пуш |
error |
причина статуса error |
первое, что читать при разборе: «connect failed», отказ публикации, отказ рукопожатия |
proto, url |
транспорт и адресат в том виде, как их задал оператор | видно, куда именно уходит поток |
opened_at |
момент старта текущего пушера | молодеет на каждом реконнекте — канал флапает |
bitrate_kbit |
измеренная скорость отправки | заметно ниже битрейта стрима — отправка не успевает |
errors_rate |
ошибки отправки в секунду | растёт при живом соединении — приёмник или канал деградируют |
bytes_total |
отправлено байт нарастающим итогом | сверка объёма отдачи по направлениям |
errors_total |
ошибки отправки нарастающим итогом | — |
reconnects_total |
подъёмы умершего пушера | растёт при status: running — канал рвётся и восстанавливается |
retransmitted_packets_total |
ретрансмиты транспорта (SRT, RIST) | растут — потери на пути к приёмнику |
rtt_ms, rtt_max_ms |
RTT до адресата: текущий и максимум за жизнь текущего пушера; только у SRT-пуша, реконнект считает максимум заново | RTT заметно выше заданной латентности — поднимайте латентность пуша |
error_events |
кольцо последних событий: ошибки отправки (момент, текст) и остановки пушера (момент, причина); ведётся только у пушей с тегом владельца user_id_<имя> в labels |
хронология рядом с полем error — первой причиной текущего отказа |
closures_by_reason |
итог остановок пушера по причинам: error, peer_closed, disabled, reconfigure, server_restart |
операторские остановки отличимы от смерти адресата причиной |
datagrams_total, frames_total |
отправленные единицы: датаграммы у пакетных транспортов, кадры у RTMP | — |
Нулевые поля в ответе опускаются: у RTMP-пуша нет датаграмм, у UDP — кадров и ретрансмитов.
Рядом со счётчиками стрима, полями верхнего уровня того же ответа, лежат три суммы по всем пушам — push_bytes_total, push_errors_total, push_reconnects_total. Они отвечают на вопрос «сколько стрим отдал вообще», не заставляя обходить карту.
Активные пуши¶
Список работающих пушей всего кластера — не обход стримов, а готовая проекция плоскости статистики:
curl -fsS -u "$ADMIN_USER:$ADMIN_PASSWORD" \
'http://central:8080/central/api-v4/pushes/active?limit=100'
Тот же путь есть на стримере: /streamer/api-v4/pushes/active. Ключ записи — тройка «стрим, пуш, узел»: у резервной группы на одну пару стрим×пуш приходятся две записи, активная и ждущая, различаемые узлом и полем standby_status. Запись несёт адресат без секретов, транспорт, владельца из тега user_id_<имя>, когда тот задан, и текущие значения: статус, время запуска текущего пушера, скорость, ошибки, реконнекты, ретрансмиты, байты и датаграммы, отставание пушера от кольца раздачи, у SRT — RTT.
{
"pushes": [
{
"stream": "tv1",
"push": "cdn-main",
"node": "node-7",
"transport": "srt",
"endpoint": "srt://203.0.113.10:9000",
"user_id": "ivan",
"status": "running",
"opened_at": "2026-10-21T09:15:02Z",
"bitrate_kbit": 2113.4,
"rtt_ms": 34,
"rtt_max_ms": 61,
"error_events": [
{"at": 1792845002, "close_reason": "error"},
{"at": 1792845062, "error": "srt connect failed: timeout after 5s"}
],
"closures_by_reason": {"error": 22, "reconfigure": 1}
}
]
}
События в error_events идут от старых к новым и ограничены кольцом: переполнение вытесняет старейшие, полная хронология нигде не хранится. Кольцо привязано к пушу, а не к пушеру — события сохраняются при реконнекте. Ресурс принимает фильтры stream, push, user_id, node, transport и limit, записи идут свежими сверху по времени запуска пушера. Выключенный пуш и пуш без пушера в список не попадают; пустой ответ означает «работающих пушей нет».
События, итог остановок по причинам и протокольная SRT-глубина (stream_push_srt_*) ведутся только у выделенных пушей — тех, чья конфигурация несёт тег владельца user_id_<имя> в labels. Пуш без владельца обходится базовым семейством серий и полями статуса; снятие тега прекращает запись новых точек, уже записанные остаются до вытеснения окном стора.
Серии Prometheus¶
Каждый счётчик пуша — своя серия с лейблом push:
| Серия | Лейблы |
|---|---|
stream_push_bytes_total |
stream, push, proto |
stream_push_errors_total |
stream, push, proto |
stream_push_reconnects_total |
stream, push, proto |
stream_push_retransmitted_packets_total |
stream, push, proto |
stream_push_closures_total |
stream, push, proto, reason |
stream_push_datagrams_total, stream_push_frames_total |
stream, push, proto |
Во встроенном Prometheus-сервере те же счётчики доступны с лейблами name (стрим) и push; на central к ним добавляется node. Протокольная глубина — stream_push_srt_* и stream_push_rist_* — приходит в скрейпе ноды вместе с опцией расширенных счётчиков. Серия stream_push_closures_total считает остановки пушера по причинам закрытого словаря и шире reconnects_total: тот считает только перезапуски после падения, здесь — все остановки; создаётся она тоже только у выделенных пушей.
# скорость отправки по каждому адресату
rate(stream_push_bytes_total{stream="tv1"}[1m])
# суммарная отдача стрима по всем пушам
sum by (name) (rate(stream_push_bytes_total{name="tv1"}[1m]))
# рвущиеся каналы: реконнекты за пять минут
increase(stream_push_reconnects_total[5m]) > 0
# потери на пути к приёмнику по SRT/RIST
rate(stream_push_retransmitted_packets_total[1m])
# недоступный адресат: серия остановок по ошибке отправки
increase(stream_push_closures_total{reason="error"}[5m]) > 0
Как читать состояние¶
status: errorи непустойerror— отправка не идёт, причина названа. Пуш при этом продолжает подниматься сам, раз в пять секунд.status: running, ноbitrate_kbitнулевой — соединение есть, данных нет: проверьте, идёт ли сам стрим.status: runningи растущийreconnects_total— канал рвётся и восстанавливается; смотритеopened_at, он показывает возраст текущего соединения.- растущий
closures_by_reasonпо причинеerror— адресат недоступен, пушер перезапускается сам; темп виден по моментам событий вerror_events. Остановки поdisabledиreconfigure— операторские, отказом сети не являются. rtt_max_msу SRT-пуша заметно выше заданной латентности — задержки не хватает на восстановление потерь: поднимите латентность пуша.status: disabled— пуш выключен в конфигурации. Счётчики заморожены на последних значениях, это не потеря данных.
Настройка¶
Передайте через central именованные pushes стрима. enabled: false приостанавливает отправку и сохраняет настройку.
Транспорт¶
Транспорт задаётся протоколом каждого именованного пуша. Контроль отправки сам не добавляет сетевой протокол.
Поддерживаемые кодеки¶
Кодеки определяет выбранный протокол: UDP, RTMP, SRT, RIST, SDI.