Remove Timestamp and change start/end times to use epoch nanos (#646)
Signed-off-by: Bogdan Drutu <bogdandrutu@gmail.com>
This commit is contained in:
parent
618e656e5f
commit
ce1cd9c3bd
|
|
@ -18,7 +18,6 @@ package io.opentelemetry.exporters.inmemory;
|
||||||
|
|
||||||
import static com.google.common.truth.Truth.assertThat;
|
import static com.google.common.truth.Truth.assertThat;
|
||||||
|
|
||||||
import io.opentelemetry.sdk.common.Timestamp;
|
|
||||||
import io.opentelemetry.sdk.trace.SpanData;
|
import io.opentelemetry.sdk.trace.SpanData;
|
||||||
import io.opentelemetry.sdk.trace.TracerSdk;
|
import io.opentelemetry.sdk.trace.TracerSdk;
|
||||||
import io.opentelemetry.sdk.trace.export.SimpleSpansProcessor;
|
import io.opentelemetry.sdk.trace.export.SimpleSpansProcessor;
|
||||||
|
|
@ -104,9 +103,9 @@ public class InMemorySpanExporterTest {
|
||||||
.setSpanId(io.opentelemetry.trace.SpanId.getInvalid())
|
.setSpanId(io.opentelemetry.trace.SpanId.getInvalid())
|
||||||
.setName("span")
|
.setName("span")
|
||||||
.setKind(io.opentelemetry.trace.Span.Kind.SERVER)
|
.setKind(io.opentelemetry.trace.Span.Kind.SERVER)
|
||||||
.setStartTimestamp(Timestamp.create(100, 100))
|
.setStartEpochNanos(100_000_000_100L)
|
||||||
.setStatus(io.opentelemetry.trace.Status.OK)
|
.setStatus(io.opentelemetry.trace.Status.OK)
|
||||||
.setEndTimestamp(Timestamp.create(200, 200))
|
.setEndEpochNanos(200_000_000_200L)
|
||||||
.build();
|
.build();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -69,11 +69,10 @@ final class Adapter {
|
||||||
target.setTraceId(TraceProtoUtils.toProtoTraceId(span.getTraceId()));
|
target.setTraceId(TraceProtoUtils.toProtoTraceId(span.getTraceId()));
|
||||||
target.setSpanId(TraceProtoUtils.toProtoSpanId(span.getSpanId()));
|
target.setSpanId(TraceProtoUtils.toProtoSpanId(span.getSpanId()));
|
||||||
target.setOperationName(span.getName());
|
target.setOperationName(span.getName());
|
||||||
Timestamp startTimestamp = TraceProtoUtils.toProtoTimestamp(span.getStartTimestamp());
|
Timestamp startTimestamp = Timestamps.fromNanos(span.getStartEpochNanos());
|
||||||
target.setStartTime(startTimestamp);
|
target.setStartTime(startTimestamp);
|
||||||
target.setDuration(
|
target.setDuration(
|
||||||
Timestamps.between(
|
Timestamps.between(startTimestamp, Timestamps.fromNanos(span.getEndEpochNanos())));
|
||||||
startTimestamp, TraceProtoUtils.toProtoTimestamp(span.getEndTimestamp())));
|
|
||||||
|
|
||||||
target.addAllTags(toKeyValues(span.getAttributes()));
|
target.addAllTags(toKeyValues(span.getAttributes()));
|
||||||
target.addAllLogs(toJaegerLogs(span.getTimedEvents()));
|
target.addAllLogs(toJaegerLogs(span.getTimedEvents()));
|
||||||
|
|
|
||||||
|
|
@ -22,9 +22,9 @@ import static org.junit.Assert.assertTrue;
|
||||||
|
|
||||||
import com.google.common.collect.ImmutableMap;
|
import com.google.common.collect.ImmutableMap;
|
||||||
import com.google.protobuf.util.Durations;
|
import com.google.protobuf.util.Durations;
|
||||||
|
import com.google.protobuf.util.Timestamps;
|
||||||
import io.opentelemetry.exporters.jaeger.proto.api_v2.Model;
|
import io.opentelemetry.exporters.jaeger.proto.api_v2.Model;
|
||||||
import io.opentelemetry.exporters.otprotocol.TraceProtoUtils;
|
import io.opentelemetry.exporters.otprotocol.TraceProtoUtils;
|
||||||
import io.opentelemetry.sdk.common.Timestamp;
|
|
||||||
import io.opentelemetry.sdk.resources.Resource;
|
import io.opentelemetry.sdk.resources.Resource;
|
||||||
import io.opentelemetry.sdk.trace.SpanData;
|
import io.opentelemetry.sdk.trace.SpanData;
|
||||||
import io.opentelemetry.sdk.trace.SpanData.TimedEvent;
|
import io.opentelemetry.sdk.trace.SpanData.TimedEvent;
|
||||||
|
|
@ -58,10 +58,8 @@ public class AdapterTest {
|
||||||
long duration = 900; // ms
|
long duration = 900; // ms
|
||||||
long startMs = System.currentTimeMillis();
|
long startMs = System.currentTimeMillis();
|
||||||
long endMs = startMs + duration;
|
long endMs = startMs + duration;
|
||||||
Timestamp startTime = toTimestamp(startMs);
|
|
||||||
Timestamp endTime = toTimestamp(endMs);
|
|
||||||
|
|
||||||
SpanData span = getSpanData(startTime, endTime);
|
SpanData span = getSpanData(startMs, endMs);
|
||||||
List<SpanData> spans = Collections.singletonList(span);
|
List<SpanData> spans = Collections.singletonList(span);
|
||||||
|
|
||||||
Collection<Model.Span> jaegerSpans = Adapter.toJaeger(spans);
|
Collection<Model.Span> jaegerSpans = Adapter.toJaeger(spans);
|
||||||
|
|
@ -75,22 +73,15 @@ public class AdapterTest {
|
||||||
long duration = 900; // ms
|
long duration = 900; // ms
|
||||||
long startMs = System.currentTimeMillis();
|
long startMs = System.currentTimeMillis();
|
||||||
long endMs = startMs + duration;
|
long endMs = startMs + duration;
|
||||||
Timestamp startTime = toTimestamp(startMs);
|
|
||||||
Timestamp endTime = toTimestamp(endMs);
|
|
||||||
|
|
||||||
SpanData span = getSpanData(startTime, endTime);
|
SpanData span = getSpanData(startMs, endMs);
|
||||||
|
|
||||||
// test
|
// test
|
||||||
Model.Span jaegerSpan = Adapter.toJaeger(span);
|
Model.Span jaegerSpan = Adapter.toJaeger(span);
|
||||||
assertEquals(TraceProtoUtils.toProtoTraceId(span.getTraceId()), jaegerSpan.getTraceId());
|
assertEquals(TraceProtoUtils.toProtoTraceId(span.getTraceId()), jaegerSpan.getTraceId());
|
||||||
assertEquals(TraceProtoUtils.toProtoSpanId(span.getSpanId()), jaegerSpan.getSpanId());
|
assertEquals(TraceProtoUtils.toProtoSpanId(span.getSpanId()), jaegerSpan.getSpanId());
|
||||||
assertEquals("GET /api/endpoint", jaegerSpan.getOperationName());
|
assertEquals("GET /api/endpoint", jaegerSpan.getOperationName());
|
||||||
assertEquals(
|
assertEquals(Timestamps.fromMillis(startMs), jaegerSpan.getStartTime());
|
||||||
com.google.protobuf.Timestamp.newBuilder()
|
|
||||||
.setSeconds(startTime.getSeconds())
|
|
||||||
.setNanos(startTime.getNanos())
|
|
||||||
.build(),
|
|
||||||
jaegerSpan.getStartTime());
|
|
||||||
assertEquals(duration, Durations.toMillis(jaegerSpan.getDuration()));
|
assertEquals(duration, Durations.toMillis(jaegerSpan.getDuration()));
|
||||||
|
|
||||||
assertEquals(4, jaegerSpan.getTagsCount());
|
assertEquals(4, jaegerSpan.getTagsCount());
|
||||||
|
|
@ -223,7 +214,7 @@ public class AdapterTest {
|
||||||
return TimedEvent.create(epochNanos, "the log message", attributes);
|
return TimedEvent.create(epochNanos, "the log message", attributes);
|
||||||
}
|
}
|
||||||
|
|
||||||
private static SpanData getSpanData(Timestamp startTime, Timestamp endTime) {
|
private static SpanData getSpanData(long startMs, long endMs) {
|
||||||
AttributeValue valueB = AttributeValue.booleanAttributeValue(true);
|
AttributeValue valueB = AttributeValue.booleanAttributeValue(true);
|
||||||
Map<String, AttributeValue> attributes = ImmutableMap.of("valueB", valueB);
|
Map<String, AttributeValue> attributes = ImmutableMap.of("valueB", valueB);
|
||||||
|
|
||||||
|
|
@ -234,8 +225,8 @@ public class AdapterTest {
|
||||||
.setSpanId(SpanId.fromLowerBase16(SPAN_ID, 0))
|
.setSpanId(SpanId.fromLowerBase16(SPAN_ID, 0))
|
||||||
.setParentSpanId(SpanId.fromLowerBase16(PARENT_SPAN_ID, 0))
|
.setParentSpanId(SpanId.fromLowerBase16(PARENT_SPAN_ID, 0))
|
||||||
.setName("GET /api/endpoint")
|
.setName("GET /api/endpoint")
|
||||||
.setStartTimestamp(startTime)
|
.setStartEpochNanos(TimeUnit.MILLISECONDS.toNanos(startMs))
|
||||||
.setEndTimestamp(endTime)
|
.setEndEpochNanos(TimeUnit.MILLISECONDS.toNanos(endMs))
|
||||||
.setAttributes(attributes)
|
.setAttributes(attributes)
|
||||||
.setTimedEvents(Collections.singletonList(getTimedEvent()))
|
.setTimedEvents(Collections.singletonList(getTimedEvent()))
|
||||||
.setLinks(Collections.singletonList(link))
|
.setLinks(Collections.singletonList(link))
|
||||||
|
|
@ -253,10 +244,6 @@ public class AdapterTest {
|
||||||
Tracestate.builder().build());
|
Tracestate.builder().build());
|
||||||
}
|
}
|
||||||
|
|
||||||
private static Timestamp toTimestamp(long ms) {
|
|
||||||
return Timestamp.create(ms / 1000, (int) ((ms % 1000) * 1000000));
|
|
||||||
}
|
|
||||||
|
|
||||||
@Nullable
|
@Nullable
|
||||||
private static Model.KeyValue getValue(List<Model.KeyValue> tagsList, String s) {
|
private static Model.KeyValue getValue(List<Model.KeyValue> tagsList, String s) {
|
||||||
for (Model.KeyValue kv : tagsList) {
|
for (Model.KeyValue kv : tagsList) {
|
||||||
|
|
|
||||||
|
|
@ -33,7 +33,6 @@ import io.opentelemetry.exporters.jaeger.proto.api_v2.Collector.PostSpansRequest
|
||||||
import io.opentelemetry.exporters.jaeger.proto.api_v2.CollectorServiceGrpc;
|
import io.opentelemetry.exporters.jaeger.proto.api_v2.CollectorServiceGrpc;
|
||||||
import io.opentelemetry.exporters.jaeger.proto.api_v2.Model;
|
import io.opentelemetry.exporters.jaeger.proto.api_v2.Model;
|
||||||
import io.opentelemetry.exporters.otprotocol.TraceProtoUtils;
|
import io.opentelemetry.exporters.otprotocol.TraceProtoUtils;
|
||||||
import io.opentelemetry.sdk.common.Timestamp;
|
|
||||||
import io.opentelemetry.sdk.trace.SpanData;
|
import io.opentelemetry.sdk.trace.SpanData;
|
||||||
import io.opentelemetry.trace.Link;
|
import io.opentelemetry.trace.Link;
|
||||||
import io.opentelemetry.trace.Span.Kind;
|
import io.opentelemetry.trace.Span.Kind;
|
||||||
|
|
@ -42,6 +41,7 @@ import io.opentelemetry.trace.Status;
|
||||||
import io.opentelemetry.trace.TraceId;
|
import io.opentelemetry.trace.TraceId;
|
||||||
import java.net.InetAddress;
|
import java.net.InetAddress;
|
||||||
import java.util.Collections;
|
import java.util.Collections;
|
||||||
|
import java.util.concurrent.TimeUnit;
|
||||||
import org.junit.Rule;
|
import org.junit.Rule;
|
||||||
import org.junit.Test;
|
import org.junit.Test;
|
||||||
import org.mockito.ArgumentCaptor;
|
import org.mockito.ArgumentCaptor;
|
||||||
|
|
@ -77,15 +77,13 @@ public class JaegerGrpcSpanExporterTest {
|
||||||
long duration = 900; // ms
|
long duration = 900; // ms
|
||||||
long startMs = System.currentTimeMillis();
|
long startMs = System.currentTimeMillis();
|
||||||
long endMs = startMs + duration;
|
long endMs = startMs + duration;
|
||||||
Timestamp startTime = Timestamp.create(startMs / 1000, (int) ((startMs % 1000) * 1000000));
|
|
||||||
Timestamp endTime = Timestamp.create(endMs / 1000, (int) ((endMs % 1000) * 1000000));
|
|
||||||
SpanData span =
|
SpanData span =
|
||||||
SpanData.newBuilder()
|
SpanData.newBuilder()
|
||||||
.setTraceId(TraceId.fromLowerBase16(TRACE_ID, 0))
|
.setTraceId(TraceId.fromLowerBase16(TRACE_ID, 0))
|
||||||
.setSpanId(SpanId.fromLowerBase16(SPAN_ID, 0))
|
.setSpanId(SpanId.fromLowerBase16(SPAN_ID, 0))
|
||||||
.setName("GET /api/endpoint")
|
.setName("GET /api/endpoint")
|
||||||
.setStartTimestamp(startTime)
|
.setStartEpochNanos(TimeUnit.MILLISECONDS.toNanos(startMs))
|
||||||
.setEndTimestamp(endTime)
|
.setEndEpochNanos(TimeUnit.MILLISECONDS.toNanos(endMs))
|
||||||
.setStatus(Status.OK)
|
.setStatus(Status.OK)
|
||||||
.setKind(Kind.CONSUMER)
|
.setKind(Kind.CONSUMER)
|
||||||
.setLinks(Collections.<Link>emptyList())
|
.setLinks(Collections.<Link>emptyList())
|
||||||
|
|
|
||||||
|
|
@ -20,7 +20,6 @@ import static java.util.Collections.singletonList;
|
||||||
import static java.util.Collections.singletonMap;
|
import static java.util.Collections.singletonMap;
|
||||||
import static org.junit.Assert.assertEquals;
|
import static org.junit.Assert.assertEquals;
|
||||||
|
|
||||||
import io.opentelemetry.sdk.common.Timestamp;
|
|
||||||
import io.opentelemetry.sdk.trace.SpanData;
|
import io.opentelemetry.sdk.trace.SpanData;
|
||||||
import io.opentelemetry.sdk.trace.export.SpanExporter.ResultCode;
|
import io.opentelemetry.sdk.trace.export.SpanExporter.ResultCode;
|
||||||
import io.opentelemetry.trace.AttributeValue;
|
import io.opentelemetry.trace.AttributeValue;
|
||||||
|
|
@ -40,8 +39,8 @@ public class LoggingExporterTest {
|
||||||
SpanData.newBuilder()
|
SpanData.newBuilder()
|
||||||
.setTraceId(new TraceId(1234L, 6789L))
|
.setTraceId(new TraceId(1234L, 6789L))
|
||||||
.setSpanId(new SpanId(9876L))
|
.setSpanId(new SpanId(9876L))
|
||||||
.setStartTimestamp(Timestamp.fromNanos(epochNanos))
|
.setStartEpochNanos(epochNanos)
|
||||||
.setEndTimestamp(Timestamp.fromNanos(epochNanos + 1000))
|
.setEndEpochNanos(epochNanos + 1000)
|
||||||
.setStatus(Status.OK)
|
.setStatus(Status.OK)
|
||||||
.setName("testSpan")
|
.setName("testSpan")
|
||||||
.setKind(Kind.INTERNAL)
|
.setKind(Kind.INTERNAL)
|
||||||
|
|
|
||||||
|
|
@ -17,7 +17,6 @@
|
||||||
package io.opentelemetry.exporters.otprotocol;
|
package io.opentelemetry.exporters.otprotocol;
|
||||||
|
|
||||||
import com.google.protobuf.ByteString;
|
import com.google.protobuf.ByteString;
|
||||||
import com.google.protobuf.Timestamp;
|
|
||||||
import io.opentelemetry.proto.trace.v1.ConstantSampler;
|
import io.opentelemetry.proto.trace.v1.ConstantSampler;
|
||||||
import io.opentelemetry.sdk.trace.Sampler;
|
import io.opentelemetry.sdk.trace.Sampler;
|
||||||
import io.opentelemetry.sdk.trace.Samplers;
|
import io.opentelemetry.sdk.trace.Samplers;
|
||||||
|
|
@ -53,19 +52,6 @@ public class TraceProtoUtils {
|
||||||
return ByteString.copyFrom(traceIdBytes);
|
return ByteString.copyFrom(traceIdBytes);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* Converts a opentelemetry Timestamp into a protobuf Timestamp.
|
|
||||||
*
|
|
||||||
* @param timestamp the opentelemetry Timestamp to convert.
|
|
||||||
* @return the protobuf Timestamp representation.
|
|
||||||
*/
|
|
||||||
public static Timestamp toProtoTimestamp(io.opentelemetry.sdk.common.Timestamp timestamp) {
|
|
||||||
return Timestamp.newBuilder()
|
|
||||||
.setNanos(timestamp.getNanos())
|
|
||||||
.setSeconds(timestamp.getSeconds())
|
|
||||||
.build();
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns a {@code TraceConfig} from the given proto.
|
* Returns a {@code TraceConfig} from the given proto.
|
||||||
*
|
*
|
||||||
|
|
|
||||||
|
|
@ -21,7 +21,6 @@ import static org.junit.Assert.assertTrue;
|
||||||
|
|
||||||
import io.opentelemetry.exporters.inmemory.InMemorySpanExporter;
|
import io.opentelemetry.exporters.inmemory.InMemorySpanExporter;
|
||||||
import io.opentelemetry.opentracingshim.TraceShim;
|
import io.opentelemetry.opentracingshim.TraceShim;
|
||||||
import io.opentelemetry.sdk.common.Timestamp;
|
|
||||||
import io.opentelemetry.sdk.distributedcontext.DistributedContextManagerSdk;
|
import io.opentelemetry.sdk.distributedcontext.DistributedContextManagerSdk;
|
||||||
import io.opentelemetry.sdk.trace.SpanData;
|
import io.opentelemetry.sdk.trace.SpanData;
|
||||||
import io.opentelemetry.sdk.trace.TracerSdk;
|
import io.opentelemetry.sdk.trace.TracerSdk;
|
||||||
|
|
@ -195,7 +194,7 @@ public final class TestUtils {
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Sorts the specified {@code List} of {@code Span} by their {@code Span.Timestamp} values,
|
* Sorts the specified {@code List} of {@code Span} by their start epoch timestamp values,
|
||||||
* returning it as a new {@code List}.
|
* returning it as a new {@code List}.
|
||||||
*/
|
*/
|
||||||
public static List<SpanData> sortByStartTime(List<SpanData> spans) {
|
public static List<SpanData> sortByStartTime(List<SpanData> spans) {
|
||||||
|
|
@ -205,7 +204,7 @@ public final class TestUtils {
|
||||||
new Comparator<SpanData>() {
|
new Comparator<SpanData>() {
|
||||||
@Override
|
@Override
|
||||||
public int compare(SpanData o1, SpanData o2) {
|
public int compare(SpanData o1, SpanData o2) {
|
||||||
return compareTimestamps(o1.getStartTimestamp(), o2.getStartTimestamp());
|
return Long.compare(o1.getStartEpochNanos(), o2.getStartEpochNanos());
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
return sortedSpans;
|
return sortedSpans;
|
||||||
|
|
@ -215,25 +214,9 @@ public final class TestUtils {
|
||||||
public static void assertSameTrace(List<SpanData> spans) {
|
public static void assertSameTrace(List<SpanData> spans) {
|
||||||
for (int i = 0; i < spans.size() - 1; i++) {
|
for (int i = 0; i < spans.size() - 1; i++) {
|
||||||
// TODO - Include nanos in this comparison.
|
// TODO - Include nanos in this comparison.
|
||||||
assertTrue(
|
assertTrue(spans.get(spans.size() - 1).getEndEpochNanos() >= spans.get(i).getEndEpochNanos());
|
||||||
spans.get(spans.size() - 1).getEndTimestamp().getSeconds()
|
|
||||||
>= spans.get(i).getEndTimestamp().getSeconds());
|
|
||||||
assertEquals(spans.get(spans.size() - 1).getTraceId(), spans.get(i).getTraceId());
|
assertEquals(spans.get(spans.size() - 1).getTraceId(), spans.get(i).getTraceId());
|
||||||
assertEquals(spans.get(spans.size() - 1).getSpanId(), spans.get(i).getParentSpanId());
|
assertEquals(spans.get(spans.size() - 1).getSpanId(), spans.get(i).getParentSpanId());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// TODO: this comparator code is duplicated in another TestUtils class. find a common home for it.
|
|
||||||
private static final Comparator<Timestamp> COMPARATOR =
|
|
||||||
new Comparator<Timestamp>() {
|
|
||||||
@Override
|
|
||||||
public int compare(Timestamp t1, Timestamp t2) {
|
|
||||||
int secDiff = Long.compare(t1.getSeconds(), t2.getSeconds());
|
|
||||||
return (secDiff != 0) ? secDiff : Integer.compare(t1.getNanos(), t2.getNanos());
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
public static int compareTimestamps(Timestamp x, Timestamp y) {
|
|
||||||
return COMPARATOR.compare(x, y);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -1,130 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright 2019, OpenTelemetry Authors
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
|
|
||||||
package io.opentelemetry.sdk.common;
|
|
||||||
|
|
||||||
import com.google.auto.value.AutoValue;
|
|
||||||
import java.math.BigDecimal;
|
|
||||||
import java.math.RoundingMode;
|
|
||||||
import javax.annotation.concurrent.Immutable;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* A representation of an instant in time. The instant is the number of nanoseconds after the number
|
|
||||||
* of seconds since the Unix Epoch.
|
|
||||||
*
|
|
||||||
* <p>Defined here instead of using {@code Instant} because the API needs to be Java 1.7 compatible.
|
|
||||||
*
|
|
||||||
* @since 0.1.0
|
|
||||||
*/
|
|
||||||
@Immutable
|
|
||||||
@AutoValue
|
|
||||||
public abstract class Timestamp {
|
|
||||||
private static final long MAX_SECONDS = 315576000000L;
|
|
||||||
private static final int MAX_NANOS = 999999999;
|
|
||||||
private static final long MILLIS_PER_SECOND = 1000L;
|
|
||||||
private static final long NANOS_PER_SECOND = 1000L * 1000L * 1000L;
|
|
||||||
private static final long NANOS_PER_MILLI = 1000L * 1000L;
|
|
||||||
|
|
||||||
Timestamp() {}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Creates a new timestamp from given seconds and nanoseconds.
|
|
||||||
*
|
|
||||||
* @param seconds Represents seconds of UTC time since Unix epoch 1970-01-01T00:00:00Z. Must be
|
|
||||||
* from from 0001-01-01T00:00:00Z to 9999-12-31T23:59:59Z inclusive.
|
|
||||||
* @param nanos Non-negative fractions of a second at nanosecond resolution. Negative second
|
|
||||||
* values with fractions must still have non-negative nanos values that count forward in time.
|
|
||||||
* Must be from 0 to 999,999,999 inclusive.
|
|
||||||
* @return new {@code Timestamp} with specified fields.
|
|
||||||
* @throws IllegalArgumentException if the arguments are out of range.
|
|
||||||
* @since 0.1.0
|
|
||||||
*/
|
|
||||||
public static Timestamp create(long seconds, int nanos) {
|
|
||||||
if (seconds < -MAX_SECONDS) {
|
|
||||||
throw new IllegalArgumentException(
|
|
||||||
"'seconds' is less than minimum (" + -MAX_SECONDS + "): " + seconds);
|
|
||||||
}
|
|
||||||
if (seconds > MAX_SECONDS) {
|
|
||||||
throw new IllegalArgumentException(
|
|
||||||
"'seconds' is greater than maximum (" + MAX_SECONDS + "): " + seconds);
|
|
||||||
}
|
|
||||||
if (nanos < 0) {
|
|
||||||
throw new IllegalArgumentException("'nanos' is less than zero: " + nanos);
|
|
||||||
}
|
|
||||||
if (nanos > MAX_NANOS) {
|
|
||||||
throw new IllegalArgumentException(
|
|
||||||
"'nanos' is greater than maximum (" + MAX_NANOS + "): " + nanos);
|
|
||||||
}
|
|
||||||
return new AutoValue_Timestamp(seconds, nanos);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Creates a new timestamp from the given milliseconds.
|
|
||||||
*
|
|
||||||
* @param epochMilli the timestamp represented in milliseconds since epoch.
|
|
||||||
* @return new {@code Timestamp} with specified fields.
|
|
||||||
* @throws IllegalArgumentException if the number of milliseconds is out of the range that can be
|
|
||||||
* represented by {@code Timestamp}.
|
|
||||||
* @since 0.1.0
|
|
||||||
*/
|
|
||||||
public static Timestamp fromMillis(long epochMilli) {
|
|
||||||
long secs = floorDiv(epochMilli, MILLIS_PER_SECOND);
|
|
||||||
int mos = (int) floorMod(epochMilli, MILLIS_PER_SECOND);
|
|
||||||
return create(secs, (int) (mos * NANOS_PER_MILLI)); // Safe int * NANOS_PER_MILLI
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Creates a new timestamp from the given milliseconds.
|
|
||||||
*
|
|
||||||
* @param epochNanos the timestamp represented in nanoseconds since epoch.
|
|
||||||
* @return new {@code Timestamp} with specified fields.
|
|
||||||
* @throws IllegalArgumentException if the number of milliseconds is out of the range that can be
|
|
||||||
* represented by {@code Timestamp}.
|
|
||||||
* @since 0.1.0
|
|
||||||
*/
|
|
||||||
public static Timestamp fromNanos(long epochNanos) {
|
|
||||||
long secs = floorDiv(epochNanos, NANOS_PER_SECOND);
|
|
||||||
int nanos = (int) floorMod(epochNanos, NANOS_PER_SECOND);
|
|
||||||
return create(secs, nanos); // Safe int * NANOS_PER_MILLI
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Returns the number of seconds since the Unix Epoch represented by this timestamp.
|
|
||||||
*
|
|
||||||
* @return the number of seconds since the Unix Epoch.
|
|
||||||
* @since 0.1.0
|
|
||||||
*/
|
|
||||||
public abstract long getSeconds();
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Returns the number of nanoseconds after the number of seconds since the Unix Epoch represented
|
|
||||||
* by this timestamp.
|
|
||||||
*
|
|
||||||
* @return the number of nanoseconds after the number of seconds since the Unix Epoch.
|
|
||||||
* @since 0.1.0
|
|
||||||
*/
|
|
||||||
public abstract int getNanos();
|
|
||||||
|
|
||||||
// Returns the result of dividing x by y rounded using floor.
|
|
||||||
private static long floorDiv(long x, long y) {
|
|
||||||
return BigDecimal.valueOf(x).divide(BigDecimal.valueOf(y), 0, RoundingMode.FLOOR).longValue();
|
|
||||||
}
|
|
||||||
|
|
||||||
// Returns the floor modulus "x - (floorDiv(x, y) * y)"
|
|
||||||
private static long floorMod(long x, long y) {
|
|
||||||
return x - floorDiv(x, y) * y;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
@ -23,7 +23,7 @@ import javax.annotation.concurrent.Immutable;
|
||||||
* This class provides a mechanism for calculating the epoch time using {@link System#nanoTime()}
|
* This class provides a mechanism for calculating the epoch time using {@link System#nanoTime()}
|
||||||
* and a reference epoch timestamp.
|
* and a reference epoch timestamp.
|
||||||
*
|
*
|
||||||
* <p>This is needed because Java has millisecond granularity for Timestamp and tracing events are
|
* <p>This is needed because Java has millisecond granularity for epoch times and tracing events are
|
||||||
* recorded more often.
|
* recorded more often.
|
||||||
*
|
*
|
||||||
* <p>This clock needs to be re-created periodically in order to re-sync with the kernel clock, and
|
* <p>This clock needs to be re-created periodically in order to re-sync with the kernel clock, and
|
||||||
|
|
|
||||||
|
|
@ -20,7 +20,6 @@ import com.google.common.annotations.VisibleForTesting;
|
||||||
import com.google.common.base.Preconditions;
|
import com.google.common.base.Preconditions;
|
||||||
import com.google.common.collect.EvictingQueue;
|
import com.google.common.collect.EvictingQueue;
|
||||||
import io.opentelemetry.sdk.common.Clock;
|
import io.opentelemetry.sdk.common.Clock;
|
||||||
import io.opentelemetry.sdk.common.Timestamp;
|
|
||||||
import io.opentelemetry.sdk.resources.Resource;
|
import io.opentelemetry.sdk.resources.Resource;
|
||||||
import io.opentelemetry.sdk.trace.config.TraceConfig;
|
import io.opentelemetry.sdk.trace.config.TraceConfig;
|
||||||
import io.opentelemetry.trace.AttributeValue;
|
import io.opentelemetry.trace.AttributeValue;
|
||||||
|
|
@ -149,8 +148,6 @@ final class RecordEventsReadableSpan implements ReadableSpan, Span {
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public SpanData toSpanData() {
|
public SpanData toSpanData() {
|
||||||
Timestamp startTimestamp = Timestamp.fromNanos(startEpochNanos);
|
|
||||||
Timestamp endTimestamp = Timestamp.fromNanos(getEndEpochNanos());
|
|
||||||
SpanContext spanContext = getSpanContext();
|
SpanContext spanContext = getSpanContext();
|
||||||
return SpanData.newBuilder()
|
return SpanData.newBuilder()
|
||||||
.setName(getName())
|
.setName(getName())
|
||||||
|
|
@ -159,8 +156,8 @@ final class RecordEventsReadableSpan implements ReadableSpan, Span {
|
||||||
.setTraceFlags(spanContext.getTraceFlags())
|
.setTraceFlags(spanContext.getTraceFlags())
|
||||||
.setTracestate(spanContext.getTracestate())
|
.setTracestate(spanContext.getTracestate())
|
||||||
.setAttributes(getAttributes())
|
.setAttributes(getAttributes())
|
||||||
.setStartTimestamp(startTimestamp)
|
.setStartEpochNanos(startEpochNanos)
|
||||||
.setEndTimestamp(endTimestamp)
|
.setEndEpochNanos(getEndEpochNanos())
|
||||||
.setKind(kind)
|
.setKind(kind)
|
||||||
.setLinks(getLinks())
|
.setLinks(getLinks())
|
||||||
.setParentSpanId(parentSpanId)
|
.setParentSpanId(parentSpanId)
|
||||||
|
|
|
||||||
|
|
@ -17,7 +17,6 @@
|
||||||
package io.opentelemetry.sdk.trace;
|
package io.opentelemetry.sdk.trace;
|
||||||
|
|
||||||
import com.google.auto.value.AutoValue;
|
import com.google.auto.value.AutoValue;
|
||||||
import io.opentelemetry.sdk.common.Timestamp;
|
|
||||||
import io.opentelemetry.sdk.resources.Resource;
|
import io.opentelemetry.sdk.resources.Resource;
|
||||||
import io.opentelemetry.trace.AttributeValue;
|
import io.opentelemetry.trace.AttributeValue;
|
||||||
import io.opentelemetry.trace.Event;
|
import io.opentelemetry.trace.Event;
|
||||||
|
|
@ -107,12 +106,12 @@ public abstract class SpanData {
|
||||||
public abstract Kind getKind();
|
public abstract Kind getKind();
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns the start {@code Timestamp} of this {@code Span}.
|
* Returns the start epoch timestamp in nanos of this {@code Span}.
|
||||||
*
|
*
|
||||||
* @return the start {@code Timestamp} of this {@code Span}.
|
* @return the start epoch timestamp in nanos of this {@code Span}.
|
||||||
* @since 0.1.0
|
* @since 0.1.0
|
||||||
*/
|
*/
|
||||||
public abstract Timestamp getStartTimestamp();
|
public abstract long getStartEpochNanos();
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns the attributes recorded for this {@code Span}.
|
* Returns the attributes recorded for this {@code Span}.
|
||||||
|
|
@ -147,12 +146,12 @@ public abstract class SpanData {
|
||||||
public abstract Status getStatus();
|
public abstract Status getStatus();
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns the end {@code Timestamp}.
|
* Returns the end epoch timestamp in nanos of this {@code Span}.
|
||||||
*
|
*
|
||||||
* @return the end {@code Timestamp}.
|
* @return the end epoch timestamp in nanos of this {@code Span}.
|
||||||
* @since 0.1.0
|
* @since 0.1.0
|
||||||
*/
|
*/
|
||||||
public abstract Timestamp getEndTimestamp();
|
public abstract long getEndEpochNanos();
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* An immutable implementation of {@link Link}.
|
* An immutable implementation of {@link Link}.
|
||||||
|
|
@ -211,9 +210,9 @@ public abstract class SpanData {
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns the {@code Timestamp} of this event.
|
* Returns the epoch time in nanos of this event.
|
||||||
*
|
*
|
||||||
* @return the {@code Timestamp} of this event.
|
* @return the epoch time in nanos of this event.
|
||||||
* @since 0.1.0
|
* @since 0.1.0
|
||||||
*/
|
*/
|
||||||
public abstract long getEpochNanos();
|
public abstract long getEpochNanos();
|
||||||
|
|
@ -336,24 +335,22 @@ public abstract class SpanData {
|
||||||
public abstract Builder setName(String name);
|
public abstract Builder setName(String name);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Set the start timestamp of the span. Must not be null.
|
* Set the start timestamp of the span.
|
||||||
*
|
*
|
||||||
* @param timestamp the start Timestamp
|
* @param epochNanos the start epoch timestamp in nanos.
|
||||||
* @return this
|
* @return this
|
||||||
* @see Timestamp
|
|
||||||
* @since 0.1.0
|
* @since 0.1.0
|
||||||
*/
|
*/
|
||||||
public abstract Builder setStartTimestamp(Timestamp timestamp);
|
public abstract Builder setStartEpochNanos(long epochNanos);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Set the end timestamp of the span. Must not be null.
|
* Set the end timestamp of the span.
|
||||||
*
|
*
|
||||||
* @param timestamp the end Timestamp
|
* @param epochNanos the end epoch timestamp in nanos.
|
||||||
* @return this
|
* @return this
|
||||||
* @see Timestamp
|
|
||||||
* @since 0.1.0
|
* @since 0.1.0
|
||||||
*/
|
*/
|
||||||
public abstract Builder setEndTimestamp(Timestamp timestamp);
|
public abstract Builder setEndEpochNanos(long epochNanos);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Set the attributes that are associated with this span, as a Map of String keys to
|
* Set the attributes that are associated with this span, as a Map of String keys to
|
||||||
|
|
|
||||||
|
|
@ -23,7 +23,7 @@ import java.util.Collections;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
import javax.annotation.concurrent.Immutable;
|
import javax.annotation.concurrent.Immutable;
|
||||||
|
|
||||||
/** Timed event that uses nanoTime to represent the Timestamp. */
|
/** Timed event. */
|
||||||
@Immutable
|
@Immutable
|
||||||
abstract class TimedEvent {
|
abstract class TimedEvent {
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -1,126 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright 2019, OpenTelemetry Authors
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
|
|
||||||
package io.opentelemetry.sdk.common;
|
|
||||||
|
|
||||||
import static com.google.common.truth.Truth.assertThat;
|
|
||||||
|
|
||||||
import org.junit.Rule;
|
|
||||||
import org.junit.Test;
|
|
||||||
import org.junit.rules.ExpectedException;
|
|
||||||
import org.junit.runner.RunWith;
|
|
||||||
import org.junit.runners.JUnit4;
|
|
||||||
|
|
||||||
/** Unit tests for {@link Timestamp}. */
|
|
||||||
@RunWith(JUnit4.class)
|
|
||||||
public class TimestampTest {
|
|
||||||
@Rule public ExpectedException thrown = ExpectedException.none();
|
|
||||||
|
|
||||||
@Test
|
|
||||||
public void timestampCreate() {
|
|
||||||
assertThat(Timestamp.create(24, 42).getSeconds()).isEqualTo(24);
|
|
||||||
assertThat(Timestamp.create(24, 42).getNanos()).isEqualTo(42);
|
|
||||||
assertThat(Timestamp.create(-24, 42).getSeconds()).isEqualTo(-24);
|
|
||||||
assertThat(Timestamp.create(-24, 42).getNanos()).isEqualTo(42);
|
|
||||||
assertThat(Timestamp.create(315576000000L, 999999999).getSeconds()).isEqualTo(315576000000L);
|
|
||||||
assertThat(Timestamp.create(315576000000L, 999999999).getNanos()).isEqualTo(999999999);
|
|
||||||
assertThat(Timestamp.create(-315576000000L, 999999999).getSeconds()).isEqualTo(-315576000000L);
|
|
||||||
assertThat(Timestamp.create(-315576000000L, 999999999).getNanos()).isEqualTo(999999999);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Test
|
|
||||||
public void create_SecondsTooLow() {
|
|
||||||
thrown.expect(IllegalArgumentException.class);
|
|
||||||
thrown.expectMessage("'seconds' is less than minimum (-315576000000): -315576000001");
|
|
||||||
Timestamp.create(-315576000001L, 0);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Test
|
|
||||||
public void create_SecondsTooHigh() {
|
|
||||||
thrown.expect(IllegalArgumentException.class);
|
|
||||||
thrown.expectMessage("'seconds' is greater than maximum (315576000000): 315576000001");
|
|
||||||
Timestamp.create(315576000001L, 0);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Test
|
|
||||||
public void create_NanosTooLow_PositiveTime() {
|
|
||||||
thrown.expect(IllegalArgumentException.class);
|
|
||||||
thrown.expectMessage("'nanos' is less than zero: -1");
|
|
||||||
Timestamp.create(1, -1);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Test
|
|
||||||
public void create_NanosTooHigh_PositiveTime() {
|
|
||||||
thrown.expect(IllegalArgumentException.class);
|
|
||||||
thrown.expectMessage("'nanos' is greater than maximum (999999999): 1000000000");
|
|
||||||
Timestamp.create(1, 1000000000);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Test
|
|
||||||
public void create_NanosTooLow_NegativeTime() {
|
|
||||||
thrown.expect(IllegalArgumentException.class);
|
|
||||||
thrown.expectMessage("'nanos' is less than zero: -1");
|
|
||||||
Timestamp.create(-1, -1);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Test
|
|
||||||
public void create_NanosTooHigh_NegativeTime() {
|
|
||||||
thrown.expect(IllegalArgumentException.class);
|
|
||||||
thrown.expectMessage("'nanos' is greater than maximum (999999999): 1000000000");
|
|
||||||
Timestamp.create(-1, 1000000000);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Test
|
|
||||||
public void timestampFromMillis() {
|
|
||||||
assertThat(Timestamp.fromMillis(0)).isEqualTo(Timestamp.create(0, 0));
|
|
||||||
assertThat(Timestamp.fromMillis(987)).isEqualTo(Timestamp.create(0, 987000000));
|
|
||||||
assertThat(Timestamp.fromMillis(3456)).isEqualTo(Timestamp.create(3, 456000000));
|
|
||||||
}
|
|
||||||
|
|
||||||
@Test
|
|
||||||
public void timestampFromMillis_Negative() {
|
|
||||||
assertThat(Timestamp.fromMillis(-1)).isEqualTo(Timestamp.create(-1, 999000000));
|
|
||||||
assertThat(Timestamp.fromMillis(-999)).isEqualTo(Timestamp.create(-1, 1000000));
|
|
||||||
assertThat(Timestamp.fromMillis(-3456)).isEqualTo(Timestamp.create(-4, 544000000));
|
|
||||||
}
|
|
||||||
|
|
||||||
@Test
|
|
||||||
public void fromMillis_TooLow() {
|
|
||||||
thrown.expect(IllegalArgumentException.class);
|
|
||||||
thrown.expectMessage("'seconds' is less than minimum (-315576000000): -315576000001");
|
|
||||||
Timestamp.fromMillis(-315576000001000L);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Test
|
|
||||||
public void fromMillis_TooHigh() {
|
|
||||||
thrown.expect(IllegalArgumentException.class);
|
|
||||||
thrown.expectMessage("'seconds' is greater than maximum (315576000000): 315576000001");
|
|
||||||
Timestamp.fromMillis(315576000001000L);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Test
|
|
||||||
public void timestamp_Equal() {
|
|
||||||
// Positive tests.
|
|
||||||
assertThat(Timestamp.create(0, 0)).isEqualTo(Timestamp.create(0, 0));
|
|
||||||
assertThat(Timestamp.create(24, 42)).isEqualTo(Timestamp.create(24, 42));
|
|
||||||
assertThat(Timestamp.create(-24, 42)).isEqualTo(Timestamp.create(-24, 42));
|
|
||||||
// Negative tests.
|
|
||||||
assertThat(Timestamp.create(25, 42)).isNotEqualTo(Timestamp.create(24, 42));
|
|
||||||
assertThat(Timestamp.create(24, 43)).isNotEqualTo(Timestamp.create(24, 42));
|
|
||||||
assertThat(Timestamp.create(-25, 42)).isNotEqualTo(Timestamp.create(-24, 42));
|
|
||||||
assertThat(Timestamp.create(-24, 43)).isNotEqualTo(Timestamp.create(-24, 42));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
@ -20,7 +20,6 @@ import static com.google.common.truth.Truth.assertThat;
|
||||||
import static org.junit.Assert.assertEquals;
|
import static org.junit.Assert.assertEquals;
|
||||||
import static org.junit.Assert.assertFalse;
|
import static org.junit.Assert.assertFalse;
|
||||||
|
|
||||||
import io.opentelemetry.sdk.common.Timestamp;
|
|
||||||
import io.opentelemetry.sdk.internal.TestClock;
|
import io.opentelemetry.sdk.internal.TestClock;
|
||||||
import io.opentelemetry.sdk.resources.Resource;
|
import io.opentelemetry.sdk.resources.Resource;
|
||||||
import io.opentelemetry.sdk.trace.config.TraceConfig;
|
import io.opentelemetry.sdk.trace.config.TraceConfig;
|
||||||
|
|
@ -101,8 +100,8 @@ public class RecordEventsReadableSpanTest {
|
||||||
Collections.<SpanData.TimedEvent>emptyList(),
|
Collections.<SpanData.TimedEvent>emptyList(),
|
||||||
Collections.singletonList(link),
|
Collections.singletonList(link),
|
||||||
SPAN_NAME,
|
SPAN_NAME,
|
||||||
Timestamp.fromNanos(startEpochNanos),
|
startEpochNanos,
|
||||||
Timestamp.fromNanos(startEpochNanos),
|
startEpochNanos,
|
||||||
Status.OK);
|
Status.OK);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -130,8 +129,8 @@ public class RecordEventsReadableSpanTest {
|
||||||
Collections.singletonList(timedEvent),
|
Collections.singletonList(timedEvent),
|
||||||
Collections.singletonList(link),
|
Collections.singletonList(link),
|
||||||
SPAN_NEW_NAME,
|
SPAN_NEW_NAME,
|
||||||
Timestamp.fromNanos(startEpochNanos),
|
startEpochNanos,
|
||||||
Timestamp.fromNanos(testClock.now()),
|
testClock.now(),
|
||||||
Status.OK);
|
Status.OK);
|
||||||
} finally {
|
} finally {
|
||||||
span.end();
|
span.end();
|
||||||
|
|
@ -159,8 +158,8 @@ public class RecordEventsReadableSpanTest {
|
||||||
Collections.singletonList(timedEvent),
|
Collections.singletonList(timedEvent),
|
||||||
Collections.singletonList(link),
|
Collections.singletonList(link),
|
||||||
SPAN_NEW_NAME,
|
SPAN_NEW_NAME,
|
||||||
Timestamp.fromNanos(startEpochNanos),
|
startEpochNanos,
|
||||||
Timestamp.fromNanos(testClock.now()),
|
testClock.now(),
|
||||||
Status.CANCELLED);
|
Status.CANCELLED);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -473,8 +472,8 @@ public class RecordEventsReadableSpanTest {
|
||||||
List<SpanData.TimedEvent> timedEvents,
|
List<SpanData.TimedEvent> timedEvents,
|
||||||
List<Link> links,
|
List<Link> links,
|
||||||
String spanName,
|
String spanName,
|
||||||
Timestamp startTime,
|
long startEpochNanos,
|
||||||
Timestamp endTime,
|
long endEpochNanos,
|
||||||
Status status) {
|
Status status) {
|
||||||
assertThat(spanData.getTraceId()).isEqualTo(traceId);
|
assertThat(spanData.getTraceId()).isEqualTo(traceId);
|
||||||
assertThat(spanData.getSpanId()).isEqualTo(spanId);
|
assertThat(spanData.getSpanId()).isEqualTo(spanId);
|
||||||
|
|
@ -485,8 +484,8 @@ public class RecordEventsReadableSpanTest {
|
||||||
assertThat(spanData.getAttributes()).isEqualTo(attributes);
|
assertThat(spanData.getAttributes()).isEqualTo(attributes);
|
||||||
assertThat(spanData.getTimedEvents()).isEqualTo(timedEvents);
|
assertThat(spanData.getTimedEvents()).isEqualTo(timedEvents);
|
||||||
assertThat(spanData.getLinks()).isEqualTo(links);
|
assertThat(spanData.getLinks()).isEqualTo(links);
|
||||||
assertThat(spanData.getStartTimestamp()).isEqualTo(startTime);
|
assertThat(spanData.getStartEpochNanos()).isEqualTo(startEpochNanos);
|
||||||
assertThat(spanData.getEndTimestamp()).isEqualTo(endTime);
|
assertThat(spanData.getEndEpochNanos()).isEqualTo(endEpochNanos);
|
||||||
assertThat(spanData.getStatus().getCanonicalCode()).isEqualTo(status.getCanonicalCode());
|
assertThat(spanData.getStatus().getCanonicalCode()).isEqualTo(status.getCanonicalCode());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -542,8 +541,8 @@ public class RecordEventsReadableSpanTest {
|
||||||
.setName(name)
|
.setName(name)
|
||||||
.setKind(kind)
|
.setKind(kind)
|
||||||
.setStatus(Status.OK)
|
.setStatus(Status.OK)
|
||||||
.setStartTimestamp(Timestamp.fromNanos(startEpochNanos))
|
.setStartEpochNanos(startEpochNanos)
|
||||||
.setEndTimestamp(Timestamp.fromNanos(endEpochNanos))
|
.setEndEpochNanos(endEpochNanos)
|
||||||
.setTimedEvents(
|
.setTimedEvents(
|
||||||
Arrays.asList(
|
Arrays.asList(
|
||||||
SpanData.TimedEvent.create(firstEventEpochNanos, "event1", event1Attributes),
|
SpanData.TimedEvent.create(firstEventEpochNanos, "event1", event1Attributes),
|
||||||
|
|
|
||||||
|
|
@ -20,7 +20,6 @@ import static java.util.Collections.emptyList;
|
||||||
import static org.junit.Assert.assertEquals;
|
import static org.junit.Assert.assertEquals;
|
||||||
import static org.junit.Assert.assertFalse;
|
import static org.junit.Assert.assertFalse;
|
||||||
|
|
||||||
import io.opentelemetry.sdk.common.Timestamp;
|
|
||||||
import io.opentelemetry.sdk.trace.SpanData.TimedEvent;
|
import io.opentelemetry.sdk.trace.SpanData.TimedEvent;
|
||||||
import io.opentelemetry.trace.AttributeValue;
|
import io.opentelemetry.trace.AttributeValue;
|
||||||
import io.opentelemetry.trace.Link;
|
import io.opentelemetry.trace.Link;
|
||||||
|
|
@ -34,6 +33,7 @@ import io.opentelemetry.trace.Tracestate;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.Collections;
|
import java.util.Collections;
|
||||||
import java.util.HashMap;
|
import java.util.HashMap;
|
||||||
|
import java.util.concurrent.TimeUnit;
|
||||||
import org.junit.Rule;
|
import org.junit.Rule;
|
||||||
import org.junit.Test;
|
import org.junit.Test;
|
||||||
import org.junit.rules.ExpectedException;
|
import org.junit.rules.ExpectedException;
|
||||||
|
|
@ -43,6 +43,8 @@ import org.junit.runners.JUnit4;
|
||||||
/** Unit tests for {@link SpanData}. */
|
/** Unit tests for {@link SpanData}. */
|
||||||
@RunWith(JUnit4.class)
|
@RunWith(JUnit4.class)
|
||||||
public class SpanDataTest {
|
public class SpanDataTest {
|
||||||
|
private static final long START_EPOCH_NANOS = TimeUnit.SECONDS.toNanos(3000) + 200;
|
||||||
|
private static final long END_EPOCH_NANOS = TimeUnit.SECONDS.toNanos(3001) + 255;
|
||||||
@Rule public final ExpectedException thrown = ExpectedException.none();
|
@Rule public final ExpectedException thrown = ExpectedException.none();
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
|
|
@ -103,8 +105,8 @@ public class SpanDataTest {
|
||||||
.setSpanId(SpanId.getInvalid())
|
.setSpanId(SpanId.getInvalid())
|
||||||
.setTraceId(TraceId.getInvalid())
|
.setTraceId(TraceId.getInvalid())
|
||||||
.setName("spanName")
|
.setName("spanName")
|
||||||
.setStartTimestamp(Timestamp.create(3000, 200))
|
.setStartEpochNanos(START_EPOCH_NANOS)
|
||||||
.setEndTimestamp(Timestamp.create(3001, 255))
|
.setEndEpochNanos(END_EPOCH_NANOS)
|
||||||
.setKind(Kind.SERVER)
|
.setKind(Kind.SERVER)
|
||||||
.setStatus(Status.OK);
|
.setStatus(Status.OK);
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -16,7 +16,6 @@
|
||||||
|
|
||||||
package io.opentelemetry.sdk.trace;
|
package io.opentelemetry.sdk.trace;
|
||||||
|
|
||||||
import io.opentelemetry.sdk.common.Timestamp;
|
|
||||||
import io.opentelemetry.sdk.trace.config.TraceConfig;
|
import io.opentelemetry.sdk.trace.config.TraceConfig;
|
||||||
import io.opentelemetry.trace.AttributeValue;
|
import io.opentelemetry.trace.AttributeValue;
|
||||||
import io.opentelemetry.trace.Span;
|
import io.opentelemetry.trace.Span;
|
||||||
|
|
@ -27,6 +26,7 @@ import io.opentelemetry.trace.TraceId;
|
||||||
import java.util.HashMap;
|
import java.util.HashMap;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
import java.util.UUID;
|
import java.util.UUID;
|
||||||
|
import java.util.concurrent.TimeUnit;
|
||||||
|
|
||||||
/** Common utilities for unit tests. */
|
/** Common utilities for unit tests. */
|
||||||
public final class TestUtils {
|
public final class TestUtils {
|
||||||
|
|
@ -57,9 +57,9 @@ public final class TestUtils {
|
||||||
.setSpanId(SpanId.getInvalid())
|
.setSpanId(SpanId.getInvalid())
|
||||||
.setName("span")
|
.setName("span")
|
||||||
.setKind(Kind.SERVER)
|
.setKind(Kind.SERVER)
|
||||||
.setStartTimestamp(Timestamp.create(100, 100))
|
.setStartEpochNanos(TimeUnit.SECONDS.toNanos(100) + 100)
|
||||||
.setStatus(Status.OK)
|
.setStatus(Status.OK)
|
||||||
.setEndTimestamp(Timestamp.create(200, 200))
|
.setEndEpochNanos(TimeUnit.SECONDS.toNanos(200) + 200)
|
||||||
.build();
|
.build();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -19,7 +19,6 @@ package io.opentelemetry.sdk.contrib.trace.testbed;
|
||||||
import static com.google.common.truth.Truth.assertThat;
|
import static com.google.common.truth.Truth.assertThat;
|
||||||
|
|
||||||
import io.opentelemetry.exporters.inmemory.InMemorySpanExporter;
|
import io.opentelemetry.exporters.inmemory.InMemorySpanExporter;
|
||||||
import io.opentelemetry.sdk.common.Timestamp;
|
|
||||||
import io.opentelemetry.sdk.trace.SpanData;
|
import io.opentelemetry.sdk.trace.SpanData;
|
||||||
import io.opentelemetry.sdk.trace.TracerSdk;
|
import io.opentelemetry.sdk.trace.TracerSdk;
|
||||||
import io.opentelemetry.sdk.trace.export.SimpleSpansProcessor;
|
import io.opentelemetry.sdk.trace.export.SimpleSpansProcessor;
|
||||||
|
|
@ -191,7 +190,7 @@ public final class TestUtils {
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Sorts the specified {@code List} of {@code Span} by their {@code Span.Timestamp} values,
|
* Sorts the specified {@code List} of {@code Span} by their start epoch timestamp values,
|
||||||
* returning it as a new {@code List}.
|
* returning it as a new {@code List}.
|
||||||
*/
|
*/
|
||||||
public static List<SpanData> sortByStartTime(List<SpanData> spans) {
|
public static List<SpanData> sortByStartTime(List<SpanData> spans) {
|
||||||
|
|
@ -201,7 +200,7 @@ public final class TestUtils {
|
||||||
new Comparator<SpanData>() {
|
new Comparator<SpanData>() {
|
||||||
@Override
|
@Override
|
||||||
public int compare(SpanData o1, SpanData o2) {
|
public int compare(SpanData o1, SpanData o2) {
|
||||||
return compareTimestamps(o1.getStartTimestamp(), o2.getStartTimestamp());
|
return Long.compare(o1.getStartEpochNanos(), o2.getStartEpochNanos());
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
return sortedSpans;
|
return sortedSpans;
|
||||||
|
|
@ -211,26 +210,10 @@ public final class TestUtils {
|
||||||
public static void assertSameTrace(List<SpanData> spans) {
|
public static void assertSameTrace(List<SpanData> spans) {
|
||||||
for (int i = 0; i < spans.size() - 1; i++) {
|
for (int i = 0; i < spans.size() - 1; i++) {
|
||||||
// TODO - Include nanos in this comparison.
|
// TODO - Include nanos in this comparison.
|
||||||
assertThat(
|
assertThat(spans.get(spans.size() - 1).getEndEpochNanos() >= spans.get(i).getEndEpochNanos())
|
||||||
spans.get(spans.size() - 1).getEndTimestamp().getSeconds()
|
|
||||||
>= spans.get(i).getEndTimestamp().getSeconds())
|
|
||||||
.isTrue();
|
.isTrue();
|
||||||
assertThat(spans.get(spans.size() - 1).getTraceId()).isEqualTo(spans.get(i).getTraceId());
|
assertThat(spans.get(spans.size() - 1).getTraceId()).isEqualTo(spans.get(i).getTraceId());
|
||||||
assertThat(spans.get(spans.size() - 1).getSpanId()).isEqualTo(spans.get(i).getParentSpanId());
|
assertThat(spans.get(spans.size() - 1).getSpanId()).isEqualTo(spans.get(i).getParentSpanId());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// TODO: this comparator code is duplicated in another TestUtils class. find a common home for it.
|
|
||||||
private static final Comparator<Timestamp> COMPARATOR =
|
|
||||||
new Comparator<Timestamp>() {
|
|
||||||
@Override
|
|
||||||
public int compare(Timestamp t1, Timestamp t2) {
|
|
||||||
int secDiff = Long.compare(t1.getSeconds(), t2.getSeconds());
|
|
||||||
return (secDiff != 0) ? secDiff : Integer.compare(t1.getNanos(), t2.getNanos());
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
public static int compareTimestamps(Timestamp x, Timestamp y) {
|
|
||||||
return COMPARATOR.compare(x, y);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue