-
-
Notifications
You must be signed in to change notification settings - Fork 1.7k
ref(replay): Replace lodash.debounce
with custom debounce implementation
#6593
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
Conversation
d543172
to
ee523b8
Compare
size-limit report 📦
|
Just a thought: Intuitively I would have implemented the debounce + With that implementation, I think we wouldn't have to track the remaining time and things like that. Was there a particular reason why you went this route? I might be missing something. |
This was also my first approach and I already implemented it that way. However, I got replay test errors I couldn't explain, which made me look at the lodash implementation more carefully and I decided to give the one-timeout approach a try. Looking back though, I think I might have missed some details in my first implementation so I'll give the 2-timeouts approach another go. In case I don't get anywhere with it, I'll come back to this version. |
6739731
to
b7ae986
Compare
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.
Ok, I've rewritten the debounce implementation with two timers, which should bring down bundle size more than the first version. This required some test adjustments (see my comment)
Also, I moved the function back to the Replay package because we can still pull it into utils if other packages need it.
@@ -54,7 +54,7 @@ describe('Replay (errorSampleRate)', () => { | |||
expect(replay).not.toHaveLastSentReplay(); | |||
|
|||
captureException(new Error('testing')); | |||
jest.runAllTimers(); | |||
jest.advanceTimersByTime(5000); |
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 had to replace a couple of runAllTimers
calls with advanceTimersByTime
because apparently, two timers don't seem to work with runAllTimers
. I'm honestly not entirely sure why and I don't fully understand what might be causing these errors but I think correctness-wise, the debounce function isn't responsible for the test fails.
WDYT, does this change make sense? @billyvg you know these tests best. Is there something I'm missing?
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.
Not sure, I would think runAllTimers
should work -- in any case I think replacing it with advanceTimersByTime
is fine.
Should we replace 5000
(and the default for flushMinDelay
) with a constant?
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.
My theory is that the cancellation of the two timers when one of them is invoked might somehow interfere with whatever runAllTimers
is doing but tbh this is a guess at best.
Should we replace 5000 (and the default for flushMinDelay) with a constant?
Sure can do
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.
Sure can do
On second thought, let's do this in a separate PR, just to not clutter this one. I've checked and we're using 5000 quite a lot in tests.
Edit: #6612
// lodash.debounce is a CJS module, so we need to convert it to ESM first | ||
commonjs(), |
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.
Since build changes are always risky, I double checked NPM packages and CDN bundles and they still work with my test apps.
964a080
to
8b0bc87
Compare
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.
Great work! 🚀
We've been using
lodash.debounce
to debounce the flushing of replay events. This has a number of drawbacks:This PR replaces lodash's implementation with a heavily simplified version of
debounce
which just does what we need it for:wait
time and gate it with amaxWait
valueflush
andcancel
function on the debounced function (analogously to lodash).With this change, we can also get rid of the package patch we introduced in #6551 and of the
commonjs()
plugin in our build process.closes #6553