Linux下Nginx的安裝、升級及動態新增模組

成長之路 - 薛亮發表於2016-07-10

系統基於ubuntu server 14.04.4 amd64

安裝

第一步 下載並解壓Nginx壓縮包

Nginx官網下載Nginx,或者在Linux上執行wget http://nginx.org/download/nginx-1.10.1.tar.gz命令直接下載
解壓nginx-1.10.1.tar.gz檔案:

tar zxvf nginx-1.10.1.tar.gz

第二步 配置

cd nginx-1.10.1
./configure --prefix=/usr/local/nginx

注意:

① 如果之前沒有安裝C compiler(C 編譯器),這一步將報如下錯誤資訊:

xueliang@dev:~/download/nginx-1.10.1$ ./configure –prefix=/usr/local/nginx
checking for OS
+ Linux 4.2.0-27-generic x86_64
checking for C compiler … not found

./configure: error: C compiler cc is not found

xueliang@dev:~/download/nginx-1.10.1$

可以參考這篇文章安裝C compiler,然後繼續下面的操作

② 如果之前沒有安裝PCRE,這一步將報如下錯誤資訊:

checking for PCRE library … not found
checking for PCRE library in /usr/local/ … not found
checking for PCRE library in /usr/include/pcre/ … not found
checking for PCRE library in /usr/pkg/ … not found
checking for PCRE library in /opt/local/ … not found

./configure: error: the HTTP rewrite module requires the PCRE library.
You can either disable the module by using –without-http_rewrite_module
option, or install the PCRE library into the system, or build the PCRE library
statically from the source with nginx by using –with-pcre= option.

xueliang@dev:~/download/nginx-1.10.1$

可以參考這篇文章安裝PCRE,然後繼續下面的操作

③ 如果之前沒有安裝zlib,這一步將報如下錯誤資訊:

checking for md5 in system md library … not found
checking for md5 in system md5 library … not found
checking for md5 in system OpenSSL crypto library … not found
checking for sha1 in system md library … not found
checking for sha1 in system OpenSSL crypto library … not found
checking for zlib library … not found

./configure: error: the HTTP gzip module requires the zlib library.
You can either disable the module by using –without-http_gzip_module
option, or install the zlib library into the system, or build the zlib library
statically from the source with nginx by using –with-zlib= option.

xueliang@dev:~/download/nginx-1.10.1$

可以參考這篇文章安裝zlib,然後繼續下面的操作

也可以跳過此步,執行預設安裝,--prefix的預設值為/usr/local/nginx,Nginx官網對此有說明:Building nginx from Sources

第三步 編譯

make

第四步 完成安裝

sudo make install

平滑升級

當需要對正在執行的Nginx進行升級時,可以在不停止Nginx的情況下,使用新版本或者重編譯的可執行程式替換舊版本的可執行程式,這裡我們從nginx-1.10.1升級到nginx-1.11.1

第一步 備份舊版本

因為Nginx的升級,實質只是用新版本的可執行檔案,替換舊版本的可執行程式,所以,對於備份,既可以只備份舊版本可執行檔案,也可以打包備份整個舊版本安裝目錄,參考命令分別如下:

只備份舊版本可執行檔案

sudo cp /usr/local/nginx/sbin/nginx /usr/local/nginx/sbin/nginx.bak

打包備份整個舊版本安裝目錄

sudo tar -cvf /usr/local/nginx.bak /usr/local/nginx

第二步 下載新版本並解壓Nginx壓縮包

對於新版本Nginx壓縮包的下載和解壓,可以參考本文關於Nginx的安裝部分的第一、二步。

第三步 使用舊版本配置引數,配置並編譯新版本Nginx

因為只是對Nginx進行升級,並不涉及配置引數的修改,所以,我們一般使用和舊版本相同的配置(當然你也可以使用全新的配置資訊),來編譯新版本的Nginx,使用如下命令檢視舊版本配置資訊:

/usr/local/nginx/sbin/nginx -V

可以得到結果如下:

xueliang@dev:~/download/nginx-1.11.1$ /usr/local/nginx/sbin/nginx -V
nginx version: nginx/1.10.1
built by gcc 4.8.4 (Ubuntu 4.8.4-2ubuntu1~14.04.3)
configure arguments: –prefix=/usr/local/nginx
xueliang@dev:~/download/nginx-1.11.1$

其中 [configure arguments: –prefix=/usr/local/nginx] 這一行即為舊版本Nginx配置資訊,這裡可以看出,舊版本只是指定了安裝路徑,使用[configure arguments:]後面的引數資訊,對新版本Nginx作相同配置,然後進行編譯:

./configure --prefix=/usr/local/nginx

第四步 編譯新版本Nginx可執行程式

make

第五步 用新版本Nginx可執行程式覆蓋舊版本可執行程式

在上一步的基礎上,執行一下命令即可:

sudo cp objs/nginx /usr/local/nginx/sbin/nginx

執行這條命令,可能會報以下異常,提示檔案被佔用:

xueliang@dev:~/download/nginx-1.11.1$ sudo cp objs/nginx /usr/local/nginx/sbin/nginx
cp: cannot create regular file ‘/usr/local/nginx/sbin/nginx’: Text file busy
xueliang@dev:~/download/nginx-1.11.1$

可以使用以下命令進行強制覆蓋:

sudo cp -rfp objs/nginx /usr/local/nginx/sbin/nginx

第六步 啟動新版本Nginx主程式

傳送 USR2訊號給舊版本主程式號:

kill -USR2 舊版本的Nginx主程式號

舊版本Nginx主程式接收到-USR2訊號,將重新命名它的.pid檔案為.oldpid,然後執行新版本的Nginx可執行程式,依次啟動新版本的主程式和工作程式:

PID PPID USER %CPU VSZ WCHAN COMMAND
33126 1 root 0.0 1164 pause nginx: master process /usr/local/nginx/sbin/nginx
33134 33126 nobody 0.0 1368 kqread nginx: worker process (nginx)
33135 33126 nobody 0.0 1380 kqread nginx: worker process (nginx)
33136 33126 nobody 0.0 1368 kqread nginx: worker process (nginx)
36264 33126 root 0.0 1148 pause nginx: master process /usr/local/nginx/sbin/nginx
36265 36264 nobody 0.0 1364 kqread nginx: worker process (nginx)
36266 36264 nobody 0.0 1364 kqread nginx: worker process (nginx)
36267 36264 nobody 0.0 1364 kqread nginx: worker process (nginx)

第七步 從容關閉舊版本的工作程式

此時,新、舊版本的Nginx例項會同時執行,共同處理請求,如果此時給舊版本主程式傳送WINCH 訊號,舊版本主程式將會給它的工作程式傳送訊息,請求它們從容關閉,此後,舊版本的工作程式開始逐步退出:

PID PPID USER %CPU VSZ WCHAN COMMAND
33126 1 root 0.0 1164 pause nginx: master process /usr/local/nginx/sbin/nginx
33135 33126 nobody 0.0 1380 kqread nginx: worker process is shutting down (nginx)
36264 33126 root 0.0 1148 pause nginx: master process /usr/local/nginx/sbin/nginx
36265 36264 nobody 0.0 1364 kqread nginx: worker process (nginx)
36266 36264 nobody 0.0 1364 kqread nginx: worker process (nginx)
36267 36264 nobody 0.0 1364 kqread nginx: worker process (nginx)

從容關閉舊版本的工作程式命令:

kill -WINCH 舊版本的Nginx主程式號

第八步 從容關閉舊版本的主程式,完成Nginx的升級

經過一段時間後,舊的工作程式(work process)處理完了所有已連線的請求後退出,僅由新版本的工作程式來處理新的請求了:

PID PPID USER %CPU VSZ WCHAN COMMAND
33126 1 root 0.0 1164 pause nginx: master process /usr/local/nginx/sbin/nginx
36264 33126 root 0.0 1148 pause nginx: master process /usr/local/nginx/sbin/nginx
36265 36264 nobody 0.0 1364 kqread nginx: worker process (nginx)
36266 36264 nobody 0.0 1364 kqread nginx: worker process (nginx)
36267 36264 nobody 0.0 1364 kqread nginx: worker process (nginx)

應該注意的是,此時,舊版本的主程式還尚未關閉它監聽的套接字,如果有需要,你仍可以恢復舊版本工作程式。如果由於某些原因,新版本的可執行檔案執行情況不理想,下面有幾種方案可供參考:

  • 給舊版本主程式傳送 HUP 訊號。舊版本主程式將在不重新讀取配置資訊的情況下,重新開啟工作程式。然後,通過給新版本主程式傳送 QUIT 訊號,所有新版本的程式將會從容關閉。
  • 給新版本主程式傳送 TERM 訊號。然後,他將會給它的工作程式傳送訊息,要求它們立即退出,緊接著,這些工作程式就會立即退出。(如果因為某些原因,新版本程式沒有退出,應該給新版本主程式傳送 KILL 訊號,強制新版本主程式退出。)新版本主程式退出的同時,舊版本主程式將會自動啟動它的工作程式。
    新版本主程式退出後,舊版本主程式將會移除名字以.oldpid 結尾的檔案,恢復為它的 .pid 檔案。
    如果升級成功,應該給舊版本主程式傳送 QUIT 訊號,使其退出,只保留新版本程式:
PID PPID USER %CPU VSZ WCHAN COMMAND
36264 33126 root 0.0 1148 pause nginx: master process /usr/local/nginx/sbin/nginx
36265 36264 nobody 0.0 1364 kqread nginx: worker process (nginx)
36266 36264 nobody 0.0 1364 kqread nginx: worker process (nginx)
36267 36264 nobody 0.0 1364 kqread nginx: worker process (nginx)

新增模組

剛接觸Nginx時,只知道Nginx的功能是分模組的,並不清楚有些模組預設是不參與到構建中去的,比如ngx_http_ssl_module模組,是用來支援https協議的,預設情況下是沒有構建到Nginx中的。

隨著業務不斷擴充套件,如果需要Nginx支援某些模組,而這些模組預設不在Nginx的構建計劃中,構建Nginx時,又沒有指定加入這些模組,該怎麼辦呢?是否能夠給已經執行的Nginx動態新增這些模組呢?答案是肯定的!

給執行中的Nginx動態新增模組的方案,與上面提到的平滑升級Nginx的方案很類似。下面我們來看一下如何給執行中的Nginx新增 ngx_http_ssl_module模組。

第一步 檢視執行中的Nginx版本,並下載、解壓對應版本的壓縮包

檢視Nginx版本:

/usr/local/nginx/sbin/nginx -v

結果:

xueliang@dev:~$ /usr/local/nginx/sbin/nginx -v
nginx version: nginx/1.11.1
xueliang@dev:~$

或者:

/usr/local/nginx/sbin/nginx -V

結果:

xueliang@dev:~$ /usr/local/nginx/sbin/nginx -V
nginx version: nginx/1.11.1
built by gcc 4.8.4 (Ubuntu 4.8.4-2ubuntu1~14.04.3)
configure arguments: –prefix=/usr/local/nginx
xueliang@dev:~$

這裡可以看出,正在執行的Nginx版本為1.11.1,參照安裝Nginx部分,下載並解壓對應版本的Nginx

第二步 編譯Nginx,同時加入需要模組配置

參考平滑升級的第三步,檢視執行中的Nginx的配置引數,並在最後追加-with-http_ssl_module

如:原配置資訊為 --prefix=/usr/local/nginx,則新配置資訊為 --prefix=/usr/local/nginx --with_http_ssl_module,配置Nginx執行的命令如下:

./configure --prefix=/usr/local/nginx --with_http_ssl_module

第三步 平滑重啟Nginx,完成動態模組新增

這一步可以參考平滑升級的第四至八步

相關文章