77
88import static io .opentelemetry .sdk .testing .assertj .OpenTelemetryAssertions .assertThat ;
99import static org .assertj .core .groups .Tuple .tuple ;
10+ import static org .junit .jupiter .params .ParameterizedInvocationConstants .ARGUMENTS_PLACEHOLDER ;
1011
1112import io .opentelemetry .api .common .AttributeKey ;
1213import io .opentelemetry .api .common .Attributes ;
1718import io .opentelemetry .sdk .metrics .data .PointData ;
1819import io .opentelemetry .sdk .testing .exporter .InMemoryMetricReader ;
1920import java .util .ArrayList ;
21+ import java .util .Arrays ;
2022import java .util .Collection ;
2123import java .util .Collections ;
2224import java .util .List ;
3133import org .junit .jupiter .api .AfterEach ;
3234import org .junit .jupiter .api .BeforeAll ;
3335import org .junit .jupiter .api .BeforeEach ;
34- import org .junit .jupiter .api .Test ;
36+ import org .junit .jupiter .params .ParameterizedTest ;
37+ import org .junit .jupiter .params .provider .MethodSource ;
3538
3639public class MetricAggregationTest {
3740
@@ -116,39 +119,61 @@ private static ObjectName getObjectName(@Nullable String a, @Nullable String b)
116119 }
117120 }
118121
119- @ Test
120- void singleInstance () throws Exception {
122+ static List <MetricInfo .Type > metricTypes () {
123+ return Arrays .asList (
124+ MetricInfo .Type .COUNTER , MetricInfo .Type .UPDOWNCOUNTER , MetricInfo .Type .GAUGE );
125+ }
126+
127+ @ ParameterizedTest (name = ARGUMENTS_PLACEHOLDER )
128+ @ MethodSource ("metricTypes" )
129+ void singleInstance (MetricInfo .Type metricType ) throws Exception {
121130 ObjectName bean = getObjectName (null , null );
122131 theServer .registerMBean (new Hello (42 ), bean );
123132
124- Collection <MetricData > data = testMetric (bean .toString (), Collections .emptyList ());
125- checkSingleValue (data , 42 );
133+ Collection <MetricData > data = testMetric (bean .toString (), Collections .emptyList (), metricType );
134+ checkSingleValue (data , 42 , metricType );
126135 }
127136
128- @ Test
129- void aggregateOneParam () throws Exception {
137+ @ ParameterizedTest (name = ARGUMENTS_PLACEHOLDER )
138+ @ MethodSource ("metricTypes" )
139+ void aggregateOneParam (MetricInfo .Type metricType ) throws Exception {
130140 theServer .registerMBean (new Hello (42 ), getObjectName ("value1" , null ));
131141 theServer .registerMBean (new Hello (37 ), getObjectName ("value2" , null ));
132142
133143 String bean = getObjectName ("*" , null ).toString ();
134- Collection <MetricData > data = testMetric (bean , Collections .emptyList ());
135- checkSingleValue (data , 79 );
144+ Collection <MetricData > data = testMetric (bean , Collections .emptyList (), metricType );
145+ int expected = 79 ;
146+ if (metricType == MetricInfo .Type .GAUGE ) {
147+ // last-value aggregation produces unpredictable result unless a single mbean instance is used
148+ // test here is only used as a way to document behavior and should not be considered a feature
149+ expected = 37 ;
150+ }
151+ checkSingleValue (data , expected , metricType );
136152 }
137153
138- @ Test
139- void aggregateMultipleParams () throws Exception {
154+ @ ParameterizedTest (name = ARGUMENTS_PLACEHOLDER )
155+ @ MethodSource ("metricTypes" )
156+ void aggregateMultipleParams (MetricInfo .Type metricType ) throws Exception {
140157 theServer .registerMBean (new Hello (1 ), getObjectName ("1" , "x" ));
141158 theServer .registerMBean (new Hello (2 ), getObjectName ("2" , "y" ));
142159 theServer .registerMBean (new Hello (3 ), getObjectName ("3" , "x" ));
143160 theServer .registerMBean (new Hello (4 ), getObjectName ("4" , "y" ));
144161
145162 String bean = getObjectName ("*" , "*" ).toString ();
146- Collection <MetricData > data = testMetric (bean , Collections .emptyList ());
147- checkSingleValue (data , 10 );
163+ Collection <MetricData > data = testMetric (bean , Collections .emptyList (), metricType );
164+
165+ int expected = 10 ;
166+ if (metricType == MetricInfo .Type .GAUGE ) {
167+ // last-value aggregation produces unpredictable result unless a single mbean instance is used
168+ // test here is only used as a way to document behavior and should not be considered a feature
169+ expected = 1 ;
170+ }
171+ checkSingleValue (data , expected , metricType );
148172 }
149173
150- @ Test
151- void partialAggregateMultipleParams () throws Exception {
174+ @ ParameterizedTest (name = ARGUMENTS_PLACEHOLDER )
175+ @ MethodSource ("metricTypes" )
176+ void partialAggregateMultipleParams (MetricInfo .Type metricType ) throws Exception {
152177 theServer .registerMBean (new Hello (1 ), getObjectName ("1" , "x" ));
153178 theServer .registerMBean (new Hello (2 ), getObjectName ("2" , "y" ));
154179 theServer .registerMBean (new Hello (3 ), getObjectName ("3" , "x" ));
@@ -160,30 +185,44 @@ void partialAggregateMultipleParams() throws Exception {
160185 Collections .singletonList (
161186 new MetricAttribute (
162187 "test.metric.param" , MetricAttributeExtractor .fromObjectNameParameter ("b" )));
163- Collection <MetricData > data = testMetric (bean , attributes );
188+ Collection <MetricData > data = testMetric (bean , attributes , metricType );
164189
165190 assertThat (data )
166191 .isNotEmpty ()
167192 .satisfiesExactly (
168193 metric -> {
169194 assertThat (metric .getName ()).isEqualTo ("test.metric" );
170195 AttributeKey <String > metricAttribute = AttributeKey .stringKey ("test.metric.param" );
171- assertThat (metric .getLongSumData ().getPoints ())
172- .extracting (LongPointData ::getValue , PointData ::getAttributes )
173- .containsExactlyInAnyOrder (
174- tuple (6L , Attributes .of (metricAttribute , "y" )),
175- tuple (4L , Attributes .of (metricAttribute , "x" )));
196+
197+ if (metricType == MetricInfo .Type .GAUGE ) {
198+ // last-value aggregation produces unpredictable result unless a single mbean
199+ // instance is used
200+ // test here is only used as a way to document behavior and should not be considered
201+ // a feature
202+ assertThat (metric .getLongGaugeData ().getPoints ())
203+ .extracting (LongPointData ::getValue , PointData ::getAttributes )
204+ .containsExactlyInAnyOrder (
205+ tuple (4L , Attributes .of (metricAttribute , "y" )),
206+ tuple (1L , Attributes .of (metricAttribute , "x" )));
207+ } else {
208+ // sum aggregation
209+ assertThat (metric .getLongSumData ().getPoints ())
210+ .extracting (LongPointData ::getValue , PointData ::getAttributes )
211+ .containsExactlyInAnyOrder (
212+ tuple (6L , Attributes .of (metricAttribute , "y" )),
213+ tuple (4L , Attributes .of (metricAttribute , "x" )));
214+ }
176215 });
177216 }
178217
179- private Collection <MetricData > testMetric (String mbean , List <MetricAttribute > attributes )
218+ private Collection <MetricData > testMetric (
219+ String mbean , List <MetricAttribute > attributes , MetricInfo .Type metricType )
180220 throws MalformedObjectNameException {
181221 JmxMetricInsight metricInsight = JmxMetricInsight .createService (sdk , 0 );
182222 MetricConfiguration metricConfiguration = new MetricConfiguration ();
183223 List <MetricExtractor > extractors = new ArrayList <>();
184224
185- MetricInfo metricInfo =
186- new MetricInfo ("test.metric" , "description" , null , "1" , MetricInfo .Type .COUNTER );
225+ MetricInfo metricInfo = new MetricInfo ("test.metric" , "description" , null , "1" , metricType );
187226 BeanAttributeExtractor beanExtractor = BeanAttributeExtractor .fromName ("Value" );
188227 MetricExtractor extractor = new MetricExtractor (beanExtractor , metricInfo , attributes );
189228 extractors .add (extractor );
@@ -196,13 +235,21 @@ private Collection<MetricData> testMetric(String mbean, List<MetricAttribute> at
196235 return waitMetricsReceived ();
197236 }
198237
199- private static void checkSingleValue (Collection <MetricData > data , long expectedValue ) {
238+ private static void checkSingleValue (
239+ Collection <MetricData > data , long expectedValue , MetricInfo .Type metricType ) {
200240 assertThat (data )
201241 .isNotEmpty ()
202242 .satisfiesExactlyInAnyOrder (
203243 metric -> {
204244 assertThat (metric .getName ()).isEqualTo ("test.metric" );
205- assertThat (metric .getLongSumData ().getPoints ())
245+
246+ Collection <LongPointData > points ;
247+ if (metricType == MetricInfo .Type .GAUGE ) {
248+ points = metric .getLongGaugeData ().getPoints ();
249+ } else {
250+ points = metric .getLongSumData ().getPoints ();
251+ }
252+ assertThat (points )
206253 .extracting (LongPointData ::getValue , PointData ::getAttributes )
207254 .containsExactlyInAnyOrder (tuple (expectedValue , Attributes .empty ()));
208255 });
0 commit comments