Nginx+keepalived项目应用
本文档适用于了解nginx+keepalived技术的人使用, 涉及到该技术的产生背景,使用场景和环境配置等。
- 环境配置
操作系统:window10 64位
虚拟机:VMware-VIMSetup-all-6.0.0-3634788
虚拟机操作系统:centos7
JDK: jdk-8u121-linux-x64.tar
Tomcat: apache-tomcat-7.0.76.tar
Nginx:1.10.3 - 背景需求
我们用的外网服务器为阿里云服务器(为什么要用阿里云服务器?主要原因是申请公网IP开放80端口不容易阿里云提供80端口,其次是可以利用阿里云在一定程度上避免遭受攻击),为了能够实现代理访问,我们在阿里云服务器上面安装Nginx,即外网在访问网址的时候,通过阿里Nginx代理到我们局域网内部的Nginx上,然后通过局域网内部的Nginx访问到我们局域网中的tomcat服务器。 - 架构图
Nginx
Nginx是高性能http服务器及反向代理服务器,官方测试nginx能够支撑5万并发连接,且CPU/内存等资源消耗非常的低,运行非常的稳定。
架构图
如图所示:当用户访问地址: ip为149时 ,利用149服务器上nginx内置的算法,将发送的http请求转发到下面tomcat服务器上面,可以有效减少单击服务器的压力
负载均衡: 上图中tomcat服务器1234,这是一个集合,每台服务器都具有等价的地位, 都可以单独对外提供服务。通过这种负载分担技术,将外部发送来的请求均匀分配到对称结构中的每一台服务器上,而接受到请求的服务器独立的回应客户的请求。
反向代理: 上图,对外表现的只有149一台服务器,但是可能走tomcat1或者tomcat2或者tomcat3等.
以代理服务器来接受internet上的连接请求,然后将请求转发给内部网络上的服务器,并将从服务器上得到的结果返回给internet上请求连接的客户端.
Keepalived
架构图
现在只有一台149服务器, 为了避免149宕机,我的系统不能访问了, 现在要做一个服务器的集群,比如说:再来一台151服务器,一旦149宕机了,我就开始访问151,这时候,就用上了keepalived
Keepalived是集群管理中保证高可用的一个服务软件,主要是为了避免ip单点故障,一般也不会单独出现,会与其他负载均衡的技术一块出现,比如说nginx/haproxy(我们的mycat 就是用的keepalived+haproxy),一起工作来达到集群的高可用
是基于VRRP协议来实现的,那么什么是VRRP协议:
VRRP(Virtual Router Redundancy Protocal) 虚拟路由冗余协议.如上面的图,就是把两台提供相同功能的路由器组成一个组,这个组中, 149服务器是master,那么151服务器就是backup,但是外界在用的时候,只是用的145的这个虚拟ip,外界认为的只是这么一台,构成虚拟路由器, 当149处于正常可用状态的时候,149服务器实际上是在负责arp相应和转发ip数据包, 151此时就处于空闲状态,简单理解: 也就是一个备胎,时刻等待着. 149会一直发一个消息,也就是master的vrrp状态通告消息. 而151在设置的时间内,如果收不到Vrrp包,就直接认为149宕机了,变成master的角色 (哈哈,我可以从备胎转成正式的了). 现在是只有一个备胎,如果有多个备胎呢,那么就得根据Vrrp的优先级,来选取一个backup来转正了.整个的切换过程,非常的快,同时对于用户来说,是完全透明的. 用户使用的会一直是145这个虚拟ip,这样就保证了服务的持续可用性
- 安装及配置使用
4.1安装
4.1.1.Nginx安装及相关配置
nginx安装教程
4.1.2. Keepalived安装及相关配置
keepalived安装教程
4.2相关配置说明
4.2.1.Nginx配置
4.2.1.1.Nginx配置文件简要说明
4.2.1.2.实际项目中配置
阿里云服务器配置
其实跟上面差不多的,我直接粘出来吧
#user nginx;
worker_processes 3;
error_log /usr/local/nginx-1.13.5/logs/error.log warn;
pid /usr/local/nginx-1.13.5/logs/nginx.pid;
worker_rlimit_nofile 65535;
events {
worker_connections 65535; # default value 1024
use epoll;
}
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 /usr/local/nginx-1.13.5/logs/access.log main;
sendfile on ;
keepalive_timeout 65;
gzip_vary on;
upstream itoo_vip_server{
#tfjybj
#server 192.168.23.150:8087
server ip:端口号(这里其实就是那个虚拟ip以及端口号);
}
#--------------------------tfjy------------------------------#
server{
listen 80;
#domain name
server_name tfjybj.com www.tfjybj.com static.tfjybj.com tfjybj.cn;
default_type 'text/html';
charset utf-8;
location /{
proxy_buffer_size 128k;
proxy_buffers 128 128k;
proxy_busy_buffers_size 128k;
proxy_pass_header Server;
proxy_set_header Host $http_host;
proxy_redirect off;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Scheme $scheme;
proxy_pass http://itoo_vip_server/;
}
#-----------------------------Production---Wecat-test-start-----------------------------
location /wx {
root /usr/local;
autoindex on;
}
#-----------------------------Production---Wecat-safe-End-----------------------------
}
include /etc/nginx/conf.d/*.conf;
}
我在这里附带一下静态文件的位置,大家参考配置文件看一下
149服务器(151相同配置,除了servername)
worker_processes 4;
worker_rlimit_nofile 65535;
events {
worker_connections 65535;
use epoll;
}
http {
include mime.types;
default_type application/octet-stream;
access_log off;
error_log logs/error.log crit;
sendfile on;
keepalive_timeout 30;
gzip_vary on;
gzip_min_length 1000;
gzip_comp_level 6;
gzip_types text/plain text/css application/json application/x-javascript text/xml application/xml application/xml+rss text/javascript;
open_file_cache max=65535 inactive=20s;
open_file_cache_valid 30s;
open_file_cache_min_uses 2;
open_file_cache_errors off;
upstream vb_server{
server 192.168.22.160:8091;
server 192.168.22.162:8080;
}
server {
listen 8087;
server_name 192.168.23.149;
charset utf-8;
#root /usr/local;
#-----------------------------Production--- ITOO-EJB-Start-----------------------------
location / {
proxy_buffer_size 128k;
proxy_buffers 128 128k;
proxy_busy_buffers_size 128k;
if ($host ~* 'tfjybj.cn'){
set $a "http://192.168.23.155:8080/itoo-test-start-web";
}
if ($host ~* 'tfjybj.com'){
#set $a "http://192.168.23.156:8090/itoo-authority-start-web/getSystemindex";
}
proxy_pass $a;
proxy_set_header Host $host:80;
echo "$host";
}
#-----------------------------Production---VBLearn-Start-----------------------------
location /vb/ {
proxy_buffer_size 128k;
proxy_buffers 128 128k;
proxy_busy_buffers_size 128k;
proxy_pass http://vb_server/vb/;
proxy_set_header Host $host:80;
}
#-----------------------------Production---VBLearn-End-----------------------------
#-----------------------------Production---Error Handing-Start---------------------
error_page 502 /502.html;
location = /502.html {
root /usr/local/nginx-1.10.3/conf;
charset GB2312;
allow all;
}
#-----------------------------Production---Error Handing-End-----------------------
}
log_format myFormat '$remote_addr¨C$remote_user [$time_local] $request $status $body_bytes_sent $http_referer $http_user_agent $http_x_forwarded_for';
access_log /usr/local/nginx-1.10.3/nginx.log myFormat;
error_log /usr/local/nginx-1.10.3/nginx_error.log;
}
大家看一下阿里云服务器 配置文件的servername一行, 有tfjybj.com 也有tfjybj.cn
如果我想让tfjybj.com 访问的是项目1. tfjybj.cn访问项目2
代理方式:
如何匹配:
利用$host可以取到不同的请求的域名, 利用echo这个模块可以将它的值打出来(由于篇幅问题,不再列出了)
然后根据不同的域名进行if判断;
经过在网上查阅相关资料以及实验发现if可以在location模块里面,而location不能在if里面;另外匹配到之后不能直接用proxy_pass关键字,于是换了一种思路用变量;
4.2.2.Keepalived配置
4.2.2.1.Keepalived配置文件简要说明
4.2.2.2.实际项目中配置
149服务器(151相同配置,不过state 是BACKUP)
“`
! Configuration File for keepalived
global_defs {
notification_email {
15732621629@163.com
}
notification_email_from 15732621629@163.com
smtp_server smtp.163.com
smtp_connect_timeout 30
router_id Nginx_149_SC
}
vrrp_sync_group VG_1 {
group {
VI_1
}
}
vrrp_script check_nginx {
script “/usr/local/keepalived-1.3.4/nginx_check.sh”
interval 3
weight -2
}
vrrp_instance VI_1 {
state MASTER
interface eno16777984
virtual_router_id 30
priority 200
advert_int 1
authentication {
auth_type PASS
auth_pass 1111
}
track_script {
check_nginx
}
virtual_ipaddress {
192.168.23.150
}
}