1月末に買ったのに何でこんな読み終わるの時間かかってるんだろう自分は。(コンスタントに読めてない)
自分が実施している負荷試験を改めて振り返って軌道修正できる良い内容だった。
概要
AWS環境でのスケールアウト性能を計測することを中心にして、 負荷試験の計画から実施、レポートまでの一連の工程とポイントを解説してくれる。
負荷試験を実施する際に陥りがちな罠についてこれでもかという程説明されている。 代表的なアンチパターンとして、
- リリース直前の工程で負荷試験を行う
- 負荷ツール側のボトルネックを考慮せずにいきなりシナリオを動かす
- いきなりスケールさせた状態で計測する
などが挙げられている。
それらのアンチパターンを解消しつつ本書のガイドに沿って負荷試験を行うことで ノイズの少ない性能データを収集することができる。
感想
特に有用に感じた内容を章別に抜き出して書き留めておく。
Chapter 3. 負荷試験の基礎知識
ここでは性能試験の重要指標となるレイテンシ、スループットについて説明されている。
「3.4. より良い負荷試験が実施されていることを示す指標」が特に有用だった。 下記を満たしている状態が適切な負荷試験を行っていることの目印とのこと。
- 負荷が対象システムに集中している状態
- ボトルネック部分を特定できている状態
ボトルネック部分が特定できているというのは個人的に重要と感じた。 つまり負荷試験を行ってデータを並べても大づかみな傾向しか解らないのであれば、 次の改善にはつながらない。したがって負荷試験の意義が減ってしまう。 負荷試験の結果を役立ててシステムを改善するためには、改善されるべき問題つまりボトルネックが発見されている必要がある。
以降の章で説明されるようにこれら指標をうまく持っていくアプローチがある。 ポイントとなるのは下記の2つである。
- 負荷ツールとシナリオのチューニングによる負荷の作成
- 反復的なテストによるボトルネックの特定
Chapter 4. 負荷試験のツール
実は攻撃ツールを用いて思ったように負荷を作るのは難しい。その難しさをこの章では説いてくれる。
大量のユーザをプログラムの多重化したスレッドで模擬するため現実の負荷とは振る舞いが異なる場合がある。
- 攻撃ツールが計測するレイテンシは中継のネットワークやSSL符号化処理の遅延が入っている
- 多重リクエストのための攻撃スレッドの同時起動を増やすと攻撃ツール自身の負荷になる
- 攻撃スレッドの動作はシーケンシャルなのでレスポンスが来るまで次のリクエストは送れない (tail latencyの影響が大きい)
- 現実では複数ユーザの計算リソースを使ってリクエストするが攻撃ツールでは計算リソースが限られる
- DNSキャッシュの影響でリクエスト先エンドポイントが限定される (GSLBを使っている場合)
このように負荷ツール自身やその実行環境が要因となって想定した負荷が生成できないということは容易に起こりうる。 それほどに陥穽が多いからこそ、本格的に負荷試験に入る前に負荷ツール側のボトルネックを解消しておく工程が必要になる。 本試験の前にプレ試験のようなフェーズを想定するべきだし、当然スケジュールにもそれを反映しなければ誤った負荷条件のまま試験を進めてしまうことになる。
Chapter 5. 負荷試験の計画
負荷試験は反復的に進めるので所要期間の確定は難しい。 初めてそのシステムで負荷試験をするならなおさら不確定要素が多いので最低でも数週間を見積もったほうが良い。 負荷試験のスケジューリングが後回しになりがちだと、充分な期間が確保できず欲しい精度のデータが取れないまま負荷試験を終えざるを得なくなってしまう。
自分が今まで経験したプロジェクトでは負荷試験の扱いはそれぞれで、入念に実施したところもあればリリース間際にばたばたと実施して焦りながら結果をまとめたりすることもあった。 入念に実施できたプロジェクトではそもそも一回のリリースが特大に大きかったので、その分潤沢に検証の期間が確保できていた、という背景もあるが。 よりリリースが頻繁に発生するプロジェクトでは性能試験も回帰的に実行できるように、本書の内容以外にも自動化の仕組みを別途作る必要がありそう。
上記のスケジュールに関する計画以外にも計画時点で決めるべきことは多くある。
- 試験目的
- 目標性能
- 試験環境
- 試験ツール
- 試験シナリオ
などなど。
このうち試験目的については一般的に下記のようなものが挙げられる。
- 応答性能の計測
- スケール特性の把握
個人的には「どのユースケースでの性能を評価すべきか」という点を決定するのが重要でありかつ難しいと感じる。
ユースケースの選定は「性能計測の意義のあるユースケース」を見極めるのが勘所となる。 これについてはまずはホワイトボックス的目線で対象コンポーネントを眺める必要がある。 外部I/Oを含むようなユースケースではボトルネックが発生しやすいので例えば、
- DBの参照
- DBの更新
- 外部システムとの連携
などを行っている箇所を中心にユースケースを選んでいくことになる。 I/Oの特性を考慮するのであればやはりコンポーネントの内部構成を知っている方がスムーズにユースケース選びができるように思える。
Chapter 7. 負荷試験の実施1 と Chapter 8. 負荷試験の実施2
これらの章では負荷試験のスケールを徐々に上げていくステップが説明されている。 最初はテスト対象のサーバ上で負荷をかけるところから始める。 いきなり大きなスケールで試験をしてしまうとどこがボトルネックなのかを簡単に切り分けられなくなるからだ。 対象システムと負荷ツールの間に介在するものをできるだけ減らしてノイズの少ないデータを採取するのがこの初期の負荷テストの目的となる。
このように小さい規模・スコープでの負荷試験から始めて、やがてLBを挟んだりスケールアウトさせる。 初期の試験では単体でのボトルネックが無いことが明らかであるため、スケールアウト後の負荷試験ではスケール特性そのものに集中して測定値を評価することができるようになる。
負荷試験は一回実施すれば終わりではなく、何度も条件を変えてボトルネックを追い詰めていく探索的な活動であることが分かる。
全体的に
本書ではいかに一つの負荷試験を成功させるかに焦点が当てられており、 まず負荷試験で確実にデータを集めたいモチベーションにはしっかり答えてくれるだろうと思った。 読んだ後に頭をよぎるのはこうした負荷試験の自動化の仕組みだ。
途中にも書いたが負荷試験が一回限りで終わる、ということは昨今のプロダクトのライフサイクル的に有り得ない。 定期的に計測してリリースとボトルネックの関係自体を観察していく継続的な活動が必要になる。 そのための技法はこの本では語られておらず、これを読んだ自分がさらなる応用編としてリサーチ・実践をしていくことになる。
その他 参考
性能試験関連でここ最近とても楽しかったサイボウズのsatさんの記事をおもむろに貼っておく。
計測したい指標を決めて、関心のあるデータをとるためのテストケースと条件作りが本当にスマートで良い試験だなと思った。 自分もいつでもこういう試験ができるようになりたい。
負荷試験といえば時雨堂さん