Escolher a cadeia pelo resultado
Uma equipa fictícia prepara um relatório de operações por dia e moeda. Define primeiro o resultado: quais eventos pertencem ao dia, quanto atraso é aceite, que identidades têm de aparecer e quem pode consultar dados brutos ou agregados. Kinesis Data Streams pode suportar aplicações que acompanham o mesmo histórico retido com progresso próprio.
Firehose entrega dados a destinos com um contrato de formato e buffering. Glue oferece transformação e catálogo; descobrir metadata não executa a transformação. Athena SQL permite analisar dados em S3.
Estes papéis podem coexistir. Escolhe os necessários e acompanha um evento desde a entrada até à linha consultada, em vez de aceitar o último estado verde do pipeline.
Conservar replay e dimensionar a unidade certa
Retenção e capacidade resolvem problemas diferentes. Se uma aplicação fica parada 32 horas e só existem 24 horas retidas, atualizar retenção na retoma não recria as primeiras oito horas. Prevê arquivo ou recuperação alternativa quando o requisito ultrapassa a retenção efetiva.
Na capacidade, procura concentração por partition key e contenção de leitura. Uma chave por organização pode concentrar muitas contas; se a ordem requerida é apenas por conta, avalia uma distribuição por accountId e valida a ordem no produtor e consumidor.
Enhanced fan-out separa capacidade de leitura entre consumidores, mas não corrige uma escrita concentrada nem um consumidor que processa devagar. A escolha exige localizar o limite observado.
Distinguir entrega, identidade e progresso
Um timeout do produtor deixa incerto se o serviço aceitou o evento. A repetição pode criar outro registo de transporte para a mesma operação. Conserva eventId ou operationId estável e define onde o efeito passa a estar confirmado.
Um consumidor que publicou 101–110 e ficou com checkpoint 100 pode voltar a processar esses eventos; o destino precisa de reconhecer o trabalho já feito. No nosso modelo, o destino oferece escrita atómica por identidade. Essa premissa deve ser implementada e verificada no sistema real.
Confirmar progresso antes de preservar resultados pode perder trabalho; preservar resultados antes de confirmar progresso exige replay controlado. Nenhuma dessas fronteiras é resolvida apenas por acrescentar workers.
Transformar sem esconder exceções
Publicar bytes não significa que o leitor os consiga interpretar. Dois objetos JSON concatenados precisam de framing compatível com o parser. Na transformação, mantém tipos e significado: um montante unknown não passa a zero sem uma regra de negócio que o autorize.
Regista o evento em quarentena com identidade, motivo e responsável. Glue bookmarks ajudam a selecionar trabalho de origem; não substituem reconciliação por evento. Ao repetir um intervalo, planeia explicitamente o destino: uma versão isolada pode ser validada antes de trocar o apontador de publicação.
Se o sistema usa append, repetir entradas pode repetir saídas. Preserva a versão disponível até o contrato permitir a troca e conserva evidência da origem usada.
Consultar o conjunto certo com acesso delimitado
Uma partição descreve a organização física, que pode diferir do dia de negócio. Se particionas por chegada, eventos do dia 10 podem estar nos dias 10, 11 e 12; lê o intervalo de chegada admissível e filtra o dia do evento. Confirma a localização na metadata: consultar raw depois de transformar curated continua a devolver a origem antiga.
Formatos colunares e filtros podem reduzir leitura, mas compara resultados equivalentes antes de interpretar bytes lidos e duração. No acesso, verifica todas as vias. Restringir SELECT em Lake Formation não elimina automaticamente autorização direta S3.
Testa a via analítica permitida e o acesso bruto que deveria ser recusado, com as identidades efetivamente utilizadas.
Workshop: reconstruir o relatório sem perder identidades
Entradas completas do modelo local: A ocorre no dia 10, chega no dia 10 e vale 1000 cêntimos EUR; B ocorre no dia 10, chega no dia 11 e vale 2000 cêntimos USD; uma repetição de A chega no dia 11 com o mesmo conteúdo; C ocorre no dia 11, chega no dia 11 e vale 500 cêntimos EUR; D ocorre no dia 10, chega no dia 12 e tem montante inválido.
O relatório é do dia 10 e permite quarentena identificada. Prevê IDs, totais e exceções antes de executar. A resposta é IDs A e B, totais EUR=1000 e USD=2000, D em quarentena; C está fora do dia pedido e a repetição de A não duplica o total.
Ler apenas a partição de chegada 10 perderia B e D. O programa rejeita repetições com conteúdo diferente para a mesma identidade, em vez de escolher uma silenciosamente. Guarda como ingestion-model.mjs e executa com Node.js.
Altera eventDay, arrivalDay ou amountCents, um de cada vez. O modelo corre apenas em memória e não implementa checkpoint, publicação concorrente ou serviços AWS.
// In-memory teaching model; no AWS calls, persistence, or concurrent publication.
const events=[
{id:'A',eventDay:10,arrivalDay:10,currency:'EUR',amountCents:1000},
{id:'B',eventDay:10,arrivalDay:11,currency:'USD',amountCents:2000},
{id:'A',eventDay:10,arrivalDay:11,currency:'EUR',amountCents:1000},
{id:'C',eventDay:11,arrivalDay:11,currency:'EUR',amountCents:500},
{id:'D',eventDay:10,arrivalDay:12,currency:'EUR',amountCents:null},
];
function report(rows,day,arrivals){
if(!Number.isInteger(day)||!Array.isArray(rows)||!Array.isArray(arrivals)||!arrivals.every(Number.isInteger))throw Error('invalid input');
const seen=new Map(), totals={}, ids=[], quarantine=[];
for(const e of rows){
if(!e||typeof e.id!=='string'||!e.id||!Number.isInteger(e.eventDay)||!Number.isInteger(e.arrivalDay))throw Error('invalid event');
if(!arrivals.includes(e.arrivalDay)||e.eventDay!==day)continue;
const identity=JSON.stringify([e.eventDay,e.currency,e.amountCents]);
if(seen.has(e.id)){if(seen.get(e.id)!==identity)throw Error('conflicting identity: '+e.id);continue;}
seen.set(e.id,identity);
if(!['EUR','USD'].includes(e.currency)||!Number.isSafeInteger(e.amountCents)){quarantine.push(e.id);continue;}
const total=(totals[e.currency]||0)+e.amountCents;
if(!Number.isSafeInteger(total))throw Error('unsafe total');
ids.push(e.id);totals[e.currency]=total;
}
return {ids:ids.sort(),totals,quarantine:quarantine.sort()};
}
console.log(JSON.stringify(report(events,10,[10,11,12])));A mesma contagem de linhas pode esconder um ID em falta e outro repetido; conserva identidade, moeda e âmbito temporal.
Armadilhas comuns
Confundir dia de chegada com dia do evento; tratar metadata como transformação; somar moedas diferentes; aceitar checkpoint como prova do efeito.
Tópicos relacionados: Eventos, filas e processamento · Eventos: permissões, capacidade e custos · Migração, validação e cutover
Aceita dados pelo conjunto e significado que o consumidor exige, com replay e exceções explicados.
Referências
- AWS Glue · AWS documentation consulted 2026-10-12
- Kinesis Data Streams concepts · AWS documentation consulted 2026-10-12
- Kinesis duplicate records · AWS documentation consulted 2026-10-12
- Kinesis enhanced fan-out · AWS documentation consulted 2026-10-12
- Data Firehose delivery · AWS documentation consulted 2026-10-12
- Glue job bookmarks · AWS documentation consulted 2026-10-12
- Athena partitioning · AWS documentation consulted 2026-10-12
- Athena columnar formats · AWS documentation consulted 2026-10-12
- Amazon Athena · AWS documentation consulted 2026-10-12
- Lake Formation underlying data access · AWS documentation consulted 2026-10-12