diff --git a/docs/apidiffs/current_vs_latest/opentelemetry-sdk-metrics.txt b/docs/apidiffs/current_vs_latest/opentelemetry-sdk-metrics.txt index a97cc879eb4..f8e8f4c44b5 100644 --- a/docs/apidiffs/current_vs_latest/opentelemetry-sdk-metrics.txt +++ b/docs/apidiffs/current_vs_latest/opentelemetry-sdk-metrics.txt @@ -1,2 +1,10 @@ Comparing source compatibility of opentelemetry-sdk-metrics-1.56.0-SNAPSHOT.jar against opentelemetry-sdk-metrics-1.55.0.jar -No changes. \ No newline at end of file ++++ NEW INTERFACE: PUBLIC(+) ABSTRACT(+) io.opentelemetry.sdk.metrics.ExemplarFilter (not serializable) + +++ CLASS FILE FORMAT VERSION: 52.0 <- n.a. + +++ NEW SUPERCLASS: java.lang.Object + +++ NEW METHOD: PUBLIC(+) STATIC(+) io.opentelemetry.sdk.metrics.ExemplarFilter alwaysOff() + +++ NEW METHOD: PUBLIC(+) STATIC(+) io.opentelemetry.sdk.metrics.ExemplarFilter alwaysOn() + +++ NEW METHOD: PUBLIC(+) STATIC(+) io.opentelemetry.sdk.metrics.ExemplarFilter traceBased() +*** MODIFIED CLASS: PUBLIC FINAL io.opentelemetry.sdk.metrics.SdkMeterProviderBuilder (not serializable) + === CLASS FILE FORMAT VERSION: 52.0 <- 52.0 + +++ NEW METHOD: PUBLIC(+) io.opentelemetry.sdk.metrics.SdkMeterProviderBuilder setExemplarFilter(io.opentelemetry.sdk.metrics.ExemplarFilter) diff --git a/integration-tests/otlp/src/main/java/io/opentelemetry/integrationtest/OtlpExporterIntegrationTest.java b/integration-tests/otlp/src/main/java/io/opentelemetry/integrationtest/OtlpExporterIntegrationTest.java index 8b82c4817d2..7052f0f635e 100644 --- a/integration-tests/otlp/src/main/java/io/opentelemetry/integrationtest/OtlpExporterIntegrationTest.java +++ b/integration-tests/otlp/src/main/java/io/opentelemetry/integrationtest/OtlpExporterIntegrationTest.java @@ -65,12 +65,10 @@ import io.opentelemetry.sdk.logs.SdkLoggerProvider; import io.opentelemetry.sdk.logs.export.BatchLogRecordProcessor; import io.opentelemetry.sdk.logs.export.LogRecordExporter; +import io.opentelemetry.sdk.metrics.ExemplarFilter; import io.opentelemetry.sdk.metrics.SdkMeterProvider; -import io.opentelemetry.sdk.metrics.SdkMeterProviderBuilder; import io.opentelemetry.sdk.metrics.export.MetricExporter; import io.opentelemetry.sdk.metrics.export.PeriodicMetricReader; -import io.opentelemetry.sdk.metrics.internal.SdkMeterProviderUtil; -import io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarFilter; import io.opentelemetry.sdk.resources.Resource; import io.opentelemetry.sdk.trace.IdGenerator; import io.opentelemetry.sdk.trace.SdkTracerProvider; @@ -461,18 +459,16 @@ void testOtlpHttpMetricExport_mtls() throws Exception { } private static void testMetricExport(MetricExporter metricExporter) { - SdkMeterProviderBuilder meterProviderBuilder = + SdkMeterProvider meterProvider = SdkMeterProvider.builder() .setResource(RESOURCE) .registerMetricReader( PeriodicMetricReader.builder(metricExporter) .setInterval(Duration.ofSeconds(Integer.MAX_VALUE)) - .build()); - - // Enable alwaysOn exemplar filter, instead of default traceBased filter - SdkMeterProviderUtil.setExemplarFilter(meterProviderBuilder, ExemplarFilter.alwaysOn()); - - SdkMeterProvider meterProvider = meterProviderBuilder.build(); + .build()) + // Enable alwaysOn exemplar filter, instead of default traceBased filter + .setExemplarFilter(ExemplarFilter.alwaysOn()) + .build(); Meter meter = meterProvider.meterBuilder(OtlpExporterIntegrationTest.class.getName()).build(); diff --git a/sdk-extensions/autoconfigure/src/main/java/io/opentelemetry/sdk/autoconfigure/MeterProviderConfiguration.java b/sdk-extensions/autoconfigure/src/main/java/io/opentelemetry/sdk/autoconfigure/MeterProviderConfiguration.java index 8686c1208c1..7395bd17bd4 100644 --- a/sdk-extensions/autoconfigure/src/main/java/io/opentelemetry/sdk/autoconfigure/MeterProviderConfiguration.java +++ b/sdk-extensions/autoconfigure/src/main/java/io/opentelemetry/sdk/autoconfigure/MeterProviderConfiguration.java @@ -9,11 +9,10 @@ import io.opentelemetry.sdk.autoconfigure.spi.ConfigProperties; import io.opentelemetry.sdk.autoconfigure.spi.ConfigurationException; import io.opentelemetry.sdk.autoconfigure.spi.internal.DefaultConfigProperties; +import io.opentelemetry.sdk.metrics.ExemplarFilter; import io.opentelemetry.sdk.metrics.SdkMeterProviderBuilder; import io.opentelemetry.sdk.metrics.export.MetricExporter; import io.opentelemetry.sdk.metrics.export.MetricReader; -import io.opentelemetry.sdk.metrics.internal.SdkMeterProviderUtil; -import io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarFilter; import io.opentelemetry.sdk.metrics.internal.state.MetricStorage; import java.io.Closeable; import java.util.Collections; @@ -43,14 +42,14 @@ static void configureMeterProvider( config.getString("otel.metrics.exemplar.filter", "trace_based").toLowerCase(Locale.ROOT); switch (exemplarFilter) { case "always_off": - SdkMeterProviderUtil.setExemplarFilter(meterProviderBuilder, ExemplarFilter.alwaysOff()); + meterProviderBuilder.setExemplarFilter(ExemplarFilter.alwaysOff()); break; case "always_on": - SdkMeterProviderUtil.setExemplarFilter(meterProviderBuilder, ExemplarFilter.alwaysOn()); + meterProviderBuilder.setExemplarFilter(ExemplarFilter.alwaysOn()); break; case "trace_based": default: - SdkMeterProviderUtil.setExemplarFilter(meterProviderBuilder, ExemplarFilter.traceBased()); + meterProviderBuilder.setExemplarFilter(ExemplarFilter.traceBased()); break; } diff --git a/sdk-extensions/autoconfigure/src/test/java/io/opentelemetry/sdk/autoconfigure/MeterProviderConfigurationTest.java b/sdk-extensions/autoconfigure/src/test/java/io/opentelemetry/sdk/autoconfigure/MeterProviderConfigurationTest.java index e136df01f4d..43f12ae6e0a 100644 --- a/sdk-extensions/autoconfigure/src/test/java/io/opentelemetry/sdk/autoconfigure/MeterProviderConfigurationTest.java +++ b/sdk-extensions/autoconfigure/src/test/java/io/opentelemetry/sdk/autoconfigure/MeterProviderConfigurationTest.java @@ -14,7 +14,7 @@ import io.opentelemetry.sdk.metrics.SdkMeterProviderBuilder; import io.opentelemetry.sdk.metrics.internal.exemplar.AlwaysOffExemplarFilter; import io.opentelemetry.sdk.metrics.internal.exemplar.AlwaysOnExemplarFilter; -import io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarFilter; +import io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarFilterInternal; import io.opentelemetry.sdk.metrics.internal.exemplar.TraceBasedExemplarFilter; import java.util.ArrayList; import java.util.Collections; @@ -45,7 +45,8 @@ void configureMeterProvider_ConfiguresExemplarFilter() { .isInstanceOf(AlwaysOnExemplarFilter.class); } - private static ObjectAssert assertExemplarFilter(Map config) { + private static ObjectAssert assertExemplarFilter( + Map config) { Map configWithDefault = new HashMap<>(config); configWithDefault.put("otel.metrics.exporter", "none"); SdkMeterProviderBuilder builder = SdkMeterProvider.builder(); @@ -57,6 +58,7 @@ private static ObjectAssert assertExemplarFilter(Map a, new ArrayList<>()); return assertThat(builder) - .extracting("exemplarFilter", as(InstanceOfAssertFactories.type(ExemplarFilter.class))); + .extracting( + "exemplarFilter", as(InstanceOfAssertFactories.type(ExemplarFilterInternal.class))); } } diff --git a/sdk-extensions/incubator/src/main/java/io/opentelemetry/sdk/extension/incubator/fileconfig/ExemplarFilterFactory.java b/sdk-extensions/incubator/src/main/java/io/opentelemetry/sdk/extension/incubator/fileconfig/ExemplarFilterFactory.java index d6485ba9931..b5c3aea4473 100644 --- a/sdk-extensions/incubator/src/main/java/io/opentelemetry/sdk/extension/incubator/fileconfig/ExemplarFilterFactory.java +++ b/sdk-extensions/incubator/src/main/java/io/opentelemetry/sdk/extension/incubator/fileconfig/ExemplarFilterFactory.java @@ -7,7 +7,7 @@ import io.opentelemetry.api.incubator.config.DeclarativeConfigException; import io.opentelemetry.sdk.extension.incubator.fileconfig.internal.model.MeterProviderModel; -import io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarFilter; +import io.opentelemetry.sdk.metrics.ExemplarFilter; final class ExemplarFilterFactory implements Factory { diff --git a/sdk-extensions/incubator/src/main/java/io/opentelemetry/sdk/extension/incubator/fileconfig/MeterProviderFactory.java b/sdk-extensions/incubator/src/main/java/io/opentelemetry/sdk/extension/incubator/fileconfig/MeterProviderFactory.java index 4854ed1199d..b0ef650ff6a 100644 --- a/sdk-extensions/incubator/src/main/java/io/opentelemetry/sdk/extension/incubator/fileconfig/MeterProviderFactory.java +++ b/sdk-extensions/incubator/src/main/java/io/opentelemetry/sdk/extension/incubator/fileconfig/MeterProviderFactory.java @@ -97,8 +97,8 @@ public SdkMeterProviderBuilder create( MeterProviderModel.ExemplarFilter exemplarFilterModel = model.getExemplarFilter(); if (exemplarFilterModel != null) { - SdkMeterProviderUtil.setExemplarFilter( - builder, ExemplarFilterFactory.getInstance().create(exemplarFilterModel, context)); + builder.setExemplarFilter( + ExemplarFilterFactory.getInstance().create(exemplarFilterModel, context)); } return builder; diff --git a/sdk-extensions/incubator/src/test/java/io/opentelemetry/sdk/extension/incubator/fileconfig/ExemplarFilterFactoryTest.java b/sdk-extensions/incubator/src/test/java/io/opentelemetry/sdk/extension/incubator/fileconfig/ExemplarFilterFactoryTest.java index e675323d6f5..79fa0bbde45 100644 --- a/sdk-extensions/incubator/src/test/java/io/opentelemetry/sdk/extension/incubator/fileconfig/ExemplarFilterFactoryTest.java +++ b/sdk-extensions/incubator/src/test/java/io/opentelemetry/sdk/extension/incubator/fileconfig/ExemplarFilterFactoryTest.java @@ -9,7 +9,7 @@ import static org.mockito.Mockito.mock; import io.opentelemetry.sdk.extension.incubator.fileconfig.internal.model.MeterProviderModel; -import io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarFilter; +import io.opentelemetry.sdk.metrics.ExemplarFilter; import java.util.stream.Stream; import org.junit.jupiter.params.ParameterizedTest; import org.junit.jupiter.params.provider.Arguments; diff --git a/sdk-extensions/incubator/src/test/java/io/opentelemetry/sdk/extension/incubator/fileconfig/MeterProviderFactoryTest.java b/sdk-extensions/incubator/src/test/java/io/opentelemetry/sdk/extension/incubator/fileconfig/MeterProviderFactoryTest.java index e877d8fa83d..da8162c0bc5 100644 --- a/sdk-extensions/incubator/src/test/java/io/opentelemetry/sdk/extension/incubator/fileconfig/MeterProviderFactoryTest.java +++ b/sdk-extensions/incubator/src/test/java/io/opentelemetry/sdk/extension/incubator/fileconfig/MeterProviderFactoryTest.java @@ -5,7 +5,6 @@ package io.opentelemetry.sdk.extension.incubator.fileconfig; -import static io.opentelemetry.sdk.metrics.internal.SdkMeterProviderUtil.setExemplarFilter; import static io.opentelemetry.sdk.metrics.internal.SdkMeterProviderUtil.setMeterConfigurator; import static io.opentelemetry.sdk.testing.assertj.OpenTelemetryAssertions.assertThat; @@ -25,12 +24,12 @@ import io.opentelemetry.sdk.extension.incubator.fileconfig.internal.model.ViewStreamModel; import io.opentelemetry.sdk.internal.ScopeConfigurator; import io.opentelemetry.sdk.internal.ScopeConfiguratorBuilder; +import io.opentelemetry.sdk.metrics.ExemplarFilter; import io.opentelemetry.sdk.metrics.InstrumentSelector; import io.opentelemetry.sdk.metrics.SdkMeterProvider; import io.opentelemetry.sdk.metrics.View; import io.opentelemetry.sdk.metrics.export.PeriodicMetricReader; import io.opentelemetry.sdk.metrics.internal.MeterConfig; -import io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarFilter; import java.io.Closeable; import java.util.ArrayList; import java.util.Collections; @@ -94,16 +93,14 @@ private static Stream createArguments() { .withConfig( new ExperimentalMeterConfigModel().withDisabled(false))))) .withExemplarFilter(MeterProviderModel.ExemplarFilter.ALWAYS_ON), - setExemplarFilter( - setMeterConfigurator( - SdkMeterProvider.builder(), - ScopeConfigurator.builder() - .setDefault(MeterConfig.disabled()) - .addCondition( - ScopeConfiguratorBuilder.nameMatchesGlob("foo"), - MeterConfig.enabled()) - .build()), - ExemplarFilter.alwaysOn()) + setMeterConfigurator( + SdkMeterProvider.builder(), + ScopeConfigurator.builder() + .setDefault(MeterConfig.disabled()) + .addCondition( + ScopeConfiguratorBuilder.nameMatchesGlob("foo"), MeterConfig.enabled()) + .build()) + .setExemplarFilter(ExemplarFilter.alwaysOn()) .registerMetricReader( PeriodicMetricReader.builder(OtlpHttpMetricExporter.getDefault()).build()) .registerView( diff --git a/sdk/metrics/src/jmh/java/io/opentelemetry/sdk/metrics/TestSdk.java b/sdk/metrics/src/jmh/java/io/opentelemetry/sdk/metrics/TestSdk.java index d4b415953a9..64bcc03ad6b 100644 --- a/sdk/metrics/src/jmh/java/io/opentelemetry/sdk/metrics/TestSdk.java +++ b/sdk/metrics/src/jmh/java/io/opentelemetry/sdk/metrics/TestSdk.java @@ -9,7 +9,6 @@ import io.opentelemetry.api.metrics.MeterProvider; import io.opentelemetry.api.trace.Tracer; import io.opentelemetry.sdk.common.Clock; -import io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarFilter; import io.opentelemetry.sdk.resources.Resource; import io.opentelemetry.sdk.testing.exporter.InMemoryMetricReader; import io.opentelemetry.sdk.trace.SdkTracerProvider; diff --git a/sdk/metrics/src/jmh/java/io/opentelemetry/sdk/metrics/internal/aggregator/HistogramCollectBenchmark.java b/sdk/metrics/src/jmh/java/io/opentelemetry/sdk/metrics/internal/aggregator/HistogramCollectBenchmark.java index acc6bdca538..be316162e7b 100644 --- a/sdk/metrics/src/jmh/java/io/opentelemetry/sdk/metrics/internal/aggregator/HistogramCollectBenchmark.java +++ b/sdk/metrics/src/jmh/java/io/opentelemetry/sdk/metrics/internal/aggregator/HistogramCollectBenchmark.java @@ -9,15 +9,13 @@ import io.opentelemetry.api.metrics.DoubleHistogram; import io.opentelemetry.sdk.common.CompletableResultCode; import io.opentelemetry.sdk.metrics.Aggregation; +import io.opentelemetry.sdk.metrics.ExemplarFilter; import io.opentelemetry.sdk.metrics.InstrumentType; import io.opentelemetry.sdk.metrics.SdkMeterProvider; -import io.opentelemetry.sdk.metrics.SdkMeterProviderBuilder; import io.opentelemetry.sdk.metrics.data.AggregationTemporality; import io.opentelemetry.sdk.metrics.data.MetricData; import io.opentelemetry.sdk.metrics.export.MetricExporter; import io.opentelemetry.sdk.metrics.export.PeriodicMetricReader; -import io.opentelemetry.sdk.metrics.internal.SdkMeterProviderUtil; -import io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarFilter; import java.time.Duration; import java.util.ArrayList; import java.util.Collection; @@ -64,7 +62,7 @@ public static class ThreadState { @Setup public void setup() { - SdkMeterProviderBuilder builder = + SdkMeterProvider sdkMeterProvider = SdkMeterProvider.builder() .registerMetricReader( PeriodicMetricReader.builder( @@ -74,10 +72,11 @@ public void setup() { aggregationTemporality, aggregationGenerator.aggregation)) // Effectively disable periodic reading so reading is only done on #flush() .setInterval(Duration.ofSeconds(Integer.MAX_VALUE)) - .build()); - // Disable exemplars - SdkMeterProviderUtil.setExemplarFilter(builder, ExemplarFilter.alwaysOff()); - sdkMeterProvider = builder.build(); + .build()) + // Disable exemplars + .setExemplarFilter(ExemplarFilter.alwaysOff()) + .build(); + histogram = sdkMeterProvider.get("meter").histogramBuilder("histogram").build(); random = new Random(); diff --git a/sdk/metrics/src/jmhBasedTest/java/io/opentelemetry/sdk/metrics/internal/state/InstrumentGarbageCollectionBenchmark.java b/sdk/metrics/src/jmhBasedTest/java/io/opentelemetry/sdk/metrics/internal/state/InstrumentGarbageCollectionBenchmark.java index d1d33632b65..3d3f9174d44 100644 --- a/sdk/metrics/src/jmhBasedTest/java/io/opentelemetry/sdk/metrics/internal/state/InstrumentGarbageCollectionBenchmark.java +++ b/sdk/metrics/src/jmhBasedTest/java/io/opentelemetry/sdk/metrics/internal/state/InstrumentGarbageCollectionBenchmark.java @@ -7,12 +7,11 @@ import io.opentelemetry.api.common.Attributes; import io.opentelemetry.sdk.common.export.MemoryMode; +import io.opentelemetry.sdk.metrics.ExemplarFilter; import io.opentelemetry.sdk.metrics.SdkMeterProvider; import io.opentelemetry.sdk.metrics.SdkMeterProviderBuilder; import io.opentelemetry.sdk.metrics.data.AggregationTemporality; import io.opentelemetry.sdk.metrics.export.PeriodicMetricReader; -import io.opentelemetry.sdk.metrics.internal.SdkMeterProviderUtil; -import io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarFilter; import io.opentelemetry.sdk.metrics.internal.state.TestInstrumentType.InstrumentTester; import io.opentelemetry.sdk.metrics.internal.state.TestInstrumentType.TestInstrumentsState; import java.time.Duration; @@ -96,7 +95,7 @@ public void setup() { attributesList = AttributesGenerator.generate(cardinality); // Disable exemplars - SdkMeterProviderUtil.setExemplarFilter(builder, ExemplarFilter.alwaysOff()); + builder.setExemplarFilter(ExemplarFilter.alwaysOff()); sdkMeterProvider = builder.build(); testInstrumentsState = diff --git a/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/ExemplarFilter.java b/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/ExemplarFilter.java new file mode 100644 index 00000000000..89ff7c5cbef --- /dev/null +++ b/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/ExemplarFilter.java @@ -0,0 +1,41 @@ +/* + * Copyright The OpenTelemetry Authors + * SPDX-License-Identifier: Apache-2.0 + */ + +package io.opentelemetry.sdk.metrics; + +import io.opentelemetry.context.Context; +import io.opentelemetry.sdk.metrics.internal.exemplar.AlwaysOffExemplarFilter; +import io.opentelemetry.sdk.metrics.internal.exemplar.AlwaysOnExemplarFilter; +import io.opentelemetry.sdk.metrics.internal.exemplar.DoubleExemplarReservoir; +import io.opentelemetry.sdk.metrics.internal.exemplar.LongExemplarReservoir; +import io.opentelemetry.sdk.metrics.internal.exemplar.TraceBasedExemplarFilter; + +/** + * Exemplar filters are used to pre-filter measurements before attempting to store them in a + * reservoir ({@link DoubleExemplarReservoir}, {@link LongExemplarReservoir}. + * + * @see SdkMeterProviderBuilder#setExemplarFilter(ExemplarFilter) + */ +// TODO(jack-berg): Have methods when custom filters are supported. +@SuppressWarnings("InterfaceWithOnlyStatics") +public interface ExemplarFilter { + /** + * A filter that only accepts measurements where there is a {@code Span} in {@link Context} that + * is being sampled. + */ + static ExemplarFilter traceBased() { + return TraceBasedExemplarFilter.getInstance(); + } + + /** A filter which makes all measurements eligible for being an exemplar. */ + static ExemplarFilter alwaysOn() { + return AlwaysOnExemplarFilter.getInstance(); + } + + /** A filter which makes no measurements eligible for being an exemplar. */ + static ExemplarFilter alwaysOff() { + return AlwaysOffExemplarFilter.getInstance(); + } +} diff --git a/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/SdkMeterProvider.java b/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/SdkMeterProvider.java index a2a076fd9a0..36f0bd92fb0 100644 --- a/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/SdkMeterProvider.java +++ b/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/SdkMeterProvider.java @@ -21,7 +21,7 @@ import io.opentelemetry.sdk.metrics.export.MetricReader; import io.opentelemetry.sdk.metrics.internal.MeterConfig; import io.opentelemetry.sdk.metrics.internal.SdkMeterProviderUtil; -import io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarFilter; +import io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarFilterInternal; import io.opentelemetry.sdk.metrics.internal.export.RegisteredReader; import io.opentelemetry.sdk.metrics.internal.state.MeterProviderSharedState; import io.opentelemetry.sdk.metrics.internal.view.RegisteredView; @@ -67,7 +67,7 @@ public static SdkMeterProviderBuilder builder() { List metricProducers, Clock clock, Resource resource, - ExemplarFilter exemplarFilter, + ExemplarFilterInternal exemplarFilter, ScopeConfigurator meterConfigurator) { long startEpochNanos = clock.now(); this.registeredViews = registeredViews; diff --git a/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/SdkMeterProviderBuilder.java b/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/SdkMeterProviderBuilder.java index 90d0c7a8fef..c0810cac3e3 100644 --- a/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/SdkMeterProviderBuilder.java +++ b/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/SdkMeterProviderBuilder.java @@ -15,7 +15,7 @@ import io.opentelemetry.sdk.metrics.internal.MeterConfig; import io.opentelemetry.sdk.metrics.internal.SdkMeterProviderUtil; import io.opentelemetry.sdk.metrics.internal.debug.SourceInfo; -import io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarFilter; +import io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarFilterInternal; import io.opentelemetry.sdk.metrics.internal.view.RegisteredView; import io.opentelemetry.sdk.resources.Resource; import java.util.ArrayList; @@ -36,7 +36,8 @@ public final class SdkMeterProviderBuilder { * * @see #setExemplarFilter(ExemplarFilter) */ - private static final ExemplarFilter DEFAULT_EXEMPLAR_FILTER = ExemplarFilter.traceBased(); + private static final ExemplarFilterInternal DEFAULT_EXEMPLAR_FILTER = + ExemplarFilterInternal.asExemplarFilterInternal(ExemplarFilter.traceBased()); private Clock clock = Clock.getDefault(); private Resource resource = Resource.getDefault(); @@ -44,7 +45,7 @@ public final class SdkMeterProviderBuilder { new IdentityHashMap<>(); private final List metricProducers = new ArrayList<>(); private final List registeredViews = new ArrayList<>(); - private ExemplarFilter exemplarFilter = DEFAULT_EXEMPLAR_FILTER; + private ExemplarFilterInternal exemplarFilter = DEFAULT_EXEMPLAR_FILTER; private ScopeConfiguratorBuilder meterConfiguratorBuilder = MeterConfig.configuratorBuilder(); @@ -80,14 +81,9 @@ public SdkMeterProviderBuilder addResource(Resource resource) { return this; } - /** - * Assign an {@link ExemplarFilter} for all metrics created by Meters. - * - *

This method is experimental so not public. You may reflectively call it using {@link - * SdkMeterProviderUtil#setExemplarFilter(SdkMeterProviderBuilder, ExemplarFilter)}. - */ - SdkMeterProviderBuilder setExemplarFilter(ExemplarFilter filter) { - this.exemplarFilter = filter; + /** Set the {@link ExemplarFilter} used for all instruments from all meters. */ + public SdkMeterProviderBuilder setExemplarFilter(ExemplarFilter filter) { + this.exemplarFilter = ExemplarFilterInternal.asExemplarFilterInternal(filter); return this; } diff --git a/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/SdkMeterProviderUtil.java b/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/SdkMeterProviderUtil.java index c324900ab7d..18a60fa2836 100644 --- a/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/SdkMeterProviderUtil.java +++ b/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/SdkMeterProviderUtil.java @@ -10,7 +10,6 @@ import io.opentelemetry.sdk.metrics.SdkMeterProvider; import io.opentelemetry.sdk.metrics.SdkMeterProviderBuilder; import io.opentelemetry.sdk.metrics.ViewBuilder; -import io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarFilter; import io.opentelemetry.sdk.metrics.internal.view.AttributesProcessor; import io.opentelemetry.sdk.metrics.internal.view.StringPredicates; import java.lang.reflect.InvocationTargetException; @@ -29,26 +28,6 @@ public final class SdkMeterProviderUtil { private SdkMeterProviderUtil() {} - /** - * Reflectively assign the {@link ExemplarFilter} to the {@link SdkMeterProviderBuilder}. - * - * @param sdkMeterProviderBuilder the builder - */ - public static SdkMeterProviderBuilder setExemplarFilter( - SdkMeterProviderBuilder sdkMeterProviderBuilder, ExemplarFilter exemplarFilter) { - try { - Method method = - SdkMeterProviderBuilder.class.getDeclaredMethod( - "setExemplarFilter", ExemplarFilter.class); - method.setAccessible(true); - method.invoke(sdkMeterProviderBuilder, exemplarFilter); - } catch (NoSuchMethodException | IllegalAccessException | InvocationTargetException e) { - throw new IllegalStateException( - "Error calling setExemplarFilter on SdkMeterProviderBuilder", e); - } - return sdkMeterProviderBuilder; - } - /** Reflectively set the {@link ScopeConfigurator} to the {@link SdkMeterProvider}. */ public static void setMeterConfigurator( SdkMeterProvider sdkMeterProvider, ScopeConfigurator scopeConfigurator) { diff --git a/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/aggregator/AggregatorFactory.java b/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/aggregator/AggregatorFactory.java index 8c5941acba3..0d6ba79b0a5 100644 --- a/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/aggregator/AggregatorFactory.java +++ b/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/aggregator/AggregatorFactory.java @@ -8,7 +8,7 @@ import io.opentelemetry.sdk.common.export.MemoryMode; import io.opentelemetry.sdk.metrics.data.PointData; import io.opentelemetry.sdk.metrics.internal.descriptor.InstrumentDescriptor; -import io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarFilter; +import io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarFilterInternal; /** * An internal interface for returning an Aggregator from an Aggregation. @@ -32,12 +32,12 @@ public interface AggregatorFactory { */ Aggregator createAggregator( InstrumentDescriptor instrumentDescriptor, - ExemplarFilter exemplarFilter, + ExemplarFilterInternal exemplarFilter, MemoryMode memoryMode); /** * Determine if the {@link Aggregator} produced by {@link #createAggregator(InstrumentDescriptor, - * ExemplarFilter, MemoryMode)} is compatible with the {@code instrumentDescriptor}. + * ExemplarFilterInternal, MemoryMode)} is compatible with the {@code instrumentDescriptor}. */ boolean isCompatibleWithInstrument(InstrumentDescriptor instrumentDescriptor); } diff --git a/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/exemplar/AlwaysOffExemplarFilter.java b/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/exemplar/AlwaysOffExemplarFilter.java index 9d74cddd7b2..1b34c7b266d 100644 --- a/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/exemplar/AlwaysOffExemplarFilter.java +++ b/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/exemplar/AlwaysOffExemplarFilter.java @@ -14,11 +14,15 @@ *

This class is internal and is hence not for public use. Its APIs are unstable and can change * at any time. */ -public final class AlwaysOffExemplarFilter implements ExemplarFilter { - static final ExemplarFilter INSTANCE = new AlwaysOffExemplarFilter(); +public final class AlwaysOffExemplarFilter implements ExemplarFilterInternal { + private static final ExemplarFilterInternal INSTANCE = new AlwaysOffExemplarFilter(); private AlwaysOffExemplarFilter() {} + public static ExemplarFilterInternal getInstance() { + return INSTANCE; + } + @Override public boolean shouldSampleMeasurement(long value, Attributes attributes, Context context) { return false; diff --git a/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/exemplar/AlwaysOnExemplarFilter.java b/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/exemplar/AlwaysOnExemplarFilter.java index a8463e038dd..aa3a7c56f31 100644 --- a/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/exemplar/AlwaysOnExemplarFilter.java +++ b/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/exemplar/AlwaysOnExemplarFilter.java @@ -14,11 +14,15 @@ *

This class is internal and is hence not for public use. Its APIs are unstable and can change * at any time. */ -public final class AlwaysOnExemplarFilter implements ExemplarFilter { - static final ExemplarFilter INSTANCE = new AlwaysOnExemplarFilter(); +public final class AlwaysOnExemplarFilter implements ExemplarFilterInternal { + private static final ExemplarFilterInternal INSTANCE = new AlwaysOnExemplarFilter(); private AlwaysOnExemplarFilter() {} + public static ExemplarFilterInternal getInstance() { + return INSTANCE; + } + @Override public boolean shouldSampleMeasurement(long value, Attributes attributes, Context context) { return true; diff --git a/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/exemplar/DoubleFilteredExemplarReservoir.java b/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/exemplar/DoubleFilteredExemplarReservoir.java index 9d768e56a10..884453a3959 100644 --- a/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/exemplar/DoubleFilteredExemplarReservoir.java +++ b/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/exemplar/DoubleFilteredExemplarReservoir.java @@ -12,10 +12,11 @@ /** A reservoir that has a pre-filter on measurements. */ class DoubleFilteredExemplarReservoir implements DoubleExemplarReservoir { - private final ExemplarFilter filter; + private final ExemplarFilterInternal filter; private final DoubleExemplarReservoir reservoir; - DoubleFilteredExemplarReservoir(ExemplarFilter filter, DoubleExemplarReservoir reservoir) { + DoubleFilteredExemplarReservoir( + ExemplarFilterInternal filter, DoubleExemplarReservoir reservoir) { this.filter = filter; this.reservoir = reservoir; } diff --git a/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/exemplar/ExemplarFilter.java b/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/exemplar/ExemplarFilterInternal.java similarity index 53% rename from sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/exemplar/ExemplarFilter.java rename to sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/exemplar/ExemplarFilterInternal.java index 4b157319d89..aa3858d670a 100644 --- a/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/exemplar/ExemplarFilter.java +++ b/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/exemplar/ExemplarFilterInternal.java @@ -7,6 +7,7 @@ import io.opentelemetry.api.common.Attributes; import io.opentelemetry.context.Context; +import io.opentelemetry.sdk.metrics.ExemplarFilter; /** * Exemplar filters are used to pre-filter measurements before attempting to store them in a @@ -15,28 +16,24 @@ *

This class is internal and is hence not for public use. Its APIs are unstable and can change * at any time. */ -public interface ExemplarFilter { - /** Returns whether or not a reservoir should attempt to filter a measurement. */ - boolean shouldSampleMeasurement(long value, Attributes attributes, Context context); - - /** Returns whether or not a reservoir should attempt to filter a measurement. */ - boolean shouldSampleMeasurement(double value, Attributes attributes, Context context); +public interface ExemplarFilterInternal extends ExemplarFilter { /** - * A filter that only accepts measurements where there is a {@code Span} in {@link Context} that - * is being sampled. + * Utility for casting {@link ExemplarFilter} to {@link ExemplarFilterInternal}, throwing if + * {@code filter} does not implement {@link ExemplarFilterInternal}. */ - static ExemplarFilter traceBased() { - return TraceBasedExemplarFilter.INSTANCE; + static ExemplarFilterInternal asExemplarFilterInternal(ExemplarFilter filter) { + if (!(filter instanceof ExemplarFilterInternal)) { + throw new IllegalArgumentException( + "Custom ExemplarFilter implementations are currently not supported. " + + "Use one of the standard implementations returned by the static factories in the ExemplarFilter class."); + } + return (ExemplarFilterInternal) filter; } - /** A filter which makes all measurements eligible for being an exemplar. */ - static ExemplarFilter alwaysOn() { - return AlwaysOnExemplarFilter.INSTANCE; - } + /** Returns whether or not a reservoir should attempt to filter a measurement. */ + boolean shouldSampleMeasurement(long value, Attributes attributes, Context context); - /** A filter which makes no measurements eligible for being an exemplar. */ - static ExemplarFilter alwaysOff() { - return AlwaysOffExemplarFilter.INSTANCE; - } + /** Returns whether or not a reservoir should attempt to filter a measurement. */ + boolean shouldSampleMeasurement(double value, Attributes attributes, Context context); } diff --git a/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/exemplar/ExemplarReservoirFactory.java b/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/exemplar/ExemplarReservoirFactory.java index b44f08b7746..2c6b74aa7f7 100644 --- a/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/exemplar/ExemplarReservoirFactory.java +++ b/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/exemplar/ExemplarReservoirFactory.java @@ -24,7 +24,7 @@ public interface ExemplarReservoirFactory { * pre-filter. */ static ExemplarReservoirFactory filtered( - ExemplarFilter filter, ExemplarReservoirFactory original) { + ExemplarFilterInternal filter, ExemplarReservoirFactory original) { return new ExemplarReservoirFactory() { @Override public DoubleExemplarReservoir createDoubleExemplarReservoir() { diff --git a/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/exemplar/LongFilteredExemplarReservoir.java b/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/exemplar/LongFilteredExemplarReservoir.java index 1cd2024674d..db7a8291687 100644 --- a/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/exemplar/LongFilteredExemplarReservoir.java +++ b/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/exemplar/LongFilteredExemplarReservoir.java @@ -12,10 +12,10 @@ /** A reservoir that has a pre-filter on measurements. */ class LongFilteredExemplarReservoir implements LongExemplarReservoir { - private final ExemplarFilter filter; + private final ExemplarFilterInternal filter; private final LongExemplarReservoir reservoir; - LongFilteredExemplarReservoir(ExemplarFilter filter, LongExemplarReservoir reservoir) { + LongFilteredExemplarReservoir(ExemplarFilterInternal filter, LongExemplarReservoir reservoir) { this.filter = filter; this.reservoir = reservoir; } diff --git a/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/exemplar/TraceBasedExemplarFilter.java b/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/exemplar/TraceBasedExemplarFilter.java index 2adfea79bb5..c172548de33 100644 --- a/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/exemplar/TraceBasedExemplarFilter.java +++ b/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/exemplar/TraceBasedExemplarFilter.java @@ -15,12 +15,16 @@ *

This class is internal and is hence not for public use. Its APIs are unstable and can change * at any time. */ -public final class TraceBasedExemplarFilter implements ExemplarFilter { +public final class TraceBasedExemplarFilter implements ExemplarFilterInternal { - static final ExemplarFilter INSTANCE = new TraceBasedExemplarFilter(); + private static final ExemplarFilterInternal INSTANCE = new TraceBasedExemplarFilter(); private TraceBasedExemplarFilter() {} + public static ExemplarFilterInternal getInstance() { + return INSTANCE; + } + @Override public boolean shouldSampleMeasurement(long value, Attributes attributes, Context context) { return hasSampledTrace(context); diff --git a/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/state/AsynchronousMetricStorage.java b/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/state/AsynchronousMetricStorage.java index 44a7a0ffe25..ee54e79ecd5 100644 --- a/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/state/AsynchronousMetricStorage.java +++ b/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/state/AsynchronousMetricStorage.java @@ -14,6 +14,7 @@ import io.opentelemetry.sdk.common.InstrumentationScopeInfo; import io.opentelemetry.sdk.common.export.MemoryMode; import io.opentelemetry.sdk.internal.ThrottlingLogger; +import io.opentelemetry.sdk.metrics.ExemplarFilter; import io.opentelemetry.sdk.metrics.View; import io.opentelemetry.sdk.metrics.data.AggregationTemporality; import io.opentelemetry.sdk.metrics.data.MetricData; @@ -24,7 +25,7 @@ import io.opentelemetry.sdk.metrics.internal.aggregator.EmptyMetricData; import io.opentelemetry.sdk.metrics.internal.descriptor.InstrumentDescriptor; import io.opentelemetry.sdk.metrics.internal.descriptor.MetricDescriptor; -import io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarFilter; +import io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarFilterInternal; import io.opentelemetry.sdk.metrics.internal.export.RegisteredReader; import io.opentelemetry.sdk.metrics.internal.view.AttributesProcessor; import io.opentelemetry.sdk.metrics.internal.view.RegisteredView; @@ -136,7 +137,7 @@ public static AsynchronousMetricStorage create( ((AggregatorFactory) view.getAggregation()) .createAggregator( instrumentDescriptor, - ExemplarFilter.alwaysOff(), + ExemplarFilterInternal.asExemplarFilterInternal(ExemplarFilter.alwaysOff()), registeredReader.getReader().getMemoryMode()); return new AsynchronousMetricStorage<>( registeredReader, diff --git a/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/state/MeterProviderSharedState.java b/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/state/MeterProviderSharedState.java index aaf932d9202..1e42b854463 100644 --- a/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/state/MeterProviderSharedState.java +++ b/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/state/MeterProviderSharedState.java @@ -8,7 +8,7 @@ import com.google.auto.value.AutoValue; import io.opentelemetry.sdk.common.Clock; import io.opentelemetry.sdk.metrics.SdkMeterProvider; -import io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarFilter; +import io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarFilterInternal; import io.opentelemetry.sdk.resources.Resource; import javax.annotation.concurrent.Immutable; @@ -23,7 +23,7 @@ public abstract class MeterProviderSharedState { public static MeterProviderSharedState create( - Clock clock, Resource resource, ExemplarFilter exemplarFilter, long startEpochNanos) { + Clock clock, Resource resource, ExemplarFilterInternal exemplarFilter, long startEpochNanos) { MeterProviderSharedState sharedState = new AutoValue_MeterProviderSharedState(clock, resource, startEpochNanos, exemplarFilter); return sharedState; @@ -40,6 +40,6 @@ public static MeterProviderSharedState create( /** Returns the timestamp when the {@link SdkMeterProvider} was started, in epoch nanos. */ public abstract long getStartEpochNanos(); - /** Returns the {@link ExemplarFilter} for remembering synchronous measurements. */ - public abstract ExemplarFilter getExemplarFilter(); + /** Returns the {@link ExemplarFilterInternal} for remembering synchronous measurements. */ + public abstract ExemplarFilterInternal getExemplarFilter(); } diff --git a/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/state/SynchronousMetricStorage.java b/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/state/SynchronousMetricStorage.java index bc9d8f60610..9df16e17911 100644 --- a/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/state/SynchronousMetricStorage.java +++ b/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/state/SynchronousMetricStorage.java @@ -12,7 +12,7 @@ import io.opentelemetry.sdk.metrics.internal.aggregator.AggregatorFactory; import io.opentelemetry.sdk.metrics.internal.descriptor.InstrumentDescriptor; import io.opentelemetry.sdk.metrics.internal.descriptor.MetricDescriptor; -import io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarFilter; +import io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarFilterInternal; import io.opentelemetry.sdk.metrics.internal.export.RegisteredReader; import io.opentelemetry.sdk.metrics.internal.view.RegisteredView; @@ -39,7 +39,7 @@ static SynchronousMetricStorage create( RegisteredReader registeredReader, RegisteredView registeredView, InstrumentDescriptor instrumentDescriptor, - ExemplarFilter exemplarFilter, + ExemplarFilterInternal exemplarFilter, boolean enabled) { View view = registeredView.getView(); MetricDescriptor metricDescriptor = diff --git a/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/view/Base2ExponentialHistogramAggregation.java b/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/view/Base2ExponentialHistogramAggregation.java index b1ada9252e4..870ac9f4d89 100644 --- a/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/view/Base2ExponentialHistogramAggregation.java +++ b/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/view/Base2ExponentialHistogramAggregation.java @@ -17,7 +17,7 @@ import io.opentelemetry.sdk.metrics.internal.aggregator.AggregatorFactory; import io.opentelemetry.sdk.metrics.internal.aggregator.DoubleBase2ExponentialHistogramAggregator; import io.opentelemetry.sdk.metrics.internal.descriptor.InstrumentDescriptor; -import io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarFilter; +import io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarFilterInternal; import io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarReservoirFactory; /** @@ -67,7 +67,7 @@ public static Aggregation create(int maxBuckets, int maxScale) { @SuppressWarnings("unchecked") public Aggregator createAggregator( InstrumentDescriptor instrumentDescriptor, - ExemplarFilter exemplarFilter, + ExemplarFilterInternal exemplarFilter, MemoryMode memoryMode) { return (Aggregator) new DoubleBase2ExponentialHistogramAggregator( diff --git a/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/view/DefaultAggregation.java b/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/view/DefaultAggregation.java index e329ff9425f..182246f2801 100644 --- a/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/view/DefaultAggregation.java +++ b/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/view/DefaultAggregation.java @@ -12,7 +12,7 @@ import io.opentelemetry.sdk.metrics.internal.aggregator.Aggregator; import io.opentelemetry.sdk.metrics.internal.aggregator.AggregatorFactory; import io.opentelemetry.sdk.metrics.internal.descriptor.InstrumentDescriptor; -import io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarFilter; +import io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarFilterInternal; import java.util.logging.Level; import java.util.logging.Logger; @@ -59,7 +59,7 @@ private static Aggregation resolve(InstrumentDescriptor instrument, boolean with @Override public Aggregator createAggregator( InstrumentDescriptor instrumentDescriptor, - ExemplarFilter exemplarFilter, + ExemplarFilterInternal exemplarFilter, MemoryMode memoryMode) { return ((AggregatorFactory) resolve(instrumentDescriptor, /* withAdvice= */ true)) .createAggregator(instrumentDescriptor, exemplarFilter, memoryMode); diff --git a/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/view/DropAggregation.java b/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/view/DropAggregation.java index 38db4acd381..592c74f013a 100644 --- a/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/view/DropAggregation.java +++ b/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/view/DropAggregation.java @@ -11,7 +11,7 @@ import io.opentelemetry.sdk.metrics.internal.aggregator.Aggregator; import io.opentelemetry.sdk.metrics.internal.aggregator.AggregatorFactory; import io.opentelemetry.sdk.metrics.internal.descriptor.InstrumentDescriptor; -import io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarFilter; +import io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarFilterInternal; /** * Configuration representing no aggregation. @@ -33,7 +33,7 @@ private DropAggregation() {} @SuppressWarnings("unchecked") public Aggregator createAggregator( InstrumentDescriptor instrumentDescriptor, - ExemplarFilter exemplarFilter, + ExemplarFilterInternal exemplarFilter, MemoryMode memoryMode) { return (Aggregator) Aggregator.drop(); } diff --git a/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/view/ExplicitBucketHistogramAggregation.java b/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/view/ExplicitBucketHistogramAggregation.java index 40c0dbabc8d..d4af55fd0ad 100644 --- a/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/view/ExplicitBucketHistogramAggregation.java +++ b/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/view/ExplicitBucketHistogramAggregation.java @@ -14,7 +14,7 @@ import io.opentelemetry.sdk.metrics.internal.aggregator.DoubleExplicitBucketHistogramAggregator; import io.opentelemetry.sdk.metrics.internal.aggregator.ExplicitBucketHistogramUtils; import io.opentelemetry.sdk.metrics.internal.descriptor.InstrumentDescriptor; -import io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarFilter; +import io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarFilterInternal; import io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarReservoirFactory; import java.util.List; @@ -51,7 +51,7 @@ private ExplicitBucketHistogramAggregation(List bucketBoundaries) { @SuppressWarnings("unchecked") public Aggregator createAggregator( InstrumentDescriptor instrumentDescriptor, - ExemplarFilter exemplarFilter, + ExemplarFilterInternal exemplarFilter, MemoryMode memoryMode) { return (Aggregator) new DoubleExplicitBucketHistogramAggregator( diff --git a/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/view/LastValueAggregation.java b/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/view/LastValueAggregation.java index 5157d846025..ee2a0e98d24 100644 --- a/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/view/LastValueAggregation.java +++ b/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/view/LastValueAggregation.java @@ -16,7 +16,7 @@ import io.opentelemetry.sdk.metrics.internal.aggregator.DoubleLastValueAggregator; import io.opentelemetry.sdk.metrics.internal.aggregator.LongLastValueAggregator; import io.opentelemetry.sdk.metrics.internal.descriptor.InstrumentDescriptor; -import io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarFilter; +import io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarFilterInternal; import io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarReservoirFactory; /** @@ -39,7 +39,7 @@ private LastValueAggregation() {} @SuppressWarnings("unchecked") public Aggregator createAggregator( InstrumentDescriptor instrumentDescriptor, - ExemplarFilter exemplarFilter, + ExemplarFilterInternal exemplarFilter, MemoryMode memoryMode) { ExemplarReservoirFactory reservoirFactory = diff --git a/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/view/SumAggregation.java b/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/view/SumAggregation.java index 52a24521348..42a003182be 100644 --- a/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/view/SumAggregation.java +++ b/sdk/metrics/src/main/java/io/opentelemetry/sdk/metrics/internal/view/SumAggregation.java @@ -15,7 +15,7 @@ import io.opentelemetry.sdk.metrics.internal.aggregator.DoubleSumAggregator; import io.opentelemetry.sdk.metrics.internal.aggregator.LongSumAggregator; import io.opentelemetry.sdk.metrics.internal.descriptor.InstrumentDescriptor; -import io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarFilter; +import io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarFilterInternal; import io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarReservoirFactory; /** @@ -37,7 +37,7 @@ private SumAggregation() {} @SuppressWarnings("unchecked") public Aggregator createAggregator( InstrumentDescriptor instrumentDescriptor, - ExemplarFilter exemplarFilter, + ExemplarFilterInternal exemplarFilter, MemoryMode memoryMode) { ExemplarReservoirFactory reservoirFactory = ExemplarReservoirFactory.filtered( diff --git a/sdk/metrics/src/test/java/io/opentelemetry/sdk/metrics/InstrumentBuilderTest.java b/sdk/metrics/src/test/java/io/opentelemetry/sdk/metrics/InstrumentBuilderTest.java index de1a351e619..6c54636ee4f 100644 --- a/sdk/metrics/src/test/java/io/opentelemetry/sdk/metrics/InstrumentBuilderTest.java +++ b/sdk/metrics/src/test/java/io/opentelemetry/sdk/metrics/InstrumentBuilderTest.java @@ -5,12 +5,12 @@ package io.opentelemetry.sdk.metrics; +import static io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarFilterInternal.asExemplarFilterInternal; import static org.assertj.core.api.Assertions.assertThat; import io.opentelemetry.sdk.common.InstrumentationScopeInfo; import io.opentelemetry.sdk.metrics.internal.MeterConfig; import io.opentelemetry.sdk.metrics.internal.descriptor.Advice; -import io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarFilter; import io.opentelemetry.sdk.metrics.internal.state.MeterProviderSharedState; import io.opentelemetry.sdk.resources.Resource; import io.opentelemetry.sdk.testing.time.TestClock; @@ -21,7 +21,10 @@ class InstrumentBuilderTest { public static final MeterProviderSharedState PROVIDER_SHARED_STATE = MeterProviderSharedState.create( - TestClock.create(), Resource.getDefault(), ExemplarFilter.alwaysOff(), 0); + TestClock.create(), + Resource.getDefault(), + asExemplarFilterInternal(ExemplarFilter.alwaysOff()), + 0); static final InstrumentationScopeInfo SCOPE = InstrumentationScopeInfo.create("scope-name"); public static final SdkMeter SDK_METER = new SdkMeter( diff --git a/sdk/metrics/src/test/java/io/opentelemetry/sdk/metrics/internal/exemplar/ExemplarFilterTest.java b/sdk/metrics/src/test/java/io/opentelemetry/sdk/metrics/internal/exemplar/ExemplarFilterTest.java index 7232fe9aee3..bbe1d1e365a 100644 --- a/sdk/metrics/src/test/java/io/opentelemetry/sdk/metrics/internal/exemplar/ExemplarFilterTest.java +++ b/sdk/metrics/src/test/java/io/opentelemetry/sdk/metrics/internal/exemplar/ExemplarFilterTest.java @@ -5,8 +5,10 @@ package io.opentelemetry.sdk.metrics.internal.exemplar; +import static io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarFilterInternal.asExemplarFilterInternal; import static org.assertj.core.api.Assertions.as; import static org.assertj.core.api.Assertions.assertThat; +import static org.assertj.core.api.Assertions.assertThatThrownBy; import io.opentelemetry.api.common.Attributes; import io.opentelemetry.api.trace.Span; @@ -14,9 +16,9 @@ import io.opentelemetry.api.trace.TraceFlags; import io.opentelemetry.api.trace.TraceState; import io.opentelemetry.context.Context; +import io.opentelemetry.sdk.metrics.ExemplarFilter; import io.opentelemetry.sdk.metrics.SdkMeterProvider; import io.opentelemetry.sdk.metrics.SdkMeterProviderBuilder; -import io.opentelemetry.sdk.metrics.internal.SdkMeterProviderUtil; import org.assertj.core.api.InstanceOfAssertFactories; import org.junit.jupiter.api.Test; @@ -27,7 +29,7 @@ class ExemplarFilterTest { @Test void alwaysOff_NeverReturnsTrue() { assertThat( - ExemplarFilter.alwaysOff() + asExemplarFilterInternal(ExemplarFilter.alwaysOff()) .shouldSampleMeasurement(1, Attributes.empty(), Context.root())) .isFalse(); } @@ -35,7 +37,7 @@ void alwaysOff_NeverReturnsTrue() { @Test void alwaysOn_AlwaysReturnsTrue() { assertThat( - ExemplarFilter.alwaysOn() + asExemplarFilterInternal(ExemplarFilter.alwaysOn()) .shouldSampleMeasurement(1, Attributes.empty(), Context.root())) .isTrue(); } @@ -43,7 +45,7 @@ void alwaysOn_AlwaysReturnsTrue() { @Test void withSampledTrace_ReturnsFalseOnNoContext() { assertThat( - ExemplarFilter.traceBased() + asExemplarFilterInternal(ExemplarFilter.traceBased()) .shouldSampleMeasurement(1, Attributes.empty(), Context.root())) .isFalse(); } @@ -56,7 +58,9 @@ void traceBased_sampleWithTrace() { Span.wrap( SpanContext.createFromRemoteParent( TRACE_ID, SPAN_ID, TraceFlags.getSampled(), TraceState.getDefault()))); - assertThat(ExemplarFilter.traceBased().shouldSampleMeasurement(1, Attributes.empty(), context)) + assertThat( + asExemplarFilterInternal(ExemplarFilter.traceBased()) + .shouldSampleMeasurement(1, Attributes.empty(), context)) .isTrue(); } @@ -68,19 +72,34 @@ void traceBased_notSampleUnsampledTrace() { Span.wrap( SpanContext.createFromRemoteParent( TRACE_ID, SPAN_ID, TraceFlags.getDefault(), TraceState.getDefault()))); - assertThat(ExemplarFilter.traceBased().shouldSampleMeasurement(1, Attributes.empty(), context)) + assertThat( + asExemplarFilterInternal(ExemplarFilter.traceBased()) + .shouldSampleMeasurement(1, Attributes.empty(), context)) .isFalse(); } @Test void setExemplarFilter() { - SdkMeterProviderBuilder builder = SdkMeterProvider.builder(); - SdkMeterProviderUtil.setExemplarFilter(builder, ExemplarFilter.alwaysOn()); + SdkMeterProviderBuilder builder = + SdkMeterProvider.builder().setExemplarFilter(ExemplarFilter.alwaysOn()); assertThat(builder) - .extracting("exemplarFilter", as(InstanceOfAssertFactories.type(ExemplarFilter.class))) + .extracting( + "exemplarFilter", as(InstanceOfAssertFactories.type(ExemplarFilterInternal.class))) .isEqualTo(ExemplarFilter.alwaysOn()); } + @Test + void asExemplarFilterInternal_Valid() { + assertThat(asExemplarFilterInternal(ExemplarFilter.traceBased())) + .isSameAs(ExemplarFilter.traceBased()); + assertThat(asExemplarFilterInternal(ExemplarFilter.alwaysOff())) + .isSameAs(ExemplarFilter.alwaysOff()); + assertThat(asExemplarFilterInternal(ExemplarFilter.alwaysOn())) + .isSameAs(ExemplarFilter.alwaysOn()); + assertThatThrownBy(() -> asExemplarFilterInternal(new ExemplarFilter() {})) + .isInstanceOf(IllegalArgumentException.class); + } + @Test void alwaysOff_toString() { assertThat(ExemplarFilter.alwaysOff().toString()).isEqualTo("AlwaysOffExemplarFilter"); diff --git a/sdk/metrics/src/test/java/io/opentelemetry/sdk/metrics/internal/exemplar/FilteredExemplarReservoirTest.java b/sdk/metrics/src/test/java/io/opentelemetry/sdk/metrics/internal/exemplar/FilteredExemplarReservoirTest.java index 7e4262981f3..1abc9e73cd4 100644 --- a/sdk/metrics/src/test/java/io/opentelemetry/sdk/metrics/internal/exemplar/FilteredExemplarReservoirTest.java +++ b/sdk/metrics/src/test/java/io/opentelemetry/sdk/metrics/internal/exemplar/FilteredExemplarReservoirTest.java @@ -25,7 +25,7 @@ class FilteredExemplarReservoirTest { @Mock DoubleExemplarReservoir doubleReservoir; @Mock LongExemplarReservoir longReservoir; - @Mock ExemplarFilter filter; + @Mock ExemplarFilterInternal filter; @Test void testFilterDouble_preventsSampling() { diff --git a/sdk/metrics/src/test/java/io/opentelemetry/sdk/metrics/internal/state/SynchronousMetricStorageTest.java b/sdk/metrics/src/test/java/io/opentelemetry/sdk/metrics/internal/state/SynchronousMetricStorageTest.java index e79f3ad9718..a3175578d77 100644 --- a/sdk/metrics/src/test/java/io/opentelemetry/sdk/metrics/internal/state/SynchronousMetricStorageTest.java +++ b/sdk/metrics/src/test/java/io/opentelemetry/sdk/metrics/internal/state/SynchronousMetricStorageTest.java @@ -6,6 +6,7 @@ package io.opentelemetry.sdk.metrics.internal.state; import static io.opentelemetry.sdk.common.export.MemoryMode.IMMUTABLE_DATA; +import static io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarFilterInternal.asExemplarFilterInternal; import static io.opentelemetry.sdk.testing.assertj.OpenTelemetryAssertions.assertThat; import static io.opentelemetry.sdk.testing.assertj.OpenTelemetryAssertions.attributeEntry; import static org.mockito.Mockito.never; @@ -23,6 +24,7 @@ import io.opentelemetry.sdk.common.InstrumentationScopeInfo; import io.opentelemetry.sdk.common.export.MemoryMode; import io.opentelemetry.sdk.metrics.Aggregation; +import io.opentelemetry.sdk.metrics.ExemplarFilter; import io.opentelemetry.sdk.metrics.InstrumentType; import io.opentelemetry.sdk.metrics.InstrumentValueType; import io.opentelemetry.sdk.metrics.data.AggregationTemporality; @@ -35,7 +37,6 @@ import io.opentelemetry.sdk.metrics.internal.descriptor.Advice; import io.opentelemetry.sdk.metrics.internal.descriptor.InstrumentDescriptor; import io.opentelemetry.sdk.metrics.internal.descriptor.MetricDescriptor; -import io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarFilter; import io.opentelemetry.sdk.metrics.internal.export.RegisteredReader; import io.opentelemetry.sdk.metrics.internal.view.AttributesProcessor; import io.opentelemetry.sdk.metrics.internal.view.ViewRegistry; @@ -102,7 +103,8 @@ private void initialize(MemoryMode memoryMode) { aggregator = spy( ((AggregatorFactory) Aggregation.sum()) - .createAggregator(DESCRIPTOR, ExemplarFilter.alwaysOff(), memoryMode)); + .createAggregator( + DESCRIPTOR, asExemplarFilterInternal(ExemplarFilter.alwaysOff()), memoryMode)); } @ParameterizedTest @@ -826,7 +828,8 @@ private static Stream concurrentStressTestArguments() { for (MemoryMode memoryMode : MemoryMode.values()) { Aggregator aggregator = ((AggregatorFactory) Aggregation.sum()) - .createAggregator(DESCRIPTOR, ExemplarFilter.alwaysOff(), memoryMode); + .createAggregator( + DESCRIPTOR, asExemplarFilterInternal(ExemplarFilter.alwaysOff()), memoryMode); argumentsList.add( Arguments.of( diff --git a/sdk/metrics/src/test/java/io/opentelemetry/sdk/metrics/internal/view/Base2ExponentialHistogramAggregationTest.java b/sdk/metrics/src/test/java/io/opentelemetry/sdk/metrics/internal/view/Base2ExponentialHistogramAggregationTest.java index 57e096e01c1..ee10e75d679 100644 --- a/sdk/metrics/src/test/java/io/opentelemetry/sdk/metrics/internal/view/Base2ExponentialHistogramAggregationTest.java +++ b/sdk/metrics/src/test/java/io/opentelemetry/sdk/metrics/internal/view/Base2ExponentialHistogramAggregationTest.java @@ -5,6 +5,7 @@ package io.opentelemetry.sdk.metrics.internal.view; +import static io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarFilterInternal.asExemplarFilterInternal; import static org.assertj.core.api.Assertions.assertThat; import static org.assertj.core.api.Assertions.assertThatThrownBy; @@ -12,6 +13,7 @@ import io.opentelemetry.context.Context; import io.opentelemetry.sdk.common.export.MemoryMode; import io.opentelemetry.sdk.metrics.Aggregation; +import io.opentelemetry.sdk.metrics.ExemplarFilter; import io.opentelemetry.sdk.metrics.InstrumentType; import io.opentelemetry.sdk.metrics.InstrumentValueType; import io.opentelemetry.sdk.metrics.data.ExponentialHistogramPointData; @@ -20,7 +22,6 @@ import io.opentelemetry.sdk.metrics.internal.aggregator.AggregatorHandle; import io.opentelemetry.sdk.metrics.internal.descriptor.Advice; import io.opentelemetry.sdk.metrics.internal.descriptor.InstrumentDescriptor; -import io.opentelemetry.sdk.metrics.internal.exemplar.ExemplarFilter; import org.junit.jupiter.api.Test; class Base2ExponentialHistogramAggregationTest { @@ -57,7 +58,7 @@ void minimumBucketsCanAccommodateMaxRange() { InstrumentType.HISTOGRAM, InstrumentValueType.DOUBLE, Advice.empty()), - ExemplarFilter.alwaysOff(), + asExemplarFilterInternal(ExemplarFilter.alwaysOff()), MemoryMode.IMMUTABLE_DATA); AggregatorHandle handle = aggregator.createHandle(); // Record max range