當前位置:首頁 » 網頁前端 » web架構nginx
擴展閱讀
webinf下怎麼引入js 2023-08-31 21:54:13
堡壘機怎麼打開web 2023-08-31 21:54:11

web架構nginx

發布時間: 2022-11-21 03:14:22

『壹』 解剖nginx伺服器架構

模塊化結構的思想是一個很久的概念,但也正是成熟的思想造就了Nginx的巨大優越性。

我們知道Nginx從總體上來講是有許多個模塊構成的。習慣將Nginx分為5大模塊分別為:核心模塊,標准HTTP模塊,可選HTTP模塊,郵件服務模塊和第三方模塊。

這5個模塊由上到下重要性一次遞減。

(1)核心模塊;

核心模塊是Nginx伺服器正常運行必不可少的模塊,如同操作系統的內核。它提供了Nginx最基本的核心服務。像進程管理、許可權控制、錯誤日誌記錄等;

(2)標准HTTP模塊;

標准HTTP模塊支持標準的HTTP的功能;

(3)可選HTTP模塊;

可選HTTP模塊主要用於擴展標準的HTTP功能,讓Nginx能處理一些特殊的服務;

(4)郵件服務模塊;

郵件服務模塊主要用於支持Nginx的郵件服務;

(5)第三方模塊;

第三方模塊是為了擴展Nginx伺服器應用,完成開發者想要的功能;

*******Nginx中的模塊命名有自己的習慣*********

一般以Ngx_作為前綴,——mole作為後綴,中間使用一個或者多個英文單詞描述模塊的工能,例如Ngx_core_mole表示該模塊提供Nginx的核心功能等;

具體各個模塊中包含哪些模塊可以自己去源碼中查詢,這里略過;

從架構設計上說,Nginx伺服器是與眾不同的。其一在於它的模塊化設計;其二也是更重要的一點在於它對與客戶端請求的處理機制上;

web伺服器和客戶端是一對多的關系,Web伺服器必須有能力同時為多個客戶端提供服務。一般來說完成並行處理請求工作有三種方式:

1.多進程方式;

2.多線程方式;

3.非同步方式;

這里簡單說明一下這三種方式:

(1)多進程方式

多進程方式指,伺服器每當收到一個客戶端時。就有伺服器主進程生成一個子進程出來和客戶端建立連接進行交互。指導連接斷開。該子進程就結束了。

多進程方式的優點是設計簡單,各個子進程相對獨立,處理客戶端請求時彼此不受干擾;缺點是操作系統生成一個子進程需要進行內存復制等操作,在資源和時間上會產生一定的開銷;當有大量請求時,會導致系統性能下降;

(2)多線程方式

多線程方式指每當伺服器接收到一個請求後,會由伺服器主進程派生出一個線程出來和客戶端進行交互。由於操作系統產生出一個線程的開銷遠遠小於一個進程的開銷。故多線程方式在很大程度上減輕了Web伺服器對系統資源的要求。但同時由於多個線程位於一個進程內,可以訪問同樣的內存空間。所以需要開發者自己對內存進程管理,增大了難度。

(3)非同步方式

非同步方式適合多進程和多線程完全不同的一種處理客戶端請求的方式。這里有幾個概念我們需要熟悉一下: 同步,非同步,阻塞,非阻塞

在網路通信中同步和非同步是描述通信模式的概念。

同步:發送方發送完請求後,需要等待接收到接收方發回的響應,才能發送下一個請求;所有請求在服務端得到同步,發送方和接收方的步調是一致的;

非同步 :和同步機制相反,在非同步機制中,發送方發出一個請求後,不等接收方響應這個請求,就繼續發送下一個請求;所有來自發送方的請求形成一個隊列,接收方處理完成後通知發送方;

在進程處理調度方式上用阻塞與非阻塞。在網路通信中主要指套接字socket的阻塞和非阻塞,而socket的實質就是IO操作。

阻塞 :調用結果返回之前,當前線程從運行狀態被掛起,一直等到調用結果返回之後,才進入就緒狀態,獲取CPU後繼續執行。

非阻塞 :和阻塞方式正好相反,如果調用結果不能馬上返回,當前線程也不會馬上返回,而是立即返回執行下一個調用。

因此就衍生出4中方式:同步阻塞,同步非阻塞,非同步阻塞,非同步非阻塞

這里簡單解釋一下非同步非阻塞:發送方向接收方發送請求後,不用等待響應,可以繼續其他工作;接收方處理請求時進行的IO操作如果不能馬上得到結果,也不必等待,而是馬上返回去去做其他事情。當IO操作完成以後,將完成狀態和結果通知接收方,接收方再響應發送方。

與此同時Nginx伺服器處理請求是怎樣的呢???

Nginx伺服器的一個顯著的優勢就是能夠同時處理大量的並發請求。它結合多進程機制和非同步機制。非同步機制使用的是非同步非阻塞方式。(Master-Worker)。

每個工作進程使用非同步非阻塞方式,可以處理多個客戶端請求。當某個工作進程接收到客戶端的請求以後,調用IO進行處理,如果不能立即得到結果,就去處理其他的請求;而客戶端在此期間也無需等待響應,可以去處理其他事情;當IO返回時,就會通知此工作進程;該進程得到通知,暫時掛起當前處理的失誤去響應客戶端請求。

也就是:

Nginx採用非同步非阻塞方式來處理請求,處理請求具體到系統底層就是讀寫事件(所謂阻塞調用方式即請求事件還沒准備好,線程只能一直去等,等事件准備好了再處理;而非阻塞即事件沒准備好,馬上返回ENGAIN,告訴你事件還沒准准備好,而在這期間可以先去做其他事,再回頭看看事件准備好了嗎,時不時會看,需要的開銷也是不小的)

非同步可以理解為循環處理多個准備好的事件,不會導致無謂的資源浪費,當有更多的並發數只會佔用更多的內存而已;

從上面我們可以知道,Nginx伺服器的工作進程調用IO後,就取進行其他工作了;當IO調用返回後,會通知工作進程。 但IO調用時如何把自己的狀態通知給工作進程的呢??

一般解決這個問題有兩種方法:

(1)讓工作進程在進行其他工作的過程中間隔一段時間就去檢查一下IO的狀態,如果完成就響應客戶端,如果未完成,繼續工作。

(2)IO調用在完成後能主動通知工作進程。

當然最好的就是用第二種方法了;像select/poll/epoll等這樣的系統調用就是用來支持第二種解決方案的。這些系統調用也常被稱為事件驅動模型。他們提供了一種機制就只讓進程同時處理多個並發請求,不用關心IO調用的具體狀態。IO調用完全由事件驅動模型來管理。

Nginx中的事件驅動模型

就是用事件驅動處理庫(多路IO復用),最常用的就是select模型,poll模型,epoll模型。

關於這三個模型的詳解在這里可以看到:https://segmentfault.com/a/1190000003063859

通過這個上面的簡單講解,再加上伺服器的架構的了解,可以對Nginx有一個簡單的了解,希望對之後的源碼剖析有幫助。

大致上Nginx的架構就是這樣:

1.Nginx啟動後,會產生一個主進程,主進程執行一系列的工作後會產生一個或者多個工作進程;

2.在客戶端請求動態站點的過程中,Nginx伺服器還涉及和後端伺服器的通信。Nginx將接收到的Web請求通過代理轉發到後端伺服器,由後端伺服器進行數據處理和組織;

3.Nginx為了提高對請求的響應效率,降低網路壓力,採用了緩存機制,將 歷史 應答數據緩存到本地。保障對緩存文件的快速訪問;

##工作進程##

工作進程的主要工作有以下幾項:

接收客戶端請求;

將請求一次送入各個功能模塊進行過濾處理;

IO調用,獲取響應數據;

與後端伺服器通信,接收後端伺服器處理結果;

數據緩存

響應客戶端請求;

##進程交互##

Nginx伺服器在使用Master-Worker模型時,會涉及到主進程和工作進程的交互和工作進程之間的交互。這兩類交互都依賴於管道機制。

1.Master-Worker交互

這條管道與普通的管道不同,它是由主進程指向工作進程的單向管道,包含主進程向工作進程發出的指令,工作進程ID等;同時主進程與外界通過信號通信;

2.worker-worker交互

這種交互是和Master-Worker交互是基本一致的。但是會通過主進程。工作進程之間是相互隔離的,所以當工作進程W1需要向工作進程W2發指令時,首先找到W2的進程ID,然後將正確的指令寫入指向W2的通道。W2收到信號採取相應的措施。

『貳』 Nginx伺服器架構初探

Nginx的每個模塊都基本符合單一職責原則

一般來說,Web伺服器完成並行處理請求工作的三種方式有:多進程方式、多進程方式和非同步方式

多進程方式是指,伺服器每當接收到一個客戶端時,就由伺服器主進程生成一個子進程出來和該客戶端建立連接進行交互,直到連接斷開,該子進程就結束了

多進程方式的優點在於,設計和實現相對簡單,各個子進程之間相對獨立,處理客戶端請求的過程彼此不受到干擾,並且當一個子進程產生問題時,不容易將影響蔓延到其他進程中,這保證了提供服務的穩定性。當子線程退出時,其佔用資源會被操作系統回收,也不會留下任何垃圾。

其缺點是操作系統中生成一個子進程需要進行大量內存復制等操作,在資源和時間上會產生一定的額外開銷。因此,如果Web伺服器接收大量並發請求,就會對系統資源造成壓力,導致系統性能下降。

Apache採用「預生成進程」方式,它將生成子進程的時機提前,在客戶端請求還沒有到來之前就預先生成好,當請求到來時,主進程分配一個子進程和該客戶端進行交互,交互完成之後,該進程也不結束,而被主進程管理起來等待下一個客戶端請求的到來

多線程方式是指當伺服器每當接收到一個客戶端時,會有伺服器主進程派生一個線程出來和該客戶端進行交互
由於操作系統產生一個線程的開銷遠遠小於產生一個進程的開銷,所以多線程方式在很大程度上減輕了Web伺服器對系統資源的要求。該方式使用線程進行任務調度,開發方面可以遵循一定的標准,這相對來說比較規范和有利於協作。
多個線程位於同一進程內,可以訪問同樣的內存空間,彼此之間相互影響;同時,在開發過程中不可避免地要由開發者自己對內存進行管理,其增加了出錯的風險

IIS伺服器使用了多線程方式對外提供服務

同步機制:發送方發送請求之後,需要等待接收到接收方發回的響應後,才接著發送下一個請求
非同步機制:發送方發送請求只有,不等待接收方響應這個請求,就繼續發送下一個請求。
在同步機制中,所有的請求在伺服器端得到同步,發送方和接收方對請求的處理步調是一致的;在非同步機制中,所有來自發送方的請求形成一個隊列,接收方處理完成後通知發送方

阻塞和非阻塞用來描述進程處理調用的方式,在網路通信中,主要指網路套接字Socket的阻塞和非阻塞方式,而Socket的實質也就是IO操作。
Socket的阻塞調用方式為,調用結果返回之前,當前線程從運行狀態被掛起,一直等到調用結果返回之前,才進入就緒狀態,獲取CPU繼續執行
Socket的非阻塞調用方式為,如果調用結果不能馬上返回,當前線程也不會被掛起,而是立即返回執行下一個調用

Nginx結合多進程機制和非同步機制對外提供服務。非同步機制使用的是非同步非阻塞方式

Nginx伺服器啟動後產生一個主進程和多個工作進程(可在配置文件中配置)。Ngnix伺服器的所有工作進程都用於接收和處理客戶端的請求。每個工作進程使用非同步非阻塞方式,可以處理多個客戶端的請求。當某個工作進程接收到客戶端的請求以後,調用IO進行處理,如果不能立即得到返回,就去處理其他的請求;而客戶端再次期間也無須等待響應,可以去處理其他的事情;當IO調用返回結果時,就會通知此工作進程;該進程得到通知,暫時掛起當前處理的事務,去響應客戶端的請求

IO調用把狀態通知給工作進程的兩種方式:

select/poll/epoll/kqueue等這樣的系統調用就是支撐第二種方案的。這種系統調用,也稱為事件模型。IO調用完全由事件驅動模型來管理,事件准備好之後就通知工作進程事件已經就緒

事件驅動就是在持續事務管理過程中,由當前時間點上出現的事件引發的調動可用資源執行相關任務,解決不斷出現的問題,防止事務堆積的一種策略

事件驅動模型一般由事件收集器、事件發送器和事件處理器三部分基本單元組成
事件收集器 專門負責收集所有的事件,包括來自用戶的(滑鼠、鍵盤事件等)、來自硬體的(時鍾事件等)和來自軟體的(操作系統、應用程序自身)。 事件發送器 負責將收集器收集到的事件分發到目標對象中。目標對象就是事件處理器所處的位置。 事件處理器 主要負責具體事件的響應工作,它往往要到實現階段才完全確定

目標對象中事件處理器的幾種方式:

大部分網路伺服器都採用第三種方式,形成了事件驅動庫。事件驅動庫又被稱為多路IO復用方法,最常見的偽:select、poll、epoll。Nginx伺服器還支持rtsig、kqueue、dev/poll和eventport

各個版本Linux和Windows平台都支持的基本事件驅動模型
使用select庫的一般步驟:

如果沒有指定其他事件驅動模型,Nginx自動編譯該庫。
使用--with-select_mole和--without-select_mole強制Nginx是否編譯該庫

Linux平台的事件驅動模型,Windows不支持。
poll和select的基本使用方式是相同的,區別在於:select需要為讀事件、寫事件和異常事件都分別創建一個描述符集合,因此在最後輪詢的時候,需要分別輪訓這三個集合。而poss庫只需要創建一個集合,在每個描述符對應的結構上分別設置讀事件、寫事件或異常事件,最後輪詢的時候,可以同時檢查這三種事件是否發生。poll庫是select庫的優化實現

如果沒有指定其他事件驅動模型,Nginx自動編譯該庫。
使用--with-poll_mole和--without-poll_mole強制Nginx是否編譯該庫

epoll屬於poll庫的一個變種,最大的區別在於效率

epoll庫通過相關調用通知內核創建一個有N個描述符的事件列表;然後,給這些描述符設置所關注的事件,並將它添加到內核的事件列表中。
完成設置之後,epoll庫就開始等待內核通知事件發生了。某一事件發生後,內核將發生事件的描述符列表上報給epoll庫。得到列表事件的epoll庫,就可以進行事件處理了

epoll庫是Linux平台上最高效的。它支持一個進程打開大數目的事件描述符,上限是系統可以打開文件的最大數目。同時,epoll庫的IO效率不隨描述符數目增加而線性下降,因為它只會對內核上報的「活躍」的描述符進行操作

使用rtsig模型時,工作進程會通過系統內核建立一個rtsig隊列用於存放標記事件發生(在Nginx伺服器應用中特指客戶端請求發生)的信號。每一個事件發生時,系統內核就會發生一個信號存放到rtsig隊列中等待工作進程的處理。

rtsig隊列有長度限制,如果超過該長度就會發生溢出。默認情況下,Linux系統事件信號隊列的最大長度設置為1024。在Liunx2.6.6-mm2之後的版本之前,通過修改內核參數/proc/sys/kernel/rtsig-max來自定義該長度設置。在Liunx2.6.6-mm2之後的版本中,該參數被取消,系統各個進程分別擁有各自的事件信號隊列,這個隊列的大小由Linux系統的RLIMIT_SIGPENDING參數定義,在執行setrlimit()系統調用時確定該大小。Linux提供了worker+rlimit_sigpending參數用於調節這種情況下的事件信號隊列長度

當rtsig隊列發生溢出時,Nginx將暫停使用rtsig模型,而調用poll庫處理未處理的事件,直到rtsig信號隊列全部清空,然後再次啟動rtsig模型,以防止新的溢出發生

編譯Nginx伺服器時,使用-with-rtsig_mole配置選項啟用rtsig模型的編譯

kqueue模型,主要用於FreeBSD4.1及以上版本、OpenBSD2.9及以上版本、NetBSD2.0及以上版本以及Mac OS X平台上。該模型也是poll庫的一個變種,其和poll庫的處理方式沒有本質上的區別。該模型同時支持條件觸發(只要滿足條件就觸發一個事件)和邊緣觸發(當狀態發生改變觸發一個事件)。在這些平台下,使用該模型用於請求處理,提高Nginx伺服器性能

/dev/poll模型,主要用於Solaris7 11/99及以上版本、HP/US 11.22及以上版本、IRIX6.5.15及以上版本和Tru 64 UNIX 5.1A及以上版本。它使用了虛擬的/dev/poll設備,開發人員可以將要監視的文件描述符加入這個設備,然後通過ioctl()調用來獲取事件通知。在以上平台中推薦使用

eventport模型,用於支持Solaris 10及以上版本。它可以有效防止內核崩潰等情況的發生

根據不同的部署平台,選擇不同的事件驅動模型以提升Nginx伺服器的處理性能

Nginx伺服器啟動後,產生一個主進程,主進程執行一系列工作後產生一個或者多個工作進程。
主進程主要進行Nginx配置文件解析、數據結構初始化、模塊配置和注冊、信號處理、網路監聽生成、工作進程生成和管理等工作;
工作進程主要進行進程初始化、模塊調用和請求處理等工作,是Nginx伺服器提供服務的主體

Nginx伺服器將接收到的Web請求通過代理轉發到後端伺服器,由後端伺服器進行數據處理和頁面組織,然後將結果返回。
Nginx伺服器為了提高對請求的響應效率,進一步降低網路壓力,採用了緩存機制,將歷史應答數據緩存到本地。在每次Nginx伺服器啟動後的一段時間內,會啟動專門的進程進行對本地緩存的內容重建索引,保證對緩存文件的快速訪問

依賴於管道機制,交互的准備工作都是在工作進程生成時完成的

Run Loops,指的是進程內部用來不停地調配工作,對事件進行循環處理的一種模型。
該模型是一個集合,集合中的每一個元素稱為一個Run-Loop。每個Run-Loop可運行在不同的模式下,其中可以包含它所監聽的輸入事件源、定時器以及在事件發生時需要通知的Run-Loop監聽器。為了監聽特定的事件,可以在Run Loops中添加相應的Run-Loop監聽器。當被監聽的事件發生時,Run-Loop會產生一個消息,被Run-Loop監聽器捕獲,從而執行預定的動作
Nginx伺服器在工作進程中實現了Run-Loop事件處理循環的使用,用來處理客戶端發送的請求事件

『叄』 如何用Nginx快速搭建一個安全的微服務架構

教你如何用Nginx搭建一個安全的、快速的微服務架構
今天我們要談論微服務以及如何使用Nginx構建一個快速的、安全的網路系統。最後,我們將向您展示一個使用Fabric模式如何非常快速和輕松地構建一個微服務的demo。
在我們探討Fabric模式之前,我想談一談微服務並且從Nginx的角度來看這意味著什麼。
0:56 - 大轉變

微服務已經引起了應用程序架構的重大轉變。

當我第一次開始構建應用程序時,他們都是差不多的。幻燈片中所展示的單體架構也象徵了應用程序的構造方式。
目前存在著某種類型的虛擬機(VM),對我來說,就是通常的Java。在虛擬機中應用的功能組件以對象的形式存在,這些對象是在內存中相互通訊的,它們將來來回回處理並進行方法調用。偶爾,你會採用諸如通知等機制來接觸到其他系統以便獲取數據或傳遞信息。

有了微服務之後,應用程序如何構建的範式是完全不同的了。你的功能組件會從在同一個主機的內存中通過虛擬機相互通訊轉變到部署在容器中,並且使用Restful API調用通過HTTP來相互連接。
這是非常強大的,因為它賦予了你功能隔離。它為您提供了更細粒度的可伸縮性,並且你可以獲得更好地處理故障的彈性。很多情況下這是簡單的事實,你只需要使用HTTP進行跨網路調用。
現在,這種方法也有一些缺點。
一件軼事


我有一個暗黑的秘密,我是一個微軟的員工並且從事.Net開發已經很多年了。當我在那兒的時候,我搭建了一個他們的名為Showcase的視頻發布平台。
Showcase是一個用來將微軟內部發布的所有視頻發布到網上的工具。人們可以觀看這些視頻並進行學習,比如Microsoft Word的使用提示和技巧。這是一個非常受歡迎的平台,我們有很多人使用它,並且其中很多人都會在我們發布的視頻上發表評論。
Showcase從一開始就是一個.Net單體應用,隨著它日益受歡迎,我們決定應該將它更換為SOA架構。轉換是相對容易的。Visual Studio提供了本質上的翻轉開關的能力,也就是將你的DLL調用轉變為Restful API調用。隨著一些小的重構,我們能夠讓我們的代碼運行得相當好。我們也為這些評論和應用內的社區功能使用智能社區服務。
緊密的迴路問題


看起來我們是SOA可行的,在我們的首次測試中,一切都工作正常,直到我們將系統切換到我們的Staging環境並開始使用生產環境數據時,我們就會看到一些嚴重的問題。這些問題在在頁面上有很多評論。
這是一個非常受歡迎的平台,其中的一些頁面已經有多達2000條評論了。當我們深入這些問題時,我們意識到這些頁面需要花費一分鍾進行渲染的原因是因為智能社區服務首先需要填充用戶名,然後對每一個用戶名都需要發起一個對於用戶資料庫的網路調用來獲得用戶詳細信息並且填充在渲染頁面上。這是非常低效的,需要一到兩分鍾來渲染頁面,而在內存中進行通常只需要5到6秒鍾。
緩解


當我們經歷了發現和解決問題的過程後,我們最終通過一些措施來調整優化系統,比如對所有的請求進行分組。我們緩存了一些數據,最終我們優化了網路來真正的提高性能。
所以,這與微服務有什麼關系呢?對的,藉助於微服務,你基本上是採用SOA架構的,並且會將其放入超光速引擎中。在SOA架構中所有的對象都是包含在單個虛擬機中並且在其內部管理,在內存中相互通訊,而現在微服務中是使用HTTP進行數據交換的。
當這樣做沒有問題時,你會獲得很好的性能和線性可伸縮性。
Nginx能夠很好地與微服務工作


Nginx是一個你可以用來過渡到微服務的最佳工具之一。
關於Nginx和微服務的一些歷史。我們從一開始就參與了微服務運動,還是第一個從Docker Hub下載應用的,我們的客戶以及那些擁有一些世界上最大的微服務安裝量的最終用戶廣泛地在他們的基礎設施使用Nginx。
原因是Nginx很小、很快並且很可靠。
Nginx微服務參考架構


我們還致力於在Nginx內部使用微服務工作已經有一段時間了。這是一個我們已經搭建的程式化的Nginx微服務參考架構,目前正在AWS上運行。
我們擁有6個核心的微服務,它們都運行在Docker容器里。我們決定建立一個多語種的應用,所以每個容器都可以運行不同的語言,我們目前使用了Ruby、Python、PHP、Java和Node.js。
我們搭建了這個使用十二要素應用的系統,稍加修改,就會使其更好地為微服務工作從而可以替代Roku平台。稍後,我們將向您展示一個實際上運行在demo里的應用。
MRA的價值


為什麼我們要建立這樣一個參考的微服務架構呢?
我們建立這個參考架構是因為我們需要給我們的客戶提供構建微服務的藍圖,我們也想在微服務上下文中測試Nginx和Nginx Plus的功能,弄清楚如何才能更好地利用它的優勢。最後,我們要確保我們對於微服務生態系統以及其可以給我們提供什麼有一個深入的理解。
網路問題


讓我們回到我們討論的大轉變。
從將運行在內存里並且被虛擬機管理的你的應用的所有功能組件遷移到通過網路進行工作並且相互通訊的方式,你會本質上引入一系列為了應用有效工作需要你解決的問題。
第一你需要服務發現,第二,你需要在架構中為所有不同的實例進行負載均衡,然後還有第三個,你需要操心性能和安全。
無論是好是壞,這些問題密不可分,你必須做權衡,有希望的是我們有一個可以解決所有這些問題的解決方案。
讓我們更深入地看待每一個問題。
服務發現

讓我們來談談服務發現。在單體應用中,APP引擎會管理所有的對象關系,你永遠不必擔心一個對象與另一個對象的相對位置,你只需要簡單的調用一個方法,虛擬機會連接到對象實例,然後在調用完畢後銷毀。
然後有了微服務,你需要考慮那些服務的位置。不幸的是,這不是一個普遍的標准流程。您正在使用的各種服務注冊中心,無論是Zookeeper、Consul、etcd或者其它的,都會以不同的方式進行工作。在這個過程中,你需要注冊你的服務,還需要能夠讀取這些服務在哪裡並且可以被連接。
負載均衡


第二個問題是關於負載均衡的。當您擁有多個服務實例時,您希望能夠輕松地連接到它們,將您的請求在它們中高效地分發,並以最快的方式執行,所以不同實例之間的負載均衡是非常重要的問題。
不幸的是,最簡單形式的負載均衡是非常低效的。當你開始使用不同的更加復雜的方案做負載均衡時,它也變得更加復雜並且不易於管理。理想情況下,您希望您的開發人員能夠基於他們的應用程序的需求決定何種負載均衡方案。例如,如果你連接到一個有狀態的應用程序,你需要擁有持久化,這樣可以確保你的Session信息會被保留。
安全和快速通訊


也許微服務最令人生畏的領域是性能和安全。
當在內存中運行時,一切都很快。現在,運行在網路上就會慢了一個數量級。
被安全地包含在一個系統中的信息,通常是二進制格式的,現在會被用文本格式在網路上傳輸。現在是比較容易在網路上布置嗅探器並能夠監聽你的應用正在被移動的所有數據。
如果要在傳輸層加密數據,那麼會在連接速率和CPU使用率方面引入顯著的開銷。SSL/TLS在其全面實施階段需要九個步驟來初始化一個請求。當你的系統每天需要處理成千上萬、幾萬、數十萬或數百萬的請求時,這就成為性能的一個重要障礙了。
一個解決方案


我們已經在Nginx開發的一些解決方案,我們認為,會解決所有的這些問題,它賦予你健壯的服務發現、非常棒的用戶可配置負載均衡以及安全和快速加密。
網路架構


讓我們來談談你可以安裝和配置你的網路架構的各種方法。
我們提出了三種網路模型,它們本身並不相互排斥,但我們認為它們屬於多種格式的。這三種模式是Proxy模式、Router Mesh模式和Fabric模式——這是最復雜的,並在許多方面在其頭部進行負載均衡。
Proxy模式


Proxy模式完全聚焦於你的微服務應用的入站流量,並且事實上忽略內部通訊。
你會獲得Nginx提供的所有的HTTP流量管理方面的福利。你可以有SSL/TLS終止、流量整形和安全,並且藉助於最新版本的Nginx Plus和ModSecurity,你可以獲得WAF能力。
你也可以緩存,你可以將Nginx提供給你的單體應用的所有東西添加到你的微服務系統里,並且藉助於Nginx Plus,你可以實現服務發現。當你的API實例上下浮動時,Nginx Plus可以在負載均衡工具里動態地添加和減去它們。
Router Mesh模式


Router Mesh模式類似於Proxy模式,在其中我們有一個前端代理服務來管理接入流量,但它也在服務之間添加了集中式的負載均衡。
每個服務連接到集中式的Router Mesh,它管理不同服務之間的連接分發。Router Mesh模式還允許你在熔斷器模式中搭建,以便可以對你的應用添加彈性並允許你採取措施來監控和拉回你的失效的服務實例。
不幸的是,因為該模式增加了一個額外的環節,如果你不得不進行SSL/TLS加密,它事實上加劇了性能問題。這就是引入Fabric模式的原因。
Fabric模式


Fabric模式是將其頭部的所有東西翻轉的模式。
就像之前的另外兩個模式一樣,在前面會有一個代理伺服器來管理流入流量,但與Router Mesh模式不同的地方就是你用運行在每個容器里的Nginx Plus來替代了集中式的Router。
這個Nginx Plus實例對於所有的HTTP流量作為反向和正向代理,使用這個系統,你可以獲得服務發現、健壯的負載均衡和最重要的高性能加密網路。
我們將探討這是如何發生的,以及我們如何處理這項工作。讓我們先來看看一個服務如何連接和分發他們的請求結構的正常流程。
正常的流程


在這個圖中,你可以看到投資管理器需要跟用戶管理器通訊來獲取信息。投資管理器創建了一個HTTP客戶端,該客戶端針對服務注冊中心發起了一個DNS請求並獲得返回的一個IP地址,接著初始化了一個到用戶管理器的SSL/TLS連接,該連接需要通過九階段的協商或者是」握手」過程。一旦數據傳輸完畢,虛擬機會關閉連接並進行HTTP客戶端的垃圾回收。
整個過程就是這樣。這是相當簡單和易於理解的。當你把它分解成這些步驟時,您可以看到該模式是如何真正完成請求和響應過程的。
在Fabric模式中,我們已經改變了這一點。
Fabric模式的細節


你會注意到的第一件事是Nginx Plus是運行在每一個服務里的,並且應用程序代碼是在本地與Nginx Plus通信的。因為這些是本地連接,你不需要擔心加密問題。它們可以是從Java或者PHP代碼到Nginx Plus實例的HTTP請求,並且都是在容器內的本地HTTP請求。
你也注意到Nginx Plus會管理到服務注冊中心的連接,我們有一個解析器,通過非同步查詢注冊中心的DNS實例來獲取所有的用戶管理器實例,並且預先建立連接,這樣當Java服務需要從用戶管理器請求一些數據的時候,可以使用預先建立的連接。
持久的SSL/TLS連接


微服務之間的有狀態的、持久化的並且可以加密的連接是真正的益處。
記得在第一個圖中服務實例是如何通過一些流程的吧,比如創建HTTP客戶端、協商SSL/TLS連接、發起請求並關閉的嗎?在這里,Nginx預先建立了微服務之間的連接,並使用Keepalive特性,保持調用之間的持續連接,這樣你就不必為每一個請求處理SSL/TLS協商了。
本質上,我們創建了一個迷你的從服務到服務的VPN連接。在我們最初的測試中,我們發現連接速度增加了77%。
熔斷器Plus


在Fabric模式以及Router Mesh模式中,你也可以從創建和使用熔斷器模式中獲得好處。
本質上,您定義了一個在服務內部的活躍的健康檢查,並設置緩存,以便在服務不可用的情況下保留數據,從而獲得完整的熔斷器功能。
所以,現在我可以確定你認為Fabirc模式聽起來很酷,並且想在實際環境中躍躍欲試。

『肆』 Nginx + Apache + Tomcat架構方式,為什麼需要ApacheApache的作用

nginx和apache兩者的作用相同,都是常見webserver伺服器,相互獨立也可相符搭配,都是用於瀏覽器用戶過來的http請求,然後把請求結果反應給瀏覽器。

apache是出現比較早的web server,90年代就有了,兼容性好文檔全應用廣泛。
nginx是後起之秀,2000年以後才有的,在web2.0年代性能遠遠超過apache,是時下比較流行的web server。

至於tomcat ,那是用來處理java程序的解釋器。本身apache也好,nginx也好,都是無法直接處理java語言的,只能通過設置,當收到java文件請求時,傳給後方tomcat處理,再把tomcat的反應回給瀏覽器。另php-fpm,是用來處理php程序的,作用跟tomcat差不多。

怎麼選擇搭配,這個就看各人的喜歡和開發需要了。我比較常用的就是nginx+php-fpm,apache+tomcat,nginx+tomcat。也試過nginx+apache+php-fpm+tomcat等復雜組合。

只要了解每個軟體的功能和作用,就可以合理利用自由搭配。

『伍』 iis apache nginx的優缺點是什麼,該如何選擇哪種架構

1,iis 不用說如果你程序是asp的你就只能選擇iis
2,apache 這個沒得說,優點很明顯,穩定,強大,php可以用mole的方式,如果你裝了xcache,沒得說apache是你最好的選擇。不過apache有個很大的缺點,ddos的時候支持的並發數非常低
3,nginx 這個重點是反向代理,如果你做鏡像或者網站靜態頁面的而且流量比較大,用nginx分流是個不錯的選擇,不過php只能用fastcgi的方式跑,缺點就是php裝了xcache他每個fastcgi的進程裡面的緩存都是獨立的,有點浪費資源的感覺,優點是ddos的時候這3個伺服器之中他是最好的,並發數支持最大。

『陸』 「微服務架構」部署NGINX Plus作為API網關,第1部分 - NGINX

了解著名的Nginx伺服器(微服務必不可少的東西)如何用作API網關。

現代應用程序體系結構的核心是HTTP API。 HTTP使應用程序能夠快速構建並輕松維護。無論應用程序的規模如何,HTTP API都提供了一個通用介面,從單用途微服務到無所不包的整體。通過使用HTTP,支持超大規模Internet屬性的Web應用程序交付的進步也可用於提供可靠和高性能的API交付。

有關API網關對微服務應用程序重要性的精彩介紹,請參閱我們博客上的構建微服務:使用API​​網關。

作為領先的高性能,輕量級反向代理和負載均衡器,NGINX Plus具有處理API流量所需的高級HTTP處理功能。這使得NGINX Plus成為構建API網關的理想平台。在這篇博文中,我們描述了許多常見的API網關用例,並展示了如何配置NGINX Plus以便以高效,可擴展且易於維護的方式處理它們。我們描述了一個完整的配置,它可以構成生產部署的基礎。

注意:除非另有說明,否則本文中的所有信息均適用於NGINX Plus和NGINX開源。

API網關的主要功能是為多個API提供單一,一致的入口點,無論它們在後端如何實現或部署。並非所有API都是微服務應用程序。我們的API網關需要管理現有的API,單塊和正在部分過渡到微服務的應用程序。

在這篇博文中,我們引用了一個假設的庫存管理API,即「倉庫API」。我們使用示例配置代碼來說明不同的用例。 Warehouse API是一個RESTful API,它使用JSON請求並生成JSON響應。但是,當部署為API網關時,使用JSON不是NGINX Plus的限制或要求; NGINX Plus與API本身使用的架構風格和數據格式無關。

Warehouse API實現為離散微服務的集合,並作為單個API發布。庫存和定價資源作為單獨的服務實施,並部署到不同的後端。所以API的路徑結構是:

例如,要查詢當前倉庫庫存,客戶端應用程序會向/ api / warehouse / inventory發出HTTP GET請求。

使用NGINX Plus作為API網關的一個優點是,它可以執行該角色,同時充當現有HTTP流量的反向代理,負載平衡器和Web伺服器。如果NGINX Plus已經是應用程序交付堆棧的一部分,那麼通常不需要部署單獨的API網關。但是,API網關所期望的某些默認行為與基於瀏覽器的流量的預期不同。出於這個原因,我們將API網關配置與基於瀏覽器的流量的任何現有(或未來)配置分開。

為實現這種分離,我們創建了一個支持多用途NGINX Plus實例的配置布局,並為通過CI / CD管道自動配置部署提供了便利的結構。 / etc / nginx下的結果目錄結構如下所示。

所有API網關配置的目錄和文件名都以api_為前綴。這些文件和目錄中的每一個都啟用API網關的不同特性和功能,並在下面詳細說明。

所有NGINX配置都以主配置文件nginx.conf開頭。要讀入API網關配置,我們在nginx.conf的http塊中添加一個指令,該指令引用包含網關配置的文件api_gateway.conf(下面的第28行)。請注意,默認的nginx.conf文件使用include偽指令從conf.d子目錄中引入基於瀏覽器的HTTP配置(第29行)。本博文廣泛使用include指令來提高可讀性並實現配置某些部分的自動化。

api_gateway.conf文件定義了將NGINX Plus公開為客戶端的API網關的虛擬伺服器。此配置公開API網關在單個入口點https://api.example.com/(第13行)發布的所有API,受第16到21行配置的TLS保護。請注意,此配置純粹是HTTPS - 沒有明文HTTP偵聽器。我們希望API客戶端知道正確的入口點並默認進行HTTPS連接。

此配置是靜態的 - 各個API及其後端服務的詳細信息在第24行的include偽指令引用的文件中指定。第27到30行處理日誌記錄默認值和錯誤處理,並在響應中討論錯誤部分如下。

一些API可以在單個後端實現,但是出於彈性或負載平衡的原因,我們通常期望存在多個API。使用微服務API,我們為每個服務定義單獨的後端;它們一起作為完整的API。在這里,我們的Warehouse API被部署為兩個獨立的服務,每個服務都有多個後端。

API網關發布的所有API的所有後端API服務都在api_backends.conf中定義。這里我們在每個塊中使用多個IP地址 - 埠對來指示API代碼的部署位置,但也可以使用主機名。 NGINX Plus訂戶還可以利用動態DNS負載平衡,自動將新後端添加到運行時配置中。

配置的這一部分首先定義Warehouse API的有效URI,然後定義用於處理對Warehouse API的請求的公共策略。

Warehouse API定義了許多塊。 NGINX Plus具有高效靈活的系統,可將請求URI與配置的一部分進行匹配。通常,請求由最具體的路徑前綴匹配,並且位置指令的順序並不重要。這里,在第3行和第8行,我們定義了兩個路徑前綴。在每種情況下,$ upstream變數都設置為上游塊的名稱,該上游塊分別代表庫存和定價服務的後端API服務。

此配置的目標是將API定義與管理API交付方式的策略分開。為此,我們最小化了API定義部分中顯示的配置。在為每個位置確定適當的上游組之後,我們停止處理並使用指令來查找API的策略(第10行)。

使用重寫指令將處理移至API策略部分

重寫指令的結果是NGINX Plus搜索匹配以/ _warehouse開頭的URI的位置塊。第15行的位置塊使用=修飾符執行完全匹配,從而加快處理速度。

在這個階段,我們的政策部分非常簡單。位置塊本身標記為第16行,這意味著客戶端無法直接向它發出請求。重新定義$ api_name變數以匹配API的名稱,以便它在日誌文件中正確顯示。最後,請求被代理到API定義部分中指定的上游組,使用$ request_uri變數 - 其中包含原始請求URI,未經修改。

API定義有兩種方法 - 廣泛而精確。每種API最合適的方法取決於API的安全要求以及後端服務是否需要處理無效的URI。

在warehouse_api_simple.conf中,我們通過在第3行和第8行定義URI前綴來使用Warehouse API的廣泛方法。這意味著以任一前綴開頭的任何URI都代理到相應的後端服務。使用基於前綴的位置匹配,對以下URI的API請求都是有效的:

如果唯一的考慮是將每個請求代理到正確的後端服務,則廣泛的方法提供最快的處理和最緊湊的配置。另一方面,精確的方法使API網關能夠通過顯式定義每個可用API資源的URI路徑來理解API的完整URI空間。採用精確的方法,Warehouse API的以下配置使用精確匹配(=)和正則表達式(〜)的組合來定義每個URI。

此配置更詳細,但更准確地描述了後端服務實現的資源。這具有保護後端服務免於格式錯誤的客戶端請求的優點,代價是正常表達式匹配的一些小額外開銷。有了這個配置,NGINX Plus接受一些URI並拒絕其他URI無效:

使用精確的API定義,現有的API文檔格式可以驅動API網關的配置。可以從OpenAPI規范(以前稱為Swagger)自動化NGINX Plus API定義。此博客文章的Gists中提供了用於此目的的示例腳本

隨著API的發展,有時會發生需要更新客戶端的重大更改。一個這樣的示例是重命名或移動API資源。與Web瀏覽器不同,API網關無法向其客戶端發送命名新位置的重定向(代碼301)。幸運的是,當修改API客戶端不切實際時,我們可以動態地重寫客戶端請求。

在下面的示例中,我們可以在第3行看到定價服務以前是作為庫存服務的一部分實現的:rewrite指令將對舊定價資源的請求轉換為新的定價服務。

動態重寫URI意味著當我們最終在第26行代理請求時,我們不能再使用$ request_uri變數(正如我們在warehouse_api_simple.conf的第21行所做的那樣)。這意味著我們需要在API定義部分的第9行和第14行使用稍微不同的重寫指令,以便在處理切換到策略部分時保留URI。

HTTP API和基於瀏覽器的流量之間的主要區別之一是如何將錯誤傳達給客戶端。當NGINX Plus作為API網關部署時,我們將其配置為以最適合API客戶端的方式返回錯誤。

頂級API網關配置包括一個定義如何處理錯誤響應的部分。

第27行的指令指定當請求與任何API定義都不匹配時,NGINX Plus會返回錯誤而不是默認錯誤。此(可選)行為要求API客戶端僅向API文檔中包含的有效URI發出請求,並防止未經授權的客戶端發現通過API網關發布的API的URI結構。

第28行指的是後端服務本身產生的錯誤。未處理的異常可能包含我們不希望發送到客戶端的堆棧跟蹤或其他敏感數據。此配置通過向客戶端發送標准化錯誤來進一步提供保護。

完整的錯誤響應列表在第29行的include偽指令引用的單獨配置文件中定義,其前幾行如下所示。如果首選不同的錯誤格式,並且通過更改第30行上的default_type值以匹配,則可以修改此文件。您還可以在每個API的策略部分中使用單獨的include指令來定義一組覆蓋默認值的錯誤響應。

有了這種配置,客戶端對無效URI的請求就會收到以下響應。

在沒有某種形式的身份驗證的情況下發布API以保護它們是不常見的。 NGINX Plus提供了幾種保護API和驗證API客戶端的方法。有關基於IP地址的訪問控制列表(ACL),數字證書身份驗證和HTTP基本身份驗證的信息,請參閱文檔。在這里,我們專注於API特定的身份驗證方法。

API密鑰身份驗證

API密鑰是客戶端和API網關已知的共享密鑰。它們本質上是作為長期憑證發布給API客戶端的長而復雜的密碼。創建API密鑰很簡單 - 只需編碼一個隨機數,如本例所示。

在頂級API網關配置文件api_gateway.conf的第6行,我們包含一個名為api_keys.conf的文件,其中包含每個API客戶端的API密鑰,由客戶端名稱或其他描述標識。

API密鑰在塊中定義。 map指令有兩個參數。第一個定義了API密鑰的位置,在本例中是在$ http_apikey變數中捕獲的客戶端請求的apikey HTTP頭。第二個參數創建一個新變數($ api_client_name)並將其設置為第一個參數與鍵匹配的行上的第二個參數的值。

例如,當客戶端提供API密鑰7B5zIqmRGXmrJTFmKa99vcit時,$ api_client_name變數設置為client_one。此變數可用於檢查經過身份驗證的客戶端,並包含在日誌條目中以進行更詳細的審核。

地圖塊的格式很簡單,易於集成到自動化工作流程中,從現有的憑證存儲生成api_keys.conf文件。 API密鑰身份驗證由每個API的策略部分強制執行。

客戶端應在apikey HTTP頭中顯示其API密鑰。如果此標頭丟失或為空(第20行),我們發送401響應以告知客戶端需要進行身份驗證。第23行處理API鍵與地圖塊中的任何鍵都不匹配的情況 - 在這種情況下,api_keys.conf第2行的默認參數將$ api_client_name設置為空字元串 - 我們發送403響應告訴身份驗證失敗的客戶端。

有了這個配置,Warehouse API現在可以實現API密鑰身份驗證。

JWT身份驗證

JSON Web令牌(JWT)越來越多地用於API身份驗證。原生JWT支持是NGINX Plus獨有的,可以在我們的博客上驗證JWT,如使用JWT和NGINX Plus驗證API客戶端中所述。

本系列的第一篇博客詳細介紹了將NGINX Plus部署為API網關的完整解決方案。可以從我們的GitHub Gist倉庫查看和下載此博客中討論的完整文件集。本系列的下一篇博客將探討更高級的用例,以保護後端服務免受惡意或行為不端的客戶端的攻擊。

原文:https://dzone.com/articles/deploying-nginx-plus-as-an-api-gateway-part-1-ngin

本文:http://pub.intelligentx.net/deploying-nginx-plus-api-gateway-part-1-nginx

討論:請加入知識星球或者小紅圈【首席架構師圈】

『柒』 17《Nginx 入門教程》Nginx 的基礎架構解析(上)

前面介紹 Nginx 時有介紹過 Nginx 的進程模型。Nginx 啟動時首先啟動一個 Master 進程,然後由 Master 進程啟動一個或者多個 Worker 子進程。Master 進程主要完成配置讀取,通過發送信號控制 Worker 進程的啟動和停止等,而 Worker 子進程是用來處理客戶端發來的 Http 請求,且Worker進程之間會通過共享內存進行通信。

假設 Nginx 啟動了多個 Worker 進程,並且在 Master 進程中通過 socket 套接字監聽80埠。 這些 Worker 進程 fork 自 Master 進程,然後每個worker進程都可以去 accept 這個監聽的 socket。 當一個連接進來後,所有在 accept 在這個 socket 上面的進程,都會收到消息,但是只有一個進程可以 accept 這個連接,其它的則 accept 失敗,這便是所謂的驚群現象。Nginx 處理這種情況的方式就是加鎖。有了鎖之後,在同一時刻,就只會有一個 Worker 進程在 accpet 連接,這樣就不會有驚群問題了。在 Worker 進程拿到 Http 請求後,就開始按照前面介紹的 11個階段處理該 Http 請求,最後返回響應結果並斷開連接。

最早我們學習了 Nginx 命令行操作,這些命令行操作都是給 Master 進程發信號,然後再由 Master 進程發送信號給 Worker 進程,從而達到控制 Worker 進程的目標。我們以 Nginx 的熱部署命令 ./nginx -s reload 來描述 Nginx 命令行的執行流程。具體過程如下:

Nginx 命令行中 -s 參數的每個值都對應這一個信號。因此,我們也可以直接對 Master 進程發生相應信號達到同樣的目的。

事件驅動模型是實現非同步非阻塞的一個手段。對於 web 伺服器來說,客戶端 A 的請求連接到服務端時,服務端的某個進程(Nginx 的 worker 進程)會處理該請求,此進程在沒有返回給客戶端 A 結果時,它又去處理了客戶端 B 的請求。服務端把客戶端 A 以及客戶端 B 發來的請求作為事件交給了"事件收集器",而"事件收集器"再把收集到的事件交由"事件發送器"發送給"事件處理器"進行處理。最後"事件處理器"處理完該事件後,通知服務端進程,服務端進程再把結果返回給客戶端A、客戶端B。在這個過程中,服務端進程做的事情屬於用戶級別的,而事件處理這部分工作屬於內核級別的。也就是說這個事件驅動模型是需要操作系統內核來作為支撐的。

Nginx 的事件驅動模型,支持 select、poll、epoll、rtsig、kqueue、/dev/poll、eventport 等。 最常用的是前三種,特別是 epoll 模型,這也是 Nginx 中的默認配置。可以說 epoll 模型成就了 Nginx 的高性能和高並發特性。

按照前面的講解,我們測試給 Nginx 的 Master 進程直接發送信號,並觀察進程情況:

可以看到 Nginx 啟動了 Master 進程(pid=10640),後由 Master 進程 fork 除了兩個 Worker 進程和兩個 Cache 進程,他們的父進程 id 均為10640。現在做如下幾個操作:

可以看到原先的 Worker 進程被殺死後,Nginx 的主進程又立馬拉起來一個新的 Worker 進程提供服務。這說明 Nginx 是非常可靠的,只要 Master 進程還在就會保證 Worker 進程持續存在並提供服務。

可以看到,在移除 Nginx 的 access.log 日誌後,在向 Nginx 主進程發送 USR1 信號,Nginx 會重新生成一個新的 access.log 日誌。

本節主要介紹 Nginx 的進程模型以及介紹了 Master 和 Worker 之間的通信過程。此外,我們介紹了 Nginx 的事件驅動模型。非同步、多路IO復用、非阻塞等特點早就了 Nginx 的高性能。接下來,我們完成了 Nginx 進程模型的幾個實驗,直觀體檢 Nginx 的進程模型。下一節將重點介紹 Nginx 模塊相關的內容,並手動實現一個簡單的 http 模塊。

『捌』 Nginx + Apache + Tomcat架構方式,為什麼需要ApacheApache的作用

這是為了讓Nginx + Apache + Tomcat架構方式實現反向代理與動靜分離
Nginx跑靜態和做負載反向代理,動態php還是交給apache處理比較穩定。nginx跑靜態的能力是無與倫比的,是目前web伺服器里最強的,但是處理動態還是用Apache好點。nginx和apache、tomcat、resin的動靜分離配置其實很簡單,就幾句配置,穩定性也非常好。你可以在網上搜索一下。

『玖』 如何在Ubuntu 16.04上使用Nginx的OpenResty Web框架

第1步 - 下載OpenResty的源代碼和依賴關系

在本節中,我們將從源代碼安裝OpenResty。

首先,從OpenResty網站的下載頁面找到最新的OpenResty源代碼版本。下載tarball,確保如果更改了版本號,請使用最新版本號。

wget https://openresty.org/download/openresty-1.11.2.2.tar.gz
下載PGP密鑰文件,以便我們可以驗證文件的內容。

wget https://openresty.org/download/openresty-1.11.2.2.tar.gz.asc
接下來,我們需要添加作者的公共密鑰,如下載頁面上所列。在撰寫本文時,這是公鑰A0E98066 。但是,請檢查它是否已更改;它被列在同一下載頁面上。

gpg --keyserver pgpkeys.mit.e --recv-key A0E98066

第2步 - 安裝OpenResty

我們將配置OpenResty與PCRE正則表達式和IPv6支持。我們還將通過提供-j2標志來並行化構建過程的一部分,這將告訴make 2個作業可以同時運行。此命令將主要測試所有依賴項是否可用於您的系統,並收集將由構建步驟稍後使用的信息。它也已經構建了一些依賴項,如LuaJIT。./configure -j2 --with-pcre-jit --with-ipv6
然後,您可以通過提供-j2並行度標志來構建OpenResty。這將編譯OpenResty本身。make -j2
最後,您可以安裝OpenResty。使用sudo確保所有文件可以復制到系統上的正確位置,以便OpenResty可以在運行時找到它們。sudo make install
您需要在防火牆中允許HTTP連接才能使Web伺服器正常工作。sudo ufw allow http
您也可以選擇允許HTTPS與sudo ufw allow https如果你要使用它。您可以通過檢查防火牆的狀態來驗證防火牆的更改。sudo ufw status
您應該看到顯示的輸出中允許HTTP流量(埠80 ),以及如果您添加它的HTTPS(埠443 )。

您現在可以檢查安裝是否有效。首先,啟動OpenResty。sudo /usr/local/openresty/bin/openresty
如果命令成功,它將立即完成而不輸出文本。在這種情況下,您可以在瀏覽器中訪問http:// your_server_ip 。 你會看到一個頁面,說歡迎來到OpenResty!確認它已完全安裝和工作。

您現在可以停止OpenResty伺服器。sudo /usr/local/openresty/bin/openresty -s quit
OpenResty已安裝,但您仍需要配置OpenResty在啟動時運行,所以伺服器不必手動啟動。

第3步 - 將OpenResty設置為服務

在這里,我們將OpenResty設置為一個服務,所以它在啟動時自動啟動。我們將使用systemd init服務。 您可以閱讀此systemd基礎教程了解更多信息,以及本單元文件教程 ,了解單元文件的具體信息。

首先使用nano或您喜歡的文本編輯器創建一個新的systemd文件。sudo nano /etc/systemd/system/openresty.service
對於本教程,我們將從全新安裝中復制默認的Nginx systemd文件,並針對OpenResty進行修改。

第4步 - 配置OpenResty

要配置OpenResty,我們使用默認的Nginx配置作為參考,以便它大部分匹配你可能會熟悉的。 首先,再次打開OpenResty配置文件: sudo nano /usr/local/openresty/nginx/conf/nginx.conf
這一次,我們將修改http塊並將此http塊中的server塊移動到一個新文件以具有更好的結構。 首先,找到http {行,並刪除之後的一切,除了最後一行與對應的} 。

當前/usr/local/openresty/nginx/conf/nginx.conf

user www-data;worker_processes auto;pid /run/openresty.pid;events {
worker_connections 1024;}http {
include mime.types;
default_type application/octet-stream;

. . .}
然後,將以下內容復制到http塊中,以便整個文件看起來像這樣。我們將一次過一個更改。

/usr/local/openresty/nginx/conf/nginx.conf

user www-data;worker_processes auto;pid /run/openresty.pid;events {
worker_connections 1024;}http {
include mime.types;
default_type application/octet-stream;

sendfile on;
tcp_nopush on;
tcp_nodelay on;

keepalive_timeout 65;

ssl_protocols TLSv1 TLSv1.1 TLSv1.2; # Dropping SSLv3, ref: POODLE
ssl_prefer_server_ciphers on;

access_log /var/log/openresty/access.log;
error_log /var/log/openresty/error.log;

gzip on;
gzip_disable "msie6";

include ../sites/*;
}
保存並關閉文件。 我們對默認文件所做的更改是:

  • 取消tcp_nopush on; ,它告訴OpenResty只發送完整的數據包。 當使用sendfile選項時,此選項很有用,這將允許OpenResty優化將靜態文件發送到客戶端。

  • 添加tcp_nodelay on; 。 此選項將嘗試盡快發送數據包,這可能看起來與上述選項相反,但它在不同的時間使用。 tcp_nodelay僅在對HTTP請求使用keepalive選項時使用,這是通過Web瀏覽器連接到Web伺服器,這將避免每次請求時啟動HTTP連接的開銷。

  • 添加和修改ssl_protocols和ssl_prefer_server_ciphers行。這些選項配置OpenResty的SSL選項。我們刪除了易受已知的HTTPS攻擊的舊協議,例如POODLE攻擊。

  • 添加access_log和error_log行,它們配置Web伺服器的日誌位置。 我們將日誌存儲在上一步中創建的/var/log/openresty目錄中。

  • 取消注釋gzip on並添加gzip_disable "msie6" 。這些選項將配置GZIP,這將壓縮網頁,以便有更少的數據傳輸。我們還添加了最後一個選項,因為Internet Explorer 6(及更早版本)並不總是正確處理GZIP內容。

  • 添加include ../sites/*; ,它告訴OpenResty在/usr/local/openresty/nginx/sites目錄中查找額外的配置文件,稍後我們將創建它。

  • 刪除所有server塊,我們將在此步驟中稍後重新定位到新文件。

  • 接下來,創建我們在include行中指定的新sites目錄。 sudo mkdir /usr/local/openresty/nginx/sites

  • 創建default網站。 sudo nano /usr/local/openresty/nginx/sites/default.conf

  • 在此新文件中添加以下內容。這是從nginx.conf重新定位原始伺服器塊,但有更多細節的內聯注釋。
  • /usr/local/openresty/nginx/sites/default.conf

  • server {

  • # Listen on port 80.

  • listen 80 default_server;

  • listen [::]:80 default_server;


  • # The document root.

  • root /usr/local/openresty/nginx/html/default;


  • # Add index.php if you are using PHP.

  • index index.html index.htm;


  • # The server name, which isn't relevant in this case, because we only have one.

  • server_name _;


  • # When we try to access this site...

  • location / {

  • # ... first attempt to serve request as file, then as a directory,

  • # then fall back to displaying a 404.

  • try_files $uri $uri/ =404;

  • }


  • # Redirect server error pages to the static page /50x.html.

  • error_page 500 502 503 504 /50x.html;

  • location = /50x.html {

  • root /usr/local/openresty/nginx/html;

  • }}

  • 保存並關閉文件。 現在,為此網站創建一個新目錄。 sudo mkdir /usr/local/openresty/nginx/html/default

  • 然後將原始index.html從其原始位置移動到新目錄。 sudo mv /usr/local/openresty/nginx/html/index.html /usr/local/openresty/nginx/html/default

  • 最後,重新啟動OpenResty以使用此新站點。 sudo systemctl restart openresty

  • 您現在可以再次訪問http:// your_server_ip ,並查看與之前相同的網頁。 現在OpenResty是完全配置的,我們可以嘗試一些由OpenResty介紹的,在Nginx默認情況下不可用的功能。
  • 第5步 - 使用OpenResty Lua模塊

  • 在本節中,我們將看看OpenResty添加的不同模塊的組合,這些模塊都存在以適應Lua腳本。我們將在整個步驟中/usr/local/openresty/nginx/sites/default.conf /usr/local/openresty/nginx/sites/default.conf,因此首先打開它。 sudo nano /usr/local/openresty/nginx/sites/default.conf

  • 首先,我們將看一下content_by_lua_block配置選項。 從下面的示例配置中復制location塊,並將其添加到server塊中,位於兩個現有location塊下面。
  • /usr/local/openresty/nginx/sites/default.conf content_by_lua_block示例

  • server {

  • . . .


  • location /example {

  • default_type 'text/plain';


  • content_by_lua_block {

  • ngx.say('Hello, Sammy!')

  • }

  • }}

  • 保存並關閉文件,然後重新載入配置。 sudo systemctl reload openresty

  • 如果您http:// your_server_ip /example訪問http:// your_server_ip /example ,您會看到一個http:// your_server_ip /example 您好,Sammy的頁面! 。讓我們解釋這是如何工作的。 content_by_lua_block配置指令執行其中的所有內容作為Lua代碼。 在這里,我們使用Lua函數ngx.say來列印消息Hello,Sammy!到頁面。 對於另一個示例,將location /example塊的內容替換為:
  • /usr/local/openresty/nginx/sites/default.conf content_by_lua_file示例

  • server {

  • . . .


  • location /example {

  • default_type 'text/plain';


  • content_by_lua_file /usr/local/openresty/nginx/html/default/index.lua;

  • }}

  • content_by_lua_file從外部文件載入Lua內容,所以讓我們創建上面指定的內容: /usr/local/openresty/nginx/html/default/index.lua 。 sudo nano /usr/local/openresty/nginx/html/default/index.lua

  • 將以下內容添加到文件,然後保存並將其關閉。
  • /usr/local/openresty/nginx/html/default/index.lua

  • local name = ngx.var.arg_name or "Anonymous"ngx.say("Hello, ", name, "!")

  • 這是一個簡單的Lua,它讀取URL中的查詢參數, name並自定義問候消息。如果沒有傳遞參數,則使用「匿名」。 再次重新載入配置。 sudo systemctl reload openresty

  • 現在,在瀏覽器中訪問http:// your_server_ip /example?name= Sammy 。 這將顯示你好,Sammy! 。 您可以更改name查詢參數,或完全忽略它。 Hello, Sammy!

  • 您還可以更改name查詢參數以顯示任何其他名稱。 警告:請勿將您要載入的Lua文件從Web訪問到的位置。如果這樣做,如果有人訪問此文件,則可能會包含應用程序代碼。將文件放在文檔根目錄之外,例如,將文檔根目錄更改為/usr/local/openresty/nginx/html/default/public ,並將Lua文件放在其上一個目錄。

『拾』 遠程伺服器返回錯誤:(502)錯誤的網關 是什麼原因、

502錯誤原因分析:

1、這類錯誤常見於Nginx+PHP的Web架構,Nginx將請求提交給網關PHP-FPM執行,但是由於某些原因請求沒有執行完畢導致PHP-FPM進程終止執行。說到此,這個問題就很明了了,與網關服務如PHP-FPM的配置有關了。

2、php-fpm.conf配置文件中有兩個參數就需要你考慮到,分別是max_children和request_terminate_timeout。

3、max_children最大子進程數,在高並發請求下,達到php-fpm最大響應數,後續的請求就會出現502錯誤的。可以通過netstat命令來查看當前連接數。

4、request_terminate_timeout設置單個請求的超時終止時間。還應該注意到php.ini中的max_execution_time參數。當請求終止時,也會出現502錯誤的。

5、當積累了大量的php請求,你重啟php-fpm釋放資源,但一兩分鍾不到,502又再次呈現, 這時還應該考慮到資料庫,查看下資料庫進程是否有大量的locked進程,資料庫死鎖導致超時,前端終止了繼續請求,但是sql語句還在等待釋放鎖,這時就要重啟資料庫服務了或kill掉死鎖SQL進程了。

6、所以在調整max_children和request_terminate_timeout、max_execution_time也需要考慮到伺服器資源使用情況及應用代碼sql執行效率情況,需要綜合衡量。502 Bad Gateway:伺服器作為網關或者代理時,為了完成請求訪問下一個伺服器,但該伺服器返回了非法的應答。 亦說Web伺服器用作網關或代理伺服器時收到了無效響應。