Split out @Async instrumentation into its own package
There was an ordering error in the conditions as well, causing the wrong async customizers to be registered. Another issue was the servlet async processing (request atribute not cached in all branches) resulting in multiple spans per request.
This commit is contained in:
@@ -56,6 +56,7 @@ public class MilliSpan implements Span {
|
||||
}
|
||||
|
||||
//for serialization
|
||||
@SuppressWarnings("unused")
|
||||
private MilliSpan() {
|
||||
this.begin = 0;
|
||||
this.name = null;
|
||||
|
||||
@@ -28,6 +28,7 @@ public class TimelineAnnotation {
|
||||
private final long time;
|
||||
private final String msg;
|
||||
|
||||
@SuppressWarnings("unused")
|
||||
private TimelineAnnotation() {
|
||||
this.time = 0;
|
||||
this.msg = null;
|
||||
|
||||
@@ -17,6 +17,7 @@
|
||||
package org.springframework.cloud.sleuth.autoconfig;
|
||||
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
|
||||
import org.springframework.cloud.sleuth.IdGenerator;
|
||||
import org.springframework.cloud.sleuth.RandomUuidGenerator;
|
||||
import org.springframework.cloud.sleuth.Sampler;
|
||||
@@ -31,6 +32,7 @@ import org.springframework.context.annotation.Configuration;
|
||||
* @author Spencer Gibb
|
||||
*/
|
||||
@Configuration
|
||||
@ConditionalOnProperty(value="spring.sleuth.enabled", matchIfMissing=true)
|
||||
public class TraceAutoConfiguration {
|
||||
|
||||
@Bean
|
||||
|
||||
@@ -0,0 +1,57 @@
|
||||
/*
|
||||
* Copyright 2015 the original author or authors.
|
||||
*
|
||||
* 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.
|
||||
*/
|
||||
|
||||
package org.springframework.cloud.sleuth.instrument.async;
|
||||
|
||||
import org.springframework.beans.BeansException;
|
||||
import org.springframework.beans.factory.BeanFactory;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.beans.factory.config.BeanPostProcessor;
|
||||
import org.springframework.boot.autoconfigure.AutoConfigureAfter;
|
||||
import org.springframework.boot.autoconfigure.AutoConfigureBefore;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnBean;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
|
||||
import org.springframework.cloud.sleuth.instrument.scheduling.TraceSchedulingAutoConfiguration;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
import org.springframework.scheduling.annotation.AsyncConfigurer;
|
||||
|
||||
@Configuration
|
||||
@ConditionalOnBean(AsyncConfigurer.class)
|
||||
@AutoConfigureBefore(AsyncDefaultAutoConfiguration.class)
|
||||
@ConditionalOnProperty(value = "spring.sleuth.async.enabled", matchIfMissing = true)
|
||||
@AutoConfigureAfter(TraceSchedulingAutoConfiguration.class)
|
||||
public class AsyncCustomAutoConfiguration implements BeanPostProcessor {
|
||||
|
||||
@Autowired
|
||||
private BeanFactory beanFactory;
|
||||
|
||||
@Override
|
||||
public Object postProcessBeforeInitialization(Object bean, String beanName)
|
||||
throws BeansException {
|
||||
return bean;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Object postProcessAfterInitialization(Object bean, String beanName)
|
||||
throws BeansException {
|
||||
if (bean instanceof AsyncConfigurer) {
|
||||
AsyncConfigurer configurer = (AsyncConfigurer) bean;
|
||||
return new LazyTraceAsyncCustomizer(this.beanFactory, configurer);
|
||||
}
|
||||
return bean;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,50 @@
|
||||
/*
|
||||
* Copyright 2015 the original author or authors.
|
||||
*
|
||||
* 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.
|
||||
*/
|
||||
|
||||
package org.springframework.cloud.sleuth.instrument.async;
|
||||
|
||||
import java.util.concurrent.Executor;
|
||||
|
||||
import org.springframework.beans.factory.BeanFactory;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.boot.autoconfigure.AutoConfigureAfter;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnBean;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
|
||||
import org.springframework.cloud.sleuth.Trace;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
import org.springframework.core.task.SimpleAsyncTaskExecutor;
|
||||
import org.springframework.scheduling.annotation.AsyncConfigurer;
|
||||
import org.springframework.scheduling.annotation.AsyncConfigurerSupport;
|
||||
import org.springframework.scheduling.annotation.EnableAsync;
|
||||
|
||||
@EnableAsync
|
||||
@Configuration
|
||||
@ConditionalOnMissingBean(AsyncConfigurer.class)
|
||||
@ConditionalOnProperty(value = "spring.sleuth.async.enabled", matchIfMissing = true)
|
||||
@ConditionalOnBean(Trace.class)
|
||||
@AutoConfigureAfter(AsyncCustomAutoConfiguration.class)
|
||||
public class AsyncDefaultAutoConfiguration extends AsyncConfigurerSupport {
|
||||
|
||||
@Autowired
|
||||
private BeanFactory beanFactory;
|
||||
|
||||
@Override
|
||||
public Executor getAsyncExecutor() {
|
||||
return new LazyTraceExecutor(this.beanFactory, new SimpleAsyncTaskExecutor());
|
||||
}
|
||||
|
||||
}
|
||||
@@ -14,7 +14,7 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.springframework.cloud.sleuth.instrument.scheduling;
|
||||
package org.springframework.cloud.sleuth.instrument.async;
|
||||
|
||||
import java.util.concurrent.Executor;
|
||||
|
||||
@@ -22,7 +22,6 @@ import lombok.RequiredArgsConstructor;
|
||||
|
||||
import org.springframework.aop.interceptor.AsyncUncaughtExceptionHandler;
|
||||
import org.springframework.beans.factory.BeanFactory;
|
||||
import org.springframework.cloud.sleuth.Trace;
|
||||
import org.springframework.scheduling.annotation.AsyncConfigurer;
|
||||
import org.springframework.scheduling.annotation.AsyncConfigurerSupport;
|
||||
|
||||
@@ -33,16 +32,12 @@ import org.springframework.scheduling.annotation.AsyncConfigurerSupport;
|
||||
@RequiredArgsConstructor
|
||||
public class LazyTraceAsyncCustomizer extends AsyncConfigurerSupport {
|
||||
|
||||
private Trace trace;
|
||||
private final BeanFactory beanFactory;
|
||||
private final AsyncConfigurer delegate;
|
||||
|
||||
@Override
|
||||
public Executor getAsyncExecutor() {
|
||||
if (this.trace == null) {
|
||||
this.trace = this.beanFactory.getBean(Trace.class);
|
||||
}
|
||||
return new TraceExecutor(this.trace, this.delegate.getAsyncExecutor());
|
||||
return new LazyTraceExecutor(this.beanFactory, this.delegate.getAsyncExecutor());
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -14,12 +14,14 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.springframework.cloud.sleuth.instrument.scheduling;
|
||||
package org.springframework.cloud.sleuth.instrument.async;
|
||||
|
||||
import java.util.concurrent.Executor;
|
||||
|
||||
import lombok.RequiredArgsConstructor;
|
||||
|
||||
import org.springframework.beans.factory.BeanFactory;
|
||||
import org.springframework.beans.factory.NoSuchBeanDefinitionException;
|
||||
import org.springframework.cloud.sleuth.Trace;
|
||||
import org.springframework.cloud.sleuth.instrument.TraceRunnable;
|
||||
|
||||
@@ -28,13 +30,22 @@ import org.springframework.cloud.sleuth.instrument.TraceRunnable;
|
||||
*
|
||||
*/
|
||||
@RequiredArgsConstructor
|
||||
public class TraceExecutor implements Executor {
|
||||
public class LazyTraceExecutor implements Executor {
|
||||
|
||||
private final Trace trace;
|
||||
private Trace trace;
|
||||
private final BeanFactory beanFactory;
|
||||
private final Executor delegate;
|
||||
|
||||
@Override
|
||||
public void execute(Runnable command) {
|
||||
if (this.trace == null) {
|
||||
try {
|
||||
this.trace = this.beanFactory.getBean(Trace.class);
|
||||
}
|
||||
catch (NoSuchBeanDefinitionException e) {
|
||||
this.delegate.execute(command);
|
||||
}
|
||||
}
|
||||
this.delegate.execute(new TraceRunnable(this.trace, command));
|
||||
}
|
||||
|
||||
@@ -16,8 +16,12 @@
|
||||
|
||||
package org.springframework.cloud.sleuth.instrument.integration;
|
||||
|
||||
import org.springframework.boot.autoconfigure.AutoConfigureAfter;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnBean;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnClass;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
|
||||
import org.springframework.cloud.sleuth.Trace;
|
||||
import org.springframework.cloud.sleuth.autoconfig.TraceAutoConfiguration;
|
||||
import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
import org.springframework.integration.config.GlobalChannelInterceptor;
|
||||
@@ -27,6 +31,8 @@ import org.springframework.integration.config.GlobalChannelInterceptor;
|
||||
*/
|
||||
@Configuration
|
||||
@ConditionalOnClass(GlobalChannelInterceptor.class)
|
||||
@ConditionalOnBean(Trace.class)
|
||||
@AutoConfigureAfter(TraceAutoConfiguration.class)
|
||||
public class TraceSpringIntegrationAutoConfiguration {
|
||||
|
||||
@Bean
|
||||
|
||||
@@ -20,25 +20,16 @@ package org.springframework.cloud.sleuth.instrument.scheduling;
|
||||
* @author Spencer Gibb
|
||||
*/
|
||||
|
||||
import java.util.concurrent.Executor;
|
||||
|
||||
import org.aspectj.lang.ProceedingJoinPoint;
|
||||
import org.springframework.beans.BeansException;
|
||||
import org.springframework.beans.factory.BeanFactory;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.beans.factory.config.BeanPostProcessor;
|
||||
import org.springframework.boot.autoconfigure.AutoConfigureAfter;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnBean;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnClass;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
|
||||
import org.springframework.cloud.sleuth.Trace;
|
||||
import org.springframework.cloud.sleuth.autoconfig.TraceAutoConfiguration;
|
||||
import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
import org.springframework.context.annotation.EnableAspectJAutoProxy;
|
||||
import org.springframework.core.task.SimpleAsyncTaskExecutor;
|
||||
import org.springframework.scheduling.annotation.AsyncConfigurer;
|
||||
import org.springframework.scheduling.annotation.AsyncConfigurerSupport;
|
||||
import org.springframework.scheduling.annotation.EnableAsync;
|
||||
|
||||
/**
|
||||
* Registers beans related to task scheduling.
|
||||
@@ -51,6 +42,8 @@ import org.springframework.scheduling.annotation.EnableAsync;
|
||||
@Configuration
|
||||
@EnableAspectJAutoProxy
|
||||
@ConditionalOnProperty(value = "spring.sleuth.schedule.enabled", matchIfMissing = true)
|
||||
@ConditionalOnBean(Trace.class)
|
||||
@AutoConfigureAfter(TraceAutoConfiguration.class)
|
||||
public class TraceSchedulingAutoConfiguration {
|
||||
|
||||
@ConditionalOnClass(ProceedingJoinPoint.class)
|
||||
@@ -59,44 +52,4 @@ public class TraceSchedulingAutoConfiguration {
|
||||
return new TraceSchedulingAspect(trace);
|
||||
}
|
||||
|
||||
@EnableAsync
|
||||
@Configuration
|
||||
@ConditionalOnMissingBean(AsyncConfigurer.class)
|
||||
protected static class AsyncDefaultConfiguration extends AsyncConfigurerSupport {
|
||||
|
||||
@Autowired
|
||||
private Trace trace;
|
||||
|
||||
@Override
|
||||
public Executor getAsyncExecutor() {
|
||||
return new TraceExecutor(this.trace, new SimpleAsyncTaskExecutor());
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Configuration
|
||||
@ConditionalOnBean(AsyncConfigurer.class)
|
||||
protected static class AsyncCustomConfiguration implements BeanPostProcessor {
|
||||
|
||||
@Autowired
|
||||
private BeanFactory beanFactory;
|
||||
|
||||
@Override
|
||||
public Object postProcessBeforeInitialization(Object bean, String beanName)
|
||||
throws BeansException {
|
||||
return bean;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Object postProcessAfterInitialization(Object bean, String beanName)
|
||||
throws BeansException {
|
||||
if (bean instanceof AsyncConfigurer) {
|
||||
AsyncConfigurer configurer = (AsyncConfigurer) bean;
|
||||
return new LazyTraceAsyncCustomizer(this.beanFactory, configurer);
|
||||
}
|
||||
return bean;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -121,6 +121,7 @@ public class TraceFilter extends OncePerRequestFilter {
|
||||
}
|
||||
else {
|
||||
traceScope = this.trace.startSpan(name);
|
||||
request.setAttribute(TRACE_REQUEST_ATTR, traceScope);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -131,13 +132,12 @@ public class TraceFilter extends OncePerRequestFilter {
|
||||
filterChain.doFilter(request, response);
|
||||
}
|
||||
finally {
|
||||
if (request.isAsyncSupported() && request.isAsyncStarted()) {
|
||||
//TODO: howto deal with response annotations and async?
|
||||
if (isAsyncStarted(request) || request.isAsyncStarted()) {
|
||||
//TODO: how to deal with response annotations and async?
|
||||
return;
|
||||
}
|
||||
if (traceScope != null) {
|
||||
addResponseAnnotations(response);
|
||||
|
||||
traceScope.close();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -19,11 +19,14 @@ import java.util.regex.Pattern;
|
||||
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.beans.factory.annotation.Value;
|
||||
import org.springframework.boot.autoconfigure.AutoConfigureAfter;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnBean;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnWebApplication;
|
||||
import org.springframework.boot.context.embedded.FilterRegistrationBean;
|
||||
import org.springframework.cloud.sleuth.Trace;
|
||||
import org.springframework.cloud.sleuth.autoconfig.TraceAutoConfiguration;
|
||||
import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
import org.springframework.util.StringUtils;
|
||||
@@ -39,6 +42,8 @@ import org.springframework.util.StringUtils;
|
||||
@Configuration
|
||||
@ConditionalOnProperty(value = "spring.sleuth.web.enabled", matchIfMissing = true)
|
||||
@ConditionalOnWebApplication
|
||||
@ConditionalOnBean(Trace.class)
|
||||
@AutoConfigureAfter(TraceAutoConfiguration.class)
|
||||
public class TraceWebAutoConfiguration {
|
||||
|
||||
/**
|
||||
|
||||
@@ -21,9 +21,13 @@ import java.util.Collection;
|
||||
import javax.annotation.PostConstruct;
|
||||
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.boot.autoconfigure.AutoConfigureAfter;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnBean;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnClass;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
|
||||
import org.springframework.cloud.sleuth.Trace;
|
||||
import org.springframework.cloud.sleuth.autoconfig.TraceAutoConfiguration;
|
||||
import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
import org.springframework.web.client.RestTemplate;
|
||||
@@ -34,6 +38,8 @@ import org.springframework.web.client.RestTemplate;
|
||||
@Configuration
|
||||
@ConditionalOnProperty(value = "spring.sleuth.client.enabled", matchIfMissing = true)
|
||||
@ConditionalOnClass(RestTemplate.class)
|
||||
@ConditionalOnBean(Trace.class)
|
||||
@AutoConfigureAfter(TraceAutoConfiguration.class)
|
||||
public class TraceWebClientAutoConfiguration {
|
||||
|
||||
@Bean
|
||||
|
||||
@@ -32,7 +32,6 @@ import com.fasterxml.jackson.databind.ObjectMapper;
|
||||
* @author Spencer Gibb
|
||||
*/
|
||||
@CommonsLog
|
||||
@Order(Ordered.LOWEST_PRECEDENCE)
|
||||
@Data
|
||||
public class JsonLogSpanListener {
|
||||
|
||||
@@ -41,16 +40,17 @@ public class JsonLogSpanListener {
|
||||
private final ObjectMapper objectMapper = new ObjectMapper();
|
||||
|
||||
public JsonLogSpanListener() {
|
||||
prefix = "[span]";
|
||||
suffix = "[endspan]";
|
||||
objectMapper.configure(DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES, false);
|
||||
this.prefix = "[span]";
|
||||
this.suffix = "[endspan]";
|
||||
this.objectMapper.configure(DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES, false);
|
||||
}
|
||||
|
||||
@SneakyThrows
|
||||
@EventListener(SpanStoppedEvent.class)
|
||||
@Order(Ordered.LOWEST_PRECEDENCE-10)
|
||||
public void stop(SpanStoppedEvent event) {
|
||||
log.info(prefix + objectMapper.writeValueAsString(event.getSpan()) +
|
||||
suffix);
|
||||
log.info(this.prefix + this.objectMapper.writeValueAsString(event.getSpan()) +
|
||||
this.suffix);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -18,8 +18,12 @@ package org.springframework.cloud.sleuth.log;
|
||||
|
||||
import org.apache.commons.logging.Log;
|
||||
import org.slf4j.MDC;
|
||||
import org.springframework.boot.autoconfigure.AutoConfigureAfter;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnBean;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnClass;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
|
||||
import org.springframework.cloud.sleuth.Trace;
|
||||
import org.springframework.cloud.sleuth.autoconfig.TraceAutoConfiguration;
|
||||
import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
|
||||
@@ -27,6 +31,8 @@ import org.springframework.context.annotation.Configuration;
|
||||
* @author Spencer Gibb
|
||||
*/
|
||||
@Configuration
|
||||
@ConditionalOnBean(Trace.class)
|
||||
@AutoConfigureAfter(TraceAutoConfiguration.class)
|
||||
public class SleuthLogAutoConfiguration {
|
||||
|
||||
@Configuration
|
||||
|
||||
@@ -33,10 +33,10 @@ import org.springframework.core.annotation.Order;
|
||||
* @author Spencer Gibb
|
||||
*/
|
||||
@Slf4j
|
||||
@Order(Ordered.LOWEST_PRECEDENCE)
|
||||
public class Slf4jSpanListener {
|
||||
|
||||
@EventListener(SpanStartedEvent.class)
|
||||
@Order(Ordered.LOWEST_PRECEDENCE)
|
||||
public void start(SpanStartedEvent event) {
|
||||
Span span = event.getSpan();
|
||||
MDC.put(Trace.SPAN_ID_NAME, span.getSpanId());
|
||||
@@ -49,6 +49,7 @@ public class Slf4jSpanListener {
|
||||
}
|
||||
|
||||
@EventListener(SpanStoppedEvent.class)
|
||||
@Order(Ordered.LOWEST_PRECEDENCE)
|
||||
public void stop(SpanStoppedEvent event) {
|
||||
//TODO: what should this log level be?
|
||||
log.info("Stopped span: {}", event.getSpan());
|
||||
|
||||
@@ -3,6 +3,8 @@ org.springframework.boot.autoconfigure.EnableAutoConfiguration=\
|
||||
org.springframework.cloud.sleuth.autoconfig.TraceAutoConfiguration,\
|
||||
org.springframework.cloud.sleuth.log.SleuthLogAutoConfiguration,\
|
||||
org.springframework.cloud.sleuth.instrument.integration.TraceSpringIntegrationAutoConfiguration,\
|
||||
org.springframework.cloud.sleuth.instrument.async.AsyncCustomAutoConfiguration,\
|
||||
org.springframework.cloud.sleuth.instrument.async.AsyncDefaultAutoConfiguration,\
|
||||
org.springframework.cloud.sleuth.instrument.scheduling.TraceSchedulingAutoConfiguration,\
|
||||
org.springframework.cloud.sleuth.instrument.web.TraceWebAutoConfiguration,\
|
||||
org.springframework.cloud.sleuth.instrument.web.client.TraceWebClientAutoConfiguration
|
||||
|
||||
@@ -16,8 +16,6 @@
|
||||
|
||||
package org.springframework.cloud.sleuth.sample;
|
||||
|
||||
import com.github.kristofa.brave.LoggingSpanCollectorImpl;
|
||||
import com.github.kristofa.brave.SpanCollector;
|
||||
import org.springframework.boot.SpringApplication;
|
||||
import org.springframework.boot.autoconfigure.SpringBootApplication;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
|
||||
@@ -27,6 +25,9 @@ import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.context.annotation.EnableAspectJAutoProxy;
|
||||
import org.springframework.scheduling.annotation.EnableAsync;
|
||||
|
||||
import com.github.kristofa.brave.LoggingSpanCollectorImpl;
|
||||
import com.github.kristofa.brave.SpanCollector;
|
||||
|
||||
/**
|
||||
* @author Spencer Gibb
|
||||
*/
|
||||
|
||||
@@ -39,7 +39,7 @@ import org.springframework.web.client.RestTemplate;
|
||||
*/
|
||||
@Slf4j
|
||||
@RestController
|
||||
class SampleController implements
|
||||
public class SampleController implements
|
||||
ApplicationListener<EmbeddedServletContainerInitializedEvent> {
|
||||
@Autowired
|
||||
private RestTemplate restTemplate;
|
||||
|
||||
@@ -49,7 +49,6 @@ import com.twitter.zipkin.gen.zipkinCoreConstants;
|
||||
* @author Spencer Gibb
|
||||
*/
|
||||
@CommonsLog
|
||||
@Order(0)
|
||||
public class ZipkinSpanListener {
|
||||
|
||||
private SpanCollector spanCollector;
|
||||
@@ -63,6 +62,7 @@ public class ZipkinSpanListener {
|
||||
}
|
||||
|
||||
@EventListener
|
||||
@Order(0)
|
||||
public void start(SpanStartedEvent event) {
|
||||
if (event.getParent()!=null && event.getParent().isRemote()) {
|
||||
event.getParent().addTimelineAnnotation(zipkinCoreConstants.SERVER_RECV);
|
||||
@@ -71,17 +71,20 @@ public class ZipkinSpanListener {
|
||||
}
|
||||
|
||||
@EventListener
|
||||
@Order(0)
|
||||
public void clientSend(ClientSentEvent event) {
|
||||
event.getSpan().addTimelineAnnotation(zipkinCoreConstants.CLIENT_SEND);
|
||||
}
|
||||
|
||||
@EventListener
|
||||
@Order(0)
|
||||
public void clientReceive(ClientReceivedEvent event) {
|
||||
event.getSpan().addTimelineAnnotation(zipkinCoreConstants.CLIENT_RECV);
|
||||
}
|
||||
|
||||
@EventListener
|
||||
public void start(SpanStoppedEvent event) {
|
||||
@Order(0)
|
||||
public void stop(SpanStoppedEvent event) {
|
||||
if (event.getParent()!=null && event.getParent().isRemote()) {
|
||||
event.getParent().addTimelineAnnotation(zipkinCoreConstants.SERVER_SEND);
|
||||
this.spanCollector.collect(convert(event.getParent()));
|
||||
@@ -93,10 +96,9 @@ public class ZipkinSpanListener {
|
||||
/**
|
||||
* Converts a given Sleuth span to a Zipkin Span.
|
||||
* <ul>
|
||||
* <li>First set the start annotation. [CS, SR], depending whether it is a client service or not.
|
||||
* <li>Set other id's, etc [TraceId's etc]
|
||||
* <li>Set id's, etc [TraceId's etc]
|
||||
* <li>Create timeline annotations based on data from HTrace Span object.
|
||||
* <li>Create binary annotations based on data from HTrace Span object.
|
||||
* <li>Set the last annotation. [SS, CR]
|
||||
* </ul>
|
||||
*/
|
||||
public com.twitter.zipkin.gen.Span convert(Span span) {
|
||||
|
||||
Reference in New Issue
Block a user