一区二区三区日韩精品-日韩经典一区二区三区-五月激情综合丁香婷婷-欧美精品中文字幕专区

分享

通向架構(gòu)師的道路(第五天)之tomcat集群

 richsky 2012-07-05

通向架構(gòu)師的道路(第五天)之tomcat集群-群貓亂舞

分類: 架構(gòu)師之路 200人閱讀 評論(0) 收藏 舉報

一、為何要集群

單臺App Server再強勁,也有其瓶勁,先來看一下下面這個真實的場景。

當時這個工程是這樣的,tomcat這一段被稱為web zone,里面用spring+ws,還裝了一個jboss的規(guī)則引擎Guvnor5.x,全部是ws沒有service layer也沒有dao layer。

然后App Zone這邊是weblogic,傳輸用的是spring rmi,然后App Zone這塊全部是service layer, dao layer和數(shù)據(jù)庫打交道。

用戶這邊用的是.net,以ws和web zone連的。

時間一長,數(shù)據(jù)一多,就出問題了。

拿Loader Runner跑下來,發(fā)覺是Web Zone這塊,App Server已經(jīng)被用到極限了。因為客戶錢不多,所以當時的Web Zone是2臺服務(wù)器,且都是32位的,內(nèi)存不少,有8GB,測試下來后發(fā)覺cpu loader又不高,但是web server這邊的吞吐量始終上不去,且和.net客戶端那邊響應(yīng)越來越慢。

分析了一下原因:單臺tomcat能夠承受的最大負載已經(jīng)到頭了,單臺tomcat的吞吐量就這么點,還要負擔Guvnor的運行,Guvnor內(nèi)有數(shù)百條業(yè)務(wù)規(guī)則要執(zhí)行。

再看了一下其它方面的代碼、SQL調(diào)優(yōu)都已經(jīng)到了極限了,所以最后沒辦法,客戶又不肯拿錢投在內(nèi)存和新機器上或者是再買臺Weblogic,只能取舍一下,搞Tomcat集群了。

二、集群分類

Tomcat作集群的邏輯架構(gòu)是上面這樣的一張圖,關(guān)鍵是我們的production環(huán)境還需要規(guī)劃好我們的物理架構(gòu)。

2.1 橫向集群

比如說,有兩臺Tomcat,分別運行在2臺物理機上,好處是最大的即CPU擴展,內(nèi)存也擴展了,處理能力也擴展了。

2.2 縱向集群

即,兩個Tomcat的實例運行在一臺物理器上,充分利用原有內(nèi)存,CPU未得到擴展。

2.3 橫向還是縱向

一般來說,廣為人們接受的是橫向擴展的集群,可做大規(guī)模集群布署。但是我們這個case受制于客戶即:

ü   不會再投入新機器了

ü   不會增加內(nèi)存了

但是呢,通過壓力測試報告我們可知:

ü   原有TomcatServer的CPU Loader不高,在23%左右

ü   原有TomcatServer上有8GB內(nèi)存,而且是32位的,單臺Tomcat只使用了1800MB左右的內(nèi)存

ü   網(wǎng)絡(luò)流量不高,單塊千兆以太網(wǎng)卡完全可以處理掉

因此,我們只能做熊掌與魚不能兼得的事,即采用了:縱向集群。

2.4 Load Balance與High Available

ü   Load Balance

簡稱LB即負載均衡,相當于1000根線程每個集群節(jié)點:Node負責(zé)處理500個,這樣的效率是最高的。

ü   High Available

簡稱HA即高可用性,相當于1000根線程還是交給一臺機器去慢慢處理,如果這臺機器崩了,另一臺機器頂上。

三、集群架構(gòu)中需要解決的問題

集群規(guī)劃好了怎么分,這不等于就可以開始實現(xiàn)集群了,一旦你的系統(tǒng)實現(xiàn)了集群,隨之而來的問題就會出現(xiàn)了。

我們原有系統(tǒng)中有這樣幾個問題,在集群環(huán)境中是需要解決的,來看:

3.1 解決上傳文件同步的問題

集群后就是兩個Tomcat了,即和兩個線程讀同一個resource的問題是一樣的,還好,我們原有上傳文件是專門有一臺文件伺服器的,這個問題不大,兩個tomcat都往一臺file server里上傳,文件伺服器已經(jīng)幫我們解決了同名文件沖突的這個問題了,如果原先的做法是把文件上傳到Tomcat的目錄中,那問題就大了,來看:

集群環(huán)境中,對于用戶來說一切操作都是透明的,他也不知道我有幾個Tomcat的實例運行在那邊。

用戶一點上傳,可能上傳到了Tomcat2中,但是下次要顯示這個文件時,可能用到的是Tomcat1內(nèi)的jsp或者是class,對不對?

于是,因為你把圖片存在了Tomcat的目錄中,因此導(dǎo)致了Tomcat1在顯示圖片時,取不到Tomcat2目錄中存放的圖片。

因此我們在工程一開始就強調(diào)存圖片時要用一臺專門的文件服務(wù)器或者是FTP服務(wù)器來存,就是為了避免將來出現(xiàn)這樣的問題。

3.2 解決Quartz在集群環(huán)境中的同步問題

我們的系統(tǒng)用到一個Quartz(一個定時服務(wù)組件)來定時觸發(fā)一些自動機制,現(xiàn)在有了兩個Tomcat,粗想想每個Tomcat里運行自己的Quartz不就行了?

但是問題來了,如果兩個Quartz在同一時間都觸發(fā)了處理同一條定單,即該條定單會被處理兩邊。。。這不是影響效率和增加出錯機率了嗎?

因為本身Quartz所承受的壓力幾乎可以忽略不計的,它只是定時會觸發(fā)腳本去運行,關(guān)鍵在于這個定時腳本的同步性,一致性的問題上。

我們曾想過的解決方法:

我們可以讓一個Tomcat布署Quartz,另一個Tomcat里不布署Quartz

但這樣做的結(jié)果就是如果布署Quartz的這個Tomcat崩潰掉了,這個Quartz是不是也崩啦?

最后解決的辦法:

所以我們還是必須在兩臺Tomcat里布署Quartz,然后使用HA的原則,即一個Quartz在運行時,另一臺Quartz在監(jiān)視著,并且不斷的和另一個Quartz之間保持勾通,一旦運行著的Quartz崩掉了,另一個Quartz在指定的秒數(shù)內(nèi)起來接替原有的Quartz繼續(xù)運行,對于Quartz,我們同樣也是面臨著一個熊掌與魚不能皆得的問題了,Quartz本身是支持集群的,而它支持的集群方式正是HA,和我們想的是一致的。

具體Quartz是如何在集群環(huán)境下作布署的,請見我的另一篇文章:quartz在集群環(huán)境下的最終解決方案

解決了上述的問題后基本我們可以開始布署Tomcat這個集群了。

 


 

四、布署Tomcat集群

準備兩個版本一致的Tomcat,分別起名為tomcat1,tomcat2。

4.1 Apache中的配置

2  worker.properties文件內(nèi)容的修改

打開Apache HttpServer中的apache安裝目錄/conf/work.properties文件,大家還記得這個文件嗎?

這是原有文件內(nèi)容:

workers.tomcat_home=d:/tomcat2

workers.java_home=C:/jdk1.6.32

ps=/

worker.list=ajp13

worker.ajp13.port=8009

worker.ajp13.host=localhost

worker.ajp13.type=ajp13


現(xiàn)在開始改動成下面這樣的內(nèi)容(把原有的worker.properties中的內(nèi)容前面都加上#注釋掉):

#workers.tomcat_home=d:/tomcat2

#workers.java_home=C:/jdk1.6.32

#ps=/

#worker.list=ajp13

#worker.ajp13.port=8009

#worker.ajp13.host=localhost

#worker.ajp13.type=ajp13

worker.list = controller

#tomcat1

worker.tomcat1.port=8009       

worker.tomcat1.host=localhost

worker.tomcat1.type=ajp13

worker.tomcat1.lbfactor=1

#tomcat2

worker.tomcat2.port=9009     

worker.tomcat2.host=localhost

worker.tomcat2.type=ajp13

worker.tomcat2.lbfactor=1

#========controller========

worker.controller.type=lb

worker.controller.balance_workers=tomcat1,tomcat2

worker.lbcontroller.sticky_session=0

worker.controller.sticky_session_force=true

worker.connection_pool_size=3000

worker.connection_pool_minsize=50

worker.connection_pool_timeout=50000

 

上面的這些設(shè)置的意思用中文來表達就是:

ü   兩個tomcat,都位于localhost

ü   兩個tomcat,tomcat1用8009,tomcat2用9009與apache保持jk_mod的通訊

ü   不采用sticky_session的機制

sticky_session即:假設(shè)現(xiàn)在用戶正連著tomcat1,而tomcat1崩了,那么此時它的session應(yīng)該被復(fù)制到tomcat2上,由tomcat2繼續(xù)負責(zé)該用戶的操作,這就是load balance,此時這個用戶因該可以繼續(xù)操作。

如果你的sticky_session設(shè)成了1,那么當你連的這臺tomcat崩了后,你的操作因為是sticky(粘)住被指定的集群節(jié)點的,因此你的session是不會被復(fù)制和同步到另一個還存活著的tomcat節(jié)點上的。

ü   兩臺tomcat被分派到的任務(wù)的權(quán)重(lbfactor)為一致

你也可以設(shè)tomcat1 的worker.tomcat2.lbfactor=10,而tomcat2的worker.tomcat2.lbfactor=2,這個值越高,該tomcat節(jié)點被分派到的任務(wù)數(shù)就越多

2  httpd.conf文件內(nèi)容的修改

找到下面這一行:

Include conf/extra/httpd-ssl.conf

我們將它注釋掉,因為我們在集群環(huán)境中不打算采用https,如果采用是https也一樣,只是為了減省開銷(很多人都是用自己的開發(fā)電腦在做實驗哦)。

#Include conf/extra/httpd-ssl.conf

找到原來的“<VirtualHost>”段

改成如下形式:

<VirtualHost *>

DocumentRoot d:/www

<Directory "d:/www/cbbs">

    AllowOverride None

    Order allow,deny

          Allow from all

</Directory>

<Directory "d:/www/cbbs/WEB-INF">

         Order deny,allow

         Deny from all

</Directory>

ServerAdmin localhost

DocumentRoot d:/www/

ServerName shnlap93:80

DirectoryIndex index.html index.htm index.jsp index.action

ErrorLog logs/shsc-error_log.txt

CustomLog logs/shsc-access_log.txt common

 

JkMount /*WEB-INF controller

JkMount /*j_spring_security_check controller

JkMount /*.action controller

JkMount /servlet/* controller

JkMount /*.jsp controller

JkMount /*.do controller

JkMount /*.action controller

 

JkMount /*fckeditor/editor/filemanager/connectors/*.* controller

JkMount /fckeditor/editor/filemanager/connectors/* controller

</VirtualHost>

注意:

原來的JKMount *** 后的 ajp13變成了什么了?

controller

4.2 tomcat中的配置

可以拿原有的tomcat復(fù)制成另一個tomcat,分別為d:\tomcat, d:\tomcat2。

打開tomcat中的conf目錄中的server.xml,找到下面這行

1)

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

記得:

一定要把tomcat2中的這邊的”SHUTDOWN”port改成另一個端口號,兩個tomcat如果是在集群環(huán)境中,此處的端口號絕不能一樣。

2)找到

<Connector port="8080" protocol="HTTP/1.1"

確保tomcat2中此處的端口不能為8080,我們就使用9090這個端口吧

3)把兩個tomcat中原有的https的配置,整段去除

4)找到

<Connector port="8080" protocol="HTTP/1.1"

               URIEncoding="UTF-8"  minSpareThreads="25" maxSpareThreads="75"

               enableLookups="false" disableUploadTimeout="true" connectionTimeout="20000"

                   acceptCount="300"  maxThreads="300" maxProcessors="1000" minProcessors="5"

                   useURIValidationHack="false"

                             compression="on" compressionMinSize="2048"

                             compressableMimeType="text/html,text/xml,text/javascript,text/css,text/plain"

               redirectPort="8443" />

確保tomcat2中這邊的redirectPort為9443

5)找到

<Connector port="8009" protocol="AJP/1.3" redirectPort="8443"

改為:

<Connector port="8009" protocol="AJP/1.3" redirectPort="8443"

                    URIEncoding="UTF-8"  minSpareThreads="25" maxSpareThreads="75"

                            enableLookups="false" disableUploadTimeout="true" connectionTimeout="20000"

                            acceptCount="300"  maxThreads="300" maxProcessors="1000" minProcessors="5"

                            useURIValidationHack="false"

                                      compression="on" compressionMinSize="2048"

compressableMimeType="text/html,text/xml,text/javascript,text/css,text/plain"

   

/>

確保tomcat2server.xml中此處的8009被改成了9009且其它內(nèi)容與上述內(nèi)容一致(redirectPort不要忘了改成9443

6)找到

<Engine name="Standalone" defaultHost="localhost" jvmRoute="jvm1">      

改成

<!-- You should set jvmRoute to support load-balancing via AJP ie :

    <Engine name="Standalone" defaultHost="localhost" jvmRoute="jvm1">        

-->

<Engine name="Standalone" defaultHost="localhost" jvmRoute="tomcat1">

同時把tomcat2中此處內(nèi)容改成

   <!-- You should set jvmRoute to support load-balancing via AJP ie :

    <Engine name="Standalone" defaultHost="localhost" jvmRoute="jvm1">        

    -->

<Engine name="Standalone" defaultHost="localhost" jvmRoute="tomcat2">

7)

在剛才的

<Engine name="Standalone" defaultHost="localhost" jvmRoute="tomcat1">

的下面與在

<!-- The request dumper valve dumps useful debugging information about

           the request and response data received and sent by Tomcat.

           Documentation at: /docs/config/valve.html -->

      <!--

      <Valve className="org.apache.catalina.valves.RequestDumperValve"/>

      -->

之上,在這之間加入如下一大陀的東西:

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

                  channelSendOptions="6"> 

              <Manager className="org.apache.catalina.ha.session.BackupManager" 

                    expireSessionsOnShutdown="false" 

                    notifyListenersOnReplication="true" 

                    mapSendOptions="6"/> 

           <Channel className="org.apache.catalina.tribes.group.GroupChannel"> 

             <Membership className="org.apache.catalina.tribes.membership.McastService" 

                         bind="127.0.0.1" 

                         address="228.0.0.4" 

                         port="45564" 

                         frequency="500" 

                         dropTime="3000"/> 

             <Receiver className="org.apache.catalina.tribes.transport.nio.NioReceiver" 

                       address="auto" 

                       port="4001" 

                       selectorTimeout="100" 

                       maxThreads="6"/> 

             <Sender className="org.apache.catalina.tribes.transport.ReplicationTransmitter"> 

               <Transport className="org.apache.catalina.tribes.transport.nio.PooledParallelSender" timeout="60000"/>  

             </Sender> 

             <Interceptor className="org.apache.catalina.tribes.group.interceptors.TcpFailureDetector"/> 

             <Interceptor className="org.apache.catalina.tribes.group.interceptors.MessageDispatch15Interceptor"/> 

             <Interceptor className="org.apache.catalina.tribes.group.interceptors.ThroughputInterceptor"/> 

           </Channel> 

              <Valve className="org.apache.catalina.ha.tcp.ReplicationValve" 

                  filter=".*\.gif;.*\.js;.*\.jpg;.*\.png;.*\.htm;.*\.html;.*\.css;.*\.txt;"/> 

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

         </Cluster>

此處有一個Receiver port=”xxxx”,兩個tomcat中此處的端口號必須唯一,即tomcat中我們使用的是port=4001,那么我們在tomcat2中將使用port=4002

8)把系統(tǒng)環(huán)境變更中的CATALINA_HOME與TOMCAT_HOME這兩個變量去除掉

9)在每個tomcat的webapps目錄下布署同樣的一個工程,在布署工程前先確保你把工程中的WEB-INF\we b.xml文件做了如下的修改,在web.xml文件的最未尾即“</web-app>”這一行前加入如下的一行:

<distributable/>

使該工程中的session可以被tomcat的集群節(jié)點進行輪循復(fù)制。


4.3 啟動集群

好了,現(xiàn)在啟動tomcat1, 啟動tomcat2(其實無所謂順序的),來看效果:

分別訪問http://localhost:8080/cbbshttp://localhost:9090/cbbs

確保兩個tomcat節(jié)點都起來了,然后此時,我們啟動Apache

然后訪問直接用http://localhost/cbbs不加端口的形式訪問:

用sally/abcdefg登錄,瞧,應(yīng)用起來了。

然后我們拿另一臺物理客戶端,登錄這個web應(yīng)用,我們可以看到:

第一個tomcat正在負責(zé)處理我們第一次登錄的請求。

當有第二個HTTP請求時,另一個tomcat自動開始肩負起我們第二個HTTP請求了,這就是Load Balance。

    本站是提供個人知識管理的網(wǎng)絡(luò)存儲空間,所有內(nèi)容均由用戶發(fā)布,不代表本站觀點。請注意甄別內(nèi)容中的聯(lián)系方式、誘導(dǎo)購買等信息,謹防詐騙。如發(fā)現(xiàn)有害或侵權(quán)內(nèi)容,請點擊一鍵舉報。
    轉(zhuǎn)藏 分享 獻花(0

    0條評論

    發(fā)表

    請遵守用戶 評論公約

    類似文章 更多

    中文字幕亚洲视频一区二区| 欧美丝袜诱惑一区二区| 午夜福利网午夜福利网| 亚洲一区二区三区在线中文字幕| 久久成人国产欧美精品一区二区 | 国自产拍偷拍福利精品图片| 国产91色综合久久高清| 亚洲精品偷拍视频免费观看| 国产白丝粉嫩av在线免费观看| 亚洲少妇一区二区三区懂色| 狠狠做深爱婷婷久久综合| 国产精品免费福利在线| 97人妻人人揉人人躁人人| 日韩黄色一级片免费收看| 日韩一级一片内射视频4k| 中文字幕一区二区久久综合| 国产一级二级三级观看| 日本和亚洲的香蕉视频| 色婷婷亚洲精品综合网| 午夜亚洲少妇福利诱惑| 亚洲中文字幕高清视频在线观看| 精品推荐国产麻豆剧传媒| 好吊日成人免费视频公开| 欧美日韩国产精品黄片| 日本大学生精油按摩在线观看| 精品欧美日韩一二三区| 国产av一二三区在线观看| 欧美日韩成人在线一区| 日本精品免费在线观看| 搡老熟女老女人一区二区| 亚洲精品中文字幕无限乱码| 丰满熟女少妇一区二区三区| 国产女优视频一区二区| 中文字幕五月婷婷免费| 国产av精品高清一区二区三区| 少妇熟女亚洲色图av天堂| 国产精品成人又粗又长又爽| 又色又爽又无遮挡的视频| 午夜精品一区二区三区国产| 日韩一区二区免费在线观看| 91福利免费一区二区三区|