Reputation: 483
Does Spring cloud sleuth support WebserviceTemplate? I mean - I have a service which makes 2 service calls - One using RestTemplate and another using Webservicetemplate. The Rest call is getting displayed in Zipkin and the Soap call using Webservicetemplate is not. Do I have to add @NewSpan to all my soap calls ? Is it not automatically done like Resttemplate?
Upvotes: 1
Views: 1572
Reputation: 1
Here is an example of how to use spring cloud sleuth with Webservicetemplate,
if service A sends a request to service B,
At first you'll send the trace id in the header of the sent request by the below code
@Service
public class WebServiceMessageCallbackImpl implements WebServiceMessageCallback {
@Autowired
private Tracer tracer;
public void doWithMessage(WebServiceMessage webServiceMessage) throws TransformerException {
Span span = tracer.currentSpan();
String traceId = span.context().traceId();
SoapMessage soapMessage = (SoapMessage) webServiceMessage;
SoapHeader header = soapMessage.getSoapHeader();
StringSource headerSource = new StringSource("<traceId>" + traceId + "</traceId>");
Transformer transformer = TransformerFactory.newInstance().newTransformer();
transformer.transform(headerSource, header.getResult());
}
}
then in service B, you'll create an interceptor, then read the trace id from the header of the coming request, then put this trace id in the MDC like in the below code
@Slf4j
@Component
public class HttpInterceptor2 extends OncePerRequestFilter {
private final String traceId = "traceId";
@Autowired
private Tracer tracer;
@Override
protected void doFilterInternal(HttpServletRequest request, HttpServletResponse response, FilterChain chain)
throws ServletException, IOException {
String payload = new String(request.getInputStream().readAllBytes(), StandardCharsets.UTF_8);
String traceId = traceId(payload);
MDC.put("traceId", traceId);
try {
chain.doFilter(request, response);
} finally {
MDC.remove(traceId);
}
}
private String traceId(String payload) {
StringBuilder token = new StringBuilder();
if (payload.contains(traceId)) {
int index = payload.indexOf(traceId);
while (index < payload.length() && payload.charAt(index) != '>') {
index++;
}
index++;
for (int i = index; ; i++) {
if (payload.charAt(i) == '<') {
break;
}
token.append(payload.charAt(i));
}
}
if (token.toString().trim().isEmpty()) {
token.append(traceId());
}
return token.toString().trim();
}
private String traceId() {
Span span = tracer.currentSpan();
String traceId = span.context().traceId();
return traceId;
}
}
Upvotes: 0
Reputation: 11149
No - we haven't added any instrumentation around Webservicetemplate. You'd have to add an interceptor similar to the one we add for RestTemplate. You'd have to pass all the tracing headers to the request so that the other side can properly parse it.
Upvotes: 2