개요


이번 글에서는 Apache HTTPD와 Tomcat 간의 세션 클러스터링 방법에 대해서 설명한다.

 

세션 클러스터링은 Web과 연동된 여러대의 Tomcat을 클러스터링하여 세션을 공유하는 기법이다. 

세션 클러스터링 시, Tomcat A의 사용자가 Tomcat B로 연결되어도 A에서 생성한 세션을 그대로 이어받을 수 있다.

 

L4 장비가 없는 로컬 환경에서 진행되므로 이번 글에서는 하나의 Apache에 2대의 톰캣을 연결한다.

 

연동 환경은 다음과 같다.

 

- OS : CentOS 6.7

- Apache Version : Apache 2.4.41

- Tomcat Version : Apache Tomcat 9.0.30

- Connector Version : JK 1.2.48

 

 

연동 전 준비사항


설정 방법은 이전 로드밸런싱 글에 나온 세팅을 그대로 사용한다.

 

https://itwarehouses.tistory.com/12?category=727632

 

Apache HTTPD to Tomcat, 로드 밸런싱(Load Balancing)

개요 이번 글에서는 Apache HTTPD와 Tomcat 간의 로드밸런싱 방법에 대해서 설명한다. 로드밸런싱은 고가용성을 위해 Apache와 Tomcat을 1:N 또는 N:N 방식으로 연결하여 Request를 분산 처리하며, 하나의 톰�

itwarehouses.tistory.com

 

 

Tomcat 설정 전 준비사항


1. Tomcat Session Clustering 간 Multicast를 위한 라우팅 설정이 필요하다.

 

위와 같이 라우팅 설정이 되어있지 않으면 해당 명령어로 주소를 추가하자.

route add -net 224.0.0.0 netmask 240.0.0.0 dev eth0(디바이스명)

 

 

 

2. Session Clustering에 사용되는 포트를 방화벽에서 허가해줘야 한다.

 

CentOS 6의 경우에는 vi /etc/sysconfig/iptables 로 아래의 내용을 추가하고 service iptables restart 실행

-A INPUT -m state --state NEW -m tcp -p tcp --dport 45564 -j ACCEPT
-A INPUT -m state --state NEW -m udp -p udp --dport 45564 -j ACCEPT
-A INPUT -m state --state NEW -m tcp -p tcp --dport 4000:4100 -j ACCEPT

 

CentOS 7의 경우에는 아래의 명령어를 실행한다.

firewall-cmd --permanent --zone=public --add-port=45564/tcp
firewall-cmd --permanent --zone=public --add-port=45564/udp
firewall-cmd --permanent --zone=public --add-port=4000-4100/tcp
firewall-cmd --reload

 

 

 

3. Apache workers.properties 파일에서 Sticky Session이 활성 되어있는지 확인한다.

 

기본값이 TRUE이기 때문에 아래와 같이 반드시 명시할 필요는 없다. 

 

false 또는 0 으로 되어있을 경우 true 또는 1로 변경한다.

 

 

 

 

Tomcat 관련 설정


Tomcat에서 설정해야할 부분은 총 3곳이다.

 

1. server.xml <Engine> 내 jvmRoute 요소 설정

 

위의 workers.properties 파일에서 로드밸런싱할 톰캣의 이름을 각각 worker1, worker2로 설정했었다.

 

각각의 Tomcat 서버에 jvmRoute 값을 worker1, worker2로 설정한다.

 

jvmRoute 값은 각 Tomcat 인스턴스의 라우팅 식별자로 사용되며, 설정 시 아래와 같이 세션 ID 값에 xxxxxx.${jvmRoute} 로 추가되어 표시된다.

 

 

2. server.xml <Host> 하위에 <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.MessageDispatchInterceptor"/>
          </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>

 

<Receiver> 내의 address 값에 ip 값을 입력하고, 같은 서버에서 여러대의 Tomcat이 동작할 경우 port의 값도 각각 다르게 설정해야 한다.

 

 

 

3. 어플리케이션 디렉터리 WEB-INF/web.xml에 <distributable /> 태그를 삽입한다.

 

 

Tomcat Documentation에 따르면 <distrubutable />이 하는 역할은 다음과 같다.

 

The <Manager> element defined inside the <Cluster> element is the template defined for all web applications that are marked <distributable/> in their web.xml file. However, you can still override the manager implementation on a per web application basis, by putting the <Manager> inside the <Context> element either in the context.xml file or the server.xml file.

 

web.xml에 <distrubutable />이 설정된 모든 어플리케이션이 server.xml에 설정한 <Manager> 설정대로 관리되는 듯 하다.

 

 

 

테스트


정상적으로 세션 클러스터링이 설정되었을 경우 테스트 방법은 아래와 같다.

 

1. Tomcat A, B 기동

2. Tomcat A 또는 B에서 처음으로 세션이 생성됨

3. 세션이 생성된 서버를 Shutdown

4. 나머지 서버의 세션 값이 처음 생성된 세션 값과 동일하면 설정 완료

 

 

1. Tomcat A, B 기동

 

 

 

2. Tomcat A 또는 B에서 세션 생성 확인 (Tomcat A에서 세션이 생성)

 

세션 값을 확인하는 방법은 여러가지가 있으나 여기서는 Chrome 브라우저의 개발자도구를 사용하였음.

 

 

3. 세션이 생성된 서버를 Shutdown(Tomcat A)

 

 

 

4. 나머지 서버(Tomcat B)의 세션 값이 처음 생성된 세션 값과 동일한지 확인

 

세션 값이 1EF398C1540F9380C4163C2F6062171F.worker1 으로 동일한 것을 확인할 수 있다.

 

만약 Session Clustering이 설정되지 않았다면 xxxxxxxx.worker2로 세션 값이 설정되었을 것이다.

 

 

 

+ Recent posts