@checkly/playwright-core 1.41.2-beta.3 → 1.41.2-beta.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/lib/checkly/fetch.js +106 -0
- package/lib/client/fetch.js +12 -1
- package/lib/protocol/validator.js +23 -2
- package/lib/server/chromium/videoRecorder.js +1 -1
- package/lib/server/dispatchers/networkDispatchers.js +8 -1
- package/lib/server/fetch.js +26 -3
- package/lib/utils/happy-eyeballs.js +17 -1
- package/lib/vite/recorder/assets/{codeMirrorModule-490993e1.js → codeMirrorModule-85487eb6.js} +10 -10
- package/lib/vite/recorder/assets/{index-40a5e9c7.js → index-b14c63fe.js} +1 -1
- package/lib/vite/recorder/index.html +1 -1
- package/lib/vite/traceViewer/assets/codeMirrorModule-c1454a2e.js +24 -0
- package/lib/vite/traceViewer/assets/wsPort-ee2830d7.js +64 -0
- package/lib/vite/traceViewer/index.decad628.js +2 -0
- package/lib/vite/traceViewer/index.html +2 -2
- package/lib/vite/traceViewer/uiMode.0d0d667b.js +4 -0
- package/lib/vite/traceViewer/uiMode.html +2 -2
- package/package.json +1 -1
|
@@ -0,0 +1,106 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
Object.defineProperty(exports, "__esModule", {
|
|
4
|
+
value: true
|
|
5
|
+
});
|
|
6
|
+
exports.setSWatcherCurrentStepData = exports.parseQueryParameters = exports.initializeTimings = exports.getTimings = exports.getRequestHeaders = exports.getClientCertificates = exports.getBody = exports.addRequestListeners = void 0;
|
|
7
|
+
/**
|
|
8
|
+
* Get client custom certificates.
|
|
9
|
+
*
|
|
10
|
+
* @param {Object} options
|
|
11
|
+
* @returns Object
|
|
12
|
+
*/
|
|
13
|
+
const getClientCertificates = options => {
|
|
14
|
+
if (!options.certs) return {};
|
|
15
|
+
return {
|
|
16
|
+
cert: options.cert,
|
|
17
|
+
key: options.key,
|
|
18
|
+
passphrase: options.passphrase,
|
|
19
|
+
ca: options.ca
|
|
20
|
+
};
|
|
21
|
+
};
|
|
22
|
+
exports.getClientCertificates = getClientCertificates;
|
|
23
|
+
const setSWatcherCurrentStepData = (sWatcher, result) => {
|
|
24
|
+
if (!sWatcher) return;
|
|
25
|
+
sWatcher.appendCurrentStepData({
|
|
26
|
+
...result.response,
|
|
27
|
+
checklyStepCategory: 'api-call'
|
|
28
|
+
});
|
|
29
|
+
};
|
|
30
|
+
exports.setSWatcherCurrentStepData = setSWatcherCurrentStepData;
|
|
31
|
+
const getRequestHeaders = headers => {
|
|
32
|
+
return Object.entries(headers).map(([key, value]) => {
|
|
33
|
+
return {
|
|
34
|
+
name: key,
|
|
35
|
+
value: value
|
|
36
|
+
};
|
|
37
|
+
});
|
|
38
|
+
};
|
|
39
|
+
exports.getRequestHeaders = getRequestHeaders;
|
|
40
|
+
const parseQueryParameters = url => {
|
|
41
|
+
const searchParams = new URL(url).searchParams;
|
|
42
|
+
const parameters = [];
|
|
43
|
+
for (const [name, value] of searchParams.entries()) {
|
|
44
|
+
parameters.push({
|
|
45
|
+
name,
|
|
46
|
+
value
|
|
47
|
+
});
|
|
48
|
+
}
|
|
49
|
+
return parameters;
|
|
50
|
+
};
|
|
51
|
+
exports.parseQueryParameters = parseQueryParameters;
|
|
52
|
+
const getTimings = eventTimes => {
|
|
53
|
+
const {
|
|
54
|
+
agent,
|
|
55
|
+
values
|
|
56
|
+
} = eventTimes;
|
|
57
|
+
const end = performance.now() - values.startTimeNow;
|
|
58
|
+
const socket = values.socket || 0;
|
|
59
|
+
const lookup = values.lookup || socket;
|
|
60
|
+
const connect = values.connect || lookup;
|
|
61
|
+
const response = values.response || connect;
|
|
62
|
+
return {
|
|
63
|
+
wait: agent ? socket - lookup : socket,
|
|
64
|
+
dns: agent ? lookup : lookup - socket,
|
|
65
|
+
tcp: agent ? connect - socket : connect - lookup,
|
|
66
|
+
firstByte: response - connect,
|
|
67
|
+
download: end - response,
|
|
68
|
+
total: end
|
|
69
|
+
};
|
|
70
|
+
};
|
|
71
|
+
exports.getTimings = getTimings;
|
|
72
|
+
const getBody = body => {
|
|
73
|
+
const responseBodySizeLimit = 100000;
|
|
74
|
+
//@ts-ignore
|
|
75
|
+
const bodyAsText = Buffer.byteLength(body, 'utf-8') > responseBodySizeLimit ? body.slice(0, responseBodySizeLimit).toString('utf8') + '...' : body.toString('utf8');
|
|
76
|
+
try {
|
|
77
|
+
return JSON.parse(bodyAsText);
|
|
78
|
+
} catch {
|
|
79
|
+
return bodyAsText;
|
|
80
|
+
}
|
|
81
|
+
};
|
|
82
|
+
exports.getBody = getBody;
|
|
83
|
+
const initializeTimings = () => {
|
|
84
|
+
return {
|
|
85
|
+
values: {
|
|
86
|
+
startTimeNow: performance.now()
|
|
87
|
+
},
|
|
88
|
+
agent: false
|
|
89
|
+
};
|
|
90
|
+
};
|
|
91
|
+
exports.initializeTimings = initializeTimings;
|
|
92
|
+
const addRequestListeners = (request, timings) => {
|
|
93
|
+
request.on('socket', socket => {
|
|
94
|
+
timings.values.socket = performance.now() - timings.values.startTimeNow;
|
|
95
|
+
socket.on('connect', () => {
|
|
96
|
+
timings.values.connect = performance.now() - timings.values.startTimeNow;
|
|
97
|
+
});
|
|
98
|
+
socket.on('lookup', () => {
|
|
99
|
+
timings.values.lookup = performance.now() - timings.values.startTimeNow;
|
|
100
|
+
});
|
|
101
|
+
socket.on('secureConnect', () => {
|
|
102
|
+
timings.values.tlsHandshake = performance.now() - timings.values.startTimeNow;
|
|
103
|
+
});
|
|
104
|
+
});
|
|
105
|
+
};
|
|
106
|
+
exports.addRequestListeners = addRequestListeners;
|
package/lib/client/fetch.js
CHANGED
|
@@ -13,6 +13,7 @@ var _channelOwner = require("./channelOwner");
|
|
|
13
13
|
var _network = require("./network");
|
|
14
14
|
var _tracing = require("./tracing");
|
|
15
15
|
var _errors = require("./errors");
|
|
16
|
+
var _fetch = require("playwright-core/lib/checkly/fetch");
|
|
16
17
|
let _Symbol$asyncDispose, _Symbol$asyncDispose2, _util$inspect$custom;
|
|
17
18
|
/**
|
|
18
19
|
* Copyright (c) Microsoft Corporation.
|
|
@@ -55,6 +56,9 @@ class APIRequest {
|
|
|
55
56
|
storageState,
|
|
56
57
|
tracesDir
|
|
57
58
|
})).request);
|
|
59
|
+
// Checkly related code.
|
|
60
|
+
//@ts-ignore
|
|
61
|
+
context.__sWatcher__ = options.sWatcher;
|
|
58
62
|
this._contexts.add(context);
|
|
59
63
|
context._request = this;
|
|
60
64
|
context._tracing._tracesDir = tracesDir;
|
|
@@ -198,8 +202,12 @@ class APIRequestContext extends _channelOwner.ChannelOwner {
|
|
|
198
202
|
failOnStatusCode: options.failOnStatusCode,
|
|
199
203
|
ignoreHTTPSErrors: options.ignoreHTTPSErrors,
|
|
200
204
|
maxRedirects: maxRedirects,
|
|
201
|
-
|
|
205
|
+
tokenizedURL: options.tokenizedURL,
|
|
206
|
+
...fixtures,
|
|
207
|
+
...(0, _fetch.getClientCertificates)(options)
|
|
202
208
|
});
|
|
209
|
+
//@ts-ignore
|
|
210
|
+
(0, _fetch.setSWatcherCurrentStepData)(this.__sWatcher__, result);
|
|
203
211
|
return new APIResponse(this, result.response);
|
|
204
212
|
});
|
|
205
213
|
}
|
|
@@ -251,6 +259,9 @@ class APIResponse {
|
|
|
251
259
|
headersArray() {
|
|
252
260
|
return this._headers.headersArray();
|
|
253
261
|
}
|
|
262
|
+
timings() {
|
|
263
|
+
return this._initializer.timings;
|
|
264
|
+
}
|
|
254
265
|
async body() {
|
|
255
266
|
try {
|
|
256
267
|
const result = await this._request._channel.fetchResponseBody({
|
|
@@ -207,7 +207,12 @@ _validatorPrimitives.scheme.APIRequestContextFetchParams = (0, _validatorPrimiti
|
|
|
207
207
|
timeout: (0, _validatorPrimitives.tOptional)(_validatorPrimitives.tNumber),
|
|
208
208
|
failOnStatusCode: (0, _validatorPrimitives.tOptional)(_validatorPrimitives.tBoolean),
|
|
209
209
|
ignoreHTTPSErrors: (0, _validatorPrimitives.tOptional)(_validatorPrimitives.tBoolean),
|
|
210
|
-
maxRedirects: (0, _validatorPrimitives.tOptional)(_validatorPrimitives.tNumber)
|
|
210
|
+
maxRedirects: (0, _validatorPrimitives.tOptional)(_validatorPrimitives.tNumber),
|
|
211
|
+
tokenizedURL: (0, _validatorPrimitives.tOptional)(_validatorPrimitives.tString),
|
|
212
|
+
cert: (0, _validatorPrimitives.tOptional)(_validatorPrimitives.tString),
|
|
213
|
+
key: (0, _validatorPrimitives.tOptional)(_validatorPrimitives.tString),
|
|
214
|
+
ca: (0, _validatorPrimitives.tOptional)(_validatorPrimitives.tString),
|
|
215
|
+
passphrase: (0, _validatorPrimitives.tOptional)(_validatorPrimitives.tString)
|
|
211
216
|
});
|
|
212
217
|
_validatorPrimitives.scheme.APIRequestContextFetchResult = (0, _validatorPrimitives.tObject)({
|
|
213
218
|
response: (0, _validatorPrimitives.tType)('APIResponse')
|
|
@@ -240,7 +245,23 @@ _validatorPrimitives.scheme.APIResponse = (0, _validatorPrimitives.tObject)({
|
|
|
240
245
|
url: _validatorPrimitives.tString,
|
|
241
246
|
status: _validatorPrimitives.tNumber,
|
|
242
247
|
statusText: _validatorPrimitives.tString,
|
|
243
|
-
headers: (0, _validatorPrimitives.tArray)((0, _validatorPrimitives.tType)('NameValue'))
|
|
248
|
+
headers: (0, _validatorPrimitives.tArray)((0, _validatorPrimitives.tType)('NameValue')),
|
|
249
|
+
requestHeaders: (0, _validatorPrimitives.tArray)((0, _validatorPrimitives.tType)('NameValue')),
|
|
250
|
+
responseHeaders: (0, _validatorPrimitives.tArray)((0, _validatorPrimitives.tType)('NameValue')),
|
|
251
|
+
body: (0, _validatorPrimitives.tOptional)(_validatorPrimitives.tAny),
|
|
252
|
+
method: _validatorPrimitives.tString,
|
|
253
|
+
tokenizedURL: (0, _validatorPrimitives.tOptional)(_validatorPrimitives.tString),
|
|
254
|
+
timings: (0, _validatorPrimitives.tObject)({
|
|
255
|
+
wait: (0, _validatorPrimitives.tOptional)(_validatorPrimitives.tNumber),
|
|
256
|
+
dns: (0, _validatorPrimitives.tOptional)(_validatorPrimitives.tNumber),
|
|
257
|
+
lookup: (0, _validatorPrimitives.tOptional)(_validatorPrimitives.tNumber),
|
|
258
|
+
connect: (0, _validatorPrimitives.tOptional)(_validatorPrimitives.tNumber),
|
|
259
|
+
tcp: (0, _validatorPrimitives.tOptional)(_validatorPrimitives.tNumber),
|
|
260
|
+
firstByte: (0, _validatorPrimitives.tOptional)(_validatorPrimitives.tNumber),
|
|
261
|
+
download: (0, _validatorPrimitives.tOptional)(_validatorPrimitives.tNumber),
|
|
262
|
+
total: (0, _validatorPrimitives.tOptional)(_validatorPrimitives.tNumber)
|
|
263
|
+
}),
|
|
264
|
+
queryParams: (0, _validatorPrimitives.tOptional)((0, _validatorPrimitives.tArray)((0, _validatorPrimitives.tType)('NameValue')))
|
|
244
265
|
});
|
|
245
266
|
_validatorPrimitives.scheme.LifecycleEvent = (0, _validatorPrimitives.tEnum)(['load', 'domcontentloaded', 'networkidle', 'commit']);
|
|
246
267
|
_validatorPrimitives.scheme.LocalUtilsInitializer = (0, _validatorPrimitives.tObject)({
|
|
@@ -25,7 +25,7 @@ var _instrumentation = require("../instrumentation");
|
|
|
25
25
|
* limitations under the License.
|
|
26
26
|
*/
|
|
27
27
|
|
|
28
|
-
const fps =
|
|
28
|
+
const fps = 12;
|
|
29
29
|
class VideoRecorder {
|
|
30
30
|
static async launch(page, ffmpegPath, options) {
|
|
31
31
|
if (!options.outputFile.endsWith('.webm')) throw new Error('File must have .webm extension');
|
|
@@ -199,7 +199,14 @@ class APIRequestContextDispatcher extends _dispatcher.Dispatcher {
|
|
|
199
199
|
status: fetchResponse.status,
|
|
200
200
|
statusText: fetchResponse.statusText,
|
|
201
201
|
headers: fetchResponse.headers,
|
|
202
|
-
fetchUid: fetchResponse.fetchUid
|
|
202
|
+
fetchUid: fetchResponse.fetchUid,
|
|
203
|
+
requestHeaders: fetchResponse.requestHeaders,
|
|
204
|
+
responseHeaders: fetchResponse.responseHeaders,
|
|
205
|
+
timings: fetchResponse.timings,
|
|
206
|
+
queryParams: fetchResponse.queryParams,
|
|
207
|
+
body: fetchResponse.body,
|
|
208
|
+
method: fetchResponse.method,
|
|
209
|
+
tokenizedURL: fetchResponse.tokenizedURL
|
|
203
210
|
}
|
|
204
211
|
};
|
|
205
212
|
}
|
package/lib/server/fetch.js
CHANGED
|
@@ -9,6 +9,7 @@ var https = _interopRequireWildcard(require("https"));
|
|
|
9
9
|
var _stream = require("stream");
|
|
10
10
|
var _url = _interopRequireDefault(require("url"));
|
|
11
11
|
var _zlib = _interopRequireDefault(require("zlib"));
|
|
12
|
+
var _perf_hooks = require("perf_hooks");
|
|
12
13
|
var _timeoutSettings = require("../common/timeoutSettings");
|
|
13
14
|
var _userAgent = require("../utils/userAgent");
|
|
14
15
|
var _utils = require("../utils");
|
|
@@ -21,6 +22,7 @@ var _instrumentation = require("./instrumentation");
|
|
|
21
22
|
var _progress = require("./progress");
|
|
22
23
|
var _tracing = require("./trace/recorder/tracing");
|
|
23
24
|
var _network = require("./network");
|
|
25
|
+
var _fetch = require("playwright-core/lib/checkly/fetch");
|
|
24
26
|
function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
|
|
25
27
|
function _getRequireWildcardCache(nodeInterop) { if (typeof WeakMap !== "function") return null; var cacheBabelInterop = new WeakMap(); var cacheNodeInterop = new WeakMap(); return (_getRequireWildcardCache = function (nodeInterop) { return nodeInterop ? cacheNodeInterop : cacheBabelInterop; })(nodeInterop); }
|
|
26
28
|
function _interopRequireWildcard(obj, nodeInterop) { if (!nodeInterop && obj && obj.__esModule) { return obj; } if (obj === null || typeof obj !== "object" && typeof obj !== "function") { return { default: obj }; } var cache = _getRequireWildcardCache(nodeInterop); if (cache && cache.has(obj)) { return cache.get(obj); } var newObj = {}; var hasPropertyDescriptor = Object.defineProperty && Object.getOwnPropertyDescriptor; for (var key in obj) { if (key !== "default" && Object.prototype.hasOwnProperty.call(obj, key)) { var desc = hasPropertyDescriptor ? Object.getOwnPropertyDescriptor(obj, key) : null; if (desc && (desc.get || desc.set)) { Object.defineProperty(newObj, key, desc); } else { newObj[key] = obj[key]; } } } newObj.default = obj; if (cache) { cache.set(obj, newObj); } return newObj; }
|
|
@@ -124,7 +126,9 @@ class APIRequestContext extends _instrumentation.SdkObject {
|
|
|
124
126
|
maxRedirects: params.maxRedirects === 0 ? -1 : params.maxRedirects === undefined ? 20 : params.maxRedirects,
|
|
125
127
|
timeout,
|
|
126
128
|
deadline,
|
|
127
|
-
__testHookLookup: params.__testHookLookup
|
|
129
|
+
__testHookLookup: params.__testHookLookup,
|
|
130
|
+
tokenizedURL: params.tokenizedURL,
|
|
131
|
+
...(0, _fetch.getClientCertificates)(params)
|
|
128
132
|
};
|
|
129
133
|
// rejectUnauthorized = undefined is treated as true in node 12.
|
|
130
134
|
if (params.ignoreHTTPSErrors || defaults.ignoreHTTPSErrors) options.rejectUnauthorized = false;
|
|
@@ -139,7 +143,14 @@ class APIRequestContext extends _instrumentation.SdkObject {
|
|
|
139
143
|
if (params.failOnStatusCode && (fetchResponse.status < 200 || fetchResponse.status >= 400)) throw new Error(`${fetchResponse.status} ${fetchResponse.statusText}`);
|
|
140
144
|
return {
|
|
141
145
|
...fetchResponse,
|
|
142
|
-
fetchUid
|
|
146
|
+
fetchUid,
|
|
147
|
+
requestHeaders: (0, _fetch.getRequestHeaders)(headers),
|
|
148
|
+
responseHeaders: fetchResponse.headers,
|
|
149
|
+
queryParams: (0, _fetch.parseQueryParameters)(fetchResponse.url),
|
|
150
|
+
url: params.tokenizedURL || fetchResponse.url,
|
|
151
|
+
timings: (0, _fetch.getTimings)(fetchResponse.timings),
|
|
152
|
+
body: (0, _fetch.getBody)(fetchResponse.body),
|
|
153
|
+
method: options.method
|
|
143
154
|
};
|
|
144
155
|
}
|
|
145
156
|
_parseSetCookieHeader(responseUrl, setCookie) {
|
|
@@ -195,7 +206,9 @@ class APIRequestContext extends _instrumentation.SdkObject {
|
|
|
195
206
|
...options,
|
|
196
207
|
agent
|
|
197
208
|
};
|
|
209
|
+
const timings = (0, _fetch.initializeTimings)();
|
|
198
210
|
const request = requestConstructor(url, requestOptions, async response => {
|
|
211
|
+
timings.values.response = _perf_hooks.performance.now() - timings.values.startTimeNow;
|
|
199
212
|
const notifyRequestFinished = body => {
|
|
200
213
|
const requestFinishedEvent = {
|
|
201
214
|
requestEvent,
|
|
@@ -292,6 +305,7 @@ class APIRequestContext extends _instrumentation.SdkObject {
|
|
|
292
305
|
response.on('aborted', () => reject(new Error('aborted')));
|
|
293
306
|
const chunks = [];
|
|
294
307
|
const notifyBodyFinished = () => {
|
|
308
|
+
timings.values.endAt = _perf_hooks.performance.now();
|
|
295
309
|
const body = Buffer.concat(chunks);
|
|
296
310
|
notifyRequestFinished(body);
|
|
297
311
|
fulfill({
|
|
@@ -299,7 +313,15 @@ class APIRequestContext extends _instrumentation.SdkObject {
|
|
|
299
313
|
status: response.statusCode || 0,
|
|
300
314
|
statusText: response.statusMessage || '',
|
|
301
315
|
headers: toHeadersArray(response.rawHeaders),
|
|
302
|
-
body
|
|
316
|
+
body,
|
|
317
|
+
timings: {
|
|
318
|
+
//@ts-ignore
|
|
319
|
+
values: {
|
|
320
|
+
...timings.values,
|
|
321
|
+
..._happyEyeballs.httpHappyEyeballsTimings.values
|
|
322
|
+
},
|
|
323
|
+
agent: _happyEyeballs.httpHappyEyeballsTimings.agent || timings.agent
|
|
324
|
+
}
|
|
303
325
|
});
|
|
304
326
|
};
|
|
305
327
|
let body = response;
|
|
@@ -328,6 +350,7 @@ class APIRequestContext extends _instrumentation.SdkObject {
|
|
|
328
350
|
body.on('data', chunk => chunks.push(chunk));
|
|
329
351
|
body.on('end', notifyBodyFinished);
|
|
330
352
|
});
|
|
353
|
+
(0, _fetch.addRequestListeners)(request, timings);
|
|
331
354
|
request.on('error', reject);
|
|
332
355
|
const disposeListener = () => {
|
|
333
356
|
reject(new Error('Request context disposed.'));
|
|
@@ -4,7 +4,7 @@ Object.defineProperty(exports, "__esModule", {
|
|
|
4
4
|
value: true
|
|
5
5
|
});
|
|
6
6
|
exports.createSocket = createSocket;
|
|
7
|
-
exports.httpsHappyEyeballsAgent = exports.httpHappyEyeballsAgent = void 0;
|
|
7
|
+
exports.httpsHappyEyeballsAgent = exports.httpHappyEyeballsTimings = exports.httpHappyEyeballsAgent = void 0;
|
|
8
8
|
var dns = _interopRequireWildcard(require("dns"));
|
|
9
9
|
var http = _interopRequireWildcard(require("http"));
|
|
10
10
|
var https = _interopRequireWildcard(require("https"));
|
|
@@ -33,6 +33,15 @@ function _interopRequireWildcard(obj, nodeInterop) { if (!nodeInterop && obj &&
|
|
|
33
33
|
// https://www.rfc-editor.org/rfc/rfc8305
|
|
34
34
|
// Same as in Chromium (https://source.chromium.org/chromium/chromium/src/+/5666ff4f5077a7e2f72902f3a95f5d553ea0d88d:net/socket/transport_connect_job.cc;l=102)
|
|
35
35
|
const connectionAttemptDelayMs = 300;
|
|
36
|
+
const timings = {
|
|
37
|
+
values: {
|
|
38
|
+
startTimeNow: 0,
|
|
39
|
+
socket: 0,
|
|
40
|
+
connect: 0,
|
|
41
|
+
lookup: 0
|
|
42
|
+
},
|
|
43
|
+
agent: false
|
|
44
|
+
};
|
|
36
45
|
class HttpHappyEyeballsAgent extends http.Agent {
|
|
37
46
|
createConnection(options, oncreate) {
|
|
38
47
|
// There is no ambiguity in case of IP address.
|
|
@@ -42,6 +51,8 @@ class HttpHappyEyeballsAgent extends http.Agent {
|
|
|
42
51
|
}
|
|
43
52
|
class HttpsHappyEyeballsAgent extends https.Agent {
|
|
44
53
|
createConnection(options, oncreate) {
|
|
54
|
+
timings.values.startTimeNow = performance.now();
|
|
55
|
+
timings.agent = true;
|
|
45
56
|
// There is no ambiguity in case of IP address.
|
|
46
57
|
if (net.isIP(clientRequestArgsToHostName(options))) return tls.connect(options);
|
|
47
58
|
createConnectionAsync(options, oncreate, /* useTLS */true).catch(err => oncreate === null || oncreate === void 0 ? void 0 : oncreate(err));
|
|
@@ -49,6 +60,7 @@ class HttpsHappyEyeballsAgent extends https.Agent {
|
|
|
49
60
|
}
|
|
50
61
|
const httpsHappyEyeballsAgent = exports.httpsHappyEyeballsAgent = new HttpsHappyEyeballsAgent();
|
|
51
62
|
const httpHappyEyeballsAgent = exports.httpHappyEyeballsAgent = new HttpHappyEyeballsAgent();
|
|
63
|
+
const httpHappyEyeballsTimings = exports.httpHappyEyeballsTimings = timings;
|
|
52
64
|
async function createSocket(host, port) {
|
|
53
65
|
return new Promise((resolve, reject) => {
|
|
54
66
|
if (net.isIP(host)) {
|
|
@@ -97,10 +109,13 @@ async function createConnectionAsync(options, oncreate, useTLS) {
|
|
|
97
109
|
port: options.port,
|
|
98
110
|
host: address
|
|
99
111
|
});
|
|
112
|
+
// Socket created
|
|
113
|
+
timings.values.socket = performance.now() - timings.values.startTimeNow;
|
|
100
114
|
|
|
101
115
|
// Each socket may fire only one of 'connect', 'timeout' or 'error' events.
|
|
102
116
|
// None of these events are fired after socket.destroy() is called.
|
|
103
117
|
socket.on('connect', () => {
|
|
118
|
+
timings.values.connect = performance.now() - timings.values.startTimeNow;
|
|
104
119
|
connected.resolve();
|
|
105
120
|
oncreate === null || oncreate === void 0 ? void 0 : oncreate(null, socket);
|
|
106
121
|
// TODO: Cache the result?
|
|
@@ -126,6 +141,7 @@ async function lookupAddresses(hostname) {
|
|
|
126
141
|
family: 0,
|
|
127
142
|
verbatim: true
|
|
128
143
|
});
|
|
144
|
+
timings.values.lookup = performance.now() - timings.values.startTimeNow;
|
|
129
145
|
let firstFamily = addresses.filter(({
|
|
130
146
|
family
|
|
131
147
|
}) => family === 6);
|