lighthouse 9.5.0-dev.20220509 → 9.6.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (259) hide show
  1. package/changelog.md +70 -0
  2. package/dist/report/bundle.esm.js +400 -808
  3. package/dist/report/flow.js +22 -27
  4. package/dist/report/standalone.js +18 -23
  5. package/flow-report/src/summary/category.tsx +1 -1
  6. package/jest.config.js +1 -1
  7. package/lighthouse-cli/.eslintrc.cjs +4 -3
  8. package/lighthouse-cli/bin.js +1 -0
  9. package/lighthouse-cli/cli-flags.js +4 -3
  10. package/lighthouse-cli/commands/commands.js +1 -0
  11. package/lighthouse-cli/commands/list-audits.js +1 -0
  12. package/lighthouse-cli/commands/list-locales.js +1 -0
  13. package/lighthouse-cli/commands/list-trace-categories.js +1 -0
  14. package/lighthouse-cli/index.js +1 -0
  15. package/lighthouse-cli/printer.js +1 -0
  16. package/lighthouse-cli/run.js +24 -9
  17. package/lighthouse-cli/sentry-prompt.js +1 -0
  18. package/lighthouse-cli/test/smokehouse/core-tests.js +1 -0
  19. package/lighthouse-cli/test/smokehouse/frontends/back-compat-util.js +1 -0
  20. package/lighthouse-cli/test/smokehouse/frontends/lib.js +1 -0
  21. package/lighthouse-cli/test/smokehouse/frontends/node.js +1 -0
  22. package/lighthouse-cli/test/smokehouse/frontends/smokehouse-bin.js +1 -0
  23. package/lighthouse-cli/test/smokehouse/lib/child-process-error.js +1 -0
  24. package/lighthouse-cli/test/smokehouse/lib/concurrent-mapper.js +1 -0
  25. package/lighthouse-cli/test/smokehouse/lib/local-console.js +1 -0
  26. package/lighthouse-cli/test/smokehouse/lighthouse-runners/bundle.js +23 -109
  27. package/lighthouse-cli/test/smokehouse/lighthouse-runners/cli.js +3 -2
  28. package/lighthouse-cli/test/smokehouse/lighthouse-runners/devtools.js +19 -28
  29. package/lighthouse-cli/test/smokehouse/report-assert.js +4 -3
  30. package/lighthouse-cli/test/smokehouse/smokehouse.js +1 -1
  31. package/lighthouse-cli/test/smokehouse/version-check-test.js +3 -0
  32. package/lighthouse-cli/test/smokehouse/version-check.js +1 -0
  33. package/lighthouse-core/audits/accessibility/accesskeys.js +1 -1
  34. package/lighthouse-core/audits/accessibility/aria-allowed-attr.js +1 -1
  35. package/lighthouse-core/audits/accessibility/aria-command-name.js +1 -1
  36. package/lighthouse-core/audits/accessibility/aria-hidden-body.js +1 -1
  37. package/lighthouse-core/audits/accessibility/aria-hidden-focus.js +1 -1
  38. package/lighthouse-core/audits/accessibility/aria-input-field-name.js +1 -1
  39. package/lighthouse-core/audits/accessibility/aria-meter-name.js +1 -1
  40. package/lighthouse-core/audits/accessibility/aria-progressbar-name.js +1 -1
  41. package/lighthouse-core/audits/accessibility/aria-required-attr.js +1 -1
  42. package/lighthouse-core/audits/accessibility/aria-required-children.js +1 -1
  43. package/lighthouse-core/audits/accessibility/aria-required-parent.js +1 -1
  44. package/lighthouse-core/audits/accessibility/aria-roles.js +1 -1
  45. package/lighthouse-core/audits/accessibility/aria-toggle-field-name.js +1 -1
  46. package/lighthouse-core/audits/accessibility/aria-tooltip-name.js +1 -1
  47. package/lighthouse-core/audits/accessibility/aria-treeitem-name.js +1 -1
  48. package/lighthouse-core/audits/accessibility/aria-valid-attr-value.js +1 -1
  49. package/lighthouse-core/audits/accessibility/aria-valid-attr.js +1 -1
  50. package/lighthouse-core/audits/accessibility/button-name.js +1 -1
  51. package/lighthouse-core/audits/accessibility/bypass.js +1 -1
  52. package/lighthouse-core/audits/accessibility/color-contrast.js +1 -1
  53. package/lighthouse-core/audits/accessibility/definition-list.js +1 -1
  54. package/lighthouse-core/audits/accessibility/dlitem.js +1 -1
  55. package/lighthouse-core/audits/accessibility/document-title.js +1 -1
  56. package/lighthouse-core/audits/accessibility/duplicate-id-active.js +1 -1
  57. package/lighthouse-core/audits/accessibility/duplicate-id-aria.js +1 -1
  58. package/lighthouse-core/audits/accessibility/form-field-multiple-labels.js +1 -1
  59. package/lighthouse-core/audits/accessibility/frame-title.js +1 -1
  60. package/lighthouse-core/audits/accessibility/heading-order.js +1 -1
  61. package/lighthouse-core/audits/accessibility/html-has-lang.js +1 -1
  62. package/lighthouse-core/audits/accessibility/html-lang-valid.js +1 -1
  63. package/lighthouse-core/audits/accessibility/image-alt.js +1 -1
  64. package/lighthouse-core/audits/accessibility/input-image-alt.js +1 -1
  65. package/lighthouse-core/audits/accessibility/label.js +1 -1
  66. package/lighthouse-core/audits/accessibility/link-name.js +1 -1
  67. package/lighthouse-core/audits/accessibility/list.js +1 -1
  68. package/lighthouse-core/audits/accessibility/listitem.js +5 -5
  69. package/lighthouse-core/audits/accessibility/meta-refresh.js +1 -1
  70. package/lighthouse-core/audits/accessibility/meta-viewport.js +1 -1
  71. package/lighthouse-core/audits/accessibility/object-alt.js +1 -1
  72. package/lighthouse-core/audits/accessibility/tabindex.js +1 -1
  73. package/lighthouse-core/audits/accessibility/td-headers-attr.js +1 -1
  74. package/lighthouse-core/audits/accessibility/th-has-data-cells.js +1 -1
  75. package/lighthouse-core/audits/accessibility/valid-lang.js +1 -1
  76. package/lighthouse-core/audits/accessibility/video-caption.js +1 -1
  77. package/lighthouse-core/audits/byte-efficiency/byte-efficiency-audit.js +1 -2
  78. package/lighthouse-core/audits/byte-efficiency/duplicated-javascript.js +12 -11
  79. package/lighthouse-core/audits/byte-efficiency/efficient-animated-content.js +1 -1
  80. package/lighthouse-core/audits/byte-efficiency/legacy-javascript.js +24 -22
  81. package/lighthouse-core/audits/byte-efficiency/offscreen-images.js +2 -3
  82. package/lighthouse-core/audits/byte-efficiency/render-blocking-resources.js +3 -2
  83. package/lighthouse-core/audits/byte-efficiency/unminified-css.js +5 -3
  84. package/lighthouse-core/audits/byte-efficiency/unminified-javascript.js +11 -10
  85. package/lighthouse-core/audits/byte-efficiency/unused-css-rules.js +1 -0
  86. package/lighthouse-core/audits/byte-efficiency/unused-javascript.js +8 -11
  87. package/lighthouse-core/audits/byte-efficiency/uses-responsive-images.js +1 -1
  88. package/lighthouse-core/audits/byte-efficiency/uses-text-compression.js +1 -1
  89. package/lighthouse-core/audits/deprecations.js +598 -8
  90. package/lighthouse-core/audits/diagnostics.js +3 -4
  91. package/lighthouse-core/audits/dobetterweb/doctype.js +9 -20
  92. package/lighthouse-core/audits/dobetterweb/geolocation-on-start.js +1 -1
  93. package/lighthouse-core/audits/dobetterweb/no-document-write.js +1 -1
  94. package/lighthouse-core/audits/dobetterweb/notification-on-start.js +1 -1
  95. package/lighthouse-core/audits/dobetterweb/uses-http2.js +1 -2
  96. package/lighthouse-core/audits/dobetterweb/uses-passive-event-listeners.js +1 -1
  97. package/lighthouse-core/audits/errors-in-console.js +2 -2
  98. package/lighthouse-core/audits/long-tasks.js +2 -3
  99. package/lighthouse-core/audits/metrics/experimental-interaction-to-next-paint.js +3 -1
  100. package/lighthouse-core/audits/metrics/first-contentful-paint-3g.js +2 -2
  101. package/lighthouse-core/audits/metrics/first-contentful-paint.js +2 -3
  102. package/lighthouse-core/audits/metrics/first-meaningful-paint.js +2 -3
  103. package/lighthouse-core/audits/metrics/interactive.js +2 -3
  104. package/lighthouse-core/audits/metrics/largest-contentful-paint.js +2 -3
  105. package/lighthouse-core/audits/metrics/max-potential-fid.js +2 -3
  106. package/lighthouse-core/audits/metrics/speed-index.js +2 -3
  107. package/lighthouse-core/audits/metrics/total-blocking-time.js +2 -3
  108. package/lighthouse-core/audits/metrics.js +2 -3
  109. package/lighthouse-core/audits/no-unload-listeners.js +15 -7
  110. package/lighthouse-core/audits/predictive-perf.js +1 -2
  111. package/lighthouse-core/audits/preload-lcp-image.js +3 -3
  112. package/lighthouse-core/audits/redirects.js +1 -1
  113. package/lighthouse-core/audits/script-treemap-data.js +45 -45
  114. package/lighthouse-core/audits/seo/http-status-code.js +4 -2
  115. package/lighthouse-core/audits/seo/link-text.js +0 -2
  116. package/lighthouse-core/audits/server-response-time.js +17 -2
  117. package/lighthouse-core/audits/service-worker.js +2 -7
  118. package/lighthouse-core/audits/timing-budget.js +2 -3
  119. package/lighthouse-core/audits/uses-rel-preconnect.js +1 -1
  120. package/lighthouse-core/audits/uses-rel-preload.js +1 -1
  121. package/lighthouse-core/audits/valid-source-maps.js +14 -12
  122. package/lighthouse-core/audits/violation-audit.js +1 -1
  123. package/lighthouse-core/audits/work-during-interaction.js +280 -0
  124. package/lighthouse-core/computed/critical-request-chains.js +9 -5
  125. package/lighthouse-core/computed/js-bundles.js +11 -11
  126. package/lighthouse-core/computed/main-resource.js +2 -3
  127. package/lighthouse-core/computed/metrics/first-contentful-paint-all-frames.js +1 -1
  128. package/lighthouse-core/computed/metrics/first-contentful-paint.js +1 -1
  129. package/lighthouse-core/computed/metrics/first-meaningful-paint.js +1 -1
  130. package/lighthouse-core/computed/metrics/interactive.js +1 -1
  131. package/lighthouse-core/computed/metrics/lantern-first-contentful-paint.js +1 -1
  132. package/lighthouse-core/computed/metrics/lantern-first-meaningful-paint.js +1 -1
  133. package/lighthouse-core/computed/metrics/lantern-interactive.js +1 -1
  134. package/lighthouse-core/computed/metrics/lantern-largest-contentful-paint.js +1 -1
  135. package/lighthouse-core/computed/metrics/lantern-max-potential-fid.js +1 -1
  136. package/lighthouse-core/computed/metrics/lantern-metric.js +5 -3
  137. package/lighthouse-core/computed/metrics/lantern-speed-index.js +1 -1
  138. package/lighthouse-core/computed/metrics/lantern-total-blocking-time.js +1 -1
  139. package/lighthouse-core/computed/metrics/largest-contentful-paint-all-frames.js +1 -1
  140. package/lighthouse-core/computed/metrics/largest-contentful-paint.js +1 -1
  141. package/lighthouse-core/computed/metrics/max-potential-fid.js +1 -1
  142. package/lighthouse-core/computed/metrics/metric.js +0 -1
  143. package/lighthouse-core/computed/metrics/responsiveness.js +12 -9
  144. package/lighthouse-core/computed/metrics/speed-index.js +1 -1
  145. package/lighthouse-core/computed/metrics/timing-summary.js +6 -13
  146. package/lighthouse-core/computed/metrics/total-blocking-time.js +1 -1
  147. package/lighthouse-core/computed/module-duplication.js +5 -6
  148. package/lighthouse-core/computed/page-dependency-graph.js +28 -55
  149. package/lighthouse-core/computed/resource-summary.js +5 -5
  150. package/lighthouse-core/computed/unused-css.js +7 -6
  151. package/lighthouse-core/computed/unused-javascript-summary.js +36 -16
  152. package/lighthouse-core/config/budget.js +2 -2
  153. package/lighthouse-core/config/default-config.js +1 -2
  154. package/lighthouse-core/config/metrics-to-audits.js +5 -0
  155. package/lighthouse-core/fraggle-rock/api.js +1 -1
  156. package/lighthouse-core/fraggle-rock/config/default-config.js +8 -5
  157. package/lighthouse-core/fraggle-rock/gather/base-artifacts.js +3 -6
  158. package/lighthouse-core/fraggle-rock/gather/driver.js +2 -2
  159. package/lighthouse-core/fraggle-rock/gather/navigation-runner.js +26 -51
  160. package/lighthouse-core/fraggle-rock/gather/runner-helpers.js +3 -0
  161. package/lighthouse-core/fraggle-rock/gather/session.js +2 -2
  162. package/lighthouse-core/fraggle-rock/gather/snapshot-runner.js +4 -5
  163. package/lighthouse-core/fraggle-rock/gather/timespan-runner.js +6 -6
  164. package/lighthouse-core/gather/connections/cri.js +0 -1
  165. package/lighthouse-core/gather/driver/execution-context.js +2 -4
  166. package/lighthouse-core/gather/driver/navigation.js +9 -9
  167. package/lighthouse-core/gather/driver/network-monitor.js +3 -16
  168. package/lighthouse-core/gather/driver.js +1 -6
  169. package/lighthouse-core/gather/fetcher.js +210 -34
  170. package/lighthouse-core/gather/gather-runner.js +17 -13
  171. package/lighthouse-core/gather/gatherers/accessibility.js +4 -16
  172. package/lighthouse-core/gather/gatherers/console-messages.js +2 -4
  173. package/lighthouse-core/gather/gatherers/dobetterweb/doctype.js +2 -4
  174. package/lighthouse-core/gather/gatherers/full-page-screenshot.js +2 -3
  175. package/lighthouse-core/gather/gatherers/js-usage.js +87 -12
  176. package/lighthouse-core/gather/gatherers/link-elements.js +14 -12
  177. package/lighthouse-core/gather/gatherers/main-document-content.js +8 -8
  178. package/lighthouse-core/gather/gatherers/script-elements.js +56 -7
  179. package/lighthouse-core/gather/gatherers/seo/robots-txt.js +30 -2
  180. package/lighthouse-core/gather/gatherers/source-maps.js +1 -3
  181. package/lighthouse-core/gather/gatherers/trace-elements.js +21 -2
  182. package/lighthouse-core/gather/gatherers/web-app-manifest.js +2 -2
  183. package/lighthouse-core/index.js +2 -26
  184. package/lighthouse-core/lib/cdt/generated/SourceMap.js +1 -1
  185. package/lighthouse-core/lib/dependency-graph/simulator/network-analyzer.js +29 -8
  186. package/lighthouse-core/lib/navigation-error.js +4 -13
  187. package/lighthouse-core/lib/script-helpers.js +6 -11
  188. package/lighthouse-core/lib/url-shim.js +2 -2
  189. package/lighthouse-core/runner.js +5 -0
  190. package/lighthouse-core/scripts/manual-chrome-launcher.js +1 -0
  191. package/lighthouse-core/util-commonjs.js +24 -28
  192. package/package.json +12 -12
  193. package/readme.md +1 -1
  194. package/report/.eslintrc.cjs +1 -3
  195. package/report/assets/styles.css +10 -12
  196. package/report/assets/templates.html +9 -10
  197. package/report/clients/bundle.js +1 -0
  198. package/report/clients/standalone.js +1 -0
  199. package/report/generator/report-generator.js +21 -46
  200. package/report/renderer/api.js +1 -0
  201. package/report/renderer/category-renderer.js +1 -0
  202. package/report/renderer/components.js +304 -303
  203. package/report/renderer/crc-details-renderer.js +1 -0
  204. package/report/renderer/details-renderer.js +10 -10
  205. package/report/renderer/dom.js +1 -0
  206. package/report/renderer/drop-down-menu.js +1 -0
  207. package/report/renderer/element-screenshot-renderer.js +4 -0
  208. package/report/renderer/features-util.js +1 -0
  209. package/report/renderer/i18n.js +62 -118
  210. package/report/renderer/logger.js +1 -0
  211. package/report/renderer/open-tab.js +3 -1
  212. package/report/renderer/performance-category-renderer.js +1 -0
  213. package/report/renderer/pwa-category-renderer.js +1 -0
  214. package/report/renderer/report-renderer.js +1 -0
  215. package/report/renderer/report-ui-features.js +1 -0
  216. package/report/renderer/snippet-renderer.js +1 -0
  217. package/report/renderer/swap-locale-feature.js +1 -0
  218. package/report/renderer/text-encoding.js +1 -0
  219. package/report/renderer/topbar-features.js +1 -0
  220. package/report/renderer/util.js +24 -27
  221. package/report/test/clients/bundle-test.js +4 -0
  222. package/report/test/generator/file-namer-test.js +1 -0
  223. package/report/test/generator/report-generator-test.js +20 -25
  224. package/report/test/renderer/category-renderer-test.js +3 -0
  225. package/report/test/renderer/components-test.js +3 -0
  226. package/report/test/renderer/crc-details-renderer-test.js +3 -0
  227. package/report/test/renderer/details-renderer-test.js +12 -58
  228. package/report/test/renderer/dom-test.js +3 -0
  229. package/report/test/renderer/element-screenshot-renderer-test.js +6 -3
  230. package/report/test/renderer/i18n-test.js +25 -70
  231. package/report/test/renderer/performance-category-renderer-test.js +4 -11
  232. package/report/test/renderer/pwa-category-renderer-test.js +3 -0
  233. package/report/test/renderer/report-renderer-axe-test.js +3 -0
  234. package/report/test/renderer/report-renderer-test.js +3 -0
  235. package/report/test/renderer/report-ui-features-test.js +3 -0
  236. package/report/test/renderer/snippet-renderer-test.js +3 -0
  237. package/report/test/renderer/text-encoding-test.js +3 -0
  238. package/report/test/renderer/util-test.js +5 -2
  239. package/report/test-assets/faux-psi.js +1 -2
  240. package/shared/localization/locales/en-US.json +260 -53
  241. package/shared/localization/locales/en-XL.json +260 -53
  242. package/shared/test/localization/format-test.js +2 -0
  243. package/shared/test/localization/locales-test.js +2 -0
  244. package/shared/test/localization/swap-locale-test.js +2 -0
  245. package/third-party/chromium-synchronization/inspector-issueAdded-types-test.js +2 -0
  246. package/third-party/chromium-synchronization/installability-errors-test.js +2 -0
  247. package/tsconfig.json +0 -1
  248. package/types/artifacts.d.ts +9 -48
  249. package/types/config.d.ts +0 -2
  250. package/types/externs.d.ts +2 -2
  251. package/types/gatherer.d.ts +2 -1
  252. package/types/global-lh.d.ts +0 -3
  253. package/types/lhr/audit-details.d.ts +3 -1
  254. package/types/lhr/lhr.d.ts +2 -2
  255. package/types/lhr/treemap.d.ts +1 -0
  256. package/lighthouse-core/audits/script-elements-test-audit.js +0 -30
  257. package/lighthouse-core/gather/gatherers/scripts.js +0 -154
  258. package/report/test/.eslintrc.cjs +0 -11
  259. package/shared/test/localization/.eslintrc.cjs +0 -11
@@ -146,5 +146,5 @@ class LanternSpeedIndex extends LanternMetric {
146
146
 
147
147
  module.exports = makeComputedArtifact(
148
148
  LanternSpeedIndex,
149
- ['devtoolsLog', 'gatherContext', 'settings', 'simulator', 'trace', 'URL']
149
+ ['devtoolsLog', 'gatherContext', 'settings', 'simulator', 'trace']
150
150
  );
@@ -122,5 +122,5 @@ class LanternTotalBlockingTime extends LanternMetric {
122
122
 
123
123
  module.exports = makeComputedArtifact(
124
124
  LanternTotalBlockingTime,
125
- ['devtoolsLog', 'gatherContext', 'settings', 'simulator', 'trace', 'URL']
125
+ ['devtoolsLog', 'gatherContext', 'settings', 'simulator', 'trace']
126
126
  );
@@ -41,5 +41,5 @@ class LargestContentfulPaintAllFrames extends NavigationMetric {
41
41
 
42
42
  module.exports = makeComputedArtifact(
43
43
  LargestContentfulPaintAllFrames,
44
- ['devtoolsLog', 'gatherContext', 'settings', 'simulator', 'trace', 'URL']
44
+ ['devtoolsLog', 'gatherContext', 'settings', 'simulator', 'trace']
45
45
  );
@@ -48,5 +48,5 @@ class LargestContentfulPaint extends NavigationMetric {
48
48
 
49
49
  module.exports = makeComputedArtifact(
50
50
  LargestContentfulPaint,
51
- ['devtoolsLog', 'gatherContext', 'settings', 'simulator', 'trace', 'URL']
51
+ ['devtoolsLog', 'gatherContext', 'settings', 'simulator', 'trace']
52
52
  );
@@ -41,5 +41,5 @@ class MaxPotentialFID extends NavigationMetric {
41
41
 
42
42
  module.exports = makeComputedArtifact(
43
43
  MaxPotentialFID,
44
- ['devtoolsLog', 'gatherContext', 'settings', 'simulator', 'trace', 'URL']
44
+ ['devtoolsLog', 'gatherContext', 'settings', 'simulator', 'trace']
45
45
  );
@@ -34,7 +34,6 @@ class Metric {
34
34
  devtoolsLog: data.devtoolsLog,
35
35
  gatherContext: data.gatherContext,
36
36
  settings: data.settings,
37
- URL: data.URL,
38
37
  };
39
38
  }
40
39
 
@@ -25,11 +25,14 @@
25
25
  * @property {number} interactionId
26
26
  */
27
27
  /** @typedef {LH.Trace.AsyncEvent & {name: 'EventTiming', args: {data: EventTimingData}}} EventTimingEvent */
28
-
28
+ /**
29
+ * A fallback EventTiming placeholder, used if updated EventTiming events are not available.
30
+ * TODO: Remove once 103.0.5052.0 is sufficiently released.
31
+ * @typedef {{name: 'FallbackTiming', duration: number}} FallbackTimingEvent
32
+ */
29
33
 
30
34
  const makeComputedArtifact = require('../computed-artifact.js');
31
35
  const ProcessedTrace = require('../processed-trace.js');
32
- const LHError = require('../../lib/lh-error.js');
33
36
 
34
37
  const KEYBOARD_EVENTS = new Set(['keydown', 'keypress', 'keyup']);
35
38
  const CLICK_TAP_DRAG_EVENTS = new Set([
@@ -77,7 +80,7 @@ class Responsiveness {
77
80
  * one interaction had this duration by returning the first found.
78
81
  * @param {ResponsivenessEvent} responsivenessEvent
79
82
  * @param {LH.Trace} trace
80
- * @return {EventTimingEvent}
83
+ * @return {EventTimingEvent|FallbackTimingEvent}
81
84
  */
82
85
  static findInteractionEvent(responsivenessEvent, {traceEvents}) {
83
86
  const candidates = traceEvents.filter(/** @return {evt is EventTimingEvent} */ evt => {
@@ -85,12 +88,12 @@ class Responsiveness {
85
88
  return evt.name === 'EventTiming' && evt.ph !== 'e';
86
89
  });
87
90
 
88
- if (candidates.length && !candidates[0].args.data.frame) {
91
+ if (candidates.length && !candidates.some(candidate => candidate.args.data?.frame)) {
89
92
  // Full EventTiming data added in https://crrev.com/c/3632661
90
- throw new LHError(
91
- LHError.errors.UNSUPPORTED_OLD_CHROME,
92
- {featureName: 'detailed EventTiming trace events'}
93
- );
93
+ return {
94
+ name: 'FallbackTiming',
95
+ duration: responsivenessEvent.args.data.maxDuration,
96
+ };
94
97
  }
95
98
 
96
99
  const {maxDuration, interactionType} = responsivenessEvent.args.data;
@@ -131,7 +134,7 @@ class Responsiveness {
131
134
  /**
132
135
  * @param {{trace: LH.Trace, settings: Immutable<LH.Config.Settings>}} data
133
136
  * @param {LH.Artifacts.ComputedContext} context
134
- * @return {Promise<EventTimingEvent|null>}
137
+ * @return {Promise<EventTimingEvent|FallbackTimingEvent|null>}
135
138
  */
136
139
  static async compute_(data, context) {
137
140
  const {settings, trace} = data;
@@ -36,5 +36,5 @@ class SpeedIndex extends NavigationMetric {
36
36
 
37
37
  module.exports = makeComputedArtifact(
38
38
  SpeedIndex,
39
- ['devtoolsLog', 'gatherContext', 'settings', 'simulator', 'trace', 'URL']
39
+ ['devtoolsLog', 'gatherContext', 'settings', 'simulator', 'trace']
40
40
  );
@@ -26,12 +26,11 @@ class TimingSummary {
26
26
  * @param {LH.DevtoolsLog} devtoolsLog
27
27
  * @param {LH.Artifacts['GatherContext']} gatherContext
28
28
  * @param {ImmutableObject<LH.Config.Settings>} settings
29
- * @param {LH.Artifacts['URL']} URL
30
29
  * @param {LH.Artifacts.ComputedContext} context
31
30
  * @return {Promise<{metrics: LH.Artifacts.TimingSummary, debugInfo: Record<string,boolean>}>}
32
31
  */
33
- static async summarize(trace, devtoolsLog, gatherContext, settings, URL, context) {
34
- const metricComputationData = {trace, devtoolsLog, gatherContext, settings, URL};
32
+ static async summarize(trace, devtoolsLog, gatherContext, settings, context) {
33
+ const metricComputationData = {trace, devtoolsLog, gatherContext, settings};
35
34
  /**
36
35
  * @template TArtifacts
37
36
  * @template TReturn
@@ -135,23 +134,17 @@ class TimingSummary {
135
134
  return {metrics, debugInfo};
136
135
  }
137
136
  /**
138
- * @param {{trace: LH.Trace, devtoolsLog: LH.DevtoolsLog, gatherContext: LH.Artifacts['GatherContext']; settings: ImmutableObject<LH.Config.Settings>, URL: LH.Artifacts['URL']}} data
137
+ * @param {{trace: LH.Trace, devtoolsLog: LH.DevtoolsLog, gatherContext: LH.Artifacts['GatherContext']; settings: ImmutableObject<LH.Config.Settings>}} data
139
138
  * @param {LH.Artifacts.ComputedContext} context
140
139
  * @return {Promise<{metrics: LH.Artifacts.TimingSummary, debugInfo: Record<string,boolean>}>}
141
140
  */
142
141
  static async compute_(data, context) {
143
- return TimingSummary.summarize(
144
- data.trace,
145
- data.devtoolsLog,
146
- data.gatherContext,
147
- data.settings,
148
- data.URL,
149
- context
150
- );
142
+ return TimingSummary.summarize(data.trace, data.devtoolsLog, data.gatherContext, data.settings,
143
+ context);
151
144
  }
152
145
  }
153
146
 
154
147
  module.exports = makeComputedArtifact(
155
148
  TimingSummary,
156
- ['devtoolsLog', 'gatherContext', 'settings', 'trace', 'URL']
149
+ ['devtoolsLog', 'gatherContext', 'settings', 'trace']
157
150
  );
@@ -70,5 +70,5 @@ class TotalBlockingTime extends ComputedMetric {
70
70
 
71
71
  module.exports = makeComputedArtifact(
72
72
  TotalBlockingTime,
73
- ['devtoolsLog', 'gatherContext', 'settings', 'simulator', 'trace', 'URL']
73
+ ['devtoolsLog', 'gatherContext', 'settings', 'simulator', 'trace']
74
74
  );
@@ -43,7 +43,7 @@ class ModuleDuplication {
43
43
  }
44
44
 
45
45
  /**
46
- * @param {Map<string, Array<{scriptId: string, resourceSize: number}>>} moduleNameToSourceData
46
+ * @param {Map<string, Array<{scriptUrl: string, resourceSize: number}>>} moduleNameToSourceData
47
47
  */
48
48
  static _normalizeAggregatedData(moduleNameToSourceData) {
49
49
  for (const [key, originalSourceData] of moduleNameToSourceData.entries()) {
@@ -74,7 +74,7 @@ class ModuleDuplication {
74
74
  }
75
75
 
76
76
  /**
77
- * @param {Pick<LH.Artifacts, 'Scripts'|'SourceMaps'>} artifacts
77
+ * @param {Pick<LH.Artifacts, 'ScriptElements'|'SourceMaps'>} artifacts
78
78
  * @param {LH.Artifacts.ComputedContext} context
79
79
  */
80
80
  static async compute_(artifacts, context) {
@@ -109,7 +109,7 @@ class ModuleDuplication {
109
109
  }
110
110
  }
111
111
 
112
- /** @type {Map<string, Array<{scriptId: string, scriptUrl: string, resourceSize: number}>>} */
112
+ /** @type {Map<string, Array<{scriptUrl: string, resourceSize: number}>>} */
113
113
  const moduleNameToSourceData = new Map();
114
114
  for (const {rawMap, script} of bundles) {
115
115
  const sourceDataArray = sourceDatasMap.get(rawMap);
@@ -122,8 +122,7 @@ class ModuleDuplication {
122
122
  moduleNameToSourceData.set(sourceData.source, data);
123
123
  }
124
124
  data.push({
125
- scriptId: script.scriptId,
126
- scriptUrl: script.url,
125
+ scriptUrl: script.src || '',
127
126
  resourceSize: sourceData.resourceSize,
128
127
  });
129
128
  }
@@ -134,4 +133,4 @@ class ModuleDuplication {
134
133
  }
135
134
  }
136
135
 
137
- module.exports = makeComputedArtifact(ModuleDuplication, ['Scripts', 'SourceMaps']);
136
+ module.exports = makeComputedArtifact(ModuleDuplication, ['ScriptElements', 'SourceMaps']);
@@ -8,14 +8,13 @@
8
8
  const makeComputedArtifact = require('./computed-artifact.js');
9
9
  const NetworkNode = require('../lib/dependency-graph/network-node.js');
10
10
  const CPUNode = require('../lib/dependency-graph/cpu-node.js');
11
+ const NetworkAnalyzer = require('../lib/dependency-graph/simulator/network-analyzer.js');
11
12
  const TracingProcessor = require('../lib/tracehouse/trace-processor.js');
12
13
  const NetworkRequest = require('../lib/network-request.js');
13
14
  const ProcessedTrace = require('./processed-trace.js');
14
15
  const NetworkRecords = require('./network-records.js');
15
- const NetworkAnalyzer = require('../lib/dependency-graph/simulator/network-analyzer.js');
16
16
 
17
17
  /** @typedef {import('../lib/dependency-graph/base-node.js').Node} Node */
18
- /** @typedef {Omit<LH.Artifacts['URL'], 'initialUrl'|'finalUrl'>} URLArtifact */
19
18
 
20
19
  // Shorter tasks have negligible impact on simulation results.
21
20
  const SIGNIFICANT_DUR_THRESHOLD_MS = 10;
@@ -389,25 +388,34 @@ class PageDependencyGraph {
389
388
  /**
390
389
  * @param {LH.Artifacts.ProcessedTrace} processedTrace
391
390
  * @param {Array<LH.Artifacts.NetworkRequest>} networkRecords
392
- * @param {URLArtifact} URL
393
391
  * @return {Node}
394
392
  */
395
- static createGraph(processedTrace, networkRecords, URL) {
393
+ static createGraph(processedTrace, networkRecords) {
396
394
  const networkNodeOutput = PageDependencyGraph.getNetworkNodeOutput(networkRecords);
397
395
  const cpuNodes = PageDependencyGraph.getCPUNodes(processedTrace);
398
- const {requestedUrl, mainDocumentUrl} = URL;
399
- if (!requestedUrl) throw new Error('requestedUrl is required to get the root request');
400
- if (!mainDocumentUrl) throw new Error('mainDocumentUrl is required to get the main resource');
401
-
402
- const rootRequest = NetworkAnalyzer.findResourceForUrl(networkRecords, requestedUrl);
403
- if (!rootRequest) throw new Error('rootRequest not found');
404
- const rootNode = networkNodeOutput.idToNodeMap.get(rootRequest.requestId);
405
- if (!rootNode) throw new Error('rootNode not found');
406
396
 
407
- const mainDocumentRequest = NetworkAnalyzer.findResourceForUrl(networkRecords, mainDocumentUrl);
408
- if (!mainDocumentRequest) throw new Error('mainDocumentRequest not found');
397
+ // The main document request is the earliest network request *of type document*.
398
+ // This will be different from the root request when there are server redirects.
399
+ const mainDocumentRequest = NetworkAnalyzer.findMainDocument(networkRecords);
409
400
  const mainDocumentNode = networkNodeOutput.idToNodeMap.get(mainDocumentRequest.requestId);
410
- if (!mainDocumentNode) throw new Error('mainDocumentNode not found');
401
+ if (!mainDocumentNode) {
402
+ // mainDocumentNode should always be found.
403
+ throw new Error('mainDocumentNode not found.');
404
+ }
405
+
406
+ // The root request is the earliest request in the main document redirect chain.
407
+ // Will be undefined if there were no redirects.
408
+ const rootRequest = mainDocumentNode.record.redirects?.[0];
409
+
410
+ let rootNode;
411
+ if (rootRequest) {
412
+ // rootNode should always be found.
413
+ rootNode = rootRequest && networkNodeOutput.idToNodeMap.get(rootRequest.requestId);
414
+ if (!rootNode) throw new Error('rootNode not found');
415
+ } else {
416
+ // Use main document as root if there were no redirects.
417
+ rootNode = mainDocumentNode;
418
+ }
411
419
 
412
420
  PageDependencyGraph.linkNetworkNodes(rootNode, networkNodeOutput);
413
421
  PageDependencyGraph.linkCPUNodes(rootNode, networkNodeOutput, cpuNodes);
@@ -453,58 +461,23 @@ class PageDependencyGraph {
453
461
  }
454
462
 
455
463
  /**
456
- * Recalculate `artifacts.URL` for clients that don't provide it.
457
- *
458
- * @param {LH.DevtoolsLog} devtoolsLog
459
- * @param {LH.Artifacts.NetworkRequest[]} networkRecords
460
- * @param {LH.Artifacts.ProcessedTrace} processedTrace
461
- * @return {URLArtifact}
462
- */
463
- static getDocumentUrls(devtoolsLog, networkRecords, processedTrace) {
464
- const mainFrameId = processedTrace.mainFrameIds.frameId;
465
-
466
- /** @type {string|undefined} */
467
- let requestedUrl;
468
- /** @type {string|undefined} */
469
- let mainDocumentUrl;
470
- for (const event of devtoolsLog) {
471
- if (event.method === 'Page.frameNavigated' && event.params.frame.id === mainFrameId) {
472
- const {url} = event.params.frame;
473
- // Only set requestedUrl on the first main frame navigation.
474
- if (!requestedUrl) requestedUrl = url;
475
- mainDocumentUrl = url;
476
- }
477
- }
478
- if (!requestedUrl || !mainDocumentUrl) throw new Error('No main frame navigations found');
479
-
480
- const initialRequest = NetworkAnalyzer.findResourceForUrl(networkRecords, requestedUrl);
481
- if (initialRequest?.redirects?.length) requestedUrl = initialRequest.redirects[0].url;
482
-
483
- return {requestedUrl, mainDocumentUrl};
484
- }
485
-
486
- /**
487
- * @param {{trace: LH.Trace, devtoolsLog: LH.DevtoolsLog, URL: LH.Artifacts['URL']}} data
464
+ * @param {{trace: LH.Trace, devtoolsLog: LH.DevtoolsLog}} data
488
465
  * @param {LH.Artifacts.ComputedContext} context
489
466
  * @return {Promise<Node>}
490
467
  */
491
468
  static async compute_(data, context) {
492
- const {trace, devtoolsLog} = data;
469
+ const trace = data.trace;
470
+ const devtoolsLog = data.devtoolsLog;
493
471
  const [processedTrace, networkRecords] = await Promise.all([
494
472
  ProcessedTrace.request(trace, context),
495
473
  NetworkRecords.request(devtoolsLog, context),
496
474
  ]);
497
475
 
498
- // COMPAT: Backport for pre-10.0 clients that don't pass the URL artifact here (e.g. pubads).
499
- // Calculates the URL artifact from the processed trace and DT log.
500
- const URL = data.URL ||
501
- PageDependencyGraph.getDocumentUrls(devtoolsLog, networkRecords, processedTrace);
502
-
503
- return PageDependencyGraph.createGraph(processedTrace, networkRecords, URL);
476
+ return PageDependencyGraph.createGraph(processedTrace, networkRecords);
504
477
  }
505
478
  }
506
479
 
507
- module.exports = makeComputedArtifact(PageDependencyGraph, ['devtoolsLog', 'trace', 'URL']);
480
+ module.exports = makeComputedArtifact(PageDependencyGraph, ['devtoolsLog', 'trace']);
508
481
 
509
482
  /**
510
483
  * @typedef {Object} NetworkNodeOutput
@@ -35,11 +35,11 @@ class ResourceSummary {
35
35
 
36
36
  /**
37
37
  * @param {Array<LH.Artifacts.NetworkRequest>} networkRecords
38
- * @param {LH.Artifacts.URL} URLArtifact
38
+ * @param {string} mainResourceURL
39
39
  * @param {ImmutableObject<LH.Budget[]|null>} budgets
40
40
  * @return {Record<LH.Budget.ResourceType, ResourceEntry>}
41
41
  */
42
- static summarize(networkRecords, URLArtifact, budgets) {
42
+ static summarize(networkRecords, mainResourceURL, budgets) {
43
43
  /** @type {Record<LH.Budget.ResourceType, ResourceEntry>} */
44
44
  const resourceSummary = {
45
45
  'stylesheet': {count: 0, resourceSize: 0, transferSize: 0},
@@ -52,13 +52,13 @@ class ResourceSummary {
52
52
  'total': {count: 0, resourceSize: 0, transferSize: 0},
53
53
  'third-party': {count: 0, resourceSize: 0, transferSize: 0},
54
54
  };
55
- const budget = Budget.getMatchingBudget(budgets, URLArtifact.mainDocumentUrl);
55
+ const budget = Budget.getMatchingBudget(budgets, mainResourceURL);
56
56
  /** @type {ReadonlyArray<string>} */
57
57
  let firstPartyHosts = [];
58
58
  if (budget?.options?.firstPartyHostnames) {
59
59
  firstPartyHosts = budget.options.firstPartyHostnames;
60
60
  } else {
61
- const rootDomain = Util.getRootDomain(URLArtifact.finalUrl);
61
+ const rootDomain = Util.getRootDomain(mainResourceURL);
62
62
  firstPartyHosts = [`*.${rootDomain}`];
63
63
  }
64
64
 
@@ -107,7 +107,7 @@ class ResourceSummary {
107
107
  */
108
108
  static async compute_(data, context) {
109
109
  const networkRecords = await NetworkRecords.request(data.devtoolsLog, context);
110
- return ResourceSummary.summarize(networkRecords, data.URL, data.budgets);
110
+ return ResourceSummary.summarize(networkRecords, data.URL.finalUrl, data.budgets);
111
111
  }
112
112
  }
113
113
 
@@ -120,11 +120,12 @@ class UnusedCSS {
120
120
 
121
121
  /**
122
122
  * @param {StyleSheetInfo} stylesheetInfo The stylesheetInfo object.
123
+ * @param {string} pageUrl The URL of the page, used to identify inline styles.
123
124
  * @return {LH.Audit.ByteEfficiencyItem}
124
125
  */
125
- static mapSheetToResult(stylesheetInfo) {
126
+ static mapSheetToResult(stylesheetInfo, pageUrl) {
126
127
  let url = stylesheetInfo.header.sourceURL;
127
- if (!url || stylesheetInfo.header.isInline) {
128
+ if (!url || url === pageUrl) {
128
129
  const contentPreview = UnusedCSS.determineContentPreview(stylesheetInfo.content);
129
130
  url = contentPreview;
130
131
  }
@@ -134,20 +135,20 @@ class UnusedCSS {
134
135
  }
135
136
 
136
137
  /**
137
- * @param {{CSSUsage: LH.Artifacts['CSSUsage'], devtoolsLog: LH.DevtoolsLog}} data
138
+ * @param {{CSSUsage: LH.Artifacts['CSSUsage'], URL: LH.Artifacts['URL'], devtoolsLog: LH.DevtoolsLog}} data
138
139
  * @param {LH.Artifacts.ComputedContext} context
139
140
  * @return {Promise<LH.Audit.ByteEfficiencyItem[]>}
140
141
  */
141
142
  static async compute_(data, context) {
142
- const {CSSUsage, devtoolsLog} = data;
143
+ const {CSSUsage, URL, devtoolsLog} = data;
143
144
  const networkRecords = await NetworkRecords.request(devtoolsLog, context);
144
145
  const indexedSheets = UnusedCSS.indexStylesheetsById(CSSUsage.stylesheets, networkRecords);
145
146
  UnusedCSS.indexUsedRules(CSSUsage.rules, indexedSheets);
146
147
 
147
148
  const items = Object.keys(indexedSheets)
148
- .map(sheetId => UnusedCSS.mapSheetToResult(indexedSheets[sheetId]));
149
+ .map(sheetId => UnusedCSS.mapSheetToResult(indexedSheets[sheetId], URL.finalUrl));
149
150
  return items;
150
151
  }
151
152
  }
152
153
 
153
- module.exports = makeComputedArtifact(UnusedCSS, ['CSSUsage', 'devtoolsLog']);
154
+ module.exports = makeComputedArtifact(UnusedCSS, ['CSSUsage', 'URL', 'devtoolsLog']);
@@ -16,14 +16,14 @@ const makeComputedArtifact = require('./computed-artifact.js');
16
16
 
17
17
  /**
18
18
  * @typedef ComputeInput
19
- * @property {string} scriptId
20
- * @property {Omit<LH.Crdp.Profiler.ScriptCoverage, 'url'>} scriptCoverage
19
+ * @property {string} url
20
+ * @property {Array<Omit<LH.Crdp.Profiler.ScriptCoverage, 'url'>>} scriptCoverages
21
21
  * @property {LH.Artifacts.Bundle=} bundle
22
22
  */
23
23
 
24
24
  /**
25
25
  * @typedef Summary
26
- * @property {string} scriptId
26
+ * @property {string} url
27
27
  * @property {number} wastedBytes
28
28
  * @property {number} totalBytes
29
29
  * @property {number} wastedBytes
@@ -68,24 +68,43 @@ class UnusedJavascriptSummary {
68
68
  }
69
69
 
70
70
  /**
71
- * @param {string} scriptId
72
- * @param {WasteData} wasteData
71
+ * @param {string} url
72
+ * @param {ReturnType<typeof UnusedJavascriptSummary.determineLengths>} lengths
73
73
  * @return {Summary}
74
74
  */
75
- static createItem(scriptId, wasteData) {
76
- const wastedRatio = (wasteData.unusedLength / wasteData.contentLength) || 0;
77
- const wastedBytes = Math.round(wasteData.contentLength * wastedRatio);
75
+ static createItem(url, lengths) {
76
+ const wastedRatio = (lengths.unused / lengths.content) || 0;
77
+ const wastedBytes = Math.round(lengths.content * wastedRatio);
78
78
 
79
79
  return {
80
- scriptId,
81
- totalBytes: wasteData.contentLength,
80
+ url,
81
+ totalBytes: lengths.content,
82
82
  wastedBytes,
83
83
  wastedPercent: 100 * wastedRatio,
84
84
  };
85
85
  }
86
86
 
87
87
  /**
88
- * @param {WasteData} wasteData
88
+ * @param {WasteData[]} wasteData
89
+ */
90
+ static determineLengths(wasteData) {
91
+ let unused = 0;
92
+ let content = 0;
93
+ // TODO: this is right for multiple script tags in an HTML document,
94
+ // but may be wrong for multiple frames using the same script resource.
95
+ for (const usage of wasteData) {
96
+ unused += usage.unusedLength;
97
+ content += usage.contentLength;
98
+ }
99
+
100
+ return {
101
+ content,
102
+ unused,
103
+ };
104
+ }
105
+
106
+ /**
107
+ * @param {WasteData[]} wasteData
89
108
  * @param {LH.Artifacts.Bundle} bundle
90
109
  */
91
110
  static createSourceWastedBytes(wasteData, bundle) {
@@ -112,7 +131,7 @@ class UnusedJavascriptSummary {
112
131
  mapping.lastColumnNumber - 1 :
113
132
  lineLengths[mapping.lineNumber];
114
133
  for (let i = mapping.columnNumber; i <= lastColumnOfMapping; i++) {
115
- if (wasteData.unusedByIndex[offset] === 1) {
134
+ if (wasteData.every(data => data.unusedByIndex[offset] === 1)) {
116
135
  const key = mapping.sourceURL || '(unmapped)';
117
136
  files[key] = (files[key] || 0) + 1;
118
137
  }
@@ -136,10 +155,11 @@ class UnusedJavascriptSummary {
136
155
  * @return {Promise<Summary>}
137
156
  */
138
157
  static async compute_(data) {
139
- const {scriptId, scriptCoverage, bundle} = data;
158
+ const {url, scriptCoverages, bundle} = data;
140
159
 
141
- const wasteData = UnusedJavascriptSummary.computeWaste(scriptCoverage);
142
- const item = UnusedJavascriptSummary.createItem(scriptId, wasteData);
160
+ const wasteData = scriptCoverages.map(UnusedJavascriptSummary.computeWaste);
161
+ const lengths = UnusedJavascriptSummary.determineLengths(wasteData);
162
+ const item = UnusedJavascriptSummary.createItem(url, lengths);
143
163
  if (!bundle) return item;
144
164
 
145
165
  return {
@@ -151,5 +171,5 @@ class UnusedJavascriptSummary {
151
171
 
152
172
  module.exports = makeComputedArtifact(
153
173
  UnusedJavascriptSummary,
154
- ['bundle', 'scriptCoverage', 'scriptId']
174
+ ['bundle', 'scriptCoverages', 'url']
155
175
  );
@@ -137,11 +137,11 @@ class Budget {
137
137
  * If multiple budgets match based on thier 'path' property,
138
138
  * then the last-listed of those budgets is returned.
139
139
  * @param {Immutable<Array<LH.Budget>>|null} budgets
140
- * @param {string|undefined} url
140
+ * @param {string} url
141
141
  * @return {Immutable<LH.Budget> | undefined} budget
142
142
  */
143
143
  static getMatchingBudget(budgets, url) {
144
- if (budgets === null || url === undefined) return;
144
+ if (budgets === null) return;
145
145
 
146
146
  // Applies the LAST matching budget.
147
147
  for (let i = budgets.length - 1; i >= 0; i--) {
@@ -41,7 +41,7 @@ const UIStrings = {
41
41
  /** Description of the Accessibility category. This is displayed at the top of a list of audits focused on making web content accessible to all users. No character length limits. 'improve the accessibility of your web app' becomes link text to additional documentation. */
42
42
  a11yCategoryDescription: 'These checks highlight opportunities to [improve the accessibility of your web app](https://web.dev/lighthouse-accessibility/). Only a subset of accessibility issues can be automatically detected so manual testing is also encouraged.',
43
43
  /** Description of the Accessibility manual checks category. This description is displayed above a list of accessibility audits that currently have no automated test and so must be verified manually by the user. No character length limits. 'conducting an accessibility review' becomes link text to additional documentation. */
44
- a11yCategoryManualDescription: 'These items address areas which an automated testing tool cannot cover. Learn more in our guide on [conducting an accessibility review](https://web.dev/how-to-review/).',
44
+ a11yCategoryManualDescription: 'These items address areas which an automated testing tool cannot cover. Learn more in our guide on [conducting an accessibility review](https://developers.google.com/web/fundamentals/accessibility/how-to-review).',
45
45
  /** Title of the best practices section of the Accessibility category. Within this section are audits with descriptive titles that highlight common accessibility best practices. */
46
46
  a11yBestPracticesGroupTitle: 'Best practices',
47
47
  /** Description of the best practices section within the Accessibility category. Within this section are audits with descriptive titles that highlight common accessibility best practices. */
@@ -143,7 +143,6 @@ const defaultConfig = {
143
143
  'link-elements',
144
144
  'meta-elements',
145
145
  'script-elements',
146
- 'scripts',
147
146
  'iframe-elements',
148
147
  'inputs',
149
148
  'main-document-content',
@@ -48,9 +48,14 @@ const clsRelevantAudits = [
48
48
  // 'preload-fonts', // actually in BP, rather than perf
49
49
  ];
50
50
 
51
+ const inpRelevantAudits = [
52
+ 'work-during-interaction',
53
+ ];
54
+
51
55
  module.exports = {
52
56
  fcpRelevantAudits,
53
57
  lcpRelevantAudits,
54
58
  tbtRelevantAudits,
55
59
  clsRelevantAudits,
60
+ inpRelevantAudits,
56
61
  };
@@ -13,7 +13,7 @@ const {generateFlowReportHtml} = require('../../report/generator/report-generato
13
13
  const Runner = require('../runner.js');
14
14
 
15
15
  /**
16
- * @param {LH.Puppeteer.Page} page
16
+ * @param {import('puppeteer').Page} page
17
17
  * @param {ConstructorParameters<LH.UserFlow>[1]} [options]
18
18
  */
19
19
  async function startFlow(page, options) {
@@ -6,19 +6,23 @@
6
6
  'use strict';
7
7
 
8
8
  const legacyDefaultConfig = require('../../config/default-config.js');
9
+ const m2a = require('../../config/metrics-to-audits.js');
9
10
  const {deepClone} = require('../../config/config-helpers.js');
10
11
 
11
12
  /** @type {LH.Config.AuditJson[]} */
12
13
  const frAudits = [
13
14
  'byte-efficiency/uses-responsive-images-snapshot',
14
15
  'metrics/experimental-interaction-to-next-paint',
16
+ 'work-during-interaction',
15
17
  ];
16
18
 
17
19
  /** @type {Record<string, LH.Config.AuditRefJson[]>} */
18
20
  const frCategoryAuditRefExtensions = {
19
21
  'performance': [
20
22
  {id: 'uses-responsive-images-snapshot', weight: 0},
21
- {id: 'experimental-interaction-to-next-paint', weight: 0, group: 'metrics', acronym: 'INP'},
23
+ {id: 'experimental-interaction-to-next-paint', weight: 0, group: 'metrics', acronym: 'INP',
24
+ relevantAudits: m2a.inpRelevantAudits},
25
+ {id: 'work-during-interaction', weight: 0},
22
26
  ],
23
27
  };
24
28
 
@@ -66,7 +70,6 @@ const artifacts = {
66
70
  RobotsTxt: '',
67
71
  ServiceWorker: '',
68
72
  ScriptElements: '',
69
- Scripts: '',
70
73
  SourceMaps: '',
71
74
  Stacks: '',
72
75
  TagsBlockingFirstPaint: '',
@@ -100,7 +103,6 @@ const defaultConfig = {
100
103
  {id: artifacts.EmbeddedContent, gatherer: 'seo/embedded-content'},
101
104
  {id: artifacts.FontSize, gatherer: 'seo/font-size'},
102
105
  {id: artifacts.Inputs, gatherer: 'inputs'},
103
- {id: artifacts.FullPageScreenshot, gatherer: 'full-page-screenshot'},
104
106
  {id: artifacts.GlobalListeners, gatherer: 'global-listeners'},
105
107
  {id: artifacts.IFrameElements, gatherer: 'iframe-elements'},
106
108
  {id: artifacts.ImageElements, gatherer: 'image-elements'},
@@ -117,7 +119,6 @@ const defaultConfig = {
117
119
  {id: artifacts.RobotsTxt, gatherer: 'seo/robots-txt'},
118
120
  {id: artifacts.ServiceWorker, gatherer: 'service-worker'},
119
121
  {id: artifacts.ScriptElements, gatherer: 'script-elements'},
120
- {id: artifacts.Scripts, gatherer: 'scripts'},
121
122
  {id: artifacts.SourceMaps, gatherer: 'source-maps'},
122
123
  {id: artifacts.Stacks, gatherer: 'stacks'},
123
124
  {id: artifacts.TagsBlockingFirstPaint, gatherer: 'dobetterweb/tags-blocking-first-paint'},
@@ -130,6 +131,9 @@ const defaultConfig = {
130
131
  // Artifact copies are renamed for compatibility with legacy artifacts.
131
132
  {id: artifacts.devtoolsLogs, gatherer: 'devtools-log-compat'},
132
133
  {id: artifacts.traces, gatherer: 'trace-compat'},
134
+
135
+ // FullPageScreenshot comes at the very end so all other node analysis is captured.
136
+ {id: artifacts.FullPageScreenshot, gatherer: 'full-page-screenshot'},
133
137
  ],
134
138
  navigations: [
135
139
  {
@@ -169,7 +173,6 @@ const defaultConfig = {
169
173
  artifacts.RobotsTxt,
170
174
  artifacts.ServiceWorker,
171
175
  artifacts.ScriptElements,
172
- artifacts.Scripts,
173
176
  artifacts.SourceMaps,
174
177
  artifacts.Stacks,
175
178
  artifacts.TagsBlockingFirstPaint,