Skip to content

Commit db36f36

Browse files
committed
小傅哥 | init sqm project
1 parent 13088c8 commit db36f36

File tree

12 files changed

+700
-1
lines changed

12 files changed

+700
-1
lines changed

README.md

+1-1
Original file line numberDiff line numberDiff line change
@@ -1,2 +1,2 @@
11
# SQM
2-
SQM
2+
服务质量监控,javaagent+asm

pom.xml

+127
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,127 @@
1+
<?xml version="1.0" encoding="UTF-8"?>
2+
<project xmlns="http://maven.apache.org/POM/4.0.0"
3+
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
4+
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
5+
<modelVersion>4.0.0</modelVersion>
6+
7+
<groupId>org.itstack</groupId>
8+
<artifactId>SQM</artifactId>
9+
<version>1.0-SNAPSHOT</version>
10+
11+
<properties>
12+
<!-- Build args -->
13+
<argline>-Xms512m -Xmx512m</argline>
14+
<skip_maven_deploy>false</skip_maven_deploy>
15+
<updateReleaseInfo>true</updateReleaseInfo>
16+
<project.build.sourceEncoding>utf-8</project.build.sourceEncoding>
17+
<maven.test.skip>true</maven.test.skip>
18+
<!-- 自定义MANIFEST.MF -->
19+
<maven.configuration.manifestFile>src/main/resources/META-INF/MANIFEST.MF</maven.configuration.manifestFile>
20+
</properties>
21+
22+
<dependencies>
23+
<dependency>
24+
<groupId>org.ow2.asm</groupId>
25+
<artifactId>asm-commons</artifactId>
26+
<version>6.2.1</version>
27+
<exclusions>
28+
<exclusion>
29+
<groupId>org.ow2.asm</groupId>
30+
<artifactId>asm-analysis</artifactId>
31+
</exclusion>
32+
<exclusion>
33+
<groupId>org.ow2.asm</groupId>
34+
<artifactId>asm-tree</artifactId>
35+
</exclusion>
36+
</exclusions>
37+
</dependency>
38+
<dependency>
39+
<groupId>junit</groupId>
40+
<artifactId>junit</artifactId>
41+
<version>4.9</version>
42+
<scope>test</scope>
43+
</dependency>
44+
<dependency>
45+
<groupId>com.alibaba</groupId>
46+
<artifactId>fastjson</artifactId>
47+
<version>1.2.40</version>
48+
</dependency>
49+
<dependency>
50+
<groupId>org.slf4j</groupId>
51+
<artifactId>slf4j-api</artifactId>
52+
<version>1.7.24</version>
53+
</dependency>
54+
<dependency>
55+
<groupId>com.alibaba</groupId>
56+
<artifactId>fastjson</artifactId>
57+
<version>1.2.67</version>
58+
</dependency>
59+
</dependencies>
60+
61+
<build>
62+
<sourceDirectory>src/main/java</sourceDirectory>
63+
<resources>
64+
<resource>
65+
<directory>src/main/resources</directory>
66+
<filtering>true</filtering>
67+
<includes>
68+
<include>**/**</include>
69+
</includes>
70+
</resource>
71+
</resources>
72+
<testSourceDirectory>src/test/java</testSourceDirectory>
73+
<testResources>
74+
<testResource>
75+
<directory>src/test/resources</directory>
76+
<filtering>true</filtering>
77+
<includes>
78+
<include>**/**</include>
79+
</includes>
80+
</testResource>
81+
</testResources>
82+
<plugins>
83+
<plugin>
84+
<groupId>org.apache.maven.plugins</groupId>
85+
<artifactId>maven-jar-plugin</artifactId>
86+
<version>2.4</version>
87+
<configuration>
88+
<archive>
89+
<manifestFile>${maven.configuration.manifestFile}</manifestFile>
90+
</archive>
91+
</configuration>
92+
</plugin>
93+
<plugin>
94+
<groupId>org.apache.maven.plugins</groupId>
95+
<artifactId>maven-resources-plugin</artifactId>
96+
<version>2.5</version>
97+
<configuration>
98+
<encoding>${project.build.sourceEncoding}</encoding>
99+
</configuration>
100+
</plugin>
101+
<plugin>
102+
<groupId>org.apache.maven.plugins</groupId>
103+
<artifactId>maven-compiler-plugin</artifactId>
104+
<version>2.3.2</version>
105+
<configuration>
106+
<source>1.8</source>
107+
<target>1.8</target>
108+
<encoding>${project.build.sourceEncoding}</encoding>
109+
</configuration>
110+
</plugin>
111+
<plugin>
112+
<groupId>org.apache.maven.plugins</groupId>
113+
<artifactId>maven-source-plugin</artifactId>
114+
<version>2.1.2</version>
115+
<executions>
116+
<execution>
117+
<id>attach-sources</id>
118+
<goals>
119+
<goal>jar</goal>
120+
</goals>
121+
</execution>
122+
</executions>
123+
</plugin>
124+
</plugins>
125+
</build>
126+
127+
</project>
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
package org.itstack.sqm.asm;
2+
3+
import org.itstack.sqm.asm.probe.ProfilingTransformer;
4+
5+
import java.lang.instrument.Instrumentation;
6+
7+
public class PreMain {
8+
9+
//JVM 首先尝试在代理类上调用以下方法
10+
public static void premain(String agentArgs, Instrumentation inst) {
11+
inst.addTransformer(new ProfilingTransformer());
12+
}
13+
14+
//如果代理类没有实现上面的方法,那么 JVM 将尝试调用该方法
15+
public static void premain(String agentArgs) {
16+
}
17+
18+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,52 @@
1+
package org.itstack.sqm.asm.probe;
2+
3+
import com.alibaba.fastjson.JSON;
4+
import org.itstack.sqm.base.MethodTag;
5+
6+
import java.util.concurrent.atomic.AtomicInteger;
7+
import java.util.concurrent.atomic.AtomicReferenceArray;
8+
9+
public final class ProfilingAspect {
10+
11+
public static final int MAX_NUM = 1024 * 32;
12+
13+
private final static AtomicInteger index = new AtomicInteger(0);
14+
private final static AtomicReferenceArray<MethodTag> methodTagArr = new AtomicReferenceArray<>(MAX_NUM);
15+
16+
public static int generateMethodId(MethodTag tag) {
17+
int methodId = index.getAndIncrement();
18+
if (methodId > MAX_NUM) return -1;
19+
methodTagArr.set(methodId, tag);
20+
return methodId;
21+
}
22+
23+
public static void point(final long startNanos, final int methodId) {
24+
MethodTag method = methodTagArr.get(methodId);
25+
System.out.println("类名:" + method.getFullClassName());
26+
System.out.println("方法:" + method.getMethodName());
27+
System.out.println("耗时:" + (System.nanoTime() - startNanos) / 1000000 + "(s)");
28+
}
29+
30+
public static void point(final long startNanos, final int methodId, Object[] requests) {
31+
MethodTag method = methodTagArr.get(methodId);
32+
System.out.println("类名:" + method.getFullClassName());
33+
System.out.println("方法:" + method.getMethodName());
34+
System.out.println("参数[类型]:" + JSON.toJSONString(method.getParameterTypeList()));
35+
System.out.println("参数[值]:" + JSON.toJSONString(requests));
36+
System.out.println("耗时:" + (System.nanoTime() - startNanos) / 1000000 + "(s)");
37+
}
38+
39+
public static void point(final long startNanos, final int methodId, Object[] requests, Object response) {
40+
MethodTag method = methodTagArr.get(methodId);
41+
System.out.println("监控 - Begin");
42+
System.out.println("类名:" + method.getFullClassName());
43+
System.out.println("方法:" + method.getMethodName());
44+
System.out.println("入参类型:" + JSON.toJSONString(method.getParameterTypeList()));
45+
System.out.println("入数[值]:" + JSON.toJSONString(requests));
46+
System.out.println("出参类型:" + method.getReturnParameterType());
47+
System.out.println("出参[值]:" + JSON.toJSONString(response));
48+
System.out.println("耗时:" + (System.nanoTime() - startNanos) / 1000000 + "(s)");
49+
System.out.println("监控 - End\r\n");
50+
}
51+
52+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,61 @@
1+
package org.itstack.sqm.asm.probe;
2+
3+
import org.itstack.sqm.config.ProfilingFilter;
4+
import org.objectweb.asm.ClassVisitor;
5+
import org.objectweb.asm.MethodVisitor;
6+
7+
import static org.objectweb.asm.Opcodes.*;
8+
9+
public class ProfilingClassAdapter extends ClassVisitor {
10+
11+
private final String className;
12+
private final String fullClazzName;
13+
private final String simpleClassName;
14+
15+
private boolean isInterface;
16+
17+
public ProfilingClassAdapter(final ClassVisitor cv, String className) {
18+
super(ASM5, cv);
19+
this.className = className;
20+
this.fullClazzName = className.replace('/', '.');
21+
this.simpleClassName = className.substring(className.lastIndexOf('/') + 1);
22+
}
23+
24+
@Override
25+
public void visit(int version, int access, String name, String signature, String superName, String[] interfaces) {
26+
super.visit(version, access, name, signature, superName, interfaces);
27+
this.isInterface = (access & ACC_INTERFACE) != 0;
28+
}
29+
30+
@Override
31+
public MethodVisitor visitMethod(int access, String name, String descriptor, String signature, String[] exceptions) {
32+
33+
// 不对接口和私有方法注入
34+
if (isInterface || (access & ACC_PRIVATE) != 0) {
35+
return super.visitMethod(access, name, descriptor, signature, exceptions);
36+
}
37+
38+
//不对抽象方法、native方法、桥接方法、合成方法进行注入
39+
if ((access & ACC_ABSTRACT) != 0
40+
|| (access & ACC_NATIVE) != 0
41+
|| (access & ACC_BRIDGE) != 0
42+
|| (access & ACC_SYNTHETIC) != 0) {
43+
return super.visitMethod(access, name, descriptor, signature, exceptions);
44+
}
45+
46+
if ("<init>".equals(name) || "<clinit>".equals(name)) {
47+
return super.visitMethod(access, name, descriptor, signature, exceptions);
48+
}
49+
50+
// 过滤Object类默认方法
51+
if (ProfilingFilter.isNotNeedInjectMethod(name)) {
52+
return super.visitMethod(access, name, descriptor, signature, exceptions);
53+
}
54+
55+
MethodVisitor mv = cv.visitMethod(access, name, descriptor, signature, exceptions);
56+
if (null == mv) return null;
57+
58+
return new ProfilingMethodVisitor(access, name, descriptor, mv, className, fullClazzName, simpleClassName);
59+
}
60+
61+
}

0 commit comments

Comments
 (0)