lighthouse icon indicating copy to clipboard operation
lighthouse copied to clipboard

`content-visibility:hidden;` halts SEO and Accessibility audits - pegs CPU by generating 200k+ console notices

Open alystair opened this issue 2 years ago • 12 comments

FAQ

  • [X] Yes, my issue is not about variability or throttling.
  • [X] Yes, my issue is not about a specific accessibility audit (file with axe-core instead).

URL

N/A

What happened?

Please forgive me I have no spare time to create a public repro - my assumption is that certain SEO/accessibility tests are attempting to do something within content-visibility:hidden; subtrees.

pegged

What did you expect?

Only a single warning at most, not hundreds of thousands bogging the computer - which are then wiped after Lighthouse finishes its work anyway...

What have you tried?

This bug occurs when running via Chome DevTools, audits complete without issue via CLI. pointer-events:none; didn't seem to make a difference either ¯_(ツ)_/¯

How were you running Lighthouse?

Chrome DevTools

Lighthouse Version

9.2.0

Chrome Version

Version 99.0.4780.0 (Official Build) canary (64-bit)

Node Version

16.13.0

OS

Windows

Relevant log output

Rendering was performed in a subtree hidden by content-visibility:hidden.

alystair avatar Dec 21 '21 21:12 alystair

Is there at least a stacktrace, if you were to expand?

connorjclark avatar Dec 21 '21 21:12 connorjclark

How would I output something like that when using LH via Chrome DevTools?

alystair avatar Dec 21 '21 21:12 alystair

image

I assume clicking on this may give a relevant stacktrace to help us debug.

connorjclark avatar Dec 21 '21 22:12 connorjclark

I was able to repro running Lighthouse on this page:

<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
</head>
<body>
  <h1>Content</h1> 
  <h1 id="hidden" style="content-visibility: hidden;">Hidden</h1> 
  <script>
    const ITERATIONS = 50;
    const h = document.getElementById('hidden');
    for (let i = 0; i < ITERATIONS; ++i) {
      const el = document.createElement('div');
      el.textContent = 'More hidden content';
      h.appendChild(el);
    }
  </script>
</body>
</html>

It only produces ~1400 messages, but the number of messages scales with the value of ITERATIONS. A page doing a lot more rendering in a hidden subtree could plausibly reach values as high as 250000.

adamraine avatar Dec 21 '21 22:12 adamraine

Thanks so much for the repro Adam! Connor if I clicked it open all that shows up are duplicate copies of the same notification - not useful I'm afraid.

alystair avatar Dec 21 '21 22:12 alystair

I wanted to use element.style.contentVisibility to give the browser some hints on things that I know are off-screen (absolute positioned). Sometimes I have an animation triggered by JS in such a container… and I also run into this information and no way to turn them off:

"Rendering was performed in a subtree hidden by content-visibility:hidden."

worldoptimizer avatar Jun 01 '22 20:06 worldoptimizer

I can confirm this issue on a page with 10k+ elements in a subtree (for example https://de.shoogle.net/brandenburg/berlin/) using content-visibility-hidden: Accessibility and SEO audits both fail.

Does LH really have to investigate every single element in those large subtrees? How about a certain parsing limit (1000?) for subtrees without additional child elements?

midzer avatar Jun 23 '22 22:06 midzer

Also getting this error from DevTools frontend

image

connorjclark avatar Jun 27 '22 20:06 connorjclark

The cleanest fix is probably to rate-limit this error in blink. https://source.corp.google.com/chrome_internal/third_party/blink/renderer/core/display_lock/display_lock_context.cc;l=49?q=%22Rendering%20was%20performed%22

connorjclark avatar Jun 27 '22 20:06 connorjclark

I filed a bug to limit the number of console messages: https://bugs.chromium.org/p/chromium/issues/detail?id=1340037 Does 1,000 console messages max sound like a good number?

josepharhar avatar Jun 27 '22 21:06 josepharhar

1000 still seems like a lot to me. However, Adam's test case above that does ~1400 resulted in LH still able to finish, so in that sense 1000 is great.

connorjclark avatar Jun 27 '22 22:06 connorjclark

Ok, I am making the change in chromium with 500 as the max number of messages

josepharhar avatar Jun 28 '22 17:06 josepharhar

The upstream bug has been fixed, closing

adamraine avatar Jul 13 '23 22:07 adamraine