From cd4301d15e8d1f3e30bbe23dc6aab3bd11f9ae18 Mon Sep 17 00:00:00 2001 From: Connor Clark Date: Tue, 6 Oct 2020 18:36:35 -0500 Subject: [PATCH 1/7] misc: return specific html element type for find --- .../report/html/renderer/category-renderer.js | 4 +-- lighthouse-core/report/html/renderer/dom.js | 25 +++++++++++++++---- .../html/renderer/pwa-category-renderer.js | 3 +-- .../report/html/renderer/report-renderer.js | 2 +- .../html/renderer/report-ui-features.js | 9 +++---- 5 files changed, 27 insertions(+), 16 deletions(-) diff --git a/lighthouse-core/report/html/renderer/category-renderer.js b/lighthouse-core/report/html/renderer/category-renderer.js index 3d2549ac5bb6..c5703dda5d71 100644 --- a/lighthouse-core/report/html/renderer/category-renderer.js +++ b/lighthouse-core/report/html/renderer/category-renderer.js @@ -100,7 +100,7 @@ class CategoryRenderer { }); } - const header = /** @type {HTMLDetailsElement} */ (this.dom.find('details', auditEl)); + const header = this.dom.find('details', auditEl); if (audit.result.details) { const elem = this.detailsRenderer.render(audit.result.details); if (elem) { @@ -326,7 +326,7 @@ class CategoryRenderer { */ renderScoreGauge(category, groupDefinitions) { // eslint-disable-line no-unused-vars const tmpl = this.dom.cloneTemplate('#tmpl-lh-gauge', this.templateContext); - const wrapper = /** @type {HTMLAnchorElement} */ (this.dom.find('.lh-gauge__wrapper', tmpl)); + const wrapper = this.dom.find('.lh-gauge__wrapper', tmpl, 'a'); wrapper.href = `#${category.id}`; if (Util.isPluginCategory(category.id)) { diff --git a/lighthouse-core/report/html/renderer/dom.js b/lighthouse-core/report/html/renderer/dom.js index 738675893b25..b74b14c9921f 100644 --- a/lighthouse-core/report/html/renderer/dom.js +++ b/lighthouse-core/report/html/renderer/dom.js @@ -213,27 +213,42 @@ class DOM { /** * Guaranteed context.querySelector. Always returns an element or throws if * nothing matches query. + * @template {string} T * @param {string} query * @param {ParentNode} context - * @return {!HTMLElement} + * @param {T=} tagName + * @return {HTMLElementByTagName[T]} */ - find(query, context) { + find(query, context, tagName) { /** @type {?HTMLElement} */ const result = context.querySelector(query); if (result === null) { throw new Error(`query ${query} not found`); } + if (tagName && result.tagName.toLowerCase() !== tagName) { + throw new Error(`expected ${tagName}, but got ${result.tagName.toLowerCase()}`); + } return result; } /** * Helper for context.querySelectorAll. Returns an Array instead of a NodeList. + * @template {string} T * @param {string} query * @param {ParentNode} context - * @return {!Array} + * @param {T=} tagName + * @return {Array} */ - findAll(query, context) { - return Array.from(context.querySelectorAll(query)); + findAll(query, context, tagName) { + const result = /** @type {HTMLElement[]} */ (Array.from(context.querySelectorAll(query))); + if (tagName) { + for (const el of result) { + if (el.tagName.toLowerCase() !== tagName) { + throw new Error(`expected ${tagName}, but got ${el.tagName.toLowerCase()}`); + } + } + } + return result; } } diff --git a/lighthouse-core/report/html/renderer/pwa-category-renderer.js b/lighthouse-core/report/html/renderer/pwa-category-renderer.js index c0872b57b019..6872119b3303 100644 --- a/lighthouse-core/report/html/renderer/pwa-category-renderer.js +++ b/lighthouse-core/report/html/renderer/pwa-category-renderer.js @@ -58,8 +58,7 @@ class PwaCategoryRenderer extends CategoryRenderer { } const tmpl = this.dom.cloneTemplate('#tmpl-lh-gauge--pwa', this.templateContext); - const wrapper = /** @type {HTMLAnchorElement} */ (this.dom.find('.lh-gauge--pwa__wrapper', - tmpl)); + const wrapper = this.dom.find('.lh-gauge--pwa__wrapper', tmpl, 'a'); wrapper.href = `#${category.id}`; // Correct IDs in case multiple instances end up in the page. diff --git a/lighthouse-core/report/html/renderer/report-renderer.js b/lighthouse-core/report/html/renderer/report-renderer.js index 85f286a98236..af57a8727ed7 100644 --- a/lighthouse-core/report/html/renderer/report-renderer.js +++ b/lighthouse-core/report/html/renderer/report-renderer.js @@ -70,7 +70,7 @@ class ReportRenderer { */ _renderReportTopbar(report) { const el = this._dom.cloneTemplate('#tmpl-lh-topbar', this._templateContext); - const metadataUrl = /** @type {HTMLAnchorElement} */ (this._dom.find('.lh-topbar__url', el)); + const metadataUrl = this._dom.find('.lh-topbar__url', el, 'a'); metadataUrl.href = metadataUrl.textContent = report.finalUrl; metadataUrl.title = report.finalUrl; return el; diff --git a/lighthouse-core/report/html/renderer/report-ui-features.js b/lighthouse-core/report/html/renderer/report-ui-features.js index ae35e209bdb9..3e8a1ed7efc6 100644 --- a/lighthouse-core/report/html/renderer/report-ui-features.js +++ b/lighthouse-core/report/html/renderer/report-ui-features.js @@ -246,8 +246,7 @@ class ReportUIFeatures { // create input box const filterTemplate = this._dom.cloneTemplate('#tmpl-lh-3p-filter', this._templateContext); - const filterInput = - /** @type {HTMLInputElement} */ (this._dom.find('input', filterTemplate)); + const filterInput = this._dom.find('input', filterTemplate, 'input'); const id = `lh-3p-filter-label--${index}`; filterInput.id = id; @@ -527,8 +526,7 @@ class ReportUIFeatures { * open a `
` element. */ expandAllDetails() { - const details = /** @type {Array} */ (this._dom.findAll( - '.lh-categories details', this._document)); + const details = this._dom.findAll('.lh-categories details', this._document, 'details'); details.map(detail => detail.open = true); } @@ -537,8 +535,7 @@ class ReportUIFeatures { * open a `
` element. */ collapseAllDetails() { - const details = /** @type {Array} */ (this._dom.findAll( - '.lh-categories details', this._document)); + const details = this._dom.findAll('.lh-categories details', this._document, 'details'); details.map(detail => detail.open = false); } From 8b1732291475018f966dcfcee02f9ac0624ffee3 Mon Sep 17 00:00:00 2001 From: Connor Clark Date: Thu, 8 Oct 2020 14:52:32 -0500 Subject: [PATCH 2/7] pr --- lighthouse-core/report/html/renderer/dom.js | 12 ++++++------ .../report/html/renderer/report-ui-features.js | 3 +-- 2 files changed, 7 insertions(+), 8 deletions(-) diff --git a/lighthouse-core/report/html/renderer/dom.js b/lighthouse-core/report/html/renderer/dom.js index b74b14c9921f..8bef68c35a06 100644 --- a/lighthouse-core/report/html/renderer/dom.js +++ b/lighthouse-core/report/html/renderer/dom.js @@ -216,7 +216,7 @@ class DOM { * @template {string} T * @param {string} query * @param {ParentNode} context - * @param {T=} tagName + * @param {T=} tagName Functionally optional, but providing it avoids needing a typecast * @return {HTMLElementByTagName[T]} */ find(query, context, tagName) { @@ -225,8 +225,8 @@ class DOM { if (result === null) { throw new Error(`query ${query} not found`); } - if (tagName && result.tagName.toLowerCase() !== tagName) { - throw new Error(`expected ${tagName}, but got ${result.tagName.toLowerCase()}`); + if (tagName && result.tagName !== tagName.toUpperCase()) { + throw new Error(`expected ${tagName.toUpperCase()}, but got ${result.tagName}`); } return result; } @@ -236,15 +236,15 @@ class DOM { * @template {string} T * @param {string} query * @param {ParentNode} context - * @param {T=} tagName + * @param {T=} tagName Functionally optional, but providing it avoids needing a typecast * @return {Array} */ findAll(query, context, tagName) { const result = /** @type {HTMLElement[]} */ (Array.from(context.querySelectorAll(query))); if (tagName) { for (const el of result) { - if (el.tagName.toLowerCase() !== tagName) { - throw new Error(`expected ${tagName}, but got ${el.tagName.toLowerCase()}`); + if (el.tagName !== tagName.toUpperCase()) { + throw new Error(`expected ${tagName.toUpperCase()}, but got ${el.tagName}`); } } } diff --git a/lighthouse-core/report/html/renderer/report-ui-features.js b/lighthouse-core/report/html/renderer/report-ui-features.js index 3e8a1ed7efc6..a32128f33b37 100644 --- a/lighthouse-core/report/html/renderer/report-ui-features.js +++ b/lighthouse-core/report/html/renderer/report-ui-features.js @@ -138,8 +138,7 @@ class ReportUIFeatures { const hasMetricError = report.categories.performance && report.categories.performance.auditRefs .some(audit => Boolean(audit.group === 'metrics' && report.audits[audit.id].errorMessage)); if (hasMetricError) { - const toggleInputEl = /** @type {HTMLInputElement} */ ( - this._dom.find('.lh-metrics-toggle__input', this._document)); + const toggleInputEl = this._dom.find('.lh-metrics-toggle__input', this._document, 'input'); toggleInputEl.checked = true; } From 53a45360d52cb6e9b64857ac56dfa6df5c73935e Mon Sep 17 00:00:00 2001 From: Connor Clark Date: Wed, 20 Jan 2021 17:21:33 -0600 Subject: [PATCH 3/7] upddate --- .../report/html/renderer/category-renderer.js | 2 +- lighthouse-core/report/html/renderer/dom.js | 11 +++-------- .../report/html/renderer/report-renderer.js | 2 +- .../report/html/renderer/report-ui-features.js | 4 ++-- package.json | 3 ++- types/externs.d.ts | 11 +++++++++++ yarn.lock | 13 +++++++++---- 7 files changed, 29 insertions(+), 17 deletions(-) diff --git a/lighthouse-core/report/html/renderer/category-renderer.js b/lighthouse-core/report/html/renderer/category-renderer.js index c5703dda5d71..a05366364a2e 100644 --- a/lighthouse-core/report/html/renderer/category-renderer.js +++ b/lighthouse-core/report/html/renderer/category-renderer.js @@ -326,7 +326,7 @@ class CategoryRenderer { */ renderScoreGauge(category, groupDefinitions) { // eslint-disable-line no-unused-vars const tmpl = this.dom.cloneTemplate('#tmpl-lh-gauge', this.templateContext); - const wrapper = this.dom.find('.lh-gauge__wrapper', tmpl, 'a'); + const wrapper = this.dom.find('a.lh-gauge__wrapper', tmpl); wrapper.href = `#${category.id}`; if (Util.isPluginCategory(category.id)) { diff --git a/lighthouse-core/report/html/renderer/dom.js b/lighthouse-core/report/html/renderer/dom.js index 8bef68c35a06..ad8aba1623e3 100644 --- a/lighthouse-core/report/html/renderer/dom.js +++ b/lighthouse-core/report/html/renderer/dom.js @@ -214,20 +214,15 @@ class DOM { * Guaranteed context.querySelector. Always returns an element or throws if * nothing matches query. * @template {string} T - * @param {string} query + * @param {T} query * @param {ParentNode} context - * @param {T=} tagName Functionally optional, but providing it avoids needing a typecast - * @return {HTMLElementByTagName[T]} */ - find(query, context, tagName) { - /** @type {?HTMLElement} */ + find(query, context) { + /** @type {?ParseQuerySelector} */ const result = context.querySelector(query); if (result === null) { throw new Error(`query ${query} not found`); } - if (tagName && result.tagName !== tagName.toUpperCase()) { - throw new Error(`expected ${tagName.toUpperCase()}, but got ${result.tagName}`); - } return result; } diff --git a/lighthouse-core/report/html/renderer/report-renderer.js b/lighthouse-core/report/html/renderer/report-renderer.js index 95814e674e6d..002e567c9ceb 100644 --- a/lighthouse-core/report/html/renderer/report-renderer.js +++ b/lighthouse-core/report/html/renderer/report-renderer.js @@ -70,7 +70,7 @@ class ReportRenderer { */ _renderReportTopbar(report) { const el = this._dom.cloneTemplate('#tmpl-lh-topbar', this._templateContext); - const metadataUrl = this._dom.find('.lh-topbar__url', el, 'a'); + const metadataUrl = this._dom.find('a.lh-topbar__url', el); metadataUrl.href = metadataUrl.textContent = report.finalUrl; metadataUrl.title = report.finalUrl; return el; diff --git a/lighthouse-core/report/html/renderer/report-ui-features.js b/lighthouse-core/report/html/renderer/report-ui-features.js index 07ed69c951e8..e4b579f996ee 100644 --- a/lighthouse-core/report/html/renderer/report-ui-features.js +++ b/lighthouse-core/report/html/renderer/report-ui-features.js @@ -147,7 +147,7 @@ class ReportUIFeatures { const hasMetricError = report.categories.performance && report.categories.performance.auditRefs .some(audit => Boolean(audit.group === 'metrics' && report.audits[audit.id].errorMessage)); if (hasMetricError) { - const toggleInputEl = this._dom.find('.lh-metrics-toggle__input', this._document, 'input'); + const toggleInputEl = this._dom.find('input.lh-metrics-toggle__input', this._document); toggleInputEl.checked = true; } @@ -255,7 +255,7 @@ class ReportUIFeatures { // create input box const filterTemplate = this._dom.cloneTemplate('#tmpl-lh-3p-filter', this._templateContext); - const filterInput = this._dom.find('input', filterTemplate, 'input'); + const filterInput = this._dom.find('input', filterTemplate); const id = `lh-3p-filter-label--${index}`; filterInput.id = id; diff --git a/package.json b/package.json index 9fd7324966f2..14000bfe8f0e 100644 --- a/package.json +++ b/package.json @@ -152,7 +152,8 @@ "pretty-json-stringify": "^0.0.2", "puppeteer": "^1.19.0", "terser": "^5.3.8", - "typescript": "4.1.2", + "typed-query-selector": "^2.3.0", + "typescript": "4.1.3", "webtreemap-cdt": "^3.0.1" }, "dependencies": { diff --git a/types/externs.d.ts b/types/externs.d.ts index 9cdc87fe2258..aa17984d69fa 100644 --- a/types/externs.d.ts +++ b/types/externs.d.ts @@ -94,6 +94,17 @@ declare global { [K in keyof T as KebabToCamelCase]: T[K]; } + type TagNameToElement< + Tag extends string + > = Tag extends keyof HTMLElementTagNameMap + ? HTMLElementTagNameMap[Tag] + : Tag extends keyof SVGElementTagNameMap + ? SVGElementTagNameMap[Tag] + : HTMLElement; // typed-query-selector use Element here, which we don't want. + type ParseQuerySelector = TagNameToElement< + import('typed-query-selector/parser').ParseSelectorToTagNames[number] + >; + module LH { // re-export useful type modules under global LH module. export import Crdp = _Crdp; diff --git a/yarn.lock b/yarn.lock index 6b74d3fb5c12..b6e1bbda93c5 100644 --- a/yarn.lock +++ b/yarn.lock @@ -7819,6 +7819,11 @@ type@^1.0.1: resolved "https://registry.yarnpkg.com/type/-/type-1.0.1.tgz#084c9a17fcc9151a2cdb1459905c2e45e4bb7d61" integrity sha512-MAM5dBMJCJNKs9E7JXo4CXRAansRfG0nlJxW7Wf6GZzSOvH31zClSaHdIMWLehe/EGMBkqeC55rrkaOr5Oo7Nw== +typed-query-selector@^2.3.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/typed-query-selector/-/typed-query-selector-2.3.0.tgz#a56db9f4d02c93d01365c07869338372947fcce7" + integrity sha512-R0PkWV4BR4FC1hblV7p6DWIp/PwUQVACZ7LVBGi04b9bsIN/9C4Sx7FyRd17MoQS4BrQOImNBY1ItR9gz+knhw== + typedarray-to-buffer@^3.1.5: version "3.1.5" resolved "https://registry.yarnpkg.com/typedarray-to-buffer/-/typedarray-to-buffer-3.1.5.tgz#a97ee7a9ff42691b9f783ff1bc5112fe3fca9080" @@ -7831,10 +7836,10 @@ typedarray@^0.0.6: resolved "https://registry.yarnpkg.com/typedarray/-/typedarray-0.0.6.tgz#867ac74e3864187b1d3d47d996a78ec5c8830777" integrity sha1-hnrHTjhkGHsdPUfZlqeOxciDB3c= -typescript@4.1.2: - version "4.1.2" - resolved "https://registry.yarnpkg.com/typescript/-/typescript-4.1.2.tgz#6369ef22516fe5e10304aae5a5c4862db55380e9" - integrity sha512-thGloWsGH3SOxv1SoY7QojKi0tc+8FnOmiarEGMbd/lar7QOEd3hvlx3Fp5y6FlDUGl9L+pd4n2e+oToGMmhRQ== +typescript@4.1.3: + version "4.1.3" + resolved "https://registry.yarnpkg.com/typescript/-/typescript-4.1.3.tgz#519d582bd94cba0cf8934c7d8e8467e473f53bb7" + integrity sha512-B3ZIOf1IKeH2ixgHhj6la6xdwR9QrLC5d1VKeCSY4tvkqhF2eqd9O7txNlS0PO3GrBAFIdr3L1ndNwteUbZLYg== uglify-js@^3.1.4: version "3.4.9" From 15f92708fcb0cbad9a45a6b4240d3ecffa2f2c00 Mon Sep 17 00:00:00 2001 From: Connor Clark Date: Thu, 21 Jan 2021 16:43:31 -0600 Subject: [PATCH 4/7] ok --- lighthouse-core/report/html/renderer/dom.js | 2 +- package.json | 2 +- types/externs.d.ts | 11 ----------- yarn.lock | 8 ++++---- 4 files changed, 6 insertions(+), 17 deletions(-) diff --git a/lighthouse-core/report/html/renderer/dom.js b/lighthouse-core/report/html/renderer/dom.js index ad8aba1623e3..22c548c1fd11 100644 --- a/lighthouse-core/report/html/renderer/dom.js +++ b/lighthouse-core/report/html/renderer/dom.js @@ -218,7 +218,7 @@ class DOM { * @param {ParentNode} context */ find(query, context) { - /** @type {?ParseQuerySelector} */ + /** @type {?import('typed-query-selector/parser').ParseSelector} */ const result = context.querySelector(query); if (result === null) { throw new Error(`query ${query} not found`); diff --git a/package.json b/package.json index 14000bfe8f0e..64288d2140b1 100644 --- a/package.json +++ b/package.json @@ -152,7 +152,7 @@ "pretty-json-stringify": "^0.0.2", "puppeteer": "^1.19.0", "terser": "^5.3.8", - "typed-query-selector": "^2.3.0", + "typed-query-selector": "^2.4.0", "typescript": "4.1.3", "webtreemap-cdt": "^3.0.1" }, diff --git a/types/externs.d.ts b/types/externs.d.ts index aa17984d69fa..9cdc87fe2258 100644 --- a/types/externs.d.ts +++ b/types/externs.d.ts @@ -94,17 +94,6 @@ declare global { [K in keyof T as KebabToCamelCase]: T[K]; } - type TagNameToElement< - Tag extends string - > = Tag extends keyof HTMLElementTagNameMap - ? HTMLElementTagNameMap[Tag] - : Tag extends keyof SVGElementTagNameMap - ? SVGElementTagNameMap[Tag] - : HTMLElement; // typed-query-selector use Element here, which we don't want. - type ParseQuerySelector = TagNameToElement< - import('typed-query-selector/parser').ParseSelectorToTagNames[number] - >; - module LH { // re-export useful type modules under global LH module. export import Crdp = _Crdp; diff --git a/yarn.lock b/yarn.lock index b6e1bbda93c5..3dcb1acadda5 100644 --- a/yarn.lock +++ b/yarn.lock @@ -7819,10 +7819,10 @@ type@^1.0.1: resolved "https://registry.yarnpkg.com/type/-/type-1.0.1.tgz#084c9a17fcc9151a2cdb1459905c2e45e4bb7d61" integrity sha512-MAM5dBMJCJNKs9E7JXo4CXRAansRfG0nlJxW7Wf6GZzSOvH31zClSaHdIMWLehe/EGMBkqeC55rrkaOr5Oo7Nw== -typed-query-selector@^2.3.0: - version "2.3.0" - resolved "https://registry.yarnpkg.com/typed-query-selector/-/typed-query-selector-2.3.0.tgz#a56db9f4d02c93d01365c07869338372947fcce7" - integrity sha512-R0PkWV4BR4FC1hblV7p6DWIp/PwUQVACZ7LVBGi04b9bsIN/9C4Sx7FyRd17MoQS4BrQOImNBY1ItR9gz+knhw== +typed-query-selector@^2.4.0: + version "2.4.0" + resolved "https://registry.yarnpkg.com/typed-query-selector/-/typed-query-selector-2.4.0.tgz#5b07b099e92c910602f55c26cdb7115618d96b6c" + integrity sha512-LVsEnvOgSjMNCPX/6zi9rhpjnTlBfnLsTta+FFJywBdQom0k5yhNraru79HFtU1Q4ncUDtRhfMMHLnbZ10NCLQ== typedarray-to-buffer@^3.1.5: version "3.1.5" From 504ec4104ea4b772d1b174c17888d0b62ad47a73 Mon Sep 17 00:00:00 2001 From: Connor Clark Date: Thu, 21 Jan 2021 17:16:20 -0600 Subject: [PATCH 5/7] update --- .../report/html/renderer/category-renderer.js | 12 ++++++------ lighthouse-core/report/html/renderer/dom.js | 2 +- .../html/renderer/element-screenshot-renderer.js | 10 +++++----- .../html/renderer/performance-category-renderer.js | 7 ++++--- .../report/html/renderer/pwa-category-renderer.js | 2 +- .../report/html/renderer/report-ui-features.js | 12 ++++++------ 6 files changed, 23 insertions(+), 22 deletions(-) diff --git a/lighthouse-core/report/html/renderer/category-renderer.js b/lighthouse-core/report/html/renderer/category-renderer.js index a05366364a2e..58af7d068526 100644 --- a/lighthouse-core/report/html/renderer/category-renderer.js +++ b/lighthouse-core/report/html/renderer/category-renderer.js @@ -144,11 +144,11 @@ class CategoryRenderer { } /** - * @return {HTMLElement} + * @return {Element} */ _createChevron() { const chevronTmpl = this.dom.cloneTemplate('#tmpl-lh-chevron', this.templateContext); - const chevronEl = this.dom.find('.lh-chevron', chevronTmpl); + const chevronEl = this.dom.find('svg.lh-chevron', chevronTmpl); return chevronEl; } @@ -287,9 +287,9 @@ class CategoryRenderer { clumpElement.setAttribute('open', ''); } - const summaryInnerEl = this.dom.find('.lh-audit-group__summary', clumpElement); - const chevronEl = summaryInnerEl.appendChild(this._createChevron()); - chevronEl.title = Util.i18n.strings.auditGroupExpandTooltip; + const summaryInnerEl = this.dom.find('div.lh-audit-group__summary', clumpElement); + summaryInnerEl.appendChild(this._createChevron()); + summaryInnerEl.title = Util.i18n.strings.auditGroupExpandTooltip; const headerEl = this.dom.find('.lh-audit-group__header', clumpElement); const title = this._clumpTitles[clumpId]; @@ -342,7 +342,7 @@ class CategoryRenderer { if (gaugeArc) this._setGaugeArc(gaugeArc, numericScore); const scoreOutOf100 = Math.round(numericScore * 100); - const percentageEl = this.dom.find('.lh-gauge__percentage', tmpl); + const percentageEl = this.dom.find('div.lh-gauge__percentage', tmpl); percentageEl.textContent = scoreOutOf100.toString(); if (category.score === null) { percentageEl.textContent = '?'; diff --git a/lighthouse-core/report/html/renderer/dom.js b/lighthouse-core/report/html/renderer/dom.js index 22c548c1fd11..50731d30ed57 100644 --- a/lighthouse-core/report/html/renderer/dom.js +++ b/lighthouse-core/report/html/renderer/dom.js @@ -218,7 +218,7 @@ class DOM { * @param {ParentNode} context */ find(query, context) { - /** @type {?import('typed-query-selector/parser').ParseSelector} */ + /** @type {?import('typed-query-selector/parser').ParseSelector} */ const result = context.querySelector(query); if (result === null) { throw new Error(`query ${query} not found`); diff --git a/lighthouse-core/report/html/renderer/element-screenshot-renderer.js b/lighthouse-core/report/html/renderer/element-screenshot-renderer.js index b9d5731ebc6a..e2f04d3d47dd 100644 --- a/lighthouse-core/report/html/renderer/element-screenshot-renderer.js +++ b/lighthouse-core/report/html/renderer/element-screenshot-renderer.js @@ -228,7 +228,7 @@ class ElementScreenshotRenderer { } const tmpl = dom.cloneTemplate('#tmpl-lh-element-screenshot', templateContext); - const containerEl = dom.find('.lh-element-screenshot', tmpl); + const containerEl = dom.find('div.lh-element-screenshot', tmpl); containerEl.dataset['rectWidth'] = elementRectSC.width.toString(); containerEl.dataset['rectHeight'] = elementRectSC.height.toString(); @@ -256,10 +256,10 @@ class ElementScreenshotRenderer { {width: screenshot.width, height: screenshot.height} ); - const contentEl = dom.find('.lh-element-screenshot__content', containerEl); + const contentEl = dom.find('div.lh-element-screenshot__content', containerEl); contentEl.style.top = `-${elementPreviewSizeDC.height}px`; - const imageEl = dom.find('.lh-element-screenshot__image', containerEl); + const imageEl = dom.find('div.lh-element-screenshot__image', containerEl); imageEl.style.width = elementPreviewSizeDC.width + 'px'; imageEl.style.height = elementPreviewSizeDC.height + 'px'; @@ -268,13 +268,13 @@ class ElementScreenshotRenderer { imageEl.style.backgroundSize = `${screenshot.width * zoomFactor}px ${screenshot.height * zoomFactor}px`; - const markerEl = dom.find('.lh-element-screenshot__element-marker', containerEl); + const markerEl = dom.find('div.lh-element-screenshot__element-marker', containerEl); markerEl.style.width = elementRectSC.width * zoomFactor + 'px'; markerEl.style.height = elementRectSC.height * zoomFactor + 'px'; markerEl.style.left = positions.clip.left * zoomFactor + 'px'; markerEl.style.top = positions.clip.top * zoomFactor + 'px'; - const maskEl = dom.find('.lh-element-screenshot__mask', containerEl); + const maskEl = dom.find('div.lh-element-screenshot__mask', containerEl); maskEl.style.width = elementPreviewSizeDC.width + 'px'; maskEl.style.height = elementPreviewSizeDC.height + 'px'; diff --git a/lighthouse-core/report/html/renderer/performance-category-renderer.js b/lighthouse-core/report/html/renderer/performance-category-renderer.js index e6fd233ba9de..2efea8bacc49 100644 --- a/lighthouse-core/report/html/renderer/performance-category-renderer.js +++ b/lighthouse-core/report/html/renderer/performance-category-renderer.js @@ -70,15 +70,16 @@ class PerformanceCategoryRenderer extends CategoryRenderer { } // Overwrite the displayValue with opportunity's wastedMs - const displayEl = this.dom.find('.lh-audit__display-text', element); + const displayEl = + this.dom.find('span.lh-audit__display-text, div.lh-audit__display-text', element); const sparklineWidthPct = `${details.overallSavingsMs / scale * 100}%`; - this.dom.find('.lh-sparkline__bar', element).style.width = sparklineWidthPct; + this.dom.find('div.lh-sparkline__bar', element).style.width = sparklineWidthPct; displayEl.textContent = Util.i18n.formatSeconds(details.overallSavingsMs, 0.01); // Set [title] tooltips if (audit.result.displayValue) { const displayValue = audit.result.displayValue; - this.dom.find('.lh-load-opportunity__sparkline', element).title = displayValue; + this.dom.find('div.lh-load-opportunity__sparkline', element).title = displayValue; displayEl.title = displayValue; } diff --git a/lighthouse-core/report/html/renderer/pwa-category-renderer.js b/lighthouse-core/report/html/renderer/pwa-category-renderer.js index 6872119b3303..fdb5b6906810 100644 --- a/lighthouse-core/report/html/renderer/pwa-category-renderer.js +++ b/lighthouse-core/report/html/renderer/pwa-category-renderer.js @@ -58,7 +58,7 @@ class PwaCategoryRenderer extends CategoryRenderer { } const tmpl = this.dom.cloneTemplate('#tmpl-lh-gauge--pwa', this.templateContext); - const wrapper = this.dom.find('.lh-gauge--pwa__wrapper', tmpl, 'a'); + const wrapper = this.dom.find('a.lh-gauge--pwa__wrapper', tmpl); wrapper.href = `#${category.id}`; // Correct IDs in case multiple instances end up in the page. diff --git a/lighthouse-core/report/html/renderer/report-ui-features.js b/lighthouse-core/report/html/renderer/report-ui-features.js index e4b579f996ee..d4d643f07529 100644 --- a/lighthouse-core/report/html/renderer/report-ui-features.js +++ b/lighthouse-core/report/html/renderer/report-ui-features.js @@ -171,7 +171,7 @@ class ReportUIFeatures { /** * Finds the first scrollable ancestor of `element`. Falls back to the document. - * @param {HTMLElement} element + * @param {Element} element * @return {Node} */ _getScrollParent(element) { @@ -360,9 +360,9 @@ class ReportUIFeatures { } _setupStickyHeaderElements() { - this.topbarEl = this._dom.find('.lh-topbar', this._document); - this.scoreScaleEl = this._dom.find('.lh-scorescale', this._document); - this.stickyHeaderEl = this._dom.find('.lh-sticky-header', this._document); + this.topbarEl = this._dom.find('div.lh-topbar', this._document); + this.scoreScaleEl = this._dom.find('div.lh-scorescale', this._document); + this.stickyHeaderEl = this._dom.find('div.lh-sticky-header', this._document); // Highlighter will be absolutely positioned at first gauge, then transformed on scroll. this.highlightEl = this._dom.createChildOf(this.stickyHeaderEl, 'div', 'lh-highlighter'); @@ -714,11 +714,11 @@ class DropDown { * @param {function(MouseEvent): any} menuClickHandler */ setup(menuClickHandler) { - this._toggleEl = this._dom.find('.lh-tools__button', this._dom.document()); + this._toggleEl = this._dom.find('button.lh-tools__button', this._dom.document()); this._toggleEl.addEventListener('click', this.onToggleClick); this._toggleEl.addEventListener('keydown', this.onToggleKeydown); - this._menuEl = this._dom.find('.lh-tools__dropdown', this._dom.document()); + this._menuEl = this._dom.find('div.lh-tools__dropdown', this._dom.document()); this._menuEl.addEventListener('keydown', this.onMenuKeydown); this._menuEl.addEventListener('click', menuClickHandler); } From 85f17f65812edc2bb3101a484089061ef303f877 Mon Sep 17 00:00:00 2001 From: Connor Clark Date: Thu, 21 Jan 2021 17:23:08 -0600 Subject: [PATCH 6/7] findAll --- lighthouse-core/report/html/renderer/dom.js | 18 +++++------------- .../report/html/renderer/report-ui-features.js | 13 ++----------- 2 files changed, 7 insertions(+), 24 deletions(-) diff --git a/lighthouse-core/report/html/renderer/dom.js b/lighthouse-core/report/html/renderer/dom.js index 50731d30ed57..8b564606772b 100644 --- a/lighthouse-core/report/html/renderer/dom.js +++ b/lighthouse-core/report/html/renderer/dom.js @@ -229,21 +229,13 @@ class DOM { /** * Helper for context.querySelectorAll. Returns an Array instead of a NodeList. * @template {string} T - * @param {string} query + * @param {T} query * @param {ParentNode} context - * @param {T=} tagName Functionally optional, but providing it avoids needing a typecast - * @return {Array} */ - findAll(query, context, tagName) { - const result = /** @type {HTMLElement[]} */ (Array.from(context.querySelectorAll(query))); - if (tagName) { - for (const el of result) { - if (el.tagName !== tagName.toUpperCase()) { - throw new Error(`expected ${tagName.toUpperCase()}, but got ${el.tagName}`); - } - } - } - return result; + findAll(query, context) { + /** @type {Array>} */ + const elements = Array.from(context.querySelectorAll(query)); + return elements; } } diff --git a/lighthouse-core/report/html/renderer/report-ui-features.js b/lighthouse-core/report/html/renderer/report-ui-features.js index d4d643f07529..15386ed3936c 100644 --- a/lighthouse-core/report/html/renderer/report-ui-features.js +++ b/lighthouse-core/report/html/renderer/report-ui-features.js @@ -350,15 +350,6 @@ class ReportUIFeatures { return thirdPartyRows; } - /** - * From a table, finds and returns URL items. - * @param {HTMLTableElement} tableEl - * @return {Array} - */ - _getUrlItems(tableEl) { - return this._dom.findAll('.lh-text__url', tableEl); - } - _setupStickyHeaderElements() { this.topbarEl = this._dom.find('div.lh-topbar', this._document); this.scoreScaleEl = this._dom.find('div.lh-scorescale', this._document); @@ -568,7 +559,7 @@ class ReportUIFeatures { * open a `
` element. */ expandAllDetails() { - const details = this._dom.findAll('.lh-categories details', this._document, 'details'); + const details = this._dom.findAll('.lh-categories details', this._document); details.map(detail => detail.open = true); } @@ -577,7 +568,7 @@ class ReportUIFeatures { * open a `
` element. */ collapseAllDetails() { - const details = this._dom.findAll('.lh-categories details', this._document, 'details'); + const details = this._dom.findAll('.lh-categories details', this._document); details.map(detail => detail.open = false); } From 27b788f147655cb64abc38cd8506eb4889234909 Mon Sep 17 00:00:00 2001 From: Connor Clark Date: Fri, 22 Jan 2021 12:54:51 -0600 Subject: [PATCH 7/7] comment --- .../report/html/renderer/performance-category-renderer.js | 1 + 1 file changed, 1 insertion(+) diff --git a/lighthouse-core/report/html/renderer/performance-category-renderer.js b/lighthouse-core/report/html/renderer/performance-category-renderer.js index 2efea8bacc49..3cbadb5e9f6c 100644 --- a/lighthouse-core/report/html/renderer/performance-category-renderer.js +++ b/lighthouse-core/report/html/renderer/performance-category-renderer.js @@ -70,6 +70,7 @@ class PerformanceCategoryRenderer extends CategoryRenderer { } // Overwrite the displayValue with opportunity's wastedMs + // TODO: normalize this to one tagName. const displayEl = this.dom.find('span.lh-audit__display-text, div.lh-audit__display-text', element); const sparklineWidthPct = `${details.overallSavingsMs / scale * 100}%`;