Merge branch 'master' into feature/423
This commit is contained in:
commit
3bc3cc53ea
|
|
@ -12,7 +12,7 @@ Sky Walking | [中文](README_ZH.md)
|
|||
|
||||
|
||||
* Auto instrumentation by javaagent, **no need to CHANGE any application source code**.
|
||||
* High performance agent. Only increase extra **10%** cpu cost in 5000+ tps application, even **do not need to use sampling mechanism**, [check test reports](#test-reports).
|
||||
* High performance agent. Only increase extra **10%** cpu cost in 5000+ tps application, even **When collect all traces**, [check test reports](#test-reports).
|
||||
* [Supported middlewares, frameworks and libraries](https://github.com/OpenSkywalking/sky-walking/wiki/3.2-supported-list).
|
||||
* Manual instrumentation
|
||||
* As an [OpenTracing supported tracer](http://opentracing.io/documentation/pages/supported-tracers)
|
||||
|
|
|
|||
|
|
@ -41,11 +41,11 @@ public class JVMMetricsServiceHandlerTestCase {
|
|||
|
||||
private final Logger logger = LoggerFactory.getLogger(JVMMetricsServiceHandlerTestCase.class);
|
||||
|
||||
private static JVMMetricsServiceGrpc.JVMMetricsServiceBlockingStub stub;
|
||||
private static JVMMetricsServiceGrpc.JVMMetricsServiceBlockingStub STUB;
|
||||
|
||||
public static void main(String[] args) {
|
||||
ManagedChannel channel = ManagedChannelBuilder.forAddress("localhost", 11800).usePlaintext(true).build();
|
||||
stub = JVMMetricsServiceGrpc.newBlockingStub(channel);
|
||||
STUB = JVMMetricsServiceGrpc.newBlockingStub(channel);
|
||||
|
||||
final long timeInterval = 1;
|
||||
Executors.newSingleThreadScheduledExecutor().scheduleAtFixedRate(() -> multiInstanceJvmSend(), 1, timeInterval, TimeUnit.SECONDS);
|
||||
|
|
@ -68,7 +68,7 @@ public class JVMMetricsServiceHandlerTestCase {
|
|||
buildGcMetric(jvmMetric);
|
||||
|
||||
jvmMetricsBuilder.addMetrics(jvmMetric.build());
|
||||
stub.collect(jvmMetricsBuilder.build());
|
||||
STUB.collect(jvmMetricsBuilder.build());
|
||||
}
|
||||
|
||||
private static void buildCpuMetric(JVMMetric.Builder jvmMetric) {
|
||||
|
|
@ -78,21 +78,21 @@ public class JVMMetricsServiceHandlerTestCase {
|
|||
}
|
||||
|
||||
private static void buildMemoryMetric(JVMMetric.Builder jvmMetric) {
|
||||
Memory.Builder builder_1 = Memory.newBuilder();
|
||||
builder_1.setIsHeap(true);
|
||||
builder_1.setInit(20);
|
||||
builder_1.setMax(100);
|
||||
builder_1.setUsed(50);
|
||||
builder_1.setCommitted(30);
|
||||
jvmMetric.addMemory(builder_1.build());
|
||||
Memory.Builder builderHeap = Memory.newBuilder();
|
||||
builderHeap.setIsHeap(true);
|
||||
builderHeap.setInit(20);
|
||||
builderHeap.setMax(100);
|
||||
builderHeap.setUsed(50);
|
||||
builderHeap.setCommitted(30);
|
||||
jvmMetric.addMemory(builderHeap.build());
|
||||
|
||||
Memory.Builder builder_2 = Memory.newBuilder();
|
||||
builder_2.setIsHeap(false);
|
||||
builder_2.setInit(200);
|
||||
builder_2.setMax(1000);
|
||||
builder_2.setUsed(500);
|
||||
builder_2.setCommitted(300);
|
||||
jvmMetric.addMemory(builder_2.build());
|
||||
Memory.Builder builderNonHeap = Memory.newBuilder();
|
||||
builderNonHeap.setIsHeap(false);
|
||||
builderNonHeap.setInit(200);
|
||||
builderNonHeap.setMax(1000);
|
||||
builderNonHeap.setUsed(500);
|
||||
builderNonHeap.setCommitted(300);
|
||||
jvmMetric.addMemory(builderNonHeap.build());
|
||||
}
|
||||
|
||||
private static void buildMemoryPoolMetric(JVMMetric.Builder jvmMetric) {
|
||||
|
|
|
|||
|
|
@ -23,12 +23,16 @@ import io.grpc.ManagedChannelBuilder;
|
|||
import org.skywalking.apm.network.proto.Application;
|
||||
import org.skywalking.apm.network.proto.ApplicationMapping;
|
||||
import org.skywalking.apm.network.proto.ApplicationRegisterServiceGrpc;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
|
||||
/**
|
||||
* @author pengys5
|
||||
*/
|
||||
public class ApplicationRegisterServiceHandlerTestCase {
|
||||
|
||||
private final Logger logger = LoggerFactory.getLogger(ApplicationRegisterServiceHandlerTestCase.class);
|
||||
|
||||
private ApplicationRegisterServiceGrpc.ApplicationRegisterServiceBlockingStub stub;
|
||||
|
||||
public void testRegister() {
|
||||
|
|
@ -37,6 +41,6 @@ public class ApplicationRegisterServiceHandlerTestCase {
|
|||
|
||||
Application application = Application.newBuilder().addApplicationCode("test141").build();
|
||||
ApplicationMapping mapping = stub.register(application);
|
||||
System.out.println(mapping.getApplication(0).getKey() + ", " + mapping.getApplication(0).getValue());
|
||||
logger.debug(mapping.getApplication(0).getKey() + ", " + mapping.getApplication(0).getValue());
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -91,42 +91,42 @@ public class TraceSegmentServiceHandlerTestCase {
|
|||
segmentBuilder.setApplicationInstanceId(2);
|
||||
segmentBuilder.setTraceSegmentId(UniqueId.newBuilder().addIdParts(200).addIdParts(200).addIdParts(200).build());
|
||||
|
||||
SpanObject.Builder span_0 = SpanObject.newBuilder();
|
||||
span_0.setSpanId(0);
|
||||
span_0.setOperationName("/dubbox-case/case/dubbox-rest");
|
||||
span_0.setOperationNameId(0);
|
||||
span_0.setParentSpanId(-1);
|
||||
span_0.setSpanLayer(SpanLayer.Http);
|
||||
span_0.setStartTime(now);
|
||||
span_0.setEndTime(now + 100000);
|
||||
span_0.setComponentId(ComponentsDefine.TOMCAT.getId());
|
||||
span_0.setIsError(false);
|
||||
span_0.setSpanType(SpanType.Entry);
|
||||
span_0.setPeerId(2);
|
||||
span_0.setPeer("localhost:8082");
|
||||
SpanObject.Builder span0 = SpanObject.newBuilder();
|
||||
span0.setSpanId(0);
|
||||
span0.setOperationName("/dubbox-case/case/dubbox-rest");
|
||||
span0.setOperationNameId(0);
|
||||
span0.setParentSpanId(-1);
|
||||
span0.setSpanLayer(SpanLayer.Http);
|
||||
span0.setStartTime(now);
|
||||
span0.setEndTime(now + 100000);
|
||||
span0.setComponentId(ComponentsDefine.TOMCAT.getId());
|
||||
span0.setIsError(false);
|
||||
span0.setSpanType(SpanType.Entry);
|
||||
span0.setPeerId(2);
|
||||
span0.setPeer("localhost:8082");
|
||||
|
||||
LogMessage.Builder log_0 = LogMessage.newBuilder();
|
||||
log_0.setTime(now);
|
||||
log_0.addData(KeyWithStringValue.newBuilder().setKey("log1").setValue("value1"));
|
||||
log_0.addData(KeyWithStringValue.newBuilder().setKey("log2").setValue("value2"));
|
||||
log_0.addData(KeyWithStringValue.newBuilder().setKey("log3").setValue("value3"));
|
||||
span_0.addLogs(log_0.build());
|
||||
LogMessage.Builder log0 = LogMessage.newBuilder();
|
||||
log0.setTime(now);
|
||||
log0.addData(KeyWithStringValue.newBuilder().setKey("log1").setValue("value1"));
|
||||
log0.addData(KeyWithStringValue.newBuilder().setKey("log2").setValue("value2"));
|
||||
log0.addData(KeyWithStringValue.newBuilder().setKey("log3").setValue("value3"));
|
||||
span0.addLogs(log0.build());
|
||||
|
||||
span_0.addTags(KeyWithStringValue.newBuilder().setKey("tag1").setValue("value1"));
|
||||
span_0.addTags(KeyWithStringValue.newBuilder().setKey("tag2").setValue("value2"));
|
||||
span_0.addTags(KeyWithStringValue.newBuilder().setKey("tag3").setValue("value3"));
|
||||
segmentBuilder.addSpans(span_0);
|
||||
span0.addTags(KeyWithStringValue.newBuilder().setKey("tag1").setValue("value1"));
|
||||
span0.addTags(KeyWithStringValue.newBuilder().setKey("tag2").setValue("value2"));
|
||||
span0.addTags(KeyWithStringValue.newBuilder().setKey("tag3").setValue("value3"));
|
||||
segmentBuilder.addSpans(span0);
|
||||
|
||||
TraceSegmentReference.Builder ref_0 = TraceSegmentReference.newBuilder();
|
||||
ref_0.setEntryServiceId(1);
|
||||
ref_0.setEntryServiceName("ServiceName");
|
||||
ref_0.setNetworkAddress("localhost:8081");
|
||||
ref_0.setNetworkAddressId(1);
|
||||
ref_0.setParentApplicationInstanceId(1);
|
||||
ref_0.setParentServiceId(1);
|
||||
ref_0.setParentServiceName("");
|
||||
ref_0.setParentSpanId(2);
|
||||
ref_0.setParentTraceSegmentId(UniqueId.newBuilder().addIdParts(100).addIdParts(100).addIdParts(100).build());
|
||||
TraceSegmentReference.Builder ref0 = TraceSegmentReference.newBuilder();
|
||||
ref0.setEntryServiceId(1);
|
||||
ref0.setEntryServiceName("ServiceName");
|
||||
ref0.setNetworkAddress("localhost:8081");
|
||||
ref0.setNetworkAddressId(1);
|
||||
ref0.setParentApplicationInstanceId(1);
|
||||
ref0.setParentServiceId(1);
|
||||
ref0.setParentServiceName("");
|
||||
ref0.setParentSpanId(2);
|
||||
ref0.setParentTraceSegmentId(UniqueId.newBuilder().addIdParts(100).addIdParts(100).addIdParts(100).build());
|
||||
// segmentBuilder.addRefs(ref_0);
|
||||
|
||||
builder.setSegment(segmentBuilder.build().toByteString());
|
||||
|
|
|
|||
|
|
@ -34,7 +34,6 @@ public class TraceSegmentJsonReaderTestCase {
|
|||
public void testRead() throws IOException {
|
||||
TraceSegmentJsonReader reader = new TraceSegmentJsonReader();
|
||||
JsonElement jsonElement = JsonFileReader.INSTANCE.read("json/segment/normal/dubbox-consumer.json");
|
||||
System.out.println(jsonElement.toString());
|
||||
|
||||
JsonReader jsonReader = new JsonReader(new StringReader(jsonElement.toString()));
|
||||
jsonReader.beginArray();
|
||||
|
|
|
|||
|
|
@ -64,14 +64,14 @@ public class SegmentPost {
|
|||
ServiceNameEsDAO serviceNameEsDAO = new ServiceNameEsDAO();
|
||||
serviceNameEsDAO.setClient(client);
|
||||
|
||||
ServiceNameDataDefine.ServiceName serviceName_1 = new ServiceNameDataDefine.ServiceName("1", "", 0, 1);
|
||||
serviceNameEsDAO.save(serviceName_1);
|
||||
ServiceNameDataDefine.ServiceName serviceName_2 = new ServiceNameDataDefine.ServiceName("2", "org.skywaking.apm.testcase.dubbo.services.GreetService.doBusiness()", 2, 2);
|
||||
serviceNameEsDAO.save(serviceName_2);
|
||||
ServiceNameDataDefine.ServiceName serviceName_3 = new ServiceNameDataDefine.ServiceName("3", "/dubbox-case/case/dubbox-rest", 2, 3);
|
||||
serviceNameEsDAO.save(serviceName_3);
|
||||
ServiceNameDataDefine.ServiceName serviceName_4 = new ServiceNameDataDefine.ServiceName("4", "org.skywaking.apm.testcase.dubbo.services.GreetService.doBusiness()", 3, 4);
|
||||
serviceNameEsDAO.save(serviceName_4);
|
||||
ServiceNameDataDefine.ServiceName serviceName1 = new ServiceNameDataDefine.ServiceName("1", "", 0, 1);
|
||||
serviceNameEsDAO.save(serviceName1);
|
||||
ServiceNameDataDefine.ServiceName serviceName2 = new ServiceNameDataDefine.ServiceName("2", "org.skywaking.apm.testcase.dubbo.services.GreetService.doBusiness()", 2, 2);
|
||||
serviceNameEsDAO.save(serviceName2);
|
||||
ServiceNameDataDefine.ServiceName serviceName3 = new ServiceNameDataDefine.ServiceName("3", "/dubbox-case/case/dubbox-rest", 2, 3);
|
||||
serviceNameEsDAO.save(serviceName3);
|
||||
ServiceNameDataDefine.ServiceName serviceName4 = new ServiceNameDataDefine.ServiceName("4", "org.skywaking.apm.testcase.dubbo.services.GreetService.doBusiness()", 3, 4);
|
||||
serviceNameEsDAO.save(serviceName4);
|
||||
|
||||
while (true) {
|
||||
JsonElement consumer = JsonFileReader.INSTANCE.read("json/segment/normal/dubbox-consumer.json");
|
||||
|
|
@ -82,12 +82,12 @@ public class SegmentPost {
|
|||
modifyTime(provider);
|
||||
HttpClientTools.INSTANCE.post("http://localhost:12800/segments", provider.toString());
|
||||
|
||||
diff = 0;
|
||||
DIFF = 0;
|
||||
Thread.sleep(1000);
|
||||
}
|
||||
}
|
||||
|
||||
private static long diff = 0;
|
||||
private static long DIFF = 0;
|
||||
|
||||
private static void modifyTime(JsonElement jsonElement) {
|
||||
JsonArray segmentArray = jsonElement.getAsJsonArray();
|
||||
|
|
@ -98,12 +98,12 @@ public class SegmentPost {
|
|||
long startTime = span.getAsJsonObject().get("st").getAsLong();
|
||||
long endTime = span.getAsJsonObject().get("et").getAsLong();
|
||||
|
||||
if (diff == 0) {
|
||||
diff = System.currentTimeMillis() - startTime;
|
||||
if (DIFF == 0) {
|
||||
DIFF = System.currentTimeMillis() - startTime;
|
||||
}
|
||||
|
||||
span.getAsJsonObject().addProperty("st", startTime + diff);
|
||||
span.getAsJsonObject().addProperty("et", endTime + diff);
|
||||
span.getAsJsonObject().addProperty("st", startTime + DIFF);
|
||||
span.getAsJsonObject().addProperty("et", endTime + DIFF);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -219,15 +219,15 @@ public class GrpcSegmentPost {
|
|||
LogMessage.Builder entryLogMessage = LogMessage.newBuilder();
|
||||
entryLogMessage.setTime(timestamp);
|
||||
|
||||
KeyWithStringValue.Builder data_1 = KeyWithStringValue.newBuilder();
|
||||
data_1.setKey("url");
|
||||
data_1.setValue("http://localhost:18080/dubbox-case/case/dubbox-rest");
|
||||
entryLogMessage.addData(data_1);
|
||||
KeyWithStringValue.Builder data1 = KeyWithStringValue.newBuilder();
|
||||
data1.setKey("url");
|
||||
data1.setValue("http://localhost:18080/dubbox-case/case/dubbox-rest");
|
||||
entryLogMessage.addData(data1);
|
||||
|
||||
KeyWithStringValue.Builder data_2 = KeyWithStringValue.newBuilder();
|
||||
data_2.setKey("http.method");
|
||||
data_2.setValue("GET");
|
||||
entryLogMessage.addData(data_2);
|
||||
KeyWithStringValue.Builder data2 = KeyWithStringValue.newBuilder();
|
||||
data2.setKey("http.method");
|
||||
data2.setValue("GET");
|
||||
entryLogMessage.addData(data2);
|
||||
entrySpan.addLogs(entryLogMessage);
|
||||
segmentBuilder.addSpans(entrySpan);
|
||||
|
||||
|
|
@ -292,15 +292,15 @@ public class GrpcSegmentPost {
|
|||
LogMessage.Builder entryLogMessage = LogMessage.newBuilder();
|
||||
entryLogMessage.setTime(timestamp);
|
||||
|
||||
KeyWithStringValue.Builder data_1 = KeyWithStringValue.newBuilder();
|
||||
data_1.setKey("url");
|
||||
data_1.setValue("rest://172.25.0.4:20880/org.skywaking.apm.testcase.dubbo.services.GreetService.doBusiness()");
|
||||
entryLogMessage.addData(data_1);
|
||||
KeyWithStringValue.Builder data1 = KeyWithStringValue.newBuilder();
|
||||
data1.setKey("url");
|
||||
data1.setValue("rest://172.25.0.4:20880/org.skywaking.apm.testcase.dubbo.services.GreetService.doBusiness()");
|
||||
entryLogMessage.addData(data1);
|
||||
|
||||
KeyWithStringValue.Builder data_2 = KeyWithStringValue.newBuilder();
|
||||
data_2.setKey("http.method");
|
||||
data_2.setValue("GET");
|
||||
entryLogMessage.addData(data_2);
|
||||
KeyWithStringValue.Builder data2 = KeyWithStringValue.newBuilder();
|
||||
data2.setKey("http.method");
|
||||
data2.setValue("GET");
|
||||
entryLogMessage.addData(data2);
|
||||
entrySpan.addLogs(entryLogMessage);
|
||||
segmentBuilder.addSpans(entrySpan);
|
||||
|
||||
|
|
|
|||
|
|
@ -57,10 +57,7 @@ public class TimeBucketUtilsTestCase {
|
|||
Calendar calendar = Calendar.getInstance();
|
||||
calendar.setTimeInMillis(1490922929258L);
|
||||
calendar.set(Calendar.SECOND, calendar.get(Calendar.SECOND) - 3);
|
||||
// System.out.println(calendar.getTimeInMillis());
|
||||
calendar.set(Calendar.SECOND, calendar.get(Calendar.SECOND) - 2);
|
||||
// System.out.println(calendar.getTimeInMillis());
|
||||
calendar.set(Calendar.SECOND, calendar.get(Calendar.SECOND) - 2);
|
||||
// System.out.println(calendar.getTimeInMillis());
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -32,9 +32,9 @@ import org.skywalking.apm.commons.datacarrier.SampleData;
|
|||
* Created by wusheng on 2016/10/26.
|
||||
*/
|
||||
public class ConsumerTest {
|
||||
public static LinkedBlockingQueue<SampleData> buffer = new LinkedBlockingQueue<SampleData>();
|
||||
public static LinkedBlockingQueue<SampleData> BUFFER = new LinkedBlockingQueue<SampleData>();
|
||||
|
||||
public static boolean isOccurError = false;
|
||||
public static boolean IS_OCCUR_ERROR = false;
|
||||
|
||||
@Test
|
||||
public void testConsumerLessThanChannel() throws IllegalAccessException {
|
||||
|
|
@ -71,7 +71,7 @@ public class ConsumerTest {
|
|||
Thread.sleep(2000);
|
||||
|
||||
List<SampleData> result = new ArrayList<SampleData>();
|
||||
buffer.drainTo(result);
|
||||
BUFFER.drainTo(result);
|
||||
|
||||
Assert.assertEquals(200, result.size());
|
||||
|
||||
|
|
@ -94,7 +94,7 @@ public class ConsumerTest {
|
|||
consumer.onError = true;
|
||||
carrier.consume(consumer, 5);
|
||||
|
||||
Assert.assertTrue(isOccurError);
|
||||
Assert.assertTrue(IS_OCCUR_ERROR);
|
||||
}
|
||||
|
||||
class SampleConsumer2 implements IConsumer<SampleData> {
|
||||
|
|
@ -116,7 +116,7 @@ public class ConsumerTest {
|
|||
|
||||
@Override
|
||||
public void onError(List<SampleData> data, Throwable t) {
|
||||
isOccurError = true;
|
||||
IS_OCCUR_ERROR = true;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
@ -126,7 +126,7 @@ public class ConsumerTest {
|
|||
}
|
||||
|
||||
private IConsumer getConsumer(DataCarrier<SampleData> carrier) throws IllegalAccessException {
|
||||
ConsumerPool pool = ((ConsumerPool)MemberModifier.field(DataCarrier.class, "consumerPool").get(carrier));
|
||||
ConsumerPool pool = (ConsumerPool)MemberModifier.field(DataCarrier.class, "consumerPool").get(carrier);
|
||||
ConsumerThread[] threads = (ConsumerThread[])MemberModifier.field(ConsumerPool.class, "consumerThreads").get(pool);
|
||||
|
||||
return (IConsumer)MemberModifier.field(ConsumerThread.class, "consumer").get(threads[0]);
|
||||
|
|
|
|||
|
|
@ -36,7 +36,7 @@ public class SampleConsumer implements IConsumer<SampleData> {
|
|||
public void consume(List<SampleData> data) {
|
||||
for (SampleData one : data) {
|
||||
one.setIntValue(this.hashCode());
|
||||
ConsumerTest.buffer.offer(one);
|
||||
ConsumerTest.BUFFER.offer(one);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -30,17 +30,17 @@ public class ConfigInitializerTest {
|
|||
@Test
|
||||
public void testInitialize() throws IllegalAccessException {
|
||||
Properties properties = new Properties();
|
||||
properties.put("Level1Object.strAttr".toLowerCase(), "stringValue");
|
||||
properties.put("Level1Object.Level2Object.intAttr".toLowerCase(), "1000");
|
||||
properties.put("Level1Object.Level2Object.longAttr".toLowerCase(), "1000");
|
||||
properties.put("Level1Object.Level2Object.booleanAttr".toLowerCase(), "true");
|
||||
properties.put("Level1Object.STR_ATTR".toLowerCase(), "stringValue");
|
||||
properties.put("Level1Object.Level2Object.INT_ATTR".toLowerCase(), "1000");
|
||||
properties.put("Level1Object.Level2Object.LONG_ATTR".toLowerCase(), "1000");
|
||||
properties.put("Level1Object.Level2Object.BOOLEAN_ATTR".toLowerCase(), "true");
|
||||
|
||||
ConfigInitializer.initialize(properties, TestPropertiesObject.class);
|
||||
|
||||
Assert.assertEquals("stringValue", TestPropertiesObject.Level1Object.strAttr);
|
||||
Assert.assertEquals(1000, TestPropertiesObject.Level1Object.Level2Object.intAttr);
|
||||
Assert.assertEquals(1000L, TestPropertiesObject.Level1Object.Level2Object.longAttr);
|
||||
Assert.assertEquals(true, TestPropertiesObject.Level1Object.Level2Object.booleanAttr);
|
||||
Assert.assertEquals("stringValue", TestPropertiesObject.Level1Object.STR_ATTR);
|
||||
Assert.assertEquals(1000, TestPropertiesObject.Level1Object.Level2Object.INT_ATTR);
|
||||
Assert.assertEquals(1000L, TestPropertiesObject.Level1Object.Level2Object.LONG_ATTR);
|
||||
Assert.assertEquals(true, TestPropertiesObject.Level1Object.Level2Object.BOOLEAN_ATTR);
|
||||
}
|
||||
|
||||
@Test
|
||||
|
|
@ -50,27 +50,27 @@ public class ConfigInitializerTest {
|
|||
|
||||
ConfigInitializer.initialize(properties, TestPropertiesObject.class);
|
||||
|
||||
Assert.assertNull(TestPropertiesObject.Level1Object.strAttr);
|
||||
Assert.assertNull(TestPropertiesObject.Level1Object.STR_ATTR);
|
||||
}
|
||||
|
||||
@Before
|
||||
public void clear() {
|
||||
TestPropertiesObject.Level1Object.strAttr = null;
|
||||
TestPropertiesObject.Level1Object.Level2Object.intAttr = 0;
|
||||
TestPropertiesObject.Level1Object.Level2Object.longAttr = 0;
|
||||
TestPropertiesObject.Level1Object.Level2Object.booleanAttr = false;
|
||||
TestPropertiesObject.Level1Object.STR_ATTR = null;
|
||||
TestPropertiesObject.Level1Object.Level2Object.INT_ATTR = 0;
|
||||
TestPropertiesObject.Level1Object.Level2Object.LONG_ATTR = 0;
|
||||
TestPropertiesObject.Level1Object.Level2Object.BOOLEAN_ATTR = false;
|
||||
}
|
||||
|
||||
public static class TestPropertiesObject {
|
||||
public static class Level1Object {
|
||||
public static String strAttr = null;
|
||||
public static String STR_ATTR = null;
|
||||
|
||||
public static class Level2Object {
|
||||
public static int intAttr = 0;
|
||||
public static int INT_ATTR = 0;
|
||||
|
||||
public static long longAttr;
|
||||
public static long LONG_ATTR;
|
||||
|
||||
public static boolean booleanAttr;
|
||||
public static boolean BOOLEAN_ATTR;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -65,6 +65,8 @@ public class ComponentsDefine {
|
|||
|
||||
public static final OfficialComponent MEMCACHE = new OfficialComponent(20, "Memcache");
|
||||
|
||||
public static final OfficialComponent SHARDING_JDBC = new OfficialComponent(21, "ShardingJDBC");
|
||||
|
||||
private static ComponentsDefine instance = new ComponentsDefine();
|
||||
|
||||
private String[] components;
|
||||
|
|
@ -74,7 +76,7 @@ public class ComponentsDefine {
|
|||
}
|
||||
|
||||
public ComponentsDefine() {
|
||||
components = new String[21];
|
||||
components = new String[22];
|
||||
addComponent(TOMCAT);
|
||||
addComponent(HTTPCLIENT);
|
||||
addComponent(DUBBO);
|
||||
|
|
@ -95,6 +97,7 @@ public class ComponentsDefine {
|
|||
addComponent(JETTY_CLIENT);
|
||||
addComponent(JETTY_SERVER);
|
||||
addComponent(MEMCACHE);
|
||||
addComponent(SHARDING_JDBC);
|
||||
}
|
||||
|
||||
private void addComponent(OfficialComponent component) {
|
||||
|
|
|
|||
|
|
@ -153,7 +153,7 @@ public class ContextManager implements TracingContextListener, BootService, Igno
|
|||
if (snapshot == null) {
|
||||
throw new IllegalArgumentException("ContextSnapshot can't be null.");
|
||||
}
|
||||
if (snapshot.isValid()) {
|
||||
if (snapshot.isValid() && !snapshot.isFromCurrent()) {
|
||||
get().continued(snapshot);
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -113,4 +113,8 @@ public class ContextSnapshot {
|
|||
public int getEntryApplicationInstanceId() {
|
||||
return entryApplicationInstanceId;
|
||||
}
|
||||
|
||||
public boolean isFromCurrent() {
|
||||
return traceSegmentId.equals(ContextManager.capture().getTraceSegmentId());
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -53,6 +53,11 @@ public final class Tags {
|
|||
*/
|
||||
public static final StringTag DB_STATEMENT = new StringTag("db.statement");
|
||||
|
||||
/**
|
||||
* DB_BIND_VARIABLES records the bind variables of sql statement.
|
||||
*/
|
||||
public static final StringTag DB_BIND_VARIABLES = new StringTag("db.bind_vars");
|
||||
|
||||
public static final class HTTP {
|
||||
public static final StringTag METHOD = new StringTag("http.method");
|
||||
}
|
||||
|
|
|
|||
|
|
@ -17,6 +17,7 @@
|
|||
*/
|
||||
package org.skywalking.apm.agent.core.boot;
|
||||
|
||||
import org.junit.Assert;
|
||||
import org.junit.Test;
|
||||
|
||||
import static org.junit.Assert.assertNotNull;
|
||||
|
|
@ -36,6 +37,6 @@ public class DefaultNamedThreadFactoryTest {
|
|||
});
|
||||
newThread.start();
|
||||
assertNotNull(newThread.getName());
|
||||
assert(newThread.getName().contains("DefaultNamedThreadFactoryTest"));
|
||||
Assert.assertTrue(newThread.getName().contains("DefaultNamedThreadFactoryTest"));
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -63,18 +63,18 @@ public class ServiceManagerTest {
|
|||
}
|
||||
|
||||
private void assertIgnoreTracingContextListener() throws Exception {
|
||||
List<TracingContextListener> LISTENERS = getFieldValue(IgnoredTracerContext.ListenerManager.class, "LISTENERS");
|
||||
assertThat(LISTENERS.size(), is(1));
|
||||
List<TracingContextListener> listeners = getFieldValue(IgnoredTracerContext.ListenerManager.class, "LISTENERS");
|
||||
assertThat(listeners.size(), is(1));
|
||||
|
||||
assertThat(LISTENERS.contains(ServiceManager.INSTANCE.findService(ContextManager.class)), is(true));
|
||||
assertThat(listeners.contains(ServiceManager.INSTANCE.findService(ContextManager.class)), is(true));
|
||||
}
|
||||
|
||||
private void assertTracingContextListener() throws Exception {
|
||||
List<TracingContextListener> LISTENERS = getFieldValue(TracingContext.ListenerManager.class, "LISTENERS");
|
||||
assertThat(LISTENERS.size(), is(3));
|
||||
List<TracingContextListener> listeners = getFieldValue(TracingContext.ListenerManager.class, "LISTENERS");
|
||||
assertThat(listeners.size(), is(3));
|
||||
|
||||
assertThat(LISTENERS.contains(ServiceManager.INSTANCE.findService(ContextManager.class)), is(true));
|
||||
assertThat(LISTENERS.contains(ServiceManager.INSTANCE.findService(TraceSegmentServiceClient.class)), is(true));
|
||||
assertThat(listeners.contains(ServiceManager.INSTANCE.findService(ContextManager.class)), is(true));
|
||||
assertThat(listeners.contains(ServiceManager.INSTANCE.findService(TraceSegmentServiceClient.class)), is(true));
|
||||
}
|
||||
|
||||
private void assertJVMService(JVMService service) {
|
||||
|
|
|
|||
|
|
@ -33,13 +33,13 @@ import static org.mockito.Mockito.times;
|
|||
* Created by wusheng on 2017/2/28.
|
||||
*/
|
||||
public class EasyLoggerTest {
|
||||
private static PrintStream outRef;
|
||||
private static PrintStream errRef;
|
||||
private static PrintStream OUT_REF;
|
||||
private static PrintStream ERR_REF;
|
||||
|
||||
@BeforeClass
|
||||
public static void initAndHoldOut() {
|
||||
outRef = System.out;
|
||||
errRef = System.err;
|
||||
OUT_REF = System.out;
|
||||
ERR_REF = System.err;
|
||||
}
|
||||
|
||||
@Test
|
||||
|
|
@ -110,7 +110,7 @@ public class EasyLoggerTest {
|
|||
|
||||
@AfterClass
|
||||
public static void reset() {
|
||||
System.setOut(outRef);
|
||||
System.setErr(errRef);
|
||||
System.setOut(OUT_REF);
|
||||
System.setErr(ERR_REF);
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -31,11 +31,11 @@ import static org.mockito.Mockito.times;
|
|||
* Created by wusheng on 2017/2/28.
|
||||
*/
|
||||
public class SystemOutWriterTest {
|
||||
private static PrintStream outRef;
|
||||
private static PrintStream OUT_REF;
|
||||
|
||||
@BeforeClass
|
||||
public static void initAndHoldOut() {
|
||||
outRef = System.out;
|
||||
OUT_REF = System.out;
|
||||
}
|
||||
|
||||
@Test
|
||||
|
|
@ -50,6 +50,6 @@ public class SystemOutWriterTest {
|
|||
|
||||
@AfterClass
|
||||
public static void reset() {
|
||||
System.setOut(outRef);
|
||||
System.setOut(OUT_REF);
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -30,11 +30,11 @@ import org.skywalking.apm.agent.core.conf.Config;
|
|||
* Created by wusheng on 2017/2/28.
|
||||
*/
|
||||
public class WriterFactoryTest {
|
||||
private static PrintStream errRef;
|
||||
private static PrintStream ERR_REF;
|
||||
|
||||
@BeforeClass
|
||||
public static void initAndHoldOut() {
|
||||
errRef = System.err;
|
||||
ERR_REF = System.err;
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
@ -54,6 +54,6 @@ public class WriterFactoryTest {
|
|||
@AfterClass
|
||||
public static void reset() {
|
||||
Config.Logging.DIR = "";
|
||||
System.setErr(errRef);
|
||||
System.setErr(ERR_REF);
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -148,6 +148,11 @@
|
|||
<artifactId>apm-spymemcached-2.x-plugin</artifactId>
|
||||
<version>${project.version}</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.skywalking</groupId>
|
||||
<artifactId>apm-sharding-jdbc-1.5.x-plugin</artifactId>
|
||||
<version>${project.version}</version>
|
||||
</dependency>
|
||||
|
||||
<!-- activation -->
|
||||
<dependency>
|
||||
|
|
|
|||
|
|
@ -45,6 +45,7 @@
|
|||
<module>nutz-plugins</module>
|
||||
<module>jetty-plugin</module>
|
||||
<module>spymemcached-2.x-plugin</module>
|
||||
<module>sharding-jdbc-1.5.x-plugin</module>
|
||||
</modules>
|
||||
<packaging>pom</packaging>
|
||||
|
||||
|
|
|
|||
|
|
@ -0,0 +1,92 @@
|
|||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<!--
|
||||
~ Copyright 2017, OpenSkywalking Organization All rights reserved.
|
||||
~
|
||||
~ Licensed under the Apache License, Version 2.0 (the "License");
|
||||
~ you may not use this file except in compliance with the License.
|
||||
~ You may obtain a copy of the License at
|
||||
~
|
||||
~ http://www.apache.org/licenses/LICENSE-2.0
|
||||
~
|
||||
~ Unless required by applicable law or agreed to in writing, software
|
||||
~ distributed under the License is distributed on an "AS IS" BASIS,
|
||||
~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
~ See the License for the specific language governing permissions and
|
||||
~ limitations under the License.
|
||||
~
|
||||
~ Project repository: https://github.com/OpenSkywalking/skywalking
|
||||
-->
|
||||
|
||||
<project xmlns="http://maven.apache.org/POM/4.0.0"
|
||||
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
|
||||
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
|
||||
<parent>
|
||||
<artifactId>apm-sdk-plugin</artifactId>
|
||||
<groupId>org.skywalking</groupId>
|
||||
<version>3.2.3-2017</version>
|
||||
</parent>
|
||||
<modelVersion>4.0.0</modelVersion>
|
||||
|
||||
<artifactId>apm-sharding-jdbc-1.5.x-plugin</artifactId>
|
||||
<packaging>jar</packaging>
|
||||
|
||||
<name>sharding-jdbc-1.5.x-plugin</name>
|
||||
<url>http://maven.apache.org</url>
|
||||
|
||||
<properties>
|
||||
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
|
||||
</properties>
|
||||
|
||||
<dependencies>
|
||||
<dependency>
|
||||
<groupId>${groupId}</groupId>
|
||||
<artifactId>apm-jdbc-plugin</artifactId>
|
||||
<version>${project.version}</version>
|
||||
<scope>test</scope>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>mysql</groupId>
|
||||
<artifactId>mysql-connector-java</artifactId>
|
||||
<version>[2.0.14,6.0.6]</version>
|
||||
<scope>test</scope>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>com.dangdang</groupId>
|
||||
<artifactId>sharding-jdbc-core</artifactId>
|
||||
<version>[1.5.0,2.0.0)</version>
|
||||
<scope>provided</scope>
|
||||
</dependency>
|
||||
</dependencies>
|
||||
|
||||
<build>
|
||||
<plugins>
|
||||
<plugin>
|
||||
<groupId>org.apache.maven.plugins</groupId>
|
||||
<artifactId>maven-deploy-plugin</artifactId>
|
||||
</plugin>
|
||||
<plugin>
|
||||
<!-- 源码插件 -->
|
||||
<groupId>org.apache.maven.plugins</groupId>
|
||||
<artifactId>maven-source-plugin</artifactId>
|
||||
<!-- 发布时自动将源码同时发布的配置 -->
|
||||
<executions>
|
||||
<execution>
|
||||
<id>attach-sources</id>
|
||||
<goals>
|
||||
<goal>jar</goal>
|
||||
</goals>
|
||||
</execution>
|
||||
</executions>
|
||||
</plugin>
|
||||
<plugin>
|
||||
<groupId>org.apache.maven.plugins</groupId>
|
||||
<artifactId>maven-compiler-plugin</artifactId>
|
||||
<configuration>
|
||||
<source>1.8</source>
|
||||
<target>1.8</target>
|
||||
</configuration>
|
||||
</plugin>
|
||||
</plugins>
|
||||
</build>
|
||||
|
||||
</project>
|
||||
|
|
@ -0,0 +1,87 @@
|
|||
/*
|
||||
* Copyright 2017, OpenSkywalking Organization All rights reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*
|
||||
* Project repository: https://github.com/OpenSkywalking/skywalking
|
||||
*/
|
||||
|
||||
package org.skywalking.apm.plugin.sjdbc;
|
||||
|
||||
import com.dangdang.ddframe.rdb.sharding.executor.event.AbstractExecutionEvent;
|
||||
import com.dangdang.ddframe.rdb.sharding.executor.event.DMLExecutionEvent;
|
||||
import com.dangdang.ddframe.rdb.sharding.executor.event.DQLExecutionEvent;
|
||||
import com.dangdang.ddframe.rdb.sharding.executor.threadlocal.ExecutorDataMap;
|
||||
import com.dangdang.ddframe.rdb.sharding.util.EventBusInstance;
|
||||
import com.google.common.base.Joiner;
|
||||
import com.google.common.eventbus.AllowConcurrentEvents;
|
||||
import com.google.common.eventbus.Subscribe;
|
||||
import org.skywalking.apm.agent.core.context.ContextManager;
|
||||
import org.skywalking.apm.agent.core.context.ContextSnapshot;
|
||||
import org.skywalking.apm.agent.core.context.tag.Tags;
|
||||
import org.skywalking.apm.agent.core.context.trace.AbstractSpan;
|
||||
import org.skywalking.apm.agent.core.context.trace.SpanLayer;
|
||||
import org.skywalking.apm.network.trace.component.ComponentsDefine;
|
||||
import org.skywalking.apm.plugin.sjdbc.define.AsyncExecuteInterceptor;
|
||||
|
||||
/**
|
||||
* Sharding-jdbc provides {@link EventBusInstance} to help external systems get events of sql execution.
|
||||
* {@link ExecuteEventListener} can get sql statement start and end events, resulting in db span.
|
||||
*
|
||||
* @author gaohongtao
|
||||
*/
|
||||
public class ExecuteEventListener {
|
||||
|
||||
public static void init() {
|
||||
EventBusInstance.getInstance().register(new ExecuteEventListener());
|
||||
}
|
||||
|
||||
@Subscribe
|
||||
@AllowConcurrentEvents
|
||||
public void listenDML(DMLExecutionEvent event) {
|
||||
handle(event, "MODIFY");
|
||||
}
|
||||
|
||||
@Subscribe
|
||||
@AllowConcurrentEvents
|
||||
public void listenDQL(DQLExecutionEvent event) {
|
||||
handle(event, "QUERY");
|
||||
}
|
||||
|
||||
private void handle(AbstractExecutionEvent event, String operation) {
|
||||
switch (event.getEventExecutionType()) {
|
||||
case BEFORE_EXECUTE:
|
||||
AbstractSpan span = ContextManager.createExitSpan("/SJDBC/BRANCH/" + operation, event.getDataSource());
|
||||
if (ExecutorDataMap.getDataMap().containsKey(AsyncExecuteInterceptor.SNAPSHOT_DATA_KEY)) {
|
||||
ContextManager.continued((ContextSnapshot)ExecutorDataMap.getDataMap().get(AsyncExecuteInterceptor.SNAPSHOT_DATA_KEY));
|
||||
}
|
||||
Tags.DB_TYPE.set(span, "sql");
|
||||
Tags.DB_INSTANCE.set(span, event.getDataSource());
|
||||
Tags.DB_STATEMENT.set(span, event.getSql());
|
||||
if (!event.getParameters().isEmpty()) {
|
||||
Tags.DB_BIND_VARIABLES.set(span, Joiner.on(",").join(event.getParameters()));
|
||||
}
|
||||
span.setComponent(ComponentsDefine.SHARDING_JDBC);
|
||||
SpanLayer.asDB(span);
|
||||
break;
|
||||
case EXECUTE_FAILURE:
|
||||
span = ContextManager.activeSpan();
|
||||
span.errorOccurred();
|
||||
if (event.getException().isPresent()) {
|
||||
span.log(event.getException().get());
|
||||
}
|
||||
case EXECUTE_SUCCESS:
|
||||
ContextManager.stopSpan();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,59 @@
|
|||
/*
|
||||
* Copyright 2017, OpenSkywalking Organization All rights reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*
|
||||
* Project repository: https://github.com/OpenSkywalking/skywalking
|
||||
*/
|
||||
|
||||
package org.skywalking.apm.plugin.sjdbc.define;
|
||||
|
||||
import com.dangdang.ddframe.rdb.sharding.constant.SQLType;
|
||||
import com.dangdang.ddframe.rdb.sharding.executor.ExecuteCallback;
|
||||
import com.dangdang.ddframe.rdb.sharding.executor.threadlocal.ExecutorDataMap;
|
||||
import java.util.Collection;
|
||||
import java.util.List;
|
||||
import org.skywalking.apm.agent.core.context.ContextManager;
|
||||
import org.skywalking.apm.agent.core.context.ContextSnapshot;
|
||||
import org.skywalking.apm.agent.core.plugin.interceptor.enhance.EnhancedInstance;
|
||||
import org.skywalking.apm.agent.core.plugin.interceptor.enhance.InstanceMethodsAroundInterceptor;
|
||||
import org.skywalking.apm.agent.core.plugin.interceptor.enhance.MethodInterceptResult;
|
||||
|
||||
import java.lang.reflect.Method;
|
||||
|
||||
/**
|
||||
* {@link AsyncExecuteInterceptor} enhances {@link com.dangdang.ddframe.rdb.sharding.executor.ExecutorEngine#asyncExecute(SQLType, Collection, List, ExecuteCallback)}
|
||||
* so that the sql executor can get a {@link ContextSnapshot} of main thread when it is executed asynchronously.
|
||||
*
|
||||
* @author gaohongtao
|
||||
*/
|
||||
public class AsyncExecuteInterceptor implements InstanceMethodsAroundInterceptor {
|
||||
|
||||
public static final String SNAPSHOT_DATA_KEY = "APM_SKYWALKING_SNAPSHOT_DATA";
|
||||
|
||||
@Override
|
||||
public void beforeMethod(EnhancedInstance objInst, Method method, Object[] allArguments, Class<?>[] argumentsTypes,
|
||||
MethodInterceptResult result) throws Throwable {
|
||||
ExecutorDataMap.getDataMap().put(SNAPSHOT_DATA_KEY, ContextManager.capture());
|
||||
}
|
||||
|
||||
@Override
|
||||
public Object afterMethod(EnhancedInstance objInst, Method method, Object[] allArguments, Class<?>[] argumentsTypes,
|
||||
Object ret) throws Throwable {
|
||||
return ret;
|
||||
}
|
||||
|
||||
@Override public void handleMethodException(EnhancedInstance objInst, Method method, Object[] allArguments,
|
||||
Class<?>[] argumentsTypes, Throwable t) {
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,57 @@
|
|||
/*
|
||||
* Copyright 2017, OpenSkywalking Organization All rights reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*
|
||||
* Project repository: https://github.com/OpenSkywalking/skywalking
|
||||
*/
|
||||
|
||||
package org.skywalking.apm.plugin.sjdbc.define;
|
||||
|
||||
import com.dangdang.ddframe.rdb.sharding.constant.SQLType;
|
||||
import com.dangdang.ddframe.rdb.sharding.executor.ExecuteCallback;
|
||||
import java.lang.reflect.Method;
|
||||
import java.util.Collection;
|
||||
import java.util.List;
|
||||
import org.skywalking.apm.agent.core.context.ContextManager;
|
||||
import org.skywalking.apm.agent.core.plugin.interceptor.enhance.EnhancedInstance;
|
||||
import org.skywalking.apm.agent.core.plugin.interceptor.enhance.InstanceMethodsAroundInterceptor;
|
||||
import org.skywalking.apm.agent.core.plugin.interceptor.enhance.MethodInterceptResult;
|
||||
import org.skywalking.apm.network.trace.component.ComponentsDefine;
|
||||
|
||||
/**
|
||||
* {@link ExecuteInterceptor} enhances {@link com.dangdang.ddframe.rdb.sharding.executor.ExecutorEngine#execute(SQLType, Collection, List, ExecuteCallback)}
|
||||
* ,creating a local span that records the overall execution of sql
|
||||
*
|
||||
* @author gaohongtao
|
||||
*/
|
||||
public class ExecuteInterceptor implements InstanceMethodsAroundInterceptor {
|
||||
@Override
|
||||
public void beforeMethod(EnhancedInstance objInst, Method method, Object[] allArguments, Class<?>[] argumentsTypes,
|
||||
MethodInterceptResult result) throws Throwable {
|
||||
SQLType sqlType = (SQLType)allArguments[0];
|
||||
ContextManager.createLocalSpan("/SJDBC/TRUNK/" + sqlType.name()).setComponent(ComponentsDefine.SHARDING_JDBC);
|
||||
}
|
||||
|
||||
@Override
|
||||
public Object afterMethod(EnhancedInstance objInst, Method method, Object[] allArguments, Class<?>[] argumentsTypes,
|
||||
Object ret) throws Throwable {
|
||||
ContextManager.stopSpan();
|
||||
return ret;
|
||||
}
|
||||
|
||||
@Override public void handleMethodException(EnhancedInstance objInst, Method method, Object[] allArguments,
|
||||
Class<?>[] argumentsTypes, Throwable t) {
|
||||
ContextManager.activeSpan().errorOccurred().log(t);
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,36 @@
|
|||
/*
|
||||
* Copyright 2017, OpenSkywalking Organization All rights reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*
|
||||
* Project repository: https://github.com/OpenSkywalking/skywalking
|
||||
*/
|
||||
|
||||
package org.skywalking.apm.plugin.sjdbc.define;
|
||||
|
||||
import com.dangdang.ddframe.rdb.sharding.executor.ExecutorEngine;
|
||||
import org.skywalking.apm.agent.core.plugin.interceptor.enhance.EnhancedInstance;
|
||||
import org.skywalking.apm.agent.core.plugin.interceptor.enhance.InstanceConstructorInterceptor;
|
||||
import org.skywalking.apm.plugin.sjdbc.ExecuteEventListener;
|
||||
|
||||
/**
|
||||
* {@link ExecutorEngineConstructorInterceptor} enhances {@link ExecutorEngine#}'s constructor, initializing {@link ExecuteEventListener}
|
||||
*
|
||||
* @author gaohongtao
|
||||
*/
|
||||
public class ExecutorEngineConstructorInterceptor implements InstanceConstructorInterceptor {
|
||||
|
||||
@Override public void onConstruct(EnhancedInstance objInst, Object[] allArguments) {
|
||||
ExecuteEventListener.init();
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,106 @@
|
|||
/*
|
||||
* Copyright 2017, OpenSkywalking Organization All rights reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*
|
||||
* Project repository: https://github.com/OpenSkywalking/skywalking
|
||||
*/
|
||||
|
||||
package org.skywalking.apm.plugin.sjdbc.define;
|
||||
|
||||
import net.bytebuddy.description.method.MethodDescription;
|
||||
import net.bytebuddy.matcher.ElementMatcher;
|
||||
import org.skywalking.apm.agent.core.plugin.interceptor.ConstructorInterceptPoint;
|
||||
import org.skywalking.apm.agent.core.plugin.interceptor.InstanceMethodsInterceptPoint;
|
||||
import org.skywalking.apm.agent.core.plugin.interceptor.enhance.ClassInstanceMethodsEnhancePluginDefine;
|
||||
import org.skywalking.apm.agent.core.plugin.match.ClassMatch;
|
||||
|
||||
import static net.bytebuddy.matcher.ElementMatchers.any;
|
||||
import static net.bytebuddy.matcher.ElementMatchers.named;
|
||||
import static org.skywalking.apm.agent.core.plugin.match.NameMatch.byName;
|
||||
|
||||
/**
|
||||
* {@link ExecutorInstrumentation} presents that skywalking intercepts {@link com.dangdang.ddframe.rdb.sharding.executor.ExecutorEngine}.
|
||||
*
|
||||
* @author gaohongtao
|
||||
*/
|
||||
public class ExecutorInstrumentation extends ClassInstanceMethodsEnhancePluginDefine {
|
||||
|
||||
private static final String ENHANCE_CLASS = "com.dangdang.ddframe.rdb.sharding.executor.ExecutorEngine";
|
||||
|
||||
private static final String EXECUTOR_ENGINE_CONSTRUCTOR_INTERCEPTOR_CLASS = "org.skywalking.apm.plugin.sjdbc.define.ExecutorEngineConstructorInterceptor";
|
||||
|
||||
private static final String EXECUTE_INTERCEPTOR_CLASS = "org.skywalking.apm.plugin.sjdbc.define.ExecuteInterceptor";
|
||||
|
||||
private static final String ASYNC_EXECUTE_INTERCEPTOR_CLASS = "org.skywalking.apm.plugin.sjdbc.define.AsyncExecuteInterceptor";
|
||||
|
||||
@Override
|
||||
protected ConstructorInterceptPoint[] getConstructorsInterceptPoints() {
|
||||
return new ConstructorInterceptPoint[] {
|
||||
new ConstructorInterceptPoint() {
|
||||
@Override
|
||||
public ElementMatcher<MethodDescription> getConstructorMatcher() {
|
||||
return any();
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getConstructorInterceptor() {
|
||||
return EXECUTOR_ENGINE_CONSTRUCTOR_INTERCEPTOR_CLASS;
|
||||
}
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
@Override
|
||||
protected InstanceMethodsInterceptPoint[] getInstanceMethodsInterceptPoints() {
|
||||
return new InstanceMethodsInterceptPoint[]{
|
||||
new InstanceMethodsInterceptPoint() {
|
||||
@Override
|
||||
public ElementMatcher<MethodDescription> getMethodsMatcher() {
|
||||
return named("execute");
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getMethodsInterceptor() {
|
||||
return EXECUTE_INTERCEPTOR_CLASS;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isOverrideArgs() {
|
||||
return false;
|
||||
}
|
||||
},
|
||||
new InstanceMethodsInterceptPoint() {
|
||||
@Override
|
||||
public ElementMatcher<MethodDescription> getMethodsMatcher() {
|
||||
return named("asyncExecute");
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getMethodsInterceptor() {
|
||||
return ASYNC_EXECUTE_INTERCEPTOR_CLASS;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isOverrideArgs() {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
@Override
|
||||
protected ClassMatch enhanceClass() {
|
||||
return byName(ENHANCE_CLASS);
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1 @@
|
|||
sharding-jdbc-1.5.x=org.skywalking.apm.plugin.sjdbc.define.ExecutorInstrumentation
|
||||
|
|
@ -0,0 +1,200 @@
|
|||
/*
|
||||
* Copyright 2017, OpenSkywalking Organization All rights reserved.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*
|
||||
* Project repository: https://github.com/OpenSkywalking/skywalking
|
||||
*/
|
||||
|
||||
package org.skywalking.apm.plugin.sjdbc;
|
||||
|
||||
import com.dangdang.ddframe.rdb.sharding.constant.SQLType;
|
||||
import com.dangdang.ddframe.rdb.sharding.executor.event.DMLExecutionEvent;
|
||||
import com.dangdang.ddframe.rdb.sharding.executor.event.DQLExecutionEvent;
|
||||
import com.dangdang.ddframe.rdb.sharding.executor.event.EventExecutionType;
|
||||
import com.dangdang.ddframe.rdb.sharding.executor.threadlocal.ExecutorDataMap;
|
||||
import com.dangdang.ddframe.rdb.sharding.util.EventBusInstance;
|
||||
import com.google.common.base.Optional;
|
||||
import java.sql.SQLException;
|
||||
import java.util.Arrays;
|
||||
import java.util.Collections;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.concurrent.ExecutorService;
|
||||
import java.util.concurrent.Executors;
|
||||
import org.junit.AfterClass;
|
||||
import org.junit.Before;
|
||||
import org.junit.BeforeClass;
|
||||
import org.junit.Rule;
|
||||
import org.junit.Test;
|
||||
import org.junit.runner.RunWith;
|
||||
import org.powermock.modules.junit4.PowerMockRunner;
|
||||
import org.powermock.modules.junit4.PowerMockRunnerDelegate;
|
||||
import org.skywalking.apm.agent.core.context.trace.AbstractTracingSpan;
|
||||
import org.skywalking.apm.agent.core.context.trace.SpanLayer;
|
||||
import org.skywalking.apm.agent.core.context.trace.TraceSegment;
|
||||
import org.skywalking.apm.agent.test.helper.SegmentHelper;
|
||||
import org.skywalking.apm.agent.test.tools.AgentServiceRule;
|
||||
import org.skywalking.apm.agent.test.tools.SegmentStorage;
|
||||
import org.skywalking.apm.agent.test.tools.SegmentStoragePoint;
|
||||
import org.skywalking.apm.agent.test.tools.TracingSegmentRunner;
|
||||
import org.skywalking.apm.network.trace.component.ComponentsDefine;
|
||||
import org.skywalking.apm.plugin.sjdbc.define.AsyncExecuteInterceptor;
|
||||
import org.skywalking.apm.plugin.sjdbc.define.ExecuteInterceptor;
|
||||
import org.skywalking.apm.plugin.sjdbc.define.ExecutorEngineConstructorInterceptor;
|
||||
|
||||
import static org.hamcrest.core.Is.is;
|
||||
import static org.junit.Assert.assertNotNull;
|
||||
import static org.junit.Assert.assertNull;
|
||||
import static org.junit.Assert.assertThat;
|
||||
import static org.skywalking.apm.agent.test.tools.SpanAssert.assertComponent;
|
||||
import static org.skywalking.apm.agent.test.tools.SpanAssert.assertLayer;
|
||||
import static org.skywalking.apm.agent.test.tools.SpanAssert.assertOccurException;
|
||||
import static org.skywalking.apm.agent.test.tools.SpanAssert.assertTag;
|
||||
|
||||
@RunWith(PowerMockRunner.class)
|
||||
@PowerMockRunnerDelegate(TracingSegmentRunner.class)
|
||||
public class InterceptorTest {
|
||||
|
||||
private static ExecutorService ES;
|
||||
|
||||
@SegmentStoragePoint
|
||||
private SegmentStorage segmentStorage;
|
||||
|
||||
@Rule
|
||||
public AgentServiceRule serviceRule = new AgentServiceRule();
|
||||
|
||||
private ExecuteInterceptor executeInterceptor;
|
||||
|
||||
private AsyncExecuteInterceptor asyncExecuteInterceptor;
|
||||
|
||||
private Object[] allArguments;
|
||||
|
||||
@BeforeClass
|
||||
public static void init() {
|
||||
ExecuteEventListener.init();
|
||||
new ExecutorEngineConstructorInterceptor().onConstruct(null, null);
|
||||
ES = Executors.newSingleThreadExecutor();
|
||||
}
|
||||
|
||||
@AfterClass
|
||||
public static void finish() {
|
||||
ES.shutdown();
|
||||
}
|
||||
|
||||
@Before
|
||||
public void setUp() throws SQLException {
|
||||
executeInterceptor = new ExecuteInterceptor();
|
||||
asyncExecuteInterceptor = new AsyncExecuteInterceptor();
|
||||
allArguments = new Object[]{SQLType.DQL, null};
|
||||
}
|
||||
|
||||
@Test
|
||||
public void assertSyncExecute() throws Throwable {
|
||||
executeInterceptor.beforeMethod(null, null, allArguments, null, null);
|
||||
sendEvent("ds_0", "select * from t_order_0");
|
||||
executeInterceptor.afterMethod(null, null, allArguments, null, null);
|
||||
assertThat(segmentStorage.getTraceSegments().size(), is(1));
|
||||
TraceSegment segment = segmentStorage.getTraceSegments().get(0);
|
||||
List<AbstractTracingSpan> spans = SegmentHelper.getSpans(segment);
|
||||
assertNotNull(spans);
|
||||
assertThat(spans.size(), is(2));
|
||||
assertSpan(spans.get(0), 0);
|
||||
assertThat(spans.get(1).getOperationName(), is("/SJDBC/TRUNK/DQL"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void assertAsyncExecute() throws Throwable {
|
||||
executeInterceptor.beforeMethod(null, null, allArguments, null, null);
|
||||
asyncExecuteInterceptor.beforeMethod(null, null, null, null, null);
|
||||
final Map<String, Object> dataMap = ExecutorDataMap.getDataMap();
|
||||
ES.submit(() -> {
|
||||
ExecutorDataMap.setDataMap(dataMap);
|
||||
sendEvent("ds_1", "select * from t_order_1");
|
||||
}).get();
|
||||
asyncExecuteInterceptor.afterMethod(null, null, null, null, null);
|
||||
sendEvent("ds_0", "select * from t_order_0");
|
||||
executeInterceptor.afterMethod(null, null, allArguments, null, null);
|
||||
assertThat(segmentStorage.getTraceSegments().size(), is(2));
|
||||
TraceSegment segment0 = segmentStorage.getTraceSegments().get(0);
|
||||
TraceSegment segment1 = segmentStorage.getTraceSegments().get(1);
|
||||
assertThat(segment0.getRefs().size(), is(1));
|
||||
assertNull(segment1.getRefs());
|
||||
List<AbstractTracingSpan> spans0 = SegmentHelper.getSpans(segment0);
|
||||
assertNotNull(spans0);
|
||||
assertThat(spans0.size(), is(1));
|
||||
assertSpan(spans0.get(0), 1);
|
||||
List<AbstractTracingSpan> spans1 = SegmentHelper.getSpans(segment1);
|
||||
assertNotNull(spans1);
|
||||
assertThat(spans1.size(), is(2));
|
||||
assertSpan(spans1.get(0), 0);
|
||||
assertThat(spans1.get(1).getOperationName(), is("/SJDBC/TRUNK/DQL"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void assertExecuteError() throws Throwable {
|
||||
executeInterceptor.beforeMethod(null, null, allArguments, null, null);
|
||||
asyncExecuteInterceptor.beforeMethod(null, null, null, null, null);
|
||||
final Map<String, Object> dataMap = ExecutorDataMap.getDataMap();
|
||||
ES.submit(() -> {
|
||||
ExecutorDataMap.setDataMap(dataMap);
|
||||
sendError();
|
||||
}).get();
|
||||
asyncExecuteInterceptor.handleMethodException(null, null, null, null, new SQLException("test"));
|
||||
asyncExecuteInterceptor.afterMethod(null, null, null, null, null);
|
||||
sendEvent("ds_0", "select * from t_order_0");
|
||||
executeInterceptor.handleMethodException(null, null, allArguments, null, new SQLException("Test"));
|
||||
executeInterceptor.afterMethod(null, null, allArguments, null, null);
|
||||
assertThat(segmentStorage.getTraceSegments().size(), is(2));
|
||||
TraceSegment segment0 = segmentStorage.getTraceSegments().get(0);
|
||||
TraceSegment segment1 = segmentStorage.getTraceSegments().get(1);
|
||||
List<AbstractTracingSpan> spans0 = SegmentHelper.getSpans(segment0);
|
||||
assertNotNull(spans0);
|
||||
assertThat(spans0.size(), is(1));
|
||||
assertErrorSpan(spans0.get(0));
|
||||
List<AbstractTracingSpan> spans1 = SegmentHelper.getSpans(segment1);
|
||||
assertNotNull(spans1);
|
||||
assertThat(spans1.size(), is(2));
|
||||
assertSpan(spans1.get(0), 0);
|
||||
assertErrorSpan(spans1.get(1));
|
||||
}
|
||||
|
||||
private void assertSpan(AbstractTracingSpan span, int index) {
|
||||
assertComponent(span, ComponentsDefine.SHARDING_JDBC);
|
||||
assertLayer(span, SpanLayer.DB);
|
||||
assertTag(span, 0, "sql");
|
||||
assertTag(span, 1, "ds_" + index);
|
||||
assertTag(span, 2, "select * from t_order_" + index);
|
||||
assertThat(span.isExit(), is(true));
|
||||
assertThat(span.getOperationName(), is("/SJDBC/BRANCH/QUERY"));
|
||||
}
|
||||
|
||||
private void assertErrorSpan(AbstractTracingSpan span) {
|
||||
assertOccurException(span, true);
|
||||
}
|
||||
|
||||
private void sendEvent(String datasource, String sql) {
|
||||
DQLExecutionEvent event = new DQLExecutionEvent(datasource, sql, Arrays.asList("1", 100));
|
||||
EventBusInstance.getInstance().post(event);
|
||||
event.setEventExecutionType(EventExecutionType.EXECUTE_SUCCESS);
|
||||
EventBusInstance.getInstance().post(event);
|
||||
}
|
||||
|
||||
private void sendError() {
|
||||
DMLExecutionEvent event = new DMLExecutionEvent("", "", Collections.emptyList());
|
||||
EventBusInstance.getInstance().post(event);
|
||||
event.setEventExecutionType(EventExecutionType.EXECUTE_FAILURE);
|
||||
event.setException(Optional.of(new SQLException("Test")));
|
||||
EventBusInstance.getInstance().post(event);
|
||||
}
|
||||
}
|
||||
|
|
@ -30,7 +30,7 @@
|
|||
|
||||
<!-- header -->
|
||||
<module name="Header">
|
||||
<property name="headerFile" value="CHECKSTYLE_HEAD"/>
|
||||
<property name="headerFile" value="${checkstyle.header.file}"/>
|
||||
</module>
|
||||
|
||||
<module name="RegexpSingleline">
|
||||
|
|
|
|||
2
pom.xml
2
pom.xml
|
|
@ -87,6 +87,7 @@
|
|||
<scala.compiler.version>2.11.7</scala.compiler.version>
|
||||
<powermock.version>1.6.4</powermock.version>
|
||||
<docker.plugin.version>0.4.13</docker.plugin.version>
|
||||
<checkstyle.header.file>java.header</checkstyle.header.file>
|
||||
</properties>
|
||||
|
||||
<dependencies>
|
||||
|
|
@ -315,6 +316,7 @@
|
|||
<configLocation>checkStyle.xml</configLocation>
|
||||
<encoding>UTF-8</encoding>
|
||||
<consoleOutput>true</consoleOutput>
|
||||
<includeTestSourceDirectory>true</includeTestSourceDirectory>
|
||||
<failsOnError>true</failsOnError>
|
||||
<excludes>org/skywalking/apm/network/**/*.java,
|
||||
org/skywalking/apm/collector/remote/grpc/**/*.java,
|
||||
|
|
|
|||
Loading…
Reference in New Issue