lighthouse 9.5.0-dev.20221018 → 9.5.0-dev.20221020

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 (83) hide show
  1. package/core/api.js +14 -10
  2. package/core/audits/accessibility/axe-audit.js +1 -1
  3. package/core/audits/accessibility/bypass.js +1 -0
  4. package/core/audits/accessibility/th-has-data-cells.js +1 -0
  5. package/core/audits/accessibility/video-caption.js +1 -0
  6. package/core/audits/autocomplete.js +3 -3
  7. package/core/audits/bootup-time.js +5 -5
  8. package/core/audits/byte-efficiency/duplicated-javascript.js +1 -1
  9. package/core/audits/byte-efficiency/legacy-javascript.js +1 -1
  10. package/core/audits/byte-efficiency/total-byte-weight.js +2 -2
  11. package/core/audits/byte-efficiency/uses-long-cache-ttl.js +3 -3
  12. package/core/audits/byte-efficiency/uses-responsive-images-snapshot.js +4 -4
  13. package/core/audits/csp-xss.js +3 -3
  14. package/core/audits/deprecations.js +2 -2
  15. package/core/audits/dobetterweb/dom-size.js +3 -3
  16. package/core/audits/dobetterweb/geolocation-on-start.js +1 -1
  17. package/core/audits/dobetterweb/inspector-issues.js +1 -1
  18. package/core/audits/dobetterweb/js-libraries.js +2 -2
  19. package/core/audits/dobetterweb/no-document-write.js +1 -1
  20. package/core/audits/dobetterweb/notification-on-start.js +1 -1
  21. package/core/audits/dobetterweb/password-inputs-can-be-pasted-into.js +1 -1
  22. package/core/audits/dobetterweb/uses-http2.js +2 -2
  23. package/core/audits/dobetterweb/uses-passive-event-listeners.js +1 -1
  24. package/core/audits/errors-in-console.js +4 -2
  25. package/core/audits/font-display.js +2 -2
  26. package/core/audits/image-aspect-ratio.js +4 -4
  27. package/core/audits/image-size-responsive.js +5 -5
  28. package/core/audits/installable-manifest.js +1 -1
  29. package/core/audits/is-on-https.js +2 -2
  30. package/core/audits/largest-contentful-paint-element.js +1 -1
  31. package/core/audits/layout-shift-elements.js +3 -3
  32. package/core/audits/lcp-lazy-loaded.js +1 -1
  33. package/core/audits/long-tasks.js +3 -3
  34. package/core/audits/main-thread-tasks.js +2 -2
  35. package/core/audits/mainthread-work-breakdown.js +4 -2
  36. package/core/audits/network-requests.js +11 -11
  37. package/core/audits/network-rtt.js +2 -2
  38. package/core/audits/network-server-latency.js +3 -3
  39. package/core/audits/no-unload-listeners.js +1 -1
  40. package/core/audits/non-composited-animations.js +2 -2
  41. package/core/audits/performance-budget.js +5 -5
  42. package/core/audits/preload-fonts.js +1 -1
  43. package/core/audits/resource-summary.js +3 -3
  44. package/core/audits/seo/crawlable-anchors.js +2 -2
  45. package/core/audits/seo/font-size.js +4 -4
  46. package/core/audits/seo/hreflang.js +3 -3
  47. package/core/audits/seo/is-crawlable.js +1 -1
  48. package/core/audits/seo/link-text.js +2 -2
  49. package/core/audits/seo/plugins.js +1 -1
  50. package/core/audits/seo/robots-txt.js +3 -3
  51. package/core/audits/seo/tap-targets.js +3 -3
  52. package/core/audits/themed-omnibox.js +6 -14
  53. package/core/audits/third-party-facades.js +3 -3
  54. package/core/audits/third-party-summary.js +3 -3
  55. package/core/audits/timing-budget.js +3 -3
  56. package/core/audits/unsized-images.js +2 -2
  57. package/core/audits/user-timings.js +6 -6
  58. package/core/audits/valid-source-maps.js +3 -3
  59. package/core/audits/work-during-interaction.js +6 -6
  60. package/core/gather/navigation-runner.js +3 -3
  61. package/core/gather/snapshot-runner.js +4 -3
  62. package/core/gather/timespan-runner.js +4 -3
  63. package/core/index.js +1 -1
  64. package/core/legacy/config/config.js +0 -26
  65. package/core/lib/bfcache-strings.js +655 -0
  66. package/core/lib/deprecations-strings.js +3 -2
  67. package/core/lib/manifest-parser.js +0 -16
  68. package/core/user-flow.js +135 -77
  69. package/core/util.cjs +27 -0
  70. package/dist/report/bundle.esm.js +38 -73
  71. package/dist/report/flow.js +2 -2
  72. package/dist/report/standalone.js +2 -2
  73. package/package.json +2 -3
  74. package/report/renderer/details-renderer.js +12 -73
  75. package/report/renderer/util.js +27 -0
  76. package/report/test/generator/report-generator-test.js +1 -1
  77. package/report/test/renderer/category-renderer-test.js +1 -1
  78. package/report/test/renderer/details-renderer-test.js +38 -38
  79. package/report/test/renderer/util-test.js +25 -0
  80. package/shared/localization/locales/en-US.json +352 -1
  81. package/shared/localization/locales/en-XL.json +352 -1
  82. package/types/lhr/audit-details.d.ts +4 -34
  83. package/types/user-flow.d.ts +10 -3
@@ -49,9 +49,9 @@ class ResourceSummary extends Audit {
49
49
 
50
50
  /** @type {LH.Audit.Details.Table['headings']} */
51
51
  const headings = [
52
- {key: 'label', itemType: 'text', text: str_(i18n.UIStrings.columnResourceType)},
53
- {key: 'requestCount', itemType: 'numeric', text: str_(i18n.UIStrings.columnRequests)},
54
- {key: 'transferSize', itemType: 'bytes', text: str_(i18n.UIStrings.columnTransferSize)},
52
+ {key: 'label', valueType: 'text', label: str_(i18n.UIStrings.columnResourceType)},
53
+ {key: 'requestCount', valueType: 'numeric', label: str_(i18n.UIStrings.columnRequests)},
54
+ {key: 'transferSize', valueType: 'bytes', label: str_(i18n.UIStrings.columnTransferSize)},
55
55
  ];
56
56
 
57
57
 
@@ -71,8 +71,8 @@ class CrawlableAnchors extends Audit {
71
71
  /** @type {LH.Audit.Details.Table['headings']} */
72
72
  const headings = [{
73
73
  key: 'node',
74
- itemType: 'node',
75
- text: str_(UIStrings.columnFailingLink),
74
+ valueType: 'node',
75
+ label: str_(UIStrings.columnFailingLink),
76
76
  }];
77
77
 
78
78
  /** @type {LH.Audit.Details.Table['items']} */
@@ -284,10 +284,10 @@ class FontSize extends Audit {
284
284
 
285
285
  /** @type {LH.Audit.Details.Table['headings']} */
286
286
  const headings = [
287
- {key: 'source', itemType: 'source-location', text: str_(i18n.UIStrings.columnSource)},
288
- {key: 'selector', itemType: 'code', text: str_(UIStrings.columnSelector)},
289
- {key: 'coverage', itemType: 'text', text: str_(UIStrings.columnPercentPageText)},
290
- {key: 'fontSize', itemType: 'text', text: str_(UIStrings.columnFontSize)},
287
+ {key: 'source', valueType: 'source-location', label: str_(i18n.UIStrings.columnSource)},
288
+ {key: 'selector', valueType: 'code', label: str_(UIStrings.columnSelector)},
289
+ {key: 'coverage', valueType: 'text', label: str_(UIStrings.columnPercentPageText)},
290
+ {key: 'fontSize', valueType: 'text', label: str_(UIStrings.columnFontSize)},
291
291
  ];
292
292
 
293
293
  const tableData = failingRules.sort((a, b) => b.textLength - a.textLength)
@@ -127,12 +127,12 @@ class Hreflang extends Audit {
127
127
  /** @type {LH.Audit.Details.Table['headings']} */
128
128
  const headings = [{
129
129
  key: 'source',
130
- itemType: 'code',
130
+ valueType: 'code',
131
131
  subItemsHeading: {
132
132
  key: 'reason',
133
- itemType: 'text',
133
+ valueType: 'text',
134
134
  },
135
- text: '',
135
+ label: '',
136
136
  }];
137
137
 
138
138
  const details = Audit.makeTableDetails(headings, invalidHreflangs);
@@ -138,7 +138,7 @@ class IsCrawlable extends Audit {
138
138
 
139
139
  /** @type {LH.Audit.Details.Table['headings']} */
140
140
  const headings = [
141
- {key: 'source', itemType: 'code', text: 'Blocking Directive Source'},
141
+ {key: 'source', valueType: 'code', label: 'Blocking Directive Source'},
142
142
  ];
143
143
  const details = Audit.makeTableDetails(headings, blockingDirectives);
144
144
 
@@ -137,8 +137,8 @@ class LinkText extends Audit {
137
137
 
138
138
  /** @type {LH.Audit.Details.Table['headings']} */
139
139
  const headings = [
140
- {key: 'href', itemType: 'url', text: 'Link destination'},
141
- {key: 'text', itemType: 'text', text: 'Link Text'},
140
+ {key: 'href', valueType: 'url', label: 'Link destination'},
141
+ {key: 'text', valueType: 'text', label: 'Link Text'},
142
142
  ];
143
143
 
144
144
  const details = Audit.makeTableDetails(headings, failingLinks, {});
@@ -134,7 +134,7 @@ class Plugins extends Audit {
134
134
 
135
135
  /** @type {LH.Audit.Details.Table['headings']} */
136
136
  const headings = [
137
- {key: 'source', itemType: 'code', text: 'Element source'},
137
+ {key: 'source', valueType: 'code', label: 'Element source'},
138
138
  ];
139
139
 
140
140
  const details = Audit.makeTableDetails(headings, plugins);
@@ -230,9 +230,9 @@ class RobotsTxt extends Audit {
230
230
 
231
231
  /** @type {LH.Audit.Details.Table['headings']} */
232
232
  const headings = [
233
- {key: 'index', itemType: 'text', text: 'Line #'},
234
- {key: 'line', itemType: 'code', text: 'Content'},
235
- {key: 'message', itemType: 'code', text: 'Error'},
233
+ {key: 'index', valueType: 'text', label: 'Line #'},
234
+ {key: 'line', valueType: 'code', label: 'Content'},
235
+ {key: 'message', valueType: 'code', label: 'Error'},
236
236
  ];
237
237
 
238
238
  const details = Audit.makeTableDetails(headings, validationErrors, {});
@@ -286,9 +286,9 @@ class TapTargets extends Audit {
286
286
 
287
287
  /** @type {LH.Audit.Details.Table['headings']} */
288
288
  const headings = [
289
- {key: 'tapTarget', itemType: 'node', text: str_(UIStrings.tapTargetHeader)},
290
- {key: 'size', itemType: 'text', text: str_(i18n.UIStrings.columnSize)},
291
- {key: 'overlappingTarget', itemType: 'node', text: str_(UIStrings.overlappingTargetHeader)},
289
+ {key: 'tapTarget', valueType: 'node', label: str_(UIStrings.tapTargetHeader)},
290
+ {key: 'size', valueType: 'text', label: str_(i18n.UIStrings.columnSize)},
291
+ {key: 'overlappingTarget', valueType: 'node', label: str_(UIStrings.overlappingTargetHeader)},
292
292
  ];
293
293
 
294
294
  const details = Audit.makeTableDetails(headings, tableItems);
@@ -4,8 +4,6 @@
4
4
  * Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the specific language governing permissions and limitations under the License.
5
5
  */
6
6
 
7
- import cssParsers from 'cssstyle/lib/parsers.js';
8
-
9
7
  import MultiCheckAudit from './multi-check-audit.js';
10
8
  import {ManifestValues} from '../computed/manifest-values.js';
11
9
  import * as i18n from '../lib/i18n/i18n.js';
@@ -28,8 +26,10 @@ const str_ = i18n.createIcuMessageFn(import.meta.url, UIStrings);
28
26
  *
29
27
  * Requirements:
30
28
  * * manifest is not empty
31
- * * manifest has a valid theme_color
32
- * * HTML has a valid theme-color meta
29
+ * * manifest has a theme_color
30
+ * * HTML has a theme-color meta
31
+ *
32
+ * Color validity is explicitly not checked.
33
33
  */
34
34
 
35
35
  class ThemedOmnibox extends MultiCheckAudit {
@@ -47,14 +47,6 @@ class ThemedOmnibox extends MultiCheckAudit {
47
47
  };
48
48
  }
49
49
 
50
- /**
51
- * @param {string} color
52
- * @return {boolean}
53
- */
54
- static isValidColor(color) {
55
- return cssParsers.valueType(color) === cssParsers.TYPES.COLOR;
56
- }
57
-
58
50
  /**
59
51
  * @param {LH.Artifacts.MetaElement|undefined} themeColorMeta
60
52
  * @param {Array<string>} failures
@@ -63,8 +55,8 @@ class ThemedOmnibox extends MultiCheckAudit {
63
55
  if (!themeColorMeta) {
64
56
  // TODO(#7238): i18n
65
57
  failures.push('No `<meta name="theme-color">` tag found');
66
- } else if (!ThemedOmnibox.isValidColor(themeColorMeta.content || '')) {
67
- failures.push('The theme-color meta tag did not contain a valid CSS color');
58
+ } else if (!themeColorMeta.content) {
59
+ failures.push('The theme-color meta tag did not contain a content value');
68
60
  }
69
61
  }
70
62
 
@@ -201,9 +201,9 @@ class ThirdPartyFacades extends Audit {
201
201
  /** @type {LH.Audit.Details.Table['headings']} */
202
202
  const headings = [
203
203
  /* eslint-disable max-len */
204
- {key: 'product', itemType: 'text', subItemsHeading: {key: 'url', itemType: 'url'}, text: str_(UIStrings.columnProduct)},
205
- {key: 'transferSize', itemType: 'bytes', subItemsHeading: {key: 'transferSize'}, granularity: 1, text: str_(i18n.UIStrings.columnTransferSize)},
206
- {key: 'blockingTime', itemType: 'ms', subItemsHeading: {key: 'blockingTime'}, granularity: 1, text: str_(i18n.UIStrings.columnBlockingTime)},
204
+ {key: 'product', valueType: 'text', subItemsHeading: {key: 'url', valueType: 'url'}, label: str_(UIStrings.columnProduct)},
205
+ {key: 'transferSize', valueType: 'bytes', subItemsHeading: {key: 'transferSize'}, granularity: 1, label: str_(i18n.UIStrings.columnTransferSize)},
206
+ {key: 'blockingTime', valueType: 'ms', subItemsHeading: {key: 'blockingTime'}, granularity: 1, label: str_(i18n.UIStrings.columnBlockingTime)},
207
207
  /* eslint-enable max-len */
208
208
  ];
209
209
 
@@ -232,9 +232,9 @@ class ThirdPartySummary extends Audit {
232
232
  /** @type {LH.Audit.Details.Table['headings']} */
233
233
  const headings = [
234
234
  /* eslint-disable max-len */
235
- {key: 'entity', itemType: 'link', text: str_(UIStrings.columnThirdParty), subItemsHeading: {key: 'url', itemType: 'url'}},
236
- {key: 'transferSize', granularity: 1, itemType: 'bytes', text: str_(i18n.UIStrings.columnTransferSize), subItemsHeading: {key: 'transferSize'}},
237
- {key: 'blockingTime', granularity: 1, itemType: 'ms', text: str_(i18n.UIStrings.columnBlockingTime), subItemsHeading: {key: 'blockingTime'}},
235
+ {key: 'entity', valueType: 'link', label: str_(UIStrings.columnThirdParty), subItemsHeading: {key: 'url', valueType: 'url'}},
236
+ {key: 'transferSize', granularity: 1, valueType: 'bytes', label: str_(i18n.UIStrings.columnTransferSize), subItemsHeading: {key: 'transferSize'}},
237
+ {key: 'blockingTime', granularity: 1, valueType: 'ms', label: str_(i18n.UIStrings.columnBlockingTime), subItemsHeading: {key: 'blockingTime'}},
238
238
  /* eslint-enable max-len */
239
239
  ];
240
240
 
@@ -154,13 +154,13 @@ class TimingBudget extends Audit {
154
154
 
155
155
  /** @type {LH.Audit.Details.Table['headings']} */
156
156
  const headers = [
157
- {key: 'label', itemType: 'text', text: str_(UIStrings.columnTimingMetric)},
157
+ {key: 'label', valueType: 'text', label: str_(UIStrings.columnTimingMetric)},
158
158
  /**
159
159
  * Note: SpeedIndex, unlike other timing metrics, is not measured in milliseconds.
160
160
  * The renderer applies the correct units to the 'measurement' and 'overBudget' columns for SpeedIndex.
161
161
  */
162
- {key: 'measurement', itemType: 'ms', text: str_(UIStrings.columnMeasurement)},
163
- {key: 'overBudget', itemType: 'ms', text: str_(i18n.UIStrings.columnOverBudget)},
162
+ {key: 'measurement', valueType: 'ms', label: str_(UIStrings.columnMeasurement)},
163
+ {key: 'overBudget', valueType: 'ms', label: str_(i18n.UIStrings.columnOverBudget)},
164
164
  ];
165
165
 
166
166
  return {
@@ -146,8 +146,8 @@ class UnsizedImages extends Audit {
146
146
 
147
147
  /** @type {LH.Audit.Details.Table['headings']} */
148
148
  const headings = [
149
- {key: 'node', itemType: 'node', text: ''},
150
- {key: 'url', itemType: 'url', text: str_(i18n.UIStrings.columnURL)},
149
+ {key: 'node', valueType: 'node', label: ''},
150
+ {key: 'url', valueType: 'url', label: str_(i18n.UIStrings.columnURL)},
151
151
  ];
152
152
 
153
153
  return {
@@ -89,12 +89,12 @@ class UserTimings extends Audit {
89
89
 
90
90
  /** @type {LH.Audit.Details.Table['headings']} */
91
91
  const headings = [
92
- {key: 'name', itemType: 'text', text: str_(i18n.UIStrings.columnName)},
93
- {key: 'timingType', itemType: 'text', text: str_(UIStrings.columnType)},
94
- {key: 'startTime', itemType: 'ms', granularity: 0.01,
95
- text: str_(i18n.UIStrings.columnStartTime)},
96
- {key: 'duration', itemType: 'ms', granularity: 0.01,
97
- text: str_(i18n.UIStrings.columnDuration)},
92
+ {key: 'name', valueType: 'text', label: str_(i18n.UIStrings.columnName)},
93
+ {key: 'timingType', valueType: 'text', label: str_(UIStrings.columnType)},
94
+ {key: 'startTime', valueType: 'ms', granularity: 0.01,
95
+ label: str_(i18n.UIStrings.columnStartTime)},
96
+ {key: 'duration', valueType: 'ms', granularity: 0.01,
97
+ label: str_(i18n.UIStrings.columnDuration)},
98
98
  ];
99
99
 
100
100
  const details = Audit.makeTableDetails(headings, tableRows);
@@ -119,11 +119,11 @@ class ValidSourceMaps extends Audit {
119
119
  /* eslint-disable max-len */
120
120
  {
121
121
  key: 'scriptUrl',
122
- itemType: 'url',
122
+ valueType: 'url',
123
123
  subItemsHeading: {key: 'error'},
124
- text: str_(i18n.UIStrings.columnURL),
124
+ label: str_(i18n.UIStrings.columnURL),
125
125
  },
126
- {key: 'sourceMapUrl', itemType: 'url', text: str_(UIStrings.columnMapURL)},
126
+ {key: 'sourceMapUrl', valueType: 'url', label: str_(UIStrings.columnMapURL)},
127
127
  /* eslint-enable max-len */
128
128
  ];
129
129
 
@@ -184,11 +184,11 @@ class WorkDuringInteraction extends Audit {
184
184
  /** @type {LH.Audit.Details.Table['headings']} */
185
185
  const headings = [
186
186
  /* eslint-disable max-len */
187
- {key: 'phase', itemType: 'text', subItemsHeading: {key: 'url', itemType: 'url'}, text: 'Phase'},
188
- {key: 'total', itemType: 'ms', subItemsHeading: {key: 'total', granularity: 1, itemType: 'ms'}, granularity: 1, text: 'Total time'},
189
- {key: null, itemType: 'ms', subItemsHeading: {key: 'scripting', granularity: 1, itemType: 'ms'}, text: 'Script evaluation'},
190
- {key: null, itemType: 'ms', subItemsHeading: {key: 'layout', granularity: 1, itemType: 'ms'}, text: taskGroups.styleLayout.label},
191
- {key: null, itemType: 'ms', subItemsHeading: {key: 'render', granularity: 1, itemType: 'ms'}, text: taskGroups.paintCompositeRender.label},
187
+ {key: 'phase', valueType: 'text', subItemsHeading: {key: 'url', valueType: 'url'}, label: 'Phase'},
188
+ {key: 'total', valueType: 'ms', subItemsHeading: {key: 'total', granularity: 1, valueType: 'ms'}, granularity: 1, label: 'Total time'},
189
+ {key: null, valueType: 'ms', subItemsHeading: {key: 'scripting', granularity: 1, valueType: 'ms'}, label: 'Script evaluation'},
190
+ {key: null, valueType: 'ms', subItemsHeading: {key: 'layout', granularity: 1, valueType: 'ms'}, label: taskGroups.styleLayout.label},
191
+ {key: null, valueType: 'ms', subItemsHeading: {key: 'render', granularity: 1, valueType: 'ms'}, label: taskGroups.paintCompositeRender.label},
192
192
  /* eslint-enable max-len */
193
193
  ];
194
194
 
@@ -208,7 +208,7 @@ class WorkDuringInteraction extends Audit {
208
208
 
209
209
  /** @type {LH.Audit.Details.Table['headings']} */
210
210
  const headings = [
211
- {key: 'node', itemType: 'node', text: str_(UIStrings.eventTarget)},
211
+ {key: 'node', valueType: 'node', label: str_(UIStrings.eventTarget)},
212
212
  ];
213
213
  const elementItems = [{node: Audit.makeNodeItem(responsivenessElement.node)}];
214
214
 
@@ -300,11 +300,12 @@ async function _cleanup({requestedUrl, driver, config}) {
300
300
  }
301
301
 
302
302
  /**
303
+ * @param {LH.Puppeteer.Page|undefined} page
303
304
  * @param {LH.NavigationRequestor|undefined} requestor
304
- * @param {{page?: LH.Puppeteer.Page, config?: LH.Config.Json, flags?: LH.Flags}} options
305
+ * @param {{config?: LH.Config.Json, flags?: LH.Flags}} [options]
305
306
  * @return {Promise<LH.Gatherer.FRGatherResult>}
306
307
  */
307
- async function navigationGather(requestor, options) {
308
+ async function navigationGather(page, requestor, options = {}) {
308
309
  const {flags = {}} = options;
309
310
  log.setLevel(flags.logLevel || 'error');
310
311
 
@@ -316,7 +317,6 @@ async function navigationGather(requestor, options) {
316
317
  const runnerOptions = {config, computedCache};
317
318
  const artifacts = await Runner.gather(
318
319
  async () => {
319
- let {page} = options;
320
320
  const normalizedRequestor = isCallback ? requestor : UrlUtils.normalizeUrl(requestor);
321
321
 
322
322
  // For navigation mode, we shouldn't connect to a browser in audit mode,
@@ -13,11 +13,12 @@ import {initializeConfig} from '../config/config.js';
13
13
  import {getBaseArtifacts, finalizeArtifacts} from './base-artifacts.js';
14
14
 
15
15
  /**
16
- * @param {{page: LH.Puppeteer.Page, config?: LH.Config.Json, flags?: LH.Flags}} options
16
+ * @param {LH.Puppeteer.Page} page
17
+ * @param {{config?: LH.Config.Json, flags?: LH.Flags}} [options]
17
18
  * @return {Promise<LH.Gatherer.FRGatherResult>}
18
19
  */
19
- async function snapshotGather(options) {
20
- const {page, flags = {}} = options;
20
+ async function snapshotGather(page, options = {}) {
21
+ const {flags = {}} = options;
21
22
  log.setLevel(flags.logLevel || 'error');
22
23
 
23
24
  const {config} = await initializeConfig('snapshot', options.config, flags);
@@ -14,11 +14,12 @@ import {initializeConfig} from '../config/config.js';
14
14
  import {getBaseArtifacts, finalizeArtifacts} from './base-artifacts.js';
15
15
 
16
16
  /**
17
- * @param {{page: LH.Puppeteer.Page, config?: LH.Config.Json, flags?: LH.Flags}} options
17
+ * @param {LH.Puppeteer.Page} page
18
+ * @param {{config?: LH.Config.Json, flags?: LH.Flags}} [options]
18
19
  * @return {Promise<{endTimespanGather(): Promise<LH.Gatherer.FRGatherResult>}>}
19
20
  */
20
- async function startTimespanGather(options) {
21
- const {page, flags = {}} = options;
21
+ async function startTimespanGather(page, options = {}) {
22
+ const {flags = {}} = options;
22
23
  log.setLevel(flags.logLevel || 'error');
23
24
 
24
25
  const {config} = await initializeConfig('timespan', options.config, flags);
package/core/index.js CHANGED
@@ -40,7 +40,7 @@ import {initializeConfig} from './config/config.js';
40
40
  * @return {Promise<LH.RunnerResult|undefined>}
41
41
  */
42
42
  async function lighthouse(url, flags = {}, configJSON, page) {
43
- return fraggleRock.navigation(url, {page, config: configJSON, flags});
43
+ return fraggleRock.navigation(page, url, {config: configJSON, flags});
44
44
  }
45
45
 
46
46
  /**
@@ -128,29 +128,6 @@ function assertValidGatherer(gathererInstance, gathererName) {
128
128
  }
129
129
  }
130
130
 
131
-
132
- /**
133
- * Validate the LH.Flags
134
- * @param {LH.Flags} flags
135
- */
136
- function assertValidFlags(flags) {
137
- // COMPAT: compatibility layer for devtools as it uses the old way and we need tests to pass
138
- // TODO(paulirish): remove this from LH once emulation refactor has rolled into DevTools
139
- // @ts-expect-error Deprecated flag
140
- if (flags.channel === 'devtools' && flags.internalDisableDeviceScreenEmulation) {
141
- // @ts-expect-error Deprecated flag
142
- flags.formFactor = flags.emulatedFormFactor;
143
- // @ts-expect-error Deprecated flag
144
- flags.emulatedFormFactor = flags.internalDisableDeviceScreenEmulation = undefined;
145
- }
146
-
147
-
148
- // @ts-expect-error Checking for removed flags
149
- if (flags.emulatedFormFactor || flags.internalDisableDeviceScreenEmulation) {
150
- throw new Error('Invalid emulation flag. Emulation configuration changed in LH 7.0. See https://github.com/GoogleChrome/lighthouse/blob/main/docs/emulation.md');
151
- }
152
- }
153
-
154
131
  /**
155
132
  * @implements {LH.Config.Config}
156
133
  */
@@ -193,9 +170,6 @@ class Config {
193
170
  // Validate and merge in plugins (if any).
194
171
  configJSON = await mergePlugins(configJSON, configDir, flags);
195
172
 
196
- if (flags) {
197
- assertValidFlags(flags);
198
- }
199
173
  const settings = resolveSettings(configJSON.settings || {}, flags);
200
174
 
201
175
  // Augment passes with necessary defaults and require gatherers.