DynamoDB色々
Kazuki Moriyama (森山 和樹)
スキーマの設計
RDBとの相違点
- RDBはクエリが柔軟なのでスキーマ定義時にクエリのことを考えなくていい
- Dyanamoでは最も重要なクエリのみ高速化するためのスキーマ設計が必要
設計手順
- 必要なクエリ=ビジネス要件・ユースケースが判明するまでスキーマを設計してはならない
- テーブル数は少なければ少ないほど良くて理想は1つ
設計時のアプローチ
- 保存と取得のデータサイズを知る
- 取得データ型=保存データ型
- データ取得の速度要件
- テーブルはなるべく少なく
- ソートの使用
- パーティションを分ける
- サブクエリはグローバルセカンダリインデックスを使用
DynamoDB に合わせた NoSQL 設計 - Amazon DynamoDB
プライマリキー
- プライマリキーはテーブルに対して1つしか定義できない
- プライマリキーは検索に使われる
パーティションキー
- 実際にデータが格納されるハッシュを決定するキー
ソートキー
- パーティションキーと同時に用いることでプライマリキーを構成する
- パーティション内の格納順番を定義する
AWS Solutions Architect ブログ: 【AWS Database Blog】DynamoDB におけるパーティションキー設計の手引き
カラムのrename
- 単純なrenameはできない
- 別カラムを作成して、そこに元データを移してから元カラムを消すとできる
- しかし元カラムを消す意味もあまりない
python - How to rename DynamoDB column/key - Stack Overflow
読み込み操作
Query
- プライマリキーに基づいて項目を探す
aws dynamodb query ~
で実行する
キー条件式
- queryで用いられる
- パーティションキーとソートキーに関する条件を記述することができる
- `—-key-condition
DynamoDB でのクエリの操作 - Amazon DynamoDB
GSIの昇順/降順
ScanIndexForward
で指定- trueで昇順、falseで降順
DynamoDB のグローバルセカンダリインデックスの使用 - Amazon DynamoDB
フィルタ
- キー条件式以外にもオプションでデータを絞ることができる
- しかしデータを読んでからの操作であるため効率的にはフィルタしない場合と同じ
--filter-expression
で実行する- 比較演算子および関数リファレンス - Amazon DynamoDB
式中の属性値とその展開
- 式中では実行時に定まる値を変数のようにプレースホルダで置く
- 実際の値は
—expression-attribute-values
で指定する - 指定は生の値ではなく、型付した辞書にする必要がある
式中の属性名とその展開
- 式中ではカラムの指定などでそのまま使用できない語がある
- 予約後の関係
- その名前に一時的に別名を与えることで式中での使用を可能にする
—expression-attribute-names
を使用する- 別名は必ず
#
で始まる必要がある
DynamoDB の式の属性名 - Amazon DynamoDB
予約語
- 検索式の中では予約語を使用できない
DynamoDB の予約語 - Amazon DynamoDB - 予約語とかぶるカラム名での検索は属性名で別名を与えると検索可能になる
DynamoDB の式の属性名 - Amazon DynamoDB
プロジェクション
- dynamoはデフォでは全てのカラムを返すが
- プロジェクションを使用すれば任意のカラムにプロジェクション(射影)できる
- e.g.
—projection-expression “Description, RelatedItems[0], ProductReviews.FiveStar”
GetItem
- プライマリキーを指定して要素を1つ取得する
- Queryなどど違ってGSIでの指定はできない
UpdateItem
- いわゆるupsert
更新の戻り値
- —return-valuesで指定する
ALL_NEW
: 更新された行の全てのカラムを返すUPDATED_NEW
: 更新されたカラムのみを返す
pythonでの操作
ステップ 3: Python で項目を作成、読み込み、更新、削除する - Amazon DynamoDB
Query
import boto3
from boto3.dynamodb.conditions import Key
dynamodb = boto3.resource('dynamodb', region\_name='us-east-1')
table = dynamodb.Table('Books')
resp = table.query(
IndexName="CategoryIndex", # GSIは使用したかったら指定する
KeyConditionExpression=Key('Category').eq('Suspense'),
)
GetItem
reader = reader\_table.get\_item(
Key={"partition\_key": some\_value, "sort\_key": some\_value}
)\["Item"\]