ISUCON8予選で惨敗してきた話

ISUCON8に、 @bgpat_ (あーちゃん)と @Owl_Works (おうるさん)と三人で出て、惨敗してきました。

あーちゃんのブログ記事

bgpat.hateblo.jp

 

 

前日まで

チームメンバー集め

まず、今年から僕は社会人枠になってしまったので、社会人枠で出てくれるメンバーを探す必要がありました。とりあえずあーちゃんに声かけました。

一人目ゲット。

二人目、誰にしようか。

 ※@showwinさんはISHOCONの主催者兼作問者

断られる。残念。来年は是非!

ISHOCON2当日を迎える。

ISHOCON2で遊ぶ。

帰ってからISHOCON2についてと、メンバー募集の求人ブログ書く。

おうるさんもメンバー求めていたらしく、声がかかる。

無事三人チーム結成される!

チーム名決め

メンバー三人、僕が馬であーちゃんが犬、おうるさんがフクロウだよねって話になった。

f:id:Goryudyuma:20180921005756p:plain

他にいい案も思いつかなかったので、「Bremen」 に決まりました。

練習会

YahooのLODGEに集まってISUCON7予選を、それから夜中にISUCON4予選をやって、当日の流れとかをやりました。でも、明らかに練習量が足りなかった。 

お互い何ができるか、どんなことが得意か、どんなことなら任せられるか、どれくらいやればどれだけ体力が残ってるかなどなど、チームメンバーのステータスを知り、お互いを信頼して。こういったことができてない(できない)即席チームは、とても弱いです。うーん、来年以降、本気で決勝目指すなら、そこからやらねばな。

当日

mixiさんのオフィスをお借りしました、ありがとうございました!

当日の流れとしては、あーちゃんのブログ以上のことは書けないので、省略するとして。ここからは反省タイムです。

まず、調査の結果GetEventがとんでもない回数呼ばれて遅いものであることがわかりました。

少し話は変わりますが、ISUCONって、学生枠での攻略法と社会人枠での攻略法は全然違うと考えています。具体的には、例えばボトルネックになるポイントが問題内に3つあるとして、学生枠で通るには2つ改善してあとを定数倍早くする、もしくは三つ改善する、くらいで通るというのが僕の肌感覚です。一方で社会人枠は三つとも改善は当たり前で+α何か改善した状態、くらいが社会人枠での突破ラインとなると思います。また、共通点としては再起動試験には絶対に落ちないようにすること、ってのが挙げられます。後は運です。

このように考えていたので、このN+1問題が解決しないと、根本的に点数は伸びなさそうだなーって考えからこのN+1問題に固執してしまい、さらに何箇所からも呼ばれている関数だったのに「それ自体を早くしないとどうしようもないよね」とか言って、分割は最低限で超大きいまま取り組んでしまいました。超大きいまま取り組むと解けないのは当たり前ですね。

また、最終的に三箇所全てに同じアプリケーションを配置する方針も少しあって、その制約のせいで例えばエンドポイントによって捌くサーバーを変える分割が気軽にできませんでした。これは完全に方針ミスです。

三箇所に同じものを配置する方針となった理由の一つは、最初のレギュレーションを読んだ時に、帯域が詰まってくるだろうと予想したから(三つとも同じものを配置してやれば帯域は三倍使えるという過去のISUCONの知見から)なのですが、そもそもベンチマーカーが一箇所にしかアクセスできない仕様と判明した時点でもう一度確認して、完全に頭の中から消し去るべきでした。調査に基づかない方針決めは本当に良くないです。

また、今回使ったデプロイ環境のせいでもあります。今回、ビルドはローカルでやってバイナリだけscpでサーバーに設置する、というデプロイのやり方でやりました。こうすることで外部パッケージの依存関係で問題を起こして本番環境を壊したりしない、同じ変更を三台のサーバーそれぞれに入れる必要はないので変更入れ忘れ事故がなくなる、それぞれ自分の環境でのビルドになるので作業中のコンフリクトが起きにくい、といったような十分なメリットがあるので採用されました。Golangはクロスコンパイルできるからこその作戦ですね。しかし、三台のサーバー全てに同じバイナリが設置されるので、それを念頭に置いた方針になってしまいました。

Redisに乗せる案もかなり初期から一応あるにはあったのですが、結局乗せ始めたのは中盤が終わりかけになってからという微妙な時間になってしまいました。これに関しても、Redis化に消極的だった僕が悪いです。Redis化に消極的だった理由は、初期ベンチマークから何かがエラーで、まともに全部Successでベンチマークが通ったことがとても稀だったからです。初期実装からエラーが出ていた理由がトランザクションがきちんと張られていなかったからっぽい?のですが、本番中はそこまでわからず、何だかよくわからないけど、例えばMySQLに入れる順番が大事(直前に練習したISUCON4予選問題)とかの隠れ仕様があり、結局Redis化しても点数伸びずに終わってもおかしくないなと思ったからでした。量が量でしたし、やるならもうRedis化に全て賭けるしかなかったですしね。それよりも確実にボトルネックとなるN+1問題の方が優先度が高いと考えていました。

こんな感じで、学生枠とは全然違った戦略を、特に練習時間も多く取れない状態で挑んだ結果の、当然の爆死でした。

感想

今年は問題が重すぎて辛かったですね。(ISHOCONの問題量に慣れてしまった可能性が微レ存・・・?)

あーちゃんはとてもデキるエンジニアなのですが、彼の作るインフラは本当に最高です。僕の方がついていけず、うまく使いこなせてないことが多かったです・・・。ただ、慣れてくると本当にいいものであることは間違いないです。

初めて組んだおうるさんも仕事がとても早くてびっくりしてました。いつの間にかタスク全部終わってる・・・みたいな感じでした。もしRubyならもっともっと活躍できたはずなので、本当にすごいエンジニアなんだなと思いました。

僕自身、Golangから少し離れていて、今ではたまにしか書かなくなってしまいました。もっと早く書けたはずなのになあ。精進が足りない。実装力をもっと鍛えねば。

足を引っ張ってしまい、二人には本当に申し訳ないです。

ISUCONはまともな環境でエンジニアしていると、どんどん弱くなっていく競技でもあると思っています。なぜなら、「永続層のDBとか、とりあえずぶっ壊してでも、なんとしてでも早くしよう」なんて思い浮かばなくなるだろうからです。まあ正攻法だけで勝てるほど強くなると、また違ってくるんでしょうけど。

そんなわけで、来年、どうなるかわからないですけど、本気で本戦目指すなら、ちゃんと練習して挑みたいですね。