CallableWithTracing implements Callable<U> { @Override @SuppressWarnings("deprecation") public U call() throws Exception { TracingState originalThreadInfo = null; try { originalThreadInfo = linkTracingToCurrentThread(spanStackForExecution, mdcContextMapForExecution); return origCallable.call(); } finally { unlinkTracingFromCurrentThread(originalThreadInfo); } } CallableWithTracing(Callable<U> origCallable);  CallableWithTracing(Callable<U> origCallable,
                               Pair<Deque<Span>, Map<String, String>> originalThreadInfo);  CallableWithTracing(Callable<U> origCallable,
                               Deque<Span> spanStackForExecution,
                               Map<String, String> mdcContextMapForExecution); static CallableWithTracing<U> withTracing(Callable<U> origCallable); static CallableWithTracing<U> withTracing(Callable<U> origCallable,
                                                         Pair<Deque<Span>, Map<String, String>> originalThreadInfo); static CallableWithTracing<U> withTracing(Callable<U> origCallable,
                                                         Deque<Span> spanStackForExecution,
                                                         Map<String, String> mdcContextMapForExecution); @Override @SuppressWarnings("deprecation") U call();  }
@DataProvider(value = { "true", "false" }) @Test public void call_handles_tracing_and_mdc_info_as_expected(boolean throwException) throws Exception { throwExceptionDuringCall = throwException; Tracer.getInstance().startRequestWithRootSpan("foo"); Deque<Span> spanStack = Tracer.getInstance().getCurrentSpanStackCopy(); Map<String, String> mdcInfo = MDC.getCopyOfContextMap(); final CallableWithTracing instance = new CallableWithTracing( callableMock, spanStack, mdcInfo ); resetTracing(); assertThat(Tracer.getInstance().getCurrentSpanStackCopy()).isNull(); assertThat(MDC.getCopyOfContextMap()).isNullOrEmpty(); Throwable ex = catchThrowable(new ThrowingCallable() { @Override public void call() throws Throwable { instance.call(); } }); verify(callableMock).call(); if (throwException) assertThat(ex).isNotNull(); else assertThat(ex).isNull(); assertThat(currentSpanStackWhenCallableWasCalled.get(0)).isEqualTo(spanStack); assertThat(currentMdcInfoWhenCallableWasCalled.get(0)).isEqualTo(mdcInfo); assertThat(Tracer.getInstance().getCurrentSpanStackCopy()).isNull(); assertThat(MDC.getCopyOfContextMap()).isNullOrEmpty(); }