Refactored Stomp Propagation Channel tests

This commit is contained in:
Marcin Grzejszczak
2016-01-04 15:54:47 +01:00
parent 04ea3c6b79
commit 7ed53116fd
6 changed files with 121 additions and 139 deletions

View File

@@ -16,10 +16,6 @@
package org.springframework.cloud.sleuth.instrument.integration;
import java.util.List;
import java.util.Map;
import java.util.TreeMap;
import org.springframework.cloud.sleuth.Span;
import org.springframework.cloud.sleuth.Trace;
import org.springframework.cloud.sleuth.trace.TraceContextHolder;
@@ -27,6 +23,10 @@ import org.springframework.messaging.Message;
import org.springframework.messaging.simp.SimpMessageHeaderAccessor;
import org.springframework.messaging.simp.SimpMessageType;
import java.util.List;
import java.util.Map;
import java.util.TreeMap;
/**
* Builder class to create STOMP message
*
@@ -77,16 +77,13 @@ public class StompMessageBuilder {
public Message<?> build() {
SimpMessageHeaderAccessor headerAccessor = SimpMessageHeaderAccessor.create(SimpMessageType.MESSAGE);
String key;
Object value;
for (Map.Entry<String, Object> entry : this.headers.entrySet()) {
key = entry.getKey();
String key = entry.getKey();
if (key != null) {
value = entry.getValue();
Object value = entry.getValue();
pushHeaders(headerAccessor, key, value);
}
}
return org.springframework.messaging.support.MessageBuilder.createMessage(this.message.getPayload(),
headerAccessor.getMessageHeaders());
}

View File

@@ -16,8 +16,6 @@
package org.springframework.cloud.sleuth.instrument.integration;
import java.util.Map;
import org.springframework.aop.support.AopUtils;
import org.springframework.cloud.sleuth.Span;
import org.springframework.cloud.sleuth.Trace;
@@ -31,6 +29,8 @@ import org.springframework.messaging.support.ChannelInterceptorAdapter;
import org.springframework.messaging.support.ExecutorChannelInterceptor;
import org.springframework.util.Assert;
import java.util.Map;
/**
*
* @author Gaurav Rai Mazra
@@ -51,9 +51,7 @@ public class TraceStompMessageContextPropagationChannelInterceptor extends Chann
if (DirectChannel.class.isAssignableFrom(AopUtils.getTargetClass(channel))) {
return message;
}
Span span = this.traceManager.getCurrentSpan();
if (span != null) {
return new MessageWithSpan(message, span);
} else {
@@ -66,7 +64,7 @@ public class TraceStompMessageContextPropagationChannelInterceptor extends Chann
if (message instanceof MessageWithSpan) {
MessageWithSpan messageWithSpan = (MessageWithSpan) message;
Message<?> messageToHandle = messageWithSpan.message;
populatePropagatedContext(messageWithSpan.span, messageToHandle, channel);
populatePropagatedContext(messageWithSpan.span);
return message;
}
@@ -83,7 +81,7 @@ public class TraceStompMessageContextPropagationChannelInterceptor extends Chann
return postReceive(message, channel);
}
protected void populatePropagatedContext(Span span, Message<?> message, MessageChannel channel) {
protected void populatePropagatedContext(Span span) {
if (span != null) {
ORIGINAL_CONTEXT.set(this.traceManager.continueSpan(span).getSavedTrace());
}
@@ -116,11 +114,9 @@ public class TraceStompMessageContextPropagationChannelInterceptor extends Chann
span.addAnnotation(key, value);
}
}
Object payload = message.getPayload();
if (payload != null) {
span.addAnnotation("/messaging/payload/type", payload.getClass().getCanonicalName());
if (payload instanceof String) {
span.addAnnotation("/messaging/payload/size", String.valueOf(((String) payload).length()));
} else if (payload instanceof byte[]) {

View File

@@ -0,0 +1,68 @@
package org.springframework.cloud.sleuth.instrument.integration;
import org.junit.After;
import org.junit.Before;
import org.junit.runner.RunWith;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.cloud.sleuth.Trace;
import org.springframework.cloud.sleuth.TraceManager;
import org.springframework.cloud.sleuth.sampler.AlwaysSampler;
import org.springframework.cloud.sleuth.trace.TraceContextHolder;
import org.springframework.messaging.Message;
import org.springframework.messaging.support.ExecutorSubscribableChannel;
import org.springframework.messaging.support.GenericMessage;
import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
import static org.assertj.core.api.BDDAssertions.then;
@RunWith(SpringJUnit4ClassRunner.class)
abstract class AbstractTraceStompIntegrationTests {
@Autowired
@Qualifier("executorSubscribableChannel")
ExecutorSubscribableChannel channel;
@Autowired TraceManager traceManager;
@Autowired StompMessageHandler stompMessageHandler;
@Autowired AlwaysSampler sampler;
@Before
public void init() {
this.channel.subscribe(stompMessageHandler);
}
@After
public void close() {
TraceContextHolder.removeCurrentTrace();
this.channel.unsubscribe(stompMessageHandler);
}
Trace givenALocallyStartedSpan() {
return traceManager.startSpan("testSendMessage", sampler, null);
}
Message<?> givenMessageToBeSampled() {
return StompMessageBuilder.fromMessage(new GenericMessage<>("Message2")).build();
}
void whenTheMessageWasSent(Message<?> message) {
this.channel.send(message);
then(stompMessageHandler.message).isNotNull();
}
String thenSpanIdFromHeadersIsNotEmpty() {
String header = getValueFromHeaders(Trace.SPAN_ID_NAME);
then(header).as("Span id should not be empty").isNotEmpty();
return header;
}
String thenTraceIdFromHeadersIsNotEmpty() {
String header = getValueFromHeaders(Trace.TRACE_ID_NAME);
then(header).as("Trace id should not be empty").isNotEmpty();
return header;
}
String getValueFromHeaders(String headerName) {
return stompMessageHandler.message.getHeaders().get(headerName, String.class);
}
}

View File

@@ -0,0 +1,15 @@
package org.springframework.cloud.sleuth.instrument.integration;
import org.springframework.messaging.Message;
import org.springframework.messaging.MessageHandler;
import org.springframework.messaging.MessagingException;
class StompMessageHandler implements MessageHandler {
Message<?> message;
@Override
public void handleMessage(Message<?> message) throws MessagingException {
this.message = message;
}
}

View File

@@ -35,27 +35,10 @@ import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
* @author Gaurav Rai Mazra
*
*/
@RunWith(SpringJUnit4ClassRunner.class)
@SpringApplicationConfiguration(classes = TestApplication.class)
@IntegrationTest
public class TraceStompMessageChannelInterceptorTests {
@Autowired
@Qualifier("executorSubscribableChannel")
private ExecutorSubscribableChannel channel;
@Autowired TraceManager traceManager;
@Autowired StompMessageHandler stompMessageHandler;
@Before
public void init() {
this.channel.subscribe(stompMessageHandler);
}
@After
public void close() {
TraceContextHolder.removeCurrentTrace();
this.channel.unsubscribe(stompMessageHandler);
}
public class TraceStompMessageChannelInterceptorTests extends AbstractTraceStompIntegrationTests {
@Test
public void should_not_create_span_if_message_contains_not_sampled_header() {
@@ -93,49 +76,20 @@ public class TraceStompMessageChannelInterceptorTests {
then(TraceContextHolder.getCurrentTrace()).isNull();
}
private Trace givenALocallyStartedSpan() {
return traceManager.startSpan("testSendMessage", new AlwaysSampler(), null);
}
private Message<?> givenMessageNotToBeSampled() {
return StompMessageBuilder.fromMessage(new GenericMessage<>("Message2")).setHeader(Trace.NOT_SAMPLED_NAME, "").build();
}
private Message<?> givenMessageToBeSampled() {
return StompMessageBuilder.fromMessage(new GenericMessage<>("Message2")).build();
}
private void whenTheMessageWasSent(Message<?> message) {
this.channel.send(message);
then(stompMessageHandler.message).isNotNull();
}
private String thenSpanIdFromHeadersIsEmpty() {
String header = getValueFromHeaders(Trace.SPAN_ID_NAME);
then(header).as("Span id should be empty").isNullOrEmpty();
return header;
}
private String thenSpanIdFromHeadersIsNotEmpty() {
String header = getValueFromHeaders(Trace.SPAN_ID_NAME);
then(header).as("Span id should not be empty").isNotEmpty();
return header;
}
private String thenTraceIdFromHeadersIsNotEmpty() {
String header = getValueFromHeaders(Trace.TRACE_ID_NAME);
then(header).as("Trace id should not be empty").isNotEmpty();
return header;
}
private void thenReceivedMessageIsEqualToTheSentOne(Message<?> message) {
then(message.getPayload()).isEqualTo(stompMessageHandler.message.getPayload());
}
private String getValueFromHeaders(String headerName) {
return stompMessageHandler.message.getHeaders().get(headerName, String.class);
}
@Configuration
@EnableAutoConfiguration
static class TestApplication {
@@ -154,14 +108,4 @@ public class TraceStompMessageChannelInterceptorTests {
return new AlwaysSampler();
}
}
static class StompMessageHandler implements MessageHandler {
Message<?> message;
@Override
public void handleMessage(Message<?> message) throws MessagingException {
this.message = message;
}
}
}

View File

@@ -1,29 +1,22 @@
package org.springframework.cloud.sleuth.instrument.integration;
import static org.assertj.core.api.BDDAssertions.then;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertNotNull;
import org.junit.After;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.boot.autoconfigure.EnableAutoConfiguration;
import org.springframework.boot.test.IntegrationTest;
import org.springframework.boot.test.SpringApplicationConfiguration;
import org.springframework.cloud.sleuth.Trace;
import org.springframework.cloud.sleuth.TraceManager;
import org.springframework.cloud.sleuth.instrument.integration.TraceStompMessageContextPropagationChannelInterceptorTests.TestApplication;
import org.springframework.cloud.sleuth.sampler.AlwaysSampler;
import org.springframework.cloud.sleuth.trace.TraceContextHolder;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.messaging.Message;
import org.springframework.messaging.MessageHandler;
import org.springframework.messaging.MessagingException;
import org.springframework.messaging.support.ExecutorSubscribableChannel;
import org.springframework.messaging.support.GenericMessage;
import org.springframework.test.annotation.DirtiesContext;
import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
/**
@@ -34,78 +27,47 @@ import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
@RunWith(SpringJUnit4ClassRunner.class)
@SpringApplicationConfiguration(classes=TestApplication.class)
@IntegrationTest
public class TraceStompMessageContextPropagationChannelInterceptorTests implements MessageHandler {
@Autowired
@Qualifier("executorSubscribableChannel")
private ExecutorSubscribableChannel channel;
public class TraceStompMessageContextPropagationChannelInterceptorTests extends AbstractTraceStompIntegrationTests {
@Autowired
private TraceManager traceManager;
@Autowired
private AlwaysSampler sampler;
private Message<?> message;
@Override
public void handleMessage(Message<?> message) throws MessagingException {
this.message = message;
}
@org.junit.Before
public void init() {
this.channel.subscribe(this);
}
@After
public void close() {
TraceContextHolder.removeCurrentTrace();
this.channel.unsubscribe(this);
}
@Test
public void testSpanPropagation() {
final TraceManager traceManager = this.traceManager;
Trace trace = traceManager.startSpan("testSendMessage", this.sampler, null);
Message<?> m = StompMessageBuilder.fromMessage(new GenericMessage<String>("Message2")).build();
public void should_propagate_span_information() {
Trace trace = givenALocallyStartedSpan();
Message<?> m = givenMessageToBeSampled();
this.channel.send(m);
String expectedSpanId = trace.getSpan().getSpanId();
whenTheMessageWasSent(m);
String expectedTraceId = trace.getSpan().getTraceId();
traceManager.close(trace);
Message<?> message = this.message;
assertNotNull("message was null", message);
String spanId = message.getHeaders().get(Trace.SPAN_ID_NAME, String.class);
assertEquals("spanId was wrong", expectedSpanId, spanId);
String traceId = message.getHeaders().get(Trace.TRACE_ID_NAME, String.class);
assertNotNull("traceId was null", traceId);
thenReceivedMessageIsNotNull();
String traceId = thenTraceIdFromHeadersIsNotEmpty();
then(traceId).isEqualTo(expectedTraceId);
thenSpanIdFromHeadersIsNotEmpty();
}
private void thenReceivedMessageIsNotNull() {
Message<?> message = stompMessageHandler.message;
then(message).isNotNull();
}
@Configuration
@EnableAutoConfiguration
static class TestApplication {
@Autowired
TraceStompMessageChannelInterceptor stompChannelInterceptor;
@Autowired
TraceStompMessageContextPropagationChannelInterceptor stompMessageContextChannelInterceptor;
@Bean
public ExecutorSubscribableChannel executorSubscribableChannel() {
@Bean ExecutorSubscribableChannel executorSubscribableChannel(
TraceStompMessageChannelInterceptor stompChannelInterceptor,
TraceStompMessageContextPropagationChannelInterceptor stompMessageContextChannelInterceptor) {
ExecutorSubscribableChannel channel = new ExecutorSubscribableChannel();
channel.addInterceptor(stompChannelInterceptor);
channel.addInterceptor(stompMessageContextChannelInterceptor);
return channel;
}
@Bean
public AlwaysSampler alwaysSampler() {
@Bean AlwaysSampler alwaysSampler() {
return new AlwaysSampler();
}
@Bean StompMessageHandler stompMessageHandler() {
return new StompMessageHandler();
}
}
}