CIサーバを制圧せよ！
プロジェクトメトリクスと自動化技術の活用よる
混乱の収拾と「最強」の組織の育成
Apr/16/2015
Hiroyuki Ito, Kazuhisa Naoi
Rakuten, Inc.
http://www.rakuten.co.jp/

自己紹介 (1)伊藤 宏幸 (The Hiro)@hageyahhoo アジャイルコーチ
 TDDグループ（当時）2自己紹介 (2)直井 和久
楽天株式会社
トラベルサービス開発・運用部
トラベルサービス開発課
Travel Extranetグループ

マネージャー3

この物語は、ここでの改善に挑んだ、実践者達の記録である。

4

お伝えしたいこと

1. プロジェクトメトリクス
2. 戦略策定の重要性

3. Infrastructure as Codeの有益性

4. Technology-Driven Development
5特にお伝えしたいこと！！

1. プロジェクトメトリクス

6アジェンダ
1. 課題の整理

2. 何を持って成果とすべきか？

3. どうやってCIサーバの負荷を減らすか？

4. どうメンバー・チームを育成していくか？

5. 結論
7

1. 課題の整理

2. 何を持って成果とすべきか？

3. どうやってCIサーバの負荷を減らすか？

4. どうメンバー・チームを育成していくか？

5. 結論
8

2014年6月末

Agile2014へ提出する論文とまさに格闘中の時期…
9

トラブル、襲来

CIサーバの負荷が高すぎて、期限通りにプロダクトをリリースできない！
これ以上CIサーバのジョブを増やしたら、サービスを提供できなくなる！
10

当時の我々の状況とあるQAプロジェクトの自動化を主導中• ビルドパイプラインの構築• リリース自動化の実現• スモークテストの構築

メインシステムの多言語化対応をマネージャとして主導中

お互い、CIサーバの設定・監視・運用には責務を持っていなかった。
11

立ち上がった。
生き残るために。
12

原因分析結果
誰も監視・メンテしていない！

スタンドアローン構成

重い…
400以上のジョブ（さらに増加の傾向）

Load averageが10を超えるのはザラ
実行待ちキューが10前後なのもザラ

そもそも画面すら開けないことが多かった。
• 「Script Console」を試すこと自体がバクチ
13

真因分析結果

組織横断的に、CIサーバ専任で動けるチームがない！
やるぞ～！

つくるぞ～！

有志のエンジニアたち

元々、ボランティアで構築・運用されていた。
14

真因分析結果

組織横断的に、CIサーバ専任ぐぬぬで動けるチームがない！
仕事多い (><)

誰かがきっと何とかしてくれる…！

有志のエンジニアたち• 問題が起きても放置されるようになってきた。
• サーバを常時監視する仕組みがなかった。
15

最初に実施した施策

CIサーバ専任の組織横断的チームの設置を提案した
負荷増大に対して、長期的・根本的に対応できるようにする中長期ビジョンの策定・実現にも責任を持つ常設チーム

正常稼動しないことが業務損失になる現状、常設・専任チームによる解決が必須と判断。
16

Jenkins Consolidation Team、結成。

※イメージです171. 課題の整理

2. 何を持って成果とすべきか？

3. どうやってCIサーバの負荷を減らすか？

4. どうメンバー・チームを育成していくか？

5. 結論
18

新たな課題何を成果として見せれば良いのか？

自分たちはどこに向かえば良いのか？

自分たちは正しい方向に進んでいると言えるのだろうか？
19

施策初期の悩み仕事である以上、成果をマネージャ層・ステークホルダーに「みせて」「喜んでもらう」
必要があるでも、そもそもCIサーバの成果って、何をどう見せれば良いのだろう？？？
試してみないと分からない仕事のため、常に振り返りながら新しい施策を打ち立て実施していく必要があった
20

解決策としてのプロジェクトメトリクス

成果としてマネージャ層・ステークホルダーに「みせ易く」「うれしい」数値を見つける
変化の見える数値を探す
定期的に数値をトラックし、特に施策実施前後の変化に注目する数値自体の有効性を常にチェックし、数値の変化の内容次第では、施策を見直す
21

プロジェクトメトリクスの前提として基本戦略・ロードマップをまず最初に明確化した。
22

特に注意した点プロダクトに関わる（極力）全ての人が合意できる目標になっているか？
（例）インフラ担当者もＯＫできる内容か？
エンジニア視点だけで満足した目標になっていないか？
• ビジネス価値の観点も含むべき持続可能な施策となっているか？
• ハネムーンナンバーは高くないか？
• 施策をリードできる人材は十分か？
23

基本戦略

1. 取り急ぎCIサーバの負荷を減らす• 高負荷ジョブを一時停止するなどして、一時しのぎと改善の時間稼ぎをする。
• 負荷分散用サーバを調達・整備し、ジョブを各サーバに「一時疎開」させる。

2. CIサーバのボトルネックを解消する• CIサーバ群をマスタースレーブ構成に改め、負荷分散を容易化する。
• 既知の技術負債等を1つ1つ解決し、CIサーバ群を「クリーン」にしていく。

3. CIサーバの使い方を教育していく
利用者（エンジニア）にCIサーバの「正しい」使い方を教えることで、技術負債・トラブルの芽を摘むと同時に、利用者の育成も図る。

4. 専任チームを後進に引き継ぐ• 伊藤・直井がリードする体制から、育成も兼ねて後進にタスクを引き継ぐ。
• 結果として、CIサーバの「正しい」使い方をさらに広めることも図る。
24

ロードマップ

25

苦悩と歓喜の始まり26

1. 課題の整理

2. 何を持って成果とすべきか？

3. どうやってCIサーバの負荷を減らすか？

4. どうメンバー・チームを育成していくか？

5. 結論
27

ご覧の有様
誰も監視・メンテしていない！

スタンドアローン構成

重い…
400以上のジョブ（さらに増加の傾向）

Load averageが10を超えるのはザラ
実行待ちキューが10前後なのもザラ

まずはこれを解決する！
28

段階的なアプローチを採用

その時点で計測可能なプロジェクトメトリクスに絞って見せることとした
29

施策
30

(1) 単純にCIサーバ数を増やす
まずメイン機の負荷を減らす

次のステップのための時間稼ぎをする

負荷の高いジョブを一時疎開する

弐号機

参号機

メイン機4台増強

量産機

量産機
31

(2) マスタースレーブ構成を適用する
マスターサーバに改造ジョブを分散実行

スレーブ1

監視の仕組みも導入・強化（後述）

マスター

スレーブ2

スレーブ3

スレーブ4
32

(3) Infrastructure as Codeを適用する
マスターを正とし、設定をスレーブと同期

Immutableなので壊されても復元可能
設定がコードなので分かりやすい

スレーブ1

マスター

スレーブ2

スレーブ3

スレーブ4
33

成果
34

インフラの整備状況の予実実施した施策

予定

実績

1ヶ月

1週間

マスタースレーブ構成を適用する

1～2ヶ月

1週間

Infrastructure as Codeを適用する

2ヶ月

1ヶ月

単純にCIサーバ数を増やす[要因]• 直井さん主導による、インフラ担当者との迅速な折衝• 若者の人間離れ（≒メンバーの予想以上のがんばり）35直井さんによる交渉・施策のポイント• インフラとの交渉は、施策実現のために必要なことをやったに過ぎない。
• この時点で、次への布石を着実に打っておいた！

36

アラートメール数の推移にみる負荷減少
アラートメール数 (2014/08/01 - 2014/09/30)
130
125
120
115
110
105
100
95
90
85
80
75
70
65
60
55
50
45
40
35
30
2520
15
1050

8月
241通

9月
108通
55.2%の削減！

サーバのload averageが10を越えたらこれを通知する仕組みが元々あったため、これを活用した。

37

Infrastructure as Codeの有益性 (1)

採用前

採用後1週間30分[要因]• コミュニケーションミスによる依頼の往復を、ほぼ無くすことができた• エンジニアが動作確認したものをインフラ担当者が実施するだけなので、作業自体が容易になった• 万が一トラブルが起きても、Immutable Infrastructureなので簡単に復旧できる

38

Infrastructure as Codeの有益性 (2)以前のインフラ運用体制

madokaグループのhomuraユーザで、Tomcatを起動・停止できるようにしたい

startup.shの権限を、774から777に変更してほしい

エンジニア

インフラ担当startup.shの権限を、777に変更しました
shutdown.shが実行できない！
homuraユーザがmadokaグループに入っていない！

39

Infrastructure as Codeの有益性 (3)以前のインフラ運用体制
コミュニケーションミスが多発しがち

エンジニアやり取りが多くなりがちで時間がかかる

インフラ担当個々のサーバで構成が異なることが多いため、事前確認で漏れを無くすことが困難

なぜその作業を依頼されたのか、その意図・目的までは伝わりづらい

実際に動作確認するまでは安心できない

指示された通りの設定は（大体）できる

大概、依頼内容および設定結果に誤りがある

大概多忙なので、作業が後手にまわりがち40

実際に面倒な目に遭いました…

Infrastructure as Codeを使って、このやり取り自体を無くしてしまいましょう！
41

Infrastructure as Codeの有益性 (4)
新しいインフラ運用体制

エンジニア

インフラ担当依頼前に各自のPCで構築・動作確認が出来る

Recipeとテストコードを実行すれば良い

必要な全ての設定は、Recipeとテストコードとして残せるダメだったら設定を戻せばよいので、作業上のリスクが少ない

RecipeとテストコードのPull Requestで、手戻りの少ない作業依頼が出来る
42

（再掲） インフラの整備状況の予実実施した施策

予定

実績

1ヶ月

1週間

マスタースレーブ構成を適用する

1～2ヶ月

1週間

Infrastructure as Codeを適用する

2ヶ月

1ヶ月

単純にCIサーバ数を増やす

43

マスターサーバが軽くなったので、もう一工夫を。

44

「もうひと工夫」の重要性

メール１つ取っても、１つ１つ着実に改善を続けたことの積み重ねが、成果を出せる組織の土台になっていく。

45

アラートメール (1) ：改善前
09:40:04 up 154 days, 19:14, 2 users, load average: 11.59,
11.32, 7.16
[Heavy Process Top 10] CPU(%), Proccess
そもそもスペルが165 xxxxx
間違っているぞ！
• uptimeコマンドを使っているが、情報が冗長• CPU使用率の高いプロセスは特定できるが…
• プロセスのユーザは特定できない• 何が問題でどう解決すれば良いのかの情報が少ない• メモリ使用率の高いプロセスは分からない• どのジョブが原因なのかを特定できない46

アラートメール (2) ：改善開始
Load average: (1.03, 1.05, 1.23)--- Top 10 Heavy CPU consumers --tomcat xxxxx--- Top 10 Heavy Memory consumers --ito xxxxx--- Jobs currently running --- Sayaka• uptimeコマンドの実行結果を、load averageのみに絞った• CPU使用率に加え、メモリ使用率の高いプロセスも特定・出力するようにした• 当該プロセスのユーザを特定・出力するようにした• 原因となるジョブ名を特定・出力するようにした
但し、一番下に出力しているため、都度メールを一番下まで見なければならない
47

アラートメール (3) ：更なる改善
Load average: 10.0, 5.2, 2.4--- Jobs currently running --- Sayaka--- Top 10 Heavy CPU consumers --tomcat xxxxx--- Top 10 Heavy Memory consumers --ito xxxxx
原因となるジョブ名を、メールの最初に出力するようにした• ジョブの特定が非常に容易になった（メールを開けば一目で分かる）• 問題のあるジョブの特定と原因調査が、非常に容易になった• と言うよりも、この時点で初めてこれができるようになった48

（特に負荷の高い）ジョブの実行頻度とその推移
ジョブ名

MadokaHomuraSayakaAnko
MamiCharlotte
QBHitomi
Uro-Buchi

負荷の高いものから（スレーブへの移行などの）対応を優先的に行なう
これを週次で関係者へメール通知することで、自発的な活動を促す

アラートの頻度32
17151313
432249

失敗から学ぶアジャイル

最初から全情報を計測するのではなく、出来るところから徐々に集めていけば良い
全部が全部役に立つ情報ではない→役に立つ情報だけを計測すれば良い
プロジェクトメトリクスを定期的に振り返り、適宜見直しを行なう必要がある

想定外の状況が生じることもままある→積極的に活用することをまず考えよう50

電撃的勝利！

※イメージです51

1. 課題の整理

2. 何を持って成果とすべきか？

3. どうやってCIサーバの負荷を減らすか？

4. どうメンバー・チームを育成していくか？

5. 結論
52

2014年9月下旬

楽天テクノロジーカンファレンス
絶賛準備中の時期ですよ。
53

成果の報酬としての新たなタスク部の2014年度（～12月）の目標として、全プロダクトのUTのラインカバレッジを65%以上にすることが設定されていたCIサーバの負荷軽減・改善が想定以上に速く進んだため、この目標もスコープに含めることとした
54

UTカバレッジを目標に設定した狙い• UT自体を、組織・エンジニアに習慣付けること。
• 達成度を活用して、メンバーのモチベーションを高めること。

55

UTカバレッジに関する当時の課題
UTカバレッジの計測手段とメトリクスの不足
1301251201151101051009590858075706560
5550454035302520151050

ツールの乱立• Cobertura• Emma(JaCoCo)• djUnit…

12.3%

施策をリードするメンバーの不足
56

（一方で）マスターサーバの更なる負荷軽減の効果
Viewを使えるようになった！

ツールを統合し、CoberturaとJaCoCoの2つに絞ることとした

CIサーバを自発的に色々と試すメンバーが増えてきた

マスター
スレーブ

次のステージに移れる！
57

(1) Viewを作成し、カバレッジを常に誰でも確認可能にした

Cobertura

JaCoCo58

(2) カバレッジの推移を、週次で記録・報告するようにした

計測対象ジョブ数74

うちカバレッジを取得している数

67

目標達成済
ジョブ数

達成率

先週比を追加し、成長の共有と成果の強調を図った

35

47.3%
(+18.9% WoW)
59

(3) 各グループからメンバーを徴発し「65%チーム」を組織した対象グループ：約10

CIサーバを自発的に色々と試すメンバーを優先的にアサインした

このチームを介して、UTカバレッジ向上の効率化を目指した
60

成果としてのUTカバレッジの目標達成率の推移
目標達成率の推移
90.0%

正直、年末に30%超えが現実的な目標と考えていた

80.0%

計測対象ジョブの絞り込みを実施

70.0%
60.0%

50.0%

16.7%

84.1%

40.0%
30.0%
20.0%

週次計測・報告による確実な前進

10.0%
0.0%

61

実際に成果を出してみて数値をキチンと計測するということから始めないと、
そもそも改善なんて生まれませんよ！

62

完全勝利！！

※イメージです631. 課題の整理

2. 何を持って成果とすべきか？

3. どうやってCIサーバの負荷を減らすか？

4. どうメンバー・チームを育成していくか？

5. 結論
64

最終的な成果

リリース遅延を解決し、再発しないようにした

CIサーバのスケールアウトを実現
・550前後のジョブが現在稼働中
後進を育成し、専任チームそのものを引き継いだ65

ロードマップ（予定）66ロードマップ（実績）

67

残課題

IT/STレベルのテストの自動化がまだまだ不足している

テスト環境でデータ競合が生じる• Immutable Infrastructureで…
リリース自動化がまだ不十分• Blue-green deploymentを…
68

新たな課題• UTカバレッジを上げさえすれば品質も上がるだろうという安易な幻想を、一部マネージャに持たせてしまいそうになった。
• 改善が劇的だったがゆえに、簡単に改善ができるものと勘違いされがち。

69

成功につなげるアジャイル戦略と（特に自動化）技術との融合による高速なPDCAサイクルの実現

PDCAサイクルの有効性を高めるためのプロジェクトメトリクスの発見・計測・見直し

上記の組み合わせによる人材・組織育成とコラボレーションの拡大70プロジェクトメトリクスのポイント

考えることのプラスになる情報を見つけよう• 現状の問題はどこにあるのか？
• 改善施策の効果はあったか？

数値の変化に意味を見いだそう• 数値の変化にこそ、真の知識が詰まっている• 変化が見える情報を見つけることが勝利の鍵

メトリクスを定期的に振り返り改善していこう• 役に立たなければ、潔く捨てる覚悟も必要• 足りなければ創ろう

コミュニケーションの手段として活用しよう• 今まで分からなかった情報を元に話をしてみると、更なる発見が得られる
7190.0%

全ては計測から80.0%

計測対象ジョブの絞り込みを実施

70.0%

60.0%

50.0%

40.0%

30.0%

20.0%

16.7%

84.1%
週次計測・報告による確実な前進

10.0%

0.0%

72

滾らせろ！