ISUCOの勝ち方

以下の動画の視聴メモ
https://www.youtube.com/watch?v=vl1mYTq1ZYI 

ISUCONとは

概要

  • アプリケーションのコードを書き換えられないコンテストへのアンチテーゼ
    • レギュレーションの中で何でもあり
  • 7時間、まる一日かけてチューニング
    • ISUCON1: ブログコメント欄 by livedoor
    • ISUCON2: チケット販売 by NHN Japan
    • ISUCON3: nopaste/画像投稿+TL by 面白法人カヤック
    • ISUCON4: パスワードリスト攻撃/動画公開 by cookpad
    • ISUCON5: by トレジャーデータ
  • ISUCONから生まれた技術
    • Kossy
    • Gazette
    • Redis::Jet
    • Plack::Middleware::Session::Simple

順位

  • ベンチマークで判定
    • スピードだけでなくエラーチェックも兼ねている
    • (チェックされていないエラーは無視できる?)

何故Webアプリのパフォーマンスが重要か

  • UX: ちょっとでも待たせるとユーザは離れる
  • KPI: Googleはスピード見てる、1秒遅れると
  • インフラコスト
    • AWS EC2の例
    • (クラウド時代ではちょっとした改善がそのままお金になる。。。)

勝ち方

準備編

  • 持ち込み機材?
  • チーム編成
    • 一人ではむり!
    • うまく分担して効率よく、ミスを減らす
    • コミュニケーションコスト
      • お互い何が得意かを知っておく、一緒に業務がベスト
      • (一緒に仕事はできないから...よく話し合おう)
  • コミュニケーション
    • チームメイトとの会話を重視しよう
      • 本線では目の前にいる
      • (予選は? 環境の良い場所に集まろう)
    • 決まったことは書き出す
      • 手戻りの防止
  • 時間配分
    • チームで認識を合わせる
    • たとえば
      • 最初の1時間は課題理解、プロファイリング(?)、方向ぎめ
      • 最後の30分は再起動テスト
        • 再起動したらアプリが起動しない、変更がもとに戻るなど
  • 事前準備
    • Private Git Repo
    • Wiki
      • メンバーの公開鍵
      • 秘伝のタレ
        • Webサーバのconfファイルとか
    • Chat room
      • Dicord?
    • 技術選択の打ち合わせ
      • 言語?ミドルウェア?
      • 現時点で提供される言語はPerl/Ruby/Go
    • 過去問
      • Vagrantだと負荷高いので、EC2やComputeEngineなどがいいかも

チューニングの進め方

  1. 課題の理解
    • レギュレーション、当日の説明をよく読む
    • スコア算出方法、失格条件は重要
      • エラーの許容数、ペナルティなど
    • 実際に課題サイトへブラウザでアクセス
    • とりあえずベンチマークを動かす
      • しばらく動かさないチームもいる...動かしとけ
      • 疎通確認として、たまに初期設定やハズレインスタンスがある
  2. プロファイリング
    • Webアプリで起きていることを知る
      • アクセスログ
        • ベンチマークがアクセスしている先を知る
        • 頻度とレスポンス時間
          • 「重たいところが優先」とは限らない、スコア計算方法次第
        • ツール(ISUCON向けに作られている)
          • analyze_apache_logs
          • kataribe
        • フォーマット->既存ログ消去->ベンチマーク実行
          • 普段はaccess_log消すとかしないし...
      • MySQLのSlowLog
        • クエリ実行回数と頻度を見る(Webサーバと一緒)
          • 速いけど回数が多いやつに気をつける
            • set global slow_query_log = 1;
            • set global long_query_time = 0; ですべてのクエリを読める
            • set global slow_query_log_file = <path to file>
            • ベンチマーク取るときはMySQLを再起動してもとに戻す(上記はconfにはかかれない)
        • ツール
          • pt-query-digest
            • pt-query-digest <path to file>
      • アプリケーションのプロファイリング
        • 各言語のプロファイリングツール
        • 発表者は言語単位より以下をよく使う
          • strace
            • システムコールレベルでアプリケーション動作確認
          • tcpdump
            • 通信内容のキャプチャ
      • サーバ負荷の確認
        • top
        • iftop: Network
        • iotop: Disk I/O
        • dstat
        • 使い慣れたものを
          • (そんなものはない)
    • プロファイリングを読む力を養っておく
  3. サーバ構成の把握
    • どのようなサーバ、ミドルウェアが動いているか
    • 設定ミスやTypoの罠も
      • Memcacheと思ったらプラグインだった...とか
  4. チューニングの方法を決める
    • ISUCONではスケールアウト/アップなし
    • 効率の良いCPUの使い方
    • チューニングすべき対象
      • 大量データの参照
      • 他サーバとの通信、特にラウンドトリップのコストが大きい新規通信
      • 大量プロセス/スレッドの調節
        • コンテキストスイッチを減らす
    • 目指すアプリケーション: 極力何もしないアプリに近づける
      • 参照を減らす・しない
      • 通信を減らす・しない
      • プロセスやスレッドを減らす・使わない

チューニングのヒント

  • Webサーバの選択
    • Apache v. Nginx
    • Nginx v. h2o
      • Nginx: プロセス、設定は色々できる
      • h2o: スレッド、コンテキストスイッチが有利
  • アプリケーションのチューニング
    • わかりやすい重い処理
      • 外部プロセス起動
      • HTMLテンプレート
      • テキスト、画像の変換
      • RDBMS/Cacheとの接続
      • N+1問題
  • DB
    • 心にいつもB+Treeを
      • (何いってるかよくわからなかった)
    • MOTTAINAI精神
      • MySQLのOFFSET
      • 捨てるデータの読み取りを最小限に
    • ISUCONでは「メモリに載っても遅い」と思ったほうがいいかも

大事なこと

  • 初期状態を記録し、いつでも戻せるように
  • 変更を都度記録し、壊れる前の状態に
  • 前日はよく寝る
  • 「諦めたらそこで試合終了」/ 「戦いは最後の五分間にあるのよ」

Q&A

  • 複数環境でやるか、みんなで同じ環境触るか
    • 発表者の経験では同じ環境のほうがいい
    • 最終的に提出できるのはひとつ
  • 幅広いレイヤ知識はどう仕入れたか
    • 経験値、キャリアの長さ
    • 自分でサービス作ってみる
    • 大規模サービス作っている会社で働く
  • MySQL Pagingの質問
    • Redisで範囲絞る工夫
    • 捨てないように書く
    • 捨てる部分を減らす
  • 「賭け」に出るタイミングは?
    • 慣れていること、秘伝のタレは最初にやっちゃう