diff --git a/cli/test/smokehouse/__snapshots__/report-assert-test.js.snap b/cli/test/smokehouse/__snapshots__/report-assert-test.js.snap index f6cbcce93b08..1dc0c6c3d68a 100644 --- a/cli/test/smokehouse/__snapshots__/report-assert-test.js.snap +++ b/cli/test/smokehouse/__snapshots__/report-assert-test.js.snap @@ -3,7 +3,7 @@ exports[`getAssertionReport works (multiple failing) 1`] = ` "X difference at cumulative-layout-shift audit.details.items.length expected: [] - found: [{\\"cumulativeLayoutShiftMainFrame\\":0.13570762803819444,\\"totalCumulativeLayoutShift\\":0.13570762803819444}] + found: [{\\"cumulativeLayoutShiftMainFrame\\":0.13570762803819444}] X difference at cumulative-layout-shift audit.details.blah @@ -24,8 +24,7 @@ exports[`getAssertionReport works (multiple failing) 1`] = ` \\"type\\": \\"debugdata\\", \\"items\\": [ { - \\"cumulativeLayoutShiftMainFrame\\": 0.13570762803819444, - \\"totalCumulativeLayoutShift\\": 0.13570762803819444 + \\"cumulativeLayoutShiftMainFrame\\": 0.13570762803819444 } ] } @@ -35,7 +34,7 @@ exports[`getAssertionReport works (multiple failing) 1`] = ` exports[`getAssertionReport works (trivial failing) 1`] = ` "X difference at cumulative-layout-shift audit.details.items.length expected: [] - found: [{\\"cumulativeLayoutShiftMainFrame\\":0.13570762803819444,\\"totalCumulativeLayoutShift\\":0.13570762803819444}] + found: [{\\"cumulativeLayoutShiftMainFrame\\":0.13570762803819444}] found result: { @@ -51,8 +50,7 @@ exports[`getAssertionReport works (trivial failing) 1`] = ` \\"type\\": \\"debugdata\\", \\"items\\": [ { - \\"cumulativeLayoutShiftMainFrame\\": 0.13570762803819444, - \\"totalCumulativeLayoutShift\\": 0.13570762803819444 + \\"cumulativeLayoutShiftMainFrame\\": 0.13570762803819444 } ] } diff --git a/cli/test/smokehouse/test-definitions/dobetterweb.js b/cli/test/smokehouse/test-definitions/dobetterweb.js index 29b6b3af1dde..1d10dc576ea2 100644 --- a/cli/test/smokehouse/test-definitions/dobetterweb.js +++ b/cli/test/smokehouse/test-definitions/dobetterweb.js @@ -574,6 +574,20 @@ const expectations = { }, }, }, + 'network-rtt': { + details: { + items: [ + {origin: 'http://localhost:10200', rtt: '>0'}, + ], + }, + }, + 'network-server-latency': { + details: { + items: [ + {origin: 'http://localhost:10200', serverResponseTime: '>0'}, + ], + }, + }, 'metrics': { // Flaky in DevTools _excludeRunner: 'devtools', @@ -585,7 +599,7 @@ const expectations = { }, 'largest-contentful-paint-element': { score: null, - displayValue: '1 element found', + displayValue: /\d+\xa0ms/, details: { items: [ { diff --git a/cli/test/smokehouse/test-definitions/perf-frame-metrics.js b/cli/test/smokehouse/test-definitions/perf-frame-metrics.js index 1031528cf33e..b82be5a9d119 100644 --- a/cli/test/smokehouse/test-definitions/perf-frame-metrics.js +++ b/cli/test/smokehouse/test-definitions/perf-frame-metrics.js @@ -78,7 +78,6 @@ const expectations = { largestContentfulPaintAllFrames: '<5000', cumulativeLayoutShift: '0.133 +/- 0.001', cumulativeLayoutShiftMainFrame: '0.001 +/- 0.0005', - totalCumulativeLayoutShift: '0.001 +/- 0.0005', }, { lcpInvalidated: false, diff --git a/cli/test/smokehouse/test-definitions/perf-trace-elements.js b/cli/test/smokehouse/test-definitions/perf-trace-elements.js index 79b8cb3fd0d7..4491dd576f97 100644 --- a/cli/test/smokehouse/test-definitions/perf-trace-elements.js +++ b/cli/test/smokehouse/test-definitions/perf-trace-elements.js @@ -144,7 +144,7 @@ const expectations = { audits: { 'largest-contentful-paint-element': { score: null, - displayValue: '1 element found', + displayValue: /\d+\xa0ms/, details: { items: { 0: { diff --git a/core/audits/audit.js b/core/audits/audit.js index f44f617692af..481d3b5d2e94 100644 --- a/core/audits/audit.js +++ b/core/audits/audit.js @@ -348,12 +348,14 @@ class Audit { /** * @param {typeof Audit} audit * @param {string | LH.IcuMessage} errorMessage + * @param {string=} errorStack * @return {LH.RawIcu} */ - static generateErrorAuditResult(audit, errorMessage) { + static generateErrorAuditResult(audit, errorMessage, errorStack) { return Audit.generateAuditResult(audit, { score: null, errorMessage, + errorStack, }); } @@ -371,7 +373,7 @@ class Audit { let scoreDisplayMode = audit.meta.scoreDisplayMode || Audit.SCORING_MODES.BINARY; // But override if product contents require it. - if (product.errorMessage) { + if (product.errorMessage !== undefined) { // Error result. scoreDisplayMode = Audit.SCORING_MODES.ERROR; } else if (product.notApplicable) { @@ -407,6 +409,7 @@ class Audit { displayValue: product.displayValue, explanation: product.explanation, errorMessage: product.errorMessage, + errorStack: product.errorStack, warnings: product.warnings, details: product.details, diff --git a/core/audits/largest-contentful-paint-element.js b/core/audits/largest-contentful-paint-element.js index 0931a744f2f8..b92bccfd9096 100644 --- a/core/audits/largest-contentful-paint-element.js +++ b/core/audits/largest-contentful-paint-element.js @@ -50,19 +50,44 @@ class LargestContentfulPaintElement extends Audit { } /** - * @param {LH.Artifacts} artifacts + * @param {LH.Artifacts.MetricComputationDataInput} metricComputationData * @param {LH.Audit.Context} context - * @return {Promise} + * @return {Promise} */ - static async makePhaseTable(artifacts, context) { - const trace = artifacts.traces[Audit.DEFAULT_PASS]; - const devtoolsLog = artifacts.devtoolsLogs[Audit.DEFAULT_PASS]; - const gatherContext = artifacts.GatherContext; - const metricComputationData = {trace, devtoolsLog, gatherContext, - settings: context.settings, URL: artifacts.URL}; + static async getOptionalLCPMetric(metricComputationData, context) { + try { + const {timing: metricLcp} = + await LargestContentfulPaint.request(metricComputationData, context); + return metricLcp; + } catch {} + } + + /** + * @param {LH.Artifacts} artifacts + * @return {LH.Audit.Details.Table|undefined} + */ + static makeElementTable(artifacts) { + const lcpElement = artifacts.TraceElements + .find(element => element.traceEventType === 'largest-contentful-paint'); + if (!lcpElement) return; + + /** @type {LH.Audit.Details.Table['headings']} */ + const headings = [ + {key: 'node', valueType: 'node', label: str_(i18n.UIStrings.columnElement)}, + ]; - const {timing: metricLcp} = - await LargestContentfulPaint.request(metricComputationData, context); + const lcpElementDetails = [{node: Audit.makeNodeItem(lcpElement.node)}]; + + return Audit.makeTableDetails(headings, lcpElementDetails); + } + + /** + * @param {number} metricLcp + * @param {LH.Artifacts.MetricComputationDataInput} metricComputationData + * @param {LH.Audit.Context} context + * @return {Promise} + */ + static async makePhaseTable(metricLcp, metricComputationData, context) { const {ttfb, loadStart, loadEnd} = await LCPBreakdown.request(metricComputationData, context); let loadDelay = 0; @@ -102,36 +127,29 @@ class LargestContentfulPaintElement extends Audit { * @return {Promise} */ static async audit(artifacts, context) { - const lcpElement = artifacts.TraceElements - .find(element => element.traceEventType === 'largest-contentful-paint'); - const lcpElementDetails = []; - if (lcpElement) { - lcpElementDetails.push({ - node: Audit.makeNodeItem(lcpElement.node), - }); - } - - /** @type {LH.Audit.Details.Table['headings']} */ - const headings = [ - {key: 'node', valueType: 'node', label: str_(i18n.UIStrings.columnElement)}, - ]; + const trace = artifacts.traces[Audit.DEFAULT_PASS]; + const devtoolsLog = artifacts.devtoolsLogs[Audit.DEFAULT_PASS]; + const gatherContext = artifacts.GatherContext; + const metricComputationData = {trace, devtoolsLog, gatherContext, + settings: context.settings, URL: artifacts.URL}; - const elementTable = Audit.makeTableDetails(headings, lcpElementDetails); + const elementTable = this.makeElementTable(artifacts); + if (!elementTable) return {score: null, notApplicable: true}; const items = [elementTable]; - if (elementTable.items.length) { - const phaseTable = await this.makePhaseTable(artifacts, context); - if (phaseTable) items.push(phaseTable); + let displayValue; + + const metricLcp = await this.getOptionalLCPMetric(metricComputationData, context); + if (metricLcp) { + displayValue = str_(i18n.UIStrings.ms, {timeInMs: metricLcp}); + const phaseTable = await this.makePhaseTable(metricLcp, metricComputationData, context); + items.push(phaseTable); } const details = Audit.makeListDetails(items); - const displayValue = str_(i18n.UIStrings.displayValueElementsFound, - {nodeCount: lcpElementDetails.length}); - return { score: 1, - notApplicable: lcpElementDetails.length === 0, displayValue, details, }; diff --git a/core/audits/metrics.js b/core/audits/metrics.js index b69f04ecb19d..d8c61020fa0a 100644 --- a/core/audits/metrics.js +++ b/core/audits/metrics.js @@ -11,10 +11,8 @@ import {TimingSummary} from '../computed/metrics/timing-summary.js'; const DECIMAL_METRIC_KEYS = new Set([ 'cumulativeLayoutShift', 'cumulativeLayoutShiftMainFrame', - 'totalCumulativeLayoutShift', 'observedCumulativeLayoutShift', 'observedCumulativeLayoutShiftMainFrame', - 'observedTotalCumulativeLayoutShift', ]); class Metrics extends Audit { diff --git a/core/audits/network-requests.js b/core/audits/network-requests.js index f7e99bf5135b..4e4ebe30fd73 100644 --- a/core/audits/network-requests.js +++ b/core/audits/network-requests.js @@ -8,6 +8,7 @@ import {Audit} from './audit.js'; import UrlUtils from '../lib/url-utils.js'; import {NetworkRecords} from '../computed/network-records.js'; import {MainResource} from '../computed/main-resource.js'; +import {EntityClassification} from '../computed/entity-classification.js'; class NetworkRequests extends Audit { /** @@ -31,6 +32,8 @@ class NetworkRequests extends Audit { static async audit(artifacts, context) { const devtoolsLog = artifacts.devtoolsLogs[Audit.DEFAULT_PASS]; const records = await NetworkRecords.request(devtoolsLog, context); + const classifiedEntities = await EntityClassification.request( + {URL: artifacts.URL, devtoolsLog}, context); const earliestRendererStartTime = records.reduce( (min, record) => Math.min(min, record.rendererStartTime), Infinity @@ -61,6 +64,8 @@ class NetworkRequests extends Audit { ((record.frameId === mainFrameId) || undefined) : undefined; + const entity = classifiedEntities.entityByUrl.get(record.url); + return { url: UrlUtils.elideDataURI(record.url), sessionTargetType: record.sessionTargetType, @@ -77,6 +82,7 @@ class NetworkRequests extends Audit { priority: record.priority, isLinkPreload, experimentalFromMainFrame, + entity: entity?.name, lrEndTimeDeltaMs: endTimeDeltaMs, // Only exists on Lightrider runs lrTCPMs: TCPMs, // Only exists on Lightrider runs lrRequestMs: requestMs, // Only exists on Lightrider runs diff --git a/core/audits/server-response-time.js b/core/audits/server-response-time.js index 41070d7fb755..cabf8e4b45ec 100644 --- a/core/audits/server-response-time.js +++ b/core/audits/server-response-time.js @@ -46,7 +46,7 @@ class ServerResponseTime extends Audit { */ static calculateResponseTime(record) { const timing = record.timing; - return timing ? timing.receiveHeadersEnd - timing.sendEnd : 0; + return timing ? timing.receiveHeadersStart - timing.sendEnd : 0; } /** diff --git a/core/computed/metrics/cumulative-layout-shift.js b/core/computed/metrics/cumulative-layout-shift.js index 122417a39e61..9f95547d2507 100644 --- a/core/computed/metrics/cumulative-layout-shift.js +++ b/core/computed/metrics/cumulative-layout-shift.js @@ -101,19 +101,10 @@ class CumulativeLayoutShift { return maxScore; } - /** - * Sum all layout shift events from the entire trace. - * @param {Array} layoutShiftEvents - * @return {number} - */ - static calculateTotalCumulativeLayoutShift(layoutShiftEvents) { - return layoutShiftEvents.reduce((sum, e) => sum += e.weightedScore, 0); - } - /** * @param {LH.Trace} trace * @param {LH.Artifacts.ComputedContext} context - * @return {Promise<{cumulativeLayoutShift: number, cumulativeLayoutShiftMainFrame: number, totalCumulativeLayoutShift: number}>} + * @return {Promise<{cumulativeLayoutShift: number, cumulativeLayoutShiftMainFrame: number}>} */ static async compute_(trace, context) { const processedTrace = await ProcessedTrace.request(trace, context); @@ -122,14 +113,9 @@ class CumulativeLayoutShift { CumulativeLayoutShift.getLayoutShiftEvents(processedTrace); const mainFrameShiftEvents = allFrameShiftEvents.filter(e => e.isMainFrame); - // The original Cumulative Layout Shift metric, the sum of all main-frame shift events. - const totalCumulativeLayoutShift = - CumulativeLayoutShift.calculateTotalCumulativeLayoutShift(mainFrameShiftEvents); - return { cumulativeLayoutShift: CumulativeLayoutShift.calculate(allFrameShiftEvents), cumulativeLayoutShiftMainFrame: CumulativeLayoutShift.calculate(mainFrameShiftEvents), - totalCumulativeLayoutShift, }; } } diff --git a/core/computed/metrics/time-to-first-byte.js b/core/computed/metrics/time-to-first-byte.js index 74ac7ff5b172..40de6b061cae 100644 --- a/core/computed/metrics/time-to-first-byte.js +++ b/core/computed/metrics/time-to-first-byte.js @@ -41,15 +41,17 @@ class TimeToFirstByte extends NavigationMetric { * @return {Promise} */ static async computeObservedMetric(data, context) { - const {processedNavigation} = data; - const timeOriginTs = processedNavigation.timestamps.timeOrigin; const mainResource = await MainResource.request(data, context); + if (!mainResource.timing) { + throw new Error('missing timing for main resource'); + } - // Technically TTFB is the start of the response headers not the end. - // That signal isn't available to us so we use header end time as a best guess. - const timestamp = mainResource.responseHeadersEndTime * 1000; + const {processedNavigation} = data; + const timeOriginTs = processedNavigation.timestamps.timeOrigin; + const timestampMs = + mainResource.timing.requestTime * 1000 + mainResource.timing.receiveHeadersStart; + const timestamp = timestampMs * 1000; const timing = (timestamp - timeOriginTs) / 1000; - return {timing, timestamp}; } } diff --git a/core/computed/metrics/timing-summary.js b/core/computed/metrics/timing-summary.js index bbbfebcd694c..6e7a856e88c2 100644 --- a/core/computed/metrics/timing-summary.js +++ b/core/computed/metrics/timing-summary.js @@ -65,7 +65,6 @@ class TimingSummary { const { cumulativeLayoutShift, cumulativeLayoutShiftMainFrame, - totalCumulativeLayoutShift, } = cumulativeLayoutShiftValues || {}; /** @type {LH.Artifacts.TimingSummary} */ @@ -89,7 +88,6 @@ class TimingSummary { maxPotentialFID: maxPotentialFID?.timing, cumulativeLayoutShift, cumulativeLayoutShiftMainFrame, - totalCumulativeLayoutShift, lcpLoadStart: lcpBreakdown?.loadStart, lcpLoadEnd: lcpBreakdown?.loadEnd, @@ -123,7 +121,6 @@ class TimingSummary { observedDomContentLoadedTs: processedNavigation?.timestamps.domContentLoaded, observedCumulativeLayoutShift: cumulativeLayoutShift, observedCumulativeLayoutShiftMainFrame: cumulativeLayoutShiftMainFrame, - observedTotalCumulativeLayoutShift: totalCumulativeLayoutShift, // Include some visual metrics from speedline observedFirstVisualChange: speedline.first, diff --git a/core/gather/driver/execution-context.js b/core/gather/driver/execution-context.js index 0f08f665b375..f5238e517d9a 100644 --- a/core/gather/driver/execution-context.js +++ b/core/gather/driver/execution-context.js @@ -125,14 +125,22 @@ class ExecutionContext { this._session.setNextProtocolTimeout(timeout); const response = await this._session.sendCommand('Runtime.evaluate', evaluationParams); - if (response.exceptionDetails) { + + const ex = response.exceptionDetails; + if (ex) { // An error occurred before we could even create a Promise, should be *very* rare. // Also occurs when the expression is not valid JavaScript. - const errorMessage = response.exceptionDetails.exception ? - response.exceptionDetails.exception.description : - response.exceptionDetails.text; - return Promise.reject(new Error(`Evaluation exception: ${errorMessage}`)); + const elidedExpression = expression.replace(/\s+/g, ' ').substring(0, 100); + const messageLines = [ + 'Runtime.evaluate exception', + `Expression: ${elidedExpression}\n---- (elided)`, + !ex.stackTrace ? `Parse error at: ${ex.lineNumber + 1}:${ex.columnNumber + 1}` : null, + ex.exception?.description || ex.text, + ].filter(Boolean); + const evaluationError = new Error(messageLines.join('\n')); + return Promise.reject(evaluationError); } + // Protocol should always return a 'result' object, but it is sometimes undefined. See #6026. if (response.result === undefined) { return Promise.reject( diff --git a/core/gather/gatherers/inspector-issues.js b/core/gather/gatherers/inspector-issues.js index c0f1bd8e0f32..c60cfa062eb1 100644 --- a/core/gather/gatherers/inspector-issues.js +++ b/core/gather/gatherers/inspector-issues.js @@ -75,6 +75,8 @@ class InspectorIssues extends FRGatherer { quirksModeIssue: [], cookieIssue: [], sharedArrayBufferIssue: [], + stylesheetLoadingIssue: [], + federatedAuthUserInfoRequestIssue: [], }; const keys = /** @type {Array} */(Object.keys(artifact)); for (const key of keys) { diff --git a/core/legacy/config/config.js b/core/legacy/config/config.js index af55d7c33d96..d5de3e613006 100644 --- a/core/legacy/config/config.js +++ b/core/legacy/config/config.js @@ -205,7 +205,7 @@ class LegacyResolvedConfig { } /** - * @deprecated `Config.fromJson` should be used instead. + * @deprecated `LegacyResolvedConfig.fromJson` should be used instead. * @constructor * @param {LH.Config} config * @param {{settings: LH.Config.Settings, passes: ?LH.Config.Pass[], audits: ?LH.Config.AuditDefn[]}} opts diff --git a/core/lib/asset-saver.js b/core/lib/asset-saver.js index 76a6736c2e91..87ac80dd4c49 100644 --- a/core/lib/asset-saver.js +++ b/core/lib/asset-saver.js @@ -7,6 +7,7 @@ import fs from 'fs'; import path from 'path'; import stream from 'stream'; +import url from 'url'; import log from 'lighthouse-logger'; @@ -16,6 +17,7 @@ import {MetricTraceEvents} from './traces/metric-trace-events.js'; import {NetworkAnalysis} from '../computed/network-analysis.js'; import {LoadSimulator} from '../computed/load-simulator.js'; import {LighthouseError} from '../lib/lh-error.js'; +import {LH_ROOT} from '../../root.js'; const optionsFilename = 'options.json'; const artifactsFilename = 'artifacts.json'; @@ -425,6 +427,22 @@ function normalizeTimingEntries(timings) { } } +/** + * @param {LH.Result} lhr + */ +function elideAuditErrorStacks(lhr) { + const baseCallFrameUrl = url.pathToFileURL(LH_ROOT); + for (const auditResult of Object.values(lhr.audits)) { + if (auditResult.errorStack) { + auditResult.errorStack = auditResult.errorStack + // Make paths relative to the repo root. + .replaceAll(baseCallFrameUrl.pathname, '') + // Remove line/col info. + .replaceAll(/:\d+:\d+/g, ''); + } + } +} + export { saveArtifacts, saveFlowArtifacts, @@ -438,4 +456,5 @@ export { saveLanternNetworkData, stringifyReplacer, normalizeTimingEntries, + elideAuditErrorStacks, }; diff --git a/core/lib/dependency-graph/simulator/network-analyzer.js b/core/lib/dependency-graph/simulator/network-analyzer.js index a3d8725af5bd..ed0c7a7bb569 100644 --- a/core/lib/dependency-graph/simulator/network-analyzer.js +++ b/core/lib/dependency-graph/simulator/network-analyzer.js @@ -139,14 +139,15 @@ class NetworkAnalyzer { const {timing, connectionReused, record} = info; if (connectionReused) return; - if (timing.connectEnd > 0 && timing.connectStart > 0 && record.protocol.startsWith('h3')) { + const {connectStart, sslStart, sslEnd, connectEnd} = timing; + if (connectEnd >= 0 && connectStart >= 0 && record.protocol.startsWith('h3')) { // These values are equal to sslStart and sslEnd for h3. - return timing.connectEnd - timing.connectStart; - } else if (timing.sslStart > 0 && timing.sslEnd > 0) { + return connectEnd - connectStart; + } else if (sslStart >= 0 && sslEnd >= 0 && sslStart !== connectStart) { // SSL can also be more than 1 RT but assume False Start was used. - return [timing.connectEnd - timing.sslStart, timing.sslStart - timing.connectStart]; - } else if (timing.connectStart > 0 && timing.connectEnd > 0) { - return timing.connectEnd - timing.connectStart; + return [connectEnd - sslStart, sslStart - connectStart]; + } else if (connectStart >= 0 && connectEnd >= 0) { + return connectEnd - connectStart; } } diff --git a/core/lib/lh-error.js b/core/lib/lh-error.js index fff6226d9bbf..adcb949fb82d 100644 --- a/core/lib/lh-error.js +++ b/core/lib/lh-error.js @@ -107,17 +107,18 @@ const str_ = i18n.createIcuMessageFn(import.meta.url, UIStrings); const LHERROR_SENTINEL = '__LighthouseErrorSentinel'; const ERROR_SENTINEL = '__ErrorSentinel'; /** - * @typedef {{sentinel: '__LighthouseErrorSentinel', code: string, stack?: string, [p: string]: string|undefined}} SerializedLighthouseError - * @typedef {{sentinel: '__ErrorSentinel', message: string, code?: string, stack?: string}} SerializedBaseError + * @typedef {{sentinel: '__LighthouseErrorSentinel', code: string, stack?: string, cause?: unknown, properties?: {[p: string]: string|undefined}}} SerializedLighthouseError + * @typedef {{sentinel: '__ErrorSentinel', message: string, code?: string, stack?: string, cause?: unknown}} SerializedBaseError */ class LighthouseError extends Error { /** * @param {LighthouseErrorDefinition} errorDefinition * @param {Record=} properties + * @param {ErrorOptions=} options */ - constructor(errorDefinition, properties) { - super(errorDefinition.code); + constructor(errorDefinition, properties, options) { + super(errorDefinition.code, options); this.name = 'LighthouseError'; this.code = errorDefinition.code; // Add additional properties to be ICU replacements in the error string. @@ -163,19 +164,20 @@ class LighthouseError extends Error { if (err instanceof LighthouseError) { // Remove class props so that remaining values were what was passed in as `properties`. // eslint-disable-next-line no-unused-vars - const {name, code, message, friendlyMessage, lhrRuntimeError, stack, ...properties} = err; + const {name, code, message, friendlyMessage, lhrRuntimeError, stack, cause, ...properties} = err; return { sentinel: LHERROR_SENTINEL, code, stack, - ...properties, + cause, + properties: /** @type {{ [p: string]: string | undefined }} */ (properties), }; } // Unexpected errors won't be LighthouseErrors, but we want them serialized as well. if (err instanceof Error) { - const {message, stack} = err; + const {message, stack, cause} = err; // @ts-expect-error - code can be helpful for e.g. node errors, so preserve it if it's present. const code = err.code; return { @@ -183,6 +185,7 @@ class LighthouseError extends Error { message, code, stack, + cause, }; } @@ -203,17 +206,18 @@ class LighthouseError extends Error { if (possibleError.sentinel === LHERROR_SENTINEL) { // Include sentinel in destructuring so it doesn't end up in `properties`. // eslint-disable-next-line no-unused-vars - const {sentinel, code, stack, ...properties} = /** @type {SerializedLighthouseError} */ (possibleError); + const {code, stack, cause, properties} = /** @type {SerializedLighthouseError} */ (possibleError); const errorDefinition = LighthouseError.errors[/** @type {keyof typeof ERRORS} */ (code)]; - const lhError = new LighthouseError(errorDefinition, properties); + const lhError = new LighthouseError(errorDefinition, properties, {cause}); lhError.stack = stack; return lhError; } if (possibleError.sentinel === ERROR_SENTINEL) { - const {message, code, stack} = /** @type {SerializedBaseError} */ (possibleError); - const error = new Error(message); + const {message, code, stack, cause} = /** @type {SerializedBaseError} */ (possibleError); + const opts = cause ? {cause} : undefined; + const error = new Error(message, opts); Object.assign(error, {code, stack}); return error; } diff --git a/core/lib/network-request.js b/core/lib/network-request.js index 990b64e12c30..f7fa5345c0a5 100644 --- a/core/lib/network-request.js +++ b/core/lib/network-request.js @@ -274,6 +274,7 @@ class NetworkRequest { } this._updateResponseHeadersEndTimeIfNecessary(); + this._backfillReceiveHeaderStartTiming(); this._updateTransferSizeForLightrider(); this._updateTimingsForLightrider(); } @@ -293,6 +294,7 @@ class NetworkRequest { this.localizedFailDescription = data.errorText; this._updateResponseHeadersEndTimeIfNecessary(); + this._backfillReceiveHeaderStartTiming(); this._updateTransferSizeForLightrider(); this._updateTimingsForLightrider(); } @@ -315,6 +317,7 @@ class NetworkRequest { this.networkEndTime = data.timestamp * 1000; this._updateResponseHeadersEndTimeIfNecessary(); + this._backfillReceiveHeaderStartTiming(); } /** @@ -449,6 +452,19 @@ class NetworkRequest { } } + /** + * TODO(compat): remove M116. + * `timing.receiveHeadersStart` was added recently, and will be in M116. Until then, + * set it to receiveHeadersEnd, which is close enough, to allow consumers of NetworkRequest + * to use the new field without accounting for this backcompat. + */ + _backfillReceiveHeaderStartTiming() { + // Do nothing if a value is already present! + if (!this.timing || this.timing.receiveHeadersStart !== undefined) return; + + this.timing.receiveHeadersStart = this.timing.receiveHeadersEnd; + } + /** * LR gets additional, accurate timing information from its underlying fetch infrastructure. This * is passed in via X-Headers similar to 'X-TotalFetchedSize'. diff --git a/core/lib/tracehouse/trace-processor.js b/core/lib/tracehouse/trace-processor.js index a397cdbfc2b4..fc64f813ff2b 100644 --- a/core/lib/tracehouse/trace-processor.js +++ b/core/lib/tracehouse/trace-processor.js @@ -705,7 +705,7 @@ class TraceProcessor { return Boolean( evt.name === 'FrameCommittedInBrowser' && evt.args.data?.frame && - evt.args.data.url + evt.args.data.url !== undefined ); }).forEach(evt => { framesById.set(evt.args.data.frame, { diff --git a/core/runner.js b/core/runner.js index 15a34835d145..64991d03a2c2 100644 --- a/core/runner.js +++ b/core/runner.js @@ -429,7 +429,7 @@ class Runner { // Create a friendlier display error and mark it as expected to avoid duplicates in Sentry const error = new LighthouseError(LighthouseError.errors.ERRORED_REQUIRED_ARTIFACT, - {artifactName, errorMessage: artifactError.message}); + {artifactName, errorMessage: artifactError.message}, {cause: artifactError}); // @ts-expect-error Non-standard property added to Error error.expected = true; throw error; @@ -468,7 +468,9 @@ class Runner { Sentry.captureException(err, {tags: {audit: audit.meta.id}, level: 'error'}); // Errors become error audit result. const errorMessage = err.friendlyMessage ? err.friendlyMessage : err.message; - auditResult = Audit.generateErrorAuditResult(audit, errorMessage); + // Prefer the stack trace closest to the error. + const stack = err.cause?.stack ?? err.stack; + auditResult = Audit.generateErrorAuditResult(audit, errorMessage, stack); } log.timeEnd(status); diff --git a/core/scripts/cleanup-LHR-for-diff.js b/core/scripts/cleanup-LHR-for-diff.js index 6dd0d8fc3024..d1d9f2d55688 100755 --- a/core/scripts/cleanup-LHR-for-diff.js +++ b/core/scripts/cleanup-LHR-for-diff.js @@ -10,6 +10,8 @@ import {readFileSync, writeFileSync} from 'fs'; +import {elideAuditErrorStacks} from '../lib/asset-saver.js'; + const filename = process.argv[2]; const extraFlag = process.argv[3]; if (!filename) throw new Error('No filename provided.'); @@ -45,6 +47,9 @@ function cleanAndFormatLHR(lhrString) { auditResult.description = '**Excluded from diff**'; } } + + elideAuditErrorStacks(lhr); + // Ensure we have a final newline to conform to .editorconfig return `${JSON.stringify(lhr, null, 2)}\n`; } diff --git a/core/scripts/update-flow-fixtures.js b/core/scripts/update-flow-fixtures.js index c968bad7d666..44d01a72eca3 100644 --- a/core/scripts/update-flow-fixtures.js +++ b/core/scripts/update-flow-fixtures.js @@ -152,6 +152,7 @@ async function generateFlowResult() { // Normalize some data so it doesn't change on every update. for (const {lhr} of flowResult.steps) { assetSaver.normalizeTimingEntries(lhr.timing.entries); + assetSaver.elideAuditErrorStacks(lhr); lhr.timing.total = lhr.timing.entries.length; } diff --git a/core/test/audits/__snapshots__/metrics-test.js.snap b/core/test/audits/__snapshots__/metrics-test.js.snap index acb8351b5734..601e70943b3a 100644 --- a/core/test/audits/__snapshots__/metrics-test.js.snap +++ b/core/test/audits/__snapshots__/metrics-test.js.snap @@ -47,7 +47,6 @@ Object { "observedSpeedIndexTs": 760623438456, "observedTimeOrigin": 0, "observedTimeOriginTs": 760620643599, - "observedTotalCumulativeLayoutShift": 0, "observedTraceEnd": 4778, "observedTraceEndTs": 760625421283, "speedIndex": 6330, @@ -55,7 +54,6 @@ Object { "timeToFirstByte": 2394, "timeToFirstByteTs": undefined, "totalBlockingTime": 162, - "totalCumulativeLayoutShift": 0, } `; @@ -106,7 +104,6 @@ Object { "observedSpeedIndexTs": 23467605703, "observedTimeOrigin": 0, "observedTimeOriginTs": 23466023130, - "observedTotalCumulativeLayoutShift": undefined, "observedTraceEnd": 6006, "observedTraceEndTs": 23472029453, "speedIndex": 1583, @@ -114,7 +111,6 @@ Object { "timeToFirstByte": 565, "timeToFirstByteTs": 23466588051, "totalBlockingTime": 0, - "totalCumulativeLayoutShift": undefined, } `; @@ -165,7 +161,6 @@ Object { "observedSpeedIndexTs": 713038416494, "observedTimeOrigin": 0, "observedTimeOriginTs": 713037023064, - "observedTotalCumulativeLayoutShift": 0, "observedTraceEnd": 7416, "observedTraceEndTs": 713044439102, "speedIndex": 3684, @@ -173,7 +168,6 @@ Object { "timeToFirstByte": 611, "timeToFirstByteTs": undefined, "totalBlockingTime": 1205, - "totalCumulativeLayoutShift": 0, } `; @@ -224,7 +218,6 @@ Object { "observedSpeedIndexTs": 225414776724, "observedTimeOrigin": 0, "observedTimeOriginTs": 225414172015, - "observedTotalCumulativeLayoutShift": 0, "observedTraceEnd": 12540, "observedTraceEndTs": 225426711887, "speedIndex": 605, @@ -232,7 +225,6 @@ Object { "timeToFirstByte": 261, "timeToFirstByteTs": 225414432704, "totalBlockingTime": 48, - "totalCumulativeLayoutShift": 0, } `; @@ -283,7 +275,6 @@ Object { "observedSpeedIndexTs": 225414776724, "observedTimeOrigin": 0, "observedTimeOriginTs": 225414172015, - "observedTotalCumulativeLayoutShift": 0, "observedTraceEnd": 12540, "observedTraceEndTs": 225426711887, "speedIndex": 1676, @@ -291,6 +282,5 @@ Object { "timeToFirstByte": 760, "timeToFirstByteTs": undefined, "totalBlockingTime": 777, - "totalCumulativeLayoutShift": 0, } `; diff --git a/core/test/audits/largest-contentful-paint-element-test.js b/core/test/audits/largest-contentful-paint-element-test.js index ae27f38bc27c..5ecdcb3f0734 100644 --- a/core/test/audits/largest-contentful-paint-element-test.js +++ b/core/test/audits/largest-contentful-paint-element-test.js @@ -101,8 +101,8 @@ describe('Performance: largest-contentful-paint-element audit', () => { const auditResult = await LargestContentfulPaintElementAudit.audit(artifacts, context); expect(auditResult.score).toEqual(1); - expect(auditResult.notApplicable).toEqual(false); - expect(auditResult.displayValue).toBeDisplayString('1 element found'); + expect(auditResult.notApplicable).toBeUndefined(); + expect(auditResult.displayValue).toBeDisplayString('5,800\xa0ms'); expect(auditResult.details.items).toHaveLength(2); expect(auditResult.details.items[0].items).toHaveLength(1); expect(auditResult.details.items[0].items[0].node.path).toEqual('1,HTML,3,BODY,5,DIV,0,HEADER'); @@ -145,10 +145,9 @@ describe('Performance: largest-contentful-paint-element audit', () => { const context = {settings: artifacts.settings, computedCache: new Map()}; const auditResult = await LargestContentfulPaintElementAudit.audit(artifacts, context); - expect(auditResult.score).toEqual(1); + expect(auditResult.score).toEqual(null); expect(auditResult.notApplicable).toEqual(true); - expect(auditResult.displayValue).toBeDisplayString('0 elements found'); - expect(auditResult.details.items).toHaveLength(1); - expect(auditResult.details.items[0].items).toHaveLength(0); + expect(auditResult.displayValue).toBeUndefined(); + expect(auditResult.details).toBeUndefined(); }); }); diff --git a/core/test/audits/metrics-test.js b/core/test/audits/metrics-test.js index e44d42ae7342..23a6615a0ffe 100644 --- a/core/test/audits/metrics-test.js +++ b/core/test/audits/metrics-test.js @@ -150,15 +150,11 @@ describe('Performance: metrics', () => { const {details} = await MetricsAudit.audit(artifacts, context); expect(details.items[0]).toMatchObject({ cumulativeLayoutShift: undefined, - cumulativeLayoutShiftMainFrame: undefined, - totalCumulativeLayoutShift: undefined, observedCumulativeLayoutShift: undefined, - observedCumulativeLayoutShiftMainFrame: undefined, - observedTotalCumulativeLayoutShift: undefined, }); }); - it('evaluates new CLS correctly across all frames', async () => { + it('evaluates CLS correctly across all frames', async () => { const URL = getURLArtifactFromDevtoolsLog(clsAllFramesDevtoolsLog); const artifacts = { URL, @@ -177,15 +173,9 @@ describe('Performance: metrics', () => { }; const {details} = await MetricsAudit.audit(artifacts, context); - // Only a single main-frame shift event, so mfCls and oldCls are equal. expect(details.items[0]).toMatchObject({ cumulativeLayoutShift: expect.toBeApproximately(0.026463, 6), - cumulativeLayoutShiftMainFrame: expect.toBeApproximately(0.001166, 6), - totalCumulativeLayoutShift: expect.toBeApproximately(0.001166, 6), - observedCumulativeLayoutShift: expect.toBeApproximately(0.026463, 6), - observedCumulativeLayoutShiftMainFrame: expect.toBeApproximately(0.001166, 6), - observedTotalCumulativeLayoutShift: expect.toBeApproximately(0.001166, 6), }); }); @@ -232,12 +222,7 @@ describe('Performance: metrics', () => { const {details} = await MetricsAudit.audit(artifacts, context); expect(details.items[0]).toMatchObject({ cumulativeLayoutShift: expect.toBeApproximately(2.268816, 6), - cumulativeLayoutShiftMainFrame: expect.toBeApproximately(2.268816, 6), - totalCumulativeLayoutShift: expect.toBeApproximately(4.809794, 6), - observedCumulativeLayoutShift: expect.toBeApproximately(2.268816, 6), - observedCumulativeLayoutShiftMainFrame: expect.toBeApproximately(2.268816, 6), - observedTotalCumulativeLayoutShift: expect.toBeApproximately(4.809794, 6), }); }); }); diff --git a/core/test/audits/metrics/cumulative-layout-shift-test.js b/core/test/audits/metrics/cumulative-layout-shift-test.js index 92f32ba65868..a60bd3938468 100644 --- a/core/test/audits/metrics/cumulative-layout-shift-test.js +++ b/core/test/audits/metrics/cumulative-layout-shift-test.js @@ -32,7 +32,6 @@ describe('Cumulative Layout Shift', () => { type: 'debugdata', items: [{ cumulativeLayoutShiftMainFrame: expect.toBeApproximately(2.268816, 6), - totalCumulativeLayoutShift: expect.toBeApproximately(4.809794, 6), }], }, }); diff --git a/core/test/audits/network-requests-test.js b/core/test/audits/network-requests-test.js index a05dfdf02a65..e57ff9af08fd 100644 --- a/core/test/audits/network-requests-test.js +++ b/core/test/audits/network-requests-test.js @@ -168,4 +168,28 @@ describe('Network requests audit', () => { isLinkPreload: true, }]); }); + + it('should include if network request was first or third party', async () => { + const records = [ + {url: 'https://example.com/'}, + {url: 'https://www.googletagmanager.com/gtm.js'}, + ]; + + const artifacts = { + devtoolsLogs: { + [NetworkRequests.DEFAULT_PASS]: networkRecordsToDevtoolsLog(records), + }, + URL: {mainDocumentUrl: 'https://example.com/'}, + GatherContext, + }; + const output = await NetworkRequests.audit(artifacts, {computedCache: new Map()}); + + expect(output.details.items).toMatchObject([{ + url: 'https://example.com/', + entity: 'example.com', + }, { + url: 'https://www.googletagmanager.com/gtm.js', + entity: 'Google Tag Manager', + }]); + }); }); diff --git a/core/test/audits/server-response-time-test.js b/core/test/audits/server-response-time-test.js index da57cc502a8e..e8aa072af9e4 100644 --- a/core/test/audits/server-response-time-test.js +++ b/core/test/audits/server-response-time-test.js @@ -11,7 +11,7 @@ describe('Performance: server-response-time audit', () => { const mainResource = { url: 'https://example.com/', requestId: '0', - timing: {receiveHeadersEnd: 830, sendEnd: 200}, + timing: {receiveHeadersStart: 830, sendEnd: 200}, }; const devtoolsLog = networkRecordsToDevtoolsLog([mainResource]); @@ -37,6 +37,33 @@ describe('Performance: server-response-time audit', () => { }); it('succeeds when response time of root document is lower than 600ms', async () => { + const mainResource = { + url: 'https://example.com/', + requestId: '0', + timing: {receiveHeadersStart: 400, sendEnd: 200}, + }; + const devtoolsLog = networkRecordsToDevtoolsLog([mainResource]); + + const artifacts = { + devtoolsLogs: {[ServerResponseTime.DEFAULT_PASS]: devtoolsLog}, + URL: {mainDocumentUrl: 'https://example.com/'}, + GatherContext: {gatherMode: 'navigation'}, + }; + + const result = await ServerResponseTime.audit(artifacts, {computedCache: new Map()}); + expect(result).toMatchObject({ + numericValue: 200, + score: 1, + metricSavings: { + FCP: 100, + LCP: 100, + }, + }); + }); + + // TODO(compat): remove M116. See _backfillReceiveHeaderStartTiming. + // eslint-disable-next-line max-len + it('succeeds when response time of root document is lower than 600ms (receiveHeadersEnd fallback)', async () => { const mainResource = { url: 'https://example.com/', requestId: '0', diff --git a/core/test/computed/metrics/cumulative-layout-shift-test.js b/core/test/computed/metrics/cumulative-layout-shift-test.js index 230d18cdf337..8f880154199a 100644 --- a/core/test/computed/metrics/cumulative-layout-shift-test.js +++ b/core/test/computed/metrics/cumulative-layout-shift-test.js @@ -26,7 +26,6 @@ describe('Metrics: CLS', () => { expect(result).toEqual({ cumulativeLayoutShift: expect.toBeApproximately(2.268816, 6), cumulativeLayoutShiftMainFrame: expect.toBeApproximately(2.268816, 6), - totalCumulativeLayoutShift: expect.toBeApproximately(4.809794, 6), }); }); @@ -40,7 +39,6 @@ describe('Metrics: CLS', () => { expect(result).toEqual({ cumulativeLayoutShift: 0.026463014612806653, cumulativeLayoutShiftMainFrame: 0.0011656245471340055, - totalCumulativeLayoutShift: 0.0011656245471340055, }); }); @@ -49,7 +47,6 @@ describe('Metrics: CLS', () => { expect(result).toEqual({ cumulativeLayoutShift: 0, cumulativeLayoutShiftMainFrame: 0, - totalCumulativeLayoutShift: 0, }); }); }); @@ -123,7 +120,6 @@ describe('Metrics: CLS', () => { expect(result).toEqual({ cumulativeLayoutShift: 4, cumulativeLayoutShiftMainFrame: 4, - totalCumulativeLayoutShift: 4, }); }); @@ -140,7 +136,6 @@ describe('Metrics: CLS', () => { expect(result).toEqual({ cumulativeLayoutShift: 3, cumulativeLayoutShiftMainFrame: 3, - totalCumulativeLayoutShift: 3, }); }); @@ -158,7 +153,6 @@ describe('Metrics: CLS', () => { expect(result).toEqual({ cumulativeLayoutShift: 0.75, cumulativeLayoutShiftMainFrame: 0.75, - totalCumulativeLayoutShift: 3.75, // 30 * 0.125 }); }); @@ -183,7 +177,6 @@ describe('Metrics: CLS', () => { expect(result).toEqual({ cumulativeLayoutShift: 1.0625, cumulativeLayoutShiftMainFrame: 1.0625, - totalCumulativeLayoutShift: 1.375, }); }); @@ -201,7 +194,6 @@ describe('Metrics: CLS', () => { expect(result).toEqual({ cumulativeLayoutShift: 3.75, // 30 * 0.125 cumulativeLayoutShiftMainFrame: 3.75, - totalCumulativeLayoutShift: 3.75, }); }); @@ -225,7 +217,6 @@ describe('Metrics: CLS', () => { expect(result).toEqual({ cumulativeLayoutShift: 3, cumulativeLayoutShiftMainFrame: 3, - totalCumulativeLayoutShift: 3, }); }); }); @@ -246,7 +237,6 @@ describe('Metrics: CLS', () => { expect(result).toEqual({ cumulativeLayoutShift: 0.75, // Same value as single-frame uniformly distributed. cumulativeLayoutShiftMainFrame: 0.125, // All 1s gaps, so only one event per cluster. - totalCumulativeLayoutShift: 1.875, // 0.125 * 15 }); }); @@ -275,7 +265,6 @@ describe('Metrics: CLS', () => { expect(result).toMatchObject({ cumulativeLayoutShift: 4, cumulativeLayoutShiftMainFrame: 2, - totalCumulativeLayoutShift: 2, }); }); @@ -330,7 +319,6 @@ describe('Metrics: CLS', () => { expect(result).toMatchObject({ cumulativeLayoutShift: 5, cumulativeLayoutShiftMainFrame: 3, - totalCumulativeLayoutShift: 3, }); }); @@ -346,7 +334,6 @@ describe('Metrics: CLS', () => { expect(result).toMatchObject({ cumulativeLayoutShift: 4, cumulativeLayoutShiftMainFrame: 2, - totalCumulativeLayoutShift: 2, }); }); @@ -375,7 +362,6 @@ describe('Metrics: CLS', () => { expect(result).toMatchObject({ cumulativeLayoutShift: 3, cumulativeLayoutShiftMainFrame: 1, - totalCumulativeLayoutShift: 1, }); }); }); @@ -395,7 +381,6 @@ describe('Metrics: CLS', () => { expect(result).toMatchObject({ cumulativeLayoutShift: 6, cumulativeLayoutShiftMainFrame: 6, - totalCumulativeLayoutShift: 6, }); }); @@ -414,7 +399,6 @@ describe('Metrics: CLS', () => { expect(result).toMatchObject({ cumulativeLayoutShift: 6, cumulativeLayoutShiftMainFrame: 1, - totalCumulativeLayoutShift: 4, }); }); @@ -428,7 +412,6 @@ describe('Metrics: CLS', () => { expect(result).toMatchObject({ cumulativeLayoutShift: 2, cumulativeLayoutShiftMainFrame: 2, - totalCumulativeLayoutShift: 2, }); }); @@ -442,7 +425,6 @@ describe('Metrics: CLS', () => { expect(result).toMatchObject({ cumulativeLayoutShift: 2, cumulativeLayoutShiftMainFrame: 1, - totalCumulativeLayoutShift: 1, }); }); }); diff --git a/core/test/computed/metrics/time-to-first-byte-test.js b/core/test/computed/metrics/time-to-first-byte-test.js index d257d6562c50..e2f111200910 100644 --- a/core/test/computed/metrics/time-to-first-byte-test.js +++ b/core/test/computed/metrics/time-to-first-byte-test.js @@ -53,7 +53,7 @@ function mockNetworkRecords() { networkRequestTime: 300, responseHeadersEndTime: 400, networkEndTime: 500, - timing: {sendEnd: 0, receiveHeadersEnd: 100}, + timing: {sendEnd: 0, receiveHeadersStart: 100}, transferSize: 16_000, url: mainDocumentUrl, frameId: 'ROOT_FRAME', diff --git a/core/test/computed/metrics/timing-summary-test.js b/core/test/computed/metrics/timing-summary-test.js index 8ceb358ed6e2..49336fc6d910 100644 --- a/core/test/computed/metrics/timing-summary-test.js +++ b/core/test/computed/metrics/timing-summary-test.js @@ -66,7 +66,6 @@ describe('Timing summary', () => { "observedSpeedIndexTs": 10328522489.12, "observedTimeOrigin": 0, "observedTimeOriginTs": 10327187909, - "observedTotalCumulativeLayoutShift": 0.0011656245471340055, "observedTraceEnd": 14214.313, "observedTraceEndTs": 10341402222, "speedIndex": 1335, @@ -74,7 +73,6 @@ describe('Timing summary', () => { "timeToFirstByte": 570.329, "timeToFirstByteTs": 10327758238, "totalBlockingTime": 2.7429999999994834, - "totalCumulativeLayoutShift": 0.0011656245471340055, } `); // Includes performance metrics diff --git a/core/test/fixtures/fraggle-rock/reports/sample-flow-result.json b/core/test/fixtures/fraggle-rock/reports/sample-flow-result.json index 559c0aeff3d0..36815a1cf0d7 100644 --- a/core/test/fixtures/fraggle-rock/reports/sample-flow-result.json +++ b/core/test/fixtures/fraggle-rock/reports/sample-flow-result.json @@ -186,8 +186,7 @@ "type": "debugdata", "items": [ { - "cumulativeLayoutShiftMainFrame": 0.002631263732910156, - "totalCumulativeLayoutShift": 0.002631263732910156 + "cumulativeLayoutShiftMainFrame": 0.002631263732910156 } ] } @@ -756,7 +755,8 @@ "mimeType": "text/html", "resourceType": "Document", "priority": "VeryHigh", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "mikescerealshack.co" }, { "url": "https://www.mikescerealshack.co/fonts/danielbd.woff2", @@ -773,7 +773,8 @@ "resourceType": "Font", "priority": "High", "isLinkPreload": true, - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "mikescerealshack.co" }, { "url": "https://events.mikescerealshack.co/js/index.js", @@ -789,7 +790,8 @@ "mimeType": "application/javascript", "resourceType": "Script", "priority": "Low", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "mikescerealshack.co" }, { "url": "https://www.mikescerealshack.co/_next/static/css/08dcb440d7d83b488817.css", @@ -806,7 +808,8 @@ "resourceType": "Stylesheet", "priority": "VeryHigh", "isLinkPreload": true, - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "mikescerealshack.co" }, { "url": "https://www.mikescerealshack.co/_next/static/chunks/main-1f8481d632114a408557.js", @@ -823,7 +826,8 @@ "resourceType": "Script", "priority": "High", "isLinkPreload": true, - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "mikescerealshack.co" }, { "url": "https://www.mikescerealshack.co/_next/static/chunks/webpack-657a8433bac0aabd564e.js", @@ -840,7 +844,8 @@ "resourceType": "Script", "priority": "High", "isLinkPreload": true, - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "mikescerealshack.co" }, { "url": "https://www.mikescerealshack.co/_next/static/chunks/framework.9d524150d48315f49e80.js", @@ -857,7 +862,8 @@ "resourceType": "Script", "priority": "High", "isLinkPreload": true, - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "mikescerealshack.co" }, { "url": "https://www.mikescerealshack.co/_next/static/chunks/commons.49455e4fa8cc3f51203f.js", @@ -874,7 +880,8 @@ "resourceType": "Script", "priority": "High", "isLinkPreload": true, - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "mikescerealshack.co" }, { "url": "https://www.mikescerealshack.co/_next/static/chunks/pages/_app-ef508c97234d1af96c47.js", @@ -891,7 +898,8 @@ "resourceType": "Script", "priority": "High", "isLinkPreload": true, - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "mikescerealshack.co" }, { "url": "https://www.mikescerealshack.co/_next/static/chunks/1aeab0175d4c4d823d7a78205bceb5dd9cd36d32.a629f28ec97ae6e480bf.js", @@ -908,7 +916,8 @@ "resourceType": "Script", "priority": "High", "isLinkPreload": true, - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "mikescerealshack.co" }, { "url": "https://www.mikescerealshack.co/_next/static/chunks/pages/index-37980adf97404e76e41a.js", @@ -925,7 +934,8 @@ "resourceType": "Script", "priority": "High", "isLinkPreload": true, - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "mikescerealshack.co" }, { "url": "https://www.mikescerealshack.co/logo-text.svg", @@ -941,7 +951,8 @@ "mimeType": "image/svg+xml", "resourceType": "Image", "priority": "Low", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "mikescerealshack.co" }, { "url": "https://www.mikescerealshack.co/_next/static/t5QnfQSErVZVsTAuFcBWI/_buildManifest.js", @@ -957,7 +968,8 @@ "mimeType": "application/javascript", "resourceType": "Script", "priority": "Low", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "mikescerealshack.co" }, { "url": "https://www.mikescerealshack.co/_next/static/t5QnfQSErVZVsTAuFcBWI/_ssgManifest.js", @@ -973,7 +985,8 @@ "mimeType": "application/javascript", "resourceType": "Script", "priority": "Low", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "mikescerealshack.co" }, { "url": "https://fonts.googleapis.com/css2?family=Poppins:wght@400;500;700&display=swap", @@ -989,7 +1002,8 @@ "mimeType": "text/css", "resourceType": "Stylesheet", "priority": "VeryLow", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "Google Fonts" }, { "url": "https://www.mikescerealshack.co/_next/static/chunks/1aeab0175d4c4d823d7a78205bceb5dd9cd36d32.a629f28ec97ae6e480bf.js", @@ -1005,7 +1019,8 @@ "mimeType": "application/javascript", "resourceType": "Other", "priority": "VeryLow", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "mikescerealshack.co" }, { "url": "https://www.mikescerealshack.co/_next/static/chunks/9ea7d3ba8dd80c65c50028121847762825088b49.dc477066508a83415fce.js", @@ -1021,7 +1036,8 @@ "mimeType": "application/javascript", "resourceType": "Other", "priority": "VeryLow", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "mikescerealshack.co" }, { "url": "https://www.mikescerealshack.co/_next/static/chunks/pages/scenes/%5Bseason%5D/%5Bepisode%5D/%5Bscene%5D-526fe33be891a56314a3.js", @@ -1037,7 +1053,8 @@ "mimeType": "application/javascript", "resourceType": "Other", "priority": "VeryLow", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "mikescerealshack.co" }, { "url": "https://fonts.gstatic.com/s/poppins/v20/pxiEyp8kv8JHgFVrJJfecnFHGPc.woff2", @@ -1053,7 +1070,8 @@ "mimeType": "font/woff2", "resourceType": "Font", "priority": "VeryHigh", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "Google Fonts" }, { "url": "https://fonts.gstatic.com/s/poppins/v20/pxiByp8kv8JHgFVrLCz7Z1xlFd2JQEk.woff2", @@ -1069,7 +1087,8 @@ "mimeType": "font/woff2", "resourceType": "Font", "priority": "VeryHigh", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "Google Fonts" }, { "url": "https://www.mikescerealshack.co/_next/static/chunks/9ea7d3ba8dd80c65c50028121847762825088b49.dc477066508a83415fce.js", @@ -1085,7 +1104,8 @@ "mimeType": "application/javascript", "resourceType": "Script", "priority": "Low", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "mikescerealshack.co" }, { "url": "https://www.mikescerealshack.co/_next/static/chunks/pages/scenes/%5Bseason%5D/%5Bepisode%5D/%5Bscene%5D-526fe33be891a56314a3.js", @@ -1101,7 +1121,8 @@ "mimeType": "application/javascript", "resourceType": "Script", "priority": "Low", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "mikescerealshack.co" }, { "url": "https://www.mikescerealshack.co/favicon.png", @@ -1117,7 +1138,8 @@ "mimeType": "image/png", "resourceType": "Other", "priority": "High", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "mikescerealshack.co" } ], "debugData": { @@ -1295,7 +1317,6 @@ "maxPotentialFID": 193, "cumulativeLayoutShift": 0.002631263732910156, "cumulativeLayoutShiftMainFrame": 0.002631263732910156, - "totalCumulativeLayoutShift": 0.002631263732910156, "lcpLoadStart": 1000, "lcpLoadEnd": 1078, "timeToFirstByte": 615, @@ -1323,7 +1344,6 @@ "observedDomContentLoadedTs": 183713237485, "observedCumulativeLayoutShift": 0.002631263732910156, "observedCumulativeLayoutShiftMainFrame": 0.002631263732910156, - "observedTotalCumulativeLayoutShift": 0.002631263732910156, "observedFirstVisualChange": 341, "observedFirstVisualChangeTs": 183713323617, "observedLastVisualChange": 575, @@ -1518,7 +1538,7 @@ "description": "This is the largest contentful element painted within the viewport. [Learn more about the Largest Contentful Paint element](https://developer.chrome.com/docs/lighthouse/performance/lighthouse-largest-contentful-paint/)", "score": null, "scoreDisplayMode": "informative", - "displayValue": "1 element found", + "displayValue": "1,370 ms", "details": { "type": "list", "items": [ @@ -5624,79 +5644,79 @@ }, { "startTime": 127, - "name": "lh:audit:network-rtt", + "name": "lh:computed:EntityClassification", "duration": 1, "entryType": "measure" }, { "startTime": 128, - "name": "lh:audit:network-server-latency", + "name": "lh:audit:network-rtt", "duration": 1, "entryType": "measure" }, { "startTime": 129, - "name": "lh:audit:main-thread-tasks", + "name": "lh:audit:network-server-latency", "duration": 1, "entryType": "measure" }, { "startTime": 130, - "name": "lh:audit:metrics", + "name": "lh:audit:main-thread-tasks", "duration": 1, "entryType": "measure" }, { "startTime": 131, - "name": "lh:computed:TimingSummary", + "name": "lh:audit:metrics", "duration": 1, "entryType": "measure" }, { "startTime": 132, - "name": "lh:computed:FirstContentfulPaintAllFrames", + "name": "lh:computed:TimingSummary", "duration": 1, "entryType": "measure" }, { "startTime": 133, - "name": "lh:computed:LargestContentfulPaintAllFrames", + "name": "lh:computed:FirstContentfulPaintAllFrames", "duration": 1, "entryType": "measure" }, { "startTime": 134, - "name": "lh:computed:LCPBreakdown", + "name": "lh:computed:LargestContentfulPaintAllFrames", "duration": 1, "entryType": "measure" }, { "startTime": 135, - "name": "lh:computed:TimeToFirstByte", + "name": "lh:computed:LCPBreakdown", "duration": 1, "entryType": "measure" }, { "startTime": 136, - "name": "lh:computed:LCPImageRecord", + "name": "lh:computed:TimeToFirstByte", "duration": 1, "entryType": "measure" }, { "startTime": 137, - "name": "lh:audit:performance-budget", + "name": "lh:computed:LCPImageRecord", "duration": 1, "entryType": "measure" }, { "startTime": 138, - "name": "lh:computed:ResourceSummary", + "name": "lh:audit:performance-budget", "duration": 1, "entryType": "measure" }, { "startTime": 139, - "name": "lh:computed:EntityClassification", + "name": "lh:computed:ResourceSummary", "duration": 1, "entryType": "measure" }, @@ -6677,6 +6697,12 @@ "timeInMs": 22.397999999999982 }, "path": "audits[network-server-latency].displayValue" + }, + { + "values": { + "timeInMs": 1372.2951999999998 + }, + "path": "audits[largest-contentful-paint-element].displayValue" } ], "core/lib/i18n/i18n.js | maxPotentialFIDMetric": [ @@ -6993,20 +7019,6 @@ "core/audits/largest-contentful-paint-element.js | description": [ "audits[largest-contentful-paint-element].description" ], - "core/lib/i18n/i18n.js | displayValueElementsFound": [ - { - "values": { - "nodeCount": 1 - }, - "path": "audits[largest-contentful-paint-element].displayValue" - }, - { - "values": { - "nodeCount": 5 - }, - "path": "audits[layout-shift-elements].displayValue" - } - ], "core/lib/i18n/i18n.js | columnElement": [ "audits[largest-contentful-paint-element].details.items[0].headings[0].label", "audits[lcp-lazy-loaded].details.headings[0].label", @@ -7046,6 +7058,14 @@ "core/audits/layout-shift-elements.js | description": [ "audits[layout-shift-elements].description" ], + "core/lib/i18n/i18n.js | displayValueElementsFound": [ + { + "values": { + "nodeCount": 5 + }, + "path": "audits[layout-shift-elements].displayValue" + } + ], "core/audits/layout-shift-elements.js | columnContribution": [ "audits[layout-shift-elements].details.headings[1].label" ], @@ -8048,8 +8068,7 @@ "type": "debugdata", "items": [ { - "cumulativeLayoutShiftMainFrame": 0.13125, - "totalCumulativeLayoutShift": 0.13125 + "cumulativeLayoutShiftMainFrame": 0.13125 } ] } @@ -8511,7 +8530,8 @@ "statusCode": 200, "mimeType": "application/javascript", "resourceType": "Script", - "priority": "Low" + "priority": "Low", + "entity": "mikescerealshack.co" }, { "url": "https://www.mikescerealshack.co/logo-text.svg", @@ -8526,7 +8546,8 @@ "statusCode": 200, "mimeType": "image/svg+xml", "resourceType": "Image", - "priority": "High" + "priority": "High", + "entity": "mikescerealshack.co" }, { "url": "https://mnl4bjjsnz-dsn.algolia.net/1/indexes/dev_OFFICE_SCENES/query", @@ -8541,7 +8562,8 @@ "statusCode": 200, "mimeType": "text/plain", "resourceType": "Preflight", - "priority": "High" + "priority": "High", + "entity": "Algolia" }, { "url": "https://mnl4bjjsnz-dsn.algolia.net/1/indexes/dev_OFFICE_SCENES/query", @@ -8556,7 +8578,8 @@ "statusCode": 200, "mimeType": "application/json", "resourceType": "Fetch", - "priority": "High" + "priority": "High", + "entity": "Algolia" }, { "url": "https://www.mikescerealshack.co/_next/static/chunks/pages/index-37980adf97404e76e41a.js", @@ -8571,7 +8594,8 @@ "statusCode": 200, "mimeType": "application/javascript", "resourceType": "Other", - "priority": "VeryLow" + "priority": "VeryLow", + "entity": "mikescerealshack.co" }, { "url": "https://www.mikescerealshack.co/_next/static/chunks/pages/terms-0236318e86139dd7d7f2.js", @@ -8586,7 +8610,8 @@ "statusCode": 200, "mimeType": "application/javascript", "resourceType": "Other", - "priority": "VeryLow" + "priority": "VeryLow", + "entity": "mikescerealshack.co" }, { "url": "https://www.mikescerealshack.co/_next/static/chunks/pages/privacy-864d3895f3c3722acef2.js", @@ -8601,7 +8626,8 @@ "statusCode": 200, "mimeType": "application/javascript", "resourceType": "Other", - "priority": "VeryLow" + "priority": "VeryLow", + "entity": "mikescerealshack.co" }, { "url": "https://www.mikescerealshack.co/_next/static/chunks/pages/privacy-864d3895f3c3722acef2.js", @@ -8616,7 +8642,8 @@ "statusCode": 200, "mimeType": "application/javascript", "resourceType": "Script", - "priority": "Low" + "priority": "Low", + "entity": "mikescerealshack.co" }, { "url": "https://www.mikescerealshack.co/_next/static/chunks/pages/terms-0236318e86139dd7d7f2.js", @@ -8631,7 +8658,8 @@ "statusCode": 200, "mimeType": "application/javascript", "resourceType": "Script", - "priority": "Low" + "priority": "Low", + "entity": "mikescerealshack.co" }, { "url": "https://cdn.mikescerealshack.co/frames/s8/e13/128w/81d89db1bf3d43b5b21f813d2f2a9777.jpg", @@ -8646,7 +8674,8 @@ "statusCode": 200, "mimeType": "image/jpeg", "resourceType": "Image", - "priority": "Low" + "priority": "Low", + "entity": "mikescerealshack.co" }, { "url": "https://cdn.mikescerealshack.co/frames/s3/e3/128w/9b3031eb3988ba363fe946929a79e016.jpg", @@ -8661,7 +8690,8 @@ "statusCode": 200, "mimeType": "image/jpeg", "resourceType": "Image", - "priority": "Low" + "priority": "Low", + "entity": "mikescerealshack.co" }, { "url": "https://cdn.mikescerealshack.co/frames/s3/e3/128w/793a408ca63a660b5d7aa1a41ac126ca.jpg", @@ -8676,7 +8706,8 @@ "statusCode": 200, "mimeType": "image/jpeg", "resourceType": "Image", - "priority": "Low" + "priority": "Low", + "entity": "mikescerealshack.co" }, { "url": "https://cdn.mikescerealshack.co/frames/s7/e11/128w/5d1df07b1741f4c3e66ed20ef00265f5.jpg", @@ -8691,7 +8722,8 @@ "statusCode": 200, "mimeType": "image/jpeg", "resourceType": "Image", - "priority": "Low" + "priority": "Low", + "entity": "mikescerealshack.co" }, { "url": "https://cdn.mikescerealshack.co/frames/s8/e13/128w/b997cdb40263ff124e2a245c5e86a9a3.jpg", @@ -8706,7 +8738,8 @@ "statusCode": 200, "mimeType": "image/jpeg", "resourceType": "Image", - "priority": "Low" + "priority": "Low", + "entity": "mikescerealshack.co" }, { "url": "https://cdn.mikescerealshack.co/frames/s8/e3/128w/08b3049589ca7ae688b0f771f9730caf.jpg", @@ -8721,7 +8754,8 @@ "statusCode": 200, "mimeType": "image/jpeg", "resourceType": "Image", - "priority": "Low" + "priority": "Low", + "entity": "mikescerealshack.co" }, { "url": "https://cdn.mikescerealshack.co/frames/s8/e13/128w/f5c5012a2afa2ac6b190dcd68306dbac.jpg", @@ -8736,7 +8770,8 @@ "statusCode": 200, "mimeType": "image/jpeg", "resourceType": "Image", - "priority": "Low" + "priority": "Low", + "entity": "mikescerealshack.co" }, { "url": "https://cdn.mikescerealshack.co/frames/s9/e9/128w/5fbc916d0fffb01af1225d4ec2ab001d.jpg", @@ -8751,7 +8786,8 @@ "statusCode": 200, "mimeType": "image/jpeg", "resourceType": "Image", - "priority": "Low" + "priority": "Low", + "entity": "mikescerealshack.co" }, { "url": "https://cdn.mikescerealshack.co/frames/s9/e9/128w/558dc2f7d9c947e5445fb3f1838cb62c.jpg", @@ -8766,7 +8802,8 @@ "statusCode": 200, "mimeType": "image/jpeg", "resourceType": "Image", - "priority": "Low" + "priority": "Low", + "entity": "mikescerealshack.co" } ], "debugData": { @@ -10948,43 +10985,43 @@ }, { "startTime": 62, - "name": "lh:audit:network-rtt", + "name": "lh:computed:EntityClassification", "duration": 1, "entryType": "measure" }, { "startTime": 63, - "name": "lh:computed:NetworkAnalysis", + "name": "lh:audit:network-rtt", "duration": 1, "entryType": "measure" }, { "startTime": 64, - "name": "lh:audit:network-server-latency", + "name": "lh:computed:NetworkAnalysis", "duration": 1, "entryType": "measure" }, { "startTime": 65, - "name": "lh:audit:main-thread-tasks", + "name": "lh:audit:network-server-latency", "duration": 1, "entryType": "measure" }, { "startTime": 66, - "name": "lh:audit:resource-summary", + "name": "lh:audit:main-thread-tasks", "duration": 1, "entryType": "measure" }, { "startTime": 67, - "name": "lh:computed:ResourceSummary", + "name": "lh:audit:resource-summary", "duration": 1, "entryType": "measure" }, { "startTime": 68, - "name": "lh:computed:EntityClassification", + "name": "lh:computed:ResourceSummary", "duration": 1, "entryType": "measure" }, @@ -16870,8 +16907,7 @@ "type": "debugdata", "items": [ { - "cumulativeLayoutShiftMainFrame": 0, - "totalCumulativeLayoutShift": 0 + "cumulativeLayoutShiftMainFrame": 0 } ] } @@ -17446,7 +17482,8 @@ "mimeType": "text/html", "resourceType": "Document", "priority": "VeryHigh", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "mikescerealshack.co" }, { "url": "https://www.mikescerealshack.co/fonts/danielbd.woff2", @@ -17463,7 +17500,8 @@ "resourceType": "Font", "priority": "High", "isLinkPreload": true, - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "mikescerealshack.co" }, { "url": "https://events.mikescerealshack.co/js/index.js", @@ -17479,7 +17517,8 @@ "mimeType": "application/javascript", "resourceType": "Script", "priority": "Low", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "mikescerealshack.co" }, { "url": "https://www.mikescerealshack.co/_next/static/css/08dcb440d7d83b488817.css", @@ -17496,7 +17535,8 @@ "resourceType": "Stylesheet", "priority": "VeryHigh", "isLinkPreload": true, - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "mikescerealshack.co" }, { "url": "https://www.mikescerealshack.co/_next/static/chunks/main-1f8481d632114a408557.js", @@ -17513,7 +17553,8 @@ "resourceType": "Script", "priority": "High", "isLinkPreload": true, - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "mikescerealshack.co" }, { "url": "https://www.mikescerealshack.co/_next/static/chunks/webpack-657a8433bac0aabd564e.js", @@ -17530,7 +17571,8 @@ "resourceType": "Script", "priority": "High", "isLinkPreload": true, - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "mikescerealshack.co" }, { "url": "https://www.mikescerealshack.co/_next/static/chunks/framework.9d524150d48315f49e80.js", @@ -17547,7 +17589,8 @@ "resourceType": "Script", "priority": "High", "isLinkPreload": true, - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "mikescerealshack.co" }, { "url": "https://www.mikescerealshack.co/_next/static/chunks/commons.49455e4fa8cc3f51203f.js", @@ -17564,7 +17607,8 @@ "resourceType": "Script", "priority": "High", "isLinkPreload": true, - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "mikescerealshack.co" }, { "url": "https://www.mikescerealshack.co/_next/static/chunks/pages/_app-ef508c97234d1af96c47.js", @@ -17581,7 +17625,8 @@ "resourceType": "Script", "priority": "High", "isLinkPreload": true, - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "mikescerealshack.co" }, { "url": "https://www.mikescerealshack.co/_next/static/chunks/1aeab0175d4c4d823d7a78205bceb5dd9cd36d32.a629f28ec97ae6e480bf.js", @@ -17598,7 +17643,8 @@ "resourceType": "Script", "priority": "High", "isLinkPreload": true, - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "mikescerealshack.co" }, { "url": "https://www.mikescerealshack.co/_next/static/chunks/pages/corrections-7a620a51252fe2c2f77b.js", @@ -17615,7 +17661,8 @@ "resourceType": "Script", "priority": "High", "isLinkPreload": true, - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "mikescerealshack.co" }, { "url": "https://www.mikescerealshack.co/logo-text.svg", @@ -17631,7 +17678,8 @@ "mimeType": "image/svg+xml", "resourceType": "Image", "priority": "Low", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "mikescerealshack.co" }, { "url": "https://www.mikescerealshack.co/oscar-actually.jpg", @@ -17647,7 +17695,8 @@ "mimeType": "image/jpeg", "resourceType": "Image", "priority": "High", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "mikescerealshack.co" }, { "url": "https://www.mikescerealshack.co/_next/static/t5QnfQSErVZVsTAuFcBWI/_buildManifest.js", @@ -17663,7 +17712,8 @@ "mimeType": "application/javascript", "resourceType": "Script", "priority": "Low", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "mikescerealshack.co" }, { "url": "https://www.mikescerealshack.co/_next/static/t5QnfQSErVZVsTAuFcBWI/_ssgManifest.js", @@ -17679,7 +17729,8 @@ "mimeType": "application/javascript", "resourceType": "Script", "priority": "Low", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "mikescerealshack.co" }, { "url": "https://fonts.googleapis.com/css2?family=Poppins:wght@400;500;700&display=swap", @@ -17695,7 +17746,8 @@ "mimeType": "text/css", "resourceType": "Stylesheet", "priority": "VeryLow", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "Google Fonts" }, { "url": "https://fonts.gstatic.com/s/poppins/v20/pxiByp8kv8JHgFVrLCz7Z1xlFd2JQEk.woff2", @@ -17711,7 +17763,8 @@ "mimeType": "font/woff2", "resourceType": "Font", "priority": "VeryHigh", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "Google Fonts" }, { "url": "https://fonts.gstatic.com/s/poppins/v20/pxiEyp8kv8JHgFVrJJfecnFHGPc.woff2", @@ -17727,7 +17780,8 @@ "mimeType": "font/woff2", "resourceType": "Font", "priority": "VeryHigh", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "Google Fonts" }, { "url": "https://www.mikescerealshack.co/_next/static/chunks/1aeab0175d4c4d823d7a78205bceb5dd9cd36d32.a629f28ec97ae6e480bf.js", @@ -17743,7 +17797,8 @@ "mimeType": "application/javascript", "resourceType": "Other", "priority": "VeryLow", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "mikescerealshack.co" }, { "url": "https://www.mikescerealshack.co/_next/static/chunks/pages/index-37980adf97404e76e41a.js", @@ -17759,7 +17814,8 @@ "mimeType": "application/javascript", "resourceType": "Other", "priority": "VeryLow", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "mikescerealshack.co" }, { "url": "https://www.mikescerealshack.co/_next/static/chunks/pages/index-37980adf97404e76e41a.js", @@ -17775,7 +17831,8 @@ "mimeType": "application/javascript", "resourceType": "Script", "priority": "Low", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "mikescerealshack.co" } ], "debugData": { @@ -17945,7 +18002,6 @@ "maxPotentialFID": 76, "cumulativeLayoutShift": 0, "cumulativeLayoutShiftMainFrame": 0, - "totalCumulativeLayoutShift": 0, "lcpLoadStart": 603, "lcpLoadEnd": 837, "timeToFirstByte": 603, @@ -17973,7 +18029,6 @@ "observedDomContentLoadedTs": 183729805229, "observedCumulativeLayoutShift": 0, "observedCumulativeLayoutShiftMainFrame": 0, - "observedTotalCumulativeLayoutShift": 0, "observedFirstVisualChange": 89, "observedFirstVisualChangeTs": 183729849318, "observedLastVisualChange": 505, @@ -18151,7 +18206,7 @@ "description": "This is the largest contentful element painted within the viewport. [Learn more about the Largest Contentful Paint element](https://developer.chrome.com/docs/lighthouse/performance/lighthouse-largest-contentful-paint/)", "score": null, "scoreDisplayMode": "informative", - "displayValue": "1 element found", + "displayValue": "1,800 ms", "details": { "type": "list", "items": [ @@ -22306,79 +22361,79 @@ }, { "startTime": 125, - "name": "lh:audit:network-rtt", + "name": "lh:computed:EntityClassification", "duration": 1, "entryType": "measure" }, { "startTime": 126, - "name": "lh:audit:network-server-latency", + "name": "lh:audit:network-rtt", "duration": 1, "entryType": "measure" }, { "startTime": 127, - "name": "lh:audit:main-thread-tasks", + "name": "lh:audit:network-server-latency", "duration": 1, "entryType": "measure" }, { "startTime": 128, - "name": "lh:audit:metrics", + "name": "lh:audit:main-thread-tasks", "duration": 1, "entryType": "measure" }, { "startTime": 129, - "name": "lh:computed:TimingSummary", + "name": "lh:audit:metrics", "duration": 1, "entryType": "measure" }, { "startTime": 130, - "name": "lh:computed:FirstContentfulPaintAllFrames", + "name": "lh:computed:TimingSummary", "duration": 1, "entryType": "measure" }, { "startTime": 131, - "name": "lh:computed:LargestContentfulPaintAllFrames", + "name": "lh:computed:FirstContentfulPaintAllFrames", "duration": 1, "entryType": "measure" }, { "startTime": 132, - "name": "lh:computed:LCPBreakdown", + "name": "lh:computed:LargestContentfulPaintAllFrames", "duration": 1, "entryType": "measure" }, { "startTime": 133, - "name": "lh:computed:TimeToFirstByte", + "name": "lh:computed:LCPBreakdown", "duration": 1, "entryType": "measure" }, { "startTime": 134, - "name": "lh:computed:LCPImageRecord", + "name": "lh:computed:TimeToFirstByte", "duration": 1, "entryType": "measure" }, { "startTime": 135, - "name": "lh:audit:performance-budget", + "name": "lh:computed:LCPImageRecord", "duration": 1, "entryType": "measure" }, { "startTime": 136, - "name": "lh:computed:ResourceSummary", + "name": "lh:audit:performance-budget", "duration": 1, "entryType": "measure" }, { "startTime": 137, - "name": "lh:computed:EntityClassification", + "name": "lh:computed:ResourceSummary", "duration": 1, "entryType": "measure" }, @@ -23353,6 +23408,12 @@ "timeInMs": 3.5377 }, "path": "audits[network-server-latency].displayValue" + }, + { + "values": { + "timeInMs": 1803.0092 + }, + "path": "audits[largest-contentful-paint-element].displayValue" } ], "core/lib/i18n/i18n.js | maxPotentialFIDMetric": [ @@ -23671,14 +23732,6 @@ "core/audits/largest-contentful-paint-element.js | description": [ "audits[largest-contentful-paint-element].description" ], - "core/lib/i18n/i18n.js | displayValueElementsFound": [ - { - "values": { - "nodeCount": 1 - }, - "path": "audits[largest-contentful-paint-element].displayValue" - } - ], "core/lib/i18n/i18n.js | columnElement": [ "audits[largest-contentful-paint-element].details.items[0].headings[0].label", "audits[lcp-lazy-loaded].details.headings[0].label", diff --git a/core/test/fixtures/lantern-baseline-accuracy.json b/core/test/fixtures/lantern-baseline-accuracy.json index 96636360fbf6..a73d62dea4f1 100644 --- a/core/test/fixtures/lantern-baseline-accuracy.json +++ b/core/test/fixtures/lantern-baseline-accuracy.json @@ -16,7 +16,7 @@ }, "roughEstimateOfTTI": { "p50": 0.27676284306826177, - "p90": 0.667039168575739, + "p90": 0.6586020003352517, "p95": 0.7422988097352994 }, "roughEstimateOfLCP": { diff --git a/core/test/fixtures/lantern-baseline-computed-values.json b/core/test/fixtures/lantern-baseline-computed-values.json index c0819f368760..a8146ecc6c45 100644 --- a/core/test/fixtures/lantern-baseline-computed-values.json +++ b/core/test/fixtures/lantern-baseline-computed-values.json @@ -4,7 +4,7 @@ {"url": "http://www.zol.com.cn/", "roughEstimateOfFCP": 3447, "optimisticFCP": 3447, "pessimisticFCP": 3447, "roughEstimateOfFMP": 3447, "optimisticFMP": 3447, "pessimisticFMP": 3447, "roughEstimateOfTTI": 15991, "optimisticTTI": 15003, "pessimisticTTI": 16979, "roughEstimateOfSI": 12512, "optimisticSI": 4861, "pessimisticSI": 9164, "roughEstimateOfLCP": 4369, "optimisticLCP": 4194, "pessimisticLCP": 4544, "roughEstimateOfTTFB": 648}, {"url": "https://birdsarentreal.com", "roughEstimateOfFCP": 2962, "optimisticFCP": 2962, "pessimisticFCP": 2962, "roughEstimateOfFMP": 3448, "optimisticFMP": 3124, "pessimisticFMP": 3772, "roughEstimateOfTTI": 13465, "optimisticTTI": 12107, "pessimisticTTI": 14823, "roughEstimateOfSI": 5123, "optimisticSI": 1323, "pessimisticSI": 5417, "roughEstimateOfLCP": 7754, "optimisticLCP": 6986, "pessimisticLCP": 8523, "roughEstimateOfTTFB": 701}, {"url": "https://depositfiles.com/", "roughEstimateOfFCP": 5098, "optimisticFCP": 5098, "pessimisticFCP": 5098, "roughEstimateOfFMP": 5486, "optimisticFMP": 5098, "pessimisticFMP": 5874, "roughEstimateOfTTI": 5982, "optimisticTTI": 5854, "pessimisticTTI": 6109, "roughEstimateOfSI": 7568, "optimisticSI": 2787, "pessimisticSI": 6025, "roughEstimateOfLCP": 6034, "optimisticLCP": 6034, "pessimisticLCP": 6034, "roughEstimateOfTTFB": 907}, - {"url": "https://en-maktoob.yahoo.com/?p=xa", "roughEstimateOfFCP": 1410, "optimisticFCP": 1410, "pessimisticFCP": 1410, "roughEstimateOfFMP": 1427, "optimisticFMP": 1410, "pessimisticFMP": 1443, "roughEstimateOfTTI": 5959, "optimisticTTI": 5356, "pessimisticTTI": 6563, "roughEstimateOfSI": 3693, "optimisticSI": 1039, "pessimisticSI": 3829, "roughEstimateOfLCP": 7119, "optimisticLCP": 7003, "pessimisticLCP": 7235, "roughEstimateOfTTFB": 618}, + {"url": "https://en-maktoob.yahoo.com/?p=xa", "roughEstimateOfFCP": 1410, "optimisticFCP": 1410, "pessimisticFCP": 1410, "roughEstimateOfFMP": 1427, "optimisticFMP": 1410, "pessimisticFMP": 1443, "roughEstimateOfTTI": 6110, "optimisticTTI": 5167, "pessimisticTTI": 7054, "roughEstimateOfSI": 3885, "optimisticSI": 1039, "pessimisticSI": 4125, "roughEstimateOfLCP": 7333, "optimisticLCP": 7251, "pessimisticLCP": 7416, "roughEstimateOfTTFB": 618}, {"url": "https://en.softonic.com", "roughEstimateOfFCP": 2191, "optimisticFCP": 2191, "pessimisticFCP": 2191, "roughEstimateOfFMP": 2584, "optimisticFMP": 2191, "pessimisticFMP": 2977, "roughEstimateOfTTI": 31427, "optimisticTTI": 27015, "pessimisticTTI": 35839, "roughEstimateOfSI": 12996, "optimisticSI": 3067, "pessimisticSI": 13771, "roughEstimateOfLCP": 3915, "optimisticLCP": 3504, "pessimisticLCP": 4325, "roughEstimateOfTTFB": 899}, {"url": "https://gm.58.com/glsanfrancisco-sl/", "roughEstimateOfFCP": 3019, "optimisticFCP": 3019, "pessimisticFCP": 3019, "roughEstimateOfFMP": 3019, "optimisticFMP": 3019, "pessimisticFMP": 3019, "roughEstimateOfTTI": 4785, "optimisticTTI": 4436, "pessimisticTTI": 5134, "roughEstimateOfSI": 4605, "optimisticSI": 1762, "pessimisticSI": 3674, "roughEstimateOfLCP": 5337, "optimisticLCP": 5045, "pessimisticLCP": 5630, "roughEstimateOfTTFB": 787}, {"url": "https://m.facebook.com/", "roughEstimateOfFCP": 2438, "optimisticFCP": 2407, "pessimisticFCP": 2468, "roughEstimateOfFMP": 2438, "optimisticFMP": 2407, "pessimisticFMP": 2468, "roughEstimateOfTTI": 4822, "optimisticTTI": 4217, "pessimisticTTI": 5427, "roughEstimateOfSI": 2685, "optimisticSI": 479, "pessimisticSI": 3484, "roughEstimateOfLCP": 3422, "optimisticLCP": 3391, "pessimisticLCP": 3452, "roughEstimateOfTTFB": 626}, @@ -28,7 +28,7 @@ {"url": "https://www.att.com/", "roughEstimateOfFCP": 5457, "optimisticFCP": 5005, "pessimisticFCP": 5910, "roughEstimateOfFMP": 5698, "optimisticFMP": 5005, "pessimisticFMP": 6391, "roughEstimateOfTTI": 30075, "optimisticTTI": 27319, "pessimisticTTI": 32831, "roughEstimateOfSI": 9164, "optimisticSI": 1858, "pessimisticSI": 10482, "roughEstimateOfLCP": 13817, "optimisticLCP": 13737, "pessimisticLCP": 13897, "roughEstimateOfTTFB": 651}, {"url": "https://www.bing.com/", "roughEstimateOfFCP": 962, "optimisticFCP": 962, "pessimisticFCP": 962, "roughEstimateOfFMP": 1339, "optimisticFMP": 962, "pessimisticFMP": 1717, "roughEstimateOfTTI": 2491, "optimisticTTI": 2241, "pessimisticTTI": 2741, "roughEstimateOfSI": 1565, "optimisticSI": 467, "pessimisticSI": 1788, "roughEstimateOfLCP": 1548, "optimisticLCP": 1262, "pessimisticLCP": 1834, "roughEstimateOfTTFB": 608}, {"url": "https://www.blogger.com/about/", "roughEstimateOfFCP": 1533, "optimisticFCP": 1533, "pessimisticFCP": 1533, "roughEstimateOfFMP": 2106, "optimisticFMP": 1956, "pessimisticFMP": 2256, "roughEstimateOfTTI": 2251, "optimisticTTI": 2222, "pessimisticTTI": 2280, "roughEstimateOfSI": 6828, "optimisticSI": 4188, "pessimisticSI": 1870, "roughEstimateOfLCP": 2385, "optimisticLCP": 2280, "pessimisticLCP": 2489, "roughEstimateOfTTFB": 603}, - {"url": "https://www.cnet.com/", "roughEstimateOfFCP": 2578, "optimisticFCP": 2218, "pessimisticFCP": 2938, "roughEstimateOfFMP": 2814, "optimisticFMP": 2539, "pessimisticFMP": 3089, "roughEstimateOfTTI": 43169, "optimisticTTI": 39862, "pessimisticTTI": 46476, "roughEstimateOfSI": 15833, "optimisticSI": 1339, "pessimisticSI": 21859, "roughEstimateOfLCP": 4265, "optimisticLCP": 4185, "pessimisticLCP": 4346, "roughEstimateOfTTFB": 608}, + {"url": "https://www.cnet.com/", "roughEstimateOfFCP": 2578, "optimisticFCP": 2218, "pessimisticFCP": 2938, "roughEstimateOfFMP": 2814, "optimisticFMP": 2539, "pessimisticFMP": 3089, "roughEstimateOfTTI": 43169, "optimisticTTI": 39862, "pessimisticTTI": 46476, "roughEstimateOfSI": 15832, "optimisticSI": 1339, "pessimisticSI": 21858, "roughEstimateOfLCP": 4265, "optimisticLCP": 4185, "pessimisticLCP": 4346, "roughEstimateOfTTFB": 608}, {"url": "https://www.codewars.com", "roughEstimateOfFCP": 2248, "optimisticFCP": 2248, "pessimisticFCP": 2248, "roughEstimateOfFMP": 3453, "optimisticFMP": 2422, "pessimisticFMP": 4483, "roughEstimateOfTTI": 8825, "optimisticTTI": 7042, "pessimisticTTI": 10608, "roughEstimateOfSI": 4008, "optimisticSI": 834, "pessimisticSI": 4755, "roughEstimateOfLCP": 9643, "optimisticLCP": 9318, "pessimisticLCP": 9968, "roughEstimateOfTTFB": 609}, {"url": "https://www.dawn.com/", "roughEstimateOfFCP": 2588, "optimisticFCP": 2262, "pessimisticFCP": 2914, "roughEstimateOfFMP": 2832, "optimisticFMP": 2588, "pessimisticFMP": 3077, "roughEstimateOfTTI": 25693, "optimisticTTI": 23532, "pessimisticTTI": 27855, "roughEstimateOfSI": 10399, "optimisticSI": 1332, "pessimisticSI": 13514, "roughEstimateOfLCP": 3892, "optimisticLCP": 3240, "pessimisticLCP": 4543, "roughEstimateOfTTFB": 652}, {"url": "https://www.deviantart.com/", "roughEstimateOfFCP": 2926, "optimisticFCP": 2926, "pessimisticFCP": 2926, "roughEstimateOfFMP": 2926, "optimisticFMP": 2926, "pessimisticFMP": 2926, "roughEstimateOfTTI": 13024, "optimisticTTI": 11062, "pessimisticTTI": 14985, "roughEstimateOfSI": 3089, "optimisticSI": 996, "pessimisticSI": 2992, "roughEstimateOfLCP": 11953, "optimisticLCP": 10408, "pessimisticLCP": 13497, "roughEstimateOfTTFB": 1009}, diff --git a/core/test/gather/driver/execution-context-test.js b/core/test/gather/driver/execution-context-test.js index b00b2fcacd4c..c8e2d5bdc904 100644 --- a/core/test/gather/driver/execution-context-test.js +++ b/core/test/gather/driver/execution-context-test.js @@ -187,6 +187,37 @@ describe('.evaluateAsync', () => { const value = await executionContext.evaluateAsync('"magic"', {useIsolation: true}); expect(value).toEqual('mocked value'); }); + + it('handles runtime evaluation exception', async () => { + /** @type {LH.Crdp.Runtime.ExceptionDetails} */ + const exceptionDetails = { + exceptionId: 1, + text: 'Uncaught', + lineNumber: 7, + columnNumber: 8, + stackTrace: {description: '', callFrames: []}, + exception: { + type: 'object', + subtype: 'error', + className: 'ReferenceError', + description: 'ReferenceError: Prosmise is not defined\n' + + ' at wrapInNativePromise (_lighthouse-eval.js:8:9)\n' + + ' at _lighthouse-eval.js:83:8', + }, + }; + sessionMock.sendCommand = createMockSendCommandFn() + .mockResponse('Page.enable') + .mockResponse('Runtime.enable') + .mockResponse('Page.getResourceTree', {frameTree: {frame: {id: '1337'}}}) + .mockResponse('Page.getFrameTree', {frameTree: {frame: {id: '1337'}}}) + .mockResponse('Page.createIsolatedWorld', {executionContextId: 9001}) + .mockResponse('Runtime.evaluate', {exceptionDetails}); + + const promise = executionContext.evaluateAsync('new Prosmise', {useIsolation: true}); + await expect(promise).rejects.toThrow(/Expression: new Prosmise/); + await expect(promise).rejects.toThrow(/elided/); + await expect(promise).rejects.toThrow(/at wrapInNativePromise/); + }); }); describe('.evaluate', () => { diff --git a/core/test/gather/gatherers/inspector-issues-test.js b/core/test/gather/gatherers/inspector-issues-test.js index 68061624d9d6..4f18572c76c8 100644 --- a/core/test/gather/gatherers/inspector-issues-test.js +++ b/core/test/gather/gatherers/inspector-issues-test.js @@ -246,6 +246,8 @@ describe('_getArtifact', () => { quirksModeIssue: [], sharedArrayBufferIssue: [], federatedAuthRequestIssue: [], + stylesheetLoadingIssue: [], + federatedAuthUserInfoRequestIssue: [], }); }); @@ -303,6 +305,8 @@ describe('_getArtifact', () => { quirksModeIssue: [], sharedArrayBufferIssue: [], federatedAuthRequestIssue: [], + stylesheetLoadingIssue: [], + federatedAuthUserInfoRequestIssue: [], }); }); }); @@ -367,6 +371,8 @@ describe('FR compat (inspector-issues)', () => { quirksModeIssue: [], sharedArrayBufferIssue: [], federatedAuthRequestIssue: [], + stylesheetLoadingIssue: [], + federatedAuthUserInfoRequestIssue: [], }); }); @@ -403,6 +409,8 @@ describe('FR compat (inspector-issues)', () => { quirksModeIssue: [], sharedArrayBufferIssue: [], federatedAuthRequestIssue: [], + stylesheetLoadingIssue: [], + federatedAuthUserInfoRequestIssue: [], }); }); }); diff --git a/core/test/lib/asset-saver-test.js b/core/test/lib/asset-saver-test.js index d567592209a7..96cdda27d34a 100644 --- a/core/test/lib/asset-saver-test.js +++ b/core/test/lib/asset-saver-test.js @@ -370,7 +370,9 @@ describe('asset-saver helper', () => { // Use an LighthouseError that has an ICU replacement. const protocolMethod = 'Page.getFastness'; const lhError = new LighthouseError( - LighthouseError.errors.PROTOCOL_TIMEOUT, {protocolMethod}); + LighthouseError.errors.PROTOCOL_TIMEOUT, + {protocolMethod}, + {cause: new Error('the cause')}); const artifacts = { traces: {}, @@ -385,6 +387,8 @@ describe('asset-saver helper', () => { expect(roundTripArtifacts.ScriptElements).toBeInstanceOf(LighthouseError); expect(roundTripArtifacts.ScriptElements.code).toEqual('PROTOCOL_TIMEOUT'); expect(roundTripArtifacts.ScriptElements.protocolMethod).toEqual(protocolMethod); + expect(roundTripArtifacts.ScriptElements.cause).toBeInstanceOf(Error); + expect(roundTripArtifacts.ScriptElements.cause.message).toEqual('the cause'); expect(roundTripArtifacts.ScriptElements.stack).toMatch( /^LighthouseError: PROTOCOL_TIMEOUT.*test[\\/]lib[\\/]asset-saver-test\.js/s); expect(roundTripArtifacts.ScriptElements.friendlyMessage) @@ -439,4 +443,29 @@ describe('asset-saver helper', () => { }); }); }); + + describe('elideAuditErrorStacks', () => { + it('elides correctly', async () => { + const lhr = JSON.parse(JSON.stringify(dbwResults)); + lhr.audits['bf-cache'].errorStack = `Error: LighthouseError: ERRORED_REQUIRED_ARTIFACT + at Runner._runAudit (${LH_ROOT}/core/runner.js:431:25) + at Runner._runAudits (${LH_ROOT}/core/runner.js:370:40) + at process.processTicksAndRejections (node:internal/process/task_queues:95:5) + at async Runner.audit (${LH_ROOT}/core/runner.js:62:32) + at async runLighthouse (${LH_ROOT}/cli/run.js:250:8) + at async ${LH_ROOT}/cli/index.js:10:1 + at :1:1`; + assetSaver.elideAuditErrorStacks(lhr); + + // eslint-disable-next-line max-len + expect(lhr.audits['bf-cache'].errorStack).toEqual(`Error: LighthouseError: ERRORED_REQUIRED_ARTIFACT + at Runner._runAudit (/core/runner.js) + at Runner._runAudits (/core/runner.js) + at process.processTicksAndRejections (node:internal/process/task_queues) + at async Runner.audit (/core/runner.js) + at async runLighthouse (/cli/run.js) + at async /cli/index.js + at `); + }); + }); }); diff --git a/core/test/lib/dependency-graph/simulator/network-analyzer-test.js b/core/test/lib/dependency-graph/simulator/network-analyzer-test.js index 02f1401bdbb8..d249dc2e21d9 100644 --- a/core/test/lib/dependency-graph/simulator/network-analyzer-test.js +++ b/core/test/lib/dependency-graph/simulator/network-analyzer-test.js @@ -136,7 +136,15 @@ describe('DependencyGraph/Simulator/NetworkAnalyzer', () => { describe('#estimateRTTByOrigin', () => { it('should infer from tcp timing when available', () => { - const timing = {connectStart: 1, connectEnd: 100}; + const timing = {connectStart: 0, connectEnd: 99}; + const record = createRecord({networkRequestTime: 0, networkEndTime: 1, timing}); + const result = NetworkAnalyzer.estimateRTTByOrigin([record]); + const expected = {min: 99, max: 99, avg: 99, median: 99}; + assert.deepStrictEqual(result.get('https://example.com'), expected); + }); + + it('should infer only one estimate if tcp and ssl start times are equal', () => { + const timing = {connectStart: 0, connectEnd: 99, sslStart: 0, sslEnd: 99}; const record = createRecord({networkRequestTime: 0, networkEndTime: 1, timing}); const result = NetworkAnalyzer.estimateRTTByOrigin([record]); const expected = {min: 99, max: 99, avg: 99, median: 99}; @@ -144,7 +152,7 @@ describe('DependencyGraph/Simulator/NetworkAnalyzer', () => { }); it('should infer from tcp and ssl timing when available', () => { - const timing = {connectStart: 1, connectEnd: 100, sslStart: 50, sslEnd: 100}; + const timing = {connectStart: 0, connectEnd: 99, sslStart: 50, sslEnd: 99}; const record = createRecord({networkRequestTime: 0, networkEndTime: 1, timing}); const result = NetworkAnalyzer.estimateRTTByOrigin([record]); const expected = {min: 49, max: 50, avg: 49.5, median: 49.5}; @@ -152,7 +160,7 @@ describe('DependencyGraph/Simulator/NetworkAnalyzer', () => { }); it('should infer from connection timing when available for h3 (one estimate)', () => { - const timing = {connectStart: 1, connectEnd: 100, sslStart: 1, sslEnd: 100}; + const timing = {connectStart: 0, connectEnd: 99, sslStart: 1, sslEnd: 99}; const record = createRecord({networkRequestTime: 0, networkEndTime: 1, timing, protocol: 'h3'}); const result = NetworkAnalyzer.estimateRTTByOrigin([record]); diff --git a/core/test/lib/network-request-test.js b/core/test/lib/network-request-test.js index c22888443ec9..cf963de66851 100644 --- a/core/test/lib/network-request-test.js +++ b/core/test/lib/network-request-test.js @@ -13,6 +13,17 @@ describe('NetworkRequest', () => { global.isLightrider = undefined; }); + it('backcompat for receiveHeadersStart', function() { + const req = { + timing: {receiveHeadersEnd: 123}, + }; + const devtoolsLog = networkRecordsToDevtoolsLog([req]); + const record = NetworkRecorder.recordsFromLogs(devtoolsLog)[0]; + + expect(record.timing.receiveHeadersStart).toEqual(123); + expect(record.timing.receiveHeadersEnd).toEqual(123); + }); + describe('update transfer size for Lightrider', () => { function getRequest() { return { @@ -108,7 +119,7 @@ describe('NetworkRequest', () => { }); }); - describe('update fetch stats for Lightrider', () => { + describe('update timings for Lightrider', () => { function getRequest() { return { rendererStartTime: 0, diff --git a/core/test/results/sample_v2.json b/core/test/results/sample_v2.json index 73efc6dccfd6..5c77b04d1d2a 100644 --- a/core/test/results/sample_v2.json +++ b/core/test/results/sample_v2.json @@ -200,8 +200,7 @@ "type": "debugdata", "items": [ { - "cumulativeLayoutShiftMainFrame": 0.13570762803819444, - "totalCumulativeLayoutShift": 0.13570762803819444 + "cumulativeLayoutShiftMainFrame": 0.13570762803819444 } ] } @@ -1277,7 +1276,8 @@ "mimeType": "text/html", "resourceType": "Document", "priority": "VeryHigh", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "localhost" }, { "url": "http://localhost:10200/dobetterweb/dbw_tester.css?delay=100", @@ -1293,7 +1293,8 @@ "mimeType": "text/css", "resourceType": "Stylesheet", "priority": "VeryHigh", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "localhost" }, { "url": "http://localhost:10200/dobetterweb/unknown404.css?delay=200", @@ -1309,7 +1310,8 @@ "mimeType": "text/css", "resourceType": "Stylesheet", "priority": "VeryHigh", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "localhost" }, { "url": "http://localhost:10200/dobetterweb/dbw_tester.css?delay=2200", @@ -1325,7 +1327,8 @@ "mimeType": "text/css", "resourceType": "Stylesheet", "priority": "VeryHigh", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "localhost" }, { "url": "http://localhost:10200/dobetterweb/dbw_disabled.css?delay=200&isdisabled", @@ -1341,7 +1344,8 @@ "mimeType": "text/css", "resourceType": "Stylesheet", "priority": "VeryHigh", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "localhost" }, { "url": "http://localhost:10200/dobetterweb/dbw_tester.css?delay=3000&capped", @@ -1357,7 +1361,8 @@ "mimeType": "text/css", "resourceType": "Stylesheet", "priority": "VeryHigh", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "localhost" }, { "url": "http://localhost:10200/dobetterweb/dbw_tester.css?delay=2000&async=true", @@ -1374,7 +1379,8 @@ "resourceType": "Stylesheet", "priority": "VeryHigh", "isLinkPreload": true, - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "localhost" }, { "url": "http://localhost:10200/dobetterweb/dbw_tester.css?delay=3000&async=true", @@ -1390,7 +1396,8 @@ "mimeType": "text/css", "resourceType": "Stylesheet", "priority": "VeryHigh", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "localhost" }, { "url": "http://localhost:10200/dobetterweb/dbw_tester.js", @@ -1406,7 +1413,8 @@ "mimeType": "application/javascript", "resourceType": "Script", "priority": "High", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "localhost" }, { "url": "http://localhost:10200/dobetterweb/empty_module.js?delay=500", @@ -1422,7 +1430,8 @@ "mimeType": "application/javascript", "resourceType": "Script", "priority": "High", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "localhost" }, { "url": "http://localhost:10200/dobetterweb/empty.css", @@ -1438,7 +1447,8 @@ "mimeType": "text/css", "resourceType": "Stylesheet", "priority": "VeryLow", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "localhost" }, { "url": "http://localhost:10200/dobetterweb/fcp-delayer.js?delay=5000", @@ -1454,7 +1464,8 @@ "mimeType": "application/javascript", "resourceType": "Script", "priority": "High", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "localhost" }, { "url": "http://localhost:10200/dobetterweb/lighthouse-480x318.jpg?iar1", @@ -1470,7 +1481,8 @@ "mimeType": "image/jpeg", "resourceType": "Image", "priority": "Low", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "localhost" }, { "url": "http://localhost:10200/dobetterweb/lighthouse-480x318.jpg?isr1", @@ -1486,7 +1498,8 @@ "mimeType": "image/jpeg", "resourceType": "Image", "priority": "High", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "localhost" }, { "url": "http://localhost:10200/dobetterweb/lighthouse-480x318.jpg?isr2", @@ -1502,7 +1515,8 @@ "mimeType": "image/jpeg", "resourceType": "Image", "priority": "High", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "localhost" }, { "url": "http://localhost:10200/dobetterweb/lighthouse-480x318.jpg?isr3", @@ -1518,7 +1532,8 @@ "mimeType": "image/jpeg", "resourceType": "Image", "priority": "High", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "localhost" }, { "url": "http://localhost:10200/dobetterweb/lighthouse-480x318.jpg", @@ -1534,7 +1549,8 @@ "mimeType": "image/jpeg", "resourceType": "Image", "priority": "High", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "localhost" }, { "url": "http://localhost:10200/dobetterweb/lighthouse-rotating.gif", @@ -1550,7 +1566,8 @@ "mimeType": "image/gif", "resourceType": "Image", "priority": "Low", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "localhost" }, { "url": "http://localhost:10200/dobetterweb/third_party/aggressive-promise-polyfill.js", @@ -1566,7 +1583,8 @@ "mimeType": "application/javascript", "resourceType": "Script", "priority": "Medium", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "localhost" }, { "url": "http://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js", @@ -1582,7 +1600,8 @@ "mimeType": "text/javascript", "resourceType": "Script", "priority": "Medium", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "Google CDN" }, { "url": "http://localhost:10200/dobetterweb/lighthouse-480x318.jpg?iar2", @@ -1598,7 +1617,8 @@ "mimeType": "image/jpeg", "resourceType": "Image", "priority": "High", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "localhost" }, { "url": "http://localhost:10200/dobetterweb/dbw_tester.css?scriptActivated&delay=200", @@ -1614,7 +1634,8 @@ "mimeType": "text/css", "resourceType": "Stylesheet", "priority": "VeryHigh", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "localhost" }, { "url": "http://localhost:10200/dobetterweb/dbw_tester.html", @@ -1630,7 +1651,8 @@ "mimeType": "text/html", "resourceType": "XHR", "priority": "VeryHigh", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "localhost" }, { "url": "blob:http://localhost:10200/3f2bc9df-684b-4541-837c-1590152ef65d", @@ -1678,7 +1700,8 @@ "mimeType": "image/vnd.microsoft.icon", "resourceType": "Other", "priority": "High", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "localhost" }, { "url": "http://localhost:10200/dobetterweb/lighthouse-1024x680.jpg?lcp&redirect=lighthouse-1024x680.jpg%3Fredirected-lcp", @@ -1693,7 +1716,8 @@ "statusCode": 302, "mimeType": "", "priority": "High", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "localhost" }, { "url": "http://localhost:10200/dobetterweb/lighthouse-1024x680.jpg?redirected-lcp", @@ -1709,7 +1733,8 @@ "mimeType": "image/jpeg", "resourceType": "Image", "priority": "High", - "experimentalFromMainFrame": true + "experimentalFromMainFrame": true, + "entity": "localhost" } ], "debugData": { @@ -1916,7 +1941,6 @@ "maxPotentialFID": 1175, "cumulativeLayoutShift": 0.13570762803819444, "cumulativeLayoutShiftMainFrame": 0.13570762803819444, - "totalCumulativeLayoutShift": 0.13570762803819444, "lcpLoadStart": 10849, "lcpLoadEnd": 12900, "timeToFirstByte": 572, @@ -1945,7 +1969,6 @@ "observedDomContentLoadedTs": 8704886496, "observedCumulativeLayoutShift": 0.13570762803819444, "observedCumulativeLayoutShiftMainFrame": 0.13570762803819444, - "observedTotalCumulativeLayoutShift": 0.13570762803819444, "observedFirstVisualChange": 8058, "observedFirstVisualChangeTs": 8704758822, "observedLastVisualChange": 8893, @@ -2283,7 +2306,7 @@ "description": "This is the largest contentful element painted within the viewport. [Learn more about the Largest Contentful Paint element](https://developer.chrome.com/docs/lighthouse/performance/lighthouse-largest-contentful-paint/)", "score": null, "scoreDisplayMode": "informative", - "displayValue": "1 element found", + "displayValue": "13,320 ms", "details": { "type": "list", "items": [ @@ -7873,6 +7896,12 @@ "duration": 100, "entryType": "measure" }, + { + "startTime": 0, + "name": "lh:computed:EntityClassification", + "duration": 100, + "entryType": "measure" + }, { "startTime": 0, "name": "lh:audit:network-rtt", @@ -7945,12 +7974,6 @@ "duration": 100, "entryType": "measure" }, - { - "startTime": 0, - "name": "lh:computed:EntityClassification", - "duration": 100, - "entryType": "measure" - }, { "startTime": 0, "name": "lh:audit:timing-budget", @@ -8983,6 +9006,12 @@ "timeInMs": 582.2760000000001 }, "path": "audits[network-server-latency].displayValue" + }, + { + "values": { + "timeInMs": 13319.961 + }, + "path": "audits[largest-contentful-paint-element].displayValue" } ], "core/lib/i18n/i18n.js | maxPotentialFIDMetric": [ @@ -9403,20 +9432,6 @@ "core/audits/largest-contentful-paint-element.js | description": [ "audits[largest-contentful-paint-element].description" ], - "core/lib/i18n/i18n.js | displayValueElementsFound": [ - { - "values": { - "nodeCount": 1 - }, - "path": "audits[largest-contentful-paint-element].displayValue" - }, - { - "values": { - "nodeCount": 5 - }, - "path": "audits[layout-shift-elements].displayValue" - } - ], "core/lib/i18n/i18n.js | columnElement": [ "audits[largest-contentful-paint-element].details.items[0].headings[0].label", "audits[layout-shift-elements].details.headings[0].label", @@ -9456,6 +9471,14 @@ "core/audits/layout-shift-elements.js | description": [ "audits[layout-shift-elements].description" ], + "core/lib/i18n/i18n.js | displayValueElementsFound": [ + { + "values": { + "nodeCount": 5 + }, + "path": "audits[layout-shift-elements].displayValue" + } + ], "core/audits/layout-shift-elements.js | columnContribution": [ "audits[layout-shift-elements].details.headings[1].label" ], diff --git a/core/test/runner-test.js b/core/test/runner-test.js index 1a443cf66fab..55c160673bf3 100644 --- a/core/test/runner-test.js +++ b/core/test/runner-test.js @@ -604,6 +604,37 @@ describe('Runner', () => { assert.strictEqual(auditResult.score, null); assert.strictEqual(auditResult.scoreDisplayMode, 'error'); assert.ok(auditResult.errorMessage.includes(errorMessage)); + assert.ok(auditResult.errorStack.match(/at [a-zA-Z]*.audit/)); + }); + }); + + it('produces an error audit result that prefers cause stack', async () => { + const errorMessage = 'Audit yourself'; + const resolvedConfig = await LegacyResolvedConfig.fromJson({ + settings: { + auditMode: moduleDir + '/fixtures/artifacts/empty-artifacts/', + }, + audits: [ + class ThrowyAudit extends Audit { + static get meta() { + return testAuditMeta; + } + static audit() { + this.aFn(); + } + static aFn() { + throw new Error(errorMessage); + } + }, + ], + }); + + return runGatherAndAudit({}, {resolvedConfig}).then(results => { + const auditResult = results.lhr.audits['throwy-audit']; + assert.strictEqual(auditResult.score, null); + assert.strictEqual(auditResult.scoreDisplayMode, 'error'); + assert.ok(auditResult.errorMessage.includes(errorMessage)); + assert.ok(auditResult.errorStack.match(/at [a-zA-Z]*.aFn/)); }); }); }); diff --git a/package.json b/package.json index 0f52d1ca975a..58d306038894 100644 --- a/package.json +++ b/package.json @@ -143,7 +143,7 @@ "cpy": "^8.1.2", "cross-env": "^7.0.2", "csv-validator": "^0.0.3", - "es-main": "^1.0.2", + "es-main": "^1.2.0", "eslint": "^8.4.1", "eslint-config-google": "^0.14.0", "eslint-formatter-codeframe": "^7.32.1", @@ -169,7 +169,7 @@ "pako": "^2.0.3", "preact": "^10.7.2", "pretty-json-stringify": "^0.0.2", - "puppeteer": "^20.1.0", + "puppeteer": "^20.5.0", "resolve": "^1.20.0", "rollup": "^2.52.7", "rollup-plugin-node-resolve": "^5.2.0", @@ -179,7 +179,7 @@ "rollup-plugin-terser": "^7.0.2", "tabulator-tables": "^4.9.3", "terser": "^5.3.8", - "testdouble": "^3.16.8", + "testdouble": "^3.17.2", "typed-query-selector": "^2.6.1", "typescript": "^5.0.4", "wait-for-expect": "^3.0.2", @@ -191,7 +191,7 @@ "chrome-launcher": "^0.15.2", "configstore": "^5.0.1", "csp_evaluator": "1.1.1", - "devtools-protocol": "0.0.1130274", + "devtools-protocol": "0.0.1155343", "enquirer": "^2.3.6", "http-link-header": "^1.1.1", "intl-messageformat": "^4.4.0", @@ -205,7 +205,7 @@ "open": "^8.4.0", "parse-cache-control": "1.0.1", "ps-list": "^8.0.0", - "puppeteer-core": "^20.1.0", + "puppeteer-core": "^20.5.0", "robots-parser": "^3.0.0", "semver": "^5.3.0", "speedline-core": "^1.4.3", @@ -215,8 +215,8 @@ "yargs-parser": "^21.0.0" }, "resolutions": { - "puppeteer/**/devtools-protocol": "0.0.1130274", - "puppeteer-core/**/devtools-protocol": "0.0.1130274" + "puppeteer/**/devtools-protocol": "0.0.1155343", + "puppeteer-core/**/devtools-protocol": "0.0.1155343" }, "repository": "GoogleChrome/lighthouse", "keywords": [ diff --git a/proto/lighthouse-result.proto b/proto/lighthouse-result.proto index 8257620c4bb5..5720e4116c0c 100644 --- a/proto/lighthouse-result.proto +++ b/proto/lighthouse-result.proto @@ -1,5 +1,7 @@ syntax = "proto3"; +package googlechrome.lighthouse; + // This comment required for Lightrider import compatibility # header import "google/protobuf/struct.proto"; diff --git a/readme.md b/readme.md index a2a345477813..1788ea000d94 100644 --- a/readme.md +++ b/readme.md @@ -297,6 +297,12 @@ for more info. # lint and test all files yarn test +# run all unit tests +yarn unit + +# run a given unit test (e.g. core/test/audits/byte-efficiency/uses-long-cache-ttl-test.js) +yarn mocha uses-long-cache-ttl + # watch for file changes and run tests # Requires http://entrproject.org : brew install entr yarn watch diff --git a/third-party/chromium-synchronization/inspector-issueAdded-types-test.js b/third-party/chromium-synchronization/inspector-issueAdded-types-test.js index 291d5adb10e9..c4b617a49434 100644 --- a/third-party/chromium-synchronization/inspector-issueAdded-types-test.js +++ b/third-party/chromium-synchronization/inspector-issueAdded-types-test.js @@ -41,6 +41,7 @@ Array [ "corsIssueDetails", "deprecationIssueDetails", "federatedAuthRequestIssueDetails", + "federatedAuthUserInfoRequestIssueDetails", "genericIssueDetails", "heavyAdIssueDetails", "lowTextContrastIssueDetails", @@ -48,6 +49,7 @@ Array [ "navigatorUserAgentIssueDetails", "quirksModeIssueDetails", "sharedArrayBufferIssueDetails", + "stylesheetLoadingIssueDetails", ] `); }); diff --git a/tsconfig-base.json b/tsconfig-base.json index e61e358647a3..9e90928e1355 100644 --- a/tsconfig-base.json +++ b/tsconfig-base.json @@ -11,7 +11,7 @@ "outDir": ".tmp/tsbuildinfo/", "rootDir": ".", - "target": "es2020", + "target": "es2022", "module": "es2022", "moduleResolution": "node", "esModuleInterop": true, diff --git a/types/artifacts.d.ts b/types/artifacts.d.ts index c293c9b48f52..75605685bddb 100644 --- a/types/artifacts.d.ts +++ b/types/artifacts.d.ts @@ -618,6 +618,8 @@ declare module Artifacts { quirksModeIssue: Crdp.Audits.QuirksModeIssueDetails[]; cookieIssue: Crdp.Audits.CookieIssueDetails[]; sharedArrayBufferIssue: Crdp.Audits.SharedArrayBufferIssueDetails[]; + stylesheetLoadingIssue: Crdp.Audits.StylesheetLoadingIssueDetails[]; + federatedAuthUserInfoRequestIssue: Crdp.Audits.FederatedAuthUserInfoRequestIssueDetails[]; } // Computed artifact types below. @@ -800,7 +802,6 @@ declare module Artifacts { maxPotentialFID: number | undefined; cumulativeLayoutShift: number | undefined; cumulativeLayoutShiftMainFrame: number | undefined; - totalCumulativeLayoutShift: number | undefined; totalBlockingTime: number | undefined; observedTimeOrigin: number; observedTimeOriginTs: number; @@ -808,7 +809,6 @@ declare module Artifacts { observedNavigationStartTs: number | undefined; observedCumulativeLayoutShift: number | undefined; observedCumulativeLayoutShiftMainFrame: number | undefined; - observedTotalCumulativeLayoutShift: number | undefined; observedFirstPaint: number | undefined; observedFirstPaintTs: number | undefined; observedFirstContentfulPaint: number | undefined; diff --git a/types/audit.d.ts b/types/audit.d.ts index ae28dafe7b03..9a83f6337722 100644 --- a/types/audit.d.ts +++ b/types/audit.d.ts @@ -75,6 +75,8 @@ declare module Audit { explanation?: string | IcuMessage; /** Error message from any exception thrown while running this audit. */ errorMessage?: string | IcuMessage; + /** Error stack from any exception thrown while running this audit. */ + errorStack?: string; warnings?: Array; /** Overrides scoreDisplayMode with notApplicable if set to true */ notApplicable?: boolean; diff --git a/types/internal/es-main.d.ts b/types/internal/es-main.d.ts deleted file mode 100644 index 08e56fa064a7..000000000000 --- a/types/internal/es-main.d.ts +++ /dev/null @@ -1,18 +0,0 @@ -/** - * @license Copyright 2021 The Lighthouse Authors. All Rights Reserved. - * Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance with the License. You may obtain a copy of the License at http://www.apache.org/licenses/LICENSE-2.0 - * Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the specific language governing permissions and limitations under the License. - */ - -/** - * @fileoverview Types for the `es-main` npm module. - */ - -/** - * Test if an ES module is run directly with Node.js. - * @param importMeta `import.meta` - */ -declare function esMain(importMeta: ImportMeta): boolean; -declare module 'es-main' { - export = esMain; -} diff --git a/types/lhr/audit-result.d.ts b/types/lhr/audit-result.d.ts index a9d95fc0cda4..7abe29ec137a 100644 --- a/types/lhr/audit-result.d.ts +++ b/types/lhr/audit-result.d.ts @@ -39,6 +39,8 @@ export interface Result { explanation?: string; /** Error message from any exception thrown while running this audit. */ errorMessage?: string; + /** Error stack from any exception thrown while running this audit. */ + errorStack?: string; warnings?: string[]; /** The scored value of the audit, provided in the range `0-1`, or null if `scoreDisplayMode` indicates not scored. */ score: number|null; diff --git a/yarn.lock b/yarn.lock index 610edb8d60da..709ff9a02d61 100644 --- a/yarn.lock +++ b/yarn.lock @@ -1123,16 +1123,15 @@ resolved "https://registry.yarnpkg.com/@protobufjs/utf8/-/utf8-1.1.0.tgz#a777360b5b39a1a2e5106f8e858f2fd2d060c570" integrity sha1-p3c2C1s5oaLlEG+OhY8v0tBgxXA= -"@puppeteer/browsers@1.0.0": - version "1.0.0" - resolved "https://registry.yarnpkg.com/@puppeteer/browsers/-/browsers-1.0.0.tgz#89de56a718c922857b1d802aac473ebbe1f54d99" - integrity sha512-YKecOIlwH0UsiM9zkKy31DYg11iD8NhOoQ7SQ4oCpwDSd1Ud31WYRoAldbVlVBj9b4hLJIXxn7XSnkH1ta1tpA== +"@puppeteer/browsers@1.4.1": + version "1.4.1" + resolved "https://registry.yarnpkg.com/@puppeteer/browsers/-/browsers-1.4.1.tgz#9c8ba163c3ef77ae3fc9708ad1f5787263f7290e" + integrity sha512-H43VosMzywHCcYcgv0GXXopvwnV21Ud9g2aXbPlQUJj1Xcz9V0wBwHeFz6saFhx/3VKisZfI1GEKEOhQCau7Vw== dependencies: debug "4.3.4" extract-zip "2.0.1" - https-proxy-agent "5.0.1" progress "2.0.3" - proxy-from-env "1.1.0" + proxy-agent "6.2.1" tar-fs "2.1.1" unbzip2-stream "1.4.3" yargs "17.7.1" @@ -1794,6 +1793,11 @@ acorn-walk@^6.0.1: resolved "https://registry.yarnpkg.com/acorn-walk/-/acorn-walk-6.1.1.tgz#d363b66f5fac5f018ff9c3a1e7b6f8e310cc3913" integrity sha512-OtUw6JUTgxA2QoqqmrmQ7F2NYqiBPi/L2jqHyFtllhOUvXYQXf0Z1CYUinIfyT4bTCGmrA7gX9FvHA81uzCoVw== +acorn-walk@^8.2.0: + version "8.2.0" + resolved "https://registry.yarnpkg.com/acorn-walk/-/acorn-walk-8.2.0.tgz#741210f2e2426454508853a2f44d0ab83b7f69c1" + integrity sha512-k+iyHEuPgSw6SbuDpGQM+06HQUa04DZ3o+F6CSzXMvvI5KMvnaEqXe+YVe555R9nn6GPt404fos4wcgpw12SDA== + acorn@^6.0.1, acorn@^6.0.2: version "6.4.2" resolved "https://registry.yarnpkg.com/acorn/-/acorn-6.4.2.tgz#35866fd710528e92de10cf06016498e47e39e1e6" @@ -1809,6 +1813,11 @@ acorn@^8.6.0: resolved "https://registry.yarnpkg.com/acorn/-/acorn-8.6.0.tgz#e3692ba0eb1a0c83eaa4f37f5fa7368dd7142895" integrity sha512-U1riIR+lBSNi3IbxtaHOIKdH8sLFv3NYfNv8sg7ZsNhcfl4HF2++BfqqrNAxoCLQW1iiylOj76ecnaUxz+z9yw== +acorn@^8.7.0: + version "8.8.2" + resolved "https://registry.yarnpkg.com/acorn/-/acorn-8.8.2.tgz#1b2f25db02af965399b9776b0c2c391276d37c4a" + integrity sha512-xjIYgE8HBrkpd/sJqOGNspf8uHG+NOHGOw6a/Urj8taM2EXfdNAH2oFcPeIFfsv3+kz/mJrS5VuMqbNLjCa2vw== + add-stream@^1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/add-stream/-/add-stream-1.0.0.tgz#6a7990437ca736d5e1288db92bd3266d5f5cb2aa" @@ -1821,6 +1830,13 @@ agent-base@6: dependencies: debug "4" +agent-base@^7.0.1, agent-base@^7.0.2, agent-base@^7.1.0: + version "7.1.0" + resolved "https://registry.yarnpkg.com/agent-base/-/agent-base-7.1.0.tgz#536802b76bc0b34aa50195eb2442276d613e3434" + integrity sha512-o/zjMZRhJxny7OyEF+Op8X+efiELC7k7yOjMzgfzVqOzXqkBkWI79YoTdOtsuWd5BWhAGAuOY/Xa6xpiaWXiNg== + dependencies: + debug "^4.3.4" + aggregate-error@^3.0.0: version "3.1.0" resolved "https://registry.yarnpkg.com/aggregate-error/-/aggregate-error-3.1.0.tgz#92670ff50f5359bdb7a3e0d40d0ec30c5737687a" @@ -2021,6 +2037,13 @@ assign-symbols@^1.0.0: resolved "https://registry.yarnpkg.com/assign-symbols/-/assign-symbols-1.0.0.tgz#59667f41fadd4f20ccbc2bb96b8d4f7f78ec0367" integrity sha1-WWZ/QfrdTyDMvCu5a41Pf3jsA2c= +ast-types@^0.13.2: + version "0.13.4" + resolved "https://registry.yarnpkg.com/ast-types/-/ast-types-0.13.4.tgz#ee0d77b343263965ecc3fb62da16e7222b2b6782" + integrity sha512-x1FCFnFifvYDDzTaLII71vG5uvDwgtmDTEVWAxrgeiR8VjMONcCXJx7E+USjDtHlwFmt9MysbqgF9b9Vjr6w+w== + dependencies: + tslib "^2.0.1" + async-limiter@~1.0.0: version "1.0.1" resolved "https://registry.yarnpkg.com/async-limiter/-/async-limiter-1.0.1.tgz#dd379e94f0db8310b08291f9d64c3209766617fd" @@ -2115,6 +2138,11 @@ base@^0.11.1: mixin-deep "^1.2.0" pascalcase "^0.1.1" +basic-ftp@^5.0.2: + version "5.0.3" + resolved "https://registry.yarnpkg.com/basic-ftp/-/basic-ftp-5.0.3.tgz#b14c0fe8111ce001ec913686434fe0c2fb461228" + integrity sha512-QHX8HLlncOLpy54mh+k/sWIFd0ThmRqwe9ZjELybGZK+tZ8rUb9VO0saKJUROTbE+KhzDUT7xziGpGrW8Kmd+g== + bcrypt-pbkdf@^1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/bcrypt-pbkdf/-/bcrypt-pbkdf-1.0.0.tgz#3ca76b85241c7170bf7d9703e7b9aa74630040d4" @@ -2419,10 +2447,10 @@ chrome-launcher@^0.15.2: is-wsl "^2.2.0" lighthouse-logger "^1.0.0" -chromium-bidi@0.4.7: - version "0.4.7" - resolved "https://registry.yarnpkg.com/chromium-bidi/-/chromium-bidi-0.4.7.tgz#4c022c2b0fb1d1c9b571fadf373042160e71d236" - integrity sha512-6+mJuFXwTMU6I3vYLs6IL8A1DyQTPjCfIL971X0aMPVGRbGnNfl6i6Cl0NMbxi2bRYLGESt9T2ZIMRM5PAEcIQ== +chromium-bidi@0.4.11: + version "0.4.11" + resolved "https://registry.yarnpkg.com/chromium-bidi/-/chromium-bidi-0.4.11.tgz#d3eafb0a99f417406a734b889dacd777be5e227c" + integrity sha512-p03ajLhlQ5gebw3cmbDBFmBc2wnJM5dnXS8Phu6mblGn/KQd76yOVL5VwE0VAisa7oazNfKGTaXlIZ8Q5Bb9OA== dependencies: mitt "3.0.0" @@ -2825,12 +2853,12 @@ cross-env@^7.0.2: dependencies: cross-spawn "^7.0.1" -cross-fetch@3.1.5: - version "3.1.5" - resolved "https://registry.yarnpkg.com/cross-fetch/-/cross-fetch-3.1.5.tgz#e1389f44d9e7ba767907f7af8454787952ab534f" - integrity sha512-lvb1SBsI0Z7GDwmuid+mU3kWVBwTVUbe7S0H52yaaAdQOXq2YktTCZdlAcNKFzE6QtRz0snpw9bNiPeOIkkQvw== +cross-fetch@3.1.6: + version "3.1.6" + resolved "https://registry.yarnpkg.com/cross-fetch/-/cross-fetch-3.1.6.tgz#bae05aa31a4da760969756318feeee6e70f15d6c" + integrity sha512-riRvo06crlE8HiqOwIpQhxwdOk4fOeR7FVM/wXoxchFEqMNUjvbs3bfo4OTgMEMHzppd4DxFBDbyySj8Cv781g== dependencies: - node-fetch "2.6.7" + node-fetch "^2.6.11" cross-spawn@^7.0.0, cross-spawn@^7.0.1, cross-spawn@^7.0.2: version "7.0.3" @@ -2890,6 +2918,11 @@ dashdash@^1.12.0: dependencies: assert-plus "^1.0.0" +data-uri-to-buffer@^5.0.1: + version "5.0.1" + resolved "https://registry.yarnpkg.com/data-uri-to-buffer/-/data-uri-to-buffer-5.0.1.tgz#db89a9e279c2ffe74f50637a59a32fb23b3e4d7c" + integrity sha512-a9l6T1qqDogvvnw0nKlfZzqsyikEBZBClF39V3TFoKhDtGBqHu2HkuomJc02j5zft8zrUaXEuoicLeW54RkzPg== + data-urls@^1.0.1: version "1.1.0" resolved "https://registry.yarnpkg.com/data-urls/-/data-urls-1.1.0.tgz#15ee0582baa5e22bb59c77140da8f9c76963bbfe" @@ -2997,15 +3030,25 @@ define-property@^2.0.2: is-descriptor "^1.0.2" isobject "^3.0.1" +degenerator@^4.0.1: + version "4.0.2" + resolved "https://registry.yarnpkg.com/degenerator/-/degenerator-4.0.2.tgz#55b7fb41239ee0ea7644fa3f2aba84e0adfaa40c" + integrity sha512-HKwIFvZROUMfH3qI3gBpD61BYh7q3c3GXD5UGZzoVNJwVSYgZKvYl1fRMXc9ozoTxl/VZxKJ5v/bA+19tywFiw== + dependencies: + ast-types "^0.13.2" + escodegen "^1.8.1" + esprima "^4.0.0" + vm2 "^3.9.17" + delayed-stream@~1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/delayed-stream/-/delayed-stream-1.0.0.tgz#df3ae199acadfb7d440aaae0b29e2272b24ec619" integrity sha1-3zrhmayt+31ECqrgsp4icrJOxhk= -devtools-protocol@0.0.1120988, devtools-protocol@0.0.1130274: - version "0.0.1130274" - resolved "https://registry.yarnpkg.com/devtools-protocol/-/devtools-protocol-0.0.1130274.tgz#1cd0c472a84fc9a09becaaed35a247a6eab9310c" - integrity sha512-kIozBWajgsi1g0W8yzALI4ZdCp6KG1yWaq8NN1ehQM3zX6JRegLSzfexz7XT5eFjmq1RkpMYgeKmfi3GsHrCLw== +devtools-protocol@0.0.1120988, devtools-protocol@0.0.1155343: + version "0.0.1155343" + resolved "https://registry.yarnpkg.com/devtools-protocol/-/devtools-protocol-0.0.1155343.tgz#9e4ce46e9b05a1be6d6b629fbfaa1a38b1c18a3b" + integrity sha512-oD9vGBV2wTc7fAzAM6KC0chSgs234V8+qDEeK+mcbRj2UvcuA7lgBztGi/opj/iahcXD3BSj8Ymvib628yy9FA== diff-sequences@^28.0.2: version "28.0.2" @@ -3145,10 +3188,10 @@ es-abstract@^1.19.0, es-abstract@^1.19.1: string.prototype.trimstart "^1.0.4" unbox-primitive "^1.0.1" -es-main@^1.0.2: - version "1.0.2" - resolved "https://registry.yarnpkg.com/es-main/-/es-main-1.0.2.tgz#c9030d78796f609f865b66f4125a78d77fec3de3" - integrity sha512-LLgW8Cby/FiyQygrI23q2EswulHiDKoyjWlDRgTGXjQ3iRim2R26VfoehpxI5oKRXSNams3L/80KtggoUdxdDQ== +es-main@^1.2.0: + version "1.2.0" + resolved "https://registry.yarnpkg.com/es-main/-/es-main-1.2.0.tgz#b85954f1d9d9f542fcb08685ec19515f969bad16" + integrity sha512-A4tCSY43O/mH4rHjG1n0mI4DhK2BmKDr8Lk8PXK/GBB6zxGFGmIW4bbkbTQ2Gi9iNamMZ9vbGrwjZOIeiM7vMw== es-module-lexer@^0.10.5: version "0.10.5" @@ -3310,7 +3353,7 @@ escape-string-regexp@^2.0.0: resolved "https://registry.yarnpkg.com/escape-string-regexp/-/escape-string-regexp-2.0.0.tgz#a30304e99daa32e23b2fd20f51babd07cffca344" integrity sha512-UpzcLCXolUWcNu5HtVMHYdXJjArjsF9C0aNnquZYY4uW/Vu0miy5YoWvbV345HauVvcAUnpRuhMMcqTcGOY2+w== -escodegen@^1.11.0: +escodegen@^1.11.0, escodegen@^1.8.1: version "1.14.3" resolved "https://registry.yarnpkg.com/escodegen/-/escodegen-1.14.3.tgz#4e7b81fba61581dc97582ed78cab7f0e8d63f503" integrity sha512-qFcX0XJkdg+PB3xjZZG/wKSuT1PnQWx57+TVSjIMmILd2yC/6ByYElPwJnslDsuWuSAp4AwJGumarAAmJch5Kw== @@ -3833,6 +3876,15 @@ fs-extra@^7.0.0: jsonfile "^4.0.0" universalify "^0.1.0" +fs-extra@^8.1.0: + version "8.1.0" + resolved "https://registry.yarnpkg.com/fs-extra/-/fs-extra-8.1.0.tgz#49d43c45a88cd9677668cb7be1b46efdb8d2e1c0" + integrity sha512-yhlQgA6mnOJUKOsRUFsgJdQCvkKhcz8tlZG5HBQfReYZy46OwLcY+Zia0mtdHsOo9y/hP+CxMN0TU9QxoOtG4g== + dependencies: + graceful-fs "^4.2.0" + jsonfile "^4.0.0" + universalify "^0.1.0" + fs.realpath@^1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/fs.realpath/-/fs.realpath-1.0.0.tgz#1504ad2523158caa40db4a2787cb01411994ea4f" @@ -3907,6 +3959,16 @@ get-tsconfig@^3.0.1: resolved "https://registry.yarnpkg.com/get-tsconfig/-/get-tsconfig-3.0.1.tgz#02cadb5abc5f0d53033c8b2f3005b84134ba22e9" integrity sha512-+m30eQjbcf3xMNdnacXH5IDAKUMbI7Mhbf3e1BHif1FzBlUhBzBlmOVc7kL4+kB035l8OCyBdI3dNXZ3of9HqA== +get-uri@^6.0.1: + version "6.0.1" + resolved "https://registry.yarnpkg.com/get-uri/-/get-uri-6.0.1.tgz#cff2ba8d456c3513a04b70c45de4dbcca5b1527c" + integrity sha512-7ZqONUVqaabogsYNWlYj0t3YZaL6dhuEueZXGF+/YVmf6dHmaFg8/6psJKqhx9QykIDKzpGcy2cn4oV4YC7V/Q== + dependencies: + basic-ftp "^5.0.2" + data-uri-to-buffer "^5.0.1" + debug "^4.3.4" + fs-extra "^8.1.0" + get-value@^2.0.3, get-value@^2.0.6: version "2.0.6" resolved "https://registry.yarnpkg.com/get-value/-/get-value-2.0.6.tgz#dc15ca1c672387ca76bd37ac0a395ba2042a2c28" @@ -4079,6 +4141,11 @@ graceful-fs@^4.1.0, graceful-fs@^4.1.11, graceful-fs@^4.1.2, graceful-fs@^4.1.6: resolved "https://registry.yarnpkg.com/graceful-fs/-/graceful-fs-4.2.6.tgz#ff040b2b0853b23c3d31027523706f1885d76bee" integrity sha512-nTnJ528pbqxYanhpDYsi4Rd8MAeaBA67+RZ10CM1m3bTAVFEDcd5AuA4a6W5YkGZ1iNXHzZz8T6TBKLeBuNriQ== +graceful-fs@^4.2.0: + version "4.2.11" + resolved "https://registry.yarnpkg.com/graceful-fs/-/graceful-fs-4.2.11.tgz#4183e4e8bf08bb6e05bbb2f7d2e0c8f712ca40e3" + integrity sha512-RbJ5/jmFcNNCcDV5o9eTnBLJ/HszWV0P73bc+Ff4nS/rJj+YaS6IGyiOL0VoBYX+l1Wrl3k63h/KrH+nhJ0XvQ== + graceful-fs@^4.2.9: version "4.2.10" resolved "https://registry.yarnpkg.com/graceful-fs/-/graceful-fs-4.2.10.tgz#147d3a006da4ca3ce14728c7aefc287c367d7a6c" @@ -4233,6 +4300,14 @@ http-parser-js@>=0.5.1: resolved "https://registry.yarnpkg.com/http-parser-js/-/http-parser-js-0.5.3.tgz#01d2709c79d41698bb01d4decc5e9da4e4a033d9" integrity sha512-t7hjvef/5HEK7RWTdUzVUhl8zkEu+LlaE0IYzdMuvbSDipxBRpOn4Uhw8ZyECEa808iVT8XCjzo6xmYt4CiLZg== +http-proxy-agent@^7.0.0: + version "7.0.0" + resolved "https://registry.yarnpkg.com/http-proxy-agent/-/http-proxy-agent-7.0.0.tgz#e9096c5afd071a3fce56e6252bb321583c124673" + integrity sha512-+ZT+iBxVUQ1asugqnD6oWoRiS25AkjNfG085dKJGtGxkdwLQrMKU5wJr2bOOFAXzKcTuqq+7fZlTMgG3SRfIYQ== + dependencies: + agent-base "^7.1.0" + debug "^4.3.4" + http-signature@~1.2.0: version "1.2.0" resolved "https://registry.yarnpkg.com/http-signature/-/http-signature-1.2.0.tgz#9aecd925114772f3d95b65a60abb8f7c18fbace1" @@ -4242,14 +4317,6 @@ http-signature@~1.2.0: jsprim "^1.2.2" sshpk "^1.7.0" -https-proxy-agent@5.0.1: - version "5.0.1" - resolved "https://registry.yarnpkg.com/https-proxy-agent/-/https-proxy-agent-5.0.1.tgz#c59ef224a04fe8b754f3db0063a25ea30d0005d6" - integrity sha512-dFcAjpTQFgoLMzC2VwU+C/CbS7uRL0lWmxDITmqm7C+7F0Odmj6s9l6alZc6AELXhrnggM2CeWSXHGOdX2YtwA== - dependencies: - agent-base "6" - debug "4" - https-proxy-agent@^5.0.0: version "5.0.0" resolved "https://registry.yarnpkg.com/https-proxy-agent/-/https-proxy-agent-5.0.0.tgz#e2a90542abb68a762e0a0850f6c9edadfd8506b2" @@ -4258,6 +4325,14 @@ https-proxy-agent@^5.0.0: agent-base "6" debug "4" +https-proxy-agent@^7.0.0: + version "7.0.0" + resolved "https://registry.yarnpkg.com/https-proxy-agent/-/https-proxy-agent-7.0.0.tgz#75cb70d04811685667183b31ab158d006750418a" + integrity sha512-0euwPCRyAPSgGdzD1IVN9nJYHtBhJwb6XPfbpQcYbPCwrBidX6GzxmchnaF4sfF/jPb74Ojx5g4yTg3sixlyPw== + dependencies: + agent-base "^7.0.2" + debug "4" + humanize-url@^1.0.0: version "1.0.1" resolved "https://registry.yarnpkg.com/humanize-url/-/humanize-url-1.0.1.tgz#f4ab99e0d288174ca4e1e50407c55fbae464efff" @@ -4378,6 +4453,16 @@ intl-messageformat@^4.1.2, intl-messageformat@^4.4.0: dependencies: intl-messageformat-parser "^1.8.1" +ip@^1.1.5: + version "1.1.8" + resolved "https://registry.yarnpkg.com/ip/-/ip-1.1.8.tgz#ae05948f6b075435ed3307acce04629da8cdbf48" + integrity sha512-PuExPYUiu6qMBQb4l06ecm6T6ujzhmh+MeJcW9wa89PoAz5pvd4zPgN5WJV104mb6S2T1AwNIAaB70JNrLQWhg== + +ip@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/ip/-/ip-2.0.0.tgz#4cf4ab182fee2314c75ede1276f8c80b479936da" + integrity sha512-WKa+XuLG1A1R0UWhl2+1XQSi+fZWMsYKffMZTTYsiZaUD8k2yDAj5atimTUD2TZkyCkNEeYE5NhFZmupOGtjYQ== + is-accessor-descriptor@^0.1.6: version "0.1.6" resolved "https://registry.yarnpkg.com/is-accessor-descriptor/-/is-accessor-descriptor-0.1.6.tgz#a9e12cb3ae8d876727eeef3843f8a0897b5c98d6" @@ -5252,6 +5337,11 @@ lru-cache@^6.0.0: dependencies: yallist "^4.0.0" +lru-cache@^7.14.1: + version "7.18.3" + resolved "https://registry.yarnpkg.com/lru-cache/-/lru-cache-7.18.3.tgz#f793896e0fd0e954a59dfdd82f0773808df6aa89" + integrity sha512-jumlc0BIUrS3qJGgIkWZsyfAM7NCWiBcCDhnd+3NNM5KbBmLTgHVfWBcg6W+rLUsIpzpERPsvwUP7CckAQSOoA== + lru_map@^0.3.3: version "0.3.3" resolved "https://registry.yarnpkg.com/lru_map/-/lru_map-0.3.3.tgz#b5c8351b9464cbd750335a79650a0ec0e56118dd" @@ -5530,18 +5620,30 @@ nested-error-stacks@^2.0.0, nested-error-stacks@^2.1.0: resolved "https://registry.yarnpkg.com/nested-error-stacks/-/nested-error-stacks-2.1.0.tgz#0fbdcf3e13fe4994781280524f8b96b0cdff9c61" integrity sha512-AO81vsIO1k1sM4Zrd6Hu7regmJN1NSiAja10gc4bX3F0wd+9rQmcuHQaHVQCYIEC8iFXnE+mavh23GOt7wBgug== +netmask@^2.0.2: + version "2.0.2" + resolved "https://registry.yarnpkg.com/netmask/-/netmask-2.0.2.tgz#8b01a07644065d536383835823bc52004ebac5e7" + integrity sha512-dBpDMdxv9Irdq66304OLfEmQ9tbNRFnFTuZiLo+bD+r332bBmMJ8GBLXklIXXgxd3+v9+KUnZaUR5PJMa75Gsg== + node-fetch@2.6.1: version "2.6.1" resolved "https://registry.yarnpkg.com/node-fetch/-/node-fetch-2.6.1.tgz#045bd323631f76ed2e2b55573394416b639a0052" integrity sha512-V4aYg89jEoVRxRb2fJdAg8FHvI7cEyYdVAh94HH0UIK8oJxUfkjlDQN9RbMx+bEjP7+ggMiFRprSti032Oipxw== -node-fetch@2.6.7, node-fetch@^2.6.1: +node-fetch@^2.6.1: version "2.6.7" resolved "https://registry.yarnpkg.com/node-fetch/-/node-fetch-2.6.7.tgz#24de9fba827e3b4ae44dc8b20256a379160052ad" integrity sha512-ZjMPFEfVx5j+y2yF35Kzx5sF7kDzxuDj6ziH4FFbOp87zKDZNx8yExJIb05OGF4Nlt9IHFIMBkRl41VdvcNdbQ== dependencies: whatwg-url "^5.0.0" +node-fetch@^2.6.11: + version "2.6.11" + resolved "https://registry.yarnpkg.com/node-fetch/-/node-fetch-2.6.11.tgz#cde7fc71deef3131ef80a738919f999e6edfff25" + integrity sha512-4I6pdBY1EthSqDmJkiNk3JIT8cswwR9nfeW/cPdUagJYEQG7R95WRH74wpz7ma8Gh/9dI9FP+OU+0E4FvtA55w== + dependencies: + whatwg-url "^5.0.0" + node-int64@^0.4.0: version "0.4.0" resolved "https://registry.yarnpkg.com/node-int64/-/node-int64-0.4.0.tgz#87a9065cdb355d3182d8f94ce11188b825c68a3b" @@ -5808,6 +5910,28 @@ p-try@^2.0.0: resolved "https://registry.yarnpkg.com/p-try/-/p-try-2.2.0.tgz#cb2868540e313d61de58fafbe35ce9004d5540e6" integrity sha512-R4nPAVTAU0B9D35/Gk3uJf/7XYbQcyohSKdvAxIRSNghFl4e71hVoGnBNQz9cWaXxO2I10KTC+3jMdvvoKw6dQ== +pac-proxy-agent@^6.0.3: + version "6.0.3" + resolved "https://registry.yarnpkg.com/pac-proxy-agent/-/pac-proxy-agent-6.0.3.tgz#61042187093b67aa7dd05b41e4ec7c241a27c428" + integrity sha512-5Hr1KgPDoc21Vn3rsXBirwwDnF/iac1jN/zkpsOYruyT+ZgsUhUOgVwq3v9+ukjZd/yGm/0nzO1fDfl7rkGoHQ== + dependencies: + agent-base "^7.0.2" + debug "^4.3.4" + get-uri "^6.0.1" + http-proxy-agent "^7.0.0" + https-proxy-agent "^7.0.0" + pac-resolver "^6.0.1" + socks-proxy-agent "^8.0.1" + +pac-resolver@^6.0.1: + version "6.0.1" + resolved "https://registry.yarnpkg.com/pac-resolver/-/pac-resolver-6.0.1.tgz#319c182d3db4e6782e79519cb4dd1dda46579292" + integrity sha512-dg497MhVT7jZegPRuOScQ/z0aV/5WR0gTdRu1md+Irs9J9o+ls5jIuxjo1WfaTG+eQQkxyn5HMGvWK+w7EIBkQ== + dependencies: + degenerator "^4.0.1" + ip "^1.1.5" + netmask "^2.0.2" + pako@^2.0.3: version "2.0.3" resolved "https://registry.yarnpkg.com/pako/-/pako-2.0.3.tgz#cdf475e31b678565251406de9e759196a0ea7a43" @@ -6067,7 +6191,21 @@ protobufjs@^6.10.0: "@types/node" ">=13.7.0" long "^4.0.0" -proxy-from-env@1.1.0: +proxy-agent@6.2.1: + version "6.2.1" + resolved "https://registry.yarnpkg.com/proxy-agent/-/proxy-agent-6.2.1.tgz#062df6609a4012fd1c108974865599b61e77abde" + integrity sha512-OIbBKlRAT+ycCm6wAYIzMwPejzRtjy8F3QiDX0eKOA3e4pe3U9F/IvzcHP42bmgQxVv97juG+J8/gx+JIeCX/Q== + dependencies: + agent-base "^7.0.2" + debug "^4.3.4" + http-proxy-agent "^7.0.0" + https-proxy-agent "^7.0.0" + lru-cache "^7.14.1" + pac-proxy-agent "^6.0.3" + proxy-from-env "^1.1.0" + socks-proxy-agent "^8.0.1" + +proxy-from-env@^1.1.0: version "1.1.0" resolved "https://registry.yarnpkg.com/proxy-from-env/-/proxy-from-env-1.1.0.tgz#e102f16ca355424865755d2c9e8ea4f24d58c3e2" integrity sha512-D+zkORCbA9f1tdWRK0RaCR3GPv50cMxcrz4X8k5LTSUD1Dkw47mKJEZQNunItRTkWwgtaUSo1RVFRIG9ZXiFYg== @@ -6095,34 +6233,26 @@ punycode@^2.1.0, punycode@^2.1.1: resolved "https://registry.yarnpkg.com/punycode/-/punycode-2.1.1.tgz#b58b010ac40c22c5657616c8d2c2c02c7bf479ec" integrity sha512-XRsRjdf+j5ml+y/6GKHPZbrF/8p2Yga0JPtdqTIY2Xe5ohJPD9saDJJLPvp9+NSBprVvevdXZybnj2cv8OEd0A== -puppeteer-core@20.1.0, puppeteer-core@^20.1.0: - version "20.1.0" - resolved "https://registry.yarnpkg.com/puppeteer-core/-/puppeteer-core-20.1.0.tgz#c74e21ad642b0adb273da83b4bf444fdecc6500f" - integrity sha512-/xTvabzAN4mnnuYkJCuWNnnEhOb3JrBTa3sY6qVi1wybuIEk5ODRg8Z5PPiKUGiKC9iG7GWOJ5CjF3iuMuxZSA== +puppeteer-core@20.5.0, puppeteer-core@^20.5.0: + version "20.5.0" + resolved "https://registry.yarnpkg.com/puppeteer-core/-/puppeteer-core-20.5.0.tgz#4b9ccd6c4ca35fe02373bf2147dc75b42ebd22c4" + integrity sha512-9ddHXUQ7jpliGei87zYTuEZYQvFj6Lzk5R8w4vT4gMmNArkEqC5CX72TnVIJiTUbiTpOXJkvMQaXIHYopjdUtQ== dependencies: - "@puppeteer/browsers" "1.0.0" - chromium-bidi "0.4.7" - cross-fetch "3.1.5" + "@puppeteer/browsers" "1.4.1" + chromium-bidi "0.4.11" + cross-fetch "3.1.6" debug "4.3.4" devtools-protocol "0.0.1120988" - extract-zip "2.0.1" - https-proxy-agent "5.0.1" - proxy-from-env "1.1.0" - tar-fs "2.1.1" - unbzip2-stream "1.4.3" ws "8.13.0" -puppeteer@^20.1.0: - version "20.1.0" - resolved "https://registry.yarnpkg.com/puppeteer/-/puppeteer-20.1.0.tgz#30331e2729b235b3306a39cab3ad5b0cf2b90e7d" - integrity sha512-kZp1eYScK1IpHxkgnDaFSGKKCzt27iZfsxO6Xlv/cklzYrhobxTK9/PxzCacPCrYnxNQwKwHzHLPOCuSyjw1jg== +puppeteer@^20.5.0: + version "20.5.0" + resolved "https://registry.yarnpkg.com/puppeteer/-/puppeteer-20.5.0.tgz#453f42edb2cb085bb237914c2bcda7938b7ab1c2" + integrity sha512-3j0JShJGDT5z8rfDKf+wZQq3IHxw7JaDAdP7py5H5zOIgmqNG0e8R19y4tFzJ8i2WC4H/0bC51rIrTXyDop1FA== dependencies: - "@puppeteer/browsers" "1.0.0" + "@puppeteer/browsers" "1.4.1" cosmiconfig "8.1.3" - https-proxy-agent "5.0.1" - progress "2.0.3" - proxy-from-env "1.1.0" - puppeteer-core "20.1.0" + puppeteer-core "20.5.0" q@^1.5.1: version "1.5.1" @@ -6142,7 +6272,7 @@ query-string@^4.1.0: object-assign "^4.1.0" strict-uri-encode "^1.0.0" -quibble@^0.6.14: +quibble@^0.6.17: version "0.6.17" resolved "https://registry.yarnpkg.com/quibble/-/quibble-0.6.17.tgz#1c47d40c4ee670fc1a5a4277ee792ca6eec8f4ca" integrity sha512-uybGnGrx1hAhBCmzmVny+ycKaS5F71+q+iWVzbf8x/HyeEMDGeiQFVjWl1zhi4rwfTHa05+/NIExC4L5YRNPjQ== @@ -6618,6 +6748,11 @@ slash@^3.0.0: resolved "https://registry.yarnpkg.com/slash/-/slash-3.0.0.tgz#6539be870c165adbd5240220dbe361f1bc4d4634" integrity sha512-g9Q1haeby36OSStwb4ntCGGGaKsaVSjQ68fBxoQcutl5fS1vuY18H3wSt3jFyFtrkx+Kz0V1G85A4MyAdDMi2Q== +smart-buffer@^4.2.0: + version "4.2.0" + resolved "https://registry.yarnpkg.com/smart-buffer/-/smart-buffer-4.2.0.tgz#6e1d71fa4f18c05f7d0ff216dd16a481d0e8d9ae" + integrity sha512-94hK0Hh8rPqQl2xXc3HsaBoOXKV20MToPkcXvwbISWLEs+64sBq5kFgn2kJDHb1Pry9yrP0dxrCI9RRci7RXKg== + snapdragon-node@^2.0.1: version "2.1.1" resolved "https://registry.yarnpkg.com/snapdragon-node/-/snapdragon-node-2.1.1.tgz#6c175f86ff14bdb0724563e8f3c1b021a286853b" @@ -6648,6 +6783,23 @@ snapdragon@^0.8.1: source-map-resolve "^0.5.0" use "^3.1.0" +socks-proxy-agent@^8.0.1: + version "8.0.1" + resolved "https://registry.yarnpkg.com/socks-proxy-agent/-/socks-proxy-agent-8.0.1.tgz#ffc5859a66dac89b0c4dab90253b96705f3e7120" + integrity sha512-59EjPbbgg8U3x62hhKOFVAmySQUcfRQ4C7Q/D5sEHnZTQRrQlNKINks44DMR1gwXp0p4LaVIeccX2KHTTcHVqQ== + dependencies: + agent-base "^7.0.1" + debug "^4.3.4" + socks "^2.7.1" + +socks@^2.7.1: + version "2.7.1" + resolved "https://registry.yarnpkg.com/socks/-/socks-2.7.1.tgz#d8e651247178fde79c0663043e07240196857d55" + integrity sha512-7maUZy1N7uo6+WVEX6psASxtNlKaNVMlGQKkG/63nEDdLOWNbiUMoLK7X4uYoLhQstau72mLgfEWcXcwsaHbYQ== + dependencies: + ip "^2.0.0" + smart-buffer "^4.2.0" + sort-keys@^1.0.0: version "1.1.2" resolved "https://registry.yarnpkg.com/sort-keys/-/sort-keys-1.1.2.tgz#441b6d4d346798f1b4e49e8920adfba0e543f9ad" @@ -7006,13 +7158,13 @@ test-exclude@^6.0.0: glob "^7.1.4" minimatch "^3.0.4" -testdouble@^3.16.8: - version "3.16.8" - resolved "https://registry.yarnpkg.com/testdouble/-/testdouble-3.16.8.tgz#9c761031f3693d973c726e31a60ee73cd2871c96" - integrity sha512-jOKYRJ9mfgDxwuUOj84sl9DWiP1+KpHcgnhjlSHC8h1ZxJT3KD1FAAFVqnqmmyrzc/+0DRbI/U5xo1/K3PLi8w== +testdouble@^3.17.2: + version "3.17.2" + resolved "https://registry.yarnpkg.com/testdouble/-/testdouble-3.17.2.tgz#a7d624c2040453580b4a636b3f017bf183a8f487" + integrity sha512-oRrk1DJISNoFr3aaczIqrrhkOUQ26BsXN3SopYT/U0GTvk9hlKPCEbd9R2uxkcufKZgEfo9D1JAB4CJrjHE9cw== dependencies: lodash "^4.17.21" - quibble "^0.6.14" + quibble "^0.6.17" stringify-object-es5 "^2.5.0" theredoc "^1.0.0" @@ -7172,6 +7324,11 @@ tslib@^1.9.3: resolved "https://registry.yarnpkg.com/tslib/-/tslib-1.10.0.tgz#c3c19f95973fb0a62973fb09d90d961ee43e5c8a" integrity sha512-qOebF53frne81cf0S9B41ByenJ3/IuH8yJKngAX35CmiZySA0khhkovshKK+jGCaMnVomla7gVlIcc3EvKPbTQ== +tslib@^2.0.1: + version "2.5.3" + resolved "https://registry.yarnpkg.com/tslib/-/tslib-2.5.3.tgz#24944ba2d990940e6e982c4bea147aba80209913" + integrity sha512-mSxlJJwl3BMEQCUNnxXBU9jP4JBktcEGhURcPR6VQVlnP0FdDEsIaz0C35dXNGLyRfrATNofF0F5p2KPxQgB+w== + tslib@^2.1.0: version "2.3.1" resolved "https://registry.yarnpkg.com/tslib/-/tslib-2.3.1.tgz#e8a335add5ceae51aa261d32a490158ef042ef01" @@ -7365,6 +7522,14 @@ verror@1.10.0: core-util-is "1.0.2" extsprintf "^1.2.0" +vm2@^3.9.17: + version "3.9.19" + resolved "https://registry.yarnpkg.com/vm2/-/vm2-3.9.19.tgz#be1e1d7a106122c6c492b4d51c2e8b93d3ed6a4a" + integrity sha512-J637XF0DHDMV57R6JyVsTak7nIL8gy5KH4r1HiwWLf/4GBbb5MKL5y7LpmF4A8E2nR6XmzpmMFQ7V7ppPTmUQg== + dependencies: + acorn "^8.7.0" + acorn-walk "^8.2.0" + w3c-hr-time@^1.0.1: version "1.0.2" resolved "https://registry.yarnpkg.com/w3c-hr-time/-/w3c-hr-time-1.0.2.tgz#0a89cdf5cc15822df9c360543676963e0cc308cd"