JVM調優的正確姿勢

本文簡單說一說JVM應如何調優。

Java語言本身的成功,除了天時地利人和,JVM功不可沒。

毫不誇張地說,JVM是現代軟件工程最成功的案例之一。它規模龐大,代碼極其複雜,但運行極其穩定可靠,所以,許多廠商的核心業務系統,纔敢放心地用Java編寫,運行在JVM之上。

因爲JVM自帶GC,又有無數可以微調的參數,所以,JVM調優,現在已經被當作Java面試的必考知識點,精通JVM調優參數的童鞋,可以冠名微操小王子。

寫了這麼多年的Java程序,很遺憾,我迄今爲止只會用兩個參數:XMS和XMX,能正確寫出如下啓動腳本:

java -Xms1g -Xmx2g -jar abc.jar

如果-server也算的話,一共會三,估計面試通過的概率不大。

我承認我對JVM調優幾乎一無所知,原因在於,還沒有遇到過性能問題必須通過JVM調優才能解決。

我發現喜歡研究JVM調優的兩類人:

  • 準備面試的;

  • 自己寫的爛代碼想甩鍋給JVM的。

絕大多數情況下,如果程序出現了性能問題,比如TPS上不去,內存撐爆了,最好自己冷靜一下,先監控一下自己程序的日誌和性能數據,如果這兩個都沒有,就一口咬定JVM有問題,有問題的很可能不是JVM,而是態度。

這並不是說JVM不會出問題,或者說JVM就肯定沒有bug,而是說,軟件領域,bug能不能儘可能地被發現然後修復,很大程度上取決於用的人是否足夠多。這個世界上用JVM的人多還是用自己寫的程序的人多?很明顯,能被某個人發現的JVM的bug可能性很低,尤其是公司線上運行的JVM並不會追求最新版本。

那麼JVM正確的調優方式是啥?我個人推薦四步走:

  1. 記錄好日誌;
  2. 對程序做好性能監控;
  3. 根據日誌和性能監控數據修改程序;
  4. 使用專業工具通過不同的JVM參數進行壓測並獲得最佳配置。

根據我的個人經驗,走完前三步,就可以高質量交付並下班回家了,第四步那是在有摸魚時間的情況下才做。

這麼多年我一共遇到過兩次因爲JVM參數引發的問題:

一次是某公司的超大型Java程序,導致PermGen OutOfMemoryError,那是JDK 1.6平臺,原因很簡單,編寫的Java類數量太多了,撐爆了默認的128M的PermGen。解決方法也很簡單,改成更大的512M(參數叫啥已經忘了,因爲新版JVM沒有PermGen限制了)。但是根本問題不是出在JVM,而是代碼太垃圾,Java類的數量超多造成的。

另一次是因爲TPS超高引起內存不足崩潰,但實際上內存有32G非常大,分配給JVM有30G,不可能用完。現實情況是EC2直接被幹掉連日誌都看不到了。如果手動把TPS降下來(每次sleep 1ms),就能以一定概率成功啓動。後諮詢AWS技術支持發現,原來是Kafka這貨爲了提高速度,用了大量的堆外內存結果在高TPS下爆了。解決方法也很簡單,把JVM內存限制在系統內存的一半,給操作系統留出足夠的內存。這次根本問題是代碼性能太高但錯誤地設定了XMS和XMX造成的。

所以,絕大部分情況下,並不需要特意去調優JVM,因爲那是最後一步的優化手段。即使真的需要,到時候再研究也不遲,因爲時間是寶貴的,在解決自己程序的性能問題之前,不必在意JVM的性能。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章