@@ -287,50 +287,11 @@ public void testGlobalMetrics() {
287287 conf ));
288288 }
289289
290- private static AggregatedMetric aggSum (double sum ) {
291- return new AggregatedMetric ("" , Double .NaN , Double .NaN , Double .NaN , sum , Double .NaN );
292- }
293-
294- private static AggregatedMetric aggAvg (double avg ) {
295- return new AggregatedMetric ("" , Double .NaN , Double .NaN , avg , Double .NaN , Double .NaN );
296- }
297-
298- private static double computeNonSourceObservedTpr (
299- double busyAvg ,
300- double bpAvg ,
301- double inputRatePerSecSum ,
302- Configuration conf ,
303- double prevTpr ) {
304- var source = new JobVertexID ();
305- var sink = new JobVertexID ();
306- var topology =
307- new JobTopology (
308- new VertexInfo (
309- source , Collections .emptyMap (), 1 , 1 , new IOMetrics (0 , 0 , 0 )),
310- new VertexInfo (
311- sink , Map .of (source , REBALANCE ), 1 , 1 , new IOMetrics (0 , 0 , 0 )));
312-
313- Map <ScalingMetric , Double > scalingMetrics = new HashMap <>();
314- var flinkMetrics = new HashMap <FlinkMetric , AggregatedMetric >();
315- flinkMetrics .put (FlinkMetric .BUSY_TIME_PER_SEC , aggAvg (busyAvg ));
316- if (!Double .isNaN (bpAvg )) {
317- flinkMetrics .put (FlinkMetric .BACKPRESSURE_TIME_PER_SEC , aggAvg (bpAvg ));
318- }
319- if (!Double .isNaN (inputRatePerSecSum )) {
320- flinkMetrics .put (FlinkMetric .NUM_RECORDS_IN_PER_SEC , aggSum (inputRatePerSecSum ));
321- }
322- ScalingMetrics .computeDataRateMetrics (
323- sink , flinkMetrics , scalingMetrics , topology , conf , () -> prevTpr );
324- return scalingMetrics .getOrDefault (ScalingMetric .OBSERVED_TPR , Double .NaN );
325- }
326-
327290 @ Test
328291 public void testNonSourceObservedTprDisabledByDefault () {
329- // Even with all required metrics present and the vertex fully engaged,
330- // OBSERVED_TPR must NOT be populated for non-sources unless the flag is on.
331- var conf = new Configuration ();
332- // Flag intentionally NOT set -> default false.
333- double tpr = computeNonSourceObservedTpr (900. , 100. , 1000. , conf , Double .NaN );
292+ double tpr =
293+ computeNonSourceObservedTpr (900. , 100. , 1000. , new Configuration (), Double .NaN );
294+
334295 assertTrue (Double .isNaN (tpr ));
335296 }
336297
@@ -339,25 +300,12 @@ public void testNonSourceObservedTprEnabled() {
339300 var conf = new Configuration ();
340301 conf .set (AutoScalerOptions .OBSERVED_TRUE_PROCESSING_RATE_NON_SOURCE_ENABLED , true );
341302
342- // Fully engaged (busy 900 + bp 100 = 1000ms/s) and 200ms/s backpressure.
343- // Wait — set bp=200 so it's clearly above zero and the formula is exercised.
344- // engagement = (busy + bp)/1000 = (700+200)/1000 = 0.9 -> below default 0.95 -> NaN
345303 assertTrue (Double .isNaN (computeNonSourceObservedTpr (700. , 200. , 1000. , conf , Double .NaN )));
346-
347- // engagement = (800+200)/1000 = 1.0 >= 0.95 -> compute
348- // observedTpr = rate / (1 - bp/1000) = 1000 / 0.8 = 1250
349304 assertEquals (1000. / 0.8 , computeNonSourceObservedTpr (800. , 200. , 1000. , conf , Double .NaN ));
350-
351- // Zero input rate while engaged -> POSITIVE_INFINITY (mirrors source behavior).
352305 assertEquals (
353306 Double .POSITIVE_INFINITY ,
354307 computeNonSourceObservedTpr (950. , 50. , 0. , conf , Double .NaN ));
355-
356- // Backpressure >= 1000ms/s -> formula degenerates -> fallback supplier (null here)
357- // is returned only if non-NaN, otherwise OBSERVED_TPR is not set.
358308 assertTrue (Double .isNaN (computeNonSourceObservedTpr (0. , 1000. , 1000. , conf , Double .NaN )));
359-
360- // Below engagement threshold -> fallback to historical observedTprAvg (PREV_TPR).
361309 assertEquals (PREV_TPR , computeNonSourceObservedTpr (100. , 100. , 1000. , conf , PREV_TPR ));
362310 }
363311
@@ -369,11 +317,8 @@ public void testNonSourceObservedTprCustomEngagementThreshold() {
369317 AutoScalerOptions .OBSERVED_TRUE_PROCESSING_RATE_NON_SOURCE_ENGAGEMENT_THRESHOLD ,
370318 0.5 );
371319
372- // engagement = 0.6 >= 0.5 -> compute
373320 assertEquals (
374321 500. / (1 - 0.1 ), computeNonSourceObservedTpr (500. , 100. , 500. , conf , Double .NaN ));
375-
376- // engagement = 0.4 < 0.5 -> NaN
377322 assertTrue (Double .isNaN (computeNonSourceObservedTpr (300. , 100. , 500. , conf , Double .NaN )));
378323 }
379324
@@ -382,21 +327,56 @@ public void testNonSourceObservedTprMissingMetricsAreSilentlySkipped() {
382327 var conf = new Configuration ();
383328 conf .set (AutoScalerOptions .OBSERVED_TRUE_PROCESSING_RATE_NON_SOURCE_ENABLED , true );
384329
385- // No backpressure metric available (e.g. older Flink / metric not requested) -> NaN
386330 assertTrue (
387331 Double .isNaN (
388332 computeNonSourceObservedTpr (900. , Double .NaN , 1000. , conf , Double .NaN )));
389- // No input rate metric available -> NaN
390333 assertTrue (
391334 Double .isNaN (
392335 computeNonSourceObservedTpr (900. , 100. , Double .NaN , conf , Double .NaN )));
393336 }
394337
338+ private static AggregatedMetric aggSum (double sum ) {
339+ return new AggregatedMetric ("" , Double .NaN , Double .NaN , Double .NaN , sum , Double .NaN );
340+ }
341+
342+ private static AggregatedMetric aggAvg (double avg ) {
343+ return new AggregatedMetric ("" , Double .NaN , Double .NaN , avg , Double .NaN , Double .NaN );
344+ }
345+
395346 private static AggregatedMetric aggMax (double max ) {
396347 return new AggregatedMetric ("" , Double .NaN , max , Double .NaN , Double .NaN , Double .NaN );
397348 }
398349
399350 private static AggregatedMetric aggAvgMax (double avg , double max ) {
400351 return new AggregatedMetric ("" , Double .NaN , max , avg , Double .NaN , Double .NaN );
401352 }
353+
354+ private static double computeNonSourceObservedTpr (
355+ double busyAvg ,
356+ double bpAvg ,
357+ double inputRatePerSecSum ,
358+ Configuration conf ,
359+ double prevTpr ) {
360+ var source = new JobVertexID ();
361+ var sink = new JobVertexID ();
362+ var topology =
363+ new JobTopology (
364+ new VertexInfo (
365+ source , Collections .emptyMap (), 1 , 1 , new IOMetrics (0 , 0 , 0 )),
366+ new VertexInfo (
367+ sink , Map .of (source , REBALANCE ), 1 , 1 , new IOMetrics (0 , 0 , 0 )));
368+
369+ Map <ScalingMetric , Double > scalingMetrics = new HashMap <>();
370+ var flinkMetrics = new HashMap <FlinkMetric , AggregatedMetric >();
371+ flinkMetrics .put (FlinkMetric .BUSY_TIME_PER_SEC , aggAvg (busyAvg ));
372+ if (!Double .isNaN (bpAvg )) {
373+ flinkMetrics .put (FlinkMetric .BACKPRESSURE_TIME_PER_SEC , aggAvg (bpAvg ));
374+ }
375+ if (!Double .isNaN (inputRatePerSecSum )) {
376+ flinkMetrics .put (FlinkMetric .NUM_RECORDS_IN_PER_SEC , aggSum (inputRatePerSecSum ));
377+ }
378+ ScalingMetrics .computeDataRateMetrics (
379+ sink , flinkMetrics , scalingMetrics , topology , conf , () -> prevTpr );
380+ return scalingMetrics .getOrDefault (ScalingMetric .OBSERVED_TPR , Double .NaN );
381+ }
402382}
0 commit comments