Arthas 常用命令

Windows下Arthas的安装和卸载
万字长文!你还敢说你看不懂阿里开源Java神器Arthas?

Arthas描述

ArthasAlibaba开源的Java诊断工具,深受开发者喜爱。

当你遇到以下类似问题而束手无策时,Arthas可以帮助你解决:
1、这个类从哪个 jar 包加载的?为什么会报各种类相关的 Exception2、我改的代码为什么没有执行到?难道是我没 commit?分支搞错了?
3、遇到问题无法在线上 debug,难道只能通过加日志再重新发布吗?
4、线上遇到某个用户的数据处理有问题,但线上同样无法 debug,线下无法重现!
5、是否有一个全局视角来查看系统的运行状况?
6、有什么办法可以监控到JVM的实时运行状态?
7、怎么快速定位应用的热点,生成火焰图?

监控方法命令

请注意,这些命令,都通过字节码增强技术来实现的,会在指定类的方法中插入一些切面来实现数据统计和观测,
因此在线上、预发使用时,请尽量明确需要观测的类、方法以及条件,诊断结束要执行  stop 或将增强过的类执行 reset 命令。
1、quit 退出当前 Arthas 客户端,其他 Arthas 客户端不受影响
2、shutdown——关闭 Arthas 服务端,所有 Arthas 客户端全部退出
3、stop——和shutdown命令一致

monitor——方法执行监控

watch——方法执行数据观测

trace——方法内部调用路径,并输出方法路径上的每个节点上耗时

stack——输出当前方法被调用的调用路径

tt——方法执行数据的时空隧道,记录下指定方法每次调用的入参和返回信息,并能对这些不同的时间下调用进行观测

watch

让你能方便的观察到指定方法的调用情况。
能观察到的范围为:返回值、抛出异常、入参,通过编写 OGNL 表达式进行对应变量的查看。

参数说明:
class-pattern		类名表达式匹配
method-pattern		方法名表达式匹配
express				观察表达式
condition-express	条件表达式
-b					在方法调用之前观察
-e					在方法异常之后观察
-s					在方法返回之后观察
-f 					在方法结束之后(正常返回和异常返回)观察 默认开启
-E					开启正则表达式匹配,默认为通配符匹配
-x					指定输出结果的属性遍历深度,默认为 1
-n 					执行的次数

特别说明:
watch 命令定义了4个观察事件点,
即 -b 方法调用前,-e 方法异常后,-s 方法返回后,-f 方法结束后

4个观察事件点 -b、-e、-s 默认关闭,-f 默认打开,
当指定观察点被打开后,在相应事件点会对观察表达式进行求值并输出

这里要注意方法入参和方法出参的区别,有可能在中间被修改导致前后不一致,
除了 -b 事件点 params 代表方法入参外,其余事件都代表方法出参

当使用 -b 时,由于观察事件点是在方法调用前,此时返回值或异常均不存在

-x 代表输出结果的深度 ,默认为 1

使用参考:
常规用法:
watch class method {params,returnObj,throwExp}  -x 1 '#cost>200'
观察表达式 { } 可以包裹结果集 , 分割。输出的表达式变量定义
params 代表参数数组,returnObj 代表返回值,throwExp 代表抛出的异常。
过滤耗时大于200ms的

特殊用法:
1、调用第一个参数的方法或属性
watch class method "{params[0].length()}"  -x 1
如果是列表参数,则可以使用这种方式来获取列表中每个对象的指定属性
watch class method "{params[0].{ #this.length()}}" -x 1

2、按照条件过滤
如果是列表,则会过滤列表中长度大于7的字符串
watch class method "{params[0].{? #this.length() > 7}}" -x 1
watch class method "{params,returnObj,throwExp}" "params[0].length() > 7" -x 1
字符串长度 > 7 才会输出 params[0] 的值


3、过滤后统计
watch class method "{params[0].{? #this.length() > 9}.size()}" -x 1


4、过滤列表参数格式
获取列表中每个对象的name属性
watch class method "{params[0].{name}}" -n 1 -x 1
watch class method "{params[0].users.{name}}" -n 1 -x 1

也可以使用方法获取
watch class method "{params[0].{getName()}}" -n 1 -x 1

也可以使用条件进行过滤筛选
watch class method "{params[0].{? name.length() > 5}}" -n 1 -x 1

按条件过滤后展示指定属性
watch class method "{params[0].{? #this.name.length() > 5}.{age}}" -n 1 -x 1

找到第一个符合条件的数据,用^
watch class method "{params[0].{^ #this.name.length() > 5}.{age}}" -n 1 -x 1

找到最后一个符合条件的数据,用$
watch class method "{params[0].{$ #this.name.length() > 5}.{age}}" -n 1 -x 1

使用临时变量,然后进行相关操作,然后展示
watch class method "(#test=params[0].{? #this.name.length() > 5}.{name}, #test.add('zhangsan'), #test)" -n 1 -x 1

获取列表中每个对象的id,name属性,并用逗号衔接,然后一行输出
watch class method "{params[0].users.{id + ',' + name}}" -n 1 -x 1

arthas 使用ognl表达式理解

trace

trace 命令能主动搜索 class-pattern/method-pattern 对应的方法内部调用路径,
渲染和统计整个调用链路上的所有性能开销和追踪调用链路。

参数说明:
class-pattern 		类名表达式匹配
method-pattern 		方法名表达式匹配
condition-express 	条件表达式
-E 					开启正则表达式匹配,默认为通配符匹配,可以加上该参数,然后根据参数或者返回值进行条件过滤
-n 					命令执行次数
#cost 				方法执行耗时

使用参考:
常规用法:
trace class method '#cost>100' -n 1
过滤大于100ms的调用链,只输出一次

特殊用法:
trace命令只会trace匹配到的函数里的子调用,并不会向下trace多层。
因为trace是代价比较贵的,多层trace可能会导致最终要trace的类和函数非常多。

动态trace:
3.3.0 版本后支持。
打开终端1,trace run函数,可以看到打印出 listenerId: 1[arthas@59161]$ trace demo.MathGame run
Press Q or Ctrl+C to abort.
Affect(class count: 1 , method count: 1) cost in 112 ms, listenerId: 1
`---ts=2020-07-09 16:48:11;thread_name=main;id=1;is_daemon=false;priority=5;TCCL=sun.misc.Launcher$AppClassLoader@3d4eac69
    `---[1.389634ms] demo.MathGame:run()
        `---[0.123934ms] demo.MathGame:primeFactors() #24 [throws Exception]

现在想要深入子函数primeFactors,可以打开一个新终端2,
使用telnet localhost 3658连接上arthas,
再trace primeFactors时,指定listenerId。
再查看终端1,可以发现trace的结果增加了一层,打印了primeFactors函数里的内容

`---ts=2020-07-09 16:49:29;thread_name=main;id=1;is_daemon=false;priority=5;TCCL=sun.misc.Launcher$AppClassLoader@3d4eac69
    `---[0.492551ms] demo.MathGame:run()
        `---[0.113929ms] demo.MathGame:primeFactors() #24 [throws Exception]
            `---[0.061462ms] demo.MathGame:primeFactors()
                `---[0.001018ms] throw:java.lang.IllegalArgumentException() #46

通过指定listenerId的方式动态trace,可以不断深入。
另外 watch/tt/monitor等命令也支持类似的功能。

tt

方法执行数据的时空隧道,记录下指定方法每次调用的入参和返回信息,并能对这些不同的时间下调用进行观测。

watch 虽然很方便和灵活,但需要提前想清楚观察表达式的拼写,这对排查问题而言要求太高。
因为很多时候我们并不清楚问题出自于何方,只能靠蛛丝马迹进行猜测。
这个时候如果能记录下当时方法调用的所有入参和返回值、抛出的异常会对整个问题的思考与判断非常有帮助。

于是乎,TimeTunnel 命令就诞生了。

参数说明:
-n 				执行次数
#cost 			过滤耗时
-t tt 			命令有很多个主参数,-t 就是其中之一。
这个参数的表明希望记录下类 *Test 的 print 方法的每次执行情况。
-s 				可以跟条件表达式 进行筛选
-l 				列出所有的记录
-i INDEX编号 	查看对应的INDEX编号的详细信息

记录说明:
表格字段			字段解释
INDEX			时间片段记录编号,每一个编号代表着一次调用,后续tt还有很多命令都是基于此编号指定记录操作,非常重要。
TIMESTAMP		方法执行的本机时间,记录了这个时间片段所发生的本机时间COST(ms)		方法执行的耗时
IS-RET			方法是否以正常返回的形式结束
IS-EXP			方法是否以抛异常的形式结束
OBJECT			执行对象的hashCode(),注意,曾经有人误认为是对象在JVM中的内存地址,但很遗憾他不是。但他能帮助你简单的标记当前执行方法的类实体
CLASS			执行的类名METHOD执行的方法名

使用参考:
tt -t class method '#cost>100'
 INDEX   TIMESTAMP            COST(ms)  IS-RET  IS-EXP   OBJECT         CLASS                          METHOD
-------------------------------------------------------------------------------------------------------------------------------------
 1000    2018-12-04 11:15:38  1.096236  false   true     0x4b67cf4d     MathGame                       primeFactors
 1001    2018-12-04 11:15:39  0.191848  false   true     0x4b67cf4d     MathGame                       primeFactors
 1002    2018-12-04 11:15:40  0.069523  false   true     0x4b67cf4d     MathGame                       primeFactors
 1003    2018-12-04 11:15:41  0.186073  false   true     0x4b67cf4d     MathGame                       primeFactors
 1004    2018-12-04 11:15:42  17.76437  true    false    0x4b67cf4d     MathGame 

查看调用信息:
对于具体一个时间片的信息而言,你可以通过 -i 参数后边跟着对应的 INDEX 编号查看到他的详细信息。
tt -i 1003
$ tt -i 1003
 INDEX            1003
 GMT-CREATE       2018-12-04 11:15:41
 COST(ms)         0.186073
 OBJECT           0x4b67cf4d
 CLASS            demo.MathGame
 METHOD           primeFactors
 IS-RETURN        false
 IS-EXCEPTION     true
 PARAMETERS[0]    @Integer[-564322413]
 THROW-EXCEPTION  java.lang.IllegalArgumentException: number is: -564322413, need >= 2
                      at demo.MathGame.primeFactors(MathGame.java:46)
                      at demo.MathGame.run(MathGame.java:24)
                      at demo.MathGame.main(MathGame.java:16)
 
Affect(row-cnt:1) cost in 11 ms.

tt -l 查看我们现有的记录
$ tt -l
 INDEX   TIMESTAMP            COST(ms)  IS-RET  IS-EXP   OBJECT         CLASS                          METHOD
-------------------------------------------------------------------------------------------------------------------------------------
 1000    2018-12-04 11:15:38  1.096236  false   true     0x4b67cf4d     MathGame                       primeFactors
 1001    2018-12-04 11:15:39  0.191848  false   true     0x4b67cf4d     MathGame                       primeFactors
 1002    2018-12-04 11:15:40  0.069523  false   true     0x4b67cf4d     MathGame                       primeFactors
 1003    2018-12-04 11:15:41  0.186073  false   true     0x4b67cf4d     MathGame                       primeFactors
 1004    2018-12-04 11:15:42  17.76437  true    false    0x4b67cf4d     MathGame                       primeFactors
                              9
 1005    2018-12-04 11:15:43  0.4776    false   true     0x4b67cf4d     MathGame                       primeFactors
Affect(row-cnt:6) cost in 4 ms.

我需要筛选出 primeFactors 方法的调用信息
tt -s
$ tt -s 'method.name=="primeFactors"'
 INDEX   TIMESTAMP            COST(ms)  IS-RET  IS-EXP   OBJECT         CLASS                          METHOD
-------------------------------------------------------------------------------------------------------------------------------------
 1000    2018-12-04 11:15:38  1.096236  false   true     0x4b67cf4d     MathGame                       primeFactors
 1001    2018-12-04 11:15:39  0.191848  false   true     0x4b67cf4d     MathGame                       primeFactors
 1002    2018-12-04 11:15:40  0.069523  false   true     0x4b67cf4d     MathGame                       primeFactors
 1003    2018-12-04 11:15:41  0.186073  false   true     0x4b67cf4d     MathGame                       primeFactors
 1004    2018-12-04 11:15:42  17.76437  true    false    0x4b67cf4d     MathGame                       primeFactors
                              9
 1005    2018-12-04 11:15:43  0.4776    false   true     0x4b67cf4d     MathGame                       primeFactors
Affect(row-cnt:6) cost in 607 ms.

stack

很多时候我们都知道一个方法被执行,但这个方法被执行的路径非常多,
或者你根本就不知道这个方法是从那里被执行了,此时你需要的是 stack 命令。

参数说明:
class-pattern 		类名表达式匹配
method-pattern 		方法名表达式匹配
condition-express 	条件表达式
-E 					开启正则表达式匹配,默认为通配符匹配
-n 					执行次数限制

使用参考:
stack class method ’#cost>5‘ 

stack demo.MathGame primeFactors ’#cost>5‘ 
输出调用链,按照执行时间过滤

stack demo.MathGame primeFactors 'params[0]<0' -n 2 
按照条件表达式进行过滤

monitor

参数说明:
class-pattern			类名表达式匹配
method-pattern			方法名表达式匹配
condition-express		条件表达式
-E						开启正则表达式匹配,默认为通配符匹配
-c						统计周期,默认值为120秒
方法拥有一个命名参数 [c:],意思是统计周期(cycle of output),拥有一个整型的参数值
-b						在方法调用之前计算condition-express

监控的维度说明:
监控项					说明
timestamp				时间戳
class					Java类
method					方法(构造方法、普通方法)
total					调用次数
success					成功次数
fail					失败次数
rt						平均RT
fail-rate				失败率

使用参考:
monitor -c 5 class method

monitor -c 5 demo.MathGame primeFactors 
每5秒统计一次

$ monitor -c 5 demo.MathGame primeFactors
Press Ctrl+C to abort.
Affect(class-cnt:1 , method-cnt:1) cost in 94 ms.
 timestamp            class          method        total  success  fail  avg-rt(ms)  fail-rate
-----------------------------------------------------------------------------------------------
 2018-12-03 19:06:38  demo.MathGame  primeFactors  5      1        4     1.15        80.00%
 
 timestamp            class          method        total  success  fail  avg-rt(ms)  fail-rate
-----------------------------------------------------------------------------------------------
 2018-12-03 19:06:43  demo.MathGame  primeFactors  5      3        2     42.29       40.00%
 
 timestamp            class          method        total  success  fail  avg-rt(ms)  fail-rate
-----------------------------------------------------------------------------------------------
 2018-12-03 19:06:48  demo.MathGame  primeFactors  5      3        2     67.92       40.00%
 
 timestamp            class          method        total  success  fail  avg-rt(ms)  fail-rate
-----------------------------------------------------------------------------------------------
 2018-12-03 19:06:53  demo.MathGame  primeFactors  5      2        3     0.25        60.00%
 
 timestamp            class          method        total  success  fail  avg-rt(ms)  fail-rate
-----------------------------------------------------------------------------------------------
 2018-12-03 19:06:58  demo.MathGame  primeFactors  1      1        0     0.45        0.00%
 
 timestamp            class          method        total  success  fail  avg-rt(ms)  fail-rate
-----------------------------------------------------------------------------------------------
 2018-12-03 19:07:03  demo.MathGame  primeFactors  2      2        0     3182.72     0.00%

计算条件表达式过滤统计结果(方法执行完毕之后)

monitor -c 5 demo.MathGame primeFactors "params[0] <= 2"
Press Q or Ctrl+C to abort.
Affect(class count: 1 , method count: 1) cost in 19 ms, listenerId: 5
 timestamp            class          method         total  success  fail  avg-rt(ms)  fail-rate        
-----------------------------------------------------------------------------------------------
 2020-09-02 09:42:36  demo.MathGame  primeFactors    5       3       2      0.09       40.00%           
 
 timestamp            class          method         total  success  fail  avg-rt(ms)  fail-rate        
----------------------------------------------------------------------------------------------
 2020-09-02 09:42:41  demo.MathGame  primeFactors    5       2       3      0.11       60.00%           
 
 timestamp            class          method         total  success  fail  avg-rt(ms)  fail-rate        
----------------------------------------------------------------------------------------------
 2020-09-02 09:42:46  demo.MathGame  primeFactors    5       1       4      0.06       80.00%           
 
 timestamp            class          method         total  success  fail  avg-rt(ms)  fail-rate        
----------------------------------------------------------------------------------------------
 2020-09-02 09:42:51  demo.MathGame  primeFactors    5       1       4      0.12       80.00%           
 
 timestamp            class          method         total  success  fail  avg-rt(ms)  fail-rate        
----------------------------------------------------------------------------------------------
 2020-09-02 09:42:56  demo.MathGame  primeFactors    5       3       2      0.15       40.00%           

jvm相关

dashboard——当前系统的实时数据面板

thread——查看当前 JVM 的线程堆栈信息

jvm——查看当前 JVM 的信息

sysprop——查看和修改JVM的系统属性

sysenv——查看JVM的环境变量

vmoption——查看和修改JVM里诊断相关的option

perfcounter——查看当前 JVMPerf Counter信息

logger——查看和修改logger

getstatic——查看类的静态属性

ognl——执行ognl表达式

mbean——查看 Mbean 的信息

heapdump——dump java heap, 类似jmap命令的heap dump功能

dashboard

当前系统的实时数据面板,按 ctrl+c 退出。

使用参考:
dashboard -i 5000 -n 10
-i 刷新实时数据的时间间隔 (ms),默认5000ms 
-n 刷新数据的次数

数据说明:
ID: 			Java级别的线程ID,注意这个ID不能跟jstack中的nativeID一一对应。
NAME: 			线程名
GROUP: 			线程组名
PRIORITY: 		线程优先级, 1~10之间的数字,越大表示优先级越高
STATE: 			线程的状态
%CPU: 			线程的cpu使用率。比如采样间隔1000ms,某个线程的增量cpu时间为100ms,则cpu使用率=100/1000=10%
DELTA_TIME: 	上次采样之后线程运行增量CPU时间,数据格式为秒
TIME: 			线程运行总CPU时间,数据格式为分:INTERRUPTED: 	线程当前的中断位状态
DAEMON: 		是否是daemon线程

在这里插入图片描述

thread

查看当前线程信息,查看线程的堆栈

参数说明:
id							线程id
-n							指定最忙的前N个线程并打印堆栈
-b							找出当前阻塞其他线程的线程
-i							指定cpu使用率统计的采样间隔,单位为毫秒,默认值为200
--all						显示所有匹配的线程
--state						查看指定状态的线程

使用参考:
thread -b, 					找出当前阻塞其他线程的线程
有时候我们发现应用卡住了, 通常是由于某个线程拿住了某个锁, 并且其他线程都在等待这把锁造成的。 
为了排查这类问题, arthas提供了thread -b, 一键找出那个罪魁祸首
thread -i 1000 : 			统计最近1000ms内的线程CPU时间。
thread -n 3 -i 1000 : 		列出1000ms内最忙的3个线程栈
thread --state WAITING 		列出等待态的线程

jvm

查看当前JVM信息

使用参考:
$ jvm
RUNTIME
--------------------------------------------------------------------------------------------------------------
 MACHINE-NAME                   37@ff267334bb65
 JVM-START-TIME                 2020-07-23 07:50:36
 MANAGEMENT-SPEC-VERSION        1.2
 SPEC-NAME                      Java Virtual Machine Specification
 SPEC-VENDOR                    Oracle Corporation
 SPEC-VERSION                   1.8
 VM-NAME                        Java HotSpot(TM) 64-Bit Server VM
 VM-VENDOR                      Oracle Corporation
 VM-VERSION                     25.201-b09
 INPUT-ARGUMENTS                []
 CLASS-PATH                     demo-arthas-spring-boot.jar
 BOOT-CLASS-PATH                /usr/lib/jvm/java-8-oracle/jre/lib/resources.jar:/usr/lib/jvm/java-8-oracle/j
                                re/lib/rt.jar:/usr/lib/jvm/java-8-oracle/jre/lib/sunrsasign.jar:/usr/lib/jvm/
                                java-8-oracle/jre/lib/jsse.jar:/usr/lib/jvm/java-8-oracle/jre/lib/jce.jar:/us
                                r/lib/jvm/java-8-oracle/jre/lib/charsets.jar:/usr/lib/jvm/java-8-oracle/jre/l
                                ib/jfr.jar:/usr/lib/jvm/java-8-oracle/jre/classes
 LIBRARY-PATH                   /usr/java/packages/lib/amd64:/usr/lib64:/lib64:/lib:/usr/lib

--------------------------------------------------------------------------------------------------------------
 CLASS-LOADING
--------------------------------------------------------------------------------------------------------------
 LOADED-CLASS-COUNT             7529
 TOTAL-LOADED-CLASS-COUNT       7529
 UNLOADED-CLASS-COUNT           0
 IS-VERBOSE                     false

--------------------------------------------------------------------------------------------------------------
 COMPILATION
--------------------------------------------------------------------------------------------------------------
 NAME                           HotSpot 64-Bit Tiered Compilers
 TOTAL-COMPILE-TIME             14921(ms)

--------------------------------------------------------------------------------------------------------------
 GARBAGE-COLLECTORS
--------------------------------------------------------------------------------------------------------------
 PS Scavenge                            name : PS Scavenge                                                                             
 [count/time (ms)]                      collectionCount : 7                                                                            
                                        collectionTime : 68                                                                            
                                                                                                                                       
 PS MarkSweep                           name : PS MarkSweep                                                                            
 [count/time (ms)]                      collectionCount : 1                                                                            
                                        collectionTime : 47 

--------------------------------------------------------------------------------------------------------------
 MEMORY-MANAGERS
--------------------------------------------------------------------------------------------------------------
 CodeCacheManager               Code Cache

 Metaspace Manager              Metaspace
                                Compressed Class Space

 Copy                           Eden Space
                                Survivor Space

 MarkSweepCompact               Eden Space
                                Survivor Space
                                Tenured Gen

--------------------------------------------------------------------------------------------------------------
 MEMORY
--------------------------------------------------------------------------------------------------------------
 HEAP-MEMORY-USAGE                      init : 268435456(256.0 MiB)                                                                    
 [memory in bytes]                      used : 18039504(17.2 MiB)                                                                      
                                        committed : 181403648(173.0 MiB)                                                               
                                        max : 3817865216(3.6 GiB)                                                                      
                                                                                                                                       
 NO-HEAP-MEMORY-USAGE                   init : 2555904(2.4 MiB)                                                                        
 [memory in bytes]                      used : 33926216(32.4 MiB)                                                                      
                                        committed : 35176448(33.5 MiB)                                                                 
                                        max : -1(-1 B)  

--------------------------------------------------------------------------------------------------------------
 OPERATING-SYSTEM
--------------------------------------------------------------------------------------------------------------
 OS                             Linux
 ARCH                           amd64
 PROCESSORS-COUNT               3
 LOAD-AVERAGE                   29.53
 VERSION                        4.15.0-52-generic

--------------------------------------------------------------------------------------------------------------
 THREAD
--------------------------------------------------------------------------------------------------------------
 COUNT                          30
 DAEMON-COUNT                   24
 PEAK-COUNT                     31
 STARTED-COUNT                  36
 DEADLOCK-COUNT                 0

--------------------------------------------------------------------------------------------------------------
 FILE-DESCRIPTOR
--------------------------------------------------------------------------------------------------------------
 MAX-FILE-DESCRIPTOR-COUNT      1048576
 OPEN-FILE-DESCRIPTOR-COUNT     100
Affect(row-cnt:0) cost in 88 ms.

THREAD相关:
COUNT: 							JVM当前活跃的线程数
DAEMON-COUNT: 					JVM当前活跃的守护线程数
PEAK-COUNT:JVM启动开始曾经活着的最大线程数
STARTED-COUNT:JVM启动开始总共启动过的线程次数
DEADLOCK-COUNT: 				JVM当前死锁的线程数

文件描述符相关:
MAX-FILE-DESCRIPTOR-COUNTJVM进程最大可以打开的文件描述符数
OPEN-FILE-DESCRIPTOR-COUNTJVM当前打开的文件描述符数

heapdump

dump java heap, 类似jmap命令的heap dump功能。

使用参考:
dump到指定文件:
[arthas@58205]$ heapdump /tmp/dump.hprof
Dumping heap to /tmp/dump.hprof...
Heap dump file created

只dump live对象:
[arthas@58205]$ heapdump --live /tmp/dump.hprof
Dumping heap to /tmp/dump.hprof...
Heap dump file created

dump到临时文件:
[arthas@58205]$ heapdump
Dumping heap to /var/folders/my/wy7c9w9j5732xbkcyt1mb4g40000gp/T/heapdump2019-09-03-16-385121018449645518991.hprof...
Heap dump file created

sysprop 和 sysenv

sysprop 查看和修改当前JVM的系统属性(System Property) 
sysenv  查看当前JVM的环境属性(System Environment Variables)

sysprop 和 sysenv使用方式类似

使用参考:
$ sysprop
 KEY                                                  VALUE
-------------------------------------------------------------------------------------------------------------------------------------
 java.runtime.name                                    Java(TM) SE Runtime Environment
 sun.boot.library.path                                /Library/Java/JavaVirtualMachines/jdk1.8.0_51.jdk/Contents/Home/jre/lib
 java.vm.version                                      25.51-b03
 user.country.format                                  CN
 gopherProxySet                                       false
 java.vm.vendor                                       Oracle Corporation
 java.vendor.url                                      http://java.oracle.com/
 path.separator                                       :
 java.vm.name                                         Java HotSpot(TM) 64-Bit Server VM
 file.encoding.pkg                                    sun.io
 user.country                                         US
 sun.java.launcher                                    SUN_STANDARD
 sun.os.patch.level                                   unknown
 java.vm.specification.name                           Java Virtual Machine Specification
 user.dir                                             /private/var/tmp
 java.runtime.version                                 1.8.0_51-b16
 java.awt.graphicsenv                                 sun.awt.CGraphicsEnvironment
 java.endorsed.dirs                                   /Library/Java/JavaVirtualMachines/jdk1.8.0_51.jdk/Contents/Home/jre/lib/endors
                                                      ed
 os.arch                                              x86_64
 java.io.tmpdir                                       /var/folders/2c/tbxwzs4s4sbcvh7frbcc7n000000gn/T/
 line.separator

 java.vm.specification.vendor                         Oracle Corporation
 os.name                                              Mac OS X
 sun.jnu.encoding                                     UTF-8
 java.library.path                                    /Users/wangtao/Library/Java/Extensions:/Library/Java/Extensions:/Network/Libra
                                                      ry/Java/Extensions:/System/Library/Java/Extensions:/usr/lib/java:.
 sun.nio.ch.bugLevel
 java.specification.name                              Java Platform API Specification
 java.class.version                                   52.0
 sun.management.compiler                              HotSpot 64-Bit Tiered Compilers
 os.version                                           10.12.6
 user.home                                            /Users/wangtao
 user.timezone                                        Asia/Shanghai
 java.awt.printerjob                                  sun.lwawt.macosx.CPrinterJob
 file.encoding                                        UTF-8
 java.specification.version                           1.8
 user.name                                            wangtao
 java.class.path                                      .
 java.vm.specification.version                        1.8
 sun.arch.data.model                                  64

查看单个属性 支持通过TAB键自动补全:
$ sysprop java.version
java.version=1.8.0_51

修改单个属性:
$ sysprop user.country
user.country=US
$ sysprop user.country CN
Successfully changed the system property.
user.country=CN

logger

查看logger信息,更新logger level

使用参考:
查看所有logger信息:
[arthas@2062]$ logger
 name                                   ROOT
 class                                  ch.qos.logback.classic.Logger
 classLoader                            sun.misc.Launcher$AppClassLoader@2a139a55
 classLoaderHash                        2a139a55
 level                                  INFO
 effectiveLevel                         INFO
 additivity                             true
 codeSource                             file:/Users/hengyunabc/.m2/repository/ch/qos/logback/logback-classic/1.2.3/logback-classic-1.2.3.jar
 appenders                              name            CONSOLE
                                        class           ch.qos.logback.core.ConsoleAppender
                                        classLoader     sun.misc.Launcher$AppClassLoader@2a139a55
                                        classLoaderHash 2a139a55
                                        target          System.out
                                        name            APPLICATION
                                        class           ch.qos.logback.core.rolling.RollingFileAppender
                                        classLoader     sun.misc.Launcher$AppClassLoader@2a139a55
                                        classLoaderHash 2a139a55
                                        file            app.log
                                        name            ASYNC
                                        class           ch.qos.logback.classic.AsyncAppender
                                        classLoader     sun.misc.Launcher$AppClassLoader@2a139a55
                                        classLoaderHash 2a139a55
                                        appenderRef     [APPLICATION]

从appenders的信息里,可以看到:
CONSOLE 				logger的target是System.out
APPLICATION 			logger是RollingFileAppender,它的file是app.log
ASYNC					它的appenderRef是APPLICATION,即异步输出到文件里

查看指定的logger信息:
按名字查找:
[arthas@2062]$ logger -n org.springframework.web
 name                                   org.springframework.web
 class                                  ch.qos.logback.classic.Logger
 classLoader                            sun.misc.Launcher$AppClassLoader@2a139a55
 classLoaderHash                        2a139a55
 level                                  null
 effectiveLevel                         INFO
 additivity                             true
 codeSource                             file:/Users/hengyunabc/.m2/repository/ch/qos/logback/logback-classic/1.2.3/logback-classic-1.2.3.jar

指定classloader查找:
注意hashcode是变化的,需要先查看当前的ClassLoader信息,提取对应ClassLoader的hashcode。
如果你使用-c,你需要手动输入hashcode:-c <hashcode>
[arthas@2062]$ logger -c 2a139a55
 name                                   ROOT
 class                                  ch.qos.logback.classic.Logger
 classLoader                            sun.misc.Launcher$AppClassLoader@2a139a55
 classLoaderHash                        2a139a55
 level                                  DEBUG
 effectiveLevel                         DEBUG
 additivity                             true
 codeSource                             file:/Users/hengyunabc/.m2/repository/ch/qos/logback/logback-classic/1.2.3/logback-classic-1.2.3.jar
 appenders                              name            CONSOLE
                                        class           ch.qos.logback.core.ConsoleAppender
                                        classLoader     sun.misc.Launcher$AppClassLoader@2a139a55
                                        classLoaderHash 2a139a55
                                        target          System.out
                                        name            APPLICATION
                                        class           ch.qos.logback.core.rolling.RollingFileAppender
                                        classLoader     sun.misc.Launcher$AppClassLoader@2a139a55
                                        classLoaderHash 2a139a55
                                        file            app.log
                                        name            ASYNC
                                        class           ch.qos.logback.classic.AsyncAppender
                                        classLoader     sun.misc.Launcher$AppClassLoader@2a139a55
                                        classLoaderHash 2a139a55
                                        appenderRef     [APPLICATION]

更新 logger level:
[arthas@2062]$ logger --name ROOT --level debug
update logger level success.

指定classloader更新 logger level:
默认情况下,logger命令会在SystemClassloader下执行,
如果应用是传统的war应用,或者spring boot fat jar启动的应用,那么需要指定classloader。
[arthas@2062]$ logger -c 2a139a55 --name ROOT --level debug

class/classloader相关
jad

反编译指定已加载类的源码

jad 命令将 JVM 中实际运行的 classbyte code 反编译成 java 代码,便于你理解业务逻辑;

在 Arthas Console 上,反编译出来的源码是带语法高亮的,阅读更方便

当然,反编译出来的 java 代码可能会存在语法错误,但不影响你进行阅读理解

使用参考:
编译java.lang.String:
$ jad java.lang.String
 
ClassLoader:
 
Location:
 
/*
* Decompiled with CFR 0_132.
*/
package java.lang;
 
import java.io.ObjectStreamField;
...
public final class String
implements Serializable,
Comparable<String>,
CharSequence {
    private final char[] value;
    private int hash;
    private static final long serialVersionUID = -6849794470754667710L;
    private static final ObjectStreamField[] serialPersistentFields = new ObjectStreamField[0];
    public static final Comparator<String> CASE_INSENSITIVE_ORDER = new CaseInsensitiveComparator();
 
    public String(byte[] arrby, int n, int n2) {
        String.checkBounds(arrby, n, n2);
        this.value = StringCoding.decode(arrby, n, n2);
    }
...

反编译时只显示源代码:
默认情况下,反编译结果里会带有ClassLoader信息,
通过--source-only选项,可以只打印源代码。
方便和mc/redefine命令结合使用。
$ jad --source-only demo.MathGame
/*
 * Decompiled with CFR 0_132.
 */
package demo;

import java.io.PrintStream;
import java.util.ArrayList;
import java.util.Iterator;
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;
...

反编译指定的函数:
jad demo.MathGame main

后台执行

arthas中的后台异步任务,使用了仿linux系统任务相关的命令。

1、使用&在后台执行任务
比如希望执行后台执行trace命令,那么调用下面命令
trace Test t & 
这时命令在后台执行,可以在console中继续执行其他命令。

2、通过jobs查看任务
如果希望查看当前有哪些arthas任务在执行,可以执行jobs命令,执行结果如下
kill job-id 	可以杀死指定任务
$ jobs
[10]*
       Stopped           watch com.taobao.container.Test test "params[0].{? #this.name == null }" -x 2
       execution count : 19
       start time      : Fri Sep 22 09:59:55 CST 2017
       timeout date    : Sat Sep 23 09:59:55 CST 2017
       session         : 3648e874-5e69-473f-9eed-7f89660b079b (current)

可以看到目前有一个后台任务在执行。
job id是10, * 表示此job是当前session创建
状态是Stopped
execution count是执行次数,从启动开始已经执行了19次
timeout date是超时的时间,到这个时间,任务将会自动超时退出

任务转换:
fg <job-id> 	可以把对应的任务转到前台继续执行
bg <job-id>		可以把对应的任务在后台继续执行

任务输出重定向:
可通过 > 或者 >> 将任务输出结果输出到指定的文件中,
可以和 & 一起使用,实现arthas命令的后台异步任务
$ trace Test t >> test.out &

其他
sc
sc命令官方文档

查看JVM已加载的类信息

参数说明:
class-pattern			类名表达式匹配
method-pattern			方法名表达式匹配
[d]						输出当前类的详细信息,
包括这个类所加载的原始文件来源、类的声明、加载的ClassLoader等详细信息。
如果一个类被多个ClassLoader所加载,则会出现多次
[E]						开启正则表达式匹配,默认为通配符匹配
[f]						输出当前类的成员变量信息(需要配合参数-d一起使用)
[x:]					指定输出静态变量时属性的遍历深度,默认为 0,即直接使用 toString 输出
[c:]					指定classClassLoader 的 hashcode
[classLoaderClass:]		指定执行表达式的 ClassLoaderclass name
[n:]					具有详细信息的匹配类的最大数量(默认为100)

特殊说明:
class-pattern支持全限定名,
如com.taobao.test.AAA,也支持com/taobao/test/AAA这样的格式,
这样,我们从异常堆栈里面把类名拷贝过来的时候,不需要在手动把/替换为.啦。

sc 默认开启了子类匹配功能,也就是说所有当前类的子类也会被搜索出来,
想要精确的匹配,请打开options disable-sub-class true开关

使用参考:
模糊搜索:
$ sc demo.*
demo.MathGame
Affect(row-cnt:1) cost in 55 ms.

打印类的详细信息:
$ sc -d demo.MathGame
class-info        demo.MathGame
code-source       /private/tmp/math-game.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@3d4eac69
                    +-sun.misc.Launcher$ExtClassLoader@66350f69
classLoaderHash   3d4eac69
 
Affect(row-cnt:1) cost in 875 ms.

打印出类的Field信息:
$ sc -d -f demo.MathGame
class-info        demo.MathGame
code-source       /private/tmp/math-game.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@3d4eac69
                    +-sun.misc.Launcher$ExtClassLoader@66350f69
classLoaderHash   3d4eac69
fields            modifierprivate,static
                  type    java.util.Random
                  name    random
                  value   java.util.Random@522b4
                          08a
 
                  modifierprivate
                  type    int
                  name    illegalArgumentCount
 
Affect(row-cnt:1) cost in 19 ms.

sm
sc命令官方文档

查看已加载类的方法信息

“Search-Method” 的简写,这个命令能搜索出所有已经加载了 Class 信息的方法信息。

sm 命令只能看到由当前类所声明 (declaring) 的方法,父类则无法看到。

参数说明:
class-pattern				类名表达式匹配
method-pattern				方法名表达式匹配
[d]							展示每个方法的详细信息
[E]							开启正则表达式匹配,默认为通配符匹配
[c:]						指定classClassLoader 的 hashcode
[classLoaderClass:]			指定执行表达式的 ClassLoaderclass name
[n:]						具有详细信息的匹配类的最大数量(默认为100)

使用参考:
$ sm java.lang.String
java.lang.String-><init>
java.lang.String->equals
java.lang.String->toString
java.lang.String->hashCode
java.lang.String->compareTo
java.lang.String->indexOf
java.lang.String->valueOf
java.lang.String->checkBounds
java.lang.String->length
java.lang.String->isEmpty
java.lang.String->charAt
java.lang.String->codePointAt
java.lang.String->codePointBefore
java.lang.String->codePointCount
java.lang.String->offsetByCodePoints
java.lang.String->getChars
java.lang.String->getBytes
java.lang.String->contentEquals
java.lang.String->nonSyncContentEquals
java.lang.String->equalsIgnoreCase
java.lang.String->compareToIgnoreCase
java.lang.String->regionMatches
java.lang.String->startsWith
java.lang.String->endsWith
java.lang.String->indexOfSupplementary
java.lang.String->lastIndexOf
java.lang.String->lastIndexOfSupplementary
java.lang.String->substring
java.lang.String->subSequence
java.lang.String->concat
java.lang.String->replace
java.lang.String->matches
java.lang.String->contains
java.lang.String->replaceFirst
java.lang.String->replaceAll
java.lang.String->split
java.lang.String->join
java.lang.String->toLowerCase
java.lang.String->toUpperCase
java.lang.String->trim
java.lang.String->toCharArray
java.lang.String->format
java.lang.String->copyValueOf
java.lang.String->intern
Affect(row-cnt:44) cost in 1342 ms.

$ sm -d java.lang.String toString
 declaring-class  java.lang.String
 method-name      toString
 modifier         public
 annotation
 parameters
 return           java.lang.String
 exceptions
 
Affect(row-cnt:1) cost in 3 ms.

火焰图 profiler
profiler官方文档

profiler 命令支持生成应用热点的火焰图。本质上是通过不断的采样,然后把收集到的采样结果生成火焰图。

使用逻辑为,采样开始--执行被测试动作--采样结束--分析。

profiler 命令基本运行结构是 profiler action [actionArg]

参数说明:
action			要执行的操作
actionArg		属性名模式
[i:]			采样间隔(单位:ns)(默认值:10'000'000,即10 ms)
[f:]			将输出转储到指定路径
[d:]			运行评测指定秒
[e:]			要跟踪哪个事件(cpu, alloc, lock, cache-misses等),默认是cpu

1、启动profiler
默认情况下,生成的是cpu的火焰图,即event为cpu。可以用-e/--event参数来指定。
$ profiler start
Started [cpu] profiling
也可以指定执行时间,比如,希望profiler执行 300 秒自动结束,可以用 -d/--duration 参数指定:
profiler start --duration 300

2、获取已采集的sample的数量
$ profiler getSamples
23

3、查看profiler状态
可以查看当前profiler在采样哪种event和采样时间。
$ profiler status
[cpu] profiling is running for 4 seconds

4、生成svg格式结果
默认情况下,生成的结果保存到应用的工作目录下的arthas-output目录里。
$ profiler stop
profiler output file: /tmp/demo/arthas-output/20191125-135546.svg
OK
也可以用--format参数指定:
$ profiler stop --format html
profiler output file: /tmp/test/arthas-output/20211207-111550.html
OK
或者在--file参数里用文件名指名格式。比如-f/--file /tmp/result.html。

简化命令:
profiler start -d 30 -e cpu -f /tmp/profiler.svg
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值