Más contenido relacionado La actualidad más candente (20) Similar a Guide to Cassandra for Production Deployments (20) Guide to Cassandra for Production Deployments1. 本番で使うための
Cassandraガイド
Guide to “Cassandra” for Production Deployments
島田慶樹 (株)ケイビーエムジェイ
2011/05/17 ソーシャルメディア、ソーシャルアプリが育てたNoSQL技術
~NoSQLセミナー
2. 提 供
世界中の人々に愛される
インターネットサービスを創り続ける
株式会社ケイビーエムジェイ
5. 自己紹介
●
氏名:島田慶樹 (SHIMADA Keiki)
●
Twitter: _shimada
●
主にRuby on Railsを使ったWebシステムの開発に
従事
●
ここ1年程、大規模ASPシステムの保守、機能追加な
どの仕事をしている
●
性能やスケーラビリティなど、非常に勉強になる現場
●
Cassandraとの出会い
7. 仕事で使っている言語は?
●
Java
●
C / C++
●
C#
●
PHP
●
Perl
●
JavaScript
●
Ruby
●
Pyhton
●
その他
8. 仕事で使っているデータベースは?
●
MySQL
●
PostgreSQL
●
Oracle
●
DB2
●
SQL Server
●
MS Access
●
Sybase
●
その他
9. 仕事でKVS / NoSQL使ってますか?
●
Memcache系
●
TokyoCabinet/Tyrant
●
MongoDB
●
Cassandra
●
HBase
●
okuyama
●
クラウド系(GAE, AWS, Azure, ...)
●
その他
11. NoSQLの位置づけ
●
A. 処理の入り口で使う =バッファ
●
B. 処理の出口で使う =キャッシュ
●
C. 処理中に使う =ワークエリア
システムの中核となるデータ(エンティティ)
は、RDBMSに格納する
※あくまで個人的な見解です
12. 一般論としての情報システム
入力
Buffer
Core system
処理
Work area
Entity
Cache
出力
14. B. 処理の出口で使う=キャッシュ
入力
Buffer
Core system
処理
Work area
同じパラメータで何
度もリクエストが来
Entity
る場合に、結果が変
わらない間は最初に
処理した結果をため Cache
ておいて直接返す
出力
15. C. 処理中に使う=ワークエリア
入力
Buffer
Core system
処理
Work area
Entity
大規模なデータ処理
のための中間データ
を一時的にストアす
る
Cache
出力
16. エンティティはRDBMSに
入力
Buffer
Core system
処理
Work area
Entity
Cache RDBMS!!
出力
19. Cassandraのデータモデル
●
カラム指向データストア
●
行ごとに違うカラム(列)を自由に作れる柔軟な
データ構造
●
ただし、サブクエリやテーブルJOINなどの機能が
ない
20. ネストしたHashTableみたいなもの
AddressBook2 = {
"仕事": {
"yamada taro": {
"name": "山田太郎",
"address": "東京都品川区****",
"phone": "03-xxxx-xxxx"
}
},
"プライベート": {
"sato hanako": {
"name": "佐藤花子",
"address": "東京都墨田区****",
"mobile": "090-xxx-xxxx",
"email": "hsato@xxxx.ne.jp"
}
}
};
22. 詳しいことは記事を参照
「Cassandra実践入門」が
gihyo.jpにて公開中
http://goo.gl/xOiKe
24. 強み、弱み、落とし穴(1)
●
勝手にシャーディング
●
スケールアウトが容易
●
ただし、キーの設計を間違うと一ヶ所にデータが集
中
●
勝手にレプリケーション
●
ただし、反映にかかる時間はベストエフォート
●
スレーブが反映前のデータを返してしまうことも
– クライアントから見るとスレーブ/マスターの区別がな
い
25. 強み、弱み、落とし穴(2)
●
勝手にフェイルオーバー
●
落ちたノードへの書込みは自動的に他のノードが受
け取り一時保管する
●
ノードが復帰したらデータが書き戻される
– 一時保管されたデータは、クライアントからは読み出せ
ないことに注意
– 本来のノードがすべて落ちたらそのデータは読めなくな
る
– 他のノードが担当を肩代わりしてくれるわけではない
26. 強み、弱み、落とし穴(3)
●
スケールアウトと負荷分散
●
ノードを新規追加すると、データ量が一番多いノー
ドからデータを半分引き取ってくれる
– 実データがどのノードに保存されているかブラックボッ
クスになっている
27. 強み、弱み、落とし穴(4)
●
データの整合性(Consistency)
●
トランザクション、ロールバック、アトミックな更
新の機能がない
●
整合性の強さをAPIで定義(整合性レベル)
– 整合性レベル=読み書きの時に通信するノードの数
– 整合性と速度はトレードオフ
29. 読み込み時に指定する整合性レベル
レベル 動作
ONE 読み込み要求に対して最初にレスポンスされてきた
データを返す
QUORUM レプリケーションファクタ値の過半数(N/2+1)か
らのレスポンスが返ってきた時点で、タイムスタン
プが最も新しいデータを返す
ALL データを持つすべてのノードからのレスポンスを待
ち、タイムスタンプが最も新しいデータを返す
“Quorum” /kwɔ́ːrəm/(会議成立などに必要な)定足数, 必要員数
30. 書き込み時に指定する整合性レベル
レベル 動作
ANY どこかで1回書き込みされたことが通知されるまで
待ってから処理を返す。本来担当すべきノードがダ
ウンしている場合は最寄りの別のノードがデータを
一時保管し、本来のノードへの伝達はキューイング
される
ONE 1つのノードでの書き込み成功が通知されてから処
理を返す
QUORUM レプリケーションファクタ値の過半数(N/2+1)か
らのレスポンスが返ってきた時点で、タイムスタン
プが最も新しいデータを返す
ALL レプリケーションファクタで指定されたすべての
ノードの書き込みに成功するのを待ってから処理を
返す
31. 強み、弱み、落とし穴(5)
●
読み書きのパフォーマンス
●
読み出しよりも書き込みの方が速い
– 読み出し:ランダムアクセスあり
– 書き込み:ランダムアクセスなし
●
コミットログ書き出し+メモリ内テーブルの書換え
で実現
●
ディスクへの書き込みは別スレッドで非同期に処理
32. 読み込みと書き込みの性能比
Host Load Read Count Read Write Write Read
(GB) Latency Count Latency /
(ms) (ms) Write
host1 8.30 11,112,703 0.19211 24,771,377 0.02160 8.89
host2 2.47 3,409,255 0.37081 6,037,249 0.01796 20.65
host3 6.52 8,690,713 0.18386 19,387,158 0.02272 8.09
host4 5.50 7,187,823 0.14506 18,943,157 0.01827 7.94
読み込み:書き込みの速度比、書込みが約8倍ほど速い
33. まとめ:Cassandraとは
●
大量のデータを大量のサーバでさばく
●
レプリケーション&シャーディング
●
一部で障害が起きても全体としては動き続ける
●
書き込みの速度に焦点を置いている
●
データの整合性を犠牲にして速度を稼ぐことが
できる
34. フィットするパターン
●
大量のデータが一斉に飛んでくる
●
大規模クラスタで負荷分散しつつ受け止めたい
●
大量データを統計処理に使いたい
●
ごく一部のデータが欠損しても全体には影響がない
●
気象、交通などセンサーデータの収集、解析
●
Webサービスでのログ/ビーコンなど
●
その他、リアルタイムな統計的処理など
36. 情報収集について
●
一次情報
●
ML
– http://www.mail-archive.com/dev@cassandra.apache.org/
●
JIRA
– https://issues.apache.org/jira/browse/CASSANDRA
●
Wiki (English)
– http://wiki.apache.org/cassandra/
●
二次情報
●
Wiki(Japanese)
– http://wiki.apache.org/cassandra/FrontPage_JP
●
ユーザー会ML(cassandra-ja)
39. 現在のプロジェクト状況
●
v0.6系の最新は0.6.13
●
v0.7系の最新は0.7.5
●
v0.8系の最新は0.8.0-beta2
40. 0.6系から0.7系への変化(1)
●
スキーマをオンラインで変更
●
[CASSANDRA-44]
– It is difcult to modify the set of ColumnFamliies in
an existing cluster
●
カラムにttl(生存期間)を指定して自動expire
●
[CASSANDRA-699]
– Add (optional) expiration time for column
●
インデックスをはったカラムの値でRowを検索
●
[CASSANDRA-749]
– Secondary indices for column families
41. 0.6系から0.7系への変化(2)
●
設定ファイルを一新/スキーマの定義をサーバの設定
ファイルから分離
●
[CASSANDRA-1133]
– utilities for schema import-from/export-to yaml.
●
[CASSANDRA-990]
– Replace cassandra.xml with cassandra.yaml
●
コマンドラインクライアントの機能向上
●
データ内容の確認、更新、スキーマ定義、ファイルか
らのコマンド読み込みなど
– [CASSANDRA-1088], [CASSANDRA-1583],
[CASSANDRA-1616], [CASSANDRA-1653],
[CASSANDRA-1687], ...
42. 0.7系から0.8系への変化
●
CQL(Cassandra Query Language)
●
[CASSANDRA-1703]
– CQL 1.0
●
カウンター専用のカラム型サポート
●
[CASSANDRA-1072]
– Increment counters
●
目玉のCQL以外に新機能はあまり多くない
●
56 fixed bugs
●
39 improvements
●
7 new features
43. Cassandra Query Language
●
SQLライクな独自のクエリ言語
●
Thrift / Avroの生のAPIを叩く必要がなくな
る
●
各プログラミング言語からのI/Fを統一
●
JDBCドライバなどの開発
●
最終的にはRPCライブラリ(Thrift / Avro)か
ら離れてCQL独自の通信層を実装したい?
44. Cassandra Query Language
●
データの取得
SELECT (FROM)? <CF>
[USING CONSISTENCY.<LVL>]
WHERE <EXPRESSION>
[ROWLIMIT X]
[COLLIMIT Y]
[ASC|DESC]
45. Cassandra Query Language
●
データの格納/変更
UPDATE <CF>
[USING CONSISTENCY.<LVL>]
SET
<cname1> = <cvalue1>,
<cname2> = <cvalue2>, ...
WHERE KEY=<key>
※UPDATEはINSERTを兼ねる模様
47. Vector clockを巡る議論
●
発端(没) [CASSANDRA-580]
●
vector clock support
●
採用 [CASSANDRA-1072]
●
Increment counters
●
没 [CASSANDRA-1421]
●
An eventually consistent approach to
counting
●
没 [CASSANDRA-1546]
●
(Yet another) approach to counting
49. クラスタ設計
●
クラスタの規模は?
●
データセンターを分けるか?
●
データの冗長度は?
50. クラスタの規模
●
ノードは後から簡単に追加できる
●
少ないノードでもオーバーヘッドが少ない
●
小さなクラスタから少しずつ育てることも可能
●
数ノードから始めて、負荷に応じて随時追加
51. データセンターを分ける?
●
“placement_strategy”
●
レプリケーション先を決めるアルゴリズム
●
レプリカを必ず別のDCに書く、などの設定が可能
●
クラスタを設計する時に決めておくべき
●
国内では東日本と西日本の2箇所、とか
●
おそらくサービスを提供する企業の
「事業継続計画(BCP)」
「災害時復旧計画(DRP)」
レベルで考慮すべき事項
52. データの冗長度
●
“replication_factor”
●
データをいくつのノードに書き込むか?
●
ノードが何台まで落ちても耐えられるか?
●
⇔ ディスク容量
●
⇔ 情報伝播の速度(整合性)
●
⇔ Consistency Level
53. データの分散アルゴリズム
(Partitioner)
●
RandomPartitioner
●
キーのハッシュ値(md5)によってランダムに振り分け
る
●
ByteOrderedPartitioner
●
キーのバイト値によって順番に振り分ける
●
CollatingOrderPreservingPartitioner
●
キーを文字列として辞書順に振り分ける
●
クラスタ単位で設定→クラスタ設計に必須
54. データの分散アルゴリズム
(Partitioner)
●
データを均等に分散したい
●
RandomPartitioner
●
キーの範囲をレンジスキャンしたい
●
ByteOrderedPartitioner
●
CollatingOrderPreservingPartitioner
●
RandomPartitionerはキーを範囲指定してアクセスする
処理ができない
●
OrderedPartitionerはノードごとのデータが偏りがち→負荷
分散が難しい
55. 一貫性レベル
Consistency Level
RF= 1 2 3 4 5 6
CL= ANY 0 0 0 0 0 0
ONE 1 1 1 1 1 1
QUORUM 1 2 2 3 3 4
ALL 1 2 3 4 5 6
効果が変わらない 非現実的
Replication FactorとConsistency Levelによって書き込ま
れるノード数の違い
56. クラスタ設計(まとめ)
●
クラスタの規模は?
– データ量と負荷に応じて決める
– スケールアップ可能
●
データセンターを分けるか?
– 提供するサービスレベルによって決める
●
データの冗長度は?
– 提供するサービスレベルによって決める
●
その他のパラメータ
– アプリケーションの要件によって決める
57. スキーマ設計の注意点
●
データをモデリングしてはいけない
●
リレーションという概念がない
●
トランザクションやロールバックがない
●
Cassandraにエンティティを保存してはいけない
●
整合性や一貫性、検索性の低さ
●
バッファ、ワークエリア、キャッシュとして使う
●
処理の単位を中心においた「ユースケース駆動」の設計
をすべき
58. エンティティはRDBに
●
Cassandraが必要なくらい大規模なプロジェ
クトで、データの入れ物としてRDBMSがない
というケースはあり得ない
●
全部をまかなえるほどCassandraは万能では
ない
Partakeは「あえて全部Cassandraでやって
みた」というネタ実験プロジェクト
59. ユースケース駆動のCF設計
●
ユーザーがサービスを利用するという意味ではない
●
アプリケーションがストレージを利用する場面という
意味
× このエンティティはどういうプロパティを持ってい
るか?
○ この処理において読み書きしたいのはどういう
データの塊か?
60. 入力
Buffer
Core system
処理
Work area
Entity
Cache
出力
61. Cassandraの使いどころ
●
ボトルネックになっている箇所をスケールさせ
るために使う
●
必要なデータの塊に対応するCFを作る
●
一度の読み書きをひとつのCFで完結させる
64. 集計前または集計済のデータを載せる
●
トランザクションやロックの機能がない
●
Check & Setができない
●
レースコンディションに弱い
Get() ⇒ 5 5+10=15 Set(15)
5 15
Get() ⇒ 5 5-1=4 Set(4)
65. キーの細分化
●
1セッションでのI/Oが別セッションに割り込
まれないように
●
例:キーをユーザー単位に分割する
66. Super Columnの罠
●
スーパーカラム
=2段にネストしたHashTable型のCF
●
Sub columnにはインデックス情報がない
●
Sub columnをひとつだけ読込もうとしても
全てのデータがメモリ上に取り出される
67. Super Columnの罠
●
悪い例:サービス別ユーザー別行動履歴
UserActivity: {
service-id-1: {
user-id-1: {
timestamp: activity1
timestamp: activity2
timestamp: activity3
:
}
user-id-2: {
timestamp: activity1
:
}
service-id-2 {
}
}
68. Super Columnの罠
●
悪い例:サービス別ユーザー別行動履歴
Get UserActivity[12][35][20110305112233]
●
特定のactivityだけを取得しようとして
も、user-id-1に含まれるデータがすべてメモ
リ上に展開される
●
→ Out of memory!
69. Super Columnの罠
●
改善案:
UserActivity: {
service-id-1$user-id-1: {
timestamp$activity-type: {
timeuuid: activity1
timeuuid: activity2
timeuuid: activity3
}
}
}
●
タイムスタンプ+行動種別で分割
●
カラム数が有限個に収まるようにする
71. 上位層を抽象化しておく
App
Get() / Set()
UserHistory
Get() / Set()
Cassandra
74. 本番システムへの適用
●
ポイント(1)
●
Cassandraがなくても動くように作る
●
ポイント(2)
●
範囲を絞って使えるようにする
●
ポイント(3)
●
すぐに切り戻せるようにする
76. 範囲を絞って使えるように
App
Cassandra-1 書き込み処理は必ずDBと
Cassandra両方に書き込む
管理画面からの設定で、グルー
プ毎にDBから読込むか
Cassandraから読込むかを切
Shard-1 Shard-2 り替える
Admin
Group-1 : read from [Shard-1]
Group-2 : read from [Cassandra-1]
77. 不具合があればすぐ切り戻す
App
Cassandra-1 書き込み処理は必ずDBと
Cassandra両方に書き込む
管理画面からの設定で、グルー
プ毎にDBから読込むか
Cassandraから読込むかを切
Shard-1 Shard-2 り替える
Admin
Group-1 : read from [Shard-1]
Group-2 : read from [Shard-2]
78. 障害検知について
●
アプリ側を監視していても、ノードが一つ二つ落ちて
いることに気づけない
●
1台だけ生き残っていてHinted Handofを受け取り続
けていた……ということもありえる
●
障害によってデータの欠損が起こったかどうか、運用
側から発見が困難
●
どの段階で復旧の可否を判断するか?
●
P2Pベースの自律分散システム=便利だけど管理が難
しい
79. バックアップとリストア(1)
●
ある時点のスナップショット、という概念がな
い
●
ノードごと、SSTableごとにJSONにダンプ/
リストアする機能があるだけ
●
各ノードごとに受け持ちのデータ範囲が違う
●
ひとつノードを停めてバックアップしている間
に別のノードがレプリカを更新してしまう
80. バックアップとリストア(2)
●
サービスを停めないと整合性のとれたバック
アップはとれない
→設計段階から織り込んでおく必要がある
→「エンティティを保存しない」の理由の一つ
83. Buffer
Core system
Work area
Entity
Cache