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

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

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

    David.Turing's blog

     

    將Spring用于高并發(fā)環(huán)境的隱憂

    最近協(xié)助一些BEA客戶做調(diào)優(yōu),他們使用了Spring,出現(xiàn)了各種各樣的性能問題,這些問題其實(shí)都是不容易重現(xiàn)的,其中,我自己捕獲了一些ThreadDump,并report了給Spring JIRA。這個(gè)Case的情況是:Spring會(huì)偶然出現(xiàn)CPU 100%的情況,WebLogic Server崩潰,我后來分析了線程Dump,覺得是一種Lock Contention的情形,幸好,Juergen Hoeller很快給我Fixed了這個(gè)Bug:
    http://jira.springframework.org/browse/SPR-4664

    使用Java編程的同學(xué)都建議Review一下,呵呵:

    這是2.5.4以前的代碼:

    /**
    *?Cache?of?TransactionAttributes,?keyed?by?DefaultCacheKey?(Method?+?target?Class).
    *?<p>As?this?base?class?is?not?marked?Serializable,?the?cache?will?be?recreated
    *?after?serialization?-?provided?that?the?concrete?subclass?is?Serializable.
    */
    final ?Map?attributeCache? = ? new ?HashMap();

    /**
    *?Determine?the?transaction?attribute?for?this?method?invocation.
    *?<p>Defaults?to?the?class's?transaction?attribute?if?no?method?attribute?is?found.
    *?
    @param ?method?the?method?for?the?current?invocation?(never?<code>null</code>)
    *?
    @param ?targetClass?the?target?class?for?this?invocation?(may?be?<code>null</code>)
    *?
    @return ?TransactionAttribute?for?this?method,?or?<code>null</code>?if?the?method
    *?is?not?transactional
    */
    public ?TransactionAttribute?getTransactionAttribute(Method?method,?Class?targetClass)?{
    // ?First,?see?if?we?have?a?cached?value.
    Object?cacheKey? = ?getCacheKey(method,?targetClass);
    synchronized ?( this .attributeCache)?{
    Object?cached?
    = ? this .attributeCache.get(cacheKey);
    if ?(cached? != ? null )?{
    // ?Value?will?either?be?canonical?value?indicating?there?is?no?transaction?attribute,
    // ?or?an?actual?transaction?attribute.
    if ?(cached? == ?NULL_TRANSACTION_ATTRIBUTE)?{
    return ? null ;
    }
    else ?{
    return ?(TransactionAttribute)?cached;
    }
    }
    else ?{
    // ?We?need?to?work?it?out.
    TransactionAttribute?txAtt? = ?computeTransactionAttribute(method,?targetClass);
    // ?Put?it?in?the?cache.
    if ?(txAtt? == ? null )?{
    this .attributeCache.put(cacheKey,?NULL_TRANSACTION_ATTRIBUTE);
    }
    else ?{
    if ?(logger.isDebugEnabled())?{
    logger.debug(
    " Adding?transactional?method?[ " ? + ?method.getName()? + ? " ]?with?attribute?[ " ? + ?txAtt? + ? " ] " );
    }
    this .attributeCache.put(cacheKey,?txAtt);
    }
    return ?txAtt;
    }
    }
    }


    這是2.5.4 Fixed后的代碼:

    ???? /**
    ?????*?Cache?of?TransactionAttributes,?keyed?by?DefaultCacheKey?(Method?+?target?Class).
    ?????*?<p>As?this?base?class?is?not?marked?Serializable,?the?cache?will?be?recreated
    ?????*?after?serialization?-?provided?that?the?concrete?subclass?is?Serializable.
    ?????
    */
    ????
    final ?Map?attributeCache? = ?CollectionFactory.createConcurrentMapIfPossible( 16 );


    ????
    /**
    ?????*?Determine?the?transaction?attribute?for?this?method?invocation.
    ?????*?<p>Defaults?to?the?class's?transaction?attribute?if?no?method?attribute?is?found.
    ?????*?
    @param ?method?the?method?for?the?current?invocation?(never?<code>null</code>)
    ?????*?
    @param ?targetClass?the?target?class?for?this?invocation?(may?be?<code>null</code>)
    ?????*?
    @return ?TransactionAttribute?for?this?method,?or?<code>null</code>?if?the?method
    ?????*?is?not?transactional
    ?????
    */
    ????
    public ?TransactionAttribute?getTransactionAttribute(Method?method,?Class?targetClass)?{
    ????????
    // ?First,?see?if?we?have?a?cached?value.
    ????????Object?cacheKey? = ?getCacheKey(method,?targetClass);
    ????????Object?cached?
    = ? this .attributeCache.get(cacheKey);
    ????????
    if ?(cached? != ? null )?{
    ????????????
    // ?Value?will?either?be?canonical?value?indicating?there?is?no?transaction?attribute,
    ????????????
    // ?or?an?actual?transaction?attribute.
    ???????????? if ?(cached? == ?NULL_TRANSACTION_ATTRIBUTE)?{
    ????????????????
    return ? null ;
    ????????????}
    ????????????
    else ?{
    ????????????????
    return ?(TransactionAttribute)?cached;
    ????????????}
    ????????}
    ????????
    else ?{
    ????????????
    // ?We?need?to?work?it?out.
    ????????????TransactionAttribute?txAtt? = ?computeTransactionAttribute(method,?targetClass);
    ????????????
    // ?Put?it?in?the?cache.
    ???????????? if ?(txAtt? == ? null )?{
    ????????????????
    this .attributeCache.put(cacheKey,?NULL_TRANSACTION_ATTRIBUTE);
    ????????????}
    ????????????
    else ?{
    ????????????????
    if ?(logger.isDebugEnabled())?{
    ????????????????????logger.debug(
    " Adding?transactional?method?[ " ? + ?method.getName()? + ? " ]?with?attribute?[ " ? + ?txAtt? + ? " ] " );
    ????????????????}
    ????????????????
    this .attributeCache.put(cacheKey,?txAtt);
    ????????????}
    ????????????
    return ?txAtt;
    ????????}
    ????}


    但是2.5.4 snapshot是未經(jīng)很好測(cè)試的版本,客戶一般不太敢用。
    我不知道其實(shí)有多少客戶真正地把Spring投入到高并發(fā)性環(huán)境下使用,
    如果有,他們應(yīng)該會(huì)能碰到我所碰到的情形。

    posted on 2008-04-19 09:47 david.turing 閱讀(11106) 評(píng)論(21)  編輯  收藏 所屬分類: BEA新聞?lì)l道

    評(píng)論

    # re: 將Spring用于高并發(fā)環(huán)境的隱憂[未登錄] 2008-04-19 10:03 BeanSoft

    沒錯(cuò),我們以前的公司也是Weblogic + Hibernate,出了性能問題了,雖然調(diào)整解決了,但不管怎么說,因?yàn)檫@些開源軟件之前開發(fā)的時(shí)候并沒有考慮高并發(fā)和集群的情況,還是比較容易出現(xiàn)問題的,尤其是沒有經(jīng)過嚴(yán)格的壓力測(cè)試。我個(gè)人認(rèn)為,目前做的比較好的軟件,依然是商業(yè)的。  回復(fù)  更多評(píng)論   

    # re: 將Spring用于高并發(fā)環(huán)境的隱憂 2008-04-19 10:56 flyisland

    1. 的確,許多開源軟件在版本發(fā)布之前是否有能力去做高并發(fā)壓力測(cè)試,值得懷疑
    2. 我想,看到david這次發(fā)現(xiàn)的問題,用戶更應(yīng)該當(dāng)心的是下次如果某個(gè)開源產(chǎn)品出了問題怎么辦。
    3. 不過目前來說是,不是“用不用開源的問題”(可以是一定要用),而是“用了開源怎么辦”的問題。所以這是開源商業(yè)模式的一個(gè)機(jī)會(huì),比如david就可以去做開源調(diào)優(yōu)的服務(wù)支持了,哈
    4. 這篇blog在我的firefox 3.0b5下排版混亂,不得不到IE下面來留言  回復(fù)  更多評(píng)論   

    # re: 將Spring用于高并發(fā)環(huán)境的隱憂[未登錄] 2008-04-19 17:43 af

    我一直認(rèn)為開源代碼是用來學(xué)習(xí)的,實(shí)際項(xiàng)目中還是不要用的好。  回復(fù)  更多評(píng)論   

    # re: 將Spring用于高并發(fā)環(huán)境的隱憂[未登錄] 2008-04-19 21:08 lj

    我很想知道在spring1.2.9或spring2.0.8有沒有這個(gè)問題  回復(fù)  更多評(píng)論   

    # re: 將Spring用于高并發(fā)環(huán)境的隱憂 2008-04-20 13:24 GoGo

    @flyisland
    FireFox不僅僅3.0亂,2.0也亂,于是IE留言之。  回復(fù)  更多評(píng)論   

    # re: 將Spring用于高并發(fā)環(huán)境的隱憂[未登錄] 2008-04-20 18:29 Roy

    @af
    你能擔(dān)保自己寫的就可以解決掉所有問題?  回復(fù)  更多評(píng)論   

    # re: 將Spring用于高并發(fā)環(huán)境的隱憂 2008-04-21 18:05 雨奏

    我用FireFox 2.0.0.13瀏覽本文再正常不過了  回復(fù)  更多評(píng)論   

    # re: 將Spring用于高并發(fā)環(huán)境的隱憂 2008-04-21 21:44 YuLimin

    new HashMap();

    這個(gè)本來就不是線程安全的東東。。。
    在寫高并發(fā)程序的時(shí)候用腳后腳想想就知道了。。。:)  回復(fù)  更多評(píng)論   

    # re: 將Spring用于高并發(fā)環(huán)境的隱憂 2008-04-22 10:16 david.turing

    說的沒錯(cuò),任何優(yōu)秀的產(chǎn)品都會(huì)有Bug,但除非用的場(chǎng)景足夠多和復(fù)雜,否則某些嚴(yán)重的Bug還是會(huì)隱藏的很深。  回復(fù)  更多評(píng)論   

    # re: 將Spring用于高并發(fā)環(huán)境的隱憂[未登錄] 2008-04-22 12:36 allenny

    你們以為Websphere,Weblogic就不會(huì)有這樣的問題了嗎??  回復(fù)  更多評(píng)論   

    # re: 將Spring用于高并發(fā)環(huán)境的隱憂 2008-04-22 17:41 MarkDong

    @af
    呵呵,我是不同意最好不用開源軟件的觀點(diǎn)。商業(yè)軟件也同樣會(huì)有問題,只不過可能隱藏的更深而已。自己寫就更不用說了,重復(fù)造輪子不說,也許還造的不如人家的圓。
      回復(fù)  更多評(píng)論   

    # re: 將Spring用于高并發(fā)環(huán)境的隱憂 2008-04-22 17:49 邢紅瑞

    這算是歷史的遺留問題吧,spring應(yīng)該使用java5的api重寫了,至少還和guice有一。,開源問題太多了,以前經(jīng)常和spring team的人扯皮一些小問題,不過我寫代碼的質(zhì)量遠(yuǎn)不如他們寫的  回復(fù)  更多評(píng)論   

    # re: 將Spring用于高并發(fā)環(huán)境的隱憂 2008-04-23 11:01 david.turing

    邢總說對(duì)了,佩服。不過,廠家的支持會(huì)讓Spring更適用于商業(yè)化。未來的WebLogic版本(Essex),應(yīng)該對(duì)Spring有較大的優(yōu)化,包括:

    1, 基于Spring的部署方式實(shí)現(xiàn)本地WLS部署,我們可以將Spring Module實(shí)現(xiàn)weblogic.application.Module接口,即可讓Spring模塊享受WebLogic的2階段部署的特性。

    2, 一些預(yù)配置的Beans能夠無需Spring配置聲明即可注入到Spring應(yīng)用中,applicationContext看上去會(huì)簡(jiǎn)潔很多

    3, 為Beans提供scope,比如ClusteringScope,以便支持集群技術(shù)

    4, WebLogic Consle展示Spring應(yīng)用的RuntimeMBeans

    5, 9.2之后WLDF可以用于上面的RuntimeMBeans,可以定期抓取Runtime信息了

    6, Spring應(yīng)用默認(rèn)支持OpenJPA作為持久層支持,當(dāng)然,KODO、Hibernate切換也是簡(jiǎn)單的
      回復(fù)  更多評(píng)論   

    # re: 將Spring用于高并發(fā)環(huán)境的隱憂 2008-04-23 13:34 MyUser

    修正后的代碼,滿足不了之前的并發(fā)需求吧??  回復(fù)  更多評(píng)論   

    # re: 將Spring用于高并發(fā)環(huán)境的隱憂 2008-04-23 13:59 Qulong

    是呀,第一段代碼能夠保證同一個(gè)TransactionAttribute只被創(chuàng)建一次,而第二段代碼無法做到吧?有可能同一個(gè)TransactionAttribute被創(chuàng)建多次,然后被put到map中覆蓋。  回復(fù)  更多評(píng)論   

    # re: 將Spring用于高并發(fā)環(huán)境的隱憂[未登錄] 2008-04-24 13:05 david.turing

    1.5的concurrent hashmap產(chǎn)生的用途就是為了hashmap同步  回復(fù)  更多評(píng)論   

    # re: 將Spring用于高并發(fā)環(huán)境的隱憂 2008-04-24 18:55 Qulong

    @david.turing

    確實(shí)是同步,但是它只能保證多個(gè)線程在同時(shí)操作Map時(shí)保證同步,但是上面的第一段代碼是分兩步來操作Map的  回復(fù)  更多評(píng)論   

    # re: 將Spring用于高并發(fā)環(huán)境的隱憂[未登錄] 2008-05-18 17:59 wfeng007

    朋友是bea的? 。。。 我們公司用了spring作了框架 然后再weblogic中 redeploy的話似乎spring的context沒有被銷毀。 我們已經(jīng)在listener中調(diào)用了context的關(guān)閉銷毀方法但是似乎沒啥效果。。。 redeploy多次后java heap就不行了。。。 不知道其他地方有沒有這種情況?????  回復(fù)  更多評(píng)論   

    # re: 將Spring用于高并發(fā)環(huán)境的隱憂 2008-06-14 09:49 david.turing

    典型的部署期泄露,這種有可能是Spring的Bug,它可能沒有正確實(shí)現(xiàn)J2EE的context銷毀接口。  回復(fù)  更多評(píng)論   

    # re: 將Spring用于高并發(fā)環(huán)境的隱憂 2009-06-17 14:14 ufo

    (web server軟件)UFO不會(huì)出現(xiàn)一個(gè)字節(jié)的內(nèi)存泄漏和一個(gè)線程的不能回收,使用UFO做Web Server的好處是網(wǎng)站能做得很穩(wěn)定,永遠(yuǎn)也不會(huì)自己down掉;UFO在托管機(jī)房丟包率很高、遭受Hacker攻擊、互聯(lián)網(wǎng) 骨干網(wǎng)被黑等惡劣的環(huán)境條件下仍然能很好地運(yùn)行;UFO在對(duì)付Hacker方面(防Hacker弄down和Hacker抓取不該訪問的資源)也有足夠措施。
    另外,UFO幾乎不會(huì)進(jìn)行垃圾回收,消耗CPU很少,在普通的PC Server上用UFO運(yùn)行網(wǎng)站,平時(shí)CPU占用率<0.1%,最多時(shí)也不會(huì)超 過5%。您知道,JVM的垃圾回收會(huì)導(dǎo)致大量的運(yùn)算,消耗很多CPU,從而導(dǎo)致Server的負(fù)載能力和響應(yīng)速度下降。UFO在對(duì)象管理方面采 用了很好的機(jī)制和算法,做得很出色。用UFO運(yùn)行網(wǎng)站,可以一直保證高負(fù)載能力,快速的響應(yīng)速度和低CPU消耗。發(fā)布網(wǎng)址:www.gm365.com
      回復(fù)  更多評(píng)論   

    # re: 將Spring用于高并發(fā)環(huán)境的隱憂[未登錄] 2014-05-14 17:12 南云

    @flyisland
    我也混亂了,ff29.  回復(fù)  更多評(píng)論   

    導(dǎo)航

    統(tǒng)計(jì)

    常用鏈接

    留言簿(110)

    我參與的團(tuán)隊(duì)

    隨筆分類(126)

    隨筆檔案(155)

    文章分類(9)

    文章檔案(19)

    相冊(cè)

    搜索

    積分與排名

    最新隨筆

    最新評(píng)論

    閱讀排行榜

    評(píng)論排行榜

    主站蜘蛛池模板: 暖暖免费日本在线中文| 免费一级毛片在线播放视频免费观看永久| 亚洲一欧洲中文字幕在线| 亚洲 日韩经典 中文字幕| 老司机午夜在线视频免费| 九九全国免费视频| 日日麻批免费40分钟无码| 日韩欧美一区二区三区免费观看 | 日韩精品无码永久免费网站| 国产黄色免费观看| **毛片免费观看久久精品| 女人18毛片免费观看| 亚洲XX00视频| 亚洲精品美女视频| 国产精品亚洲专区无码牛牛| 国产午夜成人免费看片无遮挡| 无码国产精品一区二区免费式影视 | 国产精品亚洲а∨无码播放| 亚洲一级特黄大片无码毛片| 亚洲精品美女久久久久99| 亚洲成人免费网址| 水蜜桃视频在线观看免费| 亚洲免费在线视频| 色视频色露露永久免费观看| 亚洲中文字幕无码一区| 亚洲国产精品成人综合久久久| 国产亚洲视频在线| 2022久久国产精品免费热麻豆| 国产无遮挡吃胸膜奶免费看视频| 日韩高清免费在线观看| 亚洲精品乱码久久久久久中文字幕| 亚洲不卡在线观看| 丝瓜app免费下载网址进入ios | 人妻丰满熟妇无码区免费 | 亚洲日韩精品一区二区三区| 国产婷婷综合丁香亚洲欧洲| 国产精品hd免费观看| 欧美男同gv免费网站观看| 中文字幕亚洲无线码a| 亚洲精品无码中文久久字幕| 免费91麻豆精品国产自产在线观看|