Repository: GoogleChrome/lighthouse (js)

Issue:
Confusing interface and more
<!-- Before creating an issue please make sure you are using the latest version and have checked for duplicate issues. -->

#### Provide the steps to reproduce
1. Run LH on <https://uk.wikibudgets.org/w/united-kingdom-budget-2015>

#### What is the current behavior?
The SEO section score is 100 points.
The Crawling and Indexing says "robots.txt is valid", yet there is a red triangle icon with an exclamation mark. Why?
The Content Best Practices section says "Document has a valid rel=canonical", yet there is a red triangle icon with an exclamation mark.

#### What is the expected behavior?
If something is ok or 100 point score I don't expect a red triangle icon with an exclamation mark.
When I see a red triangle icon with an exclamation mark, I expect a rollover text or other explanation of what is wrong. 


#### Environment Information
* Affected Channels: <!-- CLI, Node, Extension, DevTools -->
* Lighthouse version:
* Node.js version:
* Operating System:

**Related issues**


Pull request description:
report: handle underscored not_applicable scoreDisplayMode
(temporarily) fixes #6540

Adds a check to `Util.prepareReportResult` to convert any `scoreDisplayMode` of `'not_applicable'` to `'not-applicable'` since the API is currently returning the first variant but the report renderer only understands the second.

Ideally we'll fix this at the API level (or, booooo, change the official LH value to the underscored version), but this fix is easier to deploy for now.

See #6371 and #6201 for background.

cc @exterkamp @ebidel 

Patch:
diff --git a/lighthouse-core/report/html/renderer/util.js b/lighthouse-core/report/html/renderer/util.js
index 875a89f66..cd2cc4535 100644
--- a/lighthouse-core/report/html/renderer/util.js
+++ b/lighthouse-core/report/html/renderer/util.js
@@ -62,6 +62,15 @@ class Util {
     if (typeof clone.categories !== 'object') throw new Error('No categories provided.');
     clone.reportCategories = Object.values(clone.categories);
 
+    // The proto process turns 'not-applicable' into 'not_applicable'. Correct this to support both.
+    // TODO: remove when underscore/hyphen proto issue is resolved. See #6371, #6201.
+    for (const audit of Object.values(clone.audits)) {
+      // @ts-ignore tsc rightly flags that this value shouldn't occur.
+      if (audit.scoreDisplayMode === 'not_applicable') {
+        audit.scoreDisplayMode = 'not-applicable';
+      }
+    }
+
     // For convenience, smoosh all AuditResults into their auditDfn (which has just weight & group)
     for (const category of clone.reportCategories) {
       category.auditRefs.forEach(auditMeta => {


Test patch:
diff --git a/lighthouse-core/test/report/html/renderer/report-renderer-test.js b/lighthouse-core/test/report/html/renderer/report-renderer-test.js
index 22c3fee12..37850907f 100644
--- a/lighthouse-core/test/report/html/renderer/report-renderer-test.js
+++ b/lighthouse-core/test/report/html/renderer/report-renderer-test.js
@@ -154,4 +154,25 @@ describe('ReportRenderer', () => {
     renderer.setTemplateContext(otherDocument);
     assert.equal(renderer._templateContext, otherDocument);
   });
+
+  it('renders `not_applicable` audits as `not-applicable`', () => {
+    const clonedSampleResult = JSON.parse(JSON.stringify(sampleResultsOrig));
+
+    let notApplicableCount = 0;
+    Object.values(clonedSampleResult.audits).forEach(audit => {
+      if (audit.scoreDisplayMode === 'not-applicable') {
+        notApplicableCount++;
+        audit.scoreDisplayMode = 'not_applicable';
+      }
+    });
+
+    assert.ok(notApplicableCount > 20); // Make sure something's being tested.
+
+    const container = renderer._dom._document.body;
+    const reportElement = renderer.renderReport(sampleResults, container);
+    const notApplicableElementCount = reportElement
+      .querySelectorAll('.lh-audit--not-applicable').length;
+
+    assert.strictEqual(notApplicableCount, notApplicableElementCount);
+  });
 });
diff --git a/lighthouse-core/test/report/html/renderer/util-test.js b/lighthouse-core/test/report/html/renderer/util-test.js
index e870d48fd..bb33a218d 100644
--- a/lighthouse-core/test/report/html/renderer/util-test.js
+++ b/lighthouse-core/test/report/html/renderer/util-test.js
@@ -7,6 +7,7 @@
 
 const assert = require('assert');
 const Util = require('../../../../report/html/renderer/util.js');
+const sampleResult = require('../../../results/sample_v2.json');
 
 const NBSP = '\xa0';
 
@@ -168,4 +169,24 @@ describe('util helpers', () => {
     Util.formatDisplayValue(displayValue);
     assert.deepStrictEqual(displayValue, cloned, 'displayValue was mutated');
   });
+
+  describe('#prepareReportResult', () => {
+    it('corrects underscored `not-applicable` scoreDisplayMode', () => {
+      const clonedSampleResult = JSON.parse(JSON.stringify(sampleResult));
+
+      let notApplicableCount = 0;
+      Object.values(clonedSampleResult.audits).forEach(audit => {
+        if (audit.scoreDisplayMode === 'not-applicable') {
+          notApplicableCount++;
+          audit.scoreDisplayMode = 'not_applicable';
+        }
+      });
+
+      assert.ok(notApplicableCount > 20); // Make sure something's being tested.
+
+      // Original audit results should be restored.
+      const preparedResult = Util.prepareReportResult(clonedSampleResult);
+      assert.deepStrictEqual(preparedResult.audits, sampleResult.audits);
+    });
+  });
 });