core(driver): use execution context isolation when necessary#3500
core(driver): use execution context isolation when necessary#3500patrickhulce merged 5 commits intomasterfrom
Conversation
1a3eaf8 to
03c5e29
Compare
lighthouse-core/gather/driver.js
Outdated
| }).then(result => { | ||
| }; | ||
|
|
||
| if (useIsolation && typeof this._isolatedExecutionContextId === 'number') { |
There was a problem hiding this comment.
if isolation is requested but there is no contextId... should we throw?
There was a problem hiding this comment.
I had this originally to check for leaks and it seemed ok, but it's definitely possible and seemed bad to tank the run because it since it won't matter most of the time
perhaps something to add to sentry though when it lands?
There was a problem hiding this comment.
Seems like we should be able to figure out definitively if it's possible to reach here without having created a new context? Then future violations of this can complain loudly by throwing (alternatively, see other comment about lazily calling _createIsolatedWorld())
There was a problem hiding this comment.
going the lazy route 👍
| DIR="$( cd "$( dirname "${BASH_SOURCE[0]}" )" && pwd )" | ||
|
|
||
| for d in "$DIR"/*/ ; do | ||
| bash "${d}run-tests.sh" |
There was a problem hiding this comment.
there are a few other ways to do this, but the benefit of this approach is the failures won't be silent. :)
sgtm
There was a problem hiding this comment.
can we just manually list the files in here? If I'm messing with some smoke tests it's a lot easier to comment out lines in one place by name than look up where the individual run-tests file is
also it'd probably be better to just get rid of all the run-tests.sh files since they're all exactly the same except for the expectations and config filename strings :)
There was a problem hiding this comment.
will nuke 'em all in a follow up PR and improve this file here 👍
brendankenny
left a comment
There was a problem hiding this comment.
for future calls to evaluateAsync, how does one know if it should be isolated or not? Try the default out and if it fails (returns nothing when expected something?) try turning off isolation? :)
Is there anything we can do for these non-isolated ones (js-libraries, function callsites, and check for quiet) to make them isolated? I guess it's just unclear what's isolated and what's not if the axe checks work but js-library-detector does not
| DIR="$( cd "$( dirname "${BASH_SOURCE[0]}" )" && pwd )" | ||
|
|
||
| for d in "$DIR"/*/ ; do | ||
| bash "${d}run-tests.sh" |
There was a problem hiding this comment.
can we just manually list the files in here? If I'm messing with some smoke tests it's a lot easier to comment out lines in one place by name than look up where the individual run-tests file is
also it'd probably be better to just get rid of all the run-tests.sh files since they're all exactly the same except for the expectations and config filename strings :)
lighthouse-core/gather/driver.js
Outdated
| */ | ||
| evaluateAsync(expression) { | ||
| evaluateAsync(expression, options) { | ||
| const {useIsolation = true} = options || {}; |
There was a problem hiding this comment.
the double defaults here is kind of confusing. Maybe move the {} default for options to the params?
lighthouse-core/gather/driver.js
Outdated
| }).then(result => { | ||
| }; | ||
|
|
||
| if (useIsolation && typeof this._isolatedExecutionContextId === 'number') { |
There was a problem hiding this comment.
Seems like we should be able to figure out definitively if it's possible to reach here without having created a new context? Then future violations of this can complain loudly by throwing (alternatively, see other comment about lazily calling _createIsolatedWorld())
lighthouse-core/gather/driver.js
Outdated
| }) | ||
| .then(_ => waitForLoad && this._waitForFullyLoaded(pauseAfterLoadMs, | ||
| networkQuietThresholdMs, cpuQuietThresholdMs, maxWaitMs)) | ||
| .then(_ => this._createIsolatedWorld()) |
There was a problem hiding this comment.
Would there be downsides to clearing on all navigations (as above) but calling _createIsolatedWorld lazily on next evaluateAsync() when _isolatedExecutionContextId isn't defined?
discussed offline, decided to switch the default to useIsolation=false and just opt-in a11y for now |
03c5e29 to
2779925
Compare
2779925 to
9c446ec
Compare
9c446ec to
a860423
Compare
|
PTAL :) |
paulirish
left a comment
There was a problem hiding this comment.
this lgtm in general. just nits
| <video id="video-description"></video> | ||
| </section> | ||
| <script> | ||
| // axe fails if `define` is present but misbehaves, create a bogus implementation to exercise our |
There was a problem hiding this comment.
I don't totally get this. I'll ask you in person if i'm interpreting it correctly, but it could probably use a slightly more extended comment. :)
There was a problem hiding this comment.
// axe fails if a different UMD loader like almond.js is used on the page, see https://github.com/GoogleChrome/lighthouse/issues/2505
// We can simulate this behavior by defining a similarly misbehaving `define` function.
sounds better?
| settings: { | ||
| onlyCategories: [ | ||
| 'accessibility', | ||
| ], |
There was a problem hiding this comment.
since we were talking about it yesterday... is it possible to reuse an existing smoketest?
There was a problem hiding this comment.
I know we were literally just talking about not adding more yesterday but of all the testers that should probably get their own one, I think a11y is one of them 😆
maybe we can start by reducing DBW's 6 passes instead? :)
|
|
||
| /** | ||
| * @return {!Promise<number>} | ||
| */ |
There was a problem hiding this comment.
_acquireIsolatedContextId() ?
There was a problem hiding this comment.
discussed offline, Paul's a huge fan of getOrCreate now 🚗 🎏 🎉
lighthouse-core/gather/driver.js
Outdated
|
|
||
| return this.sendCommand('Page.getResourceTree') | ||
| .then(data => { | ||
| const frameId = data.frameTree.frame.id; |
There was a problem hiding this comment.
let's give it a worldName while we're at it.
| } | ||
|
|
||
| return this.sendCommand('Page.getResourceTree') | ||
| .then(data => { |
| * Evaluate an expression in the context of the current page. | ||
| * Evaluate an expression in the context of the current page. If useIsolation is true, the expression | ||
| * will be evaluated in a content script that has access to the page's DOM but whose JavaScript state | ||
| * is completely separate. |
| * Evaluate an expression in the given execution context; an undefined contextId implies the main | ||
| * page without isolation. | ||
| * @param {string} expression | ||
| * @param {number|undefined} contextId |
There was a problem hiding this comment.
can be {number=} FWIW
There was a problem hiding this comment.
yeah just seemed more explicit since something is always passed in but doesn't matter to me
|
|
||
| /** | ||
| * @return {!Promise<number>} | ||
| */ |
There was a problem hiding this comment.
maybe a jsdoc comment here that the contextId won't persist past a page load (so should be cleared and recreated)?
There was a problem hiding this comment.
good call, done
closes #2511
fixes #2505