メニュー

公開日:
7 min read
エンジニアリング

サーバー増強ゼロで負荷を100分の1にした話【前編】- 制約が生む創造性

サーバー増強ゼロで負荷を100分の1にした話【前編】- 制約が生む創造性のイメージ

よくある質問 (FAQ)

センター試験合否判定システムの初年度の問題は何でしたか?

午前1時の公開と同時に数万人が一斉にアクセスし、タワーサーバー1台が轟沈しました。一人あたり平其5〜6大学を登録していたため、数十万クエリが1秒間に集中し、データベースが即死したのです。

なぜサーバー増強の提案が拒否されたのですか?

「2〜3年後に生徒数が10万人を超えたら、また同じ問題が起きる」と正直に答えたためです。ボトルネックはDBにあり、Webサーバーを増やしても根本解決にならないことを正直に伝えた結果、サーバー代は出さないという決定になりました。

このシステムの独自性は何でしたか?

「配点」+「ルール」という新しいアプローチを考案しました。「英語と国語のうち、高い方の得点を採用」「数学だけ400点換算」などの複雑な条件に対応するため、Prologのような論理型プログラミングの考え方をヒントにルールベースの判定エンジンを実装し、どんな複雑な配点方式にも柔軟に対応できるようにしました。

制約が創造性を生むとはどういう意味ですか?

「サーバーを買えば解決する」という選択肢があったら、それ以上の工夫はしなかったでしょう。サーバー購入ができないという制約が、「アクセスさせない」という逆転の発想を生んだのです。正直に「将来的に問題が起きる」と答えたことで、別の道を探すしかなくなり、結果的に最高の解決策が生まれたのです。

記事後編で明かされる解決策のヒントは?

何らかの方法で「アクセスさせない」ことを実現し、午前1時の「針のような鋭いピーク」を消滅させました。後編では「枯れた技術」を使ったことが示唆されていますが、詳細は後編で明かされます。

サーバー増強ゼロで負荷を100分の1にした話【前編】

はじめに:釣られた皆様へ

最新のチューニング技術や、革新的なアルゴリズムを期待してクリックした方、申し訳ない。この記事にそんな高尚な話は出てこない。

でも、もしかしたら、もっと大切なことを持ち帰ってもらえるかもしれない。

地獄の初年度 - センター試験直後の戦場

20年前、某大手塾のセンター試験合否判定システムを学生チームと開発していた。

システムの流れ

   graph LR
    A[受験生] -->|自己採点を入力| B[判定システム]
    C[入試センター] -->|速報値発表<br/>平均点・標準偏差|     D[塾担当者]
    D -->|判定ライン設定<br/>鉛筆なめなめ| B
    B -->|23時〜判定処理開始| E[DB]
    E -->|午前1時| F[Webサーバー公開]
    F -->|結果確認| G[数万人が一斉アクセス]
    G -->|リロード地獄| H[サーバー死亡💀]

受験生は複数の大学・学部を最初から登録できた。東大理Ⅰ、京大工学部、早稲田理工…第一志望から滑り止めまで、一度に判定を受けられる仕組みだ。

初年度、地獄を見た。

午前1時の公開と同時に、数万人が一斉にアクセス。タワーサーバー1台が見事に轟沈。

アクセスログを見ると、ピークは公開後2〜3時間続いていた。だが、これは見かけの数字だ。本当はもっと鋭いピークだったはずが、サーバーがさばききれずに平坦化されただけ。実際は、午前1時の瞬間に全員が殺到していたのだ。

正直者がバカを見る?

翌年に向けての対策会議。

我々には500万円のF5ロードバランサーがあった。これを貸し出すことは可能だ。あとはWebサーバーを数台買ってもらえれば…

クライアント:「それで絶対に解決するのか?」

私:「とりあえずは解決します。でも、2〜3年後に生徒数が10万人を超えたら、また同じ問題が…」

クライアント:「じゃあ、サーバー代は出せない」

正直に答えすぎた。でも嘘はつけない。ボトルネックはDBだ。Webサーバーを10台に増やしても、全てのリクエストは結局1台のDBに集中する。根本解決にはならない。

500万円のロードバランサーは、結局うちの倉庫で眠ったままだった。

発見した事実

真のピークの鋭さを理解して、改めて分析した。

  • 午前1時の瞬間、数万人が「同時に」DBに問い合わせ
  • 一人あたり平均5〜6大学を登録
  • つまり、数十万クエリが「1秒間」に集中していた可能性
  • DBが即死するのは当然

そして、もう一つ重要な事実。皆、最初の結果確認のためだけに殺到していた。

実装した解決策

[ここでは具体的な解決策は書かない]

とにかく、ある方法を実装した。コストはゼロ。既存のリソースだけを使った。

改善後のシステムフロー(ネタバレ注意)

   graph LR
    A[受験生] -->|自己採点を入力| B[判定システム]
    C[入試センター] -->|速報値発表<br/>平均点・標準偏差| D[予備校担当者]
    D -->|判定ライン設定| B
    B -->|23時〜判定処理開始| E[DB]
    B -->|処理中に随時| M[メール送信]
    M -->|判定結果詳細| I[受験生のメールボックス]
    E -->|午前1時| F[Webサーバー公開]
    F -->|別の大学・学部で<br/>再判定したい人| J[少数のアクセス]
    J -->|余裕| K[サーバー生存😊]

結果 - CPU使用率10%以下の奇跡

翌年の結果発表日。同じタワーサーバー1台。同じDB。サーバー追加ゼロ。

午前1時、Web公開。去年なら、DBが火を噴く時間だ。

しかし…ピーク時でもCPU使用率は10%を超えなかった。DBへのクエリは激減。アクセスしてくるのは、自己採点を見直したい人や志望校を再検討したい人だけ。余裕を持ってシステムを使えた。

当社が考案して開発した合否判定システムの強みは、それまで存在しなかった複雑な配点方式に対応したことだった。

他社のシステムは、DBに配点(英語200点、数学100点…)しか入れていなかった。しかし、実際の大学入試はそんな単純ではない。

  • 「英語と国語のうち、高い方の得点を採用」
  • 「数学だけ400点換算」

こういった複雑な条件に対応するため、私は**「配点」+「ルール」**という新しいアプローチを考案した。

DBには配点だけでなく、判定ルールも格納する。Prologのような論理型プログラミングの考え方をヒントに、ルールベースの判定エンジンを実装した。これにより、どんな複雑な配点方式にも柔軟に対応できるようになった。

20年前、これは革新的だった。数年後には他社も似たような仕組みを実装し始めたが。


次回【後編】では、この解決策の真相と、20年後の今につながる教訓について語ります。