1. 內容介紹
- Nginx的基本概念
- nginx是什麼,做什麼事情?
- 反向代理
- 負載均衡
- 動靜分離
更多c/c++ Linux服務器高階知識請後臺私信【架構】獲取
分享知識點有C/C++,Linux,golang技術,Nginx,ZeroMQ,MySQL,Redis,fastdfs,MongoDB,ZK,流媒體,CDN,P2P,K8S,Docker,TCP/IP,協程,DPDK等等。
2.Nginx安裝、常用命令和配置文件
- 在Linux系統中安裝nginx
- nginx常用命令
- nginx配置文件
- nginx配置實例1-反向代理
- nginx配置實例2-負載均衡
- nginx配置實例3-動靜分離
- nginx配置高可用集群
- nginx原理
2. Nginx基本概念
2.1 Nginx概述(摘自百度百科)
Nginx (engine x) 是一個高性能的HTTP和反向代理web服務器,同時也提供了IMAP/POP3/SMTP服務。Nginx是由伊戈爾·賽索耶夫為俄羅斯訪問量第二的Rambler.ru站點(俄文:Рамблер)開發的,第一個公開版本0.1.0發佈於2004年10月4日。
其將源代碼以類BSD許可證的形式發佈,因它的穩定性、豐富的功能集、示例配置文件和低系統資源的消耗而聞名。2011年6月1日,nginx 1.0.4發佈。
Nginx是一款輕量級的Web 服務器/反向代理服務器及電子郵件(IMAP/POP3)代理服務器,在BSD-like 協議下發行。其特點是佔有內存少,併發能力強,事實上nginx的併發能力在同類型的網頁服務器中表現較好,中國大陸使用nginx網站用戶有:百度、京東、新浪、網易、騰訊、淘寶等。
2.2 Nginx作為web服務器
Nginx可以作為靜態頁面的web服務器,同時還支持CGI協議的動態語言,比如perl、php等。但是不支持java,java程序只能通過與tomcat配合完成。Nginx專為性能優化而開發,性能是其最重要的考量,實現上非常注重效率,能經受高負載的考驗。有報告稱能支持高達50000個併發。
Nginx介紹:https://lnmp.org/nginx.html
2.3 正向代理
Nginx不僅可以作為反向代理,實現負載均衡。還能作為正向代理來進行上網等功能。
正向代理:在客戶端(瀏覽器)配置代理服務器,通過代理服務器進行互聯網訪問。
正向代理:如果把局域網外的Internet想象成一個巨大的資源庫,則局域網中的客戶端要訪問Internet,則需要通過代理服務器來訪問,這種代理服務器就稱為正向代理!
2.4 反向代理
反向代理:其實客戶端對代理是無感知的,因為客戶端不需要任何配置就可以訪問,我們只需要將請求發送到反向代理服務器,由反向代理服務器去選擇目標服務器獲取數據後,再返回給客戶端,此時反向代理服務器和目標服務器對外就是一個服務器,暴露的是代理服務器地址,隱藏了真實服務器IP地址!
2.5 負載均衡
單個服務器解決不了,但是可以增加服務器的數量,然後將請求分發到各個服務器上,將原先請求集中到單個服務器的情況改為將請求分發到多個服務器上,將負載分發到不同的服務器,也就是我們所說的負載均衡!
2.6 動靜分離
為了加快網站的解析速度,可以把動態頁面和靜態頁面由不同的服務器來解決,加快解析速度。降低原來單個服務器的壓力
3. Nginx安裝
3.1 進入官網下載Nginx
官網地址:http://nginx.org/ 我選擇了1.16.1版本
3.2 安裝Nginx
3.2.1. 安裝pcre
- 官網下載pcre
官網地址:https://sourceforge.net/projects/pcre/
我下載了10.34版本
把pcre的壓縮文件放到Linux系統中
我這裡放到了usr下的src目錄中
- 解壓壓縮文件
<code>tar -xvf pcre2-10.34.tar.gz /<code>
- 進入解壓後的目錄然後執行命令
<code>./configure /<code>
- 編譯安裝
<code>make && make install /<code>
- 安裝以後使用命令查看版本號
<code>pcre-config -version /<code>
3.2.2 安裝openssl和安裝zlib
<code>yum -y install make zlib zlib devel gcc-c++ libtool openssl-devel /<code>
3.2.3 安裝Nginx
- 把nginx壓縮包丟到linux的 /usr/src 目錄下
- 解壓縮
<code>tar -xvf nginx-1.16.1.tar.gz /<code>
- 檢查。進入解壓後的目錄執行命令
<code>./configure /<code>
- 編譯安裝
<code>make && make install /<code>
安裝成功之後,在 /usr 目錄中會有個 local/nginx目錄,在nginx中有sbin有啟動腳本
- 啟動nginx
<code># 進入目錄 cd /usr/local/nginx/sbin # 執行啟動腳本 ./nginx /<code>
- 查看nginx的配置文件
<code># 找到nginx的配置目錄裡的配置文件 cd /usr/local/nginx/conf # 打開nginx的配置文件 vim nginx.conf /<code>
在瀏覽器可以通過端口號和ip地址訪問到nginx
3.2.4 linux端口解決
- 查看開放的端口號
<code>firewall-cmd --list-all /<code>
- 設置開放端口號
<code>sodu firewall-cmd --add-port=80/tcp --permanent /<code>
- 重啟防火牆
<code>firewall-cmd -reload /<code>
3.3 Nginx常用命令
- 進入nginx目錄
<code>cd /usr/local/nginx/sbin /<code>
- 查看nginx版本號
<code>nginx -v /<code>
- 查看nginx是否啟動
<code>ps -ef | grep nginx /<code>
- 停止nginx
<code>./nginx -s stop /<code>
- 啟動nginx
<code>./nginx /<code>
- 重新加載nginx(比如修改了nginx的配置文件,不想重啟nginx)
<code>./nginx -s -reload /<code>
3.4 Nginx的配置文件
3.4.1 nginx的配置文件位置
在linux中的位置(安裝目錄下的conf目錄下的nginx.conf文件)
<code>/usr/local/nginx/conf/nginx.conf /<code>
3.4.2 nginx配置文件組成
3.4.2.1 全局快
從配置文件開始到events塊之間的內容,主要會設置一些影響Nginx服務器整體運行的配置命令。主要包括配置運行Nginx服務器的用戶(組)、允許生成的worker process數,進程pid存放路徑、日誌存放路徑和類型以及配置文件的引入等。
比如 worker_processes 1; 這個值越大,可以支持的併發處理量就越多!
3.4.2.2 events塊
涉及的指令主要影響Nginx服務器與用戶的網絡連接,常用的設置包括是否開啟對多work process下的網絡連接進行序列化,是否允許同時接受多個網絡連接,選取哪種驅動模型來處理連接請求,每個word process可以同時支持的最大連接數等等!
<code>worker_connections 51200; # 配置服務器與用戶網絡連接部分 /<code>
3.4.2.3 http塊
這是nginx配置中最頻繁的部分,代理、緩存和日誌定義等絕大多數功能和第三方模塊的配置都在這裡。
需要注意的是:http塊也可以包括http全局塊、server塊。
- http全局塊
http全局塊配置的指令包括文件引入、MIME-TYPE定義、日誌自定義、連接超時時間、單連接請求數上限等。
下面這一塊截圖就是http全局塊
3.4.2.4 server塊(屬於http塊)
- 每個http塊可以有多個server塊,而每個server塊就相當於一個虛擬主機
- 而每個server塊也分為全局server塊,以及可以同時包含多個location塊。
- 全局server塊
最常見的配置是本地虛擬機主機的監聽配置和本地虛擬主機的名稱或IP配置 - location塊 一個server塊可以配置多個location塊 這塊的主要作用是基於Nginx服務器接收到的請求字符串(例如server_name/uri-string),對虛擬主機名稱(也可以是ip別名)之外的字符串(例如 前面的 /uri-string)進行匹配,對特定的請求進行處理。地址定向、數據緩存和應答控制等功能,還有許多第三方模塊的配置也在這裡進行!
4. Nginx配置實例1-反向代理
4.1 實現效果
打開瀏覽器,在地址欄輸入地址 www.xxx123.com ,跳轉到Linux系統tomcat主頁面中
4.2 準備工作
在Linux系統中安裝tomcat,使用默認端口8080
- 下載tomcat(我這裡使用tomcat8)
官網地址:https://tomcat.apache.org/ - 解壓安裝
我這裡把tomcat壓縮包放到了 /usr/src目錄中
<code>tar -xvf apache-tomcat-8.5.50.tar.gz /<code>
- 查看有無安裝jdk。tomcat需要jdk
<code>java -version /<code>
- 啟動tomcat(在tomcat的安裝目錄中有個bin目錄,進去,然後執行命令)
<code>./startup.sh /<code>
- 查看tomcat日誌信息(在tomcat的安裝目錄中有個log目錄,進去,然後執行命令)
<code>tail -f catalina.out /<code>
- 測試
瀏覽器輸入地址訪問tomcat:ip:8080
4.3 訪問過程分析
4.4 具體配置
- 在windows系統的hosts文件進行域名和ip對應關係的配置
在hosts文件中添加一行內容:linux的ip 域名
<code>172.16.124.45 xxx123.com /<code>
- 在nginx的配置文件進行請求轉發的配置(反向代理配置)
4.5 最終測試
瀏覽器訪問地址:xxx123.com
5. Nginx配置實例2-反向代理
5.1 實現效果
使用nginx反向代理,根據訪問的路徑跳轉到不同端口的服務中 nginx監聽端口為9001
訪問 ip:9001/edu/ 直接跳轉到 127.0.0.1:8080 訪問 ip:9001/vod/ 直接跳轉到 127.0.0.1:8081
5.2 準備工作
- 準備2個tomcat服務器,一個8080端口,一個8081端口
在原來tomcat同級目錄中創建兩個tomcat文件夾
<code>mkdir tomcat8080 mkdir tomcat8081 /<code>
分別在每個文件夾放入tomcat的安裝包,並進行解壓
- 創建文件夾和測試頁面(在tomcat的webapps目錄下)
5.3 具體配置
- 找到Nginx的配置文件,進行反向代理的配置
2.location指令說明
該指令用於匹配URL
語法如下
<code>location [= | ~ | ~* | ^~] uri { } /<code>
- = :用於不含正則表達式的uri前,要求請求字符串與uri嚴格匹配,如果匹配成功,就停止繼續向下搜索並立即處理該請求!
- ~ :用於表示uri包含正則表達式,並且區分大小寫
- ~* :用於表示uri包含正則表達式,並且不區分大小寫
- ^~ :用於不包含正則表達式的uri前,要求nginx服務器找到標識uri和請求字字符串匹配度最高的location後,立即使用此location處理請求,而不再使用location塊中的正則uri和請求字符串做匹配。
注意:如果uri包含正則表達式,則必須要有 ~ 或者 ~* 標識。
6. Nginx配置實例-負載均衡
6.1 實現效果
瀏覽器地址欄輸入地址,負載均衡效果,平均分配到8080端口和8081端口中
6.2 準備工作
- 準備2臺tomcat服務器,一臺8080,一臺8081
- 在兩臺tomcat裡面webapps目錄中,創建名字是edu文件夾,在edu文件夾中創建頁面a.html,用於測試
6.3 在nginx的配置文件中進行負載均衡的配置
6.4 測試
瀏覽器訪問地址:ip/edu/a.html
可以看到結果是平均分配到了2個tomcat的效果!
6.5 Nginx負載均衡分配策略
6.5.1 輪詢(默認)
每個請求按時間順序逐一分配到不同的後端服務器,如果後端服務器down掉,會自動剔除!
6.5.2 weight
weight代表權,重默認為1,權重越高被分配的客戶端越多!
指定輪詢幾率,weight和訪問比率成正比,用於後端服務器性能不均的情況。比如:
權重為10的那個會比權重為5的那個客戶端多一倍!
6.5.3 ip_hash
每個請求按訪問ip的hash解果分配,這樣每個訪客固定訪問一個後端服務器,可以解決session的問題。
這樣產生的結果:第一次這個用戶被分配到了哪個服務端,以後他只會一直訪問那個服務端!
6.5.4 fair(第三方)
按照後端服務器的響應時間來分配,響應時間短的優先分配!
7. Nginx配置實例-動靜分離
7.1 相關概念
Nginx的動靜分離簡單來說就是把動態請求和靜態請求分開,不能理解成只是單純的把動態頁面和靜態頁面物理分離。嚴格意義上說是動態請求跟靜態請求分開,可以理解成Nginx處理靜態頁面,tomcat處理動態頁面!
動靜分離從目前實現角度上來講分為2種:
- 一種是純粹把靜態文件獨立成單獨的域名,放在獨立的服務器上,也是目前主流推崇的方案!
- 另一種就是動態跟靜態文件混合在一起發佈,通過nginx來分開!
在Nginx中通過location指定不同的後綴名實現不同的請求轉發。通過expires參數設置,可以設置瀏覽器的緩存過期時間,減少與服務器之間的請求和流量!
具體Expires定義:是給一個資源設定一個過期時間,也就是說無需去服務端驗證,直接通過瀏覽器自身確認是否過期即可,所以不會產生額外的流量,此種方法非常適合不經常變動的資源。(如果經常變更的文件,不建議使用Expires來緩存),我這裡設置3d,表示在3天內訪問這個url,發送一個請求,比對服務器該文件最後更新時間沒有變化,則不從服務器抓取,返回狀態嗎304,如果有修改,則直接從服務器下載,返回狀態嗎200
7.2 準備工作
在Linux根目錄中的 data 目錄中準備2個文件夾 www 和 image,分別放html網頁和圖片。文件名字分別是 a.html 和 1.jpg
7.3 具體配置
- 在Nginx配置文件中進行配置
7.4 測試
重啟Nginx ip/www/a.html即可訪問到那個準備的網頁
8. Nginx配置實例-高可用
8.1 主備模式高可用介紹
主備模式高可用 對外暴露一個虛擬ip,用戶通過虛擬ip進行訪問,然後虛擬ip會自動分配尋找某個Nginx,Nginx再負載均衡尋找合適的tomcat進行返回響應!如果有一個nginx宕機了,會尋找另一個Nginx,如果有一個tomcat宕機了,也會尋找另一個可用的tomcat。
8.2 配置高可用的準備工作
- 需要2臺服務器
- 在2臺服務器安裝Nginx
- 在2臺服務器安裝keepalived
8.3 在2臺服務器安裝keepalived
<code>yum install keepalived -y /<code>
keepalived的安裝位置:/etc/keepalived
這安裝目錄下有個配置文件名字叫:keepalived.conf
做主備的Nginx配置都是在這個配置文件中進行配置
8.4 完成高可用配置(主備配置)
配置 keepalived.conf 文件
Nginx檢測腳本。(注意腳本文件名字和存放路徑,要與上圖中的檢測腳本路徑一致)
以上配置在兩個服務器裡面都需要配置的
8.5 把兩臺服務器上的 nginx 和 keepalived 啟動
先啟動nginx(進入到nginx的安裝目錄中的sbin目錄,再執行命令)
<code>./nginx /<code>
再啟動keepalived
<code>systemctl start keepalived service /<code>
8.6 測試
在瀏覽器地址欄輸入 虛擬ip地址 192.168.17.50
image.png
在服務器輸入命令
<code>ip a /<code>
停掉主服務器上的nginx和keepalived,再進行測試訪問虛擬ip。發現依然可以訪問。
9. Nginx配置實例(高可用配置文件詳解)
9.1 全局配置
那個是服務器的名字
在 /etc/hosts 文件中可以看到
<code>vim /etc/hosts /<code>
9.2 腳本配置
9.3 虛擬ip配置
9.4 腳本文件配置
10. Nginx的原理解析
10.1 機制介紹
10.2 master-workers的機制的好處
- 可以使用 nginx -s reload 熱部署
- 每個worker是獨立的進程,如果有其中一個進程出現問題,其他work獨立的,繼續進行爭搶,實現請求過程,不會造成服務中斷!
首先,對於每個worker進程來說,獨立的進程不需要加鎖,所以省掉了鎖帶來的開銷,同時在編程以及問題查找時,也會方便很多。其次採用獨立的進程,可以讓互相之間不會影響,一個進程退出後,其他進程還在工作,服務不會中斷,master進程則很快啟動新的 worker 進程。當然,worker進程的異常退出,肯定是程序有BUG了,異常退出,會導致當前worker上所有的請求失敗,不過不會影響所有請求,所以降低了風險!
10.3 多少worker才是最合適的?
Nginx同Redis相似,都是採用io多路複用機制,每個worker都是一個獨立的進程,但每個進程裡面只有一個主線程,通過異步非阻塞的方式來處理請求,即時是千萬個請求也不在話下。每個worker的線程可以將cpu的性能發揮到極致。所以worker數和服務器的cpu數相等是最為適宜的。設置少了會浪費cpu,設置多了會造成cpu頻繁切換上下文帶來的損耗!
10.4 連接數 worker_connection
- 發送請求,佔用了worker幾個連接數?
答案:2個(訪問靜態資源直接返回)或者4個(使用tomcat訪問數據庫) - nginx有一個master,有n個worker,每個worker支持的最大連接數是m,支持的最大併發數是多少? 普通的靜態訪問最大併發數:worker_connection * worker_processes / 2 而如果是作為http反向代理來說。最大併發數量應該是:worker_connection * worker_processes / 4