lighthouse 12.8.2 → 13.0.0

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 (270) hide show
  1. package/cli/cli-flags.js +1 -1
  2. package/cli/test/smokehouse/config/exclusions.js +0 -2
  3. package/cli/test/smokehouse/version-check.d.ts +1 -1
  4. package/core/audits/accessibility/accesskeys.js +3 -3
  5. package/core/audits/accessibility/aria-allowed-attr.js +3 -3
  6. package/core/audits/accessibility/aria-allowed-role.js +2 -1
  7. package/core/audits/accessibility/aria-command-name.js +1 -1
  8. package/core/audits/accessibility/aria-conditional-attr.js +1 -1
  9. package/core/audits/accessibility/aria-deprecated-role.js +1 -1
  10. package/core/audits/accessibility/aria-dialog-name.js +1 -1
  11. package/core/audits/accessibility/aria-hidden-body.js +3 -3
  12. package/core/audits/accessibility/aria-hidden-focus.js +3 -3
  13. package/core/audits/accessibility/aria-input-field-name.js +3 -3
  14. package/core/audits/accessibility/aria-meter-name.js +1 -1
  15. package/core/audits/accessibility/aria-progressbar-name.js +1 -1
  16. package/core/audits/accessibility/aria-prohibited-attr.js +1 -1
  17. package/core/audits/accessibility/aria-required-attr.js +3 -3
  18. package/core/audits/accessibility/aria-required-children.js +3 -3
  19. package/core/audits/accessibility/aria-required-parent.js +3 -3
  20. package/core/audits/accessibility/aria-roles.js +3 -3
  21. package/core/audits/accessibility/aria-text.js +3 -3
  22. package/core/audits/accessibility/aria-toggle-field-name.js +3 -3
  23. package/core/audits/accessibility/aria-tooltip-name.js +1 -1
  24. package/core/audits/accessibility/aria-treeitem-name.js +1 -1
  25. package/core/audits/accessibility/aria-valid-attr-value.js +3 -3
  26. package/core/audits/accessibility/aria-valid-attr.js +3 -3
  27. package/core/audits/accessibility/button-name.js +3 -3
  28. package/core/audits/accessibility/bypass.js +3 -3
  29. package/core/audits/accessibility/color-contrast.js +3 -3
  30. package/core/audits/accessibility/definition-list.js +3 -3
  31. package/core/audits/accessibility/dlitem.js +3 -3
  32. package/core/audits/accessibility/document-title.js +3 -3
  33. package/core/audits/accessibility/duplicate-id-aria.js +3 -3
  34. package/core/audits/accessibility/empty-heading.js +3 -3
  35. package/core/audits/accessibility/form-field-multiple-labels.js +3 -3
  36. package/core/audits/accessibility/frame-title.js +3 -3
  37. package/core/audits/accessibility/heading-order.js +3 -3
  38. package/core/audits/accessibility/html-has-lang.js +3 -3
  39. package/core/audits/accessibility/html-lang-valid.js +3 -3
  40. package/core/audits/accessibility/html-xml-lang-mismatch.js +3 -3
  41. package/core/audits/accessibility/identical-links-same-purpose.js +3 -3
  42. package/core/audits/accessibility/image-alt.js +3 -3
  43. package/core/audits/accessibility/image-redundant-alt.js +4 -3
  44. package/core/audits/accessibility/input-button-name.js +3 -3
  45. package/core/audits/accessibility/input-image-alt.js +3 -3
  46. package/core/audits/accessibility/label-content-name-mismatch.js +3 -3
  47. package/core/audits/accessibility/label.js +3 -3
  48. package/core/audits/accessibility/landmark-one-main.js +3 -4
  49. package/core/audits/accessibility/link-in-text-block.js +3 -3
  50. package/core/audits/accessibility/link-name.js +3 -3
  51. package/core/audits/accessibility/list.js +3 -3
  52. package/core/audits/accessibility/listitem.js +3 -3
  53. package/core/audits/accessibility/meta-refresh.js +3 -3
  54. package/core/audits/accessibility/meta-viewport.js +3 -3
  55. package/core/audits/accessibility/object-alt.js +3 -3
  56. package/core/audits/accessibility/select-name.js +3 -3
  57. package/core/audits/accessibility/skip-link.js +3 -3
  58. package/core/audits/accessibility/tabindex.js +3 -3
  59. package/core/audits/accessibility/table-duplicate-name.js +4 -3
  60. package/core/audits/accessibility/table-fake-caption.js +3 -3
  61. package/core/audits/accessibility/target-size.js +3 -3
  62. package/core/audits/accessibility/td-has-header.js +3 -3
  63. package/core/audits/accessibility/td-headers-attr.js +3 -3
  64. package/core/audits/accessibility/th-has-data-cells.js +3 -3
  65. package/core/audits/accessibility/valid-lang.js +3 -3
  66. package/core/audits/accessibility/video-caption.js +3 -3
  67. package/core/audits/audit.d.ts +0 -4
  68. package/core/audits/audit.js +2 -13
  69. package/core/audits/insights/cls-culprits-insight.js +1 -1
  70. package/core/audits/insights/dom-size-insight.js +11 -7
  71. package/core/audits/insights/font-display-insight.js +3 -1
  72. package/core/audits/insights/image-delivery-insight.js +4 -1
  73. package/core/audits/insights/insight-audit.d.ts +6 -4
  74. package/core/audits/insights/insight-audit.js +27 -8
  75. package/core/audits/insights/third-parties-insight.js +1 -1
  76. package/core/audits/layout-shifts.js +1 -1
  77. package/core/audits/predictive-perf.js +2 -2
  78. package/core/audits/seo/crawlable-anchors.js +2 -3
  79. package/core/audits/seo/manual/structured-data.js +1 -1
  80. package/core/audits/server-response-time.d.ts +0 -5
  81. package/core/audits/server-response-time.js +12 -26
  82. package/core/computed/metrics/cumulative-layout-shift.js +2 -2
  83. package/core/computed/metrics/lantern-metric.js +3 -3
  84. package/core/computed/metrics/lcp-breakdown.d.ts +10 -5
  85. package/core/computed/metrics/lcp-breakdown.js +50 -22
  86. package/core/computed/metrics/time-to-first-byte.js +33 -10
  87. package/core/computed/metrics/timing-summary.js +3 -2
  88. package/core/computed/page-dependency-graph.js +1 -1
  89. package/core/computed/trace-engine-result.js +2 -2
  90. package/core/config/default-config.js +110 -152
  91. package/core/config/experimental-config.js +1 -32
  92. package/core/config/filters.js +6 -9
  93. package/core/config/lr-desktop-config.js +0 -1
  94. package/core/config/lr-mobile-config.js +0 -1
  95. package/core/gather/driver/target-manager.d.ts +1 -1
  96. package/core/gather/driver.d.ts +1 -1
  97. package/core/gather/gatherers/anchor-elements.js +8 -24
  98. package/core/gather/gatherers/image-elements.js +32 -6
  99. package/core/gather/gatherers/inspector-issues.js +1 -28
  100. package/core/gather/gatherers/trace-elements.d.ts +2 -11
  101. package/core/gather/gatherers/trace-elements.js +9 -39
  102. package/core/gather/navigation-runner.js +0 -3
  103. package/core/gather/session.d.ts +1 -1
  104. package/core/lib/asset-saver.d.ts +2 -2
  105. package/core/lib/asset-saver.js +33 -43
  106. package/core/lib/bf-cache-strings.js +10 -9
  107. package/core/lib/deprecations-strings.js +5 -5
  108. package/core/lib/emulation.d.ts +10 -0
  109. package/core/lib/emulation.js +21 -6
  110. package/core/lib/legacy-javascript/legacy-javascript.js +4 -11
  111. package/core/lib/network-request.d.ts +0 -7
  112. package/core/lib/network-request.js +0 -16
  113. package/core/lib/proto-preprocessor.js +10 -25
  114. package/core/runner.js +1 -8
  115. package/core/scoring.js +1 -1
  116. package/dist/report/bundle.esm.js +10 -49
  117. package/dist/report/flow.js +12 -51
  118. package/dist/report/standalone.js +11 -50
  119. package/flow-report/src/i18n/i18n.d.ts +4 -6
  120. package/package.json +16 -19
  121. package/readme.md +2 -2
  122. package/report/assets/styles.css +0 -39
  123. package/report/renderer/api.js +0 -1
  124. package/report/renderer/category-renderer.js +6 -0
  125. package/report/renderer/components.js +1 -1
  126. package/report/renderer/details-renderer.d.ts +1 -2
  127. package/report/renderer/details-renderer.js +0 -1
  128. package/report/renderer/dom.d.ts +0 -13
  129. package/report/renderer/dom.js +0 -38
  130. package/report/renderer/performance-category-renderer.d.ts +0 -26
  131. package/report/renderer/performance-category-renderer.js +10 -142
  132. package/report/renderer/report-ui-features.d.ts +0 -1
  133. package/report/renderer/report-ui-features.js +2 -13
  134. package/report/renderer/report-utils.d.ts +2 -3
  135. package/report/renderer/report-utils.js +4 -6
  136. package/report/types/report-renderer.d.ts +0 -6
  137. package/shared/localization/locales/ar-XB.json +107 -455
  138. package/shared/localization/locales/ar.json +107 -455
  139. package/shared/localization/locales/bg.json +96 -444
  140. package/shared/localization/locales/ca.json +96 -444
  141. package/shared/localization/locales/cs.json +96 -444
  142. package/shared/localization/locales/da.json +96 -444
  143. package/shared/localization/locales/de.json +96 -444
  144. package/shared/localization/locales/el.json +96 -444
  145. package/shared/localization/locales/en-GB.json +96 -444
  146. package/shared/localization/locales/en-US.json +116 -467
  147. package/shared/localization/locales/en-XA.json +93 -441
  148. package/shared/localization/locales/en-XL.json +116 -467
  149. package/shared/localization/locales/es-419.json +96 -444
  150. package/shared/localization/locales/es.json +96 -444
  151. package/shared/localization/locales/fi.json +96 -444
  152. package/shared/localization/locales/fil.json +96 -444
  153. package/shared/localization/locales/fr.json +96 -444
  154. package/shared/localization/locales/he.json +118 -466
  155. package/shared/localization/locales/hi.json +96 -444
  156. package/shared/localization/locales/hr.json +100 -448
  157. package/shared/localization/locales/hu.json +96 -444
  158. package/shared/localization/locales/id.json +96 -444
  159. package/shared/localization/locales/it.json +96 -444
  160. package/shared/localization/locales/ja.json +96 -444
  161. package/shared/localization/locales/ko.json +97 -445
  162. package/shared/localization/locales/lt.json +96 -444
  163. package/shared/localization/locales/lv.json +97 -445
  164. package/shared/localization/locales/nl.json +96 -444
  165. package/shared/localization/locales/no.json +96 -444
  166. package/shared/localization/locales/pl.json +96 -444
  167. package/shared/localization/locales/pt-PT.json +96 -444
  168. package/shared/localization/locales/pt.json +97 -445
  169. package/shared/localization/locales/ro.json +97 -445
  170. package/shared/localization/locales/ru.json +96 -444
  171. package/shared/localization/locales/sk.json +96 -444
  172. package/shared/localization/locales/sl.json +96 -444
  173. package/shared/localization/locales/sr-Latn.json +96 -444
  174. package/shared/localization/locales/sr.json +96 -444
  175. package/shared/localization/locales/sv.json +96 -444
  176. package/shared/localization/locales/ta.json +96 -444
  177. package/shared/localization/locales/te.json +97 -445
  178. package/shared/localization/locales/th.json +96 -444
  179. package/shared/localization/locales/tr.json +96 -444
  180. package/shared/localization/locales/uk.json +96 -444
  181. package/shared/localization/locales/vi.json +96 -444
  182. package/shared/localization/locales/zh-HK.json +96 -444
  183. package/shared/localization/locales/zh-TW.json +97 -445
  184. package/shared/localization/locales/zh.json +96 -444
  185. package/shared/localization/locales.d.ts +2 -0
  186. package/shared/localization/locales.js +130 -139
  187. package/shared/tsconfig.json +2 -0
  188. package/tsconfig-base.json +2 -2
  189. package/tsconfig.json +1 -4
  190. package/types/artifacts.d.ts +6 -81
  191. package/types/audit.d.ts +1 -1
  192. package/types/lhr/settings.d.ts +1 -1
  193. package/core/audits/byte-efficiency/duplicated-javascript.d.ts +0 -45
  194. package/core/audits/byte-efficiency/duplicated-javascript.js +0 -223
  195. package/core/audits/byte-efficiency/efficient-animated-content.d.ts +0 -22
  196. package/core/audits/byte-efficiency/efficient-animated-content.js +0 -93
  197. package/core/audits/byte-efficiency/legacy-javascript.d.ts +0 -28
  198. package/core/audits/byte-efficiency/legacy-javascript.js +0 -144
  199. package/core/audits/byte-efficiency/modern-image-formats.d.ts +0 -38
  200. package/core/audits/byte-efficiency/modern-image-formats.js +0 -187
  201. package/core/audits/byte-efficiency/offscreen-images.d.ts +0 -63
  202. package/core/audits/byte-efficiency/offscreen-images.js +0 -240
  203. package/core/audits/byte-efficiency/render-blocking-resources.d.ts +0 -53
  204. package/core/audits/byte-efficiency/render-blocking-resources.js +0 -312
  205. package/core/audits/byte-efficiency/uses-long-cache-ttl.d.ts +0 -59
  206. package/core/audits/byte-efficiency/uses-long-cache-ttl.js +0 -293
  207. package/core/audits/byte-efficiency/uses-optimized-images.d.ts +0 -33
  208. package/core/audits/byte-efficiency/uses-optimized-images.js +0 -146
  209. package/core/audits/byte-efficiency/uses-responsive-images-snapshot.d.ts +0 -16
  210. package/core/audits/byte-efficiency/uses-responsive-images-snapshot.js +0 -106
  211. package/core/audits/byte-efficiency/uses-responsive-images.d.ts +0 -44
  212. package/core/audits/byte-efficiency/uses-responsive-images.js +0 -202
  213. package/core/audits/byte-efficiency/uses-text-compression.d.ts +0 -14
  214. package/core/audits/byte-efficiency/uses-text-compression.js +0 -108
  215. package/core/audits/critical-request-chains.d.ts +0 -44
  216. package/core/audits/critical-request-chains.js +0 -221
  217. package/core/audits/dobetterweb/dom-size.d.ts +0 -32
  218. package/core/audits/dobetterweb/dom-size.js +0 -182
  219. package/core/audits/dobetterweb/no-document-write.d.ts +0 -16
  220. package/core/audits/dobetterweb/no-document-write.js +0 -86
  221. package/core/audits/dobetterweb/uses-http2.d.ts +0 -72
  222. package/core/audits/dobetterweb/uses-http2.js +0 -276
  223. package/core/audits/dobetterweb/uses-passive-event-listeners.d.ts +0 -16
  224. package/core/audits/dobetterweb/uses-passive-event-listeners.js +0 -69
  225. package/core/audits/font-display.d.ts +0 -32
  226. package/core/audits/font-display.js +0 -195
  227. package/core/audits/largest-contentful-paint-element.d.ts +0 -34
  228. package/core/audits/largest-contentful-paint-element.js +0 -181
  229. package/core/audits/lcp-lazy-loaded.d.ts +0 -22
  230. package/core/audits/lcp-lazy-loaded.js +0 -115
  231. package/core/audits/metrics/first-meaningful-paint.d.ts +0 -12
  232. package/core/audits/metrics/first-meaningful-paint.js +0 -47
  233. package/core/audits/preload-fonts.d.ts +0 -25
  234. package/core/audits/preload-fonts.js +0 -97
  235. package/core/audits/prioritize-lcp-image.d.ts +0 -74
  236. package/core/audits/prioritize-lcp-image.js +0 -297
  237. package/core/audits/seo/font-size.d.ts +0 -24
  238. package/core/audits/seo/font-size.js +0 -344
  239. package/core/audits/third-party-facades.d.ts +0 -41
  240. package/core/audits/third-party-facades.js +0 -234
  241. package/core/audits/third-party-summary.d.ts +0 -78
  242. package/core/audits/third-party-summary.js +0 -236
  243. package/core/audits/uses-rel-preconnect.d.ts +0 -37
  244. package/core/audits/uses-rel-preconnect.js +0 -286
  245. package/core/audits/uses-rel-preload.d.ts +0 -57
  246. package/core/audits/uses-rel-preload.js +0 -263
  247. package/core/audits/viewport.d.ts +0 -17
  248. package/core/audits/viewport.js +0 -87
  249. package/core/audits/work-during-interaction.d.ts +0 -81
  250. package/core/audits/work-during-interaction.js +0 -287
  251. package/core/computed/critical-request-chains.d.ts +0 -42
  252. package/core/computed/critical-request-chains.js +0 -143
  253. package/core/computed/viewport-meta.d.ts +0 -37
  254. package/core/computed/viewport-meta.js +0 -71
  255. package/core/gather/gatherers/cache-contents.d.ts +0 -11
  256. package/core/gather/gatherers/cache-contents.js +0 -56
  257. package/core/gather/gatherers/devtools-log-compat.d.ts +0 -13
  258. package/core/gather/gatherers/devtools-log-compat.js +0 -35
  259. package/core/gather/gatherers/dobetterweb/domstats.d.ts +0 -10
  260. package/core/gather/gatherers/dobetterweb/domstats.js +0 -102
  261. package/core/gather/gatherers/dobetterweb/optimized-images.d.ts +0 -48
  262. package/core/gather/gatherers/dobetterweb/optimized-images.js +0 -169
  263. package/core/gather/gatherers/dobetterweb/response-compression.d.ts +0 -23
  264. package/core/gather/gatherers/dobetterweb/response-compression.js +0 -136
  265. package/core/gather/gatherers/seo/font-size.d.ts +0 -131
  266. package/core/gather/gatherers/seo/font-size.js +0 -347
  267. package/core/gather/gatherers/trace-compat.d.ts +0 -13
  268. package/core/gather/gatherers/trace-compat.js +0 -35
  269. package/types/internal/metaviewport-parser.d.ts +0 -13
  270. package/types/internal/parse-cache-control.d.ts +0 -20
@@ -10,42 +10,70 @@ import {LargestContentfulPaint} from './largest-contentful-paint.js';
10
10
  import {ProcessedNavigation} from '../processed-navigation.js';
11
11
  import {TimeToFirstByte} from './time-to-first-byte.js';
12
12
  import {LCPImageRecord} from '../lcp-image-record.js';
13
+ import {NavigationInsights} from '../navigation-insights.js';
13
14
 
15
+ /**
16
+ * Note: this omits renderDelay for simulated throttling.
17
+ */
14
18
  class LCPBreakdown {
15
19
  /**
16
20
  * @param {LH.Artifacts.MetricComputationDataInput} data
17
21
  * @param {LH.Artifacts.ComputedContext} context
18
- * @return {Promise<{ttfb: number, loadStart?: number, loadEnd?: number}>}
22
+ * @return {Promise<{ttfb: number, loadDelay?: number, loadDuration?: number, renderDelay?: number}>}
19
23
  */
20
24
  static async compute_(data, context) {
21
- const processedNavigation = await ProcessedNavigation.request(data.trace, context);
22
- const observedLcp = processedNavigation.timings.largestContentfulPaint;
23
- if (observedLcp === undefined) {
24
- throw new LighthouseError(LighthouseError.errors.NO_LCP);
25
- }
26
- const timeOrigin = processedNavigation.timestamps.timeOrigin / 1000;
25
+ if (data.settings.throttlingMethod === 'simulate') {
26
+ const processedNavigation = await ProcessedNavigation.request(data.trace, context);
27
+ const observedLcp = processedNavigation.timings.largestContentfulPaint;
28
+ if (observedLcp === undefined) {
29
+ throw new LighthouseError(LighthouseError.errors.NO_LCP);
30
+ }
31
+ const timeOrigin = processedNavigation.timestamps.timeOrigin / 1000;
27
32
 
28
- const {timing: ttfb} = await TimeToFirstByte.request(data, context);
33
+ const {timing: ttfb} = await TimeToFirstByte.request(data, context);
29
34
 
30
- const lcpRecord = await LCPImageRecord.request(data, context);
31
- if (!lcpRecord) {
32
- return {ttfb};
33
- }
35
+ const lcpRecord = await LCPImageRecord.request(data, context);
36
+ if (!lcpRecord) {
37
+ return {ttfb};
38
+ }
39
+
40
+ // Official LCP^tm. Will be lantern result if simulated, otherwise same as observedLcp.
41
+ const {timing: metricLcp} = await LargestContentfulPaint.request(data, context);
42
+ const throttleRatio = metricLcp / observedLcp;
34
43
 
35
- // Official LCP^tm. Will be lantern result if simulated, otherwise same as observedLcp.
36
- const {timing: metricLcp} = await LargestContentfulPaint.request(data, context);
37
- const throttleRatio = metricLcp / observedLcp;
44
+ const unclampedLoadStart = (lcpRecord.networkRequestTime - timeOrigin) * throttleRatio;
45
+ const loadDelay = Math.max(ttfb, Math.min(unclampedLoadStart, metricLcp));
38
46
 
39
- const unclampedLoadStart = (lcpRecord.networkRequestTime - timeOrigin) * throttleRatio;
40
- const loadStart = Math.max(ttfb, Math.min(unclampedLoadStart, metricLcp));
47
+ const unclampedLoadEnd = (lcpRecord.networkEndTime - timeOrigin) * throttleRatio;
48
+ const loadDuration = Math.max(loadDelay, Math.min(unclampedLoadEnd, metricLcp));
41
49
 
42
- const unclampedLoadEnd = (lcpRecord.networkEndTime - timeOrigin) * throttleRatio;
43
- const loadEnd = Math.max(loadStart, Math.min(unclampedLoadEnd, metricLcp));
50
+ return {
51
+ ttfb,
52
+ loadDelay,
53
+ loadDuration,
54
+ };
55
+ }
56
+
57
+ const {trace, settings, SourceMaps} = data;
58
+ const navInsights = await NavigationInsights.request({trace, settings, SourceMaps}, context);
59
+ const lcpBreakdown = navInsights.model.LCPBreakdown;
60
+ if (lcpBreakdown instanceof Error) {
61
+ throw new LighthouseError(LighthouseError.errors.NO_LCP, {}, {cause: lcpBreakdown});
62
+ }
63
+
64
+ if (!lcpBreakdown.subparts) {
65
+ throw new LighthouseError(LighthouseError.errors.NO_LCP);
66
+ }
44
67
 
45
68
  return {
46
- ttfb,
47
- loadStart,
48
- loadEnd,
69
+ ttfb: lcpBreakdown.subparts.ttfb.range / 1000,
70
+ loadDelay: lcpBreakdown.subparts.loadDelay !== undefined ?
71
+ lcpBreakdown.subparts.loadDelay.range / 1000 :
72
+ undefined,
73
+ loadDuration: lcpBreakdown.subparts.loadDuration !== undefined ?
74
+ lcpBreakdown.subparts.loadDuration.range / 1000 :
75
+ undefined,
76
+ renderDelay: lcpBreakdown.subparts.renderDelay.range / 1000,
49
77
  };
50
78
  }
51
79
  }
@@ -4,10 +4,14 @@
4
4
  * SPDX-License-Identifier: Apache-2.0
5
5
  */
6
6
 
7
+ import {calculateDocFirstByteTs} from '@paulirish/trace_engine/models/trace/insights/Common.js';
8
+
7
9
  import {makeComputedArtifact} from '../computed-artifact.js';
8
10
  import {NavigationMetric} from './navigation-metric.js';
9
11
  import {MainResource} from '../main-resource.js';
10
12
  import {NetworkAnalysis} from '../network-analysis.js';
13
+ import {NavigationInsights} from '../navigation-insights.js';
14
+ import {TraceEngineResult} from '../trace-engine-result.js';
11
15
 
12
16
  class TimeToFirstByte extends NavigationMetric {
13
17
  /**
@@ -41,18 +45,37 @@ class TimeToFirstByte extends NavigationMetric {
41
45
  * @return {Promise<LH.Artifacts.Metric>}
42
46
  */
43
47
  static async computeObservedMetric(data, context) {
44
- const mainResource = await MainResource.request(data, context);
45
- if (!mainResource.timing) {
46
- throw new Error('missing timing for main resource');
48
+ const {trace, settings, SourceMaps} = data;
49
+ const traceEngineResult =
50
+ await TraceEngineResult.request({trace, settings, SourceMaps}, context);
51
+ const navInsights = await NavigationInsights.request({trace, settings, SourceMaps}, context);
52
+ const lcpBreakdown = navInsights.model.LCPBreakdown;
53
+
54
+ // Defer to LCP breakdown, but if there's no LCP fallback to manual calculation.
55
+ if (!(lcpBreakdown instanceof Error) && lcpBreakdown.subparts) {
56
+ return {
57
+ timing: lcpBreakdown.subparts.ttfb.range / 1000,
58
+ timestamp: lcpBreakdown.subparts.ttfb.max,
59
+ };
60
+ } else if (navInsights.navigation?.args.data?.navigationId) {
61
+ const request = traceEngineResult.data.NetworkRequests.byId.get(
62
+ navInsights.navigation.args.data.navigationId);
63
+ if (!request) {
64
+ throw new Error();
65
+ }
66
+
67
+ const timestamp = calculateDocFirstByteTs(request);
68
+ if (timestamp === null) {
69
+ throw new Error('cannot calculate ttfb');
70
+ }
71
+
72
+ return {
73
+ timing: (timestamp - navInsights.navigation.ts) / 1000,
74
+ timestamp,
75
+ };
47
76
  }
48
77
 
49
- const {processedNavigation} = data;
50
- const timeOriginTs = processedNavigation.timestamps.timeOrigin;
51
- const timestampMs =
52
- mainResource.timing.requestTime * 1000 + mainResource.timing.receiveHeadersStart;
53
- const timestamp = timestampMs * 1000;
54
- const timing = (timestamp - timeOriginTs) / 1000;
55
- return {timing, timestamp};
78
+ throw new Error('cannot determine ttfb');
56
79
  }
57
80
  }
58
81
 
@@ -96,8 +96,9 @@ class TimingSummary {
96
96
  cumulativeLayoutShift,
97
97
  cumulativeLayoutShiftMainFrame,
98
98
 
99
- lcpLoadStart: lcpBreakdown?.loadStart,
100
- lcpLoadEnd: lcpBreakdown?.loadEnd,
99
+ lcpLoadDelay: lcpBreakdown?.loadDelay,
100
+ lcpLoadDuration: lcpBreakdown?.loadDuration,
101
+ lcpRenderDelay: lcpBreakdown?.renderDelay,
101
102
 
102
103
  timeToFirstByte: ttfb?.timing,
103
104
  timeToFirstByteTs: ttfb?.timestamp,
@@ -27,7 +27,7 @@ class PageDependencyGraph {
27
27
  if (data.fromTrace) {
28
28
  const traceEngineResult =
29
29
  await TraceEngineResult.request({trace, settings, SourceMaps}, context);
30
- const parsedTrace = traceEngineResult.parsedTrace;
30
+ const parsedTrace = traceEngineResult.data;
31
31
  const requests =
32
32
  Lantern.TraceEngineComputationData.createNetworkRequests(trace, parsedTrace);
33
33
  const graph =
@@ -62,10 +62,10 @@ class TraceEngineResult {
62
62
  return new SDK.SourceMap(compiledUrl, mapUrl, sourceMap.map);
63
63
  },
64
64
  });
65
- if (!processor.parsedTrace) throw new Error('No data');
65
+ if (!processor.data) throw new Error('No data');
66
66
  if (!processor.insights) throw new Error('No insights');
67
67
  this.localizeInsights(processor.insights);
68
- return {parsedTrace: processor.parsedTrace, insights: processor.insights};
68
+ return {data: processor.data, insights: processor.insights};
69
69
  }
70
70
 
71
71
  /**
@@ -114,12 +114,9 @@ const defaultConfig = {
114
114
 
115
115
  {id: 'Accessibility', gatherer: 'accessibility'},
116
116
  {id: 'AnchorElements', gatherer: 'anchor-elements'},
117
- {id: 'CacheContents', gatherer: 'cache-contents'},
118
117
  {id: 'ConsoleMessages', gatherer: 'console-messages'},
119
118
  {id: 'CSSUsage', gatherer: 'css-usage'},
120
119
  {id: 'Doctype', gatherer: 'dobetterweb/doctype'},
121
- {id: 'DOMStats', gatherer: 'dobetterweb/domstats'},
122
- {id: 'FontSize', gatherer: 'seo/font-size'},
123
120
  {id: 'Inputs', gatherer: 'inputs'},
124
121
  {id: 'IFrameElements', gatherer: 'iframe-elements'},
125
122
  {id: 'ImageElements', gatherer: 'image-elements'},
@@ -129,8 +126,6 @@ const defaultConfig = {
129
126
  {id: 'MainDocumentContent', gatherer: 'main-document-content'},
130
127
  {id: 'MetaElements', gatherer: 'meta-elements'},
131
128
  {id: 'NetworkUserAgent', gatherer: 'network-user-agent'},
132
- {id: 'OptimizedImages', gatherer: 'dobetterweb/optimized-images'},
133
- {id: 'ResponseCompression', gatherer: 'dobetterweb/response-compression'},
134
129
  {id: 'RobotsTxt', gatherer: 'seo/robots-txt'},
135
130
  {id: 'Scripts', gatherer: 'scripts'},
136
131
  {id: 'SourceMaps', gatherer: 'source-maps'},
@@ -139,10 +134,6 @@ const defaultConfig = {
139
134
  {id: 'TraceElements', gatherer: 'trace-elements'},
140
135
  {id: 'ViewportDimensions', gatherer: 'viewport-dimensions'},
141
136
 
142
- // Artifact copies are renamed for compatibility with legacy artifacts.
143
- {id: 'devtoolsLogs', gatherer: 'devtools-log-compat'},
144
- {id: 'traces', gatherer: 'trace-compat'},
145
-
146
137
  // FullPageScreenshot comes at the end so all other node analysis is captured.
147
138
  {id: 'FullPageScreenshot', gatherer: 'full-page-screenshot'},
148
139
 
@@ -152,10 +143,8 @@ const defaultConfig = {
152
143
  audits: [
153
144
  'is-on-https',
154
145
  'redirects-http',
155
- 'viewport',
156
146
  'metrics/first-contentful-paint',
157
147
  'metrics/largest-contentful-paint',
158
- 'metrics/first-meaningful-paint',
159
148
  'metrics/speed-index',
160
149
  'screenshot-thumbnails',
161
150
  'final-screenshot',
@@ -167,7 +156,6 @@ const defaultConfig = {
167
156
  'server-response-time',
168
157
  'metrics/interactive',
169
158
  'user-timings',
170
- 'critical-request-chains',
171
159
  'redirects',
172
160
  'image-aspect-ratio',
173
161
  'image-size-responsive',
@@ -175,8 +163,6 @@ const defaultConfig = {
175
163
  'third-party-cookies',
176
164
  'mainthread-work-breakdown',
177
165
  'bootup-time',
178
- 'uses-rel-preconnect',
179
- 'font-display',
180
166
  'diagnostics',
181
167
  'network-requests',
182
168
  'network-rtt',
@@ -184,16 +170,11 @@ const defaultConfig = {
184
170
  'main-thread-tasks',
185
171
  'metrics',
186
172
  'resource-summary',
187
- 'third-party-summary',
188
- 'third-party-facades',
189
- 'largest-contentful-paint-element',
190
- 'lcp-lazy-loaded',
191
173
  'layout-shifts',
192
174
  'long-tasks',
193
175
  'non-composited-animations',
194
176
  'unsized-images',
195
177
  'valid-source-maps',
196
- 'prioritize-lcp-image',
197
178
  'csp-xss',
198
179
  'has-hsts',
199
180
  'origin-isolation',
@@ -273,36 +254,20 @@ const defaultConfig = {
273
254
  'accessibility/manual/offscreen-content-hidden',
274
255
  'accessibility/manual/use-landmarks',
275
256
  'accessibility/manual/visual-order-follows-dom',
276
- 'byte-efficiency/uses-long-cache-ttl',
277
257
  'byte-efficiency/total-byte-weight',
278
- 'byte-efficiency/offscreen-images',
279
- 'byte-efficiency/render-blocking-resources',
280
258
  'byte-efficiency/unminified-css',
281
259
  'byte-efficiency/unminified-javascript',
282
260
  'byte-efficiency/unused-css-rules',
283
261
  'byte-efficiency/unused-javascript',
284
- 'byte-efficiency/modern-image-formats',
285
- 'byte-efficiency/uses-optimized-images',
286
- 'byte-efficiency/uses-text-compression',
287
- 'byte-efficiency/uses-responsive-images',
288
- 'byte-efficiency/efficient-animated-content',
289
- 'byte-efficiency/duplicated-javascript',
290
- 'byte-efficiency/legacy-javascript',
291
- 'byte-efficiency/uses-responsive-images-snapshot',
292
262
  'dobetterweb/doctype',
293
263
  'dobetterweb/charset',
294
- 'dobetterweb/dom-size',
295
264
  'dobetterweb/geolocation-on-start',
296
265
  'dobetterweb/inspector-issues',
297
- 'dobetterweb/no-document-write',
298
266
  'dobetterweb/js-libraries',
299
267
  'dobetterweb/notification-on-start',
300
268
  'dobetterweb/paste-preventing-inputs',
301
- 'dobetterweb/uses-http2',
302
- 'dobetterweb/uses-passive-event-listeners',
303
269
  'seo/meta-description',
304
270
  'seo/http-status-code',
305
- 'seo/font-size',
306
271
  'seo/link-text',
307
272
  'seo/crawlable-anchors',
308
273
  'seo/is-crawlable',
@@ -310,7 +275,6 @@ const defaultConfig = {
310
275
  'seo/hreflang',
311
276
  'seo/canonical',
312
277
  'seo/manual/structured-data',
313
- 'work-during-interaction',
314
278
  'bf-cache',
315
279
  'insights/cache-insight',
316
280
  'insights/cls-culprits-insight',
@@ -414,68 +378,39 @@ const defaultConfig = {
414
378
  {id: 'interaction-to-next-paint', weight: 0, group: 'metrics', acronym: 'INP'},
415
379
 
416
380
  // Insight audits.
417
- {id: 'cache-insight', weight: 0, group: 'hidden'},
418
- {id: 'cls-culprits-insight', weight: 0, group: 'hidden'},
419
- {id: 'document-latency-insight', weight: 0, group: 'hidden'},
420
- {id: 'dom-size-insight', weight: 0, group: 'hidden'},
421
- {id: 'duplicated-javascript-insight', weight: 0, group: 'hidden'},
422
- {id: 'font-display-insight', weight: 0, group: 'hidden'},
423
- {id: 'forced-reflow-insight', weight: 0, group: 'hidden'},
424
- {id: 'image-delivery-insight', weight: 0, group: 'hidden'},
425
- {id: 'inp-breakdown-insight', weight: 0, group: 'hidden'},
426
- {id: 'lcp-breakdown-insight', weight: 0, group: 'hidden'},
427
- {id: 'lcp-discovery-insight', weight: 0, group: 'hidden'},
428
- {id: 'legacy-javascript-insight', weight: 0, group: 'hidden'},
429
- {id: 'modern-http-insight', weight: 0, group: 'hidden'},
430
- {id: 'network-dependency-tree-insight', weight: 0, group: 'hidden'},
431
- {id: 'render-blocking-insight', weight: 0, group: 'hidden'},
432
- {id: 'third-parties-insight', weight: 0, group: 'hidden'},
433
- {id: 'viewport-insight', weight: 0, group: 'hidden'},
381
+ {id: 'cache-insight', weight: 0, group: 'insights'},
382
+ {id: 'cls-culprits-insight', weight: 0, group: 'insights'},
383
+ {id: 'document-latency-insight', weight: 0, group: 'insights'},
384
+ {id: 'dom-size-insight', weight: 0, group: 'insights'},
385
+ {id: 'duplicated-javascript-insight', weight: 0, group: 'insights'},
386
+ {id: 'font-display-insight', weight: 0, group: 'insights'},
387
+ {id: 'forced-reflow-insight', weight: 0, group: 'insights'},
388
+ {id: 'image-delivery-insight', weight: 0, group: 'insights'},
389
+ {id: 'inp-breakdown-insight', weight: 0, group: 'insights'},
390
+ {id: 'lcp-breakdown-insight', weight: 0, group: 'insights'},
391
+ {id: 'lcp-discovery-insight', weight: 0, group: 'insights'},
392
+ {id: 'legacy-javascript-insight', weight: 0, group: 'insights'},
393
+ {id: 'modern-http-insight', weight: 0, group: 'insights'},
394
+ {id: 'network-dependency-tree-insight', weight: 0, group: 'insights'},
395
+ {id: 'render-blocking-insight', weight: 0, group: 'insights'},
396
+ {id: 'third-parties-insight', weight: 0, group: 'insights'},
397
+ {id: 'viewport-insight', weight: 0, group: 'insights'},
434
398
 
435
399
  // These are our "invisible" metrics. Not displayed, but still in the LHR.
436
400
  {id: 'interactive', weight: 0, group: 'hidden', acronym: 'TTI'},
437
401
  {id: 'max-potential-fid', weight: 0, group: 'hidden'},
438
- {id: 'first-meaningful-paint', weight: 0, acronym: 'FMP', group: 'hidden'},
439
402
 
440
- {id: 'render-blocking-resources', weight: 0, group: 'diagnostics'},
441
- {id: 'uses-responsive-images', weight: 0, group: 'diagnostics'},
442
- {id: 'offscreen-images', weight: 0, group: 'diagnostics'},
443
403
  {id: 'unminified-css', weight: 0, group: 'diagnostics'},
444
404
  {id: 'unminified-javascript', weight: 0, group: 'diagnostics'},
445
405
  {id: 'unused-css-rules', weight: 0, group: 'diagnostics'},
446
406
  {id: 'unused-javascript', weight: 0, group: 'diagnostics'},
447
- {id: 'uses-optimized-images', weight: 0, group: 'diagnostics'},
448
- {id: 'modern-image-formats', weight: 0, group: 'diagnostics'},
449
- {id: 'uses-text-compression', weight: 0, group: 'diagnostics'},
450
- {id: 'uses-rel-preconnect', weight: 0, group: 'diagnostics'},
451
- {id: 'server-response-time', weight: 0, group: 'diagnostics'},
452
- {id: 'redirects', weight: 0, group: 'diagnostics'},
453
- {id: 'uses-http2', weight: 0, group: 'diagnostics'},
454
- {id: 'efficient-animated-content', weight: 0, group: 'diagnostics'},
455
- {id: 'duplicated-javascript', weight: 0, group: 'diagnostics'},
456
- {id: 'legacy-javascript', weight: 0, group: 'diagnostics'},
457
- {id: 'prioritize-lcp-image', weight: 0, group: 'diagnostics'},
458
407
  {id: 'total-byte-weight', weight: 0, group: 'diagnostics'},
459
- {id: 'uses-long-cache-ttl', weight: 0, group: 'diagnostics'},
460
- {id: 'dom-size', weight: 0, group: 'diagnostics'},
461
- {id: 'critical-request-chains', weight: 0, group: 'diagnostics'},
462
408
  {id: 'user-timings', weight: 0, group: 'diagnostics'},
463
409
  {id: 'bootup-time', weight: 0, group: 'diagnostics'},
464
410
  {id: 'mainthread-work-breakdown', weight: 0, group: 'diagnostics'},
465
- {id: 'font-display', weight: 0, group: 'diagnostics'},
466
- {id: 'third-party-summary', weight: 0, group: 'diagnostics'},
467
- {id: 'third-party-facades', weight: 0, group: 'diagnostics'},
468
- {id: 'largest-contentful-paint-element', weight: 0, group: 'diagnostics'},
469
- {id: 'lcp-lazy-loaded', weight: 0, group: 'diagnostics'},
470
- {id: 'layout-shifts', weight: 0, group: 'diagnostics'},
471
- {id: 'uses-passive-event-listeners', weight: 0, group: 'diagnostics'},
472
- {id: 'no-document-write', weight: 0, group: 'diagnostics'},
473
411
  {id: 'long-tasks', weight: 0, group: 'diagnostics'},
474
412
  {id: 'non-composited-animations', weight: 0, group: 'diagnostics'},
475
413
  {id: 'unsized-images', weight: 0, group: 'diagnostics'},
476
- {id: 'viewport', weight: 0, group: 'diagnostics'},
477
- {id: 'uses-responsive-images-snapshot', weight: 0, group: 'diagnostics'},
478
- {id: 'work-during-interaction', weight: 0, group: 'diagnostics'},
479
414
  {id: 'bf-cache', weight: 0, group: 'diagnostics'},
480
415
 
481
416
  // Audits past this point contain useful data but are not displayed with other audits.
@@ -489,6 +424,9 @@ const defaultConfig = {
489
424
  {id: 'final-screenshot', weight: 0, group: 'hidden'},
490
425
  {id: 'script-treemap-data', weight: 0, group: 'hidden'},
491
426
  {id: 'resource-summary', weight: 0, group: 'hidden'},
427
+ {id: 'redirects', weight: 0, group: 'hidden'},
428
+ {id: 'server-response-time', weight: 0, group: 'hidden'},
429
+ {id: 'layout-shifts', weight: 0, group: 'hidden'},
492
430
  ],
493
431
  },
494
432
  'accessibility': {
@@ -496,68 +434,86 @@ const defaultConfig = {
496
434
  description: str_(UIStrings.a11yCategoryDescription),
497
435
  manualDescription: str_(UIStrings.a11yCategoryManualDescription),
498
436
  supportedModes: ['navigation', 'snapshot'],
499
- // Audit weights are meant to match the aXe scoring system of
500
- // minor, moderate, serious, and critical.
501
- // See the audits listed at dequeuniversity.com/rules/axe/4.7.
502
- // Click on an audit and check the right hand column to see its severity.
437
+ // Audit weights weights are derived from the axe-core "Impact",
438
+ // with adjustments based on axe-core "Tags":
439
+ //
440
+ // ┌────────────┬───────────────────────────────────────────────┐
441
+ // │ Impact │ Weight Based on Tags │
442
+ // │ ├──────────────┬─────────────────┬──────────────┤
443
+ // │ │ wcag A+AA │ best-practice │ experimental │
444
+ // │ │ (ex: wcag2aa)│ (w/o wcag tag) │ │
445
+ // ├────────────┼──────────────┼─────────────────┼──────────────┤
446
+ // │ Minor │ 1 │ 0 │ 0 │
447
+ // │ Moderate │ 3 │ 3 │ 0 │
448
+ // │ Serious │ 7 │ 7 │ 0 │
449
+ // │ Critical │ 10 │ 10 │ 0 │
450
+ // └────────────┴──────────────┴─────────────────┴──────────────┘
451
+ //
452
+ // Notes:
453
+ // • Experimental rules always have weight 0
454
+ // • Best practice rules only affect scores when tagged with wcagA+AA
455
+ // and are moderate, serious, or critical.
456
+ //
457
+ // To find the latest axe-core Impact and Tag values:
458
+ // 1. Browse to https://dequeuniversity.com/rules/axe/html.
459
+ // 2. Click on the latest rule set (ex: https://dequeuniversity.com/rules/axe/html/4.10)
460
+ // 3. Review the tables
503
461
  auditRefs: [
504
- {id: 'accesskeys', weight: 7, group: 'a11y-navigation'},
505
- {id: 'aria-allowed-attr', weight: 10, group: 'a11y-aria'},
506
- {id: 'aria-allowed-role', weight: 1, group: 'a11y-aria'},
507
- {id: 'aria-command-name', weight: 7, group: 'a11y-aria'},
508
- {id: 'aria-conditional-attr', weight: 7, group: 'a11y-aria'},
509
- {id: 'aria-deprecated-role', weight: 1, group: 'a11y-aria'},
510
- {id: 'aria-dialog-name', weight: 7, group: 'a11y-aria'},
511
- {id: 'aria-hidden-body', weight: 10, group: 'a11y-aria'},
512
- {id: 'aria-hidden-focus', weight: 7, group: 'a11y-aria'},
513
- {id: 'aria-input-field-name', weight: 7, group: 'a11y-aria'},
514
- {id: 'aria-meter-name', weight: 7, group: 'a11y-aria'},
515
- {id: 'aria-progressbar-name', weight: 7, group: 'a11y-aria'},
516
- {id: 'aria-prohibited-attr', weight: 7, group: 'a11y-aria'},
517
- {id: 'aria-required-attr', weight: 10, group: 'a11y-aria'},
518
- {id: 'aria-required-children', weight: 10, group: 'a11y-aria'},
519
- {id: 'aria-required-parent', weight: 10, group: 'a11y-aria'},
520
- {id: 'aria-roles', weight: 7, group: 'a11y-aria'},
521
- {id: 'aria-text', weight: 7, group: 'a11y-aria'},
522
- {id: 'aria-toggle-field-name', weight: 7, group: 'a11y-aria'},
523
- {id: 'aria-tooltip-name', weight: 7, group: 'a11y-aria'},
524
- {id: 'aria-treeitem-name', weight: 7, group: 'a11y-aria'},
525
- {id: 'aria-valid-attr-value', weight: 10, group: 'a11y-aria'},
526
- {id: 'aria-valid-attr', weight: 10, group: 'a11y-aria'},
527
- {id: 'button-name', weight: 10, group: 'a11y-names-labels'},
528
- {id: 'bypass', weight: 7, group: 'a11y-navigation'},
529
- {id: 'color-contrast', weight: 7, group: 'a11y-color-contrast'},
530
- {id: 'definition-list', weight: 7, group: 'a11y-tables-lists'},
531
- {id: 'dlitem', weight: 7, group: 'a11y-tables-lists'},
532
- {id: 'document-title', weight: 7, group: 'a11y-names-labels'},
533
- {id: 'duplicate-id-aria', weight: 10, group: 'a11y-aria'},
534
- {id: 'form-field-multiple-labels', weight: 3, group: 'a11y-names-labels'},
535
- {id: 'frame-title', weight: 7, group: 'a11y-names-labels'},
536
- {id: 'heading-order', weight: 3, group: 'a11y-navigation'},
537
- {id: 'html-has-lang', weight: 7, group: 'a11y-language'},
538
- {id: 'html-lang-valid', weight: 7, group: 'a11y-language'},
539
- {id: 'html-xml-lang-mismatch', weight: 3, group: 'a11y-language'},
540
- {id: 'image-alt', weight: 10, group: 'a11y-names-labels'},
541
- {id: 'image-redundant-alt', weight: 1, group: 'a11y-names-labels'},
542
- {id: 'input-button-name', weight: 10, group: 'a11y-names-labels'},
543
- {id: 'input-image-alt', weight: 10, group: 'a11y-names-labels'},
544
- {id: 'label', weight: 7, group: 'a11y-names-labels'},
545
- {id: 'link-in-text-block', weight: 7, group: 'a11y-color-contrast'},
546
- {id: 'link-name', weight: 7, group: 'a11y-names-labels'},
547
- {id: 'list', weight: 7, group: 'a11y-tables-lists'},
548
- {id: 'listitem', weight: 7, group: 'a11y-tables-lists'},
549
- {id: 'meta-refresh', weight: 10, group: 'a11y-best-practices'},
550
- {id: 'meta-viewport', weight: 10, group: 'a11y-best-practices'},
551
- {id: 'object-alt', weight: 7, group: 'a11y-names-labels'},
552
- {id: 'select-name', weight: 7, group: 'a11y-names-labels'},
553
- {id: 'skip-link', weight: 3, group: 'a11y-names-labels'},
554
- {id: 'tabindex', weight: 7, group: 'a11y-navigation'},
555
- {id: 'table-duplicate-name', weight: 1, group: 'a11y-tables-lists'},
556
- {id: 'target-size', weight: 7, group: 'a11y-best-practices'},
557
- {id: 'td-headers-attr', weight: 7, group: 'a11y-tables-lists'},
558
- {id: 'th-has-data-cells', weight: 7, group: 'a11y-tables-lists'},
559
- {id: 'valid-lang', weight: 7, group: 'a11y-language'},
560
- {id: 'video-caption', weight: 10, group: 'a11y-audio-video'},
462
+ {id: 'accesskeys', weight: 7, group: 'a11y-navigation'}, // Serious, best-practice
463
+ {id: 'aria-allowed-attr', weight: 10, group: 'a11y-aria'}, // Critical, wcag2a
464
+ {id: 'aria-command-name', weight: 7, group: 'a11y-aria'}, // Serious, wcag2a
465
+ {id: 'aria-conditional-attr', weight: 7, group: 'a11y-aria'}, // Serious, wcag2a
466
+ {id: 'aria-deprecated-role', weight: 1, group: 'a11y-aria'}, // Minor, wcag2a
467
+ {id: 'aria-dialog-name', weight: 7, group: 'a11y-aria'}, // Serious, best-practice
468
+ {id: 'aria-hidden-body', weight: 10, group: 'a11y-aria'}, // Critical, wcag2a
469
+ {id: 'aria-hidden-focus', weight: 7, group: 'a11y-aria'}, // Serious, wcag2a
470
+ {id: 'aria-input-field-name', weight: 7, group: 'a11y-aria'}, // Serious, wcag2a
471
+ {id: 'aria-meter-name', weight: 7, group: 'a11y-aria'}, // Serious, wcag2a
472
+ {id: 'aria-progressbar-name', weight: 7, group: 'a11y-aria'}, // Serious, wcag2a
473
+ {id: 'aria-prohibited-attr', weight: 7, group: 'a11y-aria'}, // Serious, wcag2a
474
+ {id: 'aria-required-attr', weight: 10, group: 'a11y-aria'}, // Critical, wcag2a
475
+ {id: 'aria-required-children', weight: 10, group: 'a11y-aria'}, // Critical, wcag2a
476
+ {id: 'aria-required-parent', weight: 10, group: 'a11y-aria'}, // Critical, wcag2a
477
+ {id: 'aria-roles', weight: 10, group: 'a11y-aria'}, // Critical, wcag2a
478
+ {id: 'aria-text', weight: 7, group: 'a11y-aria'}, // Serious, best-practice
479
+ {id: 'aria-toggle-field-name', weight: 7, group: 'a11y-aria'}, // Serious, wcag2a
480
+ {id: 'aria-tooltip-name', weight: 7, group: 'a11y-aria'}, // Serious, wcag2a
481
+ {id: 'aria-treeitem-name', weight: 7, group: 'a11y-aria'}, // Serious, best-practice
482
+ {id: 'aria-valid-attr-value', weight: 10, group: 'a11y-aria'}, // Critical, wcag2a
483
+ {id: 'aria-valid-attr', weight: 10, group: 'a11y-aria'}, // Critical, wcag2a
484
+ {id: 'button-name', weight: 10, group: 'a11y-names-labels'}, // Critical, wcag2a
485
+ {id: 'bypass', weight: 7, group: 'a11y-navigation'}, // Serious, wcag2a
486
+ {id: 'color-contrast', weight: 7, group: 'a11y-color-contrast'}, // Serious, wcag2aa
487
+ {id: 'definition-list', weight: 7, group: 'a11y-tables-lists'}, // Serious, wcag2a
488
+ {id: 'dlitem', weight: 7, group: 'a11y-tables-lists'}, // Serious, wcag2a
489
+ {id: 'document-title', weight: 7, group: 'a11y-names-labels'}, // Serious, wcag2a
490
+ {id: 'duplicate-id-aria', weight: 10, group: 'a11y-aria'}, // Critical, wcag2a
491
+ {id: 'form-field-multiple-labels', weight: 3, group: 'a11y-names-labels'}, // Moderate, wcag2a
492
+ {id: 'frame-title', weight: 7, group: 'a11y-names-labels'}, // Serious, wcag2a
493
+ {id: 'heading-order', weight: 3, group: 'a11y-navigation'}, // Moderate, best-practice
494
+ {id: 'html-has-lang', weight: 7, group: 'a11y-language'}, // Serious, wcag2a
495
+ {id: 'html-lang-valid', weight: 7, group: 'a11y-language'}, // Serious, wcag2a
496
+ {id: 'html-xml-lang-mismatch', weight: 3, group: 'a11y-language'}, // Moderate, wcag2a
497
+ {id: 'image-alt', weight: 10, group: 'a11y-names-labels'}, // Critical, wcag2a
498
+ {id: 'input-button-name', weight: 10, group: 'a11y-names-labels'}, // Critical, wcag2a
499
+ {id: 'input-image-alt', weight: 10, group: 'a11y-names-labels'}, // Critical, wcag2a
500
+ {id: 'label', weight: 10, group: 'a11y-names-labels'}, // Critical, wcag2a
501
+ {id: 'link-in-text-block', weight: 7, group: 'a11y-color-contrast'}, // Serious, wcag2a
502
+ {id: 'link-name', weight: 7, group: 'a11y-names-labels'}, // Serious, wcag2a
503
+ {id: 'list', weight: 7, group: 'a11y-tables-lists'}, // Serious, wcag2a
504
+ {id: 'listitem', weight: 7, group: 'a11y-tables-lists'}, // Serious, wcag2a
505
+ {id: 'meta-refresh', weight: 10, group: 'a11y-best-practices'}, // Critical, wcag2a
506
+ {id: 'meta-viewport', weight: 10, group: 'a11y-best-practices'}, // Critical, wcag2aa
507
+ {id: 'object-alt', weight: 7, group: 'a11y-names-labels'}, // Serious, wcag2a
508
+ {id: 'select-name', weight: 10, group: 'a11y-names-labels'}, // Critical, wcag2a
509
+ {id: 'skip-link', weight: 3, group: 'a11y-names-labels'}, // Moderate, best-practice
510
+ {id: 'tabindex', weight: 7, group: 'a11y-navigation'}, // Serious, best-practice
511
+ {id: 'target-size', weight: 7, group: 'a11y-best-practices'}, // Serious, wcag22aa
512
+ {id: 'td-headers-attr', weight: 7, group: 'a11y-tables-lists'}, // Serious, wcag2a
513
+ {id: 'th-has-data-cells', weight: 7, group: 'a11y-tables-lists'}, // Serious, wcag2a
514
+ {id: 'valid-lang', weight: 7, group: 'a11y-language'}, // Serious, wcag2aa
515
+ {id: 'video-caption', weight: 10, group: 'a11y-audio-video'}, // Critical, wcag2a
516
+ {id: 'landmark-one-main', weight: 3, group: 'a11y-best-practices'}, // Moderate, best-practice
561
517
  // Manual audits
562
518
  {id: 'focusable-controls', weight: 0},
563
519
  {id: 'interactive-element-affordance', weight: 0},
@@ -569,13 +525,17 @@ const defaultConfig = {
569
525
  {id: 'offscreen-content-hidden', weight: 0},
570
526
  {id: 'custom-controls-labels', weight: 0},
571
527
  {id: 'custom-controls-roles', weight: 0},
572
- // Hidden audits
573
- {id: 'empty-heading', weight: 0, group: 'hidden'},
574
- {id: 'identical-links-same-purpose', weight: 0, group: 'hidden'},
575
- {id: 'landmark-one-main', weight: 0, group: 'hidden'},
576
- {id: 'label-content-name-mismatch', weight: 0, group: 'hidden'},
577
- {id: 'table-fake-caption', weight: 0, group: 'hidden'},
578
- {id: 'td-has-header', weight: 0, group: 'hidden'},
528
+ // Low-impact best-practices
529
+ {id: 'table-duplicate-name', weight: 0, group: 'a11y-best-practices'}, // Minor, best-practice
530
+ {id: 'empty-heading', weight: 0, group: 'a11y-best-practices'}, // Minor, best-practice
531
+ {id: 'aria-allowed-role', weight: 0, group: 'a11y-best-practices'}, // Minor, best-practice
532
+ {id: 'image-redundant-alt', weight: 0, group: 'a11y-names-labels'}, // Minor, best-practice
533
+ // WCAG AAA
534
+ {id: 'identical-links-same-purpose', weight: 0, group: 'a11y-best-practices'}, // Minor, wcag2aaa
535
+ // Hidden audits (ie. experimental)
536
+ {id: 'label-content-name-mismatch', weight: 0, group: 'hidden'}, // Serious, experimental
537
+ {id: 'table-fake-caption', weight: 0, group: 'hidden'}, // Serious, experimental
538
+ {id: 'td-has-header', weight: 0, group: 'hidden'}, // Critical, experimental
579
539
  ],
580
540
  },
581
541
  'best-practices': {
@@ -596,8 +556,6 @@ const defaultConfig = {
596
556
  {id: 'paste-preventing-inputs', weight: 3, group: 'best-practices-ux'},
597
557
  {id: 'image-aspect-ratio', weight: 1, group: 'best-practices-ux'},
598
558
  {id: 'image-size-responsive', weight: 1, group: 'best-practices-ux'},
599
- {id: 'viewport', weight: 1, group: 'best-practices-ux'},
600
- {id: 'font-size', weight: 1, group: 'best-practices-ux'},
601
559
  // Browser Compatibility
602
560
  {id: 'doctype', weight: 1, group: 'best-practices-browser-compat'},
603
561
  {id: 'charset', weight: 1, group: 'best-practices-browser-compat'},