現場で使えるDynamoDBと冪等デザインパターン
2015.10.30 Yusuke Arai, Classmethod Inc.
自己紹介• 荒井祐輔 (モバイルアプリサービス部)
• 2014.11 AndroidチームにJOIN
• 2015.04 モバイルバックエンドのScalaチームにJOIN
• Scala や API Gateway のブログをよく書いてます
• 普段は Amazon DynamoDB を Scala から JavaSDK を介して使用しています
現場で使えるDynamoDBと冪等デザインパターン
もっと使おう!DynamoDB
冪等だってあるんだよ!
もっとラフに DynamoDB を 使ってほしい
使ってみたいけど 何ができて
何ができないのか よくわからない
使いたいけど 個人アプリだから
マネーが…
高可用性・高堅牢性 以外にも
DynamoDB を 使うべき
理由があります!
•DynamoDBってなんだ
•できること/できないこと
•もっと使うために
アジェンダ
•DynamoDBってなんだ
•できること/できないこと
•もっと使うために
アジェンダ
Capacity Unit
単位で課金
10書き込みユニット ≒ 秒間10書き込み ≒ 5.5 米ドル / 月
50読み込みユニット = 秒間50読み込み ≒ 5.5 米ドル / 月
•DynamoDBってなんだ
•できること/できないこと
•もっと使うために
アジェンダ
Keyに対するValueのCRUD
TRANSACTION AND
COMMIT
• できぬこと • JOIN • TRANSACTION AND COMMIT • 詳細なクエリやオーダー
• マネーがかかること • 大量のRead/Write
• できぬこと • JOIN 頑張れる • TRANSACTION AND COMMIT • 詳細なクエリやオーダー
• マネーがかかること • 大量のRead/Write
詳細なクエリやオーダー
≒ フレキシブルな検索を 提供するには
100%向いていない
このアプリに フレキシブルな 検索機能は 必要だろうか
Remember: You Ain’t Gonna Need It
• できぬこと • JOIN 頑張れる • TRANSACTION AND COMMIT • 詳細なクエリやオーダー 向いてない
• マネーがかかること • 大量のRead/Write
• できぬこと • JOIN 頑張れる • TRANSACTION AND COMMIT • 詳細なクエリやオーダー 向いてない
• マネーがかかること • 大量のRead/Write
•DynamoDBってなんだ
•できること/できないこと
•もっと使うために
アジェンダ
TRANSACTION
大量のRead/Write
トランザクション コミット
ロールバック に相当する機能は用意
されていない
ないときつい
銀行口座のお金の振り込み
ゲーム内アイテムの受け渡し
ネットショップ買い物カゴ購入
なくてもいける
銀行口座の入金
ゲーム内アイテムの購入
買い物カゴを使わない単品購入
TRANSACTION
現実的には アプリケーションレイヤで
ある程度の堅牢さを 保証する必要が出てくる
一連の処理が どこかで失敗した 場合について考える
のは難しい
処理のリトライの しやすさを高めることで "失敗" することを恐れない
ように持っていく
何度実行しても 同じ結果になること
(※同じパラメータを渡した場合に)
POST /api/v1/accounts/john/charge{ "request_id": "ABCDEFG", "charge_amount": 20000 }
user (Hash) request_id (Range) status
user (Hash) amount
john 5000
charge_events
users
POST /api/v1/accounts/john/charge{ "request_id": "ABCDEFG", "charge_amount": 20000 }
user (Hash) request_id (Range) status
john "ABCDEFG" "Start"
user (Hash) amount
john 5000
charge_events
users
POST /api/v1/accounts/john/charge{ "request_id": "ABCDEFG", "charge_amount": 20000 }
user (Hash) request_id (Range) status
john "ABCDEFG" "Start"
user (Hash) amount
john 25000
charge_events
users
POST /api/v1/accounts/john/charge{ "request_id": "ABCDEFG", "charge_amount": 20000 }
user (Hash) request_id (Range) status
john "ABCDEFG" "Finished"
user (Hash) amount
john 25000
charge_events
users
APIを冪等にしておけば クライアントは
臆せずリトライできる
一連の処理が どこかで失敗しても
成功するまでリトライして 処理を続行させる
50 Read equals
50読み込みユニット
1000 Read equals
1000読み込みユニット
バッチ処理で クーポン情報を 2000件挿入
2000 Writes equals
2000書き込みユニット
≒1,080 米ドル / 月 !?!?
五分間分の Capacity Unit を確保している
Capacity Unit が余ると蓄積されていく
10 Read Units may handle
3000 Read Accesses in the case of Burst Capacity
リトライを しっかり行えば
怖くない
Scan/Queryと
Limit
Scan/Queryは 読み込み件数ではなく 結果サイズに対して Capacity Unit 消費
TRANSACTION
大量のRead/Write
読み込み Burst Capacity = 1500 / 5min 書き込み Burst Capacity = 300 / 5min
Amazon DynamoDB
は 1米ドル / 月 でもそれなりに活躍します
Amazon API Gateway &
AWS Lambda in 東京
DynamoDB 一択
※SimpleDB もあります※そのうち Lambda in VPC も
もっとラフに DynamoDB を 使っていこう!