-
Notifications
You must be signed in to change notification settings - Fork 9.4k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
core(fr): convert trace-elements gatherer #12442
Conversation
@@ -308,10 +314,28 @@ class TraceElements extends Gatherer { | |||
} | |||
} | |||
|
|||
await driver.sendCommand('Animation.disable'); | |||
session.sendCommand('Animation.disable'); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
should these be in stopInstrumentation
? does it matter?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
this is tricky, I'm assuming that Animation
domain needs to remain enabled for Animation.resolveAnimation
to work?
if not, then yeah definitely move to stopInstrumentation
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
why was the await
removed though? I seem to recall bad things happening in LR if there are unhandled promise rejections
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
alternate option: collect animation id -> name mapping by listening for Animation.animationCreated
and fetching at the end of stopInstrumentation
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I tried this and yeah, Animation
domain needs to be enabled. When I moved it back I forgot the await
though haha.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
what do you think about the alternate option @adamraine? it's more code and possible more animation resolution at the benefit of more idiomatic "instrumentation" followed by the artifact computation.
I could see us going either way, just interested in your thoughts.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
We're still going to have some "instrumentation" in getArtifact
when we call Runtime.callFunctionOn
. Some less destructive options I came up with:
- Remove the call to
Animation.disable
entirely - Call
Animation.disable
instopInstrumentation
, then reenable it forgetArtifact
.
I'll give your suggestion a shot though to see how destructive it is.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
So I went a little deep down this rabbit hole. I had trouble resolving the animation name from animationCreated
events, however I found that we can just get the animation name directly from animationStarted
events. Kinda wish I had thought of this when I first added animated elements to TraceElements
😆
@@ -159,7 +159,7 @@ describe('Fraggle Rock API', () => { | |||
const {lhr} = result; | |||
const {auditResults, failedAudits, erroredAudits} = getAuditsBreakdown(lhr); | |||
// TODO(FR-COMPAT): This assertion can be removed when full compatibility is reached. | |||
expect(auditResults.length).toMatchInlineSnapshot(`103`); | |||
expect(auditResults.length).toMatchInlineSnapshot(`105`); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
hm, didn't bump the timespan one? oh right trace isn't supported in timespan yet 👍
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
nice! I like this a lot 👍 feels exactly as it would be if we wrote it with FR in mind from the first place :)
* @param {LH.Gatherer.FRTransitionalContext} context | ||
*/ | ||
async stopInstrumentation(context) { | ||
if (this.onAnimationCreated) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
could avoid this if
by moving onAnimationCreated
to class property next to the map, but understand if you'd rather keep the impl inside startInstrumentation
:)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
why not a private function?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Needed access to this
, I wound up defining it in a new constructor.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
See JSUsage gatherer constructor for how to use this
in class callback functions.
* @param {LH.Gatherer.FRTransitionalContext} context | ||
*/ | ||
async stopInstrumentation(context) { | ||
if (this.onAnimationCreated) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
why not a private function?
constructor() { | ||
super(); | ||
this._onAnimationStarted = this._onAnimationStarted.bind(this); | ||
} | ||
|
||
/** @param {LH.Crdp.Animation.AnimationStartedEvent} args */ | ||
_onAnimationStarted({animation: {id, name}}) { | ||
if (name) this.animationIdToName.set(id, name); | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
constructor() { | |
super(); | |
this._onAnimationStarted = this._onAnimationStarted.bind(this); | |
} | |
/** @param {LH.Crdp.Animation.AnimationStartedEvent} args */ | |
_onAnimationStarted({animation: {id, name}}) { | |
if (name) this.animationIdToName.set(id, name); | |
} | |
/** @param {LH.Crdp.Animation.AnimationStartedEvent} args */ | |
_onAnimationStarted = ({animation: {id, name}}) => { | |
if (name) this.animationIdToName.set(id, name); | |
} |
FWIW, this was my suggestion if you're going to separate already :)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can't do it, need access to this
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
that shouldn't be a problem
$ cat > foo.js <<EOF
class Foo {
x = 1
foo = () => this.x
}
console.log(new Foo().foo())
const detached = new Foo().foo
console.log(detached()) // this works too :)
EOF
$ node foo.js
1
1
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Unfortunately eslint
disagrees. I guess it technically works though.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
That's because they don't support class fields eslint/eslint#14343
Adds support for
TraceElements
gatherer in FR.Ref #11313