ISUCON12 予選突破
チーム「と」最終31962点で11位。
方針
「まずは SQLite のまま進める。テーブル単位で徐々に MySQL に載せ替えつつも、ボトルネック解消に専念し1台でこれ以上大きく伸びなそう。と思うタイミングで複数台使う。大体16時ごろを目処」と思っていたが、結局上手くいかず何も MySQL に載せることはなく最後まで1台のまま進めることにした。また、最後の1時間で MySQL だけでも分けようとも思ったが、ログ出力を消したことで FAIL するようになったことの対応に追われて叶わず。
スコアを伸ばせたのは
- MySQL ネックの解消
- visit_history への index 追加と dispenseID の xid 化
- SQLite に対する非効率なクエリの解消
- visitor/player count と rank を都度計算せずに保存する
- score の bulk insert
ぐらいだったと思う。
使ったツール
- alp
- pt-query-digest
- pprof
- top
やったこと
錯乱しながら作業していたのであまり正確ではない。
- 10:00 - 13:00
- 13:00 - 14:45
- pprof の有効化
- MySQL ネックではなくなったので、この後 pt-query-digest は使わずに pprof と top だけ見ていた
- 何も前進せず予選敗退の恐怖に支配され心が折れかける
- pprof の有効化
- 14:45
- 妻に「切り替えてやれ」と凄まれ、自然と予選敗退の恐怖は消えさった。妻に感謝
- 14:45 - 16:00
competition
テーブルにvisitor_count
/player_count
追加- 大会終了時に計算して UPDATE
- 16:00 - 17:00
ranking (competition_id [pk], ranking [pk], score, player_id [idx1], player_display_name)
テーブルを追加して、ページングして取得できるようにする/api/player/player/:player_id
でもこのテーブルを使った
- initialize が timeout するようになったので雑に並列に insert 投げて、sleep 2s している。sync.WaitGroup 使えよという感じがするが、FAIL を繰り返していたのでとにかく通したいという思いが先行した。
- player_score を bulk insert にする
- 17:00 - 18:00
- go-json を使う
- ログ出力をやめると to many files が出るようになったので LimitNOFILE を設定
- keepalive や connection pool のサイズを変更したりしたが特段効果なし
改めて振り返ると無駄なことで時間を消費していたことが分かるし、やろうと思ったことは全然出来なかった。ただ、時間内でもっと出来たとは思えず、まあまあうまくいったほうじゃないかなという気がしている。
このままでは本戦を戦えなさそうなので、何度か練習しておこうと思う。