2 pontos por GN⁺ 2025-04-30 | 1 comentários | Compartilhar no WhatsApp
  • O cluster Multi-AZ do Amazon RDS for PostgreSQL oficialmente oferece suporte a Snapshot Isolation, mas na prática ciclos G-nonadjacent e o fenômeno de Long Fork ocorrem com frequência, violando essa garantia
  • Os testes foram realizados com base em uma carga de trabalho de transações PostgreSQL montada diretamente, e erros de consistência ocorreram em todas as versões, do PostgreSQL 13.15 ao 17.4
  • Esses erros ocorrem principalmente em nós secundários somente leitura, e o Snapshot Isolation é quebrado até mesmo no nível "Repeatable Read"
  • O cluster RDS pode estar oferecendo um nível de consistência de Parallel Snapshot Isolation, que é um modelo mais fraco do que o PostgreSQL padrão em nó único
  • Transações somente leitura podem observar ordens diferentes de transações, e essas inconsistências podem levar a erros de integridade de dados

Background

  • O PostgreSQL é um banco de dados SQL open source baseado em MVCC, oferecendo vários níveis de isolamento de transações. Na prática, Repeatable Read significa Snapshot Isolation
  • O Amazon RDS fornece PostgreSQL como um cluster gerenciado, e a configuração Multi-AZ é uma arquitetura para replicação e tolerância a falhas
  • O endpoint principal permite leitura e escrita, os secundários são somente leitura e não oferecem suporte ao nível Serializable

Test Design

  • O conjunto de testes Jepsen para PostgreSQL foi adaptado para o RDS e usado para executar testes automatizados de transações
  • As transações foram projetadas para ler listas em chaves específicas ou fazer append de inteiros únicos, com detecção de ciclos pelo verificador Elle
  • Sob carga de 150 TPS de escrita e 1600 TPS de leitura, Long Fork e G-nonadjacent foram observados em menos de 2 minutos

Results

  • Uma violação de Snapshot Isolation foi demonstrada por meio de um ciclo G-nonadjacent composto por 4 transações
    • T₂ observou as alterações de T₁, mas não viu T₃; T₄ viu T₃, mas não T₁ → surge uma contradição mútua na ordem temporal
  • Isso é um caso de Long Fork e uma evidência forte de violação de Snapshot Isolation, e
  • Nenhum Write Skew foi encontrado, o que reforça a possibilidade de Parallel Snapshot Isolation

Discussion

  • O RDS Multi-AZ tem um nível de consistência inferior ao do PostgreSQL em nó único
  • Como há possibilidade de erros de consistência ao usar nós somente leitura, pode ser necessário usar apenas o nó de escrita ou considerar incluir pelo menos uma escrita em todas as transações
  • Esta análise está em nível inicial de testes e prova a existência do problema, mas não garante sua ausência

1 comentários

 
GN⁺ 2025-04-30
Comentários do Hacker News
  • Embora isso não esteja explicitamente mencionado no título do artigo, trata-se do novo recurso do RDS, o cluster Multi-AZ

    • A instância Multi-AZ é o recurso antigo em que o banco de dados principal é replicado de forma síncrona para um banco secundário em outra AZ
    • O cluster Multi-AZ tem dois bancos secundários, e as transações são replicadas de forma síncrona para pelo menos um deles
    • Isso o torna mais robusto caso um banco secundário falhe ou tenha degradação de desempenho, além de permitir acesso somente leitura aos secundários
    • O cluster Multi-AZ não é um recurso padrão do Postgres, e esse pode ser o motivo de ele falhar no teste do Jepsen
  • Em uma empresa anterior, quando alteramos o comando pg_dump do script de backup para usar workers paralelos (flag -j), apareceram problemas de consistência na restauração do backup (erros de chave duplicada e erros de restrição de FK)

    • Reportamos o problema às listas de discussão da AWS e do Postgres, mas como ele não podia ser reproduzido facilmente, não foi resolvido
    • No fim, voltamos ao dump em thread única, e fico pensando se esse problema tem relação com o comportamento que enfrentamos
  • O trabalho foi feito pelo Jepsen de forma independente, sem remuneração

    • É o tipo de notícia que partes interessadas em RDBMS não querem ouvir em um dia bom
    • Meus respeitos ao aphyr
  • O significado prático desse problema é que leituras feitas logo após uma escrita na mesma linha podem retornar dados desatualizados

    • Antes que uma transação de escrita seja marcada como concluída, nem todas as camadas distribuídas da instância RDS Multi-AZ estão totalmente atualizadas, então uma leitura imediata pode retornar uma linha inexistente ou um valor antigo
    • Por causa do modo como o PostgreSQL lida com snapshots, não é o caso de apenas alguns bytes de um tipo de coluna multibyte serem atualizados e a leitura acabar obtendo um valor sem sentido
    • Isso parece, no fim das contas, uma condição de corrida que eventualmente se torna consistente
  • Não está claro se o problema não ocorre em clusters upstream do Postgres com múltiplas instâncias

    • Fico pensando se a AWS adicionou algo à configuração do cluster ou incluiu algum patch que provoca esse comportamento
  • O título enviado esconde o ponto principal: o RDS para PostgreSQL 17.4 não implementa corretamente o isolamento de snapshot

  • Se desenvolvedores assumirem isolamento de snapshot, mas o Amazon RDS for PostgreSQL na prática oferecer apenas isolamento de snapshot paralelo, fico pensando que tipo de falhas de segurança ou bugs em nível de aplicação podem surgir, especialmente em configurações Multi-AZ que usam endpoints de réplica de leitura

  • Isso aconteceu em todas as versões testadas, da 13.15 até a 17.4

    • Fiquei preocupado se atualizar a versão principal tinha sido uma decisão errada, mas isso não é uma regressão e sim um pedido de recurso ou um bug antigo
  • Seria bom testar com Jepsen todas as versões do Amazon RDS

  • A AWS deveria atualizar a documentação para informar isso

    • Fico pensando se corrigir o isolamento de snapshot causaria regressão de desempenho em latência ou throughput, ou se eles vão alegar que o estado atual já é forte o suficiente
    • De qualquer forma, a AWS deveria se pronunciar sobre isso