肉汁爆弾

いろいろメモっていきます

ISUCON10の予選突破のふりかえり

みなさんお久しぶりです。ブログは半年ぶりですが元気にやってます。

9/12にISUCON10の予選があり、我々チーム「カレーおじさん」は無事予選を突破してきました。わーわー。
ブログを書くまでがISUCONということで、何をやっていたかなどを振り返って記しておこうと思います。
レポジトリはこちら
github.com

@tatsumack の振り返りはこちら
tatsumack.hatenablog.com


作戦

選択言語

go

方針

「推測するな計測せよ」の格言のもとに、常に計測しつつボトルネックの解消を行う。具体的には、ベンチマーカーの実行中のプロセスの状況、
アクセスログ、クエリの実行ログを眺めるなどなど。着手順は計測した結果を参考に、効果がでそうなところから。
また、複数台構成については「2,3台目のサーバーをどういう役割にするべきか」が開始直後では判断できないと考え、ある程度のボトルネックを解消してから始めることとした。(例えば最初はDBがボトルネックだったが、クソクエリをいくつか直したらアプリケーションがボトルネックになる、といったような具合に)

分担

去年と同じ、元同僚なメンバーで参戦。

tatsumack( tatsumack (@tatsumack) | Twitter ): インフラ担当
各種計測の設定、アプリケーションコードをgithubで管理する、deployのscriptを用意するところから着手。
インフラレイヤーでのボトルネック解消を行う担当。

sugaret(僕です): アプリケーション担当1
レギュレーションや要項に目を通す、サービスの概要を把握する。エンドポイントやDDLの把握から着手。
アプリケーション/DBレイヤーのボトルネック解消を行う担当。

masakingp: アプリケーション担当2
ローカルでアプリケーションが動くようにするところから着手。
アプリケーション/DBレイヤーのボトルネック解消を行う担当。

事前準備

データの共有などはslack。流れてしまう情報を残しておこうと思い、スプレッドシートを作成・共有したがあんまり活用の機会はなかった。

タイムライン

9:00

物理集合。開始が遅れることがわかったので技術書展などを眺めながら作戦会議。

12:00 ISUCON予選開始

アクセス過多?によりベンチマーカーが実行できない状態だった。
・レギュレーション/当日マニュアルなどを熟読
・サーバー上の isuumo配下をgit管理
・ローカルで実行環境を構築
・本番での動作確認
・計測系ツールの追加

13:00〜16:00 ベンチマーカーが動くように(score: 371 -> 655)

ベンチマーク実行して、dstatやtopを見る、slow queryを見る、access_logを見たりして怪しいポイントをリストアップ
・slow queryに色々あった&mysqlのcpu使用率が100%で張り付いてたので、slow queryの上位から順番にボトルネック解消(主にindex追加)
・とりあえず指定のあったbotのリクエストをフィルターする実装をしたり(*1)

16:00〜17:00(score: 655 ->906)

・popurarity DESC, id ASCに対して「id ASC消して良くない?(≒popurarityが同じ値ないんじゃね?)」という雑な対応をしてみる(*2)
・その他クエリもindex追加など改善を続ける

17:00〜18:00(score: 906 -> 1109)

・geometryの処理(なぞって検索)をmysqlでやっていたのをgolang側に移植する
・おすすめイスのクエリ改善

18:00〜19:00(score: 1109 -> 1321)

・この辺の時点でもまだmysqlボトルネックだったようなので、web-DBの2台構成に変更
・(*1)の処理が原因?で整合性チェックにたまに落ちる状況だったので切戻した

19:00-20:00 (score: 1321 -> 1622?)

・(*2)の処理が完全に網羅できていないことに気づき、全botリクエストが弾けるように修正。
・上記修正後に1622のハイスコアを叩き出すもcancelledになり、その後は1300台が続く。(ベンチのbotリクエストの量にランダム性があった?)
・この時点でもまだmysqlボトルネックだったので、3台目もDBの構成にして着手し始める

20:00-21:00 リーダーボードが隠される(score: 1622? -> 2608)

・ギリギリのギリまで3台構成が上手く動かず、インフラ担当のtatsumack以外は作業内容のレビューなどを行いつつ実現を目指し、20:50時点でようやくベンチが通り、2608を叩き出して歓喜
ベンチマークの上振れ/下振れを考えて、何度か実行するという選択肢もあったが、20時時点のリーダーボードの状況と、ベンチに落ちたときのリスクを考えてステイすることに。

21:00-24:00

・反省会的な晩ごはん。結果待ちなので気持ちが落ち着かない。
・再起動テストなども手元で行えていないため、とにかくお祈り。お祈りしながら帰宅。

24時ごろ

・配信で本選出場者としてチーム名を呼ばれて歓喜
isucon.net

・最後の10分まで、マジでずっとinitializeの段階でベンチ落ち続けていたので、通った瞬間は大きい声が出た
f:id:sugaret:20200913160530p:plain

よかったところ

・tatsumackがスタートダッシュでISUCONで毎回使うような計測ツール、nginx、mysqlの設定などを入れてくれたのめっちゃ差がついてそう。

・masakingpがgeometory関連のロジックをgolangのコードにサクッと書き換えてくれたの、そこそこ差をつけられたポイントな気がする。

・全体としての動き方の筋は悪くなさそう。計測した結果DBがボトルネックだからDBの改善をし続け、DBのスケールアップをして、、という順序で着実にスコアを伸ばせた感がある。

改善できそうなところ

・複数台構成を最初に着手しないという方針は悪くないと思うが、複数台構成で伸びる点数が割とデカいので、もうちょっと早く着手しても良かったかも。

・終わった後のdiscordでの他のチームの方との交流で、いろんなことを
見落としてることに気づく。たとえばechoのdebugモードを切るとか、計測ツールをoffにするなど。(特にechoのdebugモードについては、開始直後に気づいていたのに忘れてしまっていた。)今回は複数台構成でハマっていたので最終的に入れられたかは不明だが、「メンバーが暇な時間を作らない」という意味でも、todoリストを作って運用するとかしたほうがよかったかも。

所感

ISUCONは体験として「リアル脱出ゲーム」に近いなと思っています。情報共有/役割分担が重要な点も似ていますし、長時間があっという間に終わる感覚も非常に似ていると感じます。こんな濃密なエンタメがタダなんて!なんとオトクなんでしょう。
まだ終わっていないですが、運営の方々、長時間お疲れさまでした、ありがとうございます。本戦もよろしくおねがいします!100万円獲るぞ!