強大的負載均衡+靜態文件WEB服務器nginx實戰

當前比較流行的負載均衡前端服務器主要有apache(with mod_proxy),nginx,lighttpd,squid,perlbal,pound,或者若是你的域名服務商提供DNS級別的負載均衡,也能夠(就是一個域名隨機指向多個IP,定製性不高)。javascript

    之前本身經常使用pound做爲前端,它專一於負載均衡,支持https協議,配置還算簡單,不過漸漸發現功能不夠強大,轉而研究其餘一些既能夠作負載均衡,又能作web服務器的高性能工具吧。Perlbal是第一個看的,大牛Danga的傑做,它們開發的memcached(分佈式內存cache系統)很是好用,Perlbal也不差,雖然是基於Perl的,速度上比純C開發的可能稍遜,但不得不說Danga大牛實力非凡。不過公司的機器都是perl5.8.5,而Perlbal必須perl5.8.8以上,升級可能有兼容性問題,故只能做罷。php

    轉而研究nginx:Nginx ("engine X") 是一個高性能的 HTTP 和 反向代理 服務器,也是一個 IMAP/POP3/SMTP 代理服務器。 Nginx 是由 Igor Sysoev 爲俄羅斯訪問量第二的 Rambler.ru 站點開發的,它已經在該站點運行超過兩年半了。Igor 將源代碼以類BSD許可證的形式發佈。儘管仍是測試版,可是,Nginx 已經由於它的穩定性、豐富的功能集、示例配置文件和低系統資源的消耗而聞名了。 css

    中文維基地址:http://wiki.codemongers.com/NginxChshtml

模塊依賴:
1 gzip支持,須要zlib http://www.zlib.net/ 下載最新版便可
2 rewrite module requires pcre library http://www.pcre.org/ 下載最新版便可
3 ssl 功能須要 openssl 庫 http://www.openssl.org/ => http://www.openssl.org/source/ LASTEST版本便可前端

 

安裝過程:java

#下載以上source到/usr/local/src/nginx/目錄下,解壓,則該目錄下狀況以下:
[root@s16 nginx]# ls
nginx-0.6.32  nginx-0.6.32.tar.gz  openssl-0.9.8i  openssl-0.9.8i.tar.gz  pcre-7.8  pcre-7.8.tar.gz  zlib-1.2.3  zlib-1.2.3.tar.gz

cd nginx-0.6.32
./configure --with-pcre=../pcre-7.8 --with-zlib=../zlib-1.2.3 --with-openssl=../openssl-0.9.8i
make
make installmysql

 

#OK,安裝完成
#修改配置:
cd /usr/local/nginx
vi conf/nginx.conf
#例如,去掉例子中的8000端口的服務器配置的註釋
sbin/nginx -t -c conf/nginx.conf (測試配置文件是否正確)
[root@s16 nginx]# sbin/nginx -t -c conf/nginx.conf   
2008/09/17 15:26:55 [info] 15879#0: the configuration file conf/nginx.conf syntax is ok
2008/09/17 15:26:55 [info] 15879#0: the configuration file conf/nginx.conf was tested successfullynginx

 

sbin/nginx  (啓動)
ps aux | grep nginx | grep -v grep (查看是否正常啓動了)
#若是沒有正常啓動,查看errorlog,默認位置:/usr/local/nginx/logs/error.logweb

 

#通過apache bench測試,nginx在serve靜態文件方面性能不比apache(with mod_perl)好多少,基本上,以65K爲分界點,小文件時nginx性能好(最高能夠達到3倍左右速度),大文件時apache性能好(不過差異有限),因此純從速度上來說,nginx並不比apache強,不過nginx小巧,消耗資源少,若是你有不少靜態小文件須要serve,的確是個不錯的選擇哦。sql

     這裏推薦一種架構:

     1 前端nginx,並serve靜態文件,如圖片,js,css等,nginx是支持gzip壓縮的

     2 後端動態程序用fastcgi(lighttpd的spawn_fcgi便可),能夠支持php,perl等多種腳本語言了

 

     下面介紹一下nginx的經常使用配置:

  1. 靜態文件用nginx直接serve:

Nginx代碼  

  1. #css|js|ico|gif|jpg|jpeg|png|txt|html|htm|xml|swf|wav這些都是靜態文件,但應分辨,js、css可能常常會變,過時時間應小一些,圖片、html基本不變,過時時間能夠設長一些  

  2. location ~* ^.+\.(ico|gif|jpg|jpeg|png|html|htm)$ {  

  3.     root         /var/www/poseidon/root/static;  

  4.     access_log   off;  

  5.     expires      30d;  

  6. }  

  7. location ~* ^.+\.(css|js|txt|xml|swf|wav)$ {  

  8.     root         /var/www/poseidon/root/static;  

  9.     access_log   off;  

  10.     expires      24h;  

  11. }  

  12. #注:location不包括?後面帶的參數,因此以上正則能夠匹配http://192.168.1.16/image/sxxx.jpg?a=xxx   

  1. 打開gzip,壓縮傳輸

    Nginx代碼  

     

    1. gzip on;  

    2. gzip_comp_level 7;  

    3. gzip_min_length  1100; #須要壓縮的最小長度  

    4. gzip_buffers    4 8k;  

    5. gzip_types      text/plain application/javascript text/css text/xml application/x-httpd-php; #指定須要壓縮的文件類型  

    6. output_buffers  1 32k;  

    7. postpone_output  1460;  

  1. 查看nginx的狀態

    Nginx代碼  

     

    1. #設定查看Nginx狀態的地址(非默認安裝模塊,須要在編譯時加上--with-http_stub_status_module)  

    2. location /NginxStatus {  

    3.     stub_status            on;  

    4.     access_log             on;  

    5.     auth_basic             "NginxStatus";  

    6.     auth_basic_user_file   /var/www/poseidon/root/passwd;  

    7. }  

  2. 使用nginx的rewrite模塊

    Nginx代碼  

     

    1. #強大的rewrite模塊:  

    2. #文檔:http://wiki.codemongers.com/NginxHttpRewriteModule  

    3. #經典示例:rewrites http://www.mydomain.nl/foo => http://mydomain.nl/foo  

    4. if ($host ~* www\.(.*)) {  

    5.   set $host_without_www $1;  

    6.   rewrite ^(.*)$ http://$host_without_www$1 permanent; # $1 contains '/foo', not 'www.mydomain.nl/foo'  

    7. }  

    8.   

    9. #咱們的應用:rewrites 全部非www.popovivi.com的訪問 => http://www.popovivi.com/xxx  

    10. if ($host != "www.popovivi.com") {  

    11.     rewrite ^(.*)$ http://www.popovivi.com$1 permanent;  

    12. }  

  3. 最多見的nginx+fastcgi+php的使用

    Shell代碼  

     

    1. #nginx+fastcgi+php-cgi套路:  

    2. wget lighttpd1.4.19(or later)  

    3. wget php5.2.6(or later)  

    4. ./configure --prefix=/usr/local/lighttpd  

    5. make & make install  

    6. ./configure --prefix=/usr/local/php-5.2.6 --enable-fastcgi --enable-sockets --enable-force-cgi-redirect --with-gd --enable-mbstring --with-zlib --with-mysql --with-gettext --with-mcrypt --with-mime-magic --with-openssl   

    7. make & make test & make install(php.ini的默認讀取位置爲[prefix]/lib)  

    8. cp php.ini-dist /usr/local/php-5.2.6/lib/php.ini  

    9. /usr/local/nginx/sbin/spawn-fcgi -a 127.0.0.1 -p 10005 -u nobody -g nobody -f /usr/local/php-5.2.6/bin/php-cgi -P /var/run/fastcgi.pid -C 15  

    10.   

    11. #修改nginx的配置文件,使用fastcgi_pass http://127.0.0.1:10005做爲後端  

    12. kill -HUP `cat /var/run/nginx.pid`  #重啓nginx  

  4. nginx+fastcgi+catalyst(for perl users):

    Shell代碼  

     

    1. #Catalyst自帶文檔:  

    2. #http://dev.catalyst.perl.org/wiki//gettingstarted/howtos/deploy/lighttpd_fastcgi.view?rev=22  

    3. #以上文檔介紹的是lighttpd和catalyst的結合,本質是同樣的  

    4. #實際上也就是用自動生成的script/[myapp]_fastcgi.pl來啓動,剩下的事,就隨意啦(只是用什麼來作前端而已)  

    5. #首先安裝FCGI模塊  

    6. cpan  

    7. install FCGI  

    8. install FCGI::ProcManager  

    9.   

    10. cd /var/www/project/script  

    11. chmod 755 project_fastcgi.pl  

    12. ./project_fastcgi.pl -listen 127.0.0.1:3003 -nproc 10 -pidfile /var/run/fcgi_catalyst.pid -daemon  

    13.   

    14. #nginx中,配置:  

    15. location / {  

    16.     fastcgi_pass 127.0.0.1:3003;  

    17.     include /var/www/project/root/fastcgi.conf;  

    18. }  

    19. #fastcgi.conf詳細(注意點:將SCRIPT_NAME替換成PATH_INFO便可)  

    20. fastcgi_param  SCRIPT_FILENAME    $document_root$fastcgi_script_name;  

    21. fastcgi_param  QUERY_STRING       $query_string;  

    22. fastcgi_param  REQUEST_METHOD     $request_method;  

    23. fastcgi_param  CONTENT_TYPE       $content_type;  

    24. fastcgi_param  CONTENT_LENGTH     $content_length;  

    25. #fastcgi_param  SCRIPT_NAME        $fastcgi_script_name;  

    26. fastcgi_param  PATH_INFO          $fastcgi_script_name;  

    27. fastcgi_param  REQUEST_URI        $request_uri;  

    28. fastcgi_param  DOCUMENT_URI       $document_uri;  

    29. fastcgi_param  DOCUMENT_ROOT      $document_root;  

    30. fastcgi_param  SERVER_PROTOCOL    $server_protocol;  

    31. fastcgi_param  GATEWAY_INTERFACE  CGI/1.1;  

    32. fastcgi_param  SERVER_SOFTWARE    nginx/$nginx_version;  

    33. fastcgi_param  REMOTE_ADDR        $remote_addr;  

    34. fastcgi_param  REMOTE_PORT        $remote_port;  

    35. fastcgi_param  SERVER_ADDR        $server_addr;  

    36. fastcgi_param  SERVER_PORT        $server_port;  

    37. fastcgi_param  SERVER_NAME        $server_name;  

     最後,由於nginx沒有方便的控制命令可用,常常要ps,kill等直接控制,比較麻煩,能夠爲它寫一個啓動腳本,例子以下:

Shell代碼  

  1. #!/bin/sh  

  2. #  

  3. # description: Starts, stops nginx  

  4. #  

  5. #chkconfig: 2345 20 80  

  6. #dscription: Startup script for nginx webserver on CentOS. Place in /etc/init.d   

  7. #  

  8. # Author: Touya  

  9. set -e  

  10.   

  11. PATH=/usr/local/sbin:/usr/local/bin:/sbin:/bin:/usr/sbin:/usr/bin  

  12. DESC="nginx daemon"  

  13. NAME=nginx  

  14. DAEMON=/usr/local/nginx/sbin/$NAME  

  15. CONFIGFILE=/var/www/poseidon/root/nginx.conf  

  16. PIDFILE=/var/run/$NAME.pid  

  17. SCRIPTNAME=/etc/init.d/$NAME  

  18.   

  19. # Gracefully exit if the package has been removed.  

  20. test -x $DAEMON || exit 0  

  21.   

  22. d_start() {  

  23. echo "Starting $DESC: $NAME"  

  24. $DAEMON -c $CONFIGFILE || echo "already running"  

  25. }  

  26.   

  27. d_stop() {  

  28. echo "Stopping $DESC: $NAME"  

  29. test -f $PIDFILE && kill -QUIT `cat $PIDFILE`  

  30. }  

  31.   

  32. d_reload() {  

  33. echo "Reloading $DESC configuration…"  

  34. kill -HUP `cat $PIDFILE` || echo "can’t reload"  

  35. }  

  36. case "$1" in  

  37. 'start')  

  38.     d_start  

  39.     echo "started."  

  40. ;;  

  41. 'stop')  

  42.     d_stop  

  43.     echo "stoped."  

  44. ;;  

  45. 'reload')  

  46.     d_reload  

  47.     echo "reloaded."  

  48. ;;  

  49. 'restart')  

  50.     echo "Restarting $DESC: $NAME ..."  

  51.     d_stop  

  52.     # One second might not be time enough for a daemon to stop,  

  53.     # if this happens, d_start will fail (and dpkg will break if  

  54.     # the package is being upgraded). Change the timeout if needed  

  55.     # be, or change d_stop to have start-stop-daemon use --retry.  

  56.     # Notice that using --retry slows down the shutdown process somewhat.  

  57.     sleep 3  

  58.     d_start  

  59.     echo "done."  

  60. ;;  

  61. 'list')  

  62.     ps auxf | egrep '(PID|nginx)' | grep -v grep  

  63. ;;  

  64. 'test')  

  65.     $DAEMON -t -c $CONFIGFILE  

  66. ;;  

  67. *)  

  68. echo "Usage: $SCRIPTNAME {reload|list|test|start|stop|restart}" >&2  

  69. exit 3  

  70. ;;  

  71. esac  

  72. exit 0  

保存文件,並chmod 755 /etc/init.d/nginx
用chkconfig --list nginx查看是不是一個可用後臺啓動服務,若是是的話,能夠直接執行chkconfig --add nginx,這個後臺服務搞定(代碼中不可省略:#chkconfig: 2345 20 80)
接下能夠用service nginx start|restart|stop來操做你的nginx服務器(restart時從新讀入config)

怎麼樣?是否是方便多了?

 

     小結:本文是我本身實踐nginx的整個經驗總結,包括了前期準備、安裝、配置、架構設計、和現有動態程序結合(公司使用的是Catalyst)、啓動腳本等等,但願對你們有幫助,少走歪路。

相關文章
相關標籤/搜索