<rt id="bn8ez"></rt>
<label id="bn8ez"></label>

  • <span id="bn8ez"></span>

    <label id="bn8ez"><meter id="bn8ez"></meter></label>

    Sky's blog

    我和我追逐的夢

    常用鏈接

    統(tǒng)計

    其他鏈接

    友情鏈接

    最新評論

    glassfish下的性能調(diào)優(yōu):令人極度困惑的Max Connections參數(shù)



    近日做性能調(diào)優(yōu),主要是針對web service,運行于glassfish之上。前期通過修改優(yōu)化代碼,基本搞定一些阻礙性能的問題,主要是代碼層次的不合理。

    之后還是發(fā)現(xiàn)性能上不去,而且表現(xiàn)明顯不合理:tps只能達到2k,而服務(wù)器cpu只停留在10%附近,壓力測試的客戶端cpu也不高,20%-30%吧。反復(fù)thread dump后檢查無果,不論是服務(wù)器端還是客戶端的工作線程都算正常,沒有發(fā)現(xiàn)線程/鎖之類的問題。分析發(fā)現(xiàn)主要的癥狀是服務(wù)器端和客戶端都壓不上去,服務(wù)器端工作線程很空閑,客戶端則忙于socket通訊及等待服務(wù)器返回。

    于是開始懷疑問題可能出現(xiàn)在網(wǎng)絡(luò)通訊上,一邊跑壓力測試,一邊用netstat命令查看socket狀態(tài),很快發(fā)現(xiàn)問題,有大量多大數(shù)k的socket連接出現(xiàn)。感覺不正常,因為應(yīng)該用的是長連接,按說正常情況socket連接數(shù)應(yīng)該近似等于并發(fā)的線程數(shù)。測試工具為客戶端soapUI,直接連接到運行在glassfish上的web service. soapUI是支持長連接的,glassfish也是支持長連接的。

    做了一下驗證,只開一個工作線程,跑了幾個請求,通過抓包工具發(fā)現(xiàn)的確是只建立了一個連接,后面的請求都是跑在同一個socket連接上。試著增加http header Connection: Keep-Alive,發(fā)現(xiàn)和默認(rèn)沒有這個參數(shù)時表現(xiàn)一致。故意設(shè)置為Connection: close,則每次請求都是重新建立連接。因此排除http 是短連接的問題。

    繼續(xù)回頭看socket狀態(tài),發(fā)現(xiàn)出現(xiàn)的多達數(shù)k的socket有很多都是處于TIME_WAIT狀態(tài),只有少數(shù)處于正常的ESTABLISHED狀態(tài)。TIME_WAIT意味著是服務(wù)器端主動要求close socket的,在長連接并且不斷有請求的情況下,服務(wù)器為什么會如此頻繁的關(guān)閉連接呢?

    試著只開一個壓力測試的工作線程,tps大概100+的情況下看服務(wù)器端的socket情況,很快發(fā)現(xiàn)問題:先是建立一個socket,ESTABLISHED狀態(tài),然后大概2s左右重新建立一個新的socket,原有的這個狀態(tài)轉(zhuǎn)為TIME_WAIT,之后每隔2-3秒左右,都會有上訴的情況出現(xiàn)----原有連接被放棄,重建新的連接。這樣socket就成了1 + n的狀態(tài):1個ESTABLISHED + n個TIME_WAIT,一定時間后TIME_WAIT的socket開始逐個消失。

    將壓力測試的工作線程加到100之后,上述情況開始變的極度激烈,大量TIME_WAIT的socket被建立,數(shù)目直接上到1w,2w乃至36000,之后開始偶爾報錯說無法連接。

    問題基本就定位在這里了,為什么明明建立好了長連接,服務(wù)器端確總是會不斷的關(guān)閉這些長連接導(dǎo)致無數(shù)的TIME_WAIT?

    試著查找資料,調(diào)整參數(shù)并反復(fù)測試,最終發(fā)現(xiàn)和兩個參數(shù)有關(guān):

    1. http.maxConnections

    glassfish官網(wǎng)說明
    https://metro.dev.java.net/guide/HTTP_Persistent_Connections__keep_alive_.html

    HTTP keep-alive behavior can be controlled by the http.keepAlive (defaulttrue) and http.maxConnections (default5) system properties. For more information, see Networking Properties

    進入http://java.sun.com/j2se/1.5.0/docs/guide/net/properties.html 頁面查看相關(guān)的系統(tǒng)屬性,最后聚焦在http.maxConnections :

    http.maxConnections (default5)
    If HTTP keep
    -alive is enabled, this value is the number of idle connections that will be simultaneously kept alive, per-destination.

    從說明上看,應(yīng)該是max idle connection,和命名maxConnections不大符合,maxConnections感覺像是最多容許開這么多長連接。考慮默認(rèn)值為5明顯應(yīng)該是max idle connection。

    后面的測試驗證,就是這個參數(shù)非常的致命,在修改為200之后,tps直接 *2。

    返回來分析這個參數(shù),默認(rèn)最多容許有5個空閑長連接。考慮到100個工作線程,正常應(yīng)該長連接數(shù)目也在100附近,考慮每次請求都要先申請一個連接,用完之后再放回,100個工作線程同時操作,很有可能同時將超過5個的連接返還給連接池。如果服務(wù)器簡單的判斷說多于5個連接然后就立即close并釋放長連接,那么就會出現(xiàn)一方面連續(xù)釋放長連接,一方面因為連接數(shù)不夠不停的創(chuàng)建新的長連接。

    換言之,當(dāng)100個線程并發(fā)在連接池中進行申請連接/返還連接的過程中,連接池內(nèi)的可用連接數(shù)是時刻變化的,實際的數(shù)目會有大的波動。而默認(rèn)的最大空閑參數(shù)過小(默認(rèn)才5)使得這個波動有極大的幾率突破限制,從而造成連接池進行不必要的釋放所謂過多的“空閑”連接。

    glassfish中,對于這個參數(shù)的修改,非常簡單,在jvm參數(shù)中增加新的一項"-Dhttp.maxConnections=250",重啟即可。


    2. maxKeepAliveRequests

        前面的調(diào)整,雖然達到了tps * 2的良好效果,但是使用netstat查看socket時,還是發(fā)現(xiàn)有非常多的TIME_TIME狀態(tài)的socket,只是數(shù)目沒有原來那么直上3w那么夸張,大概穩(wěn)定在2000附近。

        看來還是有其他的原因的,重新回頭看當(dāng)時只開一個線程測試的場景:一個線程連續(xù)提交,會出現(xiàn)1個ESTABLISHED + n個TIME_WAIT。

        感覺上像是一個長連接上只要跑一段時間或者一定的請求,socket就會被服務(wù)器端關(guān)閉。修改測試方法,讓每次請求之間等待一段時間,降低tps,發(fā)現(xiàn)關(guān)閉連接的時間間隔大為增加。

        后來google到maxKeepAliveRequests這個參數(shù),對于tomcat,apache等服務(wù)器都有支持,解釋如下:

    maxKeepAliveRequests:
    The maximum number of HTTP requests which can be pipelined until the connection is closed by the server. Setting 
    this attribute to 1 will disable HTTP/1.0 keep-alive, as well as HTTP/1.1 keep-alive and pipelining. Setting this to -1 will allow an unlimited amount of pipelined or keep-alive HTTP requests. If not specified, this attribute is set to 100.


        隨即google到grizzly也有類似的系統(tǒng)參數(shù)可以設(shè)置這個maxKeepAliveRequests

    -Dcom.sun.enterprise.web.connector.grizzly.maxKeepAliveRequests=-1

        使用關(guān)鍵字"glassfish maxKeepAliveRequests",發(fā)現(xiàn)glassfish還是有支持這個參數(shù)的,但是找不到具體設(shè)置的方法。后來在glassfish的控制臺-> Configuration -> http service -> Keep Alive 下
    發(fā)現(xiàn)了一個Max Connections參數(shù),默認(rèn)值250,解釋為"Maximum number of connections in the Keep-Alive mode",和maxKeepAliveRequests似乎完全不是一回事。

        但是試著將這個參數(shù)修改為2500之后,非常驚訝的發(fā)現(xiàn),見效了!單線程測試長連接釋放的速度明顯放慢,大體算了一下時間間隔和tpc,無論是之前的默認(rèn)250還是現(xiàn)在新修改的2500都和測試結(jié)果
    很合拍。開到100個線程測試,發(fā)現(xiàn)原有的2000附近的TIME_WAIT連接被降低到了大概300附近,明顯改觀。后面發(fā)現(xiàn),可以用下面的參數(shù)直接設(shè)置:
    asadmin set --user admin --passwordfile passwords.txt --port 47348 "server.http-service.keep-alive.max-connections=2500"

        這里就有點奇怪了,從測試結(jié)果來看,這個參數(shù)的表現(xiàn)和maxKeepAliveRequests參數(shù)的功能是一致的,但是這個參數(shù)明明叫做Max Connections,而且旁邊的注釋"Maximum number of connections in the Keep-Alive mode"也證明了這點。很令人費解,并且這里的Max Connections前面的http.maxConnections有重名嫌疑而作用明顯不同。

    下面是一個簡單的列表,其他情況相同下,分別修改者兩個參數(shù)前后的對比:

    keep-alive.max-connections   http.maxConnections     test result     
    250                                      5                                  TPS=650-700   TIME-WAIT=32600       
    250                                      200                              TPS=1200        TIME-WAIT=300        
    2500                                    5                                  TPS=650-700   TIME-WAIT=32600    
    2500                                    200                              TPS=1200        TIME-WAIT=300  

        最終的結(jié)果,還是比較理想的,修改了上述兩個參數(shù)之后,cpu終于壓上去了,tps也有了巨大的提升,而且TIME_WAIT的連接也大為減少。但是這兩個參數(shù)的名稱,注釋和實際測試中的效果,都有名不副實的感覺,令人困惑。

    后續(xù)更新:
    1. 經(jīng)同事提醒,有新的發(fā)現(xiàn),maxKeepAliveRequests得以確認(rèn)

        http://docs.sun.com/app/docs/doc/820-4343/abefk?a=view
         這里是sun的官方資料,其中對
    Max Connections 參數(shù)解釋如下:
    Max Connections

    Max Connections controls the number of requests that a particular client can make over a keep
    -alive connection. The range is any positive integer, and the default is 256.

    Adjust 
    this value based on the number of requests a typical client makes in your application. For best performance specify quite a large number, allowing clients to make many requests. 

        因此可見這個"max connections"參數(shù)的確就是通常意義上的"maxKeepAliveRequests"。這里sun的命名不大合適,容易造成誤解。

    posted on 2010-04-29 17:10 sky ao 閱讀(6765) 評論(1)  編輯  收藏 所屬分類: web service

    評論

    # re: glassfish下的性能調(diào)優(yōu):令人極度困惑的Max Connections參數(shù) 2010-04-30 12:02 99書城

    案件快速的既驕傲  回復(fù)  更多評論   

    主站蜘蛛池模板: 在线免费一区二区| 亚洲大片在线观看| 久久一本岛在免费线观看2020| 久久久久国色AV免费看图片| 亚洲AV无码片一区二区三区 | 国产一精品一av一免费爽爽| 亚洲国产成人精品无码区在线秒播 | 成人a免费α片在线视频网站| 亚洲国产成人手机在线电影bd| 亚洲第一网站免费视频| 亚洲av第一网站久章草| 亚洲成av人片天堂网| 久久伊人免费视频| 精品久久久久亚洲| gogo全球高清大胆亚洲| 91香蕉在线观看免费高清| 亚洲视频免费观看| 亚洲国产一成久久精品国产成人综合| 免费又黄又爽又猛大片午夜 | 黄色毛片免费在线观看| 亚洲av日韩av不卡在线观看 | 亚洲热线99精品视频| 最新欧洲大片免费在线| a在线观看免费视频| 亚洲天堂在线播放| 免费真实播放国产乱子伦| 无遮免费网站在线入口| 成人爽a毛片免费| 免费观看四虎精品成人| 亚洲精品第一国产综合亚AV| 婷婷亚洲综合五月天小说| 中文字幕久久亚洲一区| 国产精品久免费的黄网站| 韩国免费一级成人毛片| 精品国产日韩亚洲一区在线| 亚洲电影在线播放| 亚洲成色999久久网站| 亚洲色精品88色婷婷七月丁香| 最刺激黄a大片免费网站| 中文字幕在线免费播放| 免费一级全黄少妇性色生活片 |