ハローワークのサイトはなぜ重いのか、外部から調べてみた
リニューアル初日にダウンしたハローワークのサイトを外部から技術調査。1.6KBのCSSの配信に28秒。CDNなし、gzip圧縮なし、HTTP/2非対応、1ページ76リソース。5つの問題が連鎖していた。
コラム
kkm
Backend Engineer / AWS / Django
何を調べたのか
2026年3月23日、ハローワークインターネットサービスがリニューアル初日にダウンしました。3.5日間の全面停止メンテナンスを経ての再開直後に、サイトが極端に重くなり、ハローワーク窓口の検索端末まで影響を受ける事態になっています。
公式の説明は「アクセス集中」だけ。でも、月間8,500万アクセスのサービスをリニューアルして「アクセスが集中しました」は説明になっていません。外部から観測できる範囲で、何が起きているのかを技術的に調べてみました。
使ったのはcurl、dig、ブラウザの開発者ツールなど、誰でも使えるツールだけです。内部のソースコードやサーバー構成にアクセスしたわけではありません。
結論から言うと、1.6KBのCSSを28秒待っている
いきなり核心です。ブラウザが求人検索ページを表示するとき、CSS 26本 + JavaScript 16本の合計42ファイルをサーバーからダウンロードします。ブラウザは通常6本の並列接続でこれを処理しますが、この42ファイルの取得に28秒かかりました。
最も遅かったのはfloat_style.cssというわずか1.6KBのファイル。このファイルの配信に28秒。ファイルの中身が重いのではありません。サーバーの前で順番待ちをしているだけです。
| ファイル | サイズ | TTFB |
|---|---|---|
| float_style.css | 1.6KB | 28.1秒 |
| searchList.css | 2.3KB | 15.9秒 |
| tooltip.css | 1.7KB | 10.5秒 |
| ECA110.js | 数KB | 6.9秒 |
ファイルサイズとTTFBに相関がありません。1.6KBのCSSが28秒で、数KBのJSが7秒。これはファイルの転送時間ではなく、サーバーの処理キューで待っている時間です。先に並んだリクエストが終わるまで、後ろのリクエストは何もできずに待つしかない。これがページの表示を致命的に遅くしている原因です。
ここから先は、なぜこうなっているのかを1つずつ確認していきます。
CDNが使われていない
CDN(コンテンツ配信ネットワーク)とは、世界中に配置されたサーバーにコンテンツのコピーを置いておき、ユーザーの近くのサーバーから配信する仕組みです。大規模サイトでは必須のインフラです。
ハローワークインターネットサービスは4つのサブドメインで構成されています。DNSを引くと、それぞれ別のAzure IPアドレスが返ってきます。
| サブドメイン | 用途 | IPアドレス |
|---|---|---|
| www | トップページ・求人検索 | 20.44.143.206 |
| kyujin | 求人(事業主向け) | 20.78.255.246 |
| kyushoku | 求職(求職者向け) | 20.27.131.39 |
| jinzai | 人材(人材紹介向け) | 20.210.74.214 |
全てMicrosoft Azure(東京リージョン)のIPです。CDNを使っていれば、CloudFrontやAkamaiのCNAMEレコードが返りますが、そのような設定はどのサブドメインにもありません。
一般的な大規模サイトでは、CSSやJavaScriptなどの静的ファイルはCDN経由で配信し、アプリケーションサーバーにはリクエストを到達させない構成を取ります。ハローワークの場合、静的CSSのレスポンスヘッダー(ETagのフォーマットやTTFBのばらつきパターン)を見る限り、静的ファイルも動的ページと同じ経路を通って配信されているように見えます。
内部構成は外部からは確認できないので断定はできませんが、少なくともCDNを経由していないことは確実です。前述の「キュー待ち」が起きるのは、本来CDNが吸収すべき静的ファイルのリクエストまでサーバーが処理しようとしている可能性があるためです。
CSS・JSが圧縮されずに配信されている
Webサイトでは、CSSやJavaScriptをgzip圧縮して転送するのが標準的です。テキストファイルは圧縮効率が高く、サイズが1/3〜1/5になります。
ハローワークのサーバーにAccept-Encoding: gzip, deflate, brヘッダーを付けてリクエストしても、レスポンスにContent-Encodingヘッダーは返ってきません。gzip圧縮が有効になっていないということです。
具体例を挙げると、jQuery 3.6.3のファイルは304KBがそのまま転送されています。gzip圧縮すれば約90KBまで縮小できます。求人検索ページのCSS合計340KB + JS合計694KB = 約1MBが無圧縮で配信されている計算です。
ファイルが大きいまま転送されるということは、コネクションが長く保持されるということです。コネクションが長く保持されるということは、サーバーの同時処理スロットがより長く埋まるということです。圧縮しないことが「キュー待ち」をさらに悪化させています。
静的ファイルにキャッシュ制御がない
CSSファイルのレスポンスヘッダーを確認すると、以下のようになっています。
HTTP/1.1 200 OK Content-Type: text/css Content-Length: 30600 Last-Modified: Fri, 20 Mar 2026 06:20:27 GMT ETag: "7788-64d6eae63032b"
Cache-ControlもExpiresもありません。ブラウザに「このファイルをどのくらいキャッシュしていいか」を明示的に伝えていないということです。
Last-ModifiedとETagはあるので、ブラウザ側のヒューリスティックキャッシュは多少効きますが、CDNやリバースプロキシが適切にキャッシュするにはCache-Control: max-age=...の明示が必要です。仮にCDNを入れてもこのままではキャッシュが効かない可能性があります。
1ページで76リソース、HTTP/2非対応
求人検索ページのHTMLを取得して中身を分析すると、以下の構成でした。
| 項目 | 通常検索 | かんたん検索(新設) |
|---|---|---|
| HTML本体 | 122KB | 37KB |
| CSSファイル | 26本(合計340KB) | 14本 |
| JavaScriptファイル | 16本(合計694KB) | 6本 |
| 画像 | 45枚 | 5枚 |
| ページ重量 (画像除く) | 約1.15MB | - |
興味深いのは、今回のリニューアルで新設された「かんたん検索」は通常検索の約1/3のリソース量に抑えられていること。新しく作った部分はちゃんと軽い。問題は既存の通常検索ページです。
さらにこのサイトはHTTP/2に対応しておらず、HTTP/1.1で動いています。HTTP/1.1では1つのTCP接続で同時に1リクエストしか処理できません。ブラウザは6本の並列接続を張りますが、76リソースを6並列で取得すると13ラウンド。各ラウンドでキュー待ちが発生するため、CSS+JSだけで28秒という結果になっています。
並列接続で線形に遅くなる
CDNなしのサーバーに並列接続した場合の応答時間を計測しました。
| 同時接続数 | 全完了までの時間 |
|---|---|
| 1接続 | 0.3秒 |
| 10並列 | 2.1秒 |
| 20並列 | 6.2秒 |
| 30並列 | 10.9秒 |
同じ静的CSSファイルに対するリクエストで、接続数に比例して遅くなっています。これはサーバーの同時処理スロットが埋まり、後続のリクエストがキューで待たされていることを意味します。
これは1人のユーザーからの接続数です。月曜朝に数千人が同時にアクセスすれば、数万の並列接続が発生します。先ほどの28秒は「1人分」の待ち時間であって、実際のピーク時にはさらに悪化していた可能性が高いです。
サーバー構成から見えること
求人検索ページのCookieには、以下のようなJSESSIONIDが含まれています。
Set-Cookie: JSESSIONID=...OCP_APPLICATION_6-1; Path=/kensaku; HttpOnly; Secure
末尾のOCP_APPLICATION_6-1はRed Hat OpenShift Container Platform(OCP)のPod識別子です。複数回アクセスすると、Pod番号が6, 7, 8と変わることから、少なくとも3つのPodが稼働しており、ラウンドロビン方式でリクエストが分散されていることがわかります。
トップページのETagフォーマット("a4a3-64daa17ef7a94"、先頭のa4a3はファイルサイズ42,147バイトの16進表記と一致)から、WebサーバーはApache httpdと判定できます。
また、トップページ(静的HTML)と検索ページ(動的)ではjQueryのバージョンが異なります(トップ: 3.2.1、検索: 3.6.3)。Font Awesomeのディレクトリ名も微妙に違う(ハイフン区切りとドット区切り)。別々のチームまたは別のタイミングでデプロイされた痕跡です。
なぜ28秒もキュー待ちが発生したのか
補足しておくと、これらの問題があるからサイトが動かない、というわけではありません。実際、同日夜間にはTTFB 0.1秒で正常に動いています。インフラ構成は昼間と全く同じ。HTML 1バイト変わっていないし、CDNもgzipも追加されていません。アクセスが減っただけです。
つまり、通常のトラフィックであれば問題なく動く構成です。ただし、今回のようなアクセス集中が起きたときに逃がす仕組みがない。それが以下の5つです。
① 1ページに76リソース。求人検索ページを1回表示するだけで76個のHTTPリクエストが発生します。
② CDNなし。76リクエスト全てがオリジンサーバーに直撃します。CDNがあれば、静的ファイル(CSS, JS, 画像)はCDNが返すのでサーバーには到達しません。
③ gzip圧縮なし。jQuery 304KB、CSS合計340KBが無圧縮で転送されます。圧縮すればサイズは1/3以下になり、コネクション保持時間が短縮されます。アクセス集中時にコネクションが長時間占有されることで、キュー待ちを悪化させます。
④ HTTP/1.1のみ。1接続1リクエストの制約があり、ブラウザは6並列接続で13ラウンド処理する必要があります。HTTP/2なら1接続で全リソースを多重化でき、接続数の問題自体が消えます。
⑤ キャッシュ制御なし。Cache-Controlヘッダーが未設定のため、2回目以降のアクセスでも条件付きリクエストが発生します。
普段は問題にならないこれらが、アクセス集中時に一気に牙をむきます。
リニューアル初日の月曜朝 → 3.5日間の溜まったアクセスが殺到 → 1人あたり76リクエストがサーバーに直撃(①②)→ 無圧縮ペイロードでコネクションが長時間占有(③)→ HTTP/1.1の制約で接続数が膨張(④)→ サーバーの処理スロットが埋まる → 後続のリクエストがキュー待ち → 1.6KBのCSSが28秒待ち。
平時に見えない問題が、ピーク時にだけ表面化する。今回のリニューアル初日は、それが最悪の形で現れたケースです。
この調査の限界
この記事は外部からの観測結果に基づいています。以下の点は確認できていません。
- ? サーバーの台数やスペック(Podは3つ確認できたが、それ以上あるかもしれない)
- ? データベースの構成や負荷状況
- ? リニューアル前と後でインフラ構成が変わったかどうか
- ? 負荷テストが行われたか、その結果はどうだったか
- ? OpenShift Router(HAProxy)やAzure Load Balancerの設定
ただし、「1.6KBのCSSの配信に28秒かかる」「gzip圧縮が無効」「CDNが存在しない」「HTTP/2非対応」は、外部計測で再現可能な客観的な事実です。
とはいえ、中の人の苦労はわかる
外から「CDN入れろ」「gzip有効にしろ」と言うのは簡単です。でも、似たような規模のSIer案件をやっていた身としては、現場の大変さも想像できます。
例えば、既存のインフラをそのまま使わなきゃいけない。DBのデータ構造は変えられない。セキュリティ要件でCDNの導入に省庁の承認が要る。設定変更1つに変更管理委員会の審査が必要。テスト環境と本番環境でネットワーク構成が違う。「gzip有効にするだけ」でも、申請書を書いて、レビューを通して、テストして、承認をもらって、リリース手順書を作って、夜間にリリースして、切り戻し手順も用意する。そういう世界です。
技術的に正しいことと、組織的に実行できることの間には、深い溝があります。
それでも、です。
直したろか
繰り返しますが、サイト自体は動いています。夜間の計測ではTTFB 0.1秒で快適に使えています。問題は「次にアクセスが集中したときに同じことが起きるリスクが残っている」ことです。
CDN入れて、gzip有効にして、Cache-Control付けて、HTTP/2有効にして、CSSとJSをバンドルする。これらは「サイトを動かすため」ではなく、「アクセス集中時に崩れないようにするため」の対策です。どれも枯れた技術で、新しいことは何もありません。
とくにCDNとgzipは即効性があります。CDNを入れるだけで静的ファイルのリクエストがサーバーに到達しなくなり、gzipを有効にするだけでペイロードが1/3になる。ピーク時のキュー待ちを大幅に減らせるはずです。
ちなみに、今あなたが読んでいるこのブログはCDN + HTTP/2 + キャッシュ制御済みで、TTFBは0.03秒です。月間8,500万アクセスのハローワークが、ピーク時に12.7秒。
1,025億円の契約の中に、これらが含まれていなかったのだとしたら、それはそれで問題です。
参照元
- • ハローワークのサイトがリニューアル初日にダウン(関連ニュース記事)
- • ハローワークインターネットサービス(計測対象サイト)
- • IPinfo.io(20.44.143.206 = Microsoft Azure, Tokyo)
- • 計測手法:
curl -wによるTTFB計測、digによるDNS確認、HTTPレスポンスヘッダーの分析、並列接続負荷テスト