Merge pull request #5 from DataDog/gpolaert/dev

Gpolaert/dev
This commit is contained in:
Renaud Boutet 2017-05-04 18:48:41 +02:00 committed by GitHub
commit e6b086ac4c
5 changed files with 185 additions and 13 deletions

View File

@ -0,0 +1,32 @@
/*
* Copyright (c) 2016, Uber Technologies, Inc
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
* THE SOFTWARE.
*/
package com.datadoghq.trace;
import com.datadoghq.trace.impl.DDSpanContext;
public interface Codec<T> {
void inject(DDSpanContext context, T carrier);
DDSpanContext extract(T carrier);
}

View File

@ -118,7 +118,13 @@ public class DDSpan implements io.opentracing.Span {
* @return true if root, false otherwise
*/
private boolean isRootSpan() {
return context.getTraceId() == context.getSpanId();
if (context().getTrace().isEmpty()) {
return false;
}
// First item of the array AND tracer set
DDSpan first = (DDSpan) context().getTrace().get(0);
return first.context.getSpanId() == this.context.getSpanId() && this.context.getTracer() != null;
}
/* (non-Javadoc)

View File

@ -9,14 +9,17 @@ import java.util.Map;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import com.datadoghq.trace.Codec;
import com.datadoghq.trace.Sampler;
import com.datadoghq.trace.Writer;
import com.datadoghq.trace.propagation.impl.HTTPCodec;
import com.datadoghq.trace.writer.impl.LoggingWritter;
import io.opentracing.Span;
import io.opentracing.SpanContext;
import io.opentracing.propagation.Format;
/**
* DDTracer makes it easy to send traces and span to DD using the OpenTracing instrumentation.
*/
@ -38,6 +41,7 @@ public class DDTracer implements io.opentracing.Tracer {
private final static Logger logger = LoggerFactory.getLogger(DDTracer.class);
private final CodecRegistry registry;
/**
* Default constructor, trace/spans are logged, no trace/span dropped
@ -49,9 +53,10 @@ public class DDTracer implements io.opentracing.Tracer {
public DDTracer(Writer writer, Sampler sampler) {
this.writer = writer;
this.sampler = sampler;
registry = new CodecRegistry();
registry.register(Format.Builtin.HTTP_HEADERS, new HTTPCodec());
}
/**
* Returns the list of span context decorators
*
@ -74,14 +79,25 @@ public class DDTracer implements io.opentracing.Tracer {
return new DDSpanBuilder(operationName);
}
public <C> void inject(SpanContext spanContext, Format<C> format, C c) {
//FIXME Implement it ASAP
logger.warn("Method `inject` not implemented yet");
public <T> void inject(SpanContext spanContext, Format<T> format, T carrier) {
Codec<T> codec = registry.get(format);
if (codec == null) {
logger.warn("Unsupported format for propagation - {}", format.getClass().getName());
} else {
codec.inject((DDSpanContext) spanContext, carrier);
}
}
public <C> SpanContext extract(Format<C> format, C c) {
//FIXME Implement it ASAP
logger.warn("Method `inject` not implemented yet");
public <T> SpanContext extract(Format<T> format, T carrier) {
Codec<T> codec = registry.get(format);
if (codec == null) {
logger.warn("Unsupported format for propagation - {}", format.getClass().getName());
} else {
return codec.extract(carrier);
}
return null;
}
@ -263,6 +279,20 @@ public class DDTracer implements io.opentracing.Tracer {
}
private static class CodecRegistry {
private final Map<Format<?>, Codec<?>> codecs = new HashMap<Format<?>, Codec<?>>();
<T> Codec<T> get(Format<T> format) {
return (Codec<T>) codecs.get(format);
}
public <T> void register(Format<T> format, Codec<T> codec) {
codecs.put(format, codec);
}
}
@Override
public String toString() {
return "DDTracer{" +

View File

@ -0,0 +1,104 @@
package com.datadoghq.trace.propagation.impl;
import com.datadoghq.trace.Codec;
import com.datadoghq.trace.impl.DDSpanContext;
import io.opentracing.propagation.TextMap;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.io.UnsupportedEncodingException;
import java.net.URLDecoder;
import java.net.URLEncoder;
import java.util.Collections;
import java.util.HashMap;
import java.util.Map;
public class HTTPCodec implements Codec<TextMap> {
private static final String OT_PREFIX = "ot-tracer-";
private static final String OT_BAGGAGE_PREFIX = "ot-baggage-";
private static final String TRACE_ID_KEY = OT_PREFIX + "traceid";
private static final String SPAN_ID_KEY = OT_PREFIX + "spanid";
private static final Logger logger = LoggerFactory.getLogger(HTTPCodec.class);
@Override
public void inject(DDSpanContext context, TextMap carrier) {
carrier.put(TRACE_ID_KEY, String.valueOf(context.getTraceId()));
carrier.put(SPAN_ID_KEY, String.valueOf(context.getSpanId()));
for (Map.Entry<String, String> entry : context.baggageItems()) {
carrier.put(OT_BAGGAGE_PREFIX + entry.getKey(), encode(entry.getValue()));
}
}
@Override
public DDSpanContext extract(TextMap carrier) {
Map<String, String> baggage = Collections.emptyMap();
Long traceId = 0L;
Long spanId = 0L;
for (Map.Entry<String, String> entry : carrier) {
if (entry.getKey().equals(TRACE_ID_KEY)) {
traceId = Long.parseLong(entry.getValue());
} else if (entry.getKey().equals(SPAN_ID_KEY)) {
spanId = Long.parseLong(entry.getValue());
} else if (entry.getKey().startsWith(OT_BAGGAGE_PREFIX)) {
if (baggage.isEmpty()) {
baggage = new HashMap<String, String>();
}
baggage.put(entry.getKey(), decode(entry.getValue()));
}
}
DDSpanContext context = null;
if (traceId != 0L) {
context = new DDSpanContext(
traceId,
spanId,
0L,
null,
null,
null,
baggage,
false,
null,
null,
null,
null);
logger.debug("{} - Parent context extracted", context);
}
return context;
}
private String encode(String value) {
String encoded = value;
try {
encoded = URLEncoder.encode(value, "UTF-8");
} catch (UnsupportedEncodingException e) {
logger.info("Failed to encode value - {}", value);
}
return encoded;
}
private String decode(String value) {
String decoded = value;
try {
decoded = URLDecoder.decode(value, "UTF-8");
} catch (UnsupportedEncodingException e) {
logger.info("Failed to decode value - {}", value);
}
return decoded;
}
}

View File

@ -93,7 +93,7 @@ public class DDApi {
out.write(content);
out.close();
int responseCode = httpCon.getResponseCode();
if (responseCode != 200) {
if (responseCode == 200) {
logger.debug("Sent the payload to the DD agent.");
} else {
logger.warn("Could not send the payload to the DD agent. Status: {} ResponseMessage: {}", httpCon.getResponseCode(), httpCon.getResponseMessage());