Skip to content

Commit 926fca4

Browse files
committed
Reduced the memory footprint of the js benchmark
1 parent d481e62 commit 926fca4

File tree

3 files changed

+76
-48
lines changed

3 files changed

+76
-48
lines changed

js/lib/metrics.js

Lines changed: 51 additions & 32 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,35 @@
11
const fs = require('fs');
22
const hdr = require('hdr-histogram-js');
33

4+
// Simple accumulator for RTT stats per tick
5+
class RttAccumulator {
6+
constructor() {
7+
this.reset();
8+
}
9+
10+
reset() {
11+
this.sum = 0;
12+
this.count = 0;
13+
}
14+
15+
add(value) {
16+
this.sum += value;
17+
this.count++;
18+
}
19+
20+
getAverage() {
21+
return this.count > 0 ? this.sum / this.count : null;
22+
}
23+
}
24+
25+
function createRttHistogram() {
26+
return hdr.build({
27+
lowestDiscernibleValue: 1,
28+
highestTrackableValue: 10_000_000,
29+
numberOfSignificantValueDigits: 3
30+
});
31+
}
32+
433
function formatRow(row) {
534
const widths = [6, 15, 14, 14, 22, 14];
635
return row.map((val, i) => String(val).padEnd(widths[i] || 10)).join('');
@@ -18,8 +47,8 @@ function updateCLI(
1847
totalSubscribedRef,
1948
totalPublishersRef,
2049
messageRateTs,
21-
rttValues,
22-
rttArchive
50+
rttAccumulator,
51+
rttHistogram
2352
) {
2453
return new Promise((resolve) => {
2554
let prevTime = Date.now();
@@ -66,12 +95,11 @@ function updateCLI(
6695
let avgRttMs = null;
6796

6897
if (measureRTT) {
69-
const tickRttValues = rttValues.splice(0);
70-
if (tickRttValues.length > 0) {
71-
const sum = tickRttValues.reduce((a, b) => a + b, 0);
72-
const avgRtt = Number(sum) / tickRttValues.length;
73-
avgRttMs = avgRtt;
98+
if (rttAccumulator.count > 0) {
99+
avgRttMs = rttAccumulator.getAverage();
74100
metrics.push(avgRttMs.toFixed(3));
101+
// Reset accumulator after using the values
102+
rttAccumulator.reset();
75103
} else {
76104
metrics.push('--');
77105
}
@@ -119,7 +147,7 @@ function writeFinalResults(
119147
totalSubscribed,
120148
messageRateTs,
121149
rttValues,
122-
rttArchive,
150+
rttHistogram,
123151
perSecondStats
124152
) {
125153
const duration = (end - start);
@@ -148,38 +176,27 @@ function writeFinalResults(
148176
};
149177

150178
if (argv['measure-rtt-latency'] && !mode.includes('publish')) {
151-
const histogram = hdr.build({
152-
lowestDiscernibleValue: 1,
153-
highestTrackableValue: 10_000_000,
154-
numberOfSignificantValueDigits: 3
155-
});
156-
157-
rttArchive.forEach((rtt) => {
158-
const val = Number(rtt);
159-
if (val >= 0) histogram.recordValue(val);
160-
});
161-
162-
const avgRtt = histogram.mean ;
163-
const p50 = histogram.getValueAtPercentile(50);
164-
const p95 = histogram.getValueAtPercentile(95);
165-
const p99 = histogram.getValueAtPercentile(99);
166-
const p999 = histogram.getValueAtPercentile(99.9);
179+
const avgRtt = rttHistogram.mean;
180+
const p50 = rttHistogram.getValueAtPercentile(50);
181+
const p95 = rttHistogram.getValueAtPercentile(95);
182+
const p99 = rttHistogram.getValueAtPercentile(99);
183+
const p999 = rttHistogram.getValueAtPercentile(99.9);
167184

168185
result.RTTSummary = {
169186
AvgMs: Number(avgRtt.toFixed(3)),
170187
P50Ms: Number(p50.toFixed(3)),
171188
P95Ms: Number(p95.toFixed(3)),
172189
P99Ms: Number(p99.toFixed(3)),
173190
P999Ms: Number(p999.toFixed(3)),
174-
totalCount: histogram.totalCount
191+
totalCount: rttHistogram.totalCount
175192
};
176193

177-
console.log(`Avg RTT ${avgRtt.toFixed(3)} ms`);
178-
console.log(`P50 RTT ${p50.toFixed(3)} ms`);
179-
console.log(`P95 RTT ${p95.toFixed(3)} ms`);
180-
console.log(`P99 RTT ${p99.toFixed(3)} ms`);
181-
console.log(`P999 RTT ${p999.toFixed(3)} ms`);
182-
console.log(`Total Messages tracked latency ${histogram.totalCount} messages`);
194+
console.log(`Avg RTT ${avgRtt.toFixed(3)} ms`);
195+
console.log(`P50 RTT ${p50.toFixed(3)} ms`);
196+
console.log(`P95 RTT ${p95.toFixed(3)} ms`);
197+
console.log(`P99 RTT ${p99.toFixed(3)} ms`);
198+
console.log(`P999 RTT ${p999.toFixed(3)} ms`);
199+
console.log(`Total Messages tracked latency ${rttHistogram.totalCount} messages`);
183200
}
184201

185202
console.log('#################################################');
@@ -192,5 +209,7 @@ function writeFinalResults(
192209

193210
module.exports = {
194211
updateCLI,
195-
writeFinalResults
212+
writeFinalResults,
213+
createRttHistogram,
214+
RttAccumulator
196215
};

js/lib/redisManager.js

Lines changed: 12 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@ const Redis = require('ioredis');
22
const clusterKeySlot = require('cluster-key-slot');
33
const { publisherRoutine } = require('./publisher');
44
const { subscriberRoutine } = require('./subscriber');
5-
const { updateCLI, writeFinalResults } = require('./metrics');
5+
const { updateCLI, writeFinalResults, createRttHistogram, RttAccumulator } = require('./metrics');
66
const seedrandom = require('seedrandom');
77

88
async function runBenchmark(argv) {
@@ -25,8 +25,11 @@ async function runBenchmark(argv) {
2525
const totalConnectsRef = { value: 0 };
2626
const isRunningRef = { value: true };
2727
const messageRateTs = [];
28-
const rttValues = [];
29-
const rttArchive = [];
28+
29+
// Create efficient RTT tracking
30+
const rttAccumulator = argv['measure-rtt-latency'] ? new RttAccumulator() : null;
31+
// Create histogram for RTT recording
32+
const rttHistogram = argv['measure-rtt-latency'] ? createRttHistogram() : null;
3033

3134
const redisOptions = {
3235
host: argv.host,
@@ -166,8 +169,8 @@ async function runBenchmark(argv) {
166169
argv['measure-rtt-latency'],
167170
client,
168171
isRunningRef,
169-
rttValues,
170-
rttArchive,
172+
rttAccumulator,
173+
rttHistogram,
171174
totalMessagesRef,
172175
totalSubscribedRef,
173176
totalConnectsRef,
@@ -194,8 +197,8 @@ async function runBenchmark(argv) {
194197
totalSubscribedRef,
195198
totalPublishersRef,
196199
messageRateTs,
197-
rttValues,
198-
rttArchive,
200+
rttAccumulator,
201+
rttHistogram,
199202
() => {} // no-op, outputResults is handled after await
200203
);
201204

@@ -211,8 +214,8 @@ async function runBenchmark(argv) {
211214
totalMessagesRef.value,
212215
totalSubscribedRef.value,
213216
messageRateTs,
214-
rttValues,
215-
rttArchive,
217+
rttAccumulator,
218+
rttHistogram,
216219
perSecondStats
217220
);
218221

js/lib/subscriber.js

Lines changed: 13 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -11,8 +11,8 @@ async function subscriberRoutine(
1111
measureRTT,
1212
client,
1313
isRunningRef,
14-
rttValues,
15-
rttArchive,
14+
rttAccumulator,
15+
rttHistogram,
1616
totalMessagesRef,
1717
totalSubscribedRef,
1818
totalConnectsRef,
@@ -71,13 +71,19 @@ async function subscriberRoutine(
7171
if (measureRTT) {
7272
try {
7373
const now = Date.now();
74-
const timestamp = Number(message); // µs
74+
const timestamp = Number(message); // Timestamp from publisher
7575
const rtt = now - timestamp;
76-
if (rtt >= 0n) {
77-
rttValues.push(rtt);
78-
rttArchive.push(rtt);
76+
if (rtt >= 0) {
77+
// Add to accumulator for per-tick average calculation
78+
if (rttAccumulator) {
79+
rttAccumulator.add(rtt);
80+
}
81+
// Record directly to histogram for final stats
82+
if (rttHistogram) {
83+
rttHistogram.recordValue(rtt);
84+
}
7985
if (verbose) {
80-
console.log(`[${clientName}] RTT: ${rtt} µs`);
86+
console.log(`[${clientName}] RTT: ${rtt} ms`);
8187
}
8288
} else {
8389
console.warn(`[${clientName}] Skipping negative RTT: now=${now}, ts=${timestamp}`);

0 commit comments

Comments
 (0)