Add missing fields to OTLP metric exporters (#6402)

This commit is contained in:
jack-berg 2024-04-22 09:46:06 -05:00 committed by GitHub
parent 1960606bce
commit a5fc312d26
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
13 changed files with 211 additions and 5 deletions

View File

@ -1,2 +1,7 @@
Comparing source compatibility of against
No changes.
*** MODIFIED INTERFACE: PUBLIC ABSTRACT io.opentelemetry.sdk.metrics.export.AggregationTemporalitySelector (not serializable)
=== CLASS FILE FORMAT VERSION: 52.0 <- 52.0
+++ NEW METHOD: PUBLIC(+) STATIC(+) java.lang.String asString(io.opentelemetry.sdk.metrics.export.AggregationTemporalitySelector)
*** MODIFIED INTERFACE: PUBLIC ABSTRACT io.opentelemetry.sdk.metrics.export.DefaultAggregationSelector (not serializable)
=== CLASS FILE FORMAT VERSION: 52.0 <- 52.0
+++ NEW METHOD: PUBLIC(+) STATIC(+) java.lang.String asString(io.opentelemetry.sdk.metrics.export.DefaultAggregationSelector)

View File

@ -18,6 +18,7 @@ import io.opentelemetry.sdk.metrics.export.AggregationTemporalitySelector;
import io.opentelemetry.sdk.metrics.export.DefaultAggregationSelector;
import io.opentelemetry.sdk.metrics.export.MetricExporter;
import java.util.Collection;
import java.util.StringJoiner;
import javax.annotation.concurrent.ThreadSafe;
/**
@ -124,6 +125,15 @@ public final class OtlpHttpMetricExporter implements MetricExporter {
@Override
public String toString() {
return "OtlpHttpMetricExporter{" + builder.toString(false) + "}";
StringJoiner joiner = new StringJoiner(", ", "OtlpHttpMetricExporter{", "}");
joiner.add(builder.toString(false));
joiner.add(
"aggregationTemporalitySelector="
+ AggregationTemporalitySelector.asString(aggregationTemporalitySelector));
joiner.add(
"defaultAggregationSelector="
+ DefaultAggregationSelector.asString(defaultAggregationSelector));
joiner.add("memoryMode=" + memoryMode);
return joiner.toString();
}
}

View File

@ -18,6 +18,7 @@ import io.opentelemetry.sdk.metrics.export.AggregationTemporalitySelector;
import io.opentelemetry.sdk.metrics.export.DefaultAggregationSelector;
import io.opentelemetry.sdk.metrics.export.MetricExporter;
import java.util.Collection;
import java.util.StringJoiner;
import javax.annotation.concurrent.ThreadSafe;
/**
@ -128,6 +129,15 @@ public final class OtlpGrpcMetricExporter implements MetricExporter {
@Override
public String toString() {
return "OtlpGrpcMetricExporter{" + builder.toString(false) + "}";
StringJoiner joiner = new StringJoiner(", ", "OtlpGrpcMetricExporter{", "}");
joiner.add(builder.toString(false));
joiner.add(
"aggregationTemporalitySelector="
+ AggregationTemporalitySelector.asString(aggregationTemporalitySelector));
joiner.add(
"defaultAggregationSelector="
+ DefaultAggregationSelector.asString(defaultAggregationSelector));
joiner.add("memoryMode=" + memoryMode);
return joiner.toString();
}
}

View File

@ -23,7 +23,9 @@ import io.opentelemetry.sdk.metrics.data.AggregationTemporality;
import io.opentelemetry.sdk.metrics.data.MetricData;
import io.opentelemetry.sdk.metrics.export.AggregationTemporalitySelector;
import io.opentelemetry.sdk.metrics.export.DefaultAggregationSelector;
import io.opentelemetry.sdk.metrics.export.MetricExporter;
import java.util.List;
import java.util.concurrent.TimeUnit;
import org.junit.jupiter.api.Test;
class OtlpHttpMetricExporterOkHttpSenderTest
@ -77,6 +79,33 @@ class OtlpHttpMetricExporterOkHttpSenderTest
.hasMessage("defaultAggregationSelector");
}
/** Test configuration specific to metric exporter. */
@Test
void stringRepresentation() {
try (MetricExporter metricExporter = OtlpHttpMetricExporter.builder().build()) {
assertThat(metricExporter.toString())
.matches(
"OtlpHttpMetricExporter\\{"
+ "exporterName=otlp, "
+ "type=metric, "
+ "endpoint=http://localhost:4318/v1/metrics, "
+ "timeoutNanos="
+ TimeUnit.SECONDS.toNanos(10)
+ ", "
+ "proxyOptions=null, "
+ "compressorEncoding=null, "
+ "connectTimeoutNanos="
+ TimeUnit.SECONDS.toNanos(10)
+ ", "
+ "exportAsJson=false, "
+ "headers=Headers\\{User-Agent=OBFUSCATED\\}, "
+ "aggregationTemporalitySelector=AggregationTemporalitySelector\\{.*\\}, "
+ "defaultAggregationSelector=DefaultAggregationSelector\\{.*\\}, "
+ "memoryMode=IMMUTABLE_DATA"
+ "\\}");
}
}
@Override
protected TelemetryExporterBuilder<MetricData> exporterBuilder() {
return new HttpMetricExporterBuilderWrapper(OtlpHttpMetricExporter.builder());

View File

@ -23,8 +23,10 @@ import io.opentelemetry.sdk.metrics.data.AggregationTemporality;
import io.opentelemetry.sdk.metrics.data.MetricData;
import io.opentelemetry.sdk.metrics.export.AggregationTemporalitySelector;
import io.opentelemetry.sdk.metrics.export.DefaultAggregationSelector;
import io.opentelemetry.sdk.metrics.export.MetricExporter;
import java.io.Closeable;
import java.util.List;
import java.util.concurrent.TimeUnit;
import org.junit.jupiter.api.Test;
class OtlpGrpcMetricExporterTest
@ -78,6 +80,32 @@ class OtlpGrpcMetricExporterTest
.hasMessage("defaultAggregationSelector");
}
/** Test configuration specific to metric exporter. */
@Test
void stringRepresentation() {
try (MetricExporter metricExporter = OtlpGrpcMetricExporter.builder().build()) {
assertThat(metricExporter.toString())
.matches(
"OtlpGrpcMetricExporter\\{"
+ "exporterName=otlp, "
+ "type=metric, "
+ "endpoint=http://localhost:4317, "
+ "endpointPath=.*, "
+ "timeoutNanos="
+ TimeUnit.SECONDS.toNanos(10)
+ ", "
+ "connectTimeoutNanos="
+ TimeUnit.SECONDS.toNanos(10)
+ ", "
+ "compressorEncoding=null, "
+ "headers=Headers\\{User-Agent=OBFUSCATED\\}, "
+ "aggregationTemporalitySelector=AggregationTemporalitySelector\\{.*\\}, "
+ "defaultAggregationSelector=DefaultAggregationSelector\\{.*\\}, "
+ "memoryMode=IMMUTABLE_DATA"
+ "\\}");
}
}
@Test
void usingOkHttp() throws Exception {
try (Closeable exporter = OtlpGrpcMetricExporter.builder().build()) {

View File

@ -24,7 +24,9 @@ import io.opentelemetry.sdk.metrics.data.AggregationTemporality;
import io.opentelemetry.sdk.metrics.data.MetricData;
import io.opentelemetry.sdk.metrics.export.AggregationTemporalitySelector;
import io.opentelemetry.sdk.metrics.export.DefaultAggregationSelector;
import io.opentelemetry.sdk.metrics.export.MetricExporter;
import java.util.List;
import java.util.concurrent.TimeUnit;
import org.junit.jupiter.api.Test;
class OtlpHttpMetricExporterJdkSenderTest
@ -78,6 +80,33 @@ class OtlpHttpMetricExporterJdkSenderTest
.hasMessage("defaultAggregationSelector");
}
/** Test configuration specific to metric exporter. */
@Test
void stringRepresentation() {
try (MetricExporter metricExporter = OtlpHttpMetricExporter.builder().build()) {
assertThat(metricExporter.toString())
.matches(
"OtlpHttpMetricExporter\\{"
+ "exporterName=otlp, "
+ "type=metric, "
+ "endpoint=http://localhost:4318/v1/metrics, "
+ "timeoutNanos="
+ TimeUnit.SECONDS.toNanos(10)
+ ", "
+ "proxyOptions=null, "
+ "compressorEncoding=null, "
+ "connectTimeoutNanos="
+ TimeUnit.SECONDS.toNanos(10)
+ ", "
+ "exportAsJson=false, "
+ "headers=Headers\\{User-Agent=OBFUSCATED\\}, "
+ "aggregationTemporalitySelector=AggregationTemporalitySelector\\{.*\\}, "
+ "defaultAggregationSelector=DefaultAggregationSelector\\{.*\\}, "
+ "memoryMode=IMMUTABLE_DATA"
+ "\\}");
}
}
@Override
protected boolean hasAuthenticatorSupport() {
return false;

View File

@ -872,7 +872,7 @@ public abstract class AbstractGrpcTelemetryExporterTest<T, U extends Message> {
+ ", "
+ "compressorEncoding=null, "
+ "headers=Headers\\{User-Agent=OBFUSCATED\\}"
+ ".*" // Maybe additional grpcChannel field
+ ".*" // Maybe additional grpcChannel field, signal specific fields
+ "\\}");
} finally {
telemetryExporter.shutdown();
@ -914,7 +914,7 @@ public abstract class AbstractGrpcTelemetryExporterTest<T, U extends Message> {
+ "compressorEncoding=gzip, "
+ "headers=Headers\\{.*foo=OBFUSCATED.*\\}, "
+ "retryPolicy=RetryPolicy\\{maxAttempts=2, initialBackoff=PT0\\.05S, maxBackoff=PT3S, backoffMultiplier=1\\.3\\}"
+ ".*" // Maybe additional grpcChannel field
+ ".*" // Maybe additional grpcChannel field, signal specific fields
+ "\\}");
} finally {
telemetryExporter.shutdown();

View File

@ -858,6 +858,7 @@ public abstract class AbstractHttpTelemetryExporterTest<T, U extends Message> {
+ ", "
+ "exportAsJson=false, "
+ "headers=Headers\\{User-Agent=OBFUSCATED\\}"
+ ".*" // Maybe additional signal specific fields
+ "\\}");
} finally {
telemetryExporter.shutdown();
@ -900,6 +901,7 @@ public abstract class AbstractHttpTelemetryExporterTest<T, U extends Message> {
+ "exportAsJson=false, "
+ "headers=Headers\\{.*foo=OBFUSCATED.*\\}, "
+ "retryPolicy=RetryPolicy\\{maxAttempts=2, initialBackoff=PT0\\.05S, maxBackoff=PT3S, backoffMultiplier=1\\.3\\}"
+ ".*" // Maybe additional signal specific fields
+ "\\}");
} finally {
telemetryExporter.shutdown();

View File

@ -28,6 +28,10 @@ import io.opentelemetry.sdk.extension.incubator.fileconfig.internal.model.Header
import io.opentelemetry.sdk.extension.incubator.fileconfig.internal.model.OtlpMetric;
import io.opentelemetry.sdk.extension.incubator.fileconfig.internal.model.OtlpMetric.DefaultHistogramAggregation;
import io.opentelemetry.sdk.extension.incubator.fileconfig.internal.model.Prometheus;
import io.opentelemetry.sdk.metrics.Aggregation;
import io.opentelemetry.sdk.metrics.InstrumentType;
import io.opentelemetry.sdk.metrics.export.AggregationTemporalitySelector;
import io.opentelemetry.sdk.metrics.export.DefaultAggregationSelector;
import io.opentelemetry.sdk.metrics.export.MetricExporter;
import java.io.Closeable;
import java.io.IOException;
@ -118,6 +122,10 @@ class MetricExporterFactoryTest {
.addHeader("key2", "value2")
.setTimeout(Duration.ofSeconds(15))
.setCompression("gzip")
.setAggregationTemporalitySelector(AggregationTemporalitySelector.deltaPreferred())
.setDefaultAggregationSelector(
DefaultAggregationSelector.getDefault()
.with(InstrumentType.HISTOGRAM, Aggregation.base2ExponentialBucketHistogram()))
.build();
cleanup.addCloseable(expectedExporter);

View File

@ -7,6 +7,7 @@ package io.opentelemetry.sdk.metrics.export;
import io.opentelemetry.sdk.metrics.InstrumentType;
import io.opentelemetry.sdk.metrics.data.AggregationTemporality;
import java.util.StringJoiner;
/**
* A functional interface that selects {@link AggregationTemporality} based on {@link
@ -76,4 +77,16 @@ public interface AggregationTemporalitySelector {
/** Return the aggregation temporality for the {@link InstrumentType}. */
AggregationTemporality getAggregationTemporality(InstrumentType instrumentType);
/**
* Returns a string representation of this selector, for using in {@link Object#toString()}
* implementations.
*/
static String asString(AggregationTemporalitySelector selector) {
StringJoiner joiner = new StringJoiner(", ", "AggregationTemporalitySelector{", "}");
for (InstrumentType type : InstrumentType.values()) {
joiner.add(type.name() + "=" + selector.getAggregationTemporality(type).name());
}
return joiner.toString();
}
}

View File

@ -9,6 +9,8 @@ import static java.util.Objects.requireNonNull;
import io.opentelemetry.sdk.metrics.Aggregation;
import io.opentelemetry.sdk.metrics.InstrumentType;
import io.opentelemetry.sdk.metrics.internal.aggregator.AggregationUtil;
import java.util.StringJoiner;
/**
* A functional interface that selects default {@link Aggregation} based on {@link InstrumentType}.
@ -58,4 +60,19 @@ public interface DefaultAggregationSelector {
* <p>The default aggregation is used when an instrument does not match any views.
*/
Aggregation getDefaultAggregation(InstrumentType instrumentType);
/**
* Returns a string representation of this selector, for using in {@link Object#toString()}
* implementations.
*/
static String asString(DefaultAggregationSelector selector) {
StringJoiner joiner = new StringJoiner(", ", "DefaultAggregationSelector{", "}");
for (InstrumentType type : InstrumentType.values()) {
joiner.add(
type.name()
+ "="
+ AggregationUtil.aggregationName(selector.getDefaultAggregation(type)));
}
return joiner.toString();
}
}

View File

@ -63,4 +63,32 @@ class AggregationTemporalitySelectorTest {
assertThat(selector.getAggregationTemporality(InstrumentType.OBSERVABLE_UP_DOWN_COUNTER))
.isEqualTo(AggregationTemporality.CUMULATIVE);
}
@Test
void stringRepresentation() {
assertThat(
AggregationTemporalitySelector.asString(
AggregationTemporalitySelector.alwaysCumulative()))
.isEqualTo(
"AggregationTemporalitySelector{"
+ "COUNTER=CUMULATIVE, "
+ "UP_DOWN_COUNTER=CUMULATIVE, "
+ "HISTOGRAM=CUMULATIVE, "
+ "OBSERVABLE_COUNTER=CUMULATIVE, "
+ "OBSERVABLE_UP_DOWN_COUNTER=CUMULATIVE, "
+ "OBSERVABLE_GAUGE=CUMULATIVE"
+ "}");
assertThat(
AggregationTemporalitySelector.asString(
AggregationTemporalitySelector.deltaPreferred()))
.isEqualTo(
"AggregationTemporalitySelector{"
+ "COUNTER=DELTA, "
+ "UP_DOWN_COUNTER=CUMULATIVE, "
+ "HISTOGRAM=DELTA, "
+ "OBSERVABLE_COUNTER=DELTA, "
+ "OBSERVABLE_UP_DOWN_COUNTER=CUMULATIVE, "
+ "OBSERVABLE_GAUGE=DELTA"
+ "}");
}
}

View File

@ -61,4 +61,31 @@ class DefaultAggregationSelectorTest {
assertThat(selector2.getDefaultAggregation(InstrumentType.OBSERVABLE_GAUGE))
.isEqualTo(Aggregation.defaultAggregation());
}
@Test
void stringRepresentation() {
assertThat(DefaultAggregationSelector.asString(DefaultAggregationSelector.getDefault()))
.isEqualTo(
"DefaultAggregationSelector{"
+ "COUNTER=default, "
+ "UP_DOWN_COUNTER=default, "
+ "HISTOGRAM=default, "
+ "OBSERVABLE_COUNTER=default, "
+ "OBSERVABLE_UP_DOWN_COUNTER=default, "
+ "OBSERVABLE_GAUGE=default"
+ "}");
assertThat(
DefaultAggregationSelector.asString(
DefaultAggregationSelector.getDefault()
.with(InstrumentType.HISTOGRAM, Aggregation.base2ExponentialBucketHistogram())))
.isEqualTo(
"DefaultAggregationSelector{"
+ "COUNTER=default, "
+ "UP_DOWN_COUNTER=default, "
+ "HISTOGRAM=base2_exponential_bucket_histogram, "
+ "OBSERVABLE_COUNTER=default, "
+ "OBSERVABLE_UP_DOWN_COUNTER=default, "
+ "OBSERVABLE_GAUGE=default"
+ "}");
}
}