Skip to content

Commit

Permalink
Start timer in timeout handling after extracting request context
Browse files Browse the repository at this point in the history
Signed-off-by: Klem Yannic (INST/ECS1) <Yannic.Klem@bosch-si.com>
  • Loading branch information
Yannic92 committed Jul 10, 2018
1 parent f67e019 commit 31bab0c
Show file tree
Hide file tree
Showing 3 changed files with 17 additions and 32 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -18,15 +18,12 @@

import java.time.Duration;
import java.time.temporal.ChronoUnit;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;
import java.util.function.Supplier;

import org.eclipse.ditto.model.base.exceptions.DittoRuntimeException;
import org.eclipse.ditto.model.base.headers.DittoHeaders;
import org.eclipse.ditto.services.gateway.starter.service.util.ConfigKeys;
import org.eclipse.ditto.services.utils.tracing.MutableKamonTimer;
import org.eclipse.ditto.services.utils.tracing.MutableKamonTimerBuilder;
import org.eclipse.ditto.services.utils.tracing.TraceUtils;
import org.eclipse.ditto.services.utils.tracing.TracingTags;
import org.eclipse.ditto.signals.commands.base.exceptions.GatewayServiceUnavailableException;
Expand All @@ -53,7 +50,6 @@ public final class RequestTimeoutHandlingDirective {
private static final Duration SEARCH_WARN_TIMEOUT_MS = Duration.ofMillis(5_000);
private static final Duration HTTP_WARN_TIMEOUT_MS = Duration.ofMillis(1_000);
private static final String TRACING_ENTITY_SEARCH = "search/things";
private static final Map<String, MutableKamonTimer> timers = new ConcurrentHashMap<>();

private RequestTimeoutHandlingDirective() {
// no op
Expand All @@ -74,26 +70,25 @@ public static Route handleRequestTimeout(final String correlationId, final Suppl
return extractRequestContext(requestContext -> {


final MutableKamonTimerBuilder timerBuilder = TraceUtils.newHttpRoundtripTimer(requestContext);
final MutableKamonTimer timer =
TraceUtils.newHttpRoundTripTimer(requestContext.getRequest()).buildStartedTimer();
LOGGER.debug("Started mutable timer <{}>", timer);

final Supplier<Route> innerWithTimer = () -> Directives.mapResponse(response -> {
final MutableKamonTimer mutableTimer = timerBuilder.buildStartedTimer();
LOGGER.debug("Started mutable timer <{}>", mutableTimer);
timers.put(correlationId, mutableTimer);

final int statusCode = response.status().intValue();
mutableTimer
timer
.tag(TracingTags.STATUS_CODE, statusCode)
.stop();
checkDurationWarning(mutableTimer);
LOGGER.debug("Finished mutable timer <{}> with status <{}>", mutableTimer, statusCode);
LOGGER.debug("Finished mutable timer <{}> with status <{}>", timer, statusCode);
checkDurationWarning(timer);
return response;
}, inner);

return Directives.withRequestTimeoutResponse(
request ->
enhanceLogWithCorrelationId(correlationId, () ->
doHandleRequestTimeout(correlationId, config, requestContext)),
doHandleRequestTimeout(correlationId, config, requestContext, timer)),
innerWithTimer);
});
});
Expand All @@ -115,7 +110,7 @@ private static void checkDurationWarning(final MutableKamonTimer mutableTimer) {
}

private static HttpResponse doHandleRequestTimeout(final String correlationId, final Config config,
final RequestContext requestContext) {
final RequestContext requestContext, final MutableKamonTimer timer) {
final Duration duration = config.getDuration(ConfigKeys.AKKA_HTTP_SERVER_REQUEST_TIMEOUT);

final DittoRuntimeException cre = GatewayServiceUnavailableException
Expand All @@ -139,11 +134,11 @@ private static HttpResponse doHandleRequestTimeout(final String correlationId, f
final String rawRequestUri = getRawRequestUri(request);
LOGGER.debug("Raw request URI was: {}", rawRequestUri);

final MutableKamonTimer mutableTimer = timers.get(correlationId)
timer
.tag(TracingTags.STATUS_CODE, statusCode)
.stop();

LOGGER.debug("Finished mutable timer <{}> after a request timeout with status <{}>", mutableTimer, statusCode);
LOGGER.debug("Finished mutable timer <{}> after a request timeout with status <{}>", timer, statusCode);

/* We have to add security response headers explicitly here because SecurityResponseHeadersDirective won't be
called by akka in case of a timeout */
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -101,7 +101,9 @@ private void report(String name, Gauge gauge) {
final GaugeMetric metric = Kamon.gauge(name);
final kamon.metric.Gauge g = refine(metric);
final Object value = gauge.getValue();
if (value instanceof Long) {
if (value == null) {
// Do nothing since kamon gauges just keep reporting the previously set value
} else if (value instanceof Long) {
g.set((Long) value);
} else {
LOGGER.warn(
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -16,9 +16,7 @@
import org.eclipse.ditto.signals.base.Signal;
import org.eclipse.ditto.signals.commands.base.Command;

import akka.http.javadsl.server.RequestContext;
import kamon.Kamon;
import kamon.trace.Tracer;
import akka.http.javadsl.model.HttpRequest;

/**
* Utility for tracing Http requests.
Expand All @@ -35,9 +33,9 @@ private TraceUtils() {
throw new AssertionError();
}

public static MutableKamonTimerBuilder newHttpRoundtripTimer(final RequestContext requestContext) {
final String requestMethod = requestContext.getRequest().method().name();
final String requestPath = requestContext.getRequest().getUri().toRelative().path();
public static MutableKamonTimerBuilder newHttpRoundTripTimer(final HttpRequest request) {
final String requestMethod = request.method().name();
final String requestPath = request.getUri().toRelative().path();

final TraceInformation traceInformation = determineTraceInformation(requestPath);

Expand Down Expand Up @@ -69,16 +67,6 @@ public static MutableKamonTimerBuilder newTimer(final String tracingFilter) {
return MutableKamonTimerBuilder.newTimer(metricizeTraceUri(tracingFilter));
}

public static Tracer.SpanBuilder createTrace(final RequestContext requestContext) {
final String requestMethod = requestContext.getRequest().method().name();
final String requestPath = requestContext.getRequest().getUri().toRelative().path();

final TraceInformation traceInformation = determineTraceInformation(requestPath);

return Kamon.buildSpan(metricizeTraceUri(traceInformation.getTraceUri()))
.withTag(TracingTags.REQUEST_METHOD, requestMethod);
}

public static TraceInformation determineTraceInformation(final String requestPath) {
final TraceUriGenerator traceUriGenerator = TraceUriGenerator.getInstance();
return traceUriGenerator.apply(requestPath);
Expand Down

0 comments on commit 31bab0c

Please sign in to comment.