概述
- javaagent 技术广泛应用于对代码的增强,比如统计方法执行时间、GC 信息打印、分布式链路跟踪等;
- 实现方式包括 javassist 和 bytebuddy,bytebuddy 是对 javassist 的改进;
- 类似于 spring 中的 AOP;
Instrumentation 实现对 main 方法增强
说明:
- 新建两个项目,一个打包成增强 jar 包,一个写待增强业务代码;
- 可通过定义注解进行优化;
- 注意 maven 打包插件;
1)新建一个 maven 项目,引入 pom 依赖,并指定增强类:
<dependencies><!-- javaagent --><dependency><groupId>javassist</groupId><artifactId>javassist</artifactId><version>3.12.1.GA</version><type>jar</type></dependency>
</dependencies><build><plugins><!-- 测试javaagent相关 --><plugin><!-- 打普通的jar包 --><groupId>org.apache.maven.plugins</groupId><artifactId>maven-jar-plugin</artifactId><version>2.2</version><configuration><!-- 打包配置 --><archive><manifestEntries><Project-name>${project.name}</Project-name><Project-version>${project.version}</Project-version><!-- main方法之前需要处理的类 --><Premain-Class>com.firechou.test.javaagent.FireAgent</Premain-Class></manifestEntries></archive><skip>true</skip></configuration></plugin></plugins>
</build>
注意插件中 Premain-Class 指定的是增强类。
2)新建代理类,编写增强逻辑
public class FireAgent {/*** 在Instrumentation中有对应的说明:当jvm以代理类的方式启动时,Instrumentation的实例将传递给premain方法* @param args* @param instrumentation*/public static void premain(String args, Instrumentation instrumentation){System.out.println("agent premain(), args: " + args);}}
3) 打包成 jar
执行打包命令:
注意:不要执行 Plugins》jar》jar:jar 命令,会提示找不到目标类。
生成增强 jar 包如下:
4)在另一个项目中,新建业务代码类,即被增强的逻辑
public class FireAgentMainTest {public static void main(String[] args) {System.out.println("hello world");}
}
添加 JVM 运行参数:
-javaagent:test-javaagent/target/test-javaagent-1.0-SNAPSHOT.jar=name=jar&age=33
运行结果:
agent premain(), args: name=jar&age=33
hello world