nginx-1.8原始碼安裝配置
nginx介紹:
nginx是一款輕量級的web伺服器/反向代理伺服器及郵件代理伺服器,由俄羅斯人Igor Sysoev研發,特點是佔用記憶體較少,併發能力強,官方測試,能支援高達50000併發,還有豐富的第三方模組,滿足大部分業務需求,中國大陸使用nginx的大公司有阿里、百度、騰訊、新浪、網易等。
一、安裝(以下采用原始碼安裝,方便以後嵌入第三方模組):
1.1 系統centos6.5(nginx最好使用linux系統,對windows支援不是很好,功能模組也不多)
nginx: 192.168.4.72
apache: 192.168.4.69
apache: 192.168.4.68
1.2 安裝gcc和nginx需要的依賴庫
yum install gcc-c++ -y
yum -y install zlib-devel openssl-devel pcre-devel
1.3 如有安裝老版本,則解除安裝。
檢視:whereis nginx #如果有則解除安裝
解除安裝:yum remove nginx
1.4 下載nginx原始碼並解壓.(原始碼去官網下載,以下是官方連結)
wget http://nginx.org/download/nginx-1.8.0.tar.gz
#原始碼是採用官方穩定版本1.8.0,
解壓:tar -zxvf nginx-1.8.0.tar.gz
cd nginx-1.8.0
編譯:
./configure --user=nginx --group=nginx --prefix=/usr/local/nginx
--with-http_ssl_module --with-http_realip_module
--with-http_addition_module --with-http_sub_module
--with-http_dav_module --with-http_gunzip_module
--with-http_gzip_static_module--with-http_random_index_module
--with-http_secure_link_module--with-http_stub_status_module --with-file-aio --with-debug
注:這裡--with開頭的選項為nginx自帶的模組,需要什麼就新增,預設是不安裝,(第三方模組下面再介紹)
make && make install
1.5 建立nginx使用者及使用者組
groupadd -r nginx
useradd -s /sbin/nologin -g nginx-r nginx
1.6 啟動:
cd 到nginx目錄,看能否啟動
sbin/nginx
再ps一下,ps ax | grep nginx,看到如下,說明ok
2537 ? Ss 0:00 nginx: master process sbin/nginx
2538 ? S 0:00 nginx: worker process
nginx在啟動後,會有一個master程序和多個worker程序。master程序主要用來管理worker程序,包含:接收來自外界的訊號,向各worker程序傳送訊號,監控worker程序的執行狀態,當worker程序退出後(異常情況下),會自動重新啟動新的worker程序。
檢視安裝的nginx版本:
sbin/nginx -v
檢視安裝的編譯選項:
sbin/nginx -V
二、nginx配置及正向與反向代理:
2.1 nginx.conf配置檔案的結構
….. #全域性塊,設定nginx整體執行的配置指令
events { #events塊,設定nginx與使用者的網路連線,這塊指令對效能影響較大
…...
}
http { #http塊,包含代理,快取,日誌字義和第三方模組
…… #http的全域性塊,設定檔案引入,日誌,連線超時時間....
server { #server塊,相當於“虛擬主機”的意思,可以多個
……. #server全域性塊,作用域只在本server,不會影響其它server
location [ pattern ]{ #location塊,可以多個,對訪問使用者的url進行匹配處理,地址定向,
#資料快取,還有很多第三方模組配置也在這
…….
}
}
server { #server塊
…….
}
……. #http全域性塊
}
2.2 下面是一個正向代理的例子,指令不多(這裡只展示server段的配置,其它預設就行):
…..
server {
resolver 8.8.8.8;
listen 82;
location / {
proxy_passhttp://$http_host$request_uri;
}
}
2.3 下面是反向代理的例子(這塊指令較多,只配置關鍵的指令,其它一些指令在優化中有體現)
user nginx nginx; #這裡是nginx執行的使用者
worker_processes 2; #設定nginx服務的worker子程序,比如設為2:
error_log logs/error.log #去掉前面的#,記錄nginx錯誤日誌,方便檢查bug:
pid logs/nginx.pid #nginx的pid位置
events {
worker_connections 1024;
}
http {
include mime.types;
default_type application/octet-stream;
log_format main '$remote_addr - $remote_user [$time_local] "$request" '
'$status$body_bytes_sent "$http_referer" '
'"$http_user_agent""$http_x_forwarded_for"';
access_log logs/access.log main; #日誌存放位置
# 這裡的upstream就是配置負載均衡的,當然得兩臺以上才叫負載,我這裡的ip69和68都是用的apache, 也許你們的是tomcat,沒關係,按這樣配置一樣可以,
upstream proxy_test {
server 192.168.4.69:80weight=1; #如果要測試,把這裡換成自己要代理後端的ip
server 192.168.4.68:80weight=1;
#ip_hash; #當負載兩臺以上用ip來hash解決session的問題,一臺就別hash了。
}
server {
listen 80;
server_name www.test.com; #要訪問的域名,我這裡用的測試域名,如果有多個,用逗號分開
charset utf8;
location / {
proxy_pass http://proxy_test; #該指令設定被代理伺服器地址
#這裡proxy_test是上面的負載的名稱,對映到代理伺服器,
#可以是ip加埠, 或url ,
proxy_set_headerHost $host; #該指令接收客戶端請求頭資訊,然後傳送給被代理伺服器,
proxy_set_header X-Real-IP$remote_addr;
proxy_set_headerX-Forwarded-For $proxy_add_x_forwarded_for;
}
}
}
儲存退出後,nginx平滑重啟:sbin/nginx-s reload #載入剛剛加入的配置。
2.3.2. 測試:
後端伺服器開啟,在192.168.4.69和68的網頁檔案位置新增測試檔案test.html, 內容69上: this is test 69, 68上:this istest 68,這樣方便檢視訪問到哪臺,在本地配置好host,
開啟瀏覽器用www.test.com去訪問後端伺服器的檔案,
如: www.test.com/test.html,
瀏覽器開啟顯示有this...說明配置ok了。
然後F5重新整理一下,如果是68和69不停的切換,說明負載ok。
2.4 nginx處理請求的幾個階段:
NGX_HTTP_POST_READ_PHASE: 讀取請求內容階段
NGX_HTTP_SERVER_REWRITE_PHASE: Server請求地址重寫階段
NGX_HTTP_FIND_CONFIG_PHASE: 配置查詢階段:
NGX_HTTP_REWRITE_PHASE: Location請求地址重寫階段
NGX_HTTP_POST_REWRITE_PHASE: 請求地址重寫提交階段
NGX_HTTP_PREACCESS_PHASE: 訪問許可權檢查準備階
NGX_HTTP_ACCESS_PHASE: 訪問許可權檢查階段
NGX_HTTP_POST_ACCESS_PHASE: 訪問許可權檢查提交階段
NGX_HTTP_TRY_FILES_PHASE: 配置項try_files處理階段
NGX_HTTP_CONTENT_PHASE: 內容產生階段
NGX_HTTP_LOG_PHASE: 日誌模組處理階段
三、nginx優化:
優化不光是nginx本身,還得結合伺服器硬體來優化以及系統核心優化,下面是nginx本身的優化的一些指令:
worker_processes 4; #nginx程序數,建議按cpu數目來指定,一般為它的倍數,官方預設為1,
#當然這個值不是越大就越好,越大會影響系統的IO效率,也會增加主程序的負擔,
#我這裡使用的是4,即4核cpu, 該指令配置在全域性塊。
worker_cpu_affinity 0001 0100 1000 0010; #該指令用來分配cpu的核心,設定有點麻煩,引數是二進位制
#下面是一個8核的配置;
worker_cpu_affinity 00000001 00000010 00000100 00001000 0001000000100000 01000000 10000000;
worker_rlimit_nofile 102400;
#這個指令是指當一個nginx程序開啟的最多檔案描述符數目,理論值應該是最多開啟檔案數(ulimit -n)與nginx程序數相除,但是nginx分配請求並不是那麼均勻,所以最好與ulimit -n的值保持一致。
worker_connections 102400;
#每個程序允許的最多連線數,理論上每臺nginx伺服器的最大連線數是: worker_processes*worker_connections。
keepalive_timeout 60; #keepalive超時時間。
client_header_buffer_size 4k;
#客戶端請求頭部的緩衝區大小,這個可以根據系統分頁大小來設定,一般一個請求的頭部大小不會超過1k,不過由於一般系統分頁都要大於1k,所以這裡設定為分頁大小。(用命令getconf PAGESIZE 取得系統分頁大小)
open_file_cache max=102400 inactive=20s;
#這個將為開啟檔案指定快取,預設是沒有啟用的,max指定快取數量,建議和開啟檔案數一致,inactive是指經過多長時間檔案沒被請求後刪除快取。
open_file_cache_valid 30s;
#這個是指多長時間檢查一次快取的有效資訊。
open_file_cache_min_uses 1;
#open_file_cache指令中的inactive引數時間內檔案的最少使用次數,如果超過這個數字,檔案描述符一直是在快取中開啟的,如上例,如果有一個檔案在inactive時間內一次沒被使用,它將被移除。
下面是http段的一些指令(這些指令偏重於對生產業務的需求,有部分指令可以在全域性設定,詳細可以參考官網)
client_max_body_size 300m;
# 設定通過nginx上傳檔案的大小
proxy_connect_timeout 90;
#後端伺服器連線的超時時間_發起握手等候響應超時時間
proxy_read_timeout 180;
#連線成功後等候後端伺服器響應時間,其實已經進入後端的排隊之中等候處理,也可以說是後端伺服器處理請求的時間,當超過這個時間後,返回的是504,之前在生產環境中遇到過這個問題,也就是後端的tomcat有個程式需要解壓大檔案,花時要3分多鐘,而我這設定的是60,所以一直是504。
proxy_send_timeout 180;
#後端伺服器資料回傳時間_就是在規定時間之內後端伺服器必須傳完所有的資料
proxy_buffer_size 256k;
#設定從被代理伺服器讀取的第一部分應答的緩衝區大小,通常情況下這部分應答中包含一個小的應答頭,預設情況下這個值的大小為指令proxy_buffers中指定的一個緩衝區的大小,不過可以將其設定為更小
proxy_buffers 4 256k;
#設定用於讀取應答(來自被代理伺服器)的緩衝區數目和大小,預設情況也為分頁大小,根據作業系統的不同可能是4k或者8k
proxy_busy_buffers_size 256k; #控制同時傳輸到客戶端的buffer數量
proxy_temp_file_write_size 256k;
#設定在寫入proxy_temp_path時資料的大小,預防一個工作程序在傳遞檔案時阻塞太長
proxy_temp_path /data0/proxy_temp_dir;
#proxy_temp_path和proxy_cache_path指定的路徑必須在同一分割槽
proxy_cache_path /data0/proxy_cache_dir levels=1:2keys_zone=cache_one:200m inactive=1d max_size=30g;
#設定記憶體快取空間大小為200MB,1天沒有被訪問的內容自動清除,硬碟快取空間大小為30GB。
client_body_buffer_size 512k;
#如果把它設定為比較大的數值,例如256k,那麼,無論使用firefox還是IE瀏覽器,來提交任意小於256k的圖片,都很正常。如果註釋該指令,使用預設的client_body_buffer_size設定,也就是作業系統頁面大小的兩倍,8k或者16k,問題就出現了,無論使用firefox4.0還是IE8.0,提交一個比較大,200k左右的圖片,都返回500Internal Server Error錯誤。
gzip on; #這裡開啟壓縮功能,更快的傳輸,
gzip_min_length 1k; #壓縮大於1K的檔案,小於1K的越壓越大
gzip_buffers 4 16k; #壓縮快取大小配置。
gunzip on; #開啟解壓縮。
注:這裡出現一個問題,就是這麼多的buffers配置,是不是很多請求使用同一個buffers呢,答案是否,一個請求來時,nginx會分配獨立的一套配置給它,然後使用這些引數,當使用完,即刻就釋放了,另外這裡只是nginx常用的需要優化的指令,更多的指令參考官網:http://nginx.org/en/docs/
四、nginx的內建變數:
nginx提供了很多的內建變數,可以使用這些變數得到想關資訊
$args, 請求中的引數;
$status 響應的狀態程式碼;
$request_time 請求時間,這個時間是指nginx在這個請求中的所花的時間,精確到毫秒
$content_length, HTTP請求資訊裡的"Content-Length";
$content_type, 請求資訊裡的"Content-Type";
$document_root, 針對當前請求的根路徑設定值;
$document_uri, 與$uri相同;
$host, 請求資訊中的"Host",如果請求中沒有Host行,則等於設定的伺服器名;
$limit_rate, 對連線速率的限制;
$request_method, 請求的方法,比如"GET"、"POST"等;
$remote_addr, 客戶端地址;
$remote_port, 客戶端埠號;
$remote_user, 客戶端使用者名稱,認證用;
$request_filename, 當前請求的檔案路徑名
$request_body_file, ??
$request_uri, 請求的URI,帶引數;
$query_string, 與$args相同;
$scheme, 所用的協議,比如http或者是https,比如rewrite ^(.+)$ $scheme://example.com$1 redirect;
$server_protocol, 請求的協議版本,"HTTP/1.0"或"HTTP/1.1";
$server_addr, 伺服器地址,如果沒有用listen指明伺服器地址,使用這個變數將發起一次系統呼叫以取得地址(造成資源浪費);
$server_name, 請求到達的伺服器名;
$server_port, 請求到達的伺服器埠號;
$uri, 請求的URI,可能和最初的值有不同,比如經過重定向之類的。
五、嵌入第三方模組,這裡以nginx_upstream_check_module和lua-nginx-module為例
nginx_upstream_check_module這個模組是由淘寶姚偉斌團隊開發,已經開源,功能是對後端伺服器的健康檢查,如果後端某臺伺服器不可用時,會標記為down, 並把請求轉發給其它後端可用的伺服器。 直到該伺服器可用時,才標記為up,並轉發請求。
lua-nginx-module這個模組主要由前淘寶章亦春開發,並已經開源,程式碼在github上,現在他主要在做這方面的開源工作,並不斷在更新完善,豐富的API,功能集非常強大,主要滿足業務上的各種需求。
模組: nginx把各個功能模組載入起來,形成鏈條式的,當用戶請求過來,然後依次經過這些模組或跳過某些模組,讓這些模組實現特定的功能需求。
5.1 nginx_upstream_check_module模組下載地址:
https://github.com/yaoweibin/nginx_upstream_check_module/archive/v0.3.0.tar.gz
nginx載入模組時,需要重新編譯,編譯時加上這個
--add-module=nginx_upstream_check_module-0.3.0
配置:
upstream www.test.com {
server 172.10.2.170:80;
server 172.10.2.206:80;
check interval=3000 rise=2fall=4 timeout=1000; #該模組的配置主要在這
}
#interval檢測間隔時間,單位為毫秒,rsie請求2次正常的話,標記此realserver的狀態為up,fall表示請求4次都失敗的情況下,標記此realserver的狀態為down,timeout為超時時間,單位為毫秒。
5.2lua-nginx-module模組下載地址:
wgethttps://github.com/openresty/lua-nginx-module/archive/v0.9.13.tar.gz
下載lua需要的庫:wgethttp://luajit.org/download/LuaJIT-2.0.0-beta9.tar.gz
安裝庫: cdLuaJIT-2.0.0-beta9 make && make install PREFIX=/usr/local/luajit
ln -sfluajit-2.0.0-beta9 /usr/local/bin/luajit
配置好環境變數
exportLUAJIT_LIB=/usr/local/lib
exportLUAJIT_INC=/usr/local/include/luajit-2.0
再編譯加上 --add-module=lua-nginx-module-0.9.13
5.3 簡單例子:
location / {
content_by_lua '
ngx.say("hellonginx")
';
}
#然後用ip進行訪問,會輸出hello nginx