pixiv insideは移転しました! ≫ https://inside.pixiv.blog/

秒間50kリクエストを捌くノウハウがこの1冊に!nginx実践入門

こんにちは、@harukasanです。ピクシブでは3年以上にわたってHTTPサーバにnginxを採用しています。これらのノウハウが詰まった「nginx実践入門」が1/16(土)、技術評論社から発売されることになりました。

f:id:harukasan:20160115160510j:plain

この記事では本書からピクシブで良く使われているnginxのテクニックについてかいつまんで紹介します。

すべてのリクエストを受け止めるnginx

ピクシブのたくさんあるサービス(pixiv、pixiv Spotlight、pixivコミック、ピクシブ百科事典……)のどこかにHTTPリクエストを投げると、複数台あるフロントサーバのどれかに届きます。実際にアプリケーションを処理するのはフロントサーバの裏側にいるアプリケーションサーバです。これらのサーバにはPHPだったり、Ruby on RailsだったりPlay/Scalaだったりいろんなアプリケーションがデプロイされています。

このアプリケーションサーバにリクエストを割り振る役目をしているのがnginxです。ピクシブで動いているすべてのnginxのリクエストを合わせるとピーク時で秒間50kリクエスト以上にもなります。

f:id:harukasan:20160115123851p:plain

サービスごとにバックエンドを切り替え

ピクシブでは同じアプリケーションであっても機能ごとにサーバを分けて運用しています。すべてのリクエストを区別せずにサーバに分散しても良いですが、これだといくつか問題があります。

  • どの機能がどれだけCPUリソースを必要としているかわかりづらくなってしまう
  • ある機能が障害になるだけでサービス全体が影響を受けてしまう

これらの問題を解決するため、ドメインやパスなど様々な条件で複数のアプリケーションサーバにリクエストを振り分ける必要があります。

f:id:harukasan:20160115124747p:plain

こういう設定はnginxが得意とするところです。実際にピクシブで使っている設定を貼っておきました。

# nginx.conf
http {
    ...
    include "conf/definition_upstream.conf";
    include "sites-enabled/*.conf";
}
# sites-enabled/www.pixiv.net.conf
server {
    server_name www.pixiv.net;
    ...
    location /upload/ {
        proxy_pass http://backend_upload;
    }

    proxy_pass http://backend_www;
}
# sites-enabled/touch.pixiv.net.conf
server {
    server_name touch.pixiv.net;
    ...
    location /upload/ {
        proxy_pass http://backend_upload;
    }

    proxy_pass http://backend_touch;
}
# conf/definition_upstream.conf

# www用サーバ
upstream backend_www {
    server 192.0.2.1 weight=10;
    server 192.0.2.2 weight=10;
    server 192.0.2.3 weight=1; # なぜか負荷が高くなるので
}

# touch用サーバ
upstream backend_touch {
    server 192.0.2.11 weight=20; # 強いサーバ
    server 192.0.2.12 weight=20; # 強いサーバ
    server 192.0.2.13 weight=10;
}

# アップロード用サーバ
upstream backend_upload {
    server 192.0.2.21 weight=10;
    server 192.0.2.22 weight=10;
}

このようにアップロード機能用のサーバやサービス専用サーバなど複数種類のクラスタにリクエストを振り分けています。クラスタごとに負荷をモニタリングすることで、チューニングすべきポイントや負荷の分析がやりやすくなります。

また、upstreamディレクティブの設定はバーチャルサーバごとの設定ファイルと別ファイルに分割して管理しています。こうすることで、サーバに障害が起こった場合や追加/削除を行う場合、upstream定義を書き換えて配るだけで簡単に済ませることができます。

アクセスログを1つにまとめて収集する

これら大量のログはユーザー分析、問題発見に非常に重要なデータになることがあります。また、なにか問題があった場合には過去のログをすべて精査して調べる必要があるかもしれません。ピクシブではこれらのログをFluentdを用いて各種サービスに転送することで、問題解決に役立てています。

f:id:harukasan:20160115125246p:plain

nginxはaccess_logディレクティブを並べて書くことで1つのリクエストに対し複数のログを出力することができます。これを利用することで、サービス固有のログの他にサービス共通で記録するログを出力するように設定しています(これをglobal_access.logと呼んでいます)。共通ログ形式はLTSVです。LTSVを用いることで、Fluentd側の設定を変更することなく新しいフィールドを追加することができます。

http {
    access_log /var/log/nginx/global_access.log global;
    ...
    server {
        # サーバごとに設定する場合、globalの設定をもう一度定義する必要があることに注意
        access_log /var/log/nginx/global_access.log global;
        access_log /var/log/nginx/www.pixiv.net_access.log pixiv;
        ...
    }
   
    server {
        ...
    }
    ...
}

ピクシブのノウハウが詰まった書籍「nginx実践入門」

さて、最後に宣伝となりますが、冒頭にも触れた、ピクシブのノウハウが詰まった1冊「nginx実践入門」が発売されます(PDF版はGihyo Digital Publishingで購入できます)。

nginx実践入門 (WEB+DB PRESS plus)

nginx実践入門 (WEB+DB PRESS plus)

弊社が3年以上にわたって運用してきたnginxの様々なノウハウが詰まった1冊です。アプリケーションサーバの構築をはじめとして、HTTPS、本文中で触れたログ解析などピクシブで実際に使われている様々な技術、運用ノウハウについて網羅的に紹介することを目指しました。ピクシブの社内マニュアルとしても便利な1冊に仕上がっています。是非お手にとって頂ければ幸いです。