連載
» 2014年06月17日 18時00分 公開

これから始める人のためのNginx(1):高速・軽量・高機能……Nginxの基礎知識 (2/2)

[鶴長鎮一,@IT]
前のページへ 1|2       

高速処理の秘訣はイベント駆動

 Nginxが大量のリクエストでも同時に高速処理できるのは、イベント駆動方式を採用しているためです。

 Webサーバーのように同時に複数の処理を行うには、ディスクやネットワークといったI/Oの多重化が必要になります。I/O多重化の実装には「select」や「poll」といったシステムコールが従来使われています。

 Apache HTTPでプロセスベースやスレッドベースのMPM(マルチプロセッシングモジュール、注6)を選択すると、こうしたシステムコールが使用されます。select/pollでは、プログラムがアクセスするファイルネットワークソケットなどをOSが識別するための「ファイルディスクリプター」を1つ1つチェックします。チェックするディクリプタが増えれば処理にかかる時間も比例(注7)して長くなり、同時リクエスト数が2倍になれば処理に掛かる時間も2倍に膨らみます。

 Niginxのイベント型では、I/O多重化を実装するのに「epoll」システムコールを使用します。epollではディスクリプターの状態がカーネル内で管理されるため、プログラムが1つ1つチェックする必要がなくなります。この場合、処理にかかる時間はリクエストによらず一定(注8)になります。そのためNginxは、万単位のリクエストも高速に効率良く処理することができます。

 また、メモリの使用量が少ないのも特徴です。Apache HTTPのプロセスベースやスレッドベースのMPMでは、リクエストを処理するのにプロセスやスレッドを起動するため、使用するメモリもリクエスト数に応じて増加します。一方Nginxは単一プロセスで全てのリクエストを処理するため(注9)、リクエスト数に応じてメモリ使用量が変化することはありません。

 Nginxの省リソースの恩恵は、数万単位のリクエストを処理するような大規模サイトだけではなく、組み込みPCやマイクロサーバーのように限られたリソースしか使用できない状況にも有効です。

注6 Apache HTTPにはepollシステムコールを使ったevent MPMもあります。

注7 処理数nに比例して計算量が増える場合「0(n)」と表記します。

注8 処理数によらず計算量が一定の場合「0(1)」と表記します。

注9 Nginxのプロセス数はCPUやコア数に増減できます。


Nginxの主な機能

 Nginxの主な機能は次の通りです(以下、「http://nginx.org/ja/」より抜粋)。

基本的なHTTP機能

  • スタティックなインデックスファイルの提供、自動インデクシング、オープンなファイルディスクリプターキャッシュ
  • キャッシングで高速化されたリバースプロキシ、シンプルなロードバランシングとフォールトトレランス
  • リモートのFastCGIサーバーのキャッシングによる高速化サポート、シンプルなロードバランシングとフォールトトレランス
  • モジュールアーキテクチャ
  • SSLとTLS SNIサポート

他のHTTP機能

  • ホスト名ベースとIPベースの仮想サーバー
  • KeepAliveとパイプライン接続のサポート
  • 柔軟な設定
  • クライアント処理を中断させることなく再構成、オンラインアップグレード
  • アクセスログフォーマット、バッファーされたログ書き込み、素早いログローテーション
  • 3xx-5xxエラーコードのリダイレクト
  • rewriteモジュール
  • クライアントのIPアドレスをベースにしたアクセスコントロールとHTTPベーシック認証
  • PUT、DELETE、MKCOL、COPY、MOVEメソッド
  • FLVストリーミング
  • 速度制限
  • 同一アドレスからの同時接続もしくは同時リクエストの制限
  • 組み込みPerl

Apache HTTPとの性能比較

 試しにNgixとApache HTTPの性能を比較してみましょう。今回はIaaSサービスの「Digital Ocean」上にWebサーバーと評価を行うクライアントの2インスタンスを作成し、Apache HTTPのベンチマークソフト「ApacheBench」で評価を行います。なお結果はコンテンツの種類、ネットワーク環境やサーバー構成などで変わるため、ここでの結果は参考程度に留めてください。

 abコマンドをリスト1のように実行します。「-n」で総リクエスト数を、「-c」で同時接続数を指定します。abコマンドの結果については、1秒当たりの処理リクエスト数の平均を表す「Requests per second」に注目することにします。

$ ab -n 総リクエスト数 -c 同時接続数 http://対象URL
例)$ ab -n 10000 -c 100 http://サーバーのアドレス/test.jpg
リスト1 abコマンドの使用方法

 サーバー/クライアントのスペックは表1の通りです。NginxにはUbuntu標準の「Nginx 1.4.6」を使用します。設定を一部変更し、CPUの数に合わせて「worker_processes 1;」としました。Apache HTTPには「Apache 2.4.7」を使用し、MPMにはpreforkを別途インストールしています。Ubuntu 14.04のデフォルトではevent MPMがインストールされますが、今回はあえてプロセスベースのprefork MPMで差が分かるようにしています。Apache HTTPの設定を変更し、大量のリクエストに対応できるよう「MaxRequestWorkers 250」としています。

構成 スペック
CPU 1CPU
メモリ 1GB
ストレージ 30GB SSD
OS Ubuntu 14.04_x64
表1 計測に利用したサーバーとクライアントのスペック

 総リクエストを1万、同時接続数を100とした場合の比較は図4の通りです。コンテンツには50KBのJPEG画像を使用しました。結果はNginxの方が一割ほど多くのリクエストを処理しています。計測中にサーバーの使用メモリをfreeコマンドで計測したところ、Nginxが数MBだったのに対し、Apache HTTPは数十MBほど消費していました。

Webサーバー リクエスト数/秒
Nginx 2140.19
Apache HTTP 1898.48
図4 同時接続数:100、総リクエスト:10000の場合の平均リクエスト数/秒(編集部注:初出時、誤解を招くグラフ表示となっておりました。お詫びして修正いたします)

 次に同時接続数を上げた場合の平均リクエスト数/秒の変化を調べたところ、Nginxは同時接続数が増えても目に見えて悪くなることはありませんでしたが、Apache HTTPは劇的に悪くなりました。Nginxが同時リクエスト数が増えても、処理能力に大きな変化がないことが分かります。また使用メモリも計測したところ、同時接続数が増えても消費メモリは数MBと変化がありませんでした。一方Apache HTTPは、同時接続数が増えるとメモリの消費量も増える傾向にあり、最大で100MBを超える消費が観測されました。

コネクション数 100 200 300 400 500
Nginx 2140.19 2142.32 2065.41 1959.25 1863.31
Apache HTTP 1898.48 1546.44 1484.95 1068.95 845.7
図5 同時接続数を変更した場合の、平均リクエスト数/秒の変化

次回予告

 Nginxの概要に続き次回はインストール方法や設定方法について解説します。Nginxは動作が軽量なだけでなく、設定の容易さもライト級です。

鶴長 鎮一(つるなが しんいち)

愛知県出身、東京都在住。1970年生まれ。大学在学中から地元ISPの立ち上げに係わり、紆余曲折を経て通信キャリアに勤務。企画からコーディングやインフラ構築まで幅広い業務に従事。@ITには2001年から数多くの記事を寄稿。その他、Software Design(技術評論社)や日経Linuxでの連載をはじめ、著書に『サーバ構築の実際がわかる Apache[実践]運用/管理』(技術評論社)、『rsyslog 実践ログ管理入門』(技術評論社)、『MySQL徹底入門 第3版』(翔泳社/共著)、『PHPによるWebアプリケーションスーパーサンプル〜リッチクライアント編〜』(ソフトバンククリエイティブ/共著)ほか多数。


前のページへ 1|2       

Copyright © ITmedia, Inc. All Rights Reserved.

RSSについて

アイティメディアIDについて

メールマガジン登録

@ITのメールマガジンは、 もちろん、すべて無料です。ぜひメールマガジンをご購読ください。