久久精品人人爽,华人av在线,亚洲性视频网站,欧美专区一二三

Java線上問題排查工具Arthas 原理以及用法是什么

189次閱讀
沒有評論

共計 9143 個字符,預計需要花費 23 分鐘才能閱讀完成。

這篇文章將為大家詳細講解有關 Java 線上問題排查工具 Arthas 原理以及用法是什么,文章內容質量較高,因此丸趣 TV 小編分享給大家做個參考,希望大家閱讀完這篇文章后對相關知識有一定的了解。

前言

當你興沖沖地開始運行自己的 Java 項目時,你是否遇到過如下問題:

程序在穩定運行了,可是實現的功能點了沒反應。

為了修復 Bug 而上線的新版本,上線后發現 Bug 依然在,卻想不通哪里有問題?

想到可能出現問題的地方,卻發現那里沒打日志,沒法在運行中看到問題,只能加了日志輸出重新打包——部署——上線

程序功能正常了,可是為啥響應時間這么慢,在哪里出現了問題?

程序不但穩定運行,而且功能完美,但跑了幾天或者幾周過后,發現響應速度變慢了,是不是內存泄漏了?

以前,你碰到這些問題,解決的辦法大多是,修改代碼,重新上線。但是在大公司里,上線的流程是非常繁瑣的,如果為了多加一行日志而重新發布版本,無疑是非常折騰人的。

現在,我們有了更為優雅的線上調試方法 – 來自阿里巴巴開源的 Arthas。

下圖是 Arthas 文檔中對于為什么要使用它的描述,我進行了精簡:

Java 線上問題排查工具 Arthas 原理以及用法是什么

線上 Debug 神器 ArthasArthas 使用實例

命令的詳細文檔請參考:
alibaba.github.io/arthas/comm…

快速啟動

快速啟動它,你只需要兩行命令:

wget https://alibaba.github.io/arthas/arthas-boot.jar
java -jar arthas-boot.jar

Java 線上問題排查工具 Arthas 原理以及用法是什么

隨后,在界面出現的進程中,選擇你的程序序號,比如 1

Java 線上問題排查工具 Arthas 原理以及用法是什么

這樣你就進入了 arthas 的控制臺。

基本使用

Arthas 有如下功能:

Java 線上問題排查工具 Arthas 原理以及用法是什么

1. 首先是我認為的“上帝視角”指令:Dashboard

當前系統的實時數據面板,按 ctrl+c 退出;
當運行在 Ali-tomcat 時,會顯示當前 tomcat 的實時信息,如 HTTP 請求的 qps, rt, 錯誤數, 線程池信息等等。

通過這些,你可以對于整個程序進程有個直觀的數據監控。

Java 線上問題排查工具 Arthas 原理以及用法是什么
Java 線上問題排查工具 Arthas 原理以及用法是什么

2. 類加載問題相關指令

Java 線上問題排查工具 Arthas 原理以及用法是什么

SC:查看 JVM 已加載的類信息

通過 SC 我們可以看到我們這個類的詳細信息,包括是從哪個 jar 包讀取的,他是不是接口 / 枚舉類等,甚至包括他是從哪個類加載器加載的。

Java 線上問題排查工具 Arthas 原理以及用法是什么

上圖中代碼:

[arthas@37]$ sc -d *MathGame
 class-info demo.MathGame
 code-source /home/scrapbook/tutorial/arthas-demo.jar
 name demo.MathGame
 isInterface false
 isAnnotation false
 isEnum false
 isAnonymousClass false
 isArray false
 isLocalClass false
 isMemberClass false
 isPrimitive false
 isSynthetic false
 simple-name MathGame
 modifier public
 annotation
 interfaces
 super-class +-java.lang.Object
 class-loader +-sun.misc.Launcher$AppClassLoader@70dea4e
 +-sun.misc.Launcher$ExtClassLoader@69260973
 classLoaderHash 70dea4e

SC 也可以查看已加載的類,幫助你看是否有沒有納入進來的類,尤其是在 Spring 中,可以判斷的你的依賴有沒有正確的進來。

Java 線上問題排查工具 Arthas 原理以及用法是什么

上圖中代碼:

#  查看 JVM 已加載的類信息
[arthas@37]$ sc javax.servlet.Filter
com.example.demo.arthas.AdminFilterConfig$AdminFilter
javax.servlet.Filter
org.apache.tomcat.websocket.server.WsFilter
org.springframework.boot.web.filter.OrderedCharacterEncodingFilter
org.springframework.boot.web.filter.OrderedHiddenHttpMethodFilter
org.springframework.boot.web.filter.OrderedHttpPutFormContentFilter
org.springframework.boot.web.filter.OrderedRequestContextFilter
org.springframework.web.filter.CharacterEncodingFilter
org.springframework.web.filter.GenericFilterBean
org.springframework.web.filter.HiddenHttpMethodFilter
org.springframework.web.filter.HttpPutFormContentFilter
org.springframework.web.filter.OncePerRequestFilter
org.springframework.web.filter.RequestContextFilter
org.springframework.web.servlet.resource.ResourceUrlEncodingFilter
Affect(row-cnt:14) cost in 11 ms.
#  查看已加載類的方法信息
[arthas@37]$ sm java.math.RoundingMode
java.math.RoundingMode  init (Ljava/lang/String;II)V
java.math.RoundingMode values()[Ljava/math/RoundingMode;
java.math.RoundingMode valueOf(I)Ljava/math/RoundingMode;
java.math.RoundingMode valueOf(Ljava/lang/String;)Ljava/math/RoundingMode;
Affect(row-cnt:4) cost in 6 ms.

jad:反編譯某個類,或者反編譯某個類的某個方法。

Java 線上問題排查工具 Arthas 原理以及用法是什么

上圖中代碼:

#  反編譯只顯示源碼
jad --source-only com.Arthas
#  反編譯某個類的某個方法
jad --source-only com.Arthas mysql
[arthas@37]$ jad demo.MathGame
ClassLoader:
+-sun.misc.Launcher$AppClassLoader@70dea4e
 +-sun.misc.Launcher$ExtClassLoader@69260973
Location:
/home/scrapbook/tutorial/arthas-demo.jar
 * Decompiled with CFR.
 */
package demo;
import java.io.PrintStream;
import java.util.ArrayList;
import java.util.List;
import java.util.Random;
import java.util.concurrent.TimeUnit;
public class MathGame { private static Random random = new Random();
 public int illegalArgumentCount = 0;
 public List Integer  primeFactors(int number) { if (number   2) {
 ++this.illegalArgumentCount;
 throw new IllegalArgumentException( number is:   + number +  , need  = 2 
 }
 ArrayList Integer  result = new ArrayList Integer 
 int i = 2;
 while (i  = number) { if (number % i == 0) { result.add(i);
 number /= i;
 i = 2;
 continue;
 }
 ++i;
 }
 return result;
 }
 public static void main(String[] args) throws InterruptedException { MathGame game = new MathGame();
 do { game.run();
 TimeUnit.SECONDS.sleep(1L);
 } while (true);
 }
 public void run() throws InterruptedException {
 try { int number = random.nextInt() / 10000;
 List Integer  primeFactors = this.primeFactors(number);
 MathGame.print(number, primeFactors);
 }
 catch (Exception e) { System.out.println(String.format( illegalArgumentCount:%3d,  , this.illegalArgumentCount) + e.getMessage());
 }
 }
 public static void print(int number, List Integer  primeFactors) {
 StringBuffer sb = new StringBuffer(number +  = 
 for (int factor : primeFactors) { sb.append(factor).append( * 
 }
 if (sb.charAt(sb.length() - 1) ==  * ) { sb.deleteCharAt(sb.length() - 1);
 }
 System.out.println(sb);
 }
Affect(row-cnt:1) cost in 760 ms.

3. 方法運行相關指令

Java 線上問題排查工具 Arthas 原理以及用法是什么

watch:方法執行的數據觀測

你可以通過 watch 指令,來監控某個類,監控后,運行下你的功能,復現下場景,arthas 會提供給你具體的出參和入參,幫助你排查故障。

Java 線上問題排查工具 Arthas 原理以及用法是什么

trace:輸出方法調用路徑,并輸出耗時

這個指令對于優化代碼非常的有用,可以看出具體每個方法執行的時間,如果是 for 循環等重復語句,還能看出 n 次循環中的最大耗時,最小耗時,和平均耗時,完美!

Java 線上問題排查工具 Arthas 原理以及用法是什么

tt:官方名為時空隧道

這是我調試用的最多的指令,在你對某方法開啟 tt 后,會記錄下每一次的調用(你需要設置最大監控次數),然后你可以在任何時候會看這里面的調用,包括出參,入參,運行耗時,是否異常等。非常強大。

Java 線上問題排查工具 Arthas 原理以及用法是什么

4. 線程調試相關指令

Java 線上問題排查工具 Arthas 原理以及用法是什么

thread 相關命令:

Java 線上問題排查工具 Arthas 原理以及用法是什么

thread -n:排列出 CPU 使用率 Top N 的線程。

Java 線上問題排查工具 Arthas 原理以及用法是什么

thread -b:排查阻塞的線程

我們代碼有時候設計的不好,會引發死鎖的問題,卡住整個線程執行,使用這個指令可以輕松的找到問題線程,以及問題的執行語句。

Java 線上問題排查工具 Arthas 原理以及用法是什么
Java 線上問題排查工具 Arthas 原理以及用法是什么

5. 強大的 ognl 表達式

眾所周知,一般來說,表達式都是調試工具里最強的指令,哈哈。

Java 線上問題排查工具 Arthas 原理以及用法是什么

在 Arthas 中你可以利用 ognl 表達式語言做很多事,比如執行某個方法,獲取某個信息,甚至進行修改。

Java 線上問題排查工具 Arthas 原理以及用法是什么

[arthas@19856]$ ognl  @com.Arthas@hashSet 
@HashSet[ @String[count1],
 @String[count2],
 @String[count29],
 @String[count28],
 @String[count0],
 @String[count27],
 @String[count5],
 @String[count26],
 @String[count6],
 @String[count25],
 @String[count3],
 @String[count24],
[arthas@19856]$ ognl  @com.Arthas@hashSet.add(test) 
@Boolean[true]
[arthas@19856]$
#  查看添加的字符
[arthas@19856]$ ognl  @com.Arthas@hashSet  | grep test
 @String[test],
[arthas@19856]$

甚至你可以動態更換日志輸出級別。

Java 線上問題排查工具 Arthas 原理以及用法是什么

$ ognl  @com.lz.test@LOGGER.logger.privateConfig 
@PrivateConfig[ loggerConfig=@LoggerConfig[root],
 loggerConfigLevel=@Level[INFO],
 intLevel=@Integer[400],
$ ognl  @com.lz.test@LOGGER.logger.setLevel(@org.apache.logging.log4j.Level@ERROR) 
$ ognl  @com.lz.test@LOGGER.logger.privateConfig 
@PrivateConfig[ loggerConfig=@LoggerConfig[root],
 loggerConfigLevel=@Level[ERROR],
 intLevel=@Integer[200],
]

使用 Arthas 解決具體問題 1. 響應時間異常問題

工作中遇到一個優化問題,系統中一個導出表格的功能,響應時間長達 2 分鐘,雖然給內部使用,但也不能這么夸張,用 trace 跟蹤下方法,發現是其中的手機號加解密函數占用了非常大的時間,幾千個手機號,進行了解密后加密的精彩操作,最終導致了兩分鐘的返回時間。

Java 線上問題排查工具 Arthas 原理以及用法是什么

2. 某功能 Bug 導致服務器返回 500

首先通過 trace 看異常報錯的方法,之后通過 tt 排查方法,發現入參進來后,居然走錯了方法(因為多態),走到了返回 null 的方法中,所以導致了 NPE 空指針錯誤。

Java 線上問題排查工具 Arthas 原理以及用法是什么
Java 線上問題排查工具 Arthas 原理以及用法是什么

補充

Arthas 還支持 Web Console,詳見:
alibaba.github.io/arthas/web-…

Java 線上問題排查工具 Arthas 原理以及用法是什么

相似工具

BTrace 一是個歷史比較久的工具,觀察下來 Arthas 其實和它的理念蠻相似的,相信 Arthas 也參考過 Btrace,作為一個學習樣例來開發 Arthas。詳細的優劣勢看圖:

Java 線上問題排查工具 Arthas 原理以及用法是什么

其他的相似工具,還有 jvm-sandbox,有興趣的朋友可以去看看。

原理淺談

分為三個部分:

啟動

arthas 服務端代碼分析

arthas 客戶端代碼分析

Java 線上問題排查工具 Arthas 原理以及用法是什么

啟動

使用了阿里開源的組件 cli, 對參數進行了解析:com.taobao.arthas.boot.Bootstrap

Java 線上問題排查工具 Arthas 原理以及用法是什么

在傳入參數中沒有 pid, 則會調用本地 jps 命令, 列出 java 進程。

Java 線上問題排查工具 Arthas 原理以及用法是什么

進入主邏輯, 會在用戶目錄下建立 .arthas 目錄, 同時下載 arthas-core 和 arthas-agent 等 lib 文件, 最后啟動客戶端和服務端。

通過反射的方式來啟動字符客戶端。

Java 線上問題排查工具 Arthas 原理以及用法是什么

服務端——前置準備

看服務端啟動命令可以知道 從 arthas-core.jar 開始啟動,arthas-core 的 pom.xml 文件里面指定了 mainClass 為 com.taobao.arthas.core.Arthas,使得程序啟動的時候從該類的 main 方法開始運行。

Java 線上問題排查工具 Arthas 原理以及用法是什么

首先解析入參,生成 com.taobao.arthas.core.config.Configure 類,包含了相關配置信息;

使用 jdk-tools 里面的 VirtualMachine.loadAgent,其中第一個參數為 agent 路徑,第二個參數向 jar 包中的 agentmain() 方法傳遞參數(此處為 agent-core.jar 包路徑和 config 序列化之后的字符串),加載 arthas-agent.jar 包;

運行 arthas-agent.jar 包,指定了 Agent-Class 為 com.taobao.arthas.agent.AgentBootstrap。

Java 線上問題排查工具 Arthas 原理以及用法是什么

上圖中代碼:

public class Arthas { private Arthas(String[] args) throws Exception { attachAgent(parse(args));
 }
 private Configure parse(String[] args) {
 //  省略非關鍵代碼,解析啟動參數作為配置,并填充到 configure 對象里面
 return configure;
 }
 private void attachAgent(Configure configure) throws Exception {
 //  省略非關鍵代碼,attach 到目標進程
 virtualMachine = VirtualMachine.attach( + configure.getJavaPid());
 virtualMachine.loadAgent(configure.getArthasAgent(),
 configure.getArthasCore() +   + configure.toString());
 }
 public static void main(String[] args) { new Arthas(args);
 }
}

Java 線上問題排查工具 Arthas 原理以及用法是什么

服務端——監聽客戶端請求

如果是 exit,logout,quit,jobs,fg,bg,kill 等直接執行;

如果是其他的命令,則創建 Job,并運行;

創建 Job 時,會根據具體客戶端傳遞的命令,找到對應的 Command,并包裝成 Process, Process 再被包裝成 Job;

運行 Job 時,反向先調用 Process,再找到對應的 Command,最終調用 Command 的 process 處理請求。

服務端——Command 處理流程

不需要使用字節碼增強的命令

其中 JVM 相關的使用 java.lang.management 提供的管理接口,來查看具體的運行時數據。比較簡單,就不介紹了。

需要使用字節碼增強的命令

字節碼增加的命令統一繼承 EnhancerCommand 類,process 方法里面調用 enhance 方法進行增強。調用 Enhancer 類 enhance 方法,該方法內部調用 inst.addTransformer 方法添加自定義的 ClassFileTransformer,這邊是 Enhancer 類。

Enhancer 類使用 AdviceWeaver(繼承 ClassVisitor),用來修改類的字節碼。重寫了 visitMethod 方法,在該方法里面修改類指定的方法。visitMethod 方法里面使用了 AdviceAdapter(繼承了 MethodVisitor 類),在 onMethodEnter 方法, onMethodExit 方法中,把 Spy 類對應的方法(ON_BEFORE_METHOD,ON_RETURN_METHOD,ON_THROWS_METHOD 等)編織到目標類的方法對應的位置。

在前面 Spy 初始化的時候可以看到,這幾個方法其實指向的是 AdviceWeaver 類的 methodOnBegin,methodOnReturnEnd 等。在這些方法里面都會根據 adviceId 查找對應的 AdviceListener,并調用 AdviceListener 的對應的方法,比如 before,afterReturning, afterThrowing。

客戶端

客戶端代碼在 arthas-client 模塊里面,入口類是 com.taobao.arthas.client.TelnetConsole。

主要使用 apache commons-net jar 進行 telnet 連接,關鍵的代碼有下面幾步:

構造 TelnetClient 對象,并初始化

構造 ConsoleReader 對象,并初始化

調用 IOUtil.readWrite(telnet.getInputStream(), telnet.getOutputStream(), System.in, consoleReader.getOutput()) 處理各個流,一共有四個流:

telnet.getInputStream()

telnet.getOutputStream()

System.in

consoleReader.getOutput()

請求時:從本地 System.in 讀取,發送到 telnet.getOutputStream(),即發送給遠程服務端。響應時:從 telnet.getInputStream() 讀取遠程服務端發送過來的響應,并傳遞給 consoleReader.getOutput(),即在本地控制臺輸出。

關于源碼,深入下去還有很多東西需要生啃,我也沒有消化得很好,大家可以繼續閱讀詳細資料。

總結

Arthas 是一個線上 Debug 神器,小白也可以輕松上手。

一鍵安裝并啟動 Arthas

方式一:通過 Cloud Toolkit 實現 Arthas 一鍵遠程診斷

Cloud Toolkit 是阿里云發布的免費本地 IDE 插件,幫助開發者更高效地開發、測試、診斷并部署應用。通過插件,可以將本地應用一鍵部署到任意服務器,甚至云端(ECS、EDAS、ACK、ACR 和 小程序云等);并且還內置了 Arthas 診斷、Dubbo 工具、Terminal 終端、文件上傳、函數計算 和 MySQL 執行器等工具。不僅僅有 IntelliJ IDEA 主流版本,還有 Eclipse、Pycharm、Maven 等其他版本。

推薦使用 IDEA 插件下載 Cloud Toolkit 來使用 Arthas:
http://t.tb.cn/2A5CbHWveOXzI7sFakaCw8

方式二:直接下載

地址:
https://github.com/alibaba/arthas。

關于 Java 線上問題排查工具 Arthas 原理以及用法是什么就分享到這里了,希望以上內容可以對大家有一定的幫助,可以學到更多知識。如果覺得文章不錯,可以把它分享出去讓更多的人看到。

正文完
 
丸趣
版權聲明:本站原創文章,由 丸趣 2023-08-25發表,共計9143字。
轉載說明:除特殊說明外本站除技術相關以外文章皆由網絡搜集發布,轉載請注明出處。
評論(沒有評論)
主站蜘蛛池模板: 闻喜县| 开平市| 潮州市| 通化市| 乌什县| 绥化市| 汾阳市| 光泽县| 上杭县| 寿阳县| 额尔古纳市| 泰兴市| 交口县| 渭源县| 大厂| 太康县| 佛教| 荆州市| 肥西县| 凌云县| 蒙自县| 都兰县| 旺苍县| 资兴市| 德清县| 兰溪市| 威信县| 凌海市| 广饶县| 遂宁市| 大石桥市| 吴桥县| 广德县| 武邑县| 桃园市| 景宁| 江阴市| 永善县| 高唐县| 临猗县| 庆云县|