Nginx - 代理、缓存
Nginx
標(biāo)簽 : nginx
代理
代理服務(wù)可簡單的分為正向代理和反向代理:
正向代理: 用于代理內(nèi)部網(wǎng)絡(luò)對Internet的連接請求(如VPN/NAT),客戶端指定代理服務(wù)器,并將本來要直接發(fā)送給目標(biāo)Web服務(wù)器的HTTP請求先發(fā)送到代理服務(wù)器上, 然后由代理服務(wù)器去訪問Web服務(wù)器, 并將Web服務(wù)器的Response回傳給客戶端:
反向代理: 與正向代理相反,如果局域網(wǎng)向Internet提供資源,并讓Internet上的其他用戶可以訪問局域網(wǎng)內(nèi)資源, 也可以設(shè)置一個代理服務(wù)器, 它提供的服務(wù)就是反向代理. 反向代理服務(wù)器接受來自Internet的連接,然后將請求轉(zhuǎn)發(fā)給內(nèi)部網(wǎng)絡(luò)上的服務(wù)器,并將Response回傳給Internet上請求連接的客戶端:
總結(jié)來說:
- 正向代理和客戶端同屬一個陣營,對于目標(biāo)服務(wù)器來說,可將他們看成一個客戶端;
- 反向代理和目標(biāo)服務(wù)器同屬一個陣營,對于客戶端來說,他們”偽裝”成了一個目標(biāo)服務(wù)器.
正向代理
由于使用Nginx做正向代理服務(wù)的相對較少, 因此Nginx提供的代理服務(wù)本身也比較簡單, 提供的指令也不多, 直接由ngx_http_core_module模塊支持.
指令
- resolver
- resolver_timeout
- proxy_pass
注: proxy_pass不僅用于正向代理,更主要是應(yīng)用于反向代理服務(wù),后面還有關(guān)于它的詳細(xì)敘述.
示例
server {listen 8001;resolver 192.168.111.9 192.168.111.8 192.168.100.8 192.168.100.9;location / {proxy_pass http://$http_host$request_uri;}error_page 500 502 503 504 /50x.html;location = /50x.html {root html;}}注意:
1. 在配置正向代理的server塊中,不要使用server_name指令,即不能設(shè)置虛擬主機(jī)名或IP.
2. Nginx正向代理不支持代理HTTPS站點.
反向代理
反向代理是Nginx最常用且最重要的功能之一,由標(biāo)準(zhǔn)HTTP模塊ngx_http_proxy_model支持.同正向代理類似,反向代理一般也單獨配置一個server塊.
指令
- proxy_pass
同正向代理, 該指令用來配置被代理服務(wù)器地址,可以是主機(jī)名稱/IP地址+端口號等形式:
proxy_pass http://localhost:8000/uri/;- upstream
如果被代理的是一組服務(wù)器的話, 可以使用upstream指令配置一組后端服務(wù)器.Defines a group of servers. Servers can listen on different por ts. In addition, servers listening on TCP and UNIX-domain sockets can be mixed.
http {## ...upstream proxy_servs {server 10.45.156.170:80;server 10.45.156.171:80;server 10.45.156.172:80;}server {location ~* \.(do|jsp|jspx)?$ {proxy_pass http://proxy_servs;}## ...} }注意: 對于proxy_pass/server指令后的URL中是否包含URI, Nginx有不同的處理方式:
1. 如果URL中不包含URI, 則Nginx不會改變原地址的URI;
2. 如果URL中包含了URI, 則Nginx會使用新的URI 代替 原來的URI.
- 其他反向代理指令
| proxy_pass_request_headers on | off; | Indicates whether the header fields of the original request are passed to the proxied server. |
| proxy_pass_request_body on | off; | Indicates whether the original request body is passed to the proxied server. |
| proxy_set_header field value; | Allows redefining or appending fields to the request header passed to the proxied server. |
| proxy_set_body value; | Allows redefining the request body passed to the proxied server. |
| proxy_hide_header field; | The proxy_hide_header directive sets additional fields that will not be passed. |
| proxy_pass_header field; | Permits passing “Date”, “Server”, “X-Pad” and “X-Accel-…” header fields from a proxied server to a client. |
| proxy_bind address [transparent] | off; | Makes outgoing connections to a proxied server originate from the specified local IP address. |
| proxy_connect_timeout time; | Defines a timeout for establishing a connection with a proxied server. |
| proxy_read_timeout time; | Defines a timeout for reading a response from the proxied server. |
| proxy_send_timeout time; | Sets a timeout for transmitting a request to the proxied server. |
| proxy_http_version 1.0 | 1.1; | Sets the HTTP protocol version for proxying. By default, version 1.0 is used. |
| proxy_method method; | Specifies the HTTP method to use in requests forwarded to the proxied server instead of the method from the client request. |
| proxy_ignore_client_abort on | off; | Determines whether the connection with a proxied server should be closed when a client closes the connection without waiting for a response. |
| proxy_ignore_headers field ...; | Disables processing of certain response header fields from the proxied server. |
| proxy_redirect default | off | redirect replacement; | Sets the text that should be changed in the “Location” and “Refresh” header fields of a proxied server response. |
| proxy_intercept_errors on | off; | Determines whether proxied responses with codes greater than or equal to 300 should be passed to a client or be redirected to nginx for processing with the error_page directive. |
| proxy_headers_hash_max_size size; | Sets the maximum size of hash tables used by the proxy_hide_header and proxy_set_header directives. |
| proxy_headers_hash_bucket_size size; | Sets the bucket size for hash tables used by the proxy_hide_header and proxy_set_header directives. |
| proxy_next_upstream [flag]; | Specifies in which cases a request should be passed to the next server, detail |
| proxy_ssl_session_reuse on | off; | Determines whether SSL sessions can be reused when working with the proxied server. |
Proxy-Buffer
Proxy Buffer啟用后,Nginx會將被代理的服務(wù)器的響應(yīng)數(shù)據(jù)異步地傳遞給客戶端:
Nginx首先盡可能地從后端服務(wù)器那里接收響應(yīng)數(shù)據(jù)放在*Buffer*中,如果在接收過程中發(fā)現(xiàn)*Buffer*已經(jīng)裝滿,Nginx會將部分接收到的數(shù)據(jù)臨時存放到磁盤的臨時文件中.當(dāng)一次響應(yīng)數(shù)據(jù)被萬千接收或*Buffer*已經(jīng)裝滿時,Nginx開始向客戶端傳輸數(shù)據(jù).此時Nginx處于`BUSY`狀態(tài).而當(dāng)Proxy Buffer關(guān)閉時, Nginx只要接收到響應(yīng)數(shù)據(jù)就會同步地傳遞給客戶端,不會讀取完整響應(yīng)數(shù)據(jù).
| proxy_buffering on | off; | Enables or disables buffering of responses from the proxied server. |
| proxy_buffers number size; | Sets the number and size of the buffers used for reading a response from the proxied server, for a single connection. |
| proxy_buffer_size size; | Sets the size of the buffer used for reading the first part of the response received from the proxied server. |
| proxy_busy_buffers_size size; | When buffering of responses from the proxied server is enabled, limits the total size of buffers that can be busy sending a response to the client while the response is not yet fully read. |
| proxy_temp_path path [level1 [level2 [level3]]]; | Defines a directory for storing temporary files with data received from proxied servers. |
| proxy_temp_file_write_size size; | Limits the size of data written to a temporary file at a time, when buffering of responses from the proxied server to temporary files is enabled. |
| proxy_max_temp_file_size size; | This directive sets the maximum size of the temporary file. |
注意: Proxy Buffer配置是針對每一個請求起作用,而不是全局概念,即每個請求都會按照這些指令來配置各自的Buffer, Nginx不會生成一個公共的Proxy Buffer供代理請求使用.
負(fù)載均衡
Nginx反向代理的一個重要用途就是負(fù)載均衡:
負(fù)載均衡的原理是利用一定的分配策略將網(wǎng)絡(luò)負(fù)載平衡地分?jǐn)偟骄W(wǎng)絡(luò)集群的各個節(jié)點, 使得單個重負(fù)載任務(wù)能夠分擔(dān)到多個單元上并行處理,或使得大量的并發(fā)訪問數(shù)據(jù)流量分?jǐn)偟蕉鄠€節(jié)點上分別處理,從而減少用戶的等待響應(yīng)時間.在實際應(yīng)用中, 負(fù)載均衡會根據(jù)網(wǎng)絡(luò)的不同層次(一般按照ISO/OSI七層參考模型)進(jìn)行劃分. 現(xiàn)代負(fù)載均衡技術(shù)主要實現(xiàn)和作用于第四層/第七層,完全獨立于網(wǎng)絡(luò)基礎(chǔ)硬件設(shè)備; Nginx一般被認(rèn)為是第七層負(fù)載均衡.
負(fù)載均衡算法多種多樣: 靜態(tài)負(fù)載均衡算法/動態(tài)負(fù)載均衡算法.靜態(tài)負(fù)載均衡算法比較簡單,主要有一般輪詢算法/基于比率的加權(quán)輪詢算法以及基于優(yōu)先級的加權(quán)輪詢算法等.動態(tài)負(fù)載均衡算法在較復(fù)雜的網(wǎng)絡(luò)環(huán)境中適應(yīng)性更強(qiáng),表現(xiàn)更好,主要有基于任務(wù)量的最少連接優(yōu)先算法/基于性能的最快響應(yīng)優(yōu)先算法/預(yù)測算法以及動態(tài)性能分配算法等; Nginx實現(xiàn)采用基于優(yōu)先級的加權(quán)輪詢算法.
Nginx負(fù)載均衡
前在介紹upstream時使用了對所有請求的一般輪詢規(guī)則的負(fù)載均衡, 下面介紹基于優(yōu)先級的加權(quán)輪詢規(guī)則的負(fù)載均衡:
http {## ...upstream proxy_servs {server 10.45.156.170:80 weight=5;server 10.45.156.171:80 weight=2;server 10.45.156.172:80; #默認(rèn)weight=1}server {location ~* \.(do|jsp|jspx)?$ {proxy_pass http://proxy_servs;}## ...} }upstream的服務(wù)器組中每個server被賦予了不同的優(yōu)先級,weight就是輪詢策略的”權(quán)值”, 其中以10.45.156.170:80優(yōu)先級最高.
緩存
響應(yīng)速度是衡量Web應(yīng)用服務(wù)性能優(yōu)劣的重要指標(biāo)之一,在動態(tài)網(wǎng)站中,除了優(yōu)化發(fā)布的內(nèi)容本身之外,另一個重要的方法就是把不需要實時更新的動態(tài)頁面輸出結(jié)果轉(zhuǎn)化成靜態(tài)頁面緩存,進(jìn)而按照靜態(tài)網(wǎng)頁來訪問,提升響應(yīng)速度.
緩存驅(qū)動技術(shù)
在Nginx中, 緩存驅(qū)動技術(shù)有兩種:
404驅(qū)動
原理:
Nginx處理客戶端請求時,一旦發(fā)現(xiàn)請求資源不存在,則會產(chǎn)生404錯誤,Nginx通過捕獲該錯誤,進(jìn)一步轉(zhuǎn)向后端服務(wù)器請求數(shù)據(jù),最后將后端服務(wù)器響應(yīng)數(shù)據(jù)傳回給客戶端,同時在本地進(jìn)行緩存.
配置:
proxy_store指令是由Nginx-Proxy Store模塊提供的簡單緩存機(jī)制,詳見下文介紹.
資源不存在驅(qū)動
原理:
與404驅(qū)動大同小異, 該方法時通過location塊中的if條件判斷直接判斷請求資源是否存在, 不存在則直接驅(qū)動Nginx與后端服務(wù)器通信更新Web緩存.
配置:
!-f判斷請求資源是否存,如不存在就proxy_pass給后端服務(wù)器生成數(shù)據(jù)傳給客戶端,同時Proxy Store緩存.
Nginx緩存
Nginx自身實現(xiàn)了兩種緩存機(jī)制, Proxy Cache/Proxy Store:
Proxy Cache
Proxy Cache是Nginx自身實現(xiàn)的一個功能完整,性能不錯的緩存機(jī)制.Nginx服務(wù)啟動后, 會生成專門的進(jìn)程對磁盤上的緩存文件進(jìn)行掃描, 在內(nèi)存中建立緩存索引, 提高訪問效率, 并且還會生成專門的管理進(jìn)程對磁盤上的緩存文件進(jìn)行過期判定/更新等方面的管理. Proxy Cache緩存支持任意連接響應(yīng)數(shù)據(jù)的緩存, 不僅限于200狀態(tài)的數(shù)據(jù).
與前面介紹過的Proxy Buffer不同:Proxy Buffer實現(xiàn)了后端服務(wù)器響應(yīng)數(shù)據(jù)的異步傳輸, 而Proxy Cahce則實現(xiàn)了Nginx對客戶端數(shù)據(jù)請求的快速響應(yīng). Nginx在接收到后端服務(wù)器響應(yīng)數(shù)據(jù)后, 一方面通過Proxy Buffer機(jī)制將數(shù)據(jù)傳遞給客戶端, 另一方面根據(jù)Proxy Cahce的配置將這些數(shù)據(jù)緩存到本地, 當(dāng)客戶端下次訪問相同數(shù)據(jù)時, Nginx直接從本地檢索數(shù)據(jù)返回給客戶端, 從而減少與后端服務(wù)器的交互時間.
| proxy_cache zone | off; | Defines a shared memory zone used for caching. |
| proxy_cache_bypass string ...; | Defines conditions under which the response will not be taken from a cache. |
| proxy_cache_key string; | Defines a key for caching. |
| proxy_cache_lock on | off; | When enabled, only one request at a time will be allowed to populate a new cache element identified according to the proxy_cache_key directive by passing a request to a proxied server. |
| proxy_cache_lock_timeout time; | Sets a timeout for proxy_cache_lock. |
| proxy_cache_min_uses number; | Sets the number of requests after which the response will be cached. |
| proxy_cache_use_stale [stale] | Determines in which cases a stale cached response can be used when an error occurs during communication with the proxied server. The directive’s parameters match the parameters of the proxy_next_upstream directive. |
| proxy_cache_valid [code ...] time; | Sets caching time for different response codes. |
| proxy_cache_path path keys_zone=name:size; | Sets the path and other parameters of a cache |
| proxy_no_cache string ...; | Defines conditions under which the response will not be saved to a cache. |
注: Proxy Cache依賴于Proxy Buffer.且Proxy Cache沒有實現(xiàn)自動清理磁盤上緩存數(shù)據(jù)的能力, 因此在長時間使用過程中會對服務(wù)器存儲造成一定的壓力.
Proxy Store
Nginx還支持另一種將后端服務(wù)器數(shù)據(jù)緩存到本地的方法Proxy Store, 與Proxy Cache的區(qū)別是, 它對來自后端服務(wù)器的響應(yīng)數(shù)據(jù), 尤其是靜態(tài)數(shù)據(jù)只進(jìn)行簡單的緩存, 且只能緩存200狀態(tài)碼下的響應(yīng)數(shù)據(jù), 不支持緩存過期更新, 內(nèi)存索引建立等功能, 但支持設(shè)置用戶/用戶組對緩存的訪問權(quán)限.
| proxy_store on | off | string; | Enables saving of files to a disk. |
| proxy_store_access users:permissions ...; | Sets access permissions for newly created files and directories. |
Memcached緩存
Memcached是一套高性能的基于分布式環(huán)境的緩存系統(tǒng),用于動態(tài)Web應(yīng)用可減輕后臺數(shù)據(jù)服務(wù)器的負(fù)載, 提高客戶端響應(yīng)速度.Nginx的標(biāo)準(zhǔn)模塊ngx_http_memcached_module提供了對Memcached的支持.
| memcached_pass address; | Sets the memcached server address. |
| memcached_connect_timeout time; | Defines a timeout for establishing a connection with a memcached server. |
| memcached_read_timeout time; | Defines a timeout for reading a response from the memcached server. |
| memcached_send_timeout time; | Sets a timeout for transmitting a request to the memcached server. |
| memcached_buffer_size size; | Sets the size of the buffer used for reading the response received from the memcached server. |
| memcached_next_upstream status ... | Specifies in which cases a request should be passed to the next server. |
在配置Nginx使用Memcached時,還需要對Nginx配置的全局變量$memcached_key進(jìn)行設(shè)置.
示例
Nginx首先請求Memcached, 如果緩存沒有命中(key為"$uri?$args"), Nginx則proxy_pass給后端服務(wù)器響應(yīng)該請求, 但此時也需要后端服務(wù)器配合, 在將數(shù)據(jù)響應(yīng)給客戶端之后, 需要將響應(yīng)內(nèi)容手動寫入Memcached, 以供下次直接從Memcached檢索數(shù)據(jù).
- nginx.conf
- Java: MemcachedFilter
分布式Memcached
為了充分發(fā)揮Memcached分布式優(yōu)勢,提升服務(wù)器響應(yīng)速度,我們使用Nginx的一致性Hash模塊, 將request分布到不同的Memcached Server中, 同時, 對于訪問不命中的情況, 也需要后端服務(wù)器的支持, 后端服務(wù)器在對客戶端做出響應(yīng)的同時, 需要將響應(yīng)數(shù)據(jù)按照一致性Hash規(guī)則, 將響應(yīng)數(shù)據(jù)寫入Memcached.
安裝Nginx一致性Hash模塊
- git clone https://github.com/replay/ngx_http_consistent_hash.git
- ./configure --add-module=/root/src/ngx_http_consistent_hash/
- make && make install
Nginx官方還提供了其他一致性Hash算法的實現(xiàn), 詳細(xì)可參考https://www.nginx.com/resources/wiki/modules/
配置Memcached一致性Hash規(guī)則
- upstream memcached_servs {consistent_hash "$uri?$args";server 127.0.0.1:11211;server 127.0.0.1:11212;server 127.0.0.1:11213;}server {location / {set $memcached_key "$uri?$args";memcached_pass memcached_servs;error_page 404 =200 @send_to_backend;index index.html index.htm;}}
- Java: MemcachedFilter
總結(jié)
以上是生活随笔為你收集整理的Nginx - 代理、缓存的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: VC6工程目录下的文件说明
- 下一篇: Nginx 负载均衡器(1+2)