Skip to content

Commit 5f880f9

Browse files
committed
support jetty plugins
1 parent ea8d4a7 commit 5f880f9

File tree

19 files changed

+978
-1
lines changed

19 files changed

+978
-1
lines changed

apm-network/src/main/java/org/skywalking/apm/network/trace/component/ComponentsDefine.java

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -41,6 +41,10 @@ public class ComponentsDefine {
4141

4242
public static final OfficialComponent NUTZ_HTTP = new OfficialComponent(17, "NutzHttp");
4343

44+
public static final OfficialComponent JETTY_CLIENT = new OfficialComponent(18, "JettyClient");
45+
46+
public static final OfficialComponent JETTY_SERVER = new OfficialComponent(19, "JettyServer");
47+
4448
private static ComponentsDefine instance = new ComponentsDefine();
4549

4650
private String[] components;
@@ -50,7 +54,7 @@ public static ComponentsDefine getInstance() {
5054
}
5155

5256
public ComponentsDefine() {
53-
components = new String[18];
57+
components = new String[20];
5458
addComponent(TOMCAT);
5559
addComponent(HTTPCLIENT);
5660
addComponent(DUBBO);
@@ -68,6 +72,8 @@ public ComponentsDefine() {
6872
addComponent(STRUTS2);
6973
addComponent(NUTZ_MVC_ANNOTATION);
7074
addComponent(NUTZ_HTTP);
75+
addComponent(JETTY_CLIENT);
76+
addComponent(JETTY_SERVER);
7177
}
7278

7379
private void addComponent(OfficialComponent component) {

apm-sniffer/apm-agent/pom.xml

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -115,6 +115,16 @@
115115
<artifactId>apm-nutz-http-1.x-plugin</artifactId>
116116
<version>${project.version}</version>
117117
</dependency>
118+
<dependency>
119+
<groupId>org.skywalking</groupId>
120+
<artifactId>apm-jetty-client-9.x-plugin</artifactId>
121+
<version>${project.version}</version>
122+
</dependency>
123+
<dependency>
124+
<groupId>org.skywalking</groupId>
125+
<artifactId>apm-jetty-server-9.x-plugin</artifactId>
126+
<version>${project.version}</version>
127+
</dependency>
118128

119129
<!-- activation -->
120130
<dependency>
Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,24 @@
1+
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
2+
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
3+
<parent>
4+
<artifactId>jetty-plugins</artifactId>
5+
<groupId>org.skywalking</groupId>
6+
<version>3.2.1-2017</version>
7+
</parent>
8+
<modelVersion>4.0.0</modelVersion>
9+
10+
<artifactId>apm-jetty-client-9.x-plugin</artifactId>
11+
<packaging>jar</packaging>
12+
13+
<name>jetty-client-9.x-plugin</name>
14+
<url>http://maven.apache.org</url>
15+
16+
<dependencies>
17+
<dependency>
18+
<groupId>org.eclipse.jetty</groupId>
19+
<artifactId>jetty-client</artifactId>
20+
<version>9.0.0.v20130308</version>
21+
<scope>provided</scope>
22+
</dependency>
23+
</dependencies>
24+
</project>
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,52 @@
1+
package org.skywalking.apm.plugin.jetty.v9.client;
2+
3+
import java.lang.reflect.Method;
4+
import org.eclipse.jetty.client.HttpRequest;
5+
import org.eclipse.jetty.http.HttpFields;
6+
import org.skywalking.apm.agent.core.context.CarrierItem;
7+
import org.skywalking.apm.agent.core.context.ContextCarrier;
8+
import org.skywalking.apm.agent.core.context.ContextManager;
9+
import org.skywalking.apm.agent.core.context.tag.Tags;
10+
import org.skywalking.apm.agent.core.context.trace.AbstractSpan;
11+
import org.skywalking.apm.agent.core.context.trace.SpanLayer;
12+
import org.skywalking.apm.agent.core.plugin.interceptor.enhance.EnhancedInstance;
13+
import org.skywalking.apm.agent.core.plugin.interceptor.enhance.InstanceMethodsAroundInterceptor;
14+
import org.skywalking.apm.agent.core.plugin.interceptor.enhance.MethodInterceptResult;
15+
import org.skywalking.apm.network.trace.component.ComponentsDefine;
16+
17+
public class AsyncHttpRequestSendInterceptor implements InstanceMethodsAroundInterceptor {
18+
19+
@Override
20+
public void beforeMethod(EnhancedInstance objInst, Method method, Object[] allArguments, Class<?>[] argumentsTypes,
21+
MethodInterceptResult result) throws Throwable {
22+
HttpRequest request = (HttpRequest)objInst;
23+
ContextCarrier contextCarrier = new ContextCarrier();
24+
AbstractSpan span = ContextManager.createExitSpan(request.getURI().getPath(), contextCarrier, request.getHost() + ":" + request.getPort());
25+
span.setComponent(ComponentsDefine.JETTY_CLIENT);
26+
Tags.HTTP.METHOD.set(span, request.getMethod().asString());
27+
Tags.URL.set(span, request.getURI().toString());
28+
SpanLayer.asHttp(span);
29+
30+
CarrierItem next = contextCarrier.items();
31+
HttpFields field = request.getHeaders();
32+
while (next.hasNext()) {
33+
next = next.next();
34+
field.add(next.getHeadKey(), next.getHeadValue());
35+
}
36+
37+
EnhancedInstance callBackResult = (EnhancedInstance)allArguments[0];
38+
callBackResult.setSkyWalkingDynamicField(ContextManager.capture());
39+
}
40+
41+
@Override
42+
public Object afterMethod(EnhancedInstance objInst, Method method, Object[] allArguments, Class<?>[] argumentsTypes,
43+
Object ret) throws Throwable {
44+
ContextManager.stopSpan();
45+
return ret;
46+
}
47+
48+
@Override public void handleMethodException(EnhancedInstance objInst, Method method, Object[] allArguments,
49+
Class<?>[] argumentsTypes, Throwable t) {
50+
ContextManager.activeSpan().errorOccurred().log(t);
51+
}
52+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,52 @@
1+
package org.skywalking.apm.plugin.jetty.v9.client;
2+
3+
import java.lang.reflect.Method;
4+
import org.eclipse.jetty.client.api.Result;
5+
import org.eclipse.jetty.http.HttpFields;
6+
import org.skywalking.apm.agent.core.context.CarrierItem;
7+
import org.skywalking.apm.agent.core.context.ContextCarrier;
8+
import org.skywalking.apm.agent.core.context.ContextManager;
9+
import org.skywalking.apm.agent.core.context.ContextSnapshot;
10+
import org.skywalking.apm.agent.core.context.tag.Tags;
11+
import org.skywalking.apm.agent.core.context.trace.AbstractSpan;
12+
import org.skywalking.apm.agent.core.context.trace.SpanLayer;
13+
import org.skywalking.apm.agent.core.plugin.interceptor.enhance.EnhancedInstance;
14+
import org.skywalking.apm.agent.core.plugin.interceptor.enhance.InstanceMethodsAroundInterceptor;
15+
import org.skywalking.apm.agent.core.plugin.interceptor.enhance.MethodInterceptResult;
16+
import org.skywalking.apm.network.trace.component.ComponentsDefine;
17+
18+
public class CompleteListenerInterceptor implements InstanceMethodsAroundInterceptor {
19+
@Override
20+
public void beforeMethod(EnhancedInstance objInst, Method method, Object[] allArguments, Class<?>[] argumentsTypes,
21+
MethodInterceptResult result) throws Throwable {
22+
ContextSnapshot contextSnapshot = (ContextSnapshot)objInst.getSkyWalkingDynamicField();
23+
if (contextSnapshot != null) {
24+
Result callBackResult = (Result)allArguments[0];
25+
26+
AbstractSpan abstractSpan = ContextManager.createLocalSpan("CallBack/" + callBackResult.getRequest().getURI().getPath());
27+
ContextManager.continued(contextSnapshot);
28+
29+
if (callBackResult.isFailed()) {
30+
abstractSpan.errorOccurred().log(callBackResult.getFailure());
31+
Tags.STATUS_CODE.set(abstractSpan, Integer.toString(callBackResult.getResponse().getStatus()));
32+
}
33+
abstractSpan.setComponent(ComponentsDefine.JETTY_CLIENT);
34+
abstractSpan.setLayer(SpanLayer.HTTP);
35+
}
36+
}
37+
38+
@Override
39+
public Object afterMethod(EnhancedInstance objInst, Method method, Object[] allArguments, Class<?>[] argumentsTypes,
40+
Object ret) throws Throwable {
41+
ContextSnapshot contextSnapshot = (ContextSnapshot)objInst.getSkyWalkingDynamicField();
42+
if (contextSnapshot != null) {
43+
ContextManager.stopSpan();
44+
}
45+
return ret;
46+
}
47+
48+
@Override public void handleMethodException(EnhancedInstance objInst, Method method, Object[] allArguments,
49+
Class<?>[] argumentsTypes, Throwable t) {
50+
ContextManager.activeSpan().errorOccurred().log(t);
51+
}
52+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,49 @@
1+
package org.skywalking.apm.plugin.jetty.v9.client;
2+
3+
import java.lang.reflect.Method;
4+
import org.eclipse.jetty.client.HttpRequest;
5+
import org.eclipse.jetty.http.HttpFields;
6+
import org.skywalking.apm.agent.core.context.CarrierItem;
7+
import org.skywalking.apm.agent.core.context.ContextCarrier;
8+
import org.skywalking.apm.agent.core.context.ContextManager;
9+
import org.skywalking.apm.agent.core.context.tag.Tags;
10+
import org.skywalking.apm.agent.core.context.trace.AbstractSpan;
11+
import org.skywalking.apm.agent.core.context.trace.SpanLayer;
12+
import org.skywalking.apm.agent.core.plugin.interceptor.enhance.EnhancedInstance;
13+
import org.skywalking.apm.agent.core.plugin.interceptor.enhance.InstanceMethodsAroundInterceptor;
14+
import org.skywalking.apm.agent.core.plugin.interceptor.enhance.MethodInterceptResult;
15+
import org.skywalking.apm.network.trace.component.ComponentsDefine;
16+
17+
public class SyncHttpRequestSendInterceptor implements InstanceMethodsAroundInterceptor {
18+
19+
@Override
20+
public void beforeMethod(EnhancedInstance objInst, Method method, Object[] allArguments, Class<?>[] argumentsTypes,
21+
MethodInterceptResult result) throws Throwable {
22+
HttpRequest request = (HttpRequest)objInst;
23+
ContextCarrier contextCarrier = new ContextCarrier();
24+
AbstractSpan span = ContextManager.createExitSpan(request.getURI().getPath(), contextCarrier, request.getHost() + ":" + request.getPort());
25+
span.setComponent(ComponentsDefine.JETTY_CLIENT);
26+
Tags.HTTP.METHOD.set(span, "GET");
27+
Tags.URL.set(span, request.getURI().toString());
28+
SpanLayer.asHttp(span);
29+
30+
CarrierItem next = contextCarrier.items();
31+
HttpFields field = request.getHeaders();
32+
while (next.hasNext()) {
33+
next = next.next();
34+
field.add(next.getHeadKey(), next.getHeadValue());
35+
}
36+
}
37+
38+
@Override
39+
public Object afterMethod(EnhancedInstance objInst, Method method, Object[] allArguments, Class<?>[] argumentsTypes,
40+
Object ret) throws Throwable {
41+
ContextManager.stopSpan();
42+
return ret;
43+
}
44+
45+
@Override public void handleMethodException(EnhancedInstance objInst, Method method, Object[] allArguments,
46+
Class<?>[] argumentsTypes, Throwable t) {
47+
ContextManager.activeSpan().errorOccurred().log(t);
48+
}
49+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,53 @@
1+
package org.skywalking.apm.plugin.jetty.v9.client.define;
2+
3+
import net.bytebuddy.description.method.MethodDescription;
4+
import net.bytebuddy.matcher.ElementMatcher;
5+
import org.skywalking.apm.agent.core.plugin.interceptor.ConstructorInterceptPoint;
6+
import org.skywalking.apm.agent.core.plugin.interceptor.InstanceMethodsInterceptPoint;
7+
import org.skywalking.apm.agent.core.plugin.interceptor.enhance.ClassInstanceMethodsEnhancePluginDefine;
8+
import org.skywalking.apm.agent.core.plugin.match.ClassMatch;
9+
10+
import static net.bytebuddy.matcher.ElementMatchers.named;
11+
import static org.skywalking.apm.agent.core.plugin.match.HierarchyMatch.byHierarchyMatch;
12+
13+
/**
14+
* {@link CompleteListenerInstrumentation} enhance the <code>onComplete</code> method in all class of hierarchy
15+
* <code>org.eclipse.jetty.client.api.Response$CompleteListener</code> by <code>org.skywalking.apm.plugin.jetty.client.CompleteListenerInterceptor</code>
16+
*
17+
* @author zhangxin
18+
*/
19+
public class CompleteListenerInstrumentation extends ClassInstanceMethodsEnhancePluginDefine {
20+
21+
private static final String ENHANCE_CLASS = "org.eclipse.jetty.client.api.Response$CompleteListener";
22+
private static final String ENHANCE_METHOD = "onComplete";
23+
public static final String SEND_INTERCEPTOR = "org.skywalking.apm.plugin.jetty.client.CompleteListenerInterceptor";
24+
25+
@Override protected ConstructorInterceptPoint[] getConstructorsInterceptPoints() {
26+
return new ConstructorInterceptPoint[0];
27+
}
28+
29+
@Override protected InstanceMethodsInterceptPoint[] getInstanceMethodsInterceptPoints() {
30+
return new InstanceMethodsInterceptPoint[] {
31+
new InstanceMethodsInterceptPoint() {
32+
@Override
33+
public ElementMatcher<MethodDescription> getMethodsMatcher() {
34+
return named(ENHANCE_METHOD);
35+
}
36+
37+
@Override
38+
public String getMethodsInterceptor() {
39+
return SEND_INTERCEPTOR;
40+
}
41+
42+
@Override
43+
public boolean isOverrideArgs() {
44+
return false;
45+
}
46+
}
47+
};
48+
}
49+
50+
@Override protected ClassMatch enhanceClass() {
51+
return byHierarchyMatch(new String[] {ENHANCE_CLASS});
52+
}
53+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,70 @@
1+
package org.skywalking.apm.plugin.jetty.v9.client.define;
2+
3+
import net.bytebuddy.description.method.MethodDescription;
4+
import net.bytebuddy.matcher.ElementMatcher;
5+
import org.skywalking.apm.agent.core.plugin.interceptor.ConstructorInterceptPoint;
6+
import org.skywalking.apm.agent.core.plugin.interceptor.InstanceMethodsInterceptPoint;
7+
import org.skywalking.apm.agent.core.plugin.interceptor.enhance.ClassInstanceMethodsEnhancePluginDefine;
8+
import org.skywalking.apm.agent.core.plugin.match.ClassMatch;
9+
10+
import static net.bytebuddy.matcher.ElementMatchers.named;
11+
import static net.bytebuddy.matcher.ElementMatchers.takesArguments;
12+
import static org.skywalking.apm.agent.core.plugin.bytebuddy.ArgumentTypeNameMatch.takesArgumentWithType;
13+
import static org.skywalking.apm.agent.core.plugin.match.NameMatch.byName;
14+
15+
/**
16+
* {@link HttpRequestInstrumentation} enhance the <code>send</code> method without argument in
17+
* <code>org.eclipse.jetty.client.HttpRequest</code> by <code>org.skywalking.apm.plugin.jetty.client.SyncHttpRequestSendInterceptor</code>
18+
* and enhance the <code>send</code> with <code>org.eclipse.jetty.client.api.Response$CompleteListener</code> parameter
19+
* by <code>org.skywalking.apm.plugin.jetty.client.AsyncHttpRequestSendInterceptor</code>
20+
*
21+
* @author zhangxin
22+
*/
23+
public class HttpRequestInstrumentation extends ClassInstanceMethodsEnhancePluginDefine {
24+
25+
private static final String ENHANCE_CLASS = "org.eclipse.jetty.client.HttpRequest";
26+
private static final String ENHANCE_CLASS_NAME = "send";
27+
public static final String ASYNC_SEND_INTERCEPTOR = "org.skywalking.apm.plugin.jetty.client.AsyncHttpRequestSendInterceptor";
28+
public static final String SYNC_SEND_INTERCEPTOR = "org.skywalking.apm.plugin.jetty.client.SyncHttpRequestSendInterceptor";
29+
30+
@Override protected ConstructorInterceptPoint[] getConstructorsInterceptPoints() {
31+
return new ConstructorInterceptPoint[0];
32+
}
33+
34+
@Override protected InstanceMethodsInterceptPoint[] getInstanceMethodsInterceptPoints() {
35+
return new InstanceMethodsInterceptPoint[] {
36+
new InstanceMethodsInterceptPoint() {
37+
//sync call interceptor point
38+
@Override public ElementMatcher<MethodDescription> getMethodsMatcher() {
39+
return named(ENHANCE_CLASS_NAME).and(takesArguments(0));
40+
}
41+
42+
@Override public String getMethodsInterceptor() {
43+
return SYNC_SEND_INTERCEPTOR;
44+
}
45+
46+
@Override public boolean isOverrideArgs() {
47+
return false;
48+
}
49+
},
50+
new InstanceMethodsInterceptPoint() {
51+
//async call interceptor point
52+
@Override public ElementMatcher<MethodDescription> getMethodsMatcher() {
53+
return named(ENHANCE_CLASS_NAME).and(takesArgumentWithType(0, "org.eclipse.jetty.client.api.Response$CompleteListener"));
54+
}
55+
56+
@Override public String getMethodsInterceptor() {
57+
return ASYNC_SEND_INTERCEPTOR;
58+
}
59+
60+
@Override public boolean isOverrideArgs() {
61+
return false;
62+
}
63+
}
64+
};
65+
}
66+
67+
@Override protected ClassMatch enhanceClass() {
68+
return byName(ENHANCE_CLASS);
69+
}
70+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,2 @@
1+
jetty-client-9.x=org.skywalking.apm.plugin.jetty.v9.client.define.CompleteListenerInstrumentation
2+
jetty-client-9.x=org.skywalking.apm.plugin.jetty.v9.client.define.HttpRequestInstrumentation

0 commit comments

Comments
 (0)