本文记录常用的一些命令和场景
watch -x 3 -n 1 org.springframework.web.servlet.DispatcherServlet doDispatch '@org.springframework.web.context.request.RequestContextHolder@currentRequestAttributes().getRequest().xxx()'
注:xxx替换为实际方法,如getRequestParameterMap()可以查看请求入参; -n 1表示只取1次。
# 反编译类
jad demo.MainGame
# 反编译指定方法
jad demo.MainGame main
sc
命令可以查找到所有JVM已经加载到的类。 如果搜索的是接口,还会搜索所有的实现类。比如查看所有的 Filter
实现类
sc javax.servlet.Filter
通过 -d
参数,可以打印出类加载的具体信息,很方便查找类加载问题。
sc -d javax.servlet.Filter
sc
支持通配,比如搜索所有的 StringUtils
:
sc *StringUtils
sm
命令则是查找类的具体函数。比如:
sm java.math.RoundingMode
通过 -d
参数可以打印函数的具体属性:
sm -d java.math.RoundingMode
也可以查找特定的函数,比如查找构造函数:
sm java.math.RoundingMode <init>
在这个案例里,动态修改应用的Logger Level。
sc -d com.example.demo.arthas.user.UserController | grep classLoaderHash
$ sc -d com.example.demo.arthas.user.UserController | grep classLoaderHash
classLoaderHash 1be6f5c3
ognl -c 1be6f5c3 '@com.example.demo.arthas.user.UserController@log'
$ ognl -c 1be6f5c3 '@com.example.demo.arthas.user.UserController@log'
@Logger[
serialVersionUID=@Long[5454405123156820674],
FQCN=@String[ch.qos.logback.classic.Logger],
name=@String[com.example.demo.arthas.user.UserController],
level=null,
effectiveLevelInt=@Integer[20000],
parent=@Logger[Logger[com.example.demo.arthas.user]],
childrenList=null,
aai=null,
additive=@Boolean[true],
loggerContext=@LoggerContext[ch.qos.logback.classic.LoggerContext[default]],
]
可以知道 UserController@logger
实际使用的是logback。可以看到 level=null
,则说明实际最终的level是从 root
logger里来的。
ognl --classLoaderClass org.springframework.boot.loader.LaunchedURLClassLoader '@com.example.demo.arthas.user.UserController@logger.setLevel(@ch.qos.logback.classic.Level@DEBUG)'
再次获取 UserController@logger
,可以发现已经是 DEBUG
了:
ognl --classLoaderClass org.springframework.boot.loader.LaunchedURLClassLoader '@com.example.demo.arthas.user.UserController@logger'
$ ognl --classLoaderClass org.springframework.boot.loader.LaunchedURLClassLoader '@com.example.demo.arthas.user.UserController@logger'
@Logger[
serialVersionUID=@Long[5454405123156820674],
FQCN=@String[ch.qos.logback.classic.Logger],
name=@String[com.example.demo.arthas.user.UserController],
level=@Level[DEBUG],
effectiveLevelInt=@Integer[10000],
parent=@Logger[Logger[com.example.demo.arthas.user]],
childrenList=null,
aai=null,
additive=@Boolean[true],
loggerContext=@LoggerContext[ch.qos.logback.classic.LoggerContext[default]],
]
通过获取 root
logger,可以修改全局的logger level:
ognl --classLoaderClass org.springframework.boot.loader.LaunchedURLClassLoader '@org.slf4j.LoggerFactory@getLogger("root").setLevel(@ch.qos.logback.classic.Level@DEBUG)'