Skip to content

Comutação de fontes

media.source.failover

Um stream pode ter várias fontes. O Sapsan vigia a fonte ativa, comuta automaticamente para a próxima quando ela se degrada e volta para a principal quando ela se recupera. Esta lógica se chama LSI (Live Source Input).

Várias entradas

As entradas são listadas em ordem de prioridade — a primeira é a principal:

streams:
  - name: tv1
    inputs:
    - udp:
        host: 239.0.0.1
        port: 5000
    - tshttp:
        url: http://backup-origin.example.com/tv1/mpegts

Como funciona a comutação

Propriedades chave do algoritmo, importantes para o ar:

  • Uma fonte fica ativa apenas quando está pronta: ela precisa entregar os parâmetros do stream (MediaInfo) e um ponto inicial adequado (quadro-chave, quadro de áudio ou limite de fragmento). Até lá os espectadores continuam recebendo a fonte atual.
  • Retorno após uma janela limpa: uma entrada recuperada de maior prioridade é sondada em segundo plano. Para entradas abertas pelo Sapsan, ela deve atingir um ponto inicial adequado e passar return_alive_secs sem violações de regras antes da comutação.
  • Uma entrada caída reconecta com pausas crescentes (reconnect_initial_delay → reconnect_delay_step → reconnect_max_delay); quando todas as entradas se esgotam, a rotação recomeça da primeira.
  • Uma fonte cuja taxa de bits excede max_bitrate é interrompida à força.
  • Tempos limite separados para a falta de vídeo e de áudio: o áudio perdido com vídeo vivo também conta como degradação.

Política de comutação

A seção lsi define a política para o stream inteiro. source_options permite substituir os tempos limite, limites de bitrate e a janela limpa de uma entrada; as pausas de reconexão e o intervalo de verificação em segundo plano são definidos apenas em lsi:

streams:
  - name: tv1
    inputs:
    - udp: {host: 239.0.0.1, port: 5000}
    - udp:
        host: 239.0.0.2
        port: 5000
      source_options:
        source_timeout: 10
    lsi:
      source_timeout: 5
      video_timeout: 3
      audio_timeout: 3

Os tempos limite e o intervalo de verificação são definidos em segundos; as pausas de reconexão, em milissegundos. Parâmetros principais:

Parâmetro Descrição
source_timeout, video_timeout, audio_timeout tempos limite de ausência de dados/vídeo/áudio
max_bitrate limite de taxa de bits da fonte
reconnect_initial_delay, reconnect_delay_step, reconnect_max_delay política de reconexão (apenas lsi), milissegundos
recheck_secondary_inputs_interval intervalo de verificação de entradas inativas (apenas lsi), segundos
allow_if, deny_if (apenas em source_options) ligar/desligar uma entrada por um arquivo de bandeira externo

allow_if/deny_if permitem controlar as entradas de fora sem editar a configuração: uma entrada é usada apenas enquanto o arquivo de bandeira permite.

Estado da fonte secundária

Aplique a configuração pelo central. Defina explicitamente o intervalo de verificação em segundo plano em lsi; este exemplo verifica as entradas inativas com um intervalo de 10 segundos:

streams:
- name: tv1
  inputs:
  - udp: {host: 239.0.0.1, port: 5000}
  - udp: {host: 239.0.0.2, port: 5000}
  lsi:
    source_timeout: 5
    recheck_secondary_inputs_interval: 10

Leia o estado pela API de gerenciamento do central. Com duas entradas configuradas, inputs[1] é a segunda fonte e current indica se ela alimenta o stream agora:

curl -fsS -u "$ADMIN_USER:$ADMIN_PASSWORD" \
  http://central:8080/central/api-v4/streams/stats/tv1 \
  | jq '{active: [.inputs[] | select(.current)], secondary: .inputs[1] | {url, current, status, problems, checked_at, error, failure_cause}}'

status é o último estado observado, não uma garantia de comutação sem interrupções. checked_at contém a hora da observação RFC 3339 UTC; se ausente, ainda não houve verificação. Valores:

  • working — quadros chegando, janela limpa sem violações.
  • starting — entrada aberta, ainda sem quadros.
  • degraded — quadros chegando, uma regra de qualidade foi violada.
  • dead — sem quadros por erro ou timeout.
  • unchecked — entrada ainda não observada.

Consulte problems, error e failure_cause para saber a causa. current: false por si só não indica falha: uma reserva saudável não está selecionada para transmissão. Verifique a idade de checked_at e compare media_info das duas entradas: codecs ou geometrias diferentes não permitem presumir uma comutação sem interrupções.

Tempo nas entradas primária e reserva

Leia a seção detalhada input diretamente do streamer que captura tv1. O central entrega o estado atual compacto e não solicita essa seção ao streamer:

curl -fsS -u "$ADMIN_USER:$ADMIN_PASSWORD" \
  http://streamer:8080/streamer/api-v4/streams/stats/tv1 \
  | jq '.input | {primary_s: (.num_sec_on_primary_input // 0), secondary_s: (.num_sec_on_secondary_input // 0), no_data_s: (.num_sec_no_data // 0), switches: (.input_switches // 0), retries: (.retries // 0)}'

Esses valores acumulativos usam ticks de um segundo durante a vida das estatísticas do stream. num_sec_on_secondary_input soma todas as entradas após a primeira, não apenas a segunda. num_sec_no_data conta os segundos após o timeout sem dados. Campos zerados podem ser omitidos; use // 0 somente dentro de uma seção input realmente recebida. Uma seção ausente não significa tempo zero.

Exemplo de duas amostras:

{"t0":{"primary_s":3600,"secondary_s":120,"no_data_s":0},
 "t1":{"primary_s":3640,"secondary_s":140,"no_data_s":0}}

Durante o intervalo, a primária foi usada por 40 s e as reservas por 20 s; a proporção de reserva no tempo com dados é 20 / (40 + 20) = 33.3%. Subtraia amostras consecutivas. Se os contadores diminuírem após um reinício ou reatribuição do stream, inicie um novo intervalo; não some diferenças negativas.

Próximos passos