Skip to content

Commit a59fac4

Browse files
committedApr 11, 2021
Fix hanging promise on HTTP/2 timeout
Fixes #1492
1 parent 45b89f5 commit a59fac4

File tree

4 files changed

+32
-2
lines changed

4 files changed

+32
-2
lines changed
 

‎package.json

+1-1
Original file line numberDiff line numberDiff line change
@@ -51,7 +51,7 @@
5151
"cacheable-request": "^7.0.1",
5252
"decompress-response": "^6.0.0",
5353
"get-stream": "^6.0.0",
54-
"http2-wrapper": "^2.0.1",
54+
"http2-wrapper": "^2.0.3",
5555
"lowercase-keys": "^2.0.0",
5656
"p-cancelable": "^2.0.0",
5757
"responselike": "^2.0.0"

‎source/core/index.ts

+5
Original file line numberDiff line numberDiff line change
@@ -873,6 +873,11 @@ export default class Request extends Duplex implements RequestEvents<Request> {
873873

874874
timer(request);
875875

876+
if (this.options.http2) {
877+
// Unset stream timeout, as the `timeout` option was used only for connection timeout.
878+
request.setTimeout(0);
879+
}
880+
876881
this._cancelTimeouts = timedOut(request, timeout, url as URL);
877882

878883
const responseEventName = options.cache ? 'cacheableResponse' : 'response';

‎source/core/options.ts

+12-1
Original file line numberDiff line numberDiff line change
@@ -711,6 +711,16 @@ const cloneInternals = (internals: typeof defaultInternals): typeof defaultInter
711711
return result;
712712
};
713713

714+
const getHttp2TimeoutOption = (internals: typeof defaultInternals): number | undefined => {
715+
const delays = [internals.timeout.socket, internals.timeout.connect, internals.timeout.lookup, internals.timeout.request, internals.timeout.secureConnect].filter(delay => typeof delay === 'number') as number[];
716+
717+
if (delays.length > 0) {
718+
return Math.min(...delays);
719+
}
720+
721+
return undefined;
722+
};
723+
714724
const descriptor = {
715725
_unixOptions: {
716726
value: undefined,
@@ -2119,7 +2129,8 @@ export default class Options {
21192129
maxHeaderSize: internals.maxHeaderSize,
21202130
localAddress: internals.localAddress,
21212131
headers: internals.headers,
2122-
createConnection: internals.createConnection
2132+
createConnection: internals.createConnection,
2133+
timeout: internals.http2 ? getHttp2TimeoutOption(internals) : undefined
21232134
};
21242135
}
21252136

‎test/timeout.ts

+14
Original file line numberDiff line numberDiff line change
@@ -763,3 +763,17 @@ test('timeouts are emitted ASAP', async t => {
763763

764764
t.true(error.timings.phases.total! < (timeout + marginOfError));
765765
});
766+
767+
test('http2 timeout', async t => {
768+
await t.throwsAsync(got('https://123.123.123.123', {
769+
timeout: {
770+
request: 1
771+
},
772+
http2: true,
773+
retry: {
774+
calculateDelay: ({computedValue}) => computedValue ? 1 : 0
775+
}
776+
}), {
777+
code: 'ETIMEDOUT'
778+
});
779+
});

0 commit comments

Comments
 (0)
Please sign in to comment.