深刻理解JVM虛擬機12:JVM性能管理神器VisualVM介紹與實戰

微信公衆號【Java技術江湖】一位阿里 Java 工程師的技術小站。做者黃小斜,專一 Java 相關技術:SSM、SpringBoot、MySQL、分佈式、中間件、集羣、Linux、網絡、多線程,偶爾講點Docker、ELK,同時也分享技術乾貨和學習經驗,致力於Java全棧開發!(關注公衆號後回覆」Java「便可領取 Java基礎、進階、項目和架構師等免費學習資料,更有數據庫、分佈式、微服務等熱門技術學習視頻,內容豐富,兼顧原理和實踐,另外也將贈送做者原創的Java學習指南、Java程序員面試指南等乾貨資源)

1、VisualVM是什麼?

    VisualVM是一款免費的JAVA虛擬機圖形化監控分析工具。html

    1.  擁有圖形化的監控界面。
    2. 提供本地、遠程的JVM監控分析功能。
    3. 是一款免費的JAVA工具。
    4. VisualVM擁有豐富的插件支持。java

2、如何獲取VisualVM?

    VisualVM官方網站:http://visualvm.java.net/程序員

    VisualVM各版本下載頁面: http://visualvm.java.net/releases.html面試

     下載VisualVM時也應該注意,不一樣的JDK版本對應不一樣版本的VisualVM,具體根據安裝的JDK版原本下載第一的VisualVM。數據庫

3、獲取那個版本?

       下載版本參考:[](http://blog.csdn.net/chwshuan...Java虛擬機性能管理神器 - VisualVM(4) - JDK版本與VisualVM版本對應關係安全

備註:下列表中顯示1.3.6版本只適合JDK7和JDK8,但是我用1.3.6版仍是能夠監控JDK1.6_45的版本。性能優化

4、VisualVM能作什麼?

1. 顯示JAVA應用程序配置和運行時環境。

顯示JAVA應用程序JVM參數,系統屬性,JVM的信息和運行環境。服務器

2. 顯示本地和遠程JAVA應用程序運行狀態。

能夠鏈接到遠程服務器上運行的JAVA應用程序,監控應用程序的運行狀態。微信

3. 監控應用程序的性能消耗。

能夠監控到應用程序熱點方法的執行單次時間、總耗時、耗時佔比。網絡

4. 顯示應用程序內存分配,顯示分析堆信息。

顯示應用程序在運行時的編譯時間、加載時間、垃圾回收時間、內存區域的回收狀態等。

5. 監控應用程序線程狀態和生命週期。

監控應用程序線程的運行、休眠、等待、鎖定狀態。

6. 顯示、分析線程堆信息。

顯示線程當前運行狀態和關聯類信息。

7. 支持第三方插件來分析JAVA應用程序。

另外還提供更多更強大、方便的第三方插件。

Java虛擬機性能管理神器 - VisualVM(2)  監控遠程主機上的JAVA應用程序

    使用VisualVM監控遠程主機上JAVA應用程序時,須要開啓遠程主機上的遠程監控訪問,或者在遠程JAVA應用程序啓動時,開啓遠程監控選項,兩種方法,選擇其中一種就能夠開啓遠程監控功能,配置完成後就能夠在本地對遠程主機上的JAVA應用程序進行監控。

1.遠程服務器、應用程序配置

        1.1配合jstatd工具提供監控數據  

        1.1.1建立安全訪問文件

        在JAVA_HOME/bin目錄中,建立名稱爲jstatdAllPolicy文件(這個文件名稱也能夠順便起,不過要與jstatd啓動時指定名稱相同),將如下內容拷貝到文件中。並保證文件的權限和用戶都正確。

        grant codebase"file:${java.home}/../lib/tools.jar"{ permission java.security.AllPermission; };

1.1.2啓動jstatd服務

        在JAVA_HOME/bin目錄中,執行如下命令:

        ./jstatd -J-Djava.security.policy=jstatdAllPolicy-p 1099 -J-Djava.rmi.server.hostname=192.168.xxx.xxx

        jstatd命令描述以及參數說明:

           jstatd是一個基於RMI(Remove Method Invocation)的服務程序,它用於監控基於HotSpot的JVM中資源的建立及銷燬,而且提供了一個遠程接口容許遠程的監控工具鏈接到本地的JVM執行命令。

        -J-Djava.security.policy=jstatdAllPolicy 指定安全策略文件名稱

         -p 1099  指定啓動端口

         -J-Djava.rmi.server.hostname=192.168.xxx.xxx  指定本機IP地址,在hosts文件配置不正常時使用,最好加上。

1.2JVM啓動時配置遠程監控選項

        在須要遠程監控的JVM啓動時,開啓遠程監控選項

        -Dcom.sun.management.jmxremote.port=1099
        -Dcom.sun.management.jmxremote.ssl=false
        -Dcom.sun.management.jmxremote.authenticate=false
        -Djava.rmi.server.hostname=192.168.xxx.xxx

2.本地VisualVM配置

        在本地VisualVM的應用程序窗口,右鍵單擊【遠程】》【添加遠程主機】》【主機名】中輸入遠程主機的IP地址,點擊【高級設置】輸入遠程主機開啓的監控端口,點擊【肯定】完成配置。

        若是一切正常,就能夠看到遠程主機上的JAVA應用程序了。

Java虛擬機性能管理神器 - VisualVM(3)  排查JAVA應用程序內存泄漏

1. 發現問題

    線上應用部署完成後,運行1~2天左右就會出現假死,或者某天早上8~10點高峯期間忽然不處理數據了。因爲在測試環境的壓力測試沒有作徹底,也沒有遇到相關問題。狀況出現後對客戶的使用形成很大影響,領導要求趕忙排查出問題緣由!

2. 排查緣由

        排查緣由前,與運維溝通,瞭解線上服務器的運行狀態,經過ganglila觀察網絡、CPU、內存、磁盤的運行歷史狀態,發現程序故障前,都有一波很高的負載,排查線上日誌,負載來源在8~9點平臺接入數據量成倍增長,經過與產品和市場人員分析,此時段是用戶集中上班、接入平臺的高峯時段,訪問日誌也顯示,業務場景正常,無網絡攻擊和安全問題。屬於產品業務正常的場景。

        排除了網絡安全因素後,就從程序的運行內部進行排查,首先想到的獲取JVM的dmp文件。獲取JVM的dmp文件有兩中方式:

        1. JVM啓動時增長兩個參數,出現 OOME 時生成堆 dump: 

                -XX:+HeapDumpOnOutOfMemoryError

                生成堆文件地址:

                -XX:HeapDumpPath=/home/test/jvmlogs/ 

        2. 發現程序異常前經過執行指令,直接生成當前JVM的dmp文件,15434是指JVM的進程號

                jmap -dump:format=b,file=serviceDump.dat    15434 

        因爲第一種方式是一種過後方式,須要等待當前JVM出現問題後才能生成dmp文件,實時性不高,第二種方式在執行時,JVM是暫停服務的,因此對線上的運行會產生影響。因此建議第一種方式。

3. 解決方案

        獲取到dmp文件後,就開始進行分析。將服務器上的dmp文件拷貝到本地,而後啓動本地的VisualVM,點擊菜單欄【文件】選項,裝入dmp文件

        打開dmp文件後,查看類標籤,就能看到佔用內存的一個排行。

        而後經過檢查中查找最大的對象,排查到具體線程和對象。

        上列中的com.ctfo.trackservice.handler.TrackHandleThread#4就是重點排查對象。

        經過代碼的比對,在此線程中,有調用DAO接口,負責將數據存儲到數據庫中。而存儲到數據庫中時,因爲存儲速度較慢,致使此線程中的數據隊列滿了,數據積壓,沒法回收致使了隊列鎖定,結果就是程序假死,不處理數據。

        經過進一步分析,發現數據庫存儲時有瓶頸,雖然當前是批量提交,速度也不快。平均8000/秒的存儲速度。而數據庫有一個DG(備份)節點,採用的是同步備份方式,即主庫事務要等DG的事務也完成後才能返回成功,這樣就會由於網絡因素、DG性能因素等緣由致使性能降低。經過與DBA、產品、溝通,將同步備份改成異步備份,實時同步改成異步(異步可能會致使主備有10分鐘之內的數據延遲)。速度達到30000/秒。問題解決。

        至此,經過VisualVM分析java程序內存泄漏到此結束。不過還有幾個問題:1. 若是dmp文件較大,VisualVM分析時間可能好久;另外,VisualVM對堆的分析顯示功能還不算全面。若是須要更全面的顯示,就可使用另一個專業的dmp文件分析工具【Memory Analyzer (MAT)】,此工具能夠做爲eclipse的插件進行安裝,也能夠單獨下載使用。若是有感興趣的朋友,我我的建議仍是單獨下載使用。下載地址:http://www.eclipse.org/mat/   

 

Java虛擬機性能管理神器 - VisualVM(4) 查找JAVA應用程序耗時的方法函數

1.爲何要監控?

        JAVA程序在開發前,根據設計文檔的性能需求,是要對程序的性能指標進行測試的。好比接口每秒響應次數要求1000次/秒,就須要平均每次請求處理的時間在1ms之內,若是須要知足這個指標,就須要在開發階段對接口執行函數進行監控,也能夠經過打印日誌進行監控,從而統計對應的性能指標,而後能夠根據性能指標的要求進行相應優化。

2. 那些方法函數須要監控?

        根據具體業務的場景和需求,主要集中在IO通信、文件讀寫、數據庫操做、業務邏輯處理上,這些都是制約性能的重要因素,因此須要重點關注。

        

3. 如何排查

        在研發環境,大部分會使用syso的方式或者日誌方式打印性能損耗,若是代碼沒有加在運行時纔想起來,或者想關注忽然想起的函數,換作之前,是須要重啓服務的,若是有VisualVM就能夠直接查看耗時以及調用次數等狀況。而不用打印、輸出日誌來查看性能損耗。

4. 如何處理

        對於性能損耗的函數,根據業務邏輯能夠進行相應的優化,例如字符串處理、文件讀寫方式、SQL語句優化、多線程處理等等方式。

       因爲性能優化涉及的內容不少,這裏就不深刻了。主要是告訴你們經過VisualVM來排查問題的具體位置。

Java虛擬機性能管理神器 - VisualVM(5) 排查JAVA應用程序線程鎖

1. JAVA應用程序線程鎖緣由

        JAVA線程鎖的例子和緣由網上一大堆,我也不在這裏深刻說明,這裏主要是否講如何使用VisualVM進行排查。至於例子能夠看這裏:http://blog.csdn.net/fengzhe0411/article/details/6953370 

這個例子比較極端,通常狀況下,出現鎖競爭激烈是比較常見的。

2. 排查JAVA應用程序線程鎖

       啓動 VisualVM,在應用程序窗口,選擇對應的JAVA應用,在詳情窗口》線程標籤(勾選線程可視化),查看線程生命週期狀態,主要留意線程生命週期中紅色部分。

(1)綠色:表明運行狀態。通常屬於正常狀況。若是是多線程環境,生產者消費者模式下,消費者一直處於運行狀態,說明消費者處理性能低,跟不上生產者的節奏,須要優化對應的代碼,若是不處理,就可能致使消費者隊列阻塞的現象。對應線程的【RUNNABLE】狀態。

(2)藍色:表明線程休眠。線程中調用Thread.sleep()函數的線程狀態時,就是藍色。對應線程的【TIMED_WAITING】狀態。

(3)黃色:表明線程等待。調用線程的wait()函數就會出現黃色狀態。對應線程的【WAITING】狀態。

(4)紅色:代碼線程鎖定。對應線程的【BLOCKED】狀態。

3. 分析解決JAVA應用程序線程鎖

        發生線程鎖的緣由有不少,我所遇到比較多的狀況是多線程同時訪問同一資源,且此資源使用synchronized關鍵字,致使一個線程要等另一個線程使用完資源後才能運行。例如再沒有鏈接池的狀況下,同時訪問數據庫接口。這種狀況會致使性能的極具降低,解決的方案是增長鏈接池,或者修改訪問方式。或者將資源粒度細化,相似ConCurrentHashMap中的處理方式,將資源分爲多個更小粒度的資源,在更小粒度資源上來處理鎖,就能夠解決資源競爭激烈的問題。]

相關文章
相關標籤/搜索