Further WebFlux and Messaging Reactor Sleuth improvements (#1699)

* Improving performance and adding docs
This commit is contained in:
Marcin Grzejszczak
2020-07-28 18:02:16 +02:00
committed by GitHub
parent 5b98f79f92
commit 1c33332320
18 changed files with 479 additions and 151 deletions

View File

@@ -708,6 +708,8 @@ You can configure which URIs you would like to skip by using the `spring.sleuth.
If you have `ManagementServerProperties` on the classpath, its value of `contextPath` gets appended to the provided skip pattern.
If you want to reuse Sleuth's default skip patterns and append your own, pass those patterns by using the `spring.sleuth.web.additionalSkipPattern`.
In order to achieve best results in terms of performance and context propagation we suggest that you switch the `spring.sleuth.reactor.instrumentation-type` to `MANUAL`. In order to execute code with the span in scope you can call `WebFluxSleuthOperators.withSpanInScope`.
To change the order of tracing filter registration, please set the
`spring.sleuth.web.filter-order` property.
@@ -929,7 +931,7 @@ to add the `@Role(BeanDefinition.ROLE_INFRASTRUCTURE)` on your
Features from this section can be disabled by setting the `spring.sleuth.messaging.enabled` property with value equal to `false`.
==== Spring Integration and Spring Cloud Stream
==== Spring Integration
Spring Cloud Sleuth integrates with https://projects.spring.io/spring-integration/[Spring Integration].
It creates spans for publish and subscribe events.
@@ -947,6 +949,21 @@ it's enough for you to register beans of types:
* `Propagation.Setter<MessageHeaderAccessor, String>` - for writing headers to the message
* `Propagation.Getter<MessageHeaderAccessor, String>` - for reading headers from the message
==== Spring Cloud Function and Spring Cloud Stream
Spring Cloud Sleuth can instrument Spring Cloud Function. The way to achieve it is to provide a `Function` or `Consumer` or `Supplier` that takes in a `Message` as a parameter e.g. `Function<Message<String>, Message<Integer>>`. If the type is not `Message` then instrumentation will not take place. Out of the box instrumentation will not take place when dealing with Reactor based streams - e.g. `Function<Flux<Message<String>>, Flux<Message<Integer>>>`.
Since Spring Cloud Stream reuses Spring Cloud Function, you'll get the instrumentation out of the box.
You can disable this behavior by setting the value of `spring.sleuth.function.enabled` to `false`.
In order to work with reactive Stream functions you can leverage the `MessagingSleuthOperators` utility class that allows you to manipulate the input and output messages in order to continue the tracing context and to execute custom code within the tracing context.
[source,java]
-----
include::{project-root}/benchmarks/src/main/java/org/springframework/cloud/sleuth/benchmarks/app/stream/SleuthBenchmarkingStreamApplication.java[tags=simple_reactive,indent=0]
-----
==== Spring RabbitMq
We instrument the `RabbitTemplate` so that tracing headers get injected
@@ -1000,7 +1017,19 @@ To turn off this feature, set the `spring.sleuth.quartz.enabled` property to `fa
=== Project Reactor
For projects depending on Project Reactor such as Spring Cloud Gateway, we suggest turning the `spring.sleuth.reactor.decorate-on-each` option to `false`. That way an increased performance gain should be observed in comparison to the standard instrumentation mechanism. What this option does is it will wrap decorate `onLast` operator instead of `onEach` which will result in creation of far fewer objects. The downside of this is that when Project Reactor will change threads, the trace propagation will continue without issues, however anything relying on the `ThreadLocal` such as e.g. MDC entries can be buggy.
We have three modes of instrumenting reactor based applications that can
be set via `spring.sleuth.reactor.instrumentation-type` property:
* `ON_EACH` - wraps every Reactor operator in a trace representation. Passes the tracing context in most cases. This mode might lead to drastic performance degradation.
* `ON_LAST` - wraps last Reactor operator in a trace representation. Passes the tracing context in some cases thus accessing MDC context might not work. This mode might lead to medium performance degradation.
* `MANUAL` - wraps every Reactor in the least invasive way without passing of tracing context. It's up to the user to do it.
Current default is `ON_EACH` for backward compatibility reasons, however we encourage the users to migrate to the `MANUAL` instrumentation and profit from `WebFluxSleuthOperators` and `MessagingSleuthOperators`. The performance improvement can be substantial. Example:
[source,java]
-----
include::{project-root}/benchmarks/src/main/java/org/springframework/cloud/sleuth/benchmarks/app/webflux/SleuthBenchmarkingSpringWebFluxApp.java[tags=simple_manual,indent=0]
-----
== Log integration
Sleuth configures the logging context with variables including the service name