Nginx+Tomcat+cluster集群搭建

Tomcat1 --> 带有newrelic的主Tomcat复制版本

Tomcat2 --> 纯净的相同版本的Tomcat

Nginx1.8

SSL证书原始文件和密码

安装Nginx

nginx1.8 download - http://nginx.org/download/nginx-1.8.0.tar.gz
	安装nginx支持文件:
	![](http://i.imgur.com/16kENRp.png)
	--prefix 为Nginx的安装目录

	![](http://i.imgur.com/HVl7fIX.png)

    下载1.0.2版本OpenSSL,并解压
	wget http://www.openssl.org/source/openssl-1.0.2e.tar.gz

	下载Nginx_lua模块并解压
	wget https://github.com/chaoslawful/lua-nginx-module/archive/v0.10.4.tar.gz

	下载Lua语言
	wget http://luajit.org/download/LuaJIT-2.0.2.tar.gz
	解压 - make
	出现如下内容表示编译成功
	OK        Successfully built LuaJIT
	make[1]: Leaving directory `/usr/local/src/LuaJIT-2.0.2/src'
	==== Successfully built LuaJIT 2.0.2 ====
	make install
	出现如下内容,表示安装成功
	==== Successfully installed LuaJIT 2.0.2 to /usr/local ====
	环境变量
	export LUAJIT_LIB=/usr/local/lib
	export LUAJIT_INC=/usr/local/include/luajit-2.0
	
	安装devel_kit
	wget https://github.com/simpl/ngx_devel_kit/archive/v0.2.19.tar.gz
	解压

	安装命令
	./configure --prefix=/usr/local/nginx-1.8 --with-http_stub_status_module --with-http_gzip_static_module --with-http_ssl_module --with-openssl=/usr/local/download/openssl-1.0.2e --with-http_spdy_module --add-module=/usr/local/ngx_devel_kit-0.2.19 --add-module=/usr/local/lua-nginx-module-0.10.4
	
	#--add-module=/usr/local/jakarta/nginx_jvm_route/nginx_upstream_jvm_route
	#with-http_stub_status_module  -- 监控Nginx运行状态
	#with-http_ssl_module -- 开启Nginx支持ssl
	#with-openssl -- 使用哪一个openssl,注意这里是openssl的源码而不是安装后的目录
	#ngx_devel_kit+lua-nginx-module 是lua语言扩展包
	#SPDY 协议旨在通过压缩、多路复用和优先级来缩短网页的加载时间和提高安全性。(SPDY 是 Speedy 的昵音,意思是更快)

	make --尝试安装看看是否出错
	make install 开始正式安装

	如果出错用这个命令
	ln -s /usr/local/lib/libluajit-5.1.so.2 /lib64/libluajit-5.1.so.2

配置Nginx

user  root;
	worker_processes  4;
	
	#error_log  logs/error.log;
	#error_log  logs/error.log  notice;
	#error_log  logs/error.log  info;
	
	#pid    logs/nginx.pid;
	
	events {
	    use epoll;#linux专用,速度很快
	    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;
	
		#禁止显示nginx版本,安全性问题
	    server_tokens off;
	
	    sendfile    on;
	    #tcp_nopush   on;
	
	    #keepalive_timeout  0;
	    keepalive_timeout  120;
	
	    gzip  on;
	    gzip_min_length  1k;#1k以下文件禁用gzip
	    gzip_buffers   4 16k;
	    gzip_http_version 1.0;
	    gzip_comp_level 4;#数字大压缩比例高,cpu负载大
	    gzip_types text/html,application/x-javascript,text/css;
	    gzip_vary on;
	
	    #improve fastcgi_buffers to solve 504error
	    fastcgi_buffers 8 128k;
	
	    #time out time
	    send_timeout 120;
	
	    #404error page
	
	    #fastcgi_intercept_errors on;
	
	  #http请求转发 301重定向	
	  server {
	    listen     80;
	    server_name  localhost_80;
	
	    rewrite ^(.*)$  https://$host$1 permanent;
	  }
	
	  upstream tomcatserver {
	    ip_hash;#用户所访问的服务器绑定与ip,除非ip改变否则不会访问其他的server
	    server localhost:8080 weight=6;
	    server localhost:8081 weight=4 max_fails=3 fail_timeout=30s; #backup 备用服务器
		#1.轮询(默认)
		#2.fair; 响应优先/upstream_fair支持
		#3.url_hash 相同的url分到相同后端 - 静态缓存
		#4.ip_hash ip绑定,相同ip分到相同后端 - 弊端
		#jvm_route第三方。目前支持版本1.4,sessionId绑定
	  }
	  
	  #2 - 请求频率 
	  #令牌原理,cooke的token作为标识符,每秒限制x个请求
	  limit_req_zone $cookie_token zone=session_limit:10m rate=30r/s;

	  # HTTPS server
	  server {
	    listen    443 ssl spdy;
	    server_name  dev.seoclarity.net;
	
	    ssl on;
	    ssl_certificate /home/ssl/wildcard/chained.crt;
	    ssl_certificate_key /home/ssl/wildcard/seoclarity_net.key;
		#openssl支持的加密版本,拒绝sslv2 和 sslv3
	    ssl_protocols TLSv1 TLSv1.1 TLSv1.2;
	    #ssl_ciphers EECDH+AESGCM:EDH+AESGCM:AES256+EECDH:AES256+EDH;
		##只支持安全的加密算法,拒绝例如MD5之类的非安全算法
	    ssl_ciphers ECDH+AESGCM:DH+AESGCM:ECDH+AES256:DH+AES256:ECDH+AES128:DH+AES:ECDH+3DES:DH+3DES:RSA+AESGCM:RSA+AES:RSA+3DES:!aNULL:!MD5;
	    ssl_prefer_server_ciphers on;
		#ssl加密过的key缓存时间10分钟,不需要每次都和客户端握手
	    ssl_session_cache shared:SSL:10m;
		#完全正向加密(Perfect Forward Secrecy,PFS)
		#http://baike.baidu.com/link?url=HzOVQe-j2wN4JDJVFx_EiuPBoZp0TGN2sn8R_n4We2VedkkRX1B8UlMCO6qzIzEfXKzgGn0x_9PK7o5bAOJQha
		#黑客保存拦截的数据待破解后一次性解密,PFS应对
		#加密的随机数默认1024字节
	    ssl_dhparam /home/ssl/wildcard/dhparam.pem;
	    ssl_session_timeout 30m;
		#缓冲区
		ssl_buffer_size 1400;

	    index  index.html index.htm index.jsp;

	    location / {
	        proxy_pass http://tomcatserver;
			
			#2 - 请求频率
			#令牌原理,cooke的token作为标识符
			#burst作为备用的访问请求数,比如上面限制30r/s但是第一秒访问30+burst的请求也是允许的,但是第二秒将严格限制30r/s
			#nodelay,如果不设置该选项,严格使用平均速率限制请求数
			#第1秒25个请求时,5个请求放到第2秒执行
			#设置了的话,25个请求严格在第一秒,超过的请求直接503
			limit_req zone=session_limit burst=10;#nodelay

			#1 - 限制请求
			#API、爬虫 禁用 - CC攻击
			rewrite_by_lua '
				#从cookie中取随机数
			    local random = ngx.var.cookie_random
				#cookie中无随机数
			    if(random == nil) then
					#生成随机数
			        random = math.random(999999)
			    end
				#ip+随机数 MD5加密 --> token
			    local token = ngx.md5("opencdn" .. ngx.var.remote_addr .. random)
				#如果cookie中token != 计算的token
				if (ngx.var.cookie_token ~= token) then
					#放置token
			        ngx.header["Set-Cookie"] = {"token=" .. token, "random=" .. random}
			        #让客户端重新请求
					return ngx.redirect(ngx.var.scheme .. "://" .. ngx.var.host .. ngx.var.uri)
			    end
			';

	        proxy_redirect off;
			#后端常用参数转发,不加这些后端经常取到客户ip是127.0.0.1
	        proxy_set_header Host $host;
	        proxy_set_header X-Real-IP $remote_addr;
	        proxy_set_header REMOTE-HOST $remote_addr;
	        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
	        proxy_set_header Cookie $http_cookie;
			#文件上传最大size
	        client_max_body_size 5m;
	        client_body_buffer_size 256k;
	        proxy_connect_timeout 10;
	        proxy_send_timeout 30;
	        proxy_read_timeout 120;
	        proxy_buffer_size 256k;
	        proxy_buffers 4 256k;
	        proxy_busy_buffers_size 256k;
	        proxy_temp_file_write_size 256k;
	        #proxy_next_upstream error timeout invalid_header http_500 http_503 http_404;
	    }
	
		#监控nginx状态
	    location /ngx_status {
	        stub_status on;
	        access_log off;
	        #allow 127.0.0.1;
	        #deny all;
	    }
	
		#静态文件访问
	    location ~* ^.+\.(swf|gif|png|jpg|js|css)$ {
	        root /home/actonia/source/0729/trunk/saas/WebContent;
	        expires 15m;
	    }
	
	    #error page
	    error_page   500 502 503 504  /50x.html;
	    location = /50x.html {
	        root   html;
	    }
	  }
	}

Tomcat1配置文件

<?xml version='1.0' encoding='utf-8'?>

<Server port="8035" shutdown="SHUTDOWN">

  <Listener className="org.apache.catalina.core.AprLifecycleListener" SSLEngine="on" />
  <Listener className="org.apache.catalina.core.JasperListener" />
  <Listener className="org.apache.catalina.core.JreMemoryLeakPreventionListener" />
  <Listener className="org.apache.catalina.mbeans.ServerLifecycleListener" />
  <Listener className="org.apache.catalina.mbeans.GlobalResourcesLifecycleListener" />

  <GlobalNamingResources>

    <Resource name="UserDatabase" auth="Container"
              type="org.apache.catalina.UserDatabase"
              description="User database that can be updated and saved"
              factory="org.apache.catalina.users.MemoryUserDatabaseFactory"
              pathname="conf/tomcat-users.xml" />
  </GlobalNamingResources>

  <Service name="Catalina">

    <Connector port="8080" maxHttpHeaderSize="8192"
               maxThreads="150" minSpareThreads="25" maxSpareThreads="75"
               enableLookups="false" redirectPort="443" acceptCount="100"
               connectionTimeout="20000" disableUploadTimeout="true"
               compression="on"
               maxPostSize="0"
               URIEncoding="UTF-8"
               compressionMinSize="2048"
               noCompressionUserAgents="gozilla, traviata"
               compressableMimeType="text/html,text/xml,text/javascript,text/css,application/json" />

    <Connector port="8039" protocol="AJP/1.3" redirectPort="443" URIEncoding="UTF-8" />

    <Engine name="Catalina" defaultHost="localhost" jvmRoute="tomcat1nginx">

      <Cluster className="org.apache.catalina.ha.tcp.SimpleTcpCluster"
                 channelSendOptions="8">

          <Manager className="org.apache.catalina.ha.session.DeltaManager"
                   expireSessionsOnShutdown="false"
                   notifyListenersOnReplication="true"/>

          <Channel className="org.apache.catalina.tribes.group.GroupChannel">
            <Membership className="org.apache.catalina.tribes.membership.McastService"
                        address="228.0.0.4"#这个地址是广播地址
                        port="33451"#这个端口号2个要一样(相同广播地址相同端口认定为同一个组播)
                        frequency="500"
                        dropTime="3000"/>
                        <Receiver className="org.apache.catalina.tribes.transport.nio.NioReceiver"
                                address="auto"#组播
                                port="4000"
                                autoBind="100" #从4000开始,100以内随机挑选一个
                                selectorTimeout="5000"
                                maxThreads="6"/>

            <Sender className="org.apache.catalina.tribes.transport.ReplicationTransmitter">
              <Transport className="org.apache.catalina.tribes.transport.nio.PooledParallelSender"/>
            </Sender>
            <Interceptor className="org.apache.catalina.tribes.group.interceptors.TcpFailureDetector"/>
            <Interceptor className="org.apache.catalina.tribes.group.interceptors.MessageDispatch15Interceptor"/>
          </Channel>

          <Valve className="org.apache.catalina.ha.tcp.ReplicationValve"
                 filter=""/>
          <Valve className="org.apache.catalina.ha.session.JvmRouteBinderValve"/>

          <Deployer className="org.apache.catalina.ha.deploy.FarmWarDeployer"
                    tempDir="/tmp/war-temp/"
                    deployDir="/tmp/war-deploy/"
                    watchDir="/tmp/war-listen/"
                    watchEnabled="false"/>

          <ClusterListener className="org.apache.catalina.ha.session.JvmRouteSessionIDBinderListener"/>
          <ClusterListener className="org.apache.catalina.ha.session.ClusterSessionListener"/>

        </Cluster>

      <Realm className="org.apache.catalina.realm.UserDatabaseRealm"
             resourceName="UserDatabase"/>

      <Host name="localhost"  appBase="webapps"
            unpackWARs="true" autoDeploy="true"
            xmlValidation="false" xmlNamespaceAware="false">

        <Valve className="org.apache.catalina.valves.AccessLogValve" directory="logs"
               prefix="localhost_access_log." suffix=".txt" pattern="combined" resolveHosts="false"/>

      </Host>
    </Engine>
  </Service>
</Server>

Tomcat2配置文件

<?xml version='1.0' encoding='utf-8'?>
<Server port="8036" shutdown="SHUTDOWN">

  <Listener className="org.apache.catalina.core.AprLifecycleListener" SSLEngine="on" />
  <Listener className="org.apache.catalina.core.JasperListener" />
  <Listener className="org.apache.catalina.core.JreMemoryLeakPreventionListener" />
  <Listener className="org.apache.catalina.mbeans.ServerLifecycleListener" />
  <Listener className="org.apache.catalina.mbeans.GlobalResourcesLifecycleListener" />

  <GlobalNamingResources>

    <Resource name="UserDatabase" auth="Container"
              type="org.apache.catalina.UserDatabase"
              description="User database that can be updated and saved"
              factory="org.apache.catalina.users.MemoryUserDatabaseFactory"
              pathname="conf/tomcat-users.xml" />
  </GlobalNamingResources>

  <Service name="Catalina">

    <Connector port="8081" maxHttpHeaderSize="8192"
               maxThreads="150" minSpareThreads="25" maxSpareThreads="75"
               enableLookups="false" redirectPort="443" acceptCount="100"
               connectionTimeout="20000" disableUploadTimeout="true"
               compression="on"
               maxPostSize="0"
               URIEncoding="UTF-8"
               compressionMinSize="2048"
               noCompressionUserAgents="gozilla, traviata"
               compressableMimeType="text/html,text/xml,text/javascript,text/css,application/json" />

    <Connector port="8040" protocol="AJP/1.3" redirectPort="443" URIEncoding="UTF-8" />

    <Engine name="Catalina" defaultHost="localhost" jvmRoute="tomcat2nginx">

      <Cluster className="org.apache.catalina.ha.tcp.SimpleTcpCluster"
                 channelSendOptions="8">

          <Manager className="org.apache.catalina.ha.session.DeltaManager"
                   expireSessionsOnShutdown="false"
                   notifyListenersOnReplication="true"/>

          <Channel className="org.apache.catalina.tribes.group.GroupChannel">
            <Membership className="org.apache.catalina.tribes.membership.McastService"
                        address="228.0.0.4"#
                        port="33451"#
                        frequency="500"
                        dropTime="3000"/>
                <Receiver className="org.apache.catalina.tribes.transport.nio.NioReceiver"
                                address="auto"#
                                port="4000"#
                                autoBind="100"
                                selectorTimeout="5000"
                                maxThreads="6"/>

            <Sender className="org.apache.catalina.tribes.transport.ReplicationTransmitter">
              <Transport className="org.apache.catalina.tribes.transport.nio.PooledParallelSender"/>
            </Sender>
            <Interceptor className="org.apache.catalina.tribes.group.interceptors.TcpFailureDetector"/>
            <Interceptor className="org.apache.catalina.tribes.group.interceptors.MessageDispatch15Interceptor"/>
          </Channel>

          <Valve className="org.apache.catalina.ha.tcp.ReplicationValve"
                 filter=""/>
          <Valve className="org.apache.catalina.ha.session.JvmRouteBinderValve"/>

          <Deployer className="org.apache.catalina.ha.deploy.FarmWarDeployer"
                    tempDir="/tmp/war-temp/"
                    deployDir="/tmp/war-deploy/"
                    watchDir="/tmp/war-listen/"
                    watchEnabled="false"/>

          <ClusterListener className="org.apache.catalina.ha.session.JvmRouteSessionIDBinderListener"/>
          <ClusterListener className="org.apache.catalina.ha.session.ClusterSessionListener"/>

        </Cluster>

      <Realm className="org.apache.catalina.realm.UserDatabaseRealm"
             resourceName="UserDatabase"/>

      <Host name="localhost"  appBase="webapps"
            unpackWARs="true" autoDeploy="true"
            xmlValidation="false" xmlNamespaceAware="false">

        <Valve className="org.apache.catalina.valves.AccessLogValve" directory="logs"
               prefix="localhost_access_log." suffix=".txt" pattern="combined" resolveHosts="false"/>

      </Host>
    </Engine>
  </Service>
</Server>

以下是摘抄的组播解释

<!-- 
    Cluster(集群,族) 节点,如果你要配置tomcat集群,则需要使用此节点.
    className 表示tomcat集群时,之间相互传递信息使用那个类来实现信息之间的传递.
    channelSendOptions可以设置为2、4、8、10,每个数字代表一种方式
    2 = Channel.SEND_OPTIONS_USE_ACK(确认发送)
    4 = Channel.SEND_OPTIONS_SYNCHRONIZED_ACK(同步发送) 
    8 = Channel.SEND_OPTIONS_ASYNCHRONOUS(异步发送)
    在异步模式下,可以通过加上确认发送(Acknowledge)来提高可靠性,此时channelSendOptions设为10
-->
<Cluster className="org.apache.catalina.ha.tcp.SimpleTcpCluster" channelSendOptions="8">
    <!--
        Manager决定如何管理集群的Session信息。Tomcat提供了两种Manager:BackupManager和DeltaManager
        BackupManager-集群下的所有Session,将放到一个备份节点。集群下的所有节点都可以访问此备份节点
        DeltaManager-集群下某一节点生成、改动的Session,将复制到其他节点。
        DeltaManager是Tomcat默认的集群Manager,能满足一般的开发需求
        使用DeltaManager,每个节点部署的应用要一样;使用BackupManager,每个节点部署的应用可以不一样.

        className-指定实现org.apache.catalina.ha.ClusterManager接口的类,信息之间的管理.
        expireSessionsOnShutdown-设置为true时,一个节点关闭,将导致集群下的所有Session失效
        notifyListenersOnReplication-集群下节点间的Session复制、删除操作,是否通知session listeners
        maxInactiveInterval-集群下Session的有效时间(单位:s)。
        maxInactiveInterval内未活动的Session,将被Tomcat回收。默认值为1800(30min)
    -->
    <Manager className="org.apache.catalina.ha.session.DeltaManager"
             expireSessionsOnShutdown="false"
             notifyListenersOnReplication="true"/>

    <!--
        Channel是Tomcat节点之间进行通讯的工具。
        Channel包括5个组件:Membership、Receiver、Sender、Transport、Interceptor
    -->
    <Channel className="org.apache.catalina.tribes.group.GroupChannel">
         <!--
            Membership维护集群的可用节点列表。它可以检查到新增的节点,也可以检查到没有心跳的节点
            className-指定Membership使用的类
            address-组播地址
            port-组播端口
            frequency-发送心跳(向组播地址发送UDP数据包)的时间间隔(单位:ms)。默认值为500
            dropTime-Membership在dropTime(单位:ms)内未收到某一节点的心跳,则将该节点从可用节点列表删除。默认值为3000

            注: 组播(Multicast):一个发送者和多个接收者之间实现一对多的网络连接。
                一个发送者同时给多个接收者传输相同的数据,只需复制一份相同的数据包。
                它提高了数据传送效率,减少了骨干网络出现拥塞的可能性
                相同组播地址、端口的Tomcat节点,可以组成集群下的子集群
         -->
        <Membership className="org.apache.catalina.tribes.membership.McastService"
                    address="228.0.0.4"
                    port="45564"
                    frequency="500"
                    dropTime="3000"/>

        <!--
            Receiver : 接收器,负责接收消息
            接收器分为两种:BioReceiver(阻塞式)、NioReceiver(非阻塞式)

            className-指定Receiver使用的类
            address-接收消息的地址
            port-接收消息的端口
            autoBind-端口的变化区间
            如果port为4000,autoBind为100,接收器将在4000-4099间取一个端口,进行监听
            selectorTimeout-NioReceiver内轮询的超时时间
            maxThreads-线程池的最大线程数
        -->
        <Receiver className="org.apache.catalina.tribes.transport.nio.NioReceiver"
                  address="auto"
                  port="4000"
                  autoBind="100"
                  selectorTimeout="5000"
                  maxThreads="6"/>

        <!--
            Sender : 发送器,负责发送消息
            Sender内嵌了Transport组件,Transport真正负责发送消息
        -->
        <Sender className="org.apache.catalina.tribes.transport.ReplicationTransmitter">
            <!--
                Transport分为两种:bio.PooledMultiSender(阻塞式)、nio.PooledParallelSender(非阻塞式) 
            -->
            <Transport className="org.apache.catalina.tribes.transport.nio.PooledParallelSender"/>
        </Sender>

        <!--
            Interceptor : Cluster的拦截器
            TcpFailureDetector-网络、系统比较繁忙时,Membership可能无法及时更新可用节点列表,
            此时TcpFailureDetector可以拦截到某个节点关闭的信息,
            并尝试通过TCP连接到此节点,以确保此节点真正关闭,从而更新集群可以用节点列表                 
        -->
        <Interceptor className="org.apache.catalina.tribes.group.interceptors.TcpFailureDetector"/>

        <!--
            MessageDispatch15Interceptor-查看Cluster组件发送消息的方式是否设置为
            Channel.SEND_OPTIONS_ASYNCHRONOUS(Cluster标签下的channelSendOptions为8时)。
            设置为Channel.SEND_OPTIONS_ASYNCHRONOUS时,
            MessageDispatch15Interceptor先将等待发送的消息进行排队,然后将排好队的消息转给Sender
        -->
        <Interceptor className="org.apache.catalina.tribes.group.interceptors.MessageDispatch15Interceptor"/>
    </Channel>

    <!--
        Valve : 可以理解为Tomcat的拦截器
        ReplicationValve-在处理请求前后打日志;过滤不涉及Session变化的请求                   
        vmRouteBinderValve-Apache的mod_jk发生错误时,保证同一客户端的请求发送到集群的同一个节点
    -->
    <Valve className="org.apache.catalina.ha.tcp.ReplicationValve" filter=""/>
    <Valve className="org.apache.catalina.ha.session.JvmRouteBinderValve"/>

    <!--
        Deployer : 同步集群下所有节点的一致性。Deployer没试验成功过。。。
     -->
     <Deployer className="org.apache.catalina.ha.deploy.FarmWarDeployer"
                   tempDir="/tmp/war-temp/"
                   deployDir="/tmp/war-deploy/"
                   watchDir="/tmp/war-listen/"
                   watchEnabled="false"/>
    <!--
        ClusterListener : 监听器,监听Cluster组件接收的消息
        使用DeltaManager时,Cluster接收的信息通过ClusterSessionListener传递给DeltaManager
    -->
    <ClusterListener className="org.apache.catalina.ha.session.ClusterSessionListener"/>
</Cluster>

Nginx证书提取方法

http://blog.sina.com.cn/s/blog_4b81125f0100ky4e.html

服务器需要启用组播

查看是否启用组播

netstat -gn

因为tomcat的session同步功能需要用到组播,默认都是打开的.
可以通过指令打开
route add -net 224.0.0.0 netmask 240.0.0.0 dev eth0

其他注意事项

项目修改:

1.applicationContext-security.xml 取消https
2.web.xml 启用分布式: <distributable/> 否则会出现session无故丢失情况

关于Tomcat/部署代码 一些其他改动

1.Tomcat配置
1.结束热启动
  Tomcat conf/Catalina/localhost/ROOT.xml
  删除reloadable属性,编译时不会影响Tomcat正常运行
  
2.Tomcat8 cluster官方配置
  <Cluster className="org.apache.catalina.ha.tcp.SimpleTcpCluster"
             channelSendOptions="8">

      <Manager className="org.apache.catalina.ha.session.DeltaManager"
               expireSessionsOnShutdown="false"
               notifyListenersOnReplication="true"/>

      <Channel className="org.apache.catalina.tribes.group.GroupChannel">
        <Membership className="org.apache.catalina.tribes.membership.McastService"
                    address="228.0.0.4"
                    port="45564"
                    frequency="500"
                    dropTime="3000"/>
        <Receiver className="org.apache.catalina.tribes.transport.nio.NioReceiver"
                  address="auto"
                  port="4000"
                  autoBind="100"
                  selectorTimeout="5000"
                  maxThreads="6"/>

        <Sender className="org.apache.catalina.tribes.transport.ReplicationTransmitter">
          <Transport className="org.apache.catalina.tribes.transport.nio.PooledParallelSender"/>
        </Sender>
        <Interceptor className="org.apache.catalina.tribes.group.interceptors.TcpFailureDetector"/>
        <Interceptor className="org.apache.catalina.tribes.group.interceptors.MessageDispatch15Interceptor"/>
      </Channel>

      <Valve className="org.apache.catalina.ha.tcp.ReplicationValve"
             filter=""/>
      <Valve className="org.apache.catalina.ha.session.JvmRouteBinderValve"/>

      <Deployer className="org.apache.catalina.ha.deploy.FarmWarDeployer"
                tempDir="/tmp/war-temp/"
                deployDir="/tmp/war-deploy/"
                watchDir="/tmp/war-listen/"
                watchEnabled="false"/>

      <ClusterListener className="org.apache.catalina.ha.session.ClusterSessionListener"/>
    </Cluster>

3.Tomcat自带session持久化
取消注释,关闭功能。需要实现序列化
<!-- Uncomment this to disable session persistence across Tomcat restarts -->
<!--
<Manager pathname="" />
-->
2.关于newrelic配置
如果Tomcat路径变化,需要修改bin/下的catalina.sh 中 NR_JAR 这个变量
通用设置 : 
# ---- New Relic switch automatically added to start command on 2015 Oct 08, 05:12:50
NR_JAR="$CATALINA_BASE"/newrelic/newrelic.jar; export NR_JAR
JAVA_OPTS="$JAVA_OPTS -javaagent:$NR_JAR"; export JAVA_OPTS
3.整合Tomcat输出日志
1.进入 "从" Tomcat

2.vim bin/catalina.sh

3.增加变量
  #---- Main Tomcat Path for log----
  CATALINA_MAIN_BASE="主Tomcat Path"

4.在所有的 
  -Dcatalina.base=
  下增加 
  -Dcatalina.mainbase="$CATALINA_MAIN_BASE" \

5.找到 CATALINA_OUT="$CATALINA_BASE"/logs/catalina.out  
  修改为 CATALINA_OUT="$CATALINA_MAIN_BASE"/logs/catalina.out  

6.打开conf/logging.properties文件
  替换所有${catalina.base}为${catalina.mainbase}

7.重启"从"Tomcat,进入主Tomcat查看Log
4.Nginx配置
1.nginx默认的fastcgi进程响应缓冲区太小导致504 Gateway Time-out”错误。
  fastcgi_buffers 8 128k;

2.提升超时等待时间,不要太长吃内存
  keepalive_timeout  120;

3.解决Cookie问题
  location中
  proxy_set_header Cookie $http_cookie;
  
4.限制访问频率
  limit_req_zone $binary_remote_addr zone=one:10m rate=10r/s;