Windows下Nginx负载均衡+Tomcat原生集群实现Session共享配置
实施目的
在生产环境中实现不停机部署
实施思路
一.Tomcat原生集群实现不借助第三方工具实现多节点Session共享
二.Nginx配置负载均衡实现某一或多节点停机不影响访问
三.Nginx反向代理Tomcat集群实现80端口访问
Tomcat部分
如果是在同一台机器上,需要保证每个Tomcat的端口(一个Tomcat对应三个端口)不相同
如果是在同一台机器上,需要保证每个Tomcat的环境变量不相同
如果是不同机器则不用考虑端口和环境变量
1.把相同版本的Tomcat复制2份
节点1:apache-tomcat-8.5.27-8081
节点2:apache-tomcat-8.5.27-8082
2.修改每个Tomcat的conf/server.xml下的3个端口,避免端口冲突,我这里设置的是每个节点端口号递增1,如果不是单节点不用配置
#原端口8005,8081设置为8006,8082设置为8007
<Server port="8006" shutdown="SHUTDOWN">
#原端口8080,8081设置为8081,8082设置为8082
<Connector port="8081" protocol="HTTP/1.1"
connectionTimeout="20000"
redirectPort="8443" />
#原端口8009,8081设置为8010,8082设置为8011
<Connector port="8010" protocol="AJP/1.3" redirectPort="8443" />
3.开启Tomcat原生集群功能,去掉conf/server.xml中的Cluster的注释
<Cluster className="org.apache.catalina.ha.tcp.SimpleTcpCluster"/>
4.在webapps下发布的web项目的WEB-INF/web.xml中<web-app>标签里面添加上<distributable />,例子代码如下
<web-app xmlns="http://java.sun.com/xml/ns/j2ee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://java.sun.com/xml/ns/j2ee http://java.sun.com/xml/ns/j2ee/web-app_2_4.xsd"
version="2.4">
<display-name>TomcatClusterTest</display-name>
<distributable />
</web-app>
5.修改每个Tomcat的环境变量,在bin/startup.bat最上边加上如下语句,JDK地址每个节点相同,CATALINA_HOME根据每个Tomcat的路径具体设置
SET JAVA_HOME=d:\Java\jdk1.8.0_161
SET CATALINA_HOME=D:\apache-tomcat-8.5.27-8081
6.在项目里建立test.jsp,例子代码如下
<%@ page contentType="text/html; charset=GBK" %>
<%@ page import="java.util.*" %>
<html><head><title>Cluster App Test</title></head>
<body>
Server Info:
<%
out.println(request.getLocalAddr() + " : " + request.getLocalPort()+"<br>");%>
<%
out.println("<br> ID " + session.getId()+"<br>");
// 如果有新的 Session 属性设置
String dataName = request.getParameter("dataName");
if (dataName != null && dataName.length() > 0) {
String dataValue = request.getParameter("dataValue");
session.setAttribute(dataName, dataValue);
}
out.println("<b>Session 列表</b><br>");
System.out.println("============================");
Enumeration e = session.getAttributeNames();
while (e.hasMoreElements()) {
String name = (String)e.nextElement();
String value = session.getAttribute(name).toString();
out.println( name + " = " + value+"<br>");
System.out.println( name + " = " + value);
}
%>
<form action="test2.jsp" method="POST">
名称:<input type=text size=20 name="dataName">
<br>
值:<input type=text size=20 name="dataValue">
<br>
<input type=submit>
</form>
</body>
</html>
7.测试集群节点和Session共享,分别启动每个Tomcat,检测Session是否相同
http://localhost:8081/tc/test.jsp
http://localhost:8082/tc/test.jsp
Nginx部分
1.配置conf/nginx.conf,配置负载均衡服务器组,在server前加上如下配置
upstream tomcat_server{
#ip_hash;
server localhost:8081 weight=1 max_fails=1 fail_timeout=10s;
server localhost:8082 weight=1 max_fails=1 fail_timeout=10s;
}
本次测试采用的是轮询的方式,weight=1是分配权重,数字越高权重越大,被访问的几率越大,max_fails=1是最大失败次数,超过设置的次数,Nginx会自动标记该服务器为down状态,下次不再访问,fail_timeout=10s是失败超时时间秒数
2.配置server,红色字段为新增
listen 80;
server_name localhost;
#charset koi8-r;
#access_log logs/host.access.log main;
location / {
root html;
index index.html index.htm index.jsp;
proxy_pass http://tomcat_server;
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_connect_timeout 1;
proxy_read_timeout 1;
proxy_send_timeout 1;
}
至此,Nginx负载均衡搭建成功,接下来配合Tomcat做测试
测试
1.开启Nginx,访问http://localhost/tc/test.jsp,并不断刷新
可以看到负载均衡和Session共享已经测试成功
2.测试高可用
结语
本次搭建的本质目的其实是解决JAVAWEB项目版本更新时的部署问题,尽量做到不影响客户访问的情况下进行部署,具体操作是在部署前,先关掉某一个节点,这时候用户仍然能访问另外的节点。更新项目代码后启动停掉的节点,并立即关闭另一个节点,再对停止的节点进行相同的部署,更新后开启节点,又恢复了负载均衡的效果,也同时更新了版本,而且在更新过程中基本做到了不影响用户访问,不过具体效果还需要在实际项目测试中观察,待后续更新。
个人觉得比较好的做法是多服务器,Nginx作为前端服务器配置负载均衡和反向代理,多个Tomcat服务器部署项目,条件允许最好有单独的数据库主机。