Python(boto3)で DynamoDB の全アイテムを取得する
boto3 でテーブル全体を読むということは、scan を最後までページングするということです。各レスポンスは 1 MB で頭打ちになり、低レベルクライアントの組み込みページネーターが全ページにわたって LastEvaluatedKey を代わりに追いかけてくれます(DynamoDB のカーソルの仕組み)。
ここではページネーション以上に、どの boto3 API を選ぶかが効いてきます。そしてページネーターは、その理由の半分にすぎません。
コード
import boto3
client = boto3.client("dynamodb")
paginator = client.get_paginator("scan")
items = []
for page in paginator.paginate(TableName="Music"):
items.extend(page["Items"])
print(f"Table holds {len(items)} items")解説
- ページネーターはクライアントのものであって、リソースのものではありません —
boto3.resource("dynamodb").Table(…).scanにはページネーターがそもそも無いので、そちらではLastEvaluatedKeyのループを自分で書くことになります。それだけでも、全件読み取りに低レベルクライアントを使う十分な理由になります。 - リソース API は数値を
Decimalに変換します — 保存された{"N": "1994"}はDecimal('1994')として返り、json.dumpsはカスタムエンコーダーなしではこれのシリアライズを拒みます。上のクライアントは生の{"N": "1994"}を渡し、変換を自分に任せます(エンコーディング)。 - ページネーターは置き換えずに調整しましょう —
paginator.paginate(TableName="Music", PaginationConfig={"PageSize": 500, "MaxItems": 10000})のように。boto3 はPageSizeを "the number of items returned per page of each result"、MaxItemsを合計の上限と定義しており、後者はNextTokenを出力するのでStartingTokenで再開できます。 - 並列スキャンにはスレッドごとに 1 つのクライアントが必要で、その作り方に注意が要ります —
SegmentとTotalSegmentsが仕事を分割します。boto3 自身の指針は、クライアントはスレッドセーフだがセッションとリソースはそうではない、というものです。さらに "Invokingboto3.client()inside of a concurrent context may result in response ordering issues" とも警告しています。ファンアウトの前にクライアントを作るか、各ワーカーに専用のboto3.session.Session()を持たせましょう(並列が割に合う場面)。 itemsはテーブルのサイズまで膨らみます — テーブルが小さいと分かっている場合を除き、保持し続けるリストに追加するのではなく、ループの中でpageごとに処理しましょう。- スキャンは実行のたびに、読んだバイトすべてに課金します —
ProjectionExpressionが縮めるのはレスポンスであって請求ではありません(理由)。FilterExpressionは、アイテムが読まれて課金された後に落とします(フィルター付きの Scan)。ホットパスで欲しいのは query です。
ビジュアルに行う
フルスキャンの請求額は、アイテムサイズ × アイテム数を 4 KB 単位で切り上げたものです。アイテムサイズ計算ツールは、貼り付けたアイテムからそのアイテムあたりの側を出してくれます。
DynoTable は代わりに、無限スクロールのグリッドで実テーブルをページングします。SQL エディターは、実行前にクエリがコンパイルされる操作名を示します。RCU の見積もりは、テーブルのメタデータが対応している場合にのみ表示されます。DynoTable をダウンロードしてください。
関連する例
- Node.js で全アイテムを取得する — 明示的なループによる同じ全件読み取り。
- AWS CLI で全アイテムを取得する — CLI が代わりにページングします。
- Python での DynamoDB Scan —
FilterExpression付きのスキャン。 - 並列スキャン — Segment/TotalSegments、ワーカー数、そして手を出す価値がある場面。
- DynamoDB の Scan はなぜ遅くて高いのか? — コストモデルと、その回避方法。
- DynamoDB ProvisionedThroughputExceededException — テーブル全体を読むのは、これに当たる古典的な方法です。
- "The provided starting key is invalid" — ページネーションループで再開キーが壊れています。
参考資料
- Scan — Amazon DynamoDB API Reference
- DynamoDB.Paginator.Scan — Boto3 documentation
- Scanning tables in DynamoDB — Amazon DynamoDB Developer Guide
- DynamoDB read and write operations (capacity unit consumption) — Amazon DynamoDB Developer Guide
- Paginators — Boto3 documentation
- Clients (thread safety) — Boto3 documentation
最終検証日 2026-07-28、上記にリンクした公式 AWS ドキュメントに照らして確認しました。