メルカリさんのオフィスで開かれたMachine Learning Casual Talks (MLCT) #10に「教師なし学習によるMackerelの異常検知機能について 〜設計/運用/評価の観点から〜」というタイトルで登壇してきました。
MLCTは機械学習をサービスで運用していく知見を共有する勉強会です。YouTube等で動画配信を積極的にしてくださっていて、はてなの京都オフィスでも鑑賞会と称してランチタイムに同僚と発表を見させてもらっていました。普段から勉強させてもあっていた勉強会に、登壇という形でちょっとはお返しできているとうれしいです。登壇させて頂き、ありがとうございました!
私の発表資料はこちらです。スライド46枚ありますが、発表は15分だったので本番はこれの短縮バージョンで発表させてもらいました。
. @syou6162 さんのMackerelの異常検知の話。教師なし学習がproduction乗ってるの胸熱 #MLCT
— Aki Ariga (@chezou) 2019年5月29日
@chezouさんのこういうTweetもありましたが、開発者の僕自身結構胸熱(?)で、発表の見所としてはMackerelというプロダクトの概念にフィットするものを、運用が大変にならないようにいかにシンプルに作るか、というところです。具体的にはこういう感じ。
- どの単位で異常検知モデルを作るか
- 全体で一つだと大きすぎる、ホストに一つだと細かすぎる
- Mackerelというサービスの根幹にある「ロール」という概念をうまく利用する
- ロールは例えば、はてなブログのDBサーバーというようなグルーピングのことです
- 異常検知のために特別な設定をしてもらうというより、Mackerelの概念に沿って使ってもらえば、異常検知も自然とうまく動作するような設計を目指した
- プロダクトが先、機械学習が後
- ホストを異常と判定したときに、その根拠をどうやって提示するか
- 世の中的には、ブラックボックスのモデルを人間が解釈可能な近似したモデルを用意する(例: LIME)のが主流になりつつある
- しかし、運用観点では管理しないといけない機械学習モデルが増えて厳しい。予測のlatencyの増加という観点からも望ましくない
- 異常判定に使っている混合ガウス分布の条件付き確率分布を計算し、どのメトリックが異常かを判定している
- 混合ガウス分布は性質のよい確率モデルがベースにあるので、条件付き確率も閉じた形で書き表わせる
- 根拠提示用にもう一つモデルを用意する必要がない
- 混合ガウスを使っていたとしても、混合数が大きかったり次元数が高いとlatencyなどの観点では厳しいが、ここでも「ロールに対してモデルを作る」ということが効いてくる
- ロール内では状態数はそこまで多くならないので、混合数はそこまで大きくする必要がない
- 判定に必要な次元数を抑えるため、ドメインエキスパート(つまり監視のプロである社内のSRE)にどの特徴量は削っても監視には影響なさそうかヒアリングしにいった
- 誤検知を防ぎたいが、教師なしであるモデルの挙動を人間の直感とどう合わせるか
- ほぼ動きがないメトリックがほんの少し動いた場合、モデルは異常と判定するが人間はそれを誤報と感じる
- なるべく人間の直感に合うように振る舞わせたいが、教師ラベルを整備して制御といったことは教師なしではできない...
- 混合ガウス分布を選択したことがここで生きる
- 混合ガウス分布は由緒正しき(?)確率的生成モデルであるので、分散の事前分布に「memoryで全体のX%くらい変動するのはまあありえるよね」といった人間のドメイン知識を埋め込む
- 継続的な改善
- 自動で取れる数値はダッシュボードにまとめているが、手動でのアノテーションでのシステム評価にそれなりに力を入れている
- ほぼ全ての異常検知によるアラートに目を通し、正しいアラートか誤報かのアノテーションをしている
- 誤報率を時系列でトラッキング
- 誤報の中でカバレッジの大きいものに関しては改善の施策を実施、施策の実施後には再度アノテーションをして実際に改善しているか確認、というのをひたすら繰り返している
発表に対する反応
障害の基準がお客さんで違ったり、1ヶ月異常がなかったりするから、教師あり学習は厳しい->教師なし学習でやっている #MLCT
— takuoko (@takuoko1) 2019年5月29日
モデルをロールごとにわけることで、似たデータで1つのモデルを作れる #MLCT
— takuoko (@takuoko1) 2019年5月29日
異常検知の要件. モデルが軽量・検知の根拠がわかる・RecallよりもPrecision重視 #MLCT
— NSK (@naohachi89) 2019年5月29日
後者2つの話はTensorflow Data Validationの論文でも触れられてましたね.アラート周りは偽陽性が多いとオオカミ少年になってしまって見られなくなってしまうし, 根拠がないと次のアクションに繋がらないのでそれはそうという. #MLCT
— NSK (@naohachi89) 2019年5月29日
大量のモデルを作るので、学習は低コスト、判定もリアルタイムの必要があるのでGANやAEは避ける。近傍法は学習コストは低いが予測時のmodelのloadに時間がかかる。ので、混合ガウス分布を使っている #MLCT
— takuoko (@takuoko1) 2019年5月29日
メモリ面・速度面・コスト面を考慮して混合ガウス分布を採用 #MLCT
— NSK (@naohachi89) 2019年5月29日
解釈性, 実務でやってるとめっちゃ大事 #MLCT
— NSK (@naohachi89) 2019年5月29日
GMMの根拠を条件付き確率から計算してるのか。妥当だ #MLCT
— Aki Ariga (@chezou) 2019年5月29日
異常検知あるある 検知漏れvs誤検知のコントロールの難しさ#MLCT
— にのぴら (@nino_pira) 2019年5月29日
Mackerelでは検知漏れよりも誤検知を減らそうとしている。数十MBのメモリ使用量が増えたのを「異常」と検知してしまった #MLCT
— Aki Ariga (@chezou) 2019年5月29日
評価指標がいろいろあり、どれも見ている
— takuoko (@takuoko1) 2019年5月29日
複数評価指標としてもちながら、全体のバランスを見て向上してるか評価するタスクは多そう #MLCT
latencyを向上させるために圧縮などはしていないが、混合数をなるべく低くしてモデルサイズを小さくしている #MLCT
— takuoko (@takuoko1) 2019年5月29日
合わせて読みたい