Skip to content

Commit

Permalink
url: improving URLSearchParams
Browse files Browse the repository at this point in the history
- add some benchmarks for URLSearchParams
- change URLSearchParams backing store to an array
- add custom inspection for URLSearchParams and its iterators

PR-URL: #10399
Reviewed-By: James M Snell <jasnell@gmail.com>
  • Loading branch information
TimothyGu authored and italoacasas committed Jan 27, 2017
1 parent 999f685 commit 5d33c96
Show file tree
Hide file tree
Showing 6 changed files with 369 additions and 43 deletions.
60 changes: 60 additions & 0 deletions benchmark/url/url-searchparams-iteration.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,60 @@
'use strict';
const common = require('../common.js');
const assert = require('assert');
const URLSearchParams = new (require('url').URL)('a:').searchParams.constructor;

const bench = common.createBenchmark(main, {
method: ['forEach', 'iterator'],
n: [1e6]
});

const str = 'one=single&two=first&three=first&two=2nd&three=2nd&three=3rd';

function forEach(n) {
const params = new URLSearchParams(str);
const noDead = [];
const cb = (val, key) => {
noDead[0] = key;
noDead[1] = val;
};

bench.start();
for (var i = 0; i < n; i += 1)
params.forEach(cb);
bench.end(n);

assert.strictEqual(noDead[0], 'three');
assert.strictEqual(noDead[1], '3rd');
}

function iterator(n) {
const params = new URLSearchParams(str);
const noDead = [];

bench.start();
for (var i = 0; i < n; i += 1)
for (var pair of params) {
noDead[0] = pair[0];
noDead[1] = pair[1];
}
bench.end(n);

assert.strictEqual(noDead[0], 'three');
assert.strictEqual(noDead[1], '3rd');
}

function main(conf) {
const method = conf.method;
const n = conf.n | 0;

switch (method) {
case 'forEach':
forEach(n);
break;
case 'iterator':
iterator(n);
break;
default:
throw new Error('Unknown method');
}
}
31 changes: 31 additions & 0 deletions benchmark/url/url-searchparams-parse.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
'use strict';
const common = require('../common.js');
const URLSearchParams = new (require('url').URL)('a:').searchParams.constructor;

const inputs = {
noencode: 'foo=bar&baz=quux&xyzzy=thud',
// multicharsep: 'foo=bar&&&&&&&&&&baz=quux&&&&&&&&&&xyzzy=thud',
multicharsep: '&&&&&&&&&&&&&&&&&&&&&&&&&&&&',
encodemany: '%66%6F%6F=bar&%62%61%7A=quux&xyzzy=%74h%75d',
encodelast: 'foo=bar&baz=quux&xyzzy=thu%64',
multivalue: 'foo=bar&foo=baz&foo=quux&quuy=quuz',
multivaluemany: 'foo=bar&foo=baz&foo=quux&quuy=quuz&foo=abc&foo=def&' +
'foo=ghi&foo=jkl&foo=mno&foo=pqr&foo=stu&foo=vwxyz',
manypairs: 'a&b&c&d&e&f&g&h&i&j&k&l&m&n&o&p&q&r&s&t&u&v&w&x&y&z'
};

const bench = common.createBenchmark(main, {
type: Object.keys(inputs),
n: [1e5]
});

function main(conf) {
const input = inputs[conf.type];
const n = conf.n | 0;

var i;
bench.start();
for (i = 0; i < n; i++)
new URLSearchParams(input);
bench.end(n);
}
58 changes: 58 additions & 0 deletions benchmark/url/url-searchparams-read.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,58 @@
'use strict';
const common = require('../common.js');
const URLSearchParams = new (require('url').URL)('a:').searchParams.constructor;

const bench = common.createBenchmark(main, {
method: ['get', 'getAll', 'has'],
param: ['one', 'two', 'three', 'nonexistent'],
n: [1e6]
});

const str = 'one=single&two=first&three=first&two=2nd&three=2nd&three=3rd';

function get(n, param) {
const params = new URLSearchParams(str);

bench.start();
for (var i = 0; i < n; i += 1)
params.get(param);
bench.end(n);
}

function getAll(n, param) {
const params = new URLSearchParams(str);

bench.start();
for (var i = 0; i < n; i += 1)
params.getAll(param);
bench.end(n);
}

function has(n, param) {
const params = new URLSearchParams(str);

bench.start();
for (var i = 0; i < n; i += 1)
params.has(param);
bench.end(n);
}

function main(conf) {
const method = conf.method;
const param = conf.param;
const n = conf.n | 0;

switch (method) {
case 'get':
get(n, param);
break;
case 'getAll':
getAll(n, param);
break;
case 'has':
has(n, param);
break;
default:
throw new Error('Unknown method');
}
}
35 changes: 35 additions & 0 deletions benchmark/url/url-searchparams-stringifier.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
'use strict';
const common = require('../common.js');
const Buffer = require('buffer').Buffer;
const URLSearchParams = new (require('url').URL)('a:').searchParams.constructor;

const inputs = {
noencode: 'foo=bar&baz=quux&xyzzy=thud',
// multicharsep: 'foo=bar&&&&&&&&&&baz=quux&&&&&&&&&&xyzzy=thud',
multicharsep: '&&&&&&&&&&&&&&&&&&&&&&&&&&&&',
encodemany: '%66%6F%6F=bar&%62%61%7A=quux&xyzzy=%74h%75d',
encodelast: 'foo=bar&baz=quux&xyzzy=thu%64',
multivalue: 'foo=bar&foo=baz&foo=quux&quuy=quuz',
multivaluemany: 'foo=bar&foo=baz&foo=quux&quuy=quuz&foo=abc&foo=def&' +
'foo=ghi&foo=jkl&foo=mno&foo=pqr&foo=stu&foo=vwxyz',
manypairs: 'a&b&c&d&e&f&g&h&i&j&k&l&m&n&o&p&q&r&s&t&u&v&w&x&y&z'
};

const bench = common.createBenchmark(main, {
type: Object.keys(inputs),
n: [1e5]
});

function main(conf) {
const input = inputs[conf.type];
const n = conf.n | 0;

const params = new URLSearchParams(input);

bench.start();
// Using Buffer.from to prevent JS version from cheating with ropes instead
// of strings
for (var i = 0; i < n; i += 1)
Buffer.from(params.toString());
bench.end(n);
}
Loading

0 comments on commit 5d33c96

Please sign in to comment.