Skip to content

Commit c88f99f

Browse files
jasnellMylesBorins
authored andcommitted
test: improvements to various http tests
* Add common/countdown utility * Numerous improvements to http tests PR-URL: #14315 Reviewed-By: Benjamin Gruenbaum <[email protected]>
1 parent 860c619 commit c88f99f

24 files changed

+370
-439
lines changed

test/common/README.md

+36
Original file line numberDiff line numberDiff line change
@@ -280,6 +280,42 @@ The realpath of the 'tmp' directory.
280280

281281
Name of the temp directory used by tests.
282282

283+
## Countdown Module
284+
285+
The `Countdown` module provides a simple countdown mechanism for tests that
286+
require a particular action to be taken after a given number of completed
287+
tasks (for instance, shutting down an HTTP server after a specific number of
288+
requests).
289+
290+
<!-- eslint-disable strict, required-modules -->
291+
```js
292+
const Countdown = require('../common/countdown');
293+
294+
function doSomething() {
295+
console.log('.');
296+
}
297+
298+
const countdown = new Countdown(2, doSomething);
299+
countdown.dec();
300+
countdown.dec();
301+
```
302+
303+
### new Countdown(limit, callback)
304+
305+
* `limit` {number}
306+
* `callback` {function}
307+
308+
Creates a new `Countdown` instance.
309+
310+
### Countdown.prototype.dec()
311+
312+
Decrements the `Countdown` counter.
313+
314+
### Coutndown.prototype.remaining
315+
316+
Specifies the remaining number of times `Countdown.prototype.dec()` must be
317+
called before the callback is invoked.
318+
283319
## WPT Module
284320

285321
The wpt.js module is a port of parts of

test/common/countdown.js

+27
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,27 @@
1+
/* eslint-disable required-modules */
2+
'use strict';
3+
4+
const assert = require('assert');
5+
const kLimit = Symbol('limit');
6+
const kCallback = Symbol('callback');
7+
8+
class Countdown {
9+
constructor(limit, cb) {
10+
assert.strictEqual(typeof limit, 'number');
11+
assert.strictEqual(typeof cb, 'function');
12+
this[kLimit] = limit;
13+
this[kCallback] = cb;
14+
}
15+
16+
dec() {
17+
assert(this[kLimit] > 0, 'Countdown expired');
18+
if (--this[kLimit] === 0)
19+
this[kCallback]();
20+
}
21+
22+
get remaining() {
23+
return this[kLimit];
24+
}
25+
}
26+
27+
module.exports = Countdown;
+15
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,15 @@
1+
'use strict';
2+
3+
const common = require('../common');
4+
const assert = require('assert');
5+
const Countdown = require('../common/countdown');
6+
7+
let done = '';
8+
9+
const countdown = new Countdown(2, common.mustCall(() => done = true));
10+
assert.strictEqual(countdown.remaining, 2);
11+
countdown.dec();
12+
assert.strictEqual(countdown.remaining, 1);
13+
countdown.dec();
14+
assert.strictEqual(countdown.remaining, 0);
15+
assert.strictEqual(done, true);

test/parallel/test-http-abort-client.js

+11-26
Original file line numberDiff line numberDiff line change
@@ -2,42 +2,27 @@
22
const common = require('../common');
33
const http = require('http');
44

5-
const server = http.Server(function(req, res) {
6-
console.log('Server accepted request.');
5+
let serverRes;
6+
const server = http.Server((req, res) => {
7+
serverRes = res;
78
res.writeHead(200);
89
res.write('Part of my res.');
910

1011
res.destroy();
1112
});
1213

13-
server.listen(0, common.mustCall(function() {
14+
server.listen(0, common.mustCall(() => {
1415
http.get({
15-
port: this.address().port,
16+
port: server.address().port,
1617
headers: { connection: 'keep-alive' }
17-
}, common.mustCall(function(res) {
18+
}, common.mustCall((res) => {
1819
server.close();
20+
serverRes.destroy();
1921

20-
console.log(`Got res: ${res.statusCode}`);
21-
console.dir(res.headers);
22-
23-
res.on('data', function(chunk) {
24-
console.log(`Read ${chunk.length} bytes`);
25-
console.log(' chunk=%j', chunk.toString());
26-
});
27-
28-
res.on('end', function() {
29-
console.log('Response ended.');
30-
});
31-
32-
res.on('aborted', function() {
33-
console.log('Response aborted.');
34-
});
35-
36-
res.socket.on('close', function() {
37-
console.log('socket closed, but not res');
38-
});
39-
40-
// it would be nice if this worked:
22+
res.resume();
23+
res.on('end', common.mustCall());
24+
res.on('aborted', common.mustCall());
4125
res.on('close', common.mustCall());
26+
res.socket.on('close', common.mustCall());
4227
}));
4328
}));

test/parallel/test-http-abort-queued.js

+13-22
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,11 @@
11
'use strict';
2-
require('../common');
2+
const common = require('../common');
33
const assert = require('assert');
44
const http = require('http');
55

66
let complete;
77

8-
const server = http.createServer(function(req, res) {
8+
const server = http.createServer((req, res) => {
99
// We should not see the queued /thatotherone request within the server
1010
// as it should be aborted before it is sent.
1111
assert.strictEqual(req.url, '/');
@@ -19,10 +19,8 @@ const server = http.createServer(function(req, res) {
1919
});
2020

2121

22-
server.listen(0, function() {
23-
console.log('listen', server.address().port);
24-
25-
const agent = new http.Agent({maxSockets: 1});
22+
server.listen(0, () => {
23+
const agent = new http.Agent({ maxSockets: 1 });
2624
assert.strictEqual(Object.keys(agent.sockets).length, 0);
2725

2826
const options = {
@@ -34,7 +32,7 @@ server.listen(0, function() {
3432
};
3533

3634
const req1 = http.request(options);
37-
req1.on('response', function(res1) {
35+
req1.on('response', (res1) => {
3836
assert.strictEqual(Object.keys(agent.sockets).length, 1);
3937
assert.strictEqual(Object.keys(agent.requests).length, 0);
4038

@@ -48,7 +46,9 @@ server.listen(0, function() {
4846
assert.strictEqual(Object.keys(agent.sockets).length, 1);
4947
assert.strictEqual(Object.keys(agent.requests).length, 1);
5048

51-
req2.on('error', function(err) {
49+
// TODO(jasnell): This event does not appear to currently be triggered.
50+
// is this handler actually required?
51+
req2.on('error', (err) => {
5252
// This is expected in response to our explicit abort call
5353
assert.strictEqual(err.code, 'ECONNRESET');
5454
});
@@ -59,25 +59,16 @@ server.listen(0, function() {
5959
assert.strictEqual(Object.keys(agent.sockets).length, 1);
6060
assert.strictEqual(Object.keys(agent.requests).length, 1);
6161

62-
console.log(`Got res: ${res1.statusCode}`);
63-
console.dir(res1.headers);
64-
65-
res1.on('data', function(chunk) {
66-
console.log(`Read ${chunk.length} bytes`);
67-
console.log(' chunk=%j', chunk.toString());
68-
complete();
69-
});
62+
res1.on('data', (chunk) => complete());
7063

71-
res1.on('end', function() {
72-
console.log('Response ended.');
73-
74-
setTimeout(function() {
64+
res1.on('end', common.mustCall(() => {
65+
setTimeout(common.mustCall(() => {
7566
assert.strictEqual(Object.keys(agent.sockets).length, 0);
7667
assert.strictEqual(Object.keys(agent.requests).length, 0);
7768

7869
server.close();
79-
}, 100);
80-
});
70+
}), 100);
71+
}));
8172
});
8273

8374
req1.end();

test/parallel/test-http-after-connect.js

+20-30
Original file line numberDiff line numberDiff line change
@@ -2,61 +2,51 @@
22
const common = require('../common');
33
const assert = require('assert');
44
const http = require('http');
5+
const Countdown = require('../common/countdown');
56

6-
let clientResponses = 0;
7-
8-
const server = http.createServer(common.mustCall(function(req, res) {
9-
console.error('Server got GET request');
7+
const server = http.createServer(common.mustCall((req, res) => {
108
req.resume();
119
res.writeHead(200);
1210
res.write('');
13-
setTimeout(function() {
14-
res.end(req.url);
15-
}, 50);
11+
setTimeout(() => res.end(req.url), 50);
1612
}, 2));
17-
server.on('connect', common.mustCall(function(req, socket) {
18-
console.error('Server got CONNECT request');
13+
14+
const countdown = new Countdown(2, common.mustCall(() => server.close()));
15+
16+
server.on('connect', common.mustCall((req, socket) => {
1917
socket.write('HTTP/1.1 200 Connection established\r\n\r\n');
2018
socket.resume();
21-
socket.on('end', function() {
22-
socket.end();
23-
});
19+
socket.on('end', () => socket.end());
2420
}));
25-
server.listen(0, function() {
21+
22+
server.listen(0, common.mustCall(() => {
2623
const req = http.request({
27-
port: this.address().port,
24+
port: server.address().port,
2825
method: 'CONNECT',
2926
path: 'google.com:80'
3027
});
31-
req.on('connect', common.mustCall(function(res, socket) {
32-
console.error('Client got CONNECT response');
28+
req.on('connect', common.mustCall((res, socket) => {
3329
socket.end();
34-
socket.on('end', function() {
30+
socket.on('end', common.mustCall(() => {
3531
doRequest(0);
3632
doRequest(1);
37-
});
33+
}));
3834
socket.resume();
3935
}));
4036
req.end();
41-
});
37+
}));
4238

4339
function doRequest(i) {
4440
http.get({
4541
port: server.address().port,
4642
path: `/request${i}`
47-
}, common.mustCall(function(res) {
48-
console.error('Client got GET response');
43+
}, common.mustCall((res) => {
4944
let data = '';
5045
res.setEncoding('utf8');
51-
res.on('data', function(chunk) {
52-
data += chunk;
53-
});
54-
res.on('end', function() {
46+
res.on('data', (chunk) => data += chunk);
47+
res.on('end', common.mustCall(() => {
5548
assert.strictEqual(data, `/request${i}`);
56-
++clientResponses;
57-
if (clientResponses === 2) {
58-
server.close();
59-
}
60-
});
49+
countdown.dec();
50+
}));
6151
}));
6252
}

0 commit comments

Comments
 (0)