Iniciante4 min de leitura

Query vs Scan no DynamoDB

Query lê uma única coleção de itens pela chave de partição (opcionalmente estreitando a chave de ordenação); Scan lê a tabela inteira e filtra depois. Eles parecem similares na API, mas cobram — e escalam — de formas completamente diferentes.

Quando devo usar Query vs Scan no DynamoDB?

Use Query sempre que você conseguir nomear a partição que precisa — ele lê uma única coleção de itens e cobra apenas pelos itens correspondentes. Recorra ao Scan somente para exportações pontuais ou tabelas pequenas; ele lê cada item e cobra pela tabela inteira antes que qualquer FilterExpression seja executada. Em dados reais, o Query vence.

  • Query é direcionado: você paga pelos itens da partição correspondente.
  • Scan é exaustivo: você paga para ler cada item e depois descarta a maioria com um FilterExpression que roda depois que a leitura é tarifada.

Em uma tabela de qualquer tamanho real, um Scan com filtro é a clássica armadilha do "por que minha conta está enorme e minha latência pior que a do RDS".

Lado a lado

QueryScan
LeiturasUma partição (por PK)Todo item da tabela
Capacidade cobradaItens correspondentes na partiçãoTabela inteira, antes de filtrar
FilterExpressionAplicado após a leitura — ainda cobrado pela leituraIgual — filtrar nunca corta o custo
LatênciaConstante conforme a tabela cresceCresce com o tamanho da tabela
Paginação1 MB/página → LastEvaluatedKey1 MB/página; paralelizável
Use paraPadrões de acesso conhecidosExportações pontuais, tabelas mínimas

A pegadinha-chave: um FilterExpression roda depois que o DynamoDB tarifa a leitura, em ambas as operações. Um Scan que "retorna 10 linhas" pode cobrar pela leitura de um milhão — filtrar é uma conveniência, nunca um controle de custo.

Use Query

Query  PK = "USER#42"  AND  SK begins_with "ORDER#"

Se você se pegar recorrendo ao Scan para responder a um padrão de acesso comum, isso é um sinal de modelagem: adicione um Global Secondary Index para que o padrão vire um Query.

A escolha se resume a uma pergunta — você consegue nomear a partição que precisa?

SimNãoSimNãoPadrão de acessoChave de partição conhecida?Query uma partiçãoUm GSI consegue chaveá-la?Adicione um GSIScan a tabela inteira

Se a chave é conhecida você usa Query; se não, adicione um GSI para torná-la um, e recorra ao Scan só quando nenhuma chave servir.

Quando o Scan é aceitável

Exportações pontuais, tabelas de configuração mínimas e jobs em segundo plano que paginam por toda a tabela de propósito. Use Segment/TotalSegments para dividir um Scan entre workers (um scan paralelo) quando você genuinamente precisa ler tudo.

Um SELECT * FROM table reflexivo sobre o DynamoDB é o mesmo anti-padrão em roupagem PartiQL — ele compila para um Scan. Quando você realmente precisa de análises entre itens (um GROUP BY, um JOIN, uma agregação), o SQL Workbench do DynoTable os roda no lado do cliente sobre um conjunto de resultados limitado, em vez de martelar a tabela.

Estime as unidades de leitura que cada padrão vai custar com a calculadora de capacidade e experimente o DynoTable para rodar e inspecionar essas consultas contra suas próprias tabelas.

Atualizado