How to Run ZK on Apache + Tomcat clustering, Part I
Ian Tsai, Engineer, Potix Corporation
April 30, 2007
- Apache 2.2.4 latter
- Apache JK Connector 1.2.22
- ZK newest
Let's think more about ZK framework's natural property: Program simple ZUML page and let server-side computing facade complex client-side AJAX presentation. For this purpose, our machine will have to do session talking, event processing and page interpretation. Those are all stateful works and relied on your server's stability.
Clustering is a useful technology for this situation. In the past, this could be a rocket science for general web developer, but now open source's power offering us an easy way to attach it... with a little configuration. This series of articles will try to use Eclipse to show how to develop ZK web application in a clustering environment, and what kind of traps, errors and myths you should avoid. The topic of the first article here is very simple:
Let's build an easy clustering environment to run ZK-Demo.
A Simple Case of Clustering
The clustering demonstration we'll build in this article is shown below:
Procedure for Eclipse & Tomcat Configuration
- Launch the IDE Eclipse3.2. If you don't have it, download here.
- Create a web project you desired. In this case, we use zkDemo which I name it zkDemoWeb. Right click your Package Explorer [new] -> [project] then create [Web] -> [Dynamic Web Project]. Fill those blanks with your definitions.
- Right click the project you created. Chose [Run As]->[Run On Server], and then you can choose an existing server or Manually define a new one.
- Add your web project to this server config. Clicking [Finish] and Eclipse will create a project named "Servers" for its self. If you have doing this before and manually define a new server, Eclipse will add a new item for your config.
- Add more server nodes. Now we got a project, a server config. For the next, we'll create more Tomcat server config to build our clustering system. Right click [Servers] -> [New] -> [Other...] and create new Server config items. Because session replication costly while cluster nodes more then three (it's about math, think about fully connected graph K3~K4), I only add two more.
- Configuring Tomcat server nodes' [server.xml] which is in:TOMCAT_HOME/conf/server.xml To enable the cluster features correctly. You can read more detail information here, or following steps 7.
- Set these ports in [server.xml] to different. Because we run tomcat instances at the same machine. We need to avoid conflict between cluster nodes. The ports need to set different are:
- I.Server admin port: origin is 8005, I set 8025 to 8027.
<Server port="8006" shutdown="SHUTDOWN"> </Server>
- II.Default HTTP Connector port: I set 8081 to 8083.
<!-- Define a non-SSL HTTP/1.1 Connector on port 8080 --> <Connector acceptCount="100" connectionTimeout="20000" disableUploadTimeout="true" enableLookups="false" maxHttpHeaderSize="8192" maxSpareThreads="75" maxThreads="150" minSpareThreads="25" port="8081" redirectPort="8444"/>
- III.AJP 1.3 Connector port: origin is 8009, I set 8009 to 8011
<!-- Define an AJP 1.3 Connector on port 8010 --> <Connector enableLookups="false" port="8010" protocol="AJP/1.3" redirectPort="8444"/>
- IV.Set engine's attribute:[jvmRoute]. This attribute let load balancer pass sessions correctly between cluster node and user's browser. Booking each nodes name and we'll use it at procedure for Apache & JK Side.
<!-- You should set jvmRoute to support load-balancing via AJP ie : --> <Engine defaultHost="localhost" jvmRoute="worker1" name="Standalone">
- V.Unmark cluster tag section. Set 's [tcpListenPort] in different. I set them 4001 to 4003.
<Receiver className="org.apache.catalina.cluster.tcp.ReplicationListener" tcpListenAddress="auto" tcpListenPort="4002" tcpSelectorTimeout="100" tcpThreadCount="6"/>
- 8. Configuring your web project distributable. The step is simple. First, All your session attributes must implement java.io.Serializable. and the second, make sure your web.xml has the <distributable/> element.
Procedure for Apache & JK Configuration
- Download and install Apache Httpd and you can view the detail docs here.
- Download JK Connector here(mod jk-apache-2.2.4.so) and you can view the detail docs here.
- Configuring Apache + JK. Put the unzipped file [mod_jk-apache-2.2.4.so] to [Apache_home/ modules] and create two files in [Apache_home/conf] for JK's Configuration. Named them [uriworkermap.properties] and [workers.properties]. You can download samples here.
- Configuring [httpd.conf] which is:Apache_Home/conf/httpd.conf. This file is Apache HTTP Server's central control. In order to tell Apache the existence of JK Connector module and the module's config, we add this part inside:
#***********module JK Module******************* LoadModule jk_module modules/mod_jk.so # # Configure mod_jk # JkWorkersFile conf/workers.properties JkMountFile conf/uriworkermap.properties JkLogFile logs/mod_jk.log JkLogLevel warn
- 5. Configure [workers.properties]. The following code shows how to set JK as a load balancer and how to mount cluster nodes onto it.
# Define some properties # Define ApacheJkLb,jkstatus which can be used in uriworkermap.properties. the ApacheJkLb is loadbalancing worker worker.list= ApacheJkLb, jkstatus # Set properties for worker1 (ajp13) worker.worker1.type=ajp13 worker.worker1.host=localhost worker.worker1.port=8010 worker.worker1.lbfactor=1 worker.worker1.connection_pool_timeout=600 worker.worker1.socket_keepalive=True worker.worker1.socket_timeout=60 # Set properties for worker2 (ajp13) worker.worker2.type=ajp13 worker.worker2.host=localhost worker.worker2.port=8009 worker.worker2.lbfactor=1 worker.worker2.connection_pool_timeout=600 worker.worker2.socket_keepalive=True worker.worker2.socket_timeout=60 # Set properties for worker3 (ajp13) worker.worker3.type=ajp13 worker.worker3.host=localhost worker.worker3.port=8011 worker.worker3.lbfactor=1 worker.worker3.connection_pool_timeout=600 worker.worker3.socket_keepalive=True worker.worker3.socket_timeout=60 # Set "worker.WORKER_NAME.type=lb" will open JK's Load balancering function. In other words, JK becomes a load balancer. worker.ApacheJkLb.type=lb # Add those workers to the load balancer you defind befor. worker.ApacheJkLb.balance_workers=worker1,worker2,worker3 # Set "worker.WORKER_NAME.type=status" to open a channel to Admin JK Connector. worker.jkstatus.type=status
- 6. Configure [uriworkermap.properties]. The following code defines the strategy to direct clients request. Please read the comments for details.
# General syntax for this file is: # [URL]=[Worker name] # #Direct those requests have such patterns to the cluster nodes defined in workers.properties # # /zkDemoWeb/*=ApacheJkLb /*.zul=ApacheJkLb /*.dsp=ApacheJkLb # # Except /jkManager because we need a url to jkstatus # /jkManager=jkstatus # # For no mapping the url has to start with exclamation (!) # Usually used in static data requests. because httpd serv these is faster then Tomcat. # So here's an EASY WAY to "Over Write" ZK's .css, .img and .js. # you have neither CRUD zk's jar file nor editing language-addon.xml... # you just redirect all these kind of requests to Apache Http Server!!! # !/img/*.jpeg=ApacheJkLb !/img/*.gif=ApacheJkLb !/img/*.jpg=ApacheJkLb !/img/*.png=ApacheJkLb !/flash/*.swf=ApacheJkLb !/activex/*.ocx=ApacheJkLb !/css/*.css=ApacheJkLb !/js/*.js=ApacheJkLb
Running our Clustering System
The sequence to start which side doesn't matter. Just put the zkDemo into the project you created and enjoy it! Let's take a look of the console:
2007/4/30 AM 08:37:30 org.apache.catalina.cluster.tcp.SimpleTcpCluster start INFO: Cluster is about to start 2007/4/30 AM 08:37:30 org.apache.catalina.cluster.tcp.ReplicationTransmitter start INFO: Start ClusterSender at cluster Standalone:type=Cluster,host=localhost with name Standalone: type=ClusterSender,host=localhost 2007/4/30 AM 08:37:30 org.apache.catalina.cluster.mcast.McastService start INFO: Sleeping for 2000 milliseconds to establish cluster membership 2007/4/30 AM 08:37:32 org.apache.catalina.cluster.mcast.McastService registerMBean INFO: membership mbean registered (Standalone:type=ClusterMembership,host=localhost) 2007/4/30 AM 08:37:32 org.apache.catalina.cluster.deploy.FarmWarDeployer start INFO: Cluster FarmWarDeployer started. 2007/4/30 AM 08:37:33 org.apache.catalina.cluster.session.DeltaManager start INFO: Register manager /zkDemoWeb to cluster element Host with name localhost 2007/4/30 AM 08:37:33 org.apache.catalina.cluster.session.DeltaManager start INFO: Starting clustering manager at /zkDemoWeb 2007/4/30 AM 08:37:33 org.apache.catalina.cluster.session.DeltaManager getAllClusterSessions
While your Tomcat started with no error message, you must see some messages like this.
INFO: Parsing jndi:/localhost/zkDemoWeb/WEB-INF/zk.xml 2007/4/30 AM 08:37:33 org.zkoss.zk.ui.sys.ConfigParser parseClass:255 INFO: Using org.zkoss.zk.ui.http.SerializableUiFactory for interface org.zkoss.zk.ui.sys.UiFactory 2007/4/30 AM 08:37:34 org.apache.coyote.http11.Http11BaseProtocol start INFO: Starting Coyote HTTP/1.1 on http-8081 2007/4/30 AM 08:37:34 org.apache.jk.common.ChannelSocket init INFO: JK: ajp13 listening on /0.0.0.0:8010 2007/4/30 AM 08:37:34 org.apache.jk.server.JkMain start INFO: Jk running ID=0 time=0/47 config=null 2007/4/30 AM 08:37:34 org.apache.catalina.storeconfig.StoreLoader load INFO: Find registry server-registry.xml at classpath resource 2007/4/30 AM 08:37:34 org.apache.catalina.startup.Catalina start INFO: Server startup in 3969 ms 2007/4/30 AM 08:38:44 org.apache.catalina.cluster.tcp.SimpleTcpCluster memberAdded INFO: Replication member added:org.apache.catalina.cluster.mcast.McastMember[tcp://10.1.3.52:4001,catalina,10.1.3.52,4001, alive=0]
This console clip shows the first Node detect the second Node has being added, And they replicate their sessions.
Serve your static data with Apache can speed up your user's responsiveness. And it can do MORE... Overwrite ZK's theme!
|Copyright © Potix Corporation. This article is licensed under GNU Free Documentation License.|