Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

benchmark: introduce benchmark combination filtering #45735

Closed
wants to merge 2 commits into from
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 6 additions & 0 deletions benchmark/buffers/buffer-copy.js
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,12 @@ const bench = common.createBenchmark(main, {
bytes: [0, 8, 128, 32 * 1024],
partial: ['true', 'false'],
n: [6e6]
}, {
combinationFilter: (p) => {
return (p.partial === 'false' && p.bytes === 0) ||
(p.partial !== 'false' && p.bytes !== 0);
},
test: { partial: 'false', bytes: 0 },
mscdex marked this conversation as resolved.
Show resolved Hide resolved
});

function main({ n, bytes, partial }) {
Expand Down
7 changes: 6 additions & 1 deletion benchmark/buffers/buffer-indexof.js
Original file line number Diff line number Diff line change
Expand Up @@ -19,9 +19,14 @@ const searchStrings = [

const bench = common.createBenchmark(main, {
search: searchStrings,
encoding: ['utf8', 'ucs2'],
encoding: ['undefined', 'utf8', 'ucs2'],
type: ['buffer', 'string'],
n: [5e4]
}, {
combinationFilter: (p) => {
return (p.type === 'buffer' && p.encoding === 'undefined') ||
(p.type !== 'buffer' && p.encoding !== 'undefined');
},
});

function main({ n, search, encoding, type }) {
Expand Down
7 changes: 6 additions & 1 deletion benchmark/buffers/buffer-tostring.js
Original file line number Diff line number Diff line change
Expand Up @@ -3,10 +3,15 @@
const common = require('../common.js');

const bench = common.createBenchmark(main, {
encoding: ['utf8', 'ascii', 'latin1', 'hex', 'UCS-2'],
encoding: ['', 'utf8', 'ascii', 'latin1', 'hex', 'UCS-2'],
args: [0, 1, 3],
len: [1, 64, 1024],
n: [1e6]
}, {
combinationFilter: (p) => {
return (p.args === 0 && p.encoding === '') ||
(p.args !== 0 && p.encoding !== '');
},
});

function main({ encoding, args, len, n }) {
Expand Down
23 changes: 22 additions & 1 deletion benchmark/common.js
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,10 @@
const child_process = require('child_process');
const http_benchmarkers = require('./_http-benchmarkers.js');

function allow() {
return true;
}

class Benchmark {
constructor(fn, configs, options = {}) {
// Used to make sure a benchmark only start a timer once
Expand Down Expand Up @@ -31,9 +35,17 @@ class Benchmark {
this.flags = this.flags.concat(options.flags);
}

if (typeof options.combinationFilter === 'function')
this.combinationFilter = options.combinationFilter;
else
this.combinationFilter = allow;

// The configuration list as a queue of jobs
this.queue = this._queue(this.options);

if (this.queue.length === 0)
return;

// The configuration of the current job, head of the queue
this.config = this.queue[0];

Expand Down Expand Up @@ -108,6 +120,7 @@ class Benchmark {
_queue(options) {
const queue = [];
const keys = Object.keys(options);
const { combinationFilter } = this;

// Perform a depth-first walk through all options to generate a
// configuration list that contains all combinations.
Expand All @@ -131,7 +144,15 @@ class Benchmark {
if (keyIndex + 1 < keys.length) {
recursive(keyIndex + 1, currConfig);
} else {
queue.push(currConfig);
// Check if we should allow the current combination
const allowed = combinationFilter({ ...currConfig });
if (typeof allowed !== 'boolean') {
throw new TypeError(
'Combination filter must always return a boolean'
);
}
if (allowed)
queue.push(currConfig);
}
}
}
Expand Down
8 changes: 6 additions & 2 deletions doc/contributing/writing-and-running-benchmarks.md
Original file line number Diff line number Diff line change
Expand Up @@ -450,8 +450,12 @@ The arguments of `createBenchmark` are:
possible combinations of these parameters, unless specified otherwise.
Each configuration is a property with an array of possible values.
The configuration values can only be strings or numbers.
* `options` {Object} The benchmark options. At the moment only the `flags`
option for specifying command line flags is supported.
* `options` {Object} The benchmark options. Supported options:
* `flags` {Array} Contains node-specific command line flags to pass to
the child process.
* `combinationFilter` {Function} Has a single parameter which is an object
containing a combination of benchmark parameters. It should return `true`
or `false` to indicate whether the combination should be included or not.

`createBenchmark` returns a `bench` object, which is used for timing
the runtime of the benchmark. Run `bench.start()` after the initialization
Expand Down