Nginx-1.18 + Https(免費版) + openresty-1.17.8.2 + LVS+keepalived實戰(Centos7.8)
一.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網站用戶有:百度、京東、新浪、網易、騰訊、淘寶等,

二.Centos7.x 下 nginx的骨架搭建
1.nginx下載
點擊進入nginx首頁
選擇Stable version下的版本(穩定版本)
2.nginx服務器部署
安裝相關依賴:
yum -y install gcc zlib zlib-devel pcre-devel openssl openssl-devel
匯入安裝包進行解壓
tar -zxvf xxx
在nginx根目錄進行編譯:
./configure
make
make install
默認安裝路徑:
cd /usr/local/nginx
nginx基本操作:
cd /usr/local/nginx/sbin
./nginx #默認組態檔啟動
?
./nginx -s reload #重啟,加載默認組態檔
./nginx -s stop #停止
?
./nginx -c /usr/local/nginx/conf/nginx.conf #啟動指定某個組態檔
?
?
關閉行程,nginx有master process 和worker process,關閉master即可
ps -ef | grep “nginx”
kill -9 PID `
查看nginx行程
ps -ef | grep "nginx"
3.nginx組態檔
打開組態檔
cd /usr/local/nginx/conf
vim nginx.conf
# 每個配置項由配置指令和指令引數 2 個部分構成
#user root; # 指定Nginx Worker行程運行以及用戶組
worker_processes 1; # 一般和cpu核數一致
?
#error_log logs/error.log; # 錯誤日志的存放路徑 和錯誤日志
#error_log logs/error.log notice;
#error_log logs/error.log info;
?
#pid logs/nginx.pid; # 行程PID存放路徑
?
?
# 事件模塊指令,用來指定Nginx的IO模型,Nginx支持的有select、poll、kqueue、epoll 等,不同的是epoll用在Linux平臺上,而kqueue用在BSD系統中,對于Linux系統,epoll作業模式是首選
events {
use epoll;
# 定義Nginx每個行程的最大連接數, 作為服務器來說: worker_connections * worker_processes,
# 作為反向代理來說,最大并發數量應該是worker_connections * worker_processes/2,因為反向代理服務器,每個 并發會建立與客戶端的連接和與后端服務的連接,會占用兩個連接
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;
?
# 是否開啟高效傳輸模式 on開啟 off關閉
sendfile on;
#減少網路報文段的數量
#tcp_nopush on;
?
#keepalive_timeout 0;
# 客戶端連接保持活動的超時時間,超過這個時間之后,服務器會關閉該連接
keepalive_timeout 65;
? #壓縮,可節省帶寬
#gzip on;
# 虛擬主機的配置
server {
listen 80; # 虛擬主機的服務埠
server_name localhost; #用來指定IP地址或域名,多個域名之間用空格分開
?
#charset koi8-r;
?
#access_log logs/host.access.log main;
?
#URL地址匹配
location / {
root html; # 服務默認啟動目錄
index index.html index.htm; #默認訪問檔案,按照順序找
}
?
#error_page 404 /404.html; #錯誤狀態碼的顯示頁面
?
# redirect server error pages to the static page /50x.html
#
error_page 500 502 503 504 /50x.html;
location = /50x.html {
root html;
}
?
# proxy the PHP scripts to Apache listening on 127.0.0.1:80
#
#location ~ \.php$ {
# proxy_pass http://127.0.0.1;
#}
?
# pass the PHP scripts to FastCGI server listening on 127.0.0.1:9000
#
#location ~ \.php$ {
# root html;
# fastcgi_pass 127.0.0.1:9000;
# fastcgi_index index.php;
# fastcgi_param SCRIPT_FILENAME /scripts$fastcgi_script_name;
# include fastcgi_params;
#}
?
# deny access to .htaccess files, if Apache's document root
# concurs with nginx's one
#
#location ~ /\.ht {
# deny all;
#}
}
?
?
# another virtual host using mix of IP-, name-, and port-based configuration
#
#server {
# listen 8000;
# listen somename:8080;
# server_name somename alias another.alias;
?
# location / {
# root html;
# index index.html index.htm;
# }
#}
?
?
# HTTPS server
#
#server {
# listen 443 ssl;
# server_name localhost;
?
# ssl_certificate cert.pem;
# ssl_certificate_key cert.key;
?
# ssl_session_cache shared:SSL:1m;
# ssl_session_timeout 5m;
?
# ssl_ciphers HIGH:!aNULL:!MD5;
# ssl_prefer_server_ciphers on;
?
# location / {
# root html;
# index index.html index.htm;
# }
#}
}
三.實戰
1.檔案服務器實戰
server {
listen 80; # 虛擬主機的服務埠
server_name localhost; #用來指定IP地址或域名,多個域名之間用空格分開
?
#charset koi8-r;
?
#access_log logs/host.access.log main;
?
#URL地址匹配
location /app/img {
alias /usr/local/software/img/; #圖片存盤的路徑
}
?
#error_page 404 /404.html; #錯誤狀態碼的顯示頁面
?
# redirect server error pages to the static page /50x.html
#
error_page 500 502 503 504 /50x.html;
location = /50x.html {
root html;
}
?
# proxy the PHP scripts to Apache listening on 127.0.0.1:80
#
#location ~ \.php$ {
# proxy_pass http://127.0.0.1;
#}
?
# pass the PHP scripts to FastCGI server listening on 127.0.0.1:9000
#
#location ~ \.php$ {
# root html;
# fastcgi_pass 127.0.0.1:9000;
# fastcgi_index index.php;
# fastcgi_param SCRIPT_FILENAME /scripts$fastcgi_script_name;
# include fastcgi_params;
#}
?
# deny access to .htaccess files, if Apache's document root
# concurs with nginx's one
#
#location ~ /\.ht {
# deny all;
#}
}
2.accessLog日志挖掘實戰
- 組態檔:
log_format main '$remote_addr - $remote_user [$time_local] "$request" '
'$status $body_bytes_sent "$http_referer" '
'"$http_user_agent" "$http_x_forwarded_for" $upstream_cache_status $request_time';
?
?
server {
listen 80;
server_name aabbcc.com;
?
location / {
root /usr/local/nginx/html;
index xxx.html;
}
#charset koi8-r;
#啟用虛擬主機下的access_log和存盤路徑
access_log logs/host.access.log main;
}
- 日志:
122.70.148.18 - - [04/Aug/2020:14:46:48 +0800] "GET /user/api/v1/product/order/query_state?product_id=1&token=xeyJhbGciOJE HTTP/1.1" 200 48 "https://x.net/" "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/84.0.4147.89 Safari/537.36"
- 決議:
$remote_addr 對應的是真實日志里的122.70.148.18,即客戶端的IP,
?
$remote_user 對應的是第二個中杠“-”,沒有遠程用戶,所以用“-”填充,
?
[$time_local]對應的是[04/Aug/2020:14:46:48 +0800],
?
“$request”對應的是"GET /user/api/v1/product/order/query_state?product_id=1&token=xeyJhbGciOJE HTTP/1.1",
?
$status對應的是200狀態碼,200表示正常訪問,
?
$body_bytes_sent對應的是48位元組,即回應body的大小,
?
“$http_referer” 對應的是”https://x.net/“,若是直接打開域名瀏覽的時,referer就會沒有值,為”-“,
?
“$http_user_agent” 對應的是”Mozilla/5.0 (Macintosh; Intel Mac OS X 10.12; rv:56.0) Gecko/20100101 Firefox/56.0”,如果為空可能是爬出
?
“$http_x_forwarded_for” 對應的是”-“或者空,
$upstream_response_time:指從Nginx向后端建立連接開始到接受完資料然后關閉連接為止的時間
?
$request_time一般會比upstream_response_time大,因為用戶網路較差,或者傳遞資料較大時,前者會耗時大很多
- 日常使用
查看訪問最頻繁的前100個IP
awk '{print $1}' access_temp.log | sort -n |uniq -c | sort -rn | head -n 100
統計訪問最多的url 前20名
cat access_temp.log |awk '{print $7}'| sort|uniq -c| sort -rn| head -20 | more
統計耗時介面, 列出傳輸時間超過 2 秒的介面,顯示前5條
cat xxx.log|awk '($NF > 2){print $7}'|sort -n|uniq -c|sort -nr|head -5
?
備注:$NF 表示最后一列, awk '{print $NF}'
- 基礎
awk 是文本處理工具,默認按照空格切分,$N 是第切割后第N個,從1開始
?
sort命令用于將文本檔案內容加以排序,-n 按照數值排,-r 按照倒序來排
案例的sort -n 是按照第一列的數值大小進行排序,從小到大,倒序就是 sort -rn
?
uniq 去除重復出現的行列, -c 在每列旁邊顯示該行重復出現的次數,
?
3.負載均衡實戰
- 配置案例: 輪詢策略(適合靜態檔案服務器)
upstream lbs {
server 192.168.0.106:8080;
server 192.168.0.106:8081;
}
?server {
listen 80;
server_name localhost;
?
location /api/ {
proxy_pass http://lbs;
proxy_redirect default;
}
}
- 配置案例: 權重策略
upstream lbs {
server 192.168.0.106:8080 weight=5;
server 192.168.0.106:8081 weight=10;
}
?server {
listen 80;
server_name localhost;
?
location /api/ {
proxy_pass http://lbs;
proxy_redirect default;
}
}
- 配置案例: ip hash(使用場景:websocket)
upstream lbs {
ip_hash
server 192.168.0.106:8080;
server 192.168.0.106:8081;
}
?server {
listen 80;
server_name localhost;
?
location /api/ {
proxy_pass http://lbs;
proxy_redirect default;
}
}
- 配置案例: 其它
upstream lbs {
server 192.168.0.106:8080 down;
server 192.168.0.106:8081;
server 192.168.0.106:8082 backup;
#允許nginx與后端節點嘗試失敗的次數,和60s后再重新嘗試,可以通過指令proxy_next_upstream來配置什么是失敗的嘗試,proxy_next_upstream來配置,
server 192.168.0.106:8084 max_fails=2 fail_timeout=60s;
}
?server {
listen 80;
server_name localhost;
?
location /api/ {
proxy_pass http://lbs;
#proxy_next_upstream來配置
proxy_next_upstream error timeout http_500 http_503 http_404
}
}
4.全域例外兜底資料回傳實戰
upstream lbs {
server 192.168.0.106:8080 down;
server 192.168.0.106:8081;
server 192.168.0.106:8082 backup;
#允許nginx與后端節點嘗試失敗的次數,和60s后再重新嘗試,可以通過指令proxy_next_upstream來配置什么是失敗的嘗試,proxy_next_upstream來配置,
server 192.168.0.106:8084 max_fails=2 fail_timeout=60s;
}
location / {
proxy_pass http://lbs;
proxy_redirect default;
proxy_next_upstream error timeout http_503 non_idempotent;
?
#開啟錯誤攔截配置,一定要開啟
proxy_intercept_errors on;
}
?
# 不加 =200,則回傳的就是原先的http錯誤碼;配上后如果出現500等錯誤都回傳給用戶200狀態,并跳轉至/default_api
error_page 404 500 502 503 504 =200 /default_api;
location = /default_api {
default_type application/json;
return 200 '{"code":"-1","msg":"invoke fail, not found "}';
5.后端服務獲取用戶真是ip實戰
upstream lbs {
server 192.168.0.106:8080 down;
server 192.168.0.106:8081;
server 192.168.0.106:8082 backup;
#允許nginx與后端節點嘗試失敗的次數,和60s后再重新嘗試,可以通過指令proxy_next_upstream來配置什么是失敗的嘗試,proxy_next_upstream來配置,
server 192.168.0.106:8084 max_fails=2 fail_timeout=60s;
}
location / {
proxy_pass http://lbs;
proxy_redirect default;
# 存放用戶的真實ip
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
}
6.ip封禁實戰
在conf目錄下創建一個檔案
touch blacklist.conf
修改檔案內容
vim blacklist.conf
deny 192.168.11.1;
deny 192.168.11.2;
deny 192.168.11.3;
配置主組態檔
vim nginx.conf
單獨網站屏蔽IP的方法,把include xxx; 放到網址對應的在server{}陳述句塊,虛擬主機
所有網站屏蔽IP的方法,把include xxx; 放到http {}陳述句塊,
?
nginx配置如下:
?
http{
# ....
include blacklist.conf;
}
?
location / {
proxy_pass http://lbs;
proxy_redirect default;
}
?
拓展-自動化封禁思路
撰寫shell腳本
AWK統計access.log,記錄每秒訪問超過60次的ip,然后配合nginx或者iptables進行封禁
crontab定時跑腳本
7.瀏覽器跨域配置實戰
只針對后端的介面服務
location / {
add_header 'Access-Control-Allow-Origin' $http_origin;
add_header 'Access-Control-Allow-Credentials' 'true';
#如果有不同需要自行添加
add_header 'Access-Control-Allow-Headers' 'DNT,web-token,token,app-token,Authorization,Accept,Origin,Keep-Alive,User-Agent,X-Mx-ReqToken,X-Data-Type,X-Auth-Token,X-Requested-With,If-Modified-Since,Cache-Control,Content-Type,Range';
#如果有不同需要自行添加
add_header Access-Control-Allow-Methods 'GET,POST,OPTIONS';
?
#如果預檢請求則回傳成功,不需要轉發到后端
if ($request_method = 'OPTIONS') {
add_header 'Access-Control-Max-Age' 1728000;
add_header 'Content-Type' 'text/plain; charset=utf-8';
add_header 'Content-Length' 0;
return 200;
}
}
8.websocket實戰
server {
listen 80;
server_name abc.net;
location / {
proxy_pass http://lbs;
proxy_read_timeout 300s; //websocket空閑保持時長
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_http_version 1.1;
#核心是下面的配置 其他和普通反向代理沒區別, 表示請求服務器升級協議為WebSocket
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection $connection_upgrade;
}
}
服務器處理完請求后,回應如下報文# 狀態碼為101
HTTP/1.1 101 Switching Protocols
Upgrade: websocket
Connection: upgrade
9.快取前置實戰
upstream lbs {
server 192.168.0.106:8080;
server 192.168.0.106:8081;
}
#全域快取配置,優先級最高,默認快取get、head請求,在沒人訪問的情況下60m洗掉快取(非活躍狀態下)
proxy_cache_path /root/cache levels=1:2 keys_zone=xd_cache:10m max_size=1g inactive=5s use_temp_path=off;
?server {
listen 80;
server_name localhost;
?
location /api/ {
proxy_pass http://lbs;
proxy_cache xd_cache;
#只要到時間就會洗掉(活躍狀態的)
proxy_cache_valid 200 304 1m;
proxy_cache_valid 404 1m;
proxy_cache_key $host$uri$is_args$args;
add_header Nginx-Cache "$upstream_cache_status";
}
}
10.檔案壓縮實戰(節省帶寬)
#開啟gzip,減少我們發送的資料量
gzip on;
gzip_min_length 1k;
?
#4個單位為16k的記憶體作為壓縮結果流快取
gzip_buffers 4 16k;
?
#gzip壓縮比,可在1~9中設定,1壓縮比最小,速度最快,9壓縮比最大,速度最慢,消耗CPU
gzip_comp_level 4;
?
#壓縮的型別
gzip_types application/javascript text/plain text/css application/json application/xml text/javascript;
?
#給代理服務器用的,有的瀏覽器支持壓縮,有的不支持,所以避免浪費不支持的也壓縮,所以根據客戶端的HTTP頭來判斷,是否需要壓縮
gzip_vary on;
?
#禁用IE6以下的gzip壓縮,IE某些版本對gzip的壓縮支持很不好
gzip_disable "MSIE [1-6].";
?server {
listen 80;
server_name localhost;
?
#靜態資源存盤路徑
location /static {
alias /usr/local/software/static
}
}
四.規則應用(可略過)
1.location
正則
^ 以什么開始
$ 以什么結束
?
^/api/user$
location 路徑匹配
語法 location [ = | ~ | ~* | ^~ ] uri { … }
location = /uri
= 表示精準匹配,只要完全匹配上才能生效
location /uri
不帶任何修飾符,表示前綴匹配
location ^~ /uri/
匹配任何已 /uri/ 開頭的任何查詢并且停止搜索
location /
通用匹配,任何未匹配到其他location的請求都會匹配到
正則匹配
區分大小寫匹配(~)
不區分大小寫匹配(~*)
優先級(不要寫復雜,容易出問題和遺忘)
精準匹配 > 字串匹配(若有多個匹配項匹配成功,那么選擇匹配長的并記錄) > 正則匹配
案例
server {
?
server_name abc.net;
?
location ~^/api/pub$ {
...
}
?
}
?
^/api/pub$這個正則運算式表示字串必須以/開始,以b $結束,中間必須是/api/pub
?
http://abc.net/api/v1 匹配(完全匹配)
?
http://abc.net/API/PUB 不匹配,大小寫敏感
?
http://abc.net/api/pub?key1=value1 匹配
?
http://abc.net/api/pub/ 不匹配
?
http://abc.net/api/public 不匹配,不能匹配正則運算式
測驗
location = /img/test.png {
return 1;
}
?
location /img/test.png {
return 2;
}
?
location ^~/img/ {
return 3;
}
?
location = / {
return 4;
}
?
location / {
return 5;
}
2.rewrite重定向
在location中添加
語法 rewrite regex replacement[flag]
rewrite ^/(.*) http://xxx.net/$1 permanent
#這是一個正則運算式,匹配完整的域名和后面的路徑地址
#replacement部分是https://xxx.net/$1,$1是取自regex部分()里的內容
| 標記符號 | 說明 |
|---|---|
| last | 本條規則匹配完成后繼續向下匹配新的location URI規則 |
| break | 本條規則匹配完成后終止,不在匹配任何規則 |
| redirect | 回傳302臨時重定向 |
| permanent | 回傳301永久重定向 |
五.nginx整合https
可以通過阿里云進行SSL免費證書申請并下載
證書名稱如下:
5022224_custompang.net.key
5022224_custompang.net.pem
將證書放入/usr/local/software/biz/key/中
先洗掉原生的nginx
cd /usr/local
rm -rf nginx
進入nginx根目錄執行
./configure --prefix=/usr/local/nginx --with-http_stub_status_module --with-http_ssl_module
?
make
?
make install
進入安裝后的nginx配置目錄
cd /usr/local/nginx/conf
打開nginx.conf找到如下內容
server {
listen 443 ssl;
server_name custompang.net;
?#匯入證書
ssl_certificate /usr/local/software/biz/key/5022224_custompang.net.pem;
ssl_certificate_key /usr/local/software/biz/key/5022224_custompang.net.key;
?
ssl_session_cache shared:SSL:1m;
ssl_session_timeout 5m;
?
ssl_ciphers HIGH:!aNULL:!MD5;
ssl_prefer_server_ciphers on;
?
location / {
root html;
index index.html index.htm;
}
}
?
六.nginx整合OpenResty
1.介紹
由章亦春發起,是基于Ngnix和Lua的高性能web平臺,內部集成精良的LUa庫、第三方模塊、依賴, 開發者可以方便搭建能夠處理高并發、擴展性極高的動態web應用、web服務、動態網關,
?
OpenResty將Nginx核心、LuaJIT、許多有用的Lua庫和Nginx第三方模塊打包在一起
?
Nginx是C語言開發,如果要二次擴展是很麻煩的,而基于OpenResty,開發人員可以使用 Lua 編程語言對 Nginx 核心模塊進行二次開發拓展
?
性能強大,OpenResty可以快速構造出1萬以上并發連接回應的超高性能Web應用系統
官網:http://openresty.org
阿里、騰訊、新浪、酷狗音樂等都是 OpenResty 的深度用戶
2.OpenResty安裝
網站:http://openresty.org/en/linux-packages.html#centos
yum install wget
wget https://openresty.org/package/centos/openresty.repo
sudo mv openresty.repo /etc/yum.repos.d/
sudo yum check-update
sudo yum install openresty
安裝命令列工具
sudo yum install openresty-resty
列出所有 openresty 倉庫里的軟體包
sudo yum --disablerepo="*" --enablerepo="openresty" list available
查看版本
resty -V
默認安裝路徑
/usr/local/openresty
3.OpenResty實戰
(1)helloworld開發實戰
編輯:vim /usr/local/openresty/nginx/conf/nginx.conf
使用代碼塊形式:
http{
# 虛擬機主機塊
server{
# 監聽埠
listen 80;
# 配置請求的路由
location /{
default_type text/html;
content_by_lua_block{
ngx.say("hello world; 123");
}
}
}
}
訪問 curl 127.0.0.1
如果瀏覽器訪問會出現檔案下載,因為沒有Html頭資訊
使用檔案掃描方式:
#使用其他方式
http{
# 虛擬機主機塊,還需要配置lua檔案掃描路徑
lua_package_path "$prefix/lualib/?.lua;;";
lua_package_cpath "$prefix/lualib/?.so;;";
server{
# 監聽埠
listen 80;
# 配置請求的路由
location /{
default_type text/html;
content_by_lua_file lua/123.lua;
}
}
}
(2)內網訪問限制實戰(配置白名單)
組態檔:
http{
?
upstream lbs {
server 192.168.159.138:8080
}
# 這里設定為 off,是為了避免每次修改之后都要重新 reload 的麻煩,
# 在生產環境上需要 lua_code_cache 設定成 on,
lua_code_cache off;
?
# lua_package_path可以配置openresty的檔案尋址路徑,$PREFIX 為openresty安裝路徑
# 檔案名使用“?”作為通配符,多個路徑使用“;”分隔,默認的查找路徑用“;;”
# 設定純 Lua 擴展庫的搜尋路徑
lua_package_path "$prefix/lualib/?.lua;;";
?
# 設定 C 撰寫的 Lua 擴展模塊的搜尋路徑(也可以用 ';;')
lua_package_cpath "$prefix/lualib/?.so;;";
?
server {
location / {
access_by_lua_file lua/white_ip_list.lua;
proxy_pass http://lbs;
}
}
lua腳本撰寫
cd /usr/local/openresty/nginx/
mkdir lua
cd lua
touch white_ip_list.lua
#定義一個變數
local white_ips = {["127.0.0.1","192.168.1.1"]=true}
?
local ip = ngx.var.remote_addr
if true ~= white_ips[ip] then
ngx.exit(ngx.HTTP_FORBIDDEN)
return;
end
(3)下載限速實戰
組態檔:
http{
?
# 這里設定為 off,是為了避免每次修改之后都要重新 reload 的麻煩,
# 在生產環境上需要 lua_code_cache 設定成 on,
lua_code_cache off;
?
# lua_package_path可以配置openresty的檔案尋址路徑,$PREFIX 為openresty安裝路徑
# 檔案名使用“?”作為通配符,多個路徑使用“;”分隔,默認的查找路徑用“;;”
# 設定純 Lua 擴展庫的搜尋路徑
lua_package_path "$prefix/lualib/?.lua;;";
?
# 設定 C 撰寫的 Lua 擴展模塊的搜尋路徑(也可以用 ';;')
lua_package_cpath "$prefix/lualib/?.so;;";
?
server {
location /download {
access_by_lua_block {
#當前請求的回應上限是 每秒 300K 位元組
ngx.var.limit_rate = "300K"
}
alias /usr/local/software/app;
}
七.nginx實作高可用
1.介紹
-
官網 www.linuxvirtualserver.org
-
LVS是Linux Virtual Server,Linux虛擬服務器,是一個虛擬的服務器集群系統
?專案是由章文嵩博士成立,是中國國內最早出現的自由軟體專案之一
?Linux2.4 內核以后,LVS 已經是 Linux 標準內核的一部分
提供了10多種調度演算法: 輪詢、加權輪詢、最小連接、目標地址散列、源地址散列等 -
三種負載均衡轉發技術
-
NAT:資料進出都通過 LVS, 前端的Master既要處理客戶端發起的請求,又要處理后臺RealServer的回應資訊,將RealServer回應的資訊再轉發給客戶端, 容易成為整個集群系統性能的瓶頸; (支持任意系統且可以實作埠映射)
-
DR: 移花接木,最高效的負載均衡規則,前端的Master只處理客戶端的請求,將請求轉發給RealServer,由后臺的RealServer直接回應客戶端,不再經過Master, 性能要優于LVS-NAT; 需要LVS和RS集群系結同一個VIP(支持多數系統,不可以實作埠映射)
-
TUNL:隧道技術,前端的Master只處理客戶端的請求,將請求轉發給RealServer,然后由后臺的RealServer直接回應客戶端,不再經過Master;(支持少數系統,不可以實作埠映射))

-
keepalived是一個類似于交換機制的軟體,核心作用是檢測服務器的狀態,如果有一臺web服務器作業出現故障,Keepalived將檢測到并將有故障的服務器從系統中剔除,使用其他服務器代替該服務器的作業,當服務器作業正常后Keepalived自動將服務器加入到服務器群中,這些作業全部自動完成,
后來加入了vrrp(虛擬路由器冗余協議),除了為lvs提供高可用還可以為其他服務器比如Mysql、Haproxy等軟體提供高可用方案
2.lvs+keepalived實戰
- 系統環境:centos7.8
Linux frank20210105 3.10.0-1127.19.1.el7.x86_64 #1 SMP Tue Aug 25 17:23:54 UTC 2020 x86_64 x86_64 x86_64 GNU/Linux
- 添加相關依賴:
yum install -y gcc
yum install -y openssl-devel
yum install -y libnl libnl-devel
yum install -y libnfnetlink-devel
yum install -y net-tools
yum install -y vim wget
yum install -y keepalived
systemctl stop firewalld
setenforce 0
vi /etc/sysconfig/selinux 修改selinux=disabled
cd /etc/keepalived
service keepalived start
通過ps -ef | grep keepalived 查看是否啟動成功
- 具體配置:
先關閉keepalived進行配置:service keepalived stop
具體組態檔如下:
- Master:
! Configuration File for keepalived
global_defs {
router_id LVS_DEVEL # 設定lvs的id,在一個網路內應該是唯一的
enable_script_security #允許執行外部腳本
}
#配置vrrp_script,主要用于健康檢查及檢查失敗后執行的動作,
vrrp_script chk_real_server {
#健康檢查腳本,當腳本回傳值不為0時認為失敗
script "/usr/local/software/conf/chk_server.sh"
#檢查頻率,以下配置每2秒檢查1次
interval 2
#當檢查失敗后,將vrrp_instance的priority減小5
weight -5
#連續監測失敗3次,才認為真的健康檢查失敗,并調整優先級
fall 3
#連續監測2次成功,就認為成功,但不調整優先級
rise 2
user root
}
#配置對外提供服務的VIP vrrp_instance配置
vrrp_instance VI_1 {
#指定vrrp_instance的狀態,是MASTER還是BACKUP主要還是看優先級,
state MASTER
#指定vrrp_instance系結的網卡,最終通過指定的網卡系結VIP
interface ens33
#相當于VRID,用于在一個網內區分組播,需要組播域內內唯一,
virtual_router_id 51
#本機的優先級,VRID相同的機器中,優先級最高的會被選舉為MASTER
#主備不同,需要修改
priority 100
#心跳間隔檢查,默認為1s,MASTER會每隔1秒發送一個報文告知組內其他機器自己還活著,
advert_int 1
authentication {
auth_type PASS
auth_pass 1111
}
#定義虛擬IP(VIP)為192.168.159.100,可多設,每行一個
virtual_ipaddress {
192.168.159.100
}
#本vrrp_instance所參考的腳本配置,名稱就是vrrp_script 定義的容器名
track_script {
chk_real_server
}
}
# 定義對外提供服務的LVS的VIP以及port
virtual_server 192.168.159.100 80 {
# 設定健康檢查時間,單位是秒
delay_loop 6
# 設定負載調度的演算法為rr
lb_algo rr
# 設定LVS實作負載的機制,有NAT、TUN、DR三個模式
lb_kind NAT
# 會話保持時間
persistence_timeout 50
#指定轉發協議型別(TCP、UDP)
protocol TCP
# 指定real server1的IP地址
#主備不同,需要修改,主備相同,不需要改
real_server 192.168.159.145 80 {
# 配置節點權值,數字越大權重越高
weight 1
# 健康檢查方式
TCP_CHECK { # 健康檢查方式
connect_timeout 10 # 連接超時
retry 3 # 重試次數
delay_before_retry 3 # 重試間隔
connect_port 80 # 檢查時連接的埠
}
}
}
- Backup:
! Configuration File for keepalived
global_defs {
router_id LVS_DEVEL # 設定lvs的id,在一個網路內應該是唯一的
enable_script_security #允許執行外部腳本
}
#配置vrrp_script,主要用于健康檢查及檢查失敗后執行的動作,
vrrp_script chk_real_server {
#健康檢查腳本,當腳本回傳值不為0時認為失敗
script "/usr/local/software/conf/chk_server.sh"
#檢查頻率,以下配置每2秒檢查1次
interval 2
#當檢查失敗后,將vrrp_instance的priority減小5
weight -5
#連續監測失敗3次,才認為真的健康檢查失敗,并調整優先級
fall 3
#連續監測2次成功,就認為成功,但不調整優先級
rise 2
user root
}
#配置對外提供服務的VIP vrrp_instance配置
vrrp_instance VI_1 {
#指定vrrp_instance的狀態,是MASTER還是BACKUP主要還是看優先級,
state BACKUP
#指定vrrp_instance系結的網卡,最終通過指定的網卡系結VIP
interface ens33
#相當于VRID,用于在一個網內區分組播,需要組播域內內唯一,
virtual_router_id 51
#本機的優先級,VRID相同的機器中,優先級最高的會被選舉為MASTER
#主備不同,需要修改
priority 50
#心跳間隔檢查,默認為1s,MASTER會每隔1秒發送一個報文告知組內其他機器自己還活著,
advert_int 1
authentication {
auth_type PASS
auth_pass 1111
}
#定義虛擬IP(VIP)為192.168.159.100,可多設,每行一個
virtual_ipaddress {
192.168.159.100
}
#本vrrp_instance所參考的腳本配置,名稱就是vrrp_script 定義的容器名
track_script {
chk_real_server
}
}
#定義對外提供服務的LVS的VIP以及port
virtual_server 192.168.159.100 80 {
# 設定健康檢查時間,單位是秒
delay_loop 6
# 設定負載調度的演算法為rr
lb_algo rr
# 設定LVS實作負載的機制,有NAT、TUN、DR三個模式
lb_kind NAT
# 會話保持時間
persistence_timeout 50
#指定轉發協議型別(TCP、UDP)
protocol TCP
# 指定real server1的IP地址
#主備不同,需要修改,主備相同,不需要改
real_server 192.168.159.146 80 {
# 配置節點權值,數字越大權重越高
weight 1
# 健康檢查方式
TCP_CHECK { # 健康檢查方式
connect_timeout 10 # 連接超時
retry 3 # 重試次數
delay_before_retry 3 # 重試間隔
connect_port 80 # 檢查時連接的埠
}
}
}
創建chk_server.sh實作:
當nginx服務掛掉時,也將本機的keepalived 關閉掉
vim /usr/local/software/conf/chk_server.sh
#!/bin/bash
#檢查nginx行程是否存在
counter=$(ps -C nginx --no-heading|wc -l)
if [ "${counter}" -eq "0" ]; then
service keepalived stop
echo 'nginx server is died.......'
fi
兩臺設備分別啟動
service keepalived start
查看節點狀態
service keepalived status
啟動成功后通過ip -a 查看虛擬ip,默認掛載到Master主機的網卡
- 配置注意
router_id后面跟的自定義的ID在同一個網路下是一致的
?
state后跟的MASTER和BACKUP必須是大寫;否則會造成配置無法生效的問題
?
interface 網卡ID;要根據自己的實際情況來看,可以使用以下方式查詢 ip a 查詢
?
在BACKUP節點上,其keepalived.conf與Master上基本一致,修改state為BACKUP,priority值改小即可
?
authentication主備之間的認證方式,一般使用PASS即可;主備的配置必須一致,不能超過8位
特別注意: 需要關閉selinux,不然sh腳本可能不生效
getenforce 查看
setenforce 0 關閉 將Enforcing 狀態變為 Permissive
如果實在啟動不成功,那么可以重新下載進行配置:
yum remove keepalived
yum install -y keepalived
組態檔替換為keepalived
- 生產環境問題
VIP : 阿里云(LBS)、華為云、騰訊云、AWS
八.nginx內置變數
提供豐富的內置變數, openresty里面使用參考下面的檔案
https://github.com/openresty/lua-nginx-module#ngxvarvariable
名稱 說明
$arg_name 請求中的name引數
$args 請求中的引數
$content_length HTTP請求資訊里的"Content-Length"
$content_type 請求資訊里的"Content-Type"
$host 請求資訊中的"Host",如果請求中沒有Host行,則等于設定的服務器名
$hostname 機器名使用 gethostname系統呼叫的值
$http_cookie cookie 資訊
$http_referer 參考地址
$http_user_agent 客戶端代理資訊
$http_via 最后一個訪問服務器的Ip地址,
$http_x_forwarded_for 相當于網路訪問路徑
$is_args 如果請求行帶有引數,回傳“?”,否則回傳空字串
$limit_rate 對連接速率的限制
$nginx_version 當前運行的nginx版本號
$pid worker行程的PID
$query_string 與$args相同
$remote_addr 客戶端IP地址
$remote_port 客戶端埠號
$request 用戶請求
$request_method 請求的方法,比如"GET"、"POST"等
$request_uri 請求的URI,帶引數
$scheme 所用的協議,比如http或者是https
$server_name 請求到達的服務器名
$server_port 請求到達的服務器埠號
$server_protocol 請求的協議版本,"HTTP/1.0"或"HTTP/1.1"
$uri 請求的URI,可能和最初的值有不同,比如經過重定向之類的
nginx對于請求的處理分多個階段,Nginx , 從而讓第三方模塊通過掛載行為在不同的階段來控制, 大致如下
- 初始化階段(Initialization Phase)
init_by_lua_file
init_worker_by_lua_file
- 重寫與訪問階段(Rewrite / Access Phase)
rewrite_by_lua_file
access_by_lua_file
- 內容生成階段(Content Phase)
content_by_lua_file
日志記錄階段(Log Phase),,,,
如果大家有更多的資源希望能一起分享,謝謝大家!!!
轉載請註明出處,本文鏈接:https://www.uj5u.com/qita/260340.html
標籤:其他
