Atualização_2024-11-13
- O relatório inicial afirmava que consumidores com auto-commit ativado poderiam causar perda de dados ao fazer commit automático do offset retornado no poll mais recente.
- No entanto, vários leitores contestaram isso, argumentando que consumidores com auto-commit na verdade fazem commit do offset do poll anterior, e não do mais recente.
- Resultados de experimentos com o cliente Java Kafka também sustentam isso, embora o comportamento possa variar entre clientes.
- A alegação específica sobre auto-commit foi removida do relatório, e mais pesquisa é necessária.
Contexto
- Kafka é um sistema de streaming popular que oferece replicação, sharding e logs append-only.
- Bufstream é uma solução alternativa ao Kafka que prioriza governança de dados e eficiência de custos em ambientes de nuvem.
- Assim como o Kafka, o Bufstream oferece coleções de logs parcialmente ordenados chamadas tópicos, e cada tópico é dividido em partições.
- O Bufstream é compatível com clientes Kafka padrão e é composto por um agente, um serviço sem estado que fornece a API do Kafka, um object store que armazena os dados e um serviço de coordenação.
- O Bufstream reduz custos gravando o armazenamento de dados diretamente em serviços de object storage e pode operar em VMs sem estado com escalonamento automático.
Segurança do cliente
- O Bufstream foi projetado para várias aplicações de streaming e define diferentes opções de configuração de cliente para operação segura.
- Assim como o Kafka, usa
acks = all por padrão e define enable.auto.commit = false para evitar perda de dados.
- Usa
auto.offset.reset = earliest para permitir que consumidores observem o log inteiro.
Transações
- O Bufstream oferece suporte ao sistema de transações do Kafka e, por meio de configuração complexa, fornece uma forma fraca de atomicidade.
- Consumidores podem executar com níveis de isolamento
read_uncommitted ou read_committed, e read_committed evita alguns fenômenos (G1a, G1c).
- Em Kafka, Redpanda e Bufstream, o fenômeno G0 ocorre, o que não está alinhado com os níveis de isolamento documentados.
Projeto dos testes
- Foram testadas as versões de Bufstream de 0.1.0 a 0.1.3 usando a biblioteca de testes Jepsen e o Java Kafka Client.
- Os testes avaliam a segurança do Bufstream injetando várias falhas.
Fila
- Foi projetada uma carga de trabalho de fila alinhada ao modelo de dados do Kafka para uso no Bufstream.
- Cada processo lógico executa clientes de produtor, consumidor e administrador, enviando registros para várias chaves.
Abortos
- Com base em resultados inesperados, foi projetada uma carga de trabalho para abortar transações e rastrear offsets.
- Os offsets após transações abortadas foram classificados em quatro categorias: avanço, retrocesso, retrocesso maior e outros.
Resultados do Bufstream
Consumidor travado (#1)
- Da versão 0.1.0 até 0.1.3-rc.8, ocorreu um problema em que chamadas
consumer.poll() retornavam imediatamente sem retornar registros.
- O Bufstream resolveu o problema em 0.1.3-rc.6 atualizando o cache.
Produtor e consumidor travados (#2)
- Mesmo em 0.1.3-rc.6, houve problemas em que chamadas
InitProducerId falhavam ou chamadas listOffsets falhavam.
- O Bufstream resolveu o problema adicionando lógica extra de polling.
Offset 0 incorreto (#3)
- Da versão 0.1.0 até 0.1.3-rc.2, ocorreu um problema em que offsets 0 incorretos eram atribuídos.
- O Bufstream resolveu esse problema em 0.1.3-rc.6.
Perda de escrita transacional (#4)
- Na versão 0.1.2, ocorreu um problema em que registros de transações confirmadas desapareciam.
- O Bufstream resolveu o problema em 0.1.3-rc2.
Perda de escrita causada por filtragem no lado do servidor (#5)
- Na versão 0.1.3-rc.8, ocorreu perda de escrita em resposta a falhas leves.
- O Bufstream resolveu o problema em 0.1.3-rc.12.
Resultados do Kafka
Mensagem de erro enganosa (KIP-588)
- Há um problema em que
ProducerFencedException também ocorre em timeouts de transação.
- Recomenda-se que a equipe do Kafka altere a mensagem de erro.
Possibilidade de espera infinita ao encerrar o consumidor (KAFKA-17734)
- Há um problema em que a chamada
Consumer.close() pode ficar esperando indefinidamente em IO de rede.
- O problema está sendo acompanhado por meio de KAFKA-17734.
Offsets imprevisíveis do consumidor após falha de transação (KAFKA-17582)
- Falta documentação sobre o comportamento pretendido dos offsets do consumidor quando uma transação falha.
- Após uma transação abortada, o consumidor pode retroceder o offset ou continuar avançando.
1 comentários
Opiniões no Hacker News
Ao investigar problemas que ocorriam no Kafka, foi encontrada uma escrita invisível. Isso levanta a possibilidade de que uma mensagem
Produceatrasada seja incluída em uma transação futura, violando as garantias transacionais. Também há suspeita de que o Kafka Java Client possa reutilizar números de sequência quando uma requisição expira por timeout. São necessários mais testes no KafkaAo ver a página do produto do Bufstream, fiquei me perguntando como duas afirmações podem ser compatíveis
Fiquei surpreso com o recurso de auto-commit do Kafka
pollé chamado. Se o processamento das mensagens não tiver sido concluído, há risco de perder o progresso das mensagens em caso de falhaO protocolo de transações do Kafka parece ter um problema fundamental e precisa ser corrigido
Fico curioso se o Kyle já analisou o NATS Jetstream
Não consegui encontrar o projeto do bufstream no GitHub. Fico curioso se alguém tem alguma pista
Depois de ler o post do blog e a documentação relacionados, parece que o Kafka define “exactly-once delivery” como uma propriedade de uma “operação de leitura-processamento-escrita”. Parece que seria melhor descrever isso como uma transação
A frase “transações podem ser observadas em parte ou no todo” parece que deveria ser lida como “consumidores podem observar em parte ou no todo”
Fico curioso para que esse software é usado. Instrumentação? Caixa-preta?