dz網(wǎng)站建設(shè)數(shù)據(jù)分析平臺(tái)
概述
- javaagent 技術(shù)廣泛應(yīng)用于對(duì)代碼的增強(qiáng),比如統(tǒng)計(jì)方法執(zhí)行時(shí)間、GC 信息打印、分布式鏈路跟蹤等;
- 實(shí)現(xiàn)方式包括 javassist 和 bytebuddy,bytebuddy 是對(duì) javassist 的改進(jìn);
- 類似于 spring 中的 AOP;
Instrumentation 實(shí)現(xiàn)對(duì) main 方法增強(qiáng)
說明:
- 新建兩個(gè)項(xiàng)目,一個(gè)打包成增強(qiáng) jar 包,一個(gè)寫待增強(qiáng)業(yè)務(wù)代碼;
- 可通過定義注解進(jìn)行優(yōu)化;
- 注意 maven 打包插件;
1)新建一個(gè) maven 項(xiàng)目,引入 pom 依賴,并指定增強(qiáng)類:
<dependencies><!-- javaagent --><dependency><groupId>javassist</groupId><artifactId>javassist</artifactId><version>3.12.1.GA</version><type>jar</type></dependency>
</dependencies><build><plugins><!-- 測(cè)試javaagent相關(guān) --><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 指定的是增強(qiáng)類。
2)新建代理類,編寫增強(qiáng)邏輯
public class FireAgent {/*** 在Instrumentation中有對(duì)應(yīng)的說明:當(dāng)jvm以代理類的方式啟動(dòng)時(shí),Instrumentation的實(shí)例將傳遞給premain方法* @param args* @param instrumentation*/public static void premain(String args, Instrumentation instrumentation){System.out.println("agent premain(), args: " + args);}}
3) 打包成 jar
執(zhí)行打包命令:
注意:不要執(zhí)行 Plugins》jar》jar:jar 命令,會(huì)提示找不到目標(biāo)類。
生成增強(qiáng) jar 包如下:
4)在另一個(gè)項(xiàng)目中,新建業(yè)務(wù)代碼類,即被增強(qiáng)的邏輯
public class FireAgentMainTest {public static void main(String[] args) {System.out.println("hello world");}
}
添加 JVM 運(yùn)行參數(shù):
-javaagent:test-javaagent/target/test-javaagent-1.0-SNAPSHOT.jar=name=jar&age=33
運(yùn)行結(jié)果:
agent premain(), args: name=jar&age=33
hello world