Akemi

Tomcat综合案例

2024/08/23

环境说明

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
CentOS Linux release 7.9.2009 (Core)
jdk1.8.0-u421
tomcat 9.0.43
nignx 1.18
mysql 5.7.44 主从复制

主机地址
192.168.10.125 mysql-1
192.168.10.161 web1
192.168.10.162 web2
192.168.10.163 web3
192.168.10.164 nginx1
192.168.10.165 nginx2
vip 192.168.10.51/24

tomcat常用作java容器,擅长处理动态请求,但无法抗高并发
nginx擅长处理静态请求,并且可以处理高并发,可以做反向代理
两种整合方式:
1.动静分离:
将静态界面交给nginx,动态请求交给后端tomcat。只能针对非高并发的场景
2.负载均衡:
通过nginx反向代理和负载均衡,转发给后端tomcat
实际场景中,会使用cdn(比如cloudflare)来缓存静态资源,如果没有再访问源站服务器

NFS服务器准备

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
mkdir -p /root/data/jdk1.8
echo "/root/data/jdk1.8/ 192.168.10.0/24(rw,sync,no_root_squash,no_subtree_check)" >> /etc/exports
echo "/root/data/tomcat/ 192.168.10.0/24(rw,sync,no_root_squash,no_subtree_check)" >> /etc/exports

#下载jdk包与tomcat包
tar -xf jdk-8u421-linux-x64.tar.gz
cp jdk1.8.0_421/* /root/data/jdk1.8/
chmod -R 777 /root/data/

wget https://dlcdn.apache.org/tomcat/tomcat-9/v9.0.93/bin/apache-tomcat-9.0.93.tar.gz
tar -xf apache-tomcat-9.0.93.tar.gz
cp -R apache-tomcat-9.0.93 /root/data/tomcat
mkdir /root/data/tomcat/tomcat-apps/ROOT
cp jpress-web-newest.war /root/data/tomcat/tomcat-apps/jpress.war

#修改conf/server.xml
vim /root/data/tomcat/conf/server.xml
<Server port="8001" shutdown="SHUTDOWN">
...
<Connector port="8081" protocol="HTTP/1.1"
connectionTimeout="20000"
redirectPort="8443"
maxParameterCount="1000"
...
<Host name="www.it2.com" appBase="tomcat-apps"
unpackWARs="true" autoDeploy="true">

chmod -R 777 /root/data
exportfs -arv
#exporting 192.168.10.0/24:/root/data/tomcat
#exporting 192.168.10.0/24:/root/data/jdk1.8

数据库部分

1
2
3
4
create database jpress;
CREATE USER 'jpress'@'%' IDENTIFIED BY '123456';
GRANT ALL PRIVILEGES ON jpress.* TO 'jpress'@'%';
FLUSH PRIVILEGES;

web服务器准备

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
每台web服务器,先做其中一台
yum -y install nfs-utils
mkdir /usr/local/jdk1.8
mkdir /usr/local/tomcat
mount -t nfs 192.168.10.102:/root/data/jdk1.8 /usr/local/jdk1.8/
mount -t nfs 192.168.10.102:/root/data/tomcat /usr/local/tomcat
echo 'export JAVA_HOME=/usr/local/jdk1.8' >> /etc/profile
source /etc/profile

#启动
/usr/local/tomcat/bin/startup.sh

#网页安装
http://www.it2.com:8081/jpress/install

#安装完成后为web2 web3进行挂载
yum -y install nfs-utils
mkdir /usr/local/jdk1.8
mkdir /usr/local/tomcat
mount -t nfs 192.168.10.102:/root/data/jdk1.8 /usr/local/jdk1.8/
mount -t nfs 192.168.10.102:/root/data/tomcat /usr/local/tomcat
echo 'export JAVA_HOME=/usr/local/jdk1.8' >> /etc/profile
source /etc/profile
/usr/local/tomcat/bin/shutdown.sh
/usr/local/tomcat/bin/startup.sh

nginx负载均衡

主配置文件

1
2
3
4
5
6
7
8
9
10
11
12
13
cat > /usr/local/nginx/conf/nginx.conf << 'EOF'
worker_processes 1;
events {
worker_connections 1024;
}
http {
include /usr/local/nginx/conf/vhost/*.conf;
include mime.types;
default_type application/octet-stream;
sendfile on;
keepalive_timeout 65;
}
EOF

子配置文件

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
mkdir -p /usr/local/nginx/conf/vhost

将原本用户nginx的负载均衡配置改为备用
mv /usr/local/nginx/conf/vhost/nginx-LB.conf /usr/local/nginx/conf/vhost/nginx-LB.conf.bak

cat > /usr/local/nginx/conf/vhost/tomcat-LB.conf << 'EOF'
upstream java {
server 192.168.10.161:8081 weight=3 max_fails=3 fail_timeout=20s;
server 192.168.10.162:8081 weight=3 max_fails=3 fail_timeout=20s;
server 192.168.10.163:8081 weight=3 max_fails=3 fail_timeout=20s;
}
server {
listen 80;
server_name www.it.com;
location / {
proxy_pass http://java;
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_set_header X-Forwarded-Proto $scheme;
}
}
EOF
#先把keepalived关了,不然会一直自动拉活
systemctl stop keepalived.service
pkill nginx
nginx -t
nginx -s reload
nginx

curl 192.168.10.164:80/jpress/ > /dev/null 2>&1
echo $?
#0
#可以正常访问,就不放图了

scp -r /usr/local/nginx/conf nginx2:/usr/local/nginx/conf
chown -R www.www /usr/local/nginx

nginx集成keepalived

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
#将原本的文件备份,再创建一个新的配置文件
nginx1主:
mv /etc/keepalived/keepalived.conf /etc/keepalived/nginx-keepalived.conf.bak
cat > /etc/keepalived/keepalived.conf << 'EOF'
! Configuration File for keepalived
global_defs {
router_id lb01
}
vrrp_script check_nginx {
script "/etc/keepalived/check_nginx.sh"
interval 5
}
vrrp_instance it {
state MASTER
interface ens18
virtual_router_id 51
priority 150
advert_int 1
authentication {
auth_type PASS
auth_pass 1111
}
virtual_ipaddress {
192.168.10.51/24
}
track_script {
check_nginx
}
}
EOF

nginx2备:
mv /etc/keepalived/keepalived.conf /etc/keepalived/nginx-keepalived.conf.bak
cat > /etc/keepalived/keepalived.conf << 'EOF'
! Configuration File for keepalived
global_defs {
router_id lb02
}
vrrp_script check_nginx {
script "/etc/keepalived/check_nginx.sh"
interval 5
}
vrrp_instance it {
state SLAVE
interface ens18
virtual_router_id 51
priority 100
advert_int 1
authentication {
auth_type PASS
auth_pass 1111
}
virtual_ipaddress {
192.168.10.51/24
}
track_script {
check_nginx
}
}
EOF

检测脚本

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
cat > /etc/keepalived/check_nginx.sh <<'EOF'
#!/bin/bash
counter=$(ps -ef |grep nginx | grep sbin | egrep -cv "grep|$$" )
if [ $counter -eq 0 ]; then
nginx
echo "${date +%F} nginx重启" >> /etc/keepalived/check.log
sleep 2
counter=$(ps -ef |grep nginx | grep sbin | egrep -cv "grep|$$" )
if [ $counter -eq 0 ]; then
systemctl stop keepalived
echo "$(hostname)主机nginx服务异常,vip已切换" | mail -s "keepalived告警" alertwarning@163.com
fi
fi
ip a | grep -q 192.168.10.51
if [ $? -eq 0 ];then
ssh nginx1 "ip a | grep -q 192.168.10.51"
if [ $? -eq 0 ];then
echo "${date +%F} 脑裂" >> /etc/keepalived/check.log
echo "出现脑裂" | mail -s "keepalived脑裂警告" alertwarning@163.com
fi
fi
EOF
systemctl daemon-reload
systemctl restart keepalived.service

keepalive拉活nginx测试

1
2
3
4
5
ps -ef | grep -c nginx
#5
pkill nginx
ps -ef | grep -c nginx
#5

keepalived vip漂移测试

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
#查看现在状态
主:
ip a | grep ens18 -A 10 | grep -w inet
# inet 192.168.10.164/24 brd 192.168.10.255 scope global noprefixroute ens18
# inet 192.168.10.51/24 scope global secondary ens18
备:
ip a | grep ens18 -A 10 | grep -w inet
# inet 192.168.10.165/24 brd 192.168.10.255 scope global noprefixroute ens18

#关闭主节点的keepalived
systemctl stop keepalived.service

#此时查看状态
主:
ip a | grep ens18 -A 10 | grep -w inet
# inet 192.168.10.164/24 brd 192.168.10.255 scope global noprefixroute ens18
备:
ip a | grep ens18 -A 10 | grep -w inet
# inet 192.168.10.165/24 brd 192.168.10.255 scope global noprefixroute ens18
# inet 192.168.10.51/24 scope global secondary ens18

keepalive相关故障总结(搬运)

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
日志查看地址:/var/log/messages

日志问题与解决方案
1. 日志提示:
WARNING - script '/etc/keepalived/check_nginx.sh' is not executable for uid:gid 0:0 - disabling.
原因:keepalived监控脚本没有执行权限。
解决:
chmod +x /etc/keepalived/check_nginx.sh

2. 日志提示:
/etc/keepalived/check_nginx.sh exited due to signal 15
解决:
# 调整脚本执行间隔
interval 5
# 心跳检查间隔时间
advert_int 1
注意:确保监控脚本的执行时间大于advert_int的值。

3. 日志提示:
Error exec-ing command ‘/etc/keepalived/nginx_check.sh’, error 2: No such file or directory
原因:脚本文件可能不存在或路径错误,或者脚本文件格式不正确。
解决:
使用vi创建并编辑脚本:
vi nginx_check.sh
脚本编写完成后,使用sh命令测试执行:

sh nginx_check.sh
若执行报错(如语法错误),检查并修改脚本内容。
使用vim检查并修改脚本文件格式:

vim nginx_check.sh
:set ff? # 查看当前文件格式
:set ff=unix # 设置为UNIX格式
# 或者
:set fileformat=unix

4. 问题描述:
如果MASTER关闭,但是BACKUP没有抢占VIP,可能是防火墙阻挡了VRRP广播。
解决:
在iptables中添加规则以允许VRRP广播:
iptables -A INPUT -p vrrp -j ACCEPT
CATALOG
  1. 1. 环境说明
  2. 2. NFS服务器准备
  3. 3. web服务器准备
  4. 4. nginx负载均衡
  5. 5. nginx集成keepalived
  6. 6. keepalive相关故障总结(搬运)