Grunt task for benchmarking.
Documentation | npm | Issues | Repository
Current package version: 1.0.2
@stackline/grunt-benchmark is the Stackline-maintained distribution of grunt-benchmark@1.0.0. It is an independent continuation of grunt-benchmark; original authors and licenses remain credited below.
| Item | Value |
|---|---|
| Package | @stackline/grunt-benchmark@1.0.2 |
| API target | grunt-benchmark@1.0.0 |
| Supported Node.js | >= 0.10.0 |
| License | MIT |
| Main entry | lib/grunt-benchmark.js |
| Runtime dependencies | benchmark, cli-table |
npm install @stackline/grunt-benchmarkPreserve existing imports and plugin resolution with an npm alias:
npm install grunt-benchmark@npm:@stackline/grunt-benchmarkGrunt task for benchmarking with Benchmark.js.
Install this grunt plugin next to your project's
Gruntfile with: npm install @stackline/grunt-benchmark
Then add this line to your project's Gruntfile:
grunt.loadNpmTasks('@stackline/grunt-benchmark');Create a benchmarks/ folder and create a benchmark script within that folder,
ie fibonacci.js:
var fibonacci = function(n) {
return n < 2 ? n : fibonacci(n - 1) + fibonacci(n - 2);
};
module.exports = function() {
fibonacci(10);
};Then setup your Gruntfile config to run the benchmarks within the benchmarks/ folder:
grunt.initConfig({
benchmark: {
all: {
src: ['benchmarks/*.js'],
dest: 'benchmarks/results.csv'
}
}
});Then run the task:
$ grunt benchmark
Running "benchmark:all" (benchmark) task
Benchmarking "0" [benchmarks/test-timeout.js] x10...
>> test-timeout x 418,070 ops/sec ±12.73% (46 runs sampled)
Benchmark name, date, times and per iteration will be logged in a csv format.
You can add test options to pass to Benchmark.js by exporting an object of [test options].
module.exports = {
name: 'Timeout (asynchronous)',
maxTime: 2,
defer: true,
onComplete: function() {
console.log('Hooray!');
},
fn: function(deferred) {
setTimeout(function() {
deferred.resolve();
}, 500);
}
};Result:
$ grunt benchmark
Running "benchmark:singleTest" (benchmark) task
Benchmarking "Timeout (asynchronous)" [benchmarks/singleTest.js]...
Hooray!
>> Timeout (asynchronous) x 2.00 ops/sec ±0.14% (8 runs sampled)
You can pit implementations against one another by creating a test suite.
var fibonacci = function(n) {
return n < 2 ? n : fibonacci(n - 1) + fibonacci(n - 2);
};
var fibonacci_memoized = (function ( ) {
var memo = [0, 1];
var fib = function (n) {
var result = memo[n];
if (typeof result !== 'number') {
result = fib(n - 1) + fib(n - 2);
memo[n] = result;
}
return result;
};
return fib;
}());
// A test suite
module.exports = {
name: 'Fibonacci Showdown',
tests: {
'Fibonacci': function() {
fibonacci(10);
fibonacci(5);
},
'Fibonacci2': function() {
fibonacci_memoized(10);
fibonacci_memoized(5);
}
}
};Result:
$ grunt benchmark
Running "benchmark:fibonacci" (benchmark) task
Benchmarking suite "Fibonacci" [benchmarks/fibonacci.js]...
>> fibonacci x 13,386,628 ops/sec ±8.63% (74 runs sampled)
>> fibonacci_memoized x 30,509,658 ops/sec ±2.10% (89 runs sampled)
Fastest is fibonacci_memoized
Set exports.tests to an Object that maps test names to functions and or [Benchmark.js test options].
module.exports = {
name: 'Timeout Showdown',
tests: {
'Return immediately (synchronous)': function() {
return;
},
'Timeout: 50ms (asynchronous)': {
defer: true,
fn: function(deferred) {
setTimeout(deferred.resolve, 50);
}
},
'Timeout: 100ms (asynchronous)': {
defer: true,
fn: function(done) {
setTimeout(deferred.resolve, 100);
}
}
}
};Set exports.tests to an Array of functions and or [Benchmark.js test options].
module.exports = {
name: 'Timeout Showdown',
tests: [
{
name: 'Return immediately (synchronous)',
fn: function() {
return;
}
},
{
name: 'Timeout: 50ms (asynchronous)',
defer: true,
fn: function(done) {
setTimeout(done, 50);
}
},
{
name: 'Timeout: 100ms (asynchronous)',
defer: true,
fn: function(done) {
setTimeout(done, 100);
}
}
]
};Included is a helper, spawnTask, for running Grunt tasks within your
benchmarks. This example will create a function to run the watch task:
// benchmarks/watch.js
// Create a spawnable watch task. Doesn't actually spawn until called.
var watchTask = require('@stackline/grunt-benchmark').spawnTask('watch', {
// Text trigger to look for to know when to run the next step or exit
trigger: 'Waiting...',
// Base folder and Gruntfile
// You'll want to setup a fixture base folder and Gruntfile.js
// to ensure your Grunt'ing appropriately
base: 'path/to/a/gruntfile-base',
gruntfile: 'path/to/a/Gruntfile.js'
// Additional Grunt options can be specified here
});
// Our actual benchmark
module.exports = function(done) {
// start the watch task
watchTask([function() {
// After trigger found, run this sync function
// this will trigger the watch task
grunt.file.write('path/to/file.js', 'var test = false;');
}, function() {
// After the previous funciton has ran and another trigger hit...
// run this next sync function
grunt.file.delete('path/to/file.js');
}], function(result) {
// All done, do something more with the output result or finish up the benchmark
done();
});
};Test results will be saved to a file if a destination file is provided.
grunt.initConfig({
benchmark: {
singleTest: {
src: ['benchmarks/fibonacci.js'],
dest: 'results/fibonacci.csv'
}
}
});Results can be saved as 'csv' or 'json'. The format is determined from the dest file extension or by setting the format option:
grunt.initConfig({
benchmark: {
singleTest: {
src: ['benchmarks/fibonacci.js'],
dest: 'results/fibonacci.txt',
options : {
format: 'csv'
}
}
}
});You can specify a truthy displayResults option inside your Grunt config to
display the results using cli-table.
It will automatically pick up the dest property, so that must be set for this
to work.
grunt.initConfig({
benchmark: {
options: {
// This can also be set inside specific tests.
displayResults: true
},
singleTest: {
src: ['benchmarks/fibonacci.js'],
dest: 'results/fibonacci.csv'
}
}
});The output will look something like:
Running "benchmark:fibonacci" (benchmark) task
Running suite Fibonacci [benchmarks/fibonacci.js]...
>> fibonacci x 13,386,628 ops/sec ±8.63% (74 runs sampled)
>> fibonacci_memoized x 30,509,658 ops/sec ±2.10% (89 runs sampled)
Results:
┌──────────────────────┬───────────────────────────────────────────┬───────┬─────────┬────────┬────────────────────┐
│ name │ date │ error │ count │ cycles │ hz │
├──────────────────────┼───────────────────────────────────────────┼───────┼─────────┼────────┼────────────────────┤
│ "fibonacci" │ "Tue Apr 23 2013 21:25:49 GMT-0700 (PDT)" │ │ 906237 │ 4 │ 15154635.038364386 │
├──────────────────────┼───────────────────────────────────────────┼───────┼─────────┼────────┼────────────────────┤
│ "fibonacci_memoized" │ "Fri May 24 2013 19:52:02 GMT-0400 (EDT)" │ │ 1804104 │ 4 │ 31131880.83560733 │
├──────────────────────┼───────────────────────────────────────────┼───────┼─────────┼────────┼────────────────────┤
│ "fibonacci" │ "Tue Apr 23 2013 22:10:55 GMT-0700 (PDT)" │ │ 910791 │ 4 │ 13386627.749339204 │
├──────────────────────┼───────────────────────────────────────────┼───────┼─────────┼────────┼────────────────────┤
│ "fibonacci_memoized" │ "Fri May 24 2013 19:52:11 GMT-0400 (EDT)" │ │ 1764921 │ 4 │ 30509657.596336514 │
└──────────────────────┴───────────────────────────────────────────┴───────┴─────────┴────────┴────────────────────┘In lieu of a formal styleguide, take care to maintain the existing coding style. Lint and test your code using grunt.
- 1.0.0 Support multiple suites in one file (@zoltan-mihalyi). Update deps.
- 0.3.0 Add json output format (@creynders).
- 0.2.0 Switched to benchmark.js. Huge thanks to @lazd!
- 0.1.3 Ability to log dest to a csv file. Support Grunt@0.4.0rc7.
- 0.1.2 Update to work with Grunt@0.4.0rc3.
- 0.1.1 Fix require path
- 0.1.0 Initial release
Copyright (c) 2016 Kyle Robinson Young
Licensed under the MIT license.
- Original project: grunt-benchmark.
- Kyle Robinson Young.
- Stackline maintenance: Alexandro Paixao Marques and Stackline contributors.
Original copyright, license notices and contributor acknowledgements remain part of this distribution. Stackline maintenance does not replace authorship of the original work.
Use this repository's issue tracker for reproducible bugs and feature requests. Join r/Stackline for examples, usage questions and release discussions.