@@ -42,32 +42,39 @@ public class StatsCollector {
42
42
private static final double BYTES_PER_MB = 1 << 20 ;
43
43
private static final double BYTES_PER_GB = 1 << 30 ;
44
44
45
- // max to 9999.9 (167 min)
45
+ // max to 9999.9 s (167 min)
46
46
private static final DecimalFormat DURATION_FORMAT = new PaddingDecimalFormat ("0.0" , 6 );
47
- // max to 999999.99 (1M msg/s)
47
+ // max to 99.99%
48
+ private static final DecimalFormat PERCENT_FORMAT = new PaddingDecimalFormat ("0.00" , 5 );
49
+ // max to 99999 MiB (100 GiB)
50
+ private static final DecimalFormat MEMORY_FORMAT = new PaddingDecimalFormat ("0" , 5 );
51
+ // max to 999999.99 msg/s (1M msg/s)
48
52
private static final DecimalFormat RATE_FORMAT = new PaddingDecimalFormat ("0.00" , 9 );
49
- // max to 999.99 (1 GB /s)
53
+ // max to 999.99 MiB/s (1 GiB /s)
50
54
private static final DecimalFormat THROUGHPUT_FORMAT = new PaddingDecimalFormat ("0.00" , 6 );
51
- // max to 99999.999 (100 s)
55
+ // max to 99999.999 ms (100 s)
52
56
private static final DecimalFormat LATENCY_FORMAT = new PaddingDecimalFormat ("0.000" , 9 );
57
+ // max to 999.99
53
58
private static final DecimalFormat COUNT_FORMAT = new PaddingDecimalFormat ("0.00" , 6 );
54
59
55
60
private static final String PERIOD_LOG_FORMAT = "{}s" +
61
+ " | CPU {}% | Mem {} MiB heap / {} MiB direct" +
56
62
" | Prod rate {} msg/s / {} MiB/s | Prod err {} err/s" +
57
63
" | Cons rate {} msg/s / {} MiB/s | Backlog: {} K msg" +
58
- " | Prod Latency (ms) avg: {} - 50%: {} - 99%: {} - 99.9%: {} - Max : {}" +
59
- " | E2E Latency (ms) avg: {} - 50%: {} - 99%: {} - 99.9%: {} - Max : {}" ;
64
+ " | Prod Latency (ms) avg: {} - min: {} - 50%: {} - 99%: {} - 99.9%: {} - max : {}" +
65
+ " | E2E Latency (ms) avg: {} - min: {} - 50%: {} - 99%: {} - 99.9%: {} - max : {}" ;
60
66
private static final String SUMMARY_LOG_FORMAT = "Summary" +
61
67
" | Prod rate {} msg/s / {} MiB/s | Prod total {} M msg / {} GiB / {} K err" +
62
68
" | Cons rate {} msg/s / {} MiB/s | Cons total {} M msg / {} GiB" +
63
- " | Prod Latency (ms) avg: {} - 50%: {} - 75%: {} - 90%: {} - 95%: {} - 99%: {} - 99.9%: {} - 99.99%: {} - Max : {}" +
64
- " | E2E Latency (ms) avg: {} - 50%: {} - 75%: {} - 90%: {} - 95%: {} - 99%: {} - 99.9%: {} - 99.99%: {} - Max : {}" ;
69
+ " | Prod Latency (ms) avg: {} - min: {} - 50%: {} - 75%: {} - 90%: {} - 95%: {} - 99%: {} - 99.9%: {} - 99.99%: {} - max : {}" +
70
+ " | E2E Latency (ms) avg: {} - min: {} - 50%: {} - 75%: {} - 90%: {} - 95%: {} - 99%: {} - 99.9%: {} - 99.99%: {} - max : {}" ;
65
71
66
72
private static final Logger LOGGER = LoggerFactory .getLogger (StatsCollector .class );
67
73
68
74
public static Result printAndCollectStats (Stats stats , StopCondition condition , long intervalNanos ,
69
75
PerfConfig config ) {
70
76
final long start = System .nanoTime ();
77
+ CpuMonitor cpu = new CpuMonitor ();
71
78
Result result = new Result (config );
72
79
73
80
long last = start ;
@@ -82,7 +89,7 @@ public static Result printAndCollectStats(Stats stats, StopCondition condition,
82
89
double elapsed = (periodStats .nowNanos - last ) / NANOS_PER_SEC ;
83
90
double elapsedTotal = (periodStats .nowNanos - start ) / NANOS_PER_SEC ;
84
91
85
- PeriodResult periodResult = new PeriodResult (periodStats , elapsed , config .groupsPerTopic );
92
+ PeriodResult periodResult = new PeriodResult (cpu , periodStats , elapsed , config .groupsPerTopic );
86
93
result .update (periodResult , elapsedTotal );
87
94
periodResult .logIt (elapsedTotal );
88
95
@@ -152,6 +159,7 @@ public static class Result {
152
159
public final List <Double > consumeThroughputBps = new ArrayList <>();
153
160
public final List <Long > backlog = new ArrayList <>();
154
161
public final List <Double > produceLatencyMeanMicros = new ArrayList <>();
162
+ public final List <Double > produceLatencyMinMicros = new ArrayList <>();
155
163
public final List <Double > produceLatency50thMicros = new ArrayList <>();
156
164
public final List <Double > produceLatency75thMicros = new ArrayList <>();
157
165
public final List <Double > produceLatency90thMicros = new ArrayList <>();
@@ -162,6 +170,7 @@ public static class Result {
162
170
public final List <Double > produceLatencyMaxMicros = new ArrayList <>();
163
171
public Map <Double , Long > produceLatencyQuantilesMicros ;
164
172
public final List <Double > endToEndLatencyMeanMicros = new ArrayList <>();
173
+ public final List <Double > endToEndLatencyMinMicros = new ArrayList <>();
165
174
public final List <Double > endToEndLatency50thMicros = new ArrayList <>();
166
175
public final List <Double > endToEndLatency75thMicros = new ArrayList <>();
167
176
public final List <Double > endToEndLatency90thMicros = new ArrayList <>();
@@ -186,6 +195,7 @@ private void update(PeriodResult periodResult, double elapsedTotal) {
186
195
this .consumeThroughputBps .add (periodResult .consumeThroughputBps );
187
196
this .backlog .add (periodResult .backlog );
188
197
this .produceLatencyMeanMicros .add (periodResult .produceLatencyMeanMicros );
198
+ this .produceLatencyMinMicros .add (periodResult .produceLatencyMinMicros );
189
199
this .produceLatency50thMicros .add (periodResult .produceLatency50thMicros );
190
200
this .produceLatency75thMicros .add (periodResult .produceLatency75thMicros );
191
201
this .produceLatency90thMicros .add (periodResult .produceLatency90thMicros );
@@ -195,6 +205,7 @@ private void update(PeriodResult periodResult, double elapsedTotal) {
195
205
this .produceLatency9999thMicros .add (periodResult .produceLatency9999thMicros );
196
206
this .produceLatencyMaxMicros .add (periodResult .produceLatencyMaxMicros );
197
207
this .endToEndLatencyMeanMicros .add (periodResult .endToEndLatencyMeanMicros );
208
+ this .endToEndLatencyMinMicros .add (periodResult .endToEndLatencyMinMicros );
198
209
this .endToEndLatency50thMicros .add (periodResult .endToEndLatency50thMicros );
199
210
this .endToEndLatency75thMicros .add (periodResult .endToEndLatency75thMicros );
200
211
this .endToEndLatency90thMicros .add (periodResult .endToEndLatency90thMicros );
@@ -239,13 +250,17 @@ private void update(CumulativeResult cumulativeResult) {
239
250
}
240
251
241
252
private static class PeriodResult {
253
+ private final double cpuUsage ;
254
+ private final long heapMemoryUsed ;
255
+ private final long directMemoryUsed ;
242
256
private final double produceRate ;
243
257
private final double produceThroughputBps ;
244
258
private final double errorRate ;
245
259
private final double consumeRate ;
246
260
private final double consumeThroughputBps ;
247
261
private final long backlog ;
248
262
private final double produceLatencyMeanMicros ;
263
+ private final double produceLatencyMinMicros ;
249
264
private final double produceLatency50thMicros ;
250
265
private final double produceLatency75thMicros ;
251
266
private final double produceLatency90thMicros ;
@@ -255,6 +270,7 @@ private static class PeriodResult {
255
270
private final double produceLatency9999thMicros ;
256
271
private final double produceLatencyMaxMicros ;
257
272
private final double endToEndLatencyMeanMicros ;
273
+ private final double endToEndLatencyMinMicros ;
258
274
private final double endToEndLatency50thMicros ;
259
275
private final double endToEndLatency75thMicros ;
260
276
private final double endToEndLatency90thMicros ;
@@ -264,14 +280,18 @@ private static class PeriodResult {
264
280
private final double endToEndLatency9999thMicros ;
265
281
private final double endToEndLatencyMaxMicros ;
266
282
267
- private PeriodResult (PeriodStats stats , double elapsed , int readWriteRatio ) {
283
+ private PeriodResult (CpuMonitor cpu , PeriodStats stats , double elapsed , int readWriteRatio ) {
284
+ this .cpuUsage = cpu .usage ();
285
+ this .heapMemoryUsed = MemoryMonitor .heapUsed ();
286
+ this .directMemoryUsed = MemoryMonitor .directUsed ();
268
287
this .produceRate = stats .messagesSent / elapsed ;
269
288
this .produceThroughputBps = stats .bytesSent / elapsed ;
270
289
this .errorRate = stats .messagesSendFailed / elapsed ;
271
290
this .consumeRate = stats .messagesReceived / elapsed ;
272
291
this .consumeThroughputBps = stats .bytesReceived / elapsed ;
273
292
this .backlog = Math .max (0 , readWriteRatio * stats .totalMessagesSent - stats .totalMessagesReceived );
274
293
this .produceLatencyMeanMicros = stats .sendLatencyMicros .getMean ();
294
+ this .produceLatencyMinMicros = stats .sendLatencyMicros .getMinValue ();
275
295
this .produceLatency50thMicros = stats .sendLatencyMicros .getValueAtPercentile (50 );
276
296
this .produceLatency75thMicros = stats .sendLatencyMicros .getValueAtPercentile (75 );
277
297
this .produceLatency90thMicros = stats .sendLatencyMicros .getValueAtPercentile (90 );
@@ -281,6 +301,7 @@ private PeriodResult(PeriodStats stats, double elapsed, int readWriteRatio) {
281
301
this .produceLatency9999thMicros = stats .sendLatencyMicros .getValueAtPercentile (99.99 );
282
302
this .produceLatencyMaxMicros = stats .sendLatencyMicros .getMaxValue ();
283
303
this .endToEndLatencyMeanMicros = stats .endToEndLatencyMicros .getMean ();
304
+ this .endToEndLatencyMinMicros = stats .endToEndLatencyMicros .getMinValue ();
284
305
this .endToEndLatency50thMicros = stats .endToEndLatencyMicros .getValueAtPercentile (50 );
285
306
this .endToEndLatency75thMicros = stats .endToEndLatencyMicros .getValueAtPercentile (75 );
286
307
this .endToEndLatency90thMicros = stats .endToEndLatencyMicros .getValueAtPercentile (90 );
@@ -294,18 +315,23 @@ private PeriodResult(PeriodStats stats, double elapsed, int readWriteRatio) {
294
315
private void logIt (double elapsedTotal ) {
295
316
LOGGER .info (PERIOD_LOG_FORMAT ,
296
317
DURATION_FORMAT .format (elapsedTotal ),
318
+ PERCENT_FORMAT .format (cpuUsage * 100 ),
319
+ MEMORY_FORMAT .format (heapMemoryUsed / BYTES_PER_MB ),
320
+ MEMORY_FORMAT .format (directMemoryUsed / BYTES_PER_MB ),
297
321
RATE_FORMAT .format (produceRate ),
298
322
THROUGHPUT_FORMAT .format (produceThroughputBps / BYTES_PER_MB ),
299
323
RATE_FORMAT .format (errorRate ),
300
324
RATE_FORMAT .format (consumeRate ),
301
325
THROUGHPUT_FORMAT .format (consumeThroughputBps / BYTES_PER_MB ),
302
326
COUNT_FORMAT .format (backlog / 1_000.0 ),
303
327
LATENCY_FORMAT .format (produceLatencyMeanMicros / MICROS_PER_MILLI ),
328
+ LATENCY_FORMAT .format (produceLatencyMinMicros / MICROS_PER_MILLI ),
304
329
LATENCY_FORMAT .format (produceLatency50thMicros / MICROS_PER_MILLI ),
305
330
LATENCY_FORMAT .format (produceLatency99thMicros / MICROS_PER_MILLI ),
306
331
LATENCY_FORMAT .format (produceLatency999thMicros / MICROS_PER_MILLI ),
307
332
LATENCY_FORMAT .format (produceLatencyMaxMicros / MICROS_PER_MILLI ),
308
333
LATENCY_FORMAT .format (endToEndLatencyMeanMicros / MICROS_PER_MILLI ),
334
+ LATENCY_FORMAT .format (endToEndLatencyMinMicros / MICROS_PER_MILLI ),
309
335
LATENCY_FORMAT .format (endToEndLatency50thMicros / MICROS_PER_MILLI ),
310
336
LATENCY_FORMAT .format (endToEndLatency99thMicros / MICROS_PER_MILLI ),
311
337
LATENCY_FORMAT .format (endToEndLatency999thMicros / MICROS_PER_MILLI ),
@@ -325,6 +351,7 @@ private static class CumulativeResult {
325
351
private final double consumeCountTotal ;
326
352
private final double consumeSizeTotalBytes ;
327
353
private final double produceLatencyMeanTotalMicros ;
354
+ private final double produceLatencyMinTotalMicros ;
328
355
private final double produceLatency50thTotalMicros ;
329
356
private final double produceLatency75thTotalMicros ;
330
357
private final double produceLatency90thTotalMicros ;
@@ -335,6 +362,7 @@ private static class CumulativeResult {
335
362
private final double produceLatencyMaxTotalMicros ;
336
363
public final Map <Double , Long > produceLatencyQuantilesMicros = new TreeMap <>();
337
364
private final double endToEndLatencyMeanTotalMicros ;
365
+ private final double endToEndLatencyMinTotalMicros ;
338
366
private final double endToEndLatency50thTotalMicros ;
339
367
private final double endToEndLatency75thTotalMicros ;
340
368
private final double endToEndLatency90thTotalMicros ;
@@ -356,6 +384,7 @@ private CumulativeResult(CumulativeStats stats, double elapsedTotal) {
356
384
consumeCountTotal = stats .totalMessagesReceived ;
357
385
consumeSizeTotalBytes = stats .totalBytesReceived ;
358
386
produceLatencyMeanTotalMicros = stats .totalSendLatencyMicros .getMean ();
387
+ produceLatencyMinTotalMicros = stats .totalSendLatencyMicros .getMinValue ();
359
388
produceLatency50thTotalMicros = stats .totalSendLatencyMicros .getValueAtPercentile (50 );
360
389
produceLatency75thTotalMicros = stats .totalSendLatencyMicros .getValueAtPercentile (75 );
361
390
produceLatency90thTotalMicros = stats .totalSendLatencyMicros .getValueAtPercentile (90 );
@@ -368,6 +397,7 @@ private CumulativeResult(CumulativeStats stats, double elapsedTotal) {
368
397
value -> produceLatencyQuantilesMicros .put (value .getPercentile (), value .getValueIteratedTo ())
369
398
);
370
399
endToEndLatencyMeanTotalMicros = stats .totalEndToEndLatencyMicros .getMean ();
400
+ endToEndLatencyMinTotalMicros = stats .totalEndToEndLatencyMicros .getMinValue ();
371
401
endToEndLatency50thTotalMicros = stats .totalEndToEndLatencyMicros .getValueAtPercentile (50 );
372
402
endToEndLatency75thTotalMicros = stats .totalEndToEndLatencyMicros .getValueAtPercentile (75 );
373
403
endToEndLatency90thTotalMicros = stats .totalEndToEndLatencyMicros .getValueAtPercentile (90 );
@@ -393,6 +423,7 @@ private void logIt() {
393
423
COUNT_FORMAT .format (consumeCountTotal / 1_000_000.0 ),
394
424
COUNT_FORMAT .format (consumeSizeTotalBytes / BYTES_PER_GB ),
395
425
LATENCY_FORMAT .format (produceLatencyMeanTotalMicros / MICROS_PER_MILLI ),
426
+ LATENCY_FORMAT .format (produceLatencyMinTotalMicros / MICROS_PER_MILLI ),
396
427
LATENCY_FORMAT .format (produceLatency50thTotalMicros / MICROS_PER_MILLI ),
397
428
LATENCY_FORMAT .format (produceLatency75thTotalMicros / MICROS_PER_MILLI ),
398
429
LATENCY_FORMAT .format (produceLatency90thTotalMicros / MICROS_PER_MILLI ),
@@ -402,6 +433,7 @@ private void logIt() {
402
433
LATENCY_FORMAT .format (produceLatency9999thTotalMicros / MICROS_PER_MILLI ),
403
434
LATENCY_FORMAT .format (produceLatencyMaxTotalMicros / MICROS_PER_MILLI ),
404
435
LATENCY_FORMAT .format (endToEndLatencyMeanTotalMicros / MICROS_PER_MILLI ),
436
+ LATENCY_FORMAT .format (endToEndLatencyMinTotalMicros / MICROS_PER_MILLI ),
405
437
LATENCY_FORMAT .format (endToEndLatency50thTotalMicros / MICROS_PER_MILLI ),
406
438
LATENCY_FORMAT .format (endToEndLatency75thTotalMicros / MICROS_PER_MILLI ),
407
439
LATENCY_FORMAT .format (endToEndLatency90thTotalMicros / MICROS_PER_MILLI ),
0 commit comments