Skip to content

feat(tracing): Expose cancelIdleTimeout and add option to make it permanent #7236

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

Merged
merged 13 commits into from
Mar 7, 2023

Conversation

krystofwoldrich
Copy link
Contributor

@krystofwoldrich krystofwoldrich commented Feb 21, 2023

This relates to UI Event Transactions and its implementation in RN.

Public cancelIdleTimeout with a permanent option will be used in case of the scenario: Same UI element with the different event. We want to finish the current UI Event Transaction by the end of the last span and we don't need the IdleTrasaction to wait anymore as the newly created span will be assigned to the newly started transaction for the different user interaction event.

Context:

Todo

  • Write tests for new permanent cancel behavior

@github-actions
Copy link
Contributor

Replay SDK metrics 🚀

    Plain +Sentry +Replay
Revision Value Value Diff Ratio Value Diff Ratio
LCP This PR f5b7b10 109.16 ms 141.26 ms +32.10 ms +29.41 % 163.53 ms +54.37 ms +49.81 %
Previous 12e34d4 120.79 ms 144.24 ms +23.45 ms +19.42 % 149.36 ms +28.57 ms +23.65 %
CLS This PR f5b7b10 0.06 ms 0.06 ms +0.00 ms +0.06 % 0.06 ms -0.00 ms -0.38 %
Previous 12e34d4 0.06 ms 0.06 ms -0.00 ms -0.10 % 0.06 ms +0.00 ms +0.09 %
CPU This PR f5b7b10 24.87 % 21.92 % -2.95 pp -11.84 % 29.52 % +4.65 pp +18.70 %
Previous 12e34d4 25.72 % 25.96 % +0.24 pp +0.93 % 31.49 % +5.77 pp +22.42 %
JS heap avg This PR f5b7b10 1.94 MB 1.99 MB +54.07 kB +2.79 % 2.86 MB +924.77 kB +47.69 %
Previous 12e34d4 1.94 MB 2.06 MB +116.91 kB +6.03 % 2.87 MB +930.12 kB +47.96 %
JS heap max This PR f5b7b10 2.3 MB 2.56 MB +253.16 kB +10.99 % 3.36 MB +1.05 MB +45.63 %
Previous 12e34d4 2.32 MB 2.58 MB +259.14 kB +11.17 % 3.36 MB +1.04 MB +44.66 %
netTx This PR f5b7b10 0 B 0 B 0 B n/a 2.21 kB +2.21 kB n/a
Previous 12e34d4 0 B 0 B 0 B n/a 2.26 kB +2.26 kB n/a
netRx This PR f5b7b10 0 B 0 B 0 B n/a 41 B +41 B n/a
Previous 12e34d4 0 B 0 B 0 B n/a 41 B +41 B n/a
netCount This PR f5b7b10 0 0 0 n/a 1 +1 n/a
Previous 12e34d4 0 0 0 n/a 1 +1 n/a
netTime This PR f5b7b10 0.00 ms 0.00 ms 0.00 ms n/a 121.33 ms +121.33 ms n/a
Previous 12e34d4 0.00 ms 0.00 ms 0.00 ms n/a 109.67 ms +109.67 ms n/a

Previous results on branch: develop

RevisionLCPCLSCPUJS heap avgJS heap maxnetTxnetRxnetCountnetTime
12e34d4+28.57 ms+0.00 ms+5.77 pp+930.12 kB+1.04 MB+2.26 kB+41 B+1+109.67 ms
c46c56c+65.45 ms-0.00 ms+5.38 pp+930.26 kB+1.07 MB+2.21 kB+41 B+1+91.29 ms
7f4c4ec+56.64 ms-0.00 ms+5.57 pp+927.42 kB+1.06 MB+2.21 kB+41 B+1+110.83 ms
00d2360+55.18 ms+0.00 ms+2.23 pp+934.14 kB+1.05 MB+2.22 kB+41 B+1+71.65 ms

*) pp - percentage points - an absolute difference between two percentages.
Last updated: Tue, 21 Feb 2023 10:34:55 GMT

@github-actions
Copy link
Contributor

github-actions bot commented Feb 21, 2023

size-limit report 📦

Path Size
@sentry/browser - ES5 CDN Bundle (gzipped + minified) 20.13 KB (+0.01% 🔺)
@sentry/browser - ES5 CDN Bundle (minified) 62.55 KB (0%)
@sentry/browser - ES6 CDN Bundle (gzipped + minified) 18.76 KB (0%)
@sentry/browser - ES6 CDN Bundle (minified) 55.53 KB (0%)
@sentry/browser - Webpack (gzipped + minified) 20.5 KB (0%)
@sentry/browser - Webpack (minified) 66.99 KB (0%)
@sentry/react - Webpack (gzipped + minified) 20.53 KB (0%)
@sentry/nextjs Client - Webpack (gzipped + minified) 48.28 KB (+0.16% 🔺)
@sentry/browser + @sentry/tracing - ES5 CDN Bundle (gzipped + minified) 27.26 KB (+0.22% 🔺)
@sentry/browser + @sentry/tracing - ES6 CDN Bundle (gzipped + minified) 25.52 KB (+0.25% 🔺)
@sentry/replay ES6 CDN Bundle (gzipped + minified) 43.12 KB (+0.14% 🔺)
@sentry/replay - Webpack (gzipped + minified) 37.15 KB (+0.14% 🔺)
@sentry/browser + @sentry/tracing + @sentry/replay - ES6 CDN Bundle (gzipped + minified) 60.92 KB (+0.2% 🔺)
@sentry/browser + @sentry/replay - ES6 CDN Bundle (gzipped + minified) 54.24 KB (+0.1% 🔺)

@AbhiPrasad
Copy link
Member

Can you add some more details about why we need restartIdleTimeout to make this work? (for future readers)

@krystofwoldrich krystofwoldrich changed the title feat(idletransaction): Add restartIdleTimeout to the public interface feat(idletransaction): Expose idleTimeout management functions Feb 21, 2023
@krystofwoldrich
Copy link
Contributor Author

@AbhiPrasad I've updated the readme with more detail.

@krystofwoldrich krystofwoldrich marked this pull request as ready for review February 27, 2023 13:25
@krystofwoldrich
Copy link
Contributor Author

This is ready for feedback. 🙏

@0Calories
Copy link
Contributor

Hi @krystofwoldrich! 👋

The Performance team is also working on UI event transactions for Frontend transactions this quarter, and we had a question about this:

For what reason do we want to keep the transaction running if the same UI element is being interacted with? This might not result in the best product experience, because imagine a scenario where a user repeatedly clicks on an element which fetches data -> the transaction will end up extremely large. Transactions like this won't be a good representation of the spans involved in an interaction -> paint loop.

@krystofwoldrich
Copy link
Contributor Author

krystofwoldrich commented Feb 28, 2023

👋 @0Calories Thanks for the reply.

I imagine a refresh scenario, a user is tapping a refresh button. In that case, I would like to see all the requests in one transaction as they are related to each other. If the tapping of the button would cause multiple transactions to be created we would lose the information about the sequence. There might be some broken requests before the first successful one.

After the idle timeout, the transaction will be finished and on the next tap, a new one will be created.

The scenarios are described here. Maybe @philipphofmann knows more reasons why to keep the same interaction with the same element in one transaction.

@0Calories
Copy link
Contributor

@krystofwoldrich I had read all of the scenarios and most of them make sense to me 👍

Regarding your scenario with a user repeatedly tapping a refresh button, I can see why this would be valuable. However, the Performance product was built around the idea that one transaction would represent a singular action (i.e pageload, navigation, click), and excessive data stored within interactions would muddle up our metrics and make it harder to understand the true overall performance of that action.

The scenario you describe sounds like it would better served by Sessions / Replay, since it already captures all interactions a user is performing within a session

@krystofwoldrich
Copy link
Contributor Author

@0Calories So you would treat Scenario: Same UI element with same event as Scenario: Same UI element with different event, meaning finish the transaction started by the first touch and start a new one?

@krystofwoldrich
Copy link
Contributor Author

But regardless of this one scenario, we need to expose cancelIdleTimeout and then restartIdleTimeout also makes sense.

@romtsn
Copy link
Member

romtsn commented Mar 1, 2023

@0Calories we've mainly decided to do that to save user's transaction quota if someone is rage-tapping on a button, for example. It can indeed result in endless transactions, but those we should prevent with a finalTimeout (hard deadline). Though I'm not opposed to changing this behavior and finish the previous transaction as cancelled, if a user clicks on the same button again. We should just align with @philipphofmann @brustolin and @marandaneto on that.

Btw, this is also the reason we're dropping child-less transactions now - to save the transaction quota, as these transactions don't really bring any value if there are no spans in them. With introduction of INP this may change though.

@philipphofmann
Copy link
Member

We added UI event transactions to collect more spans. Our SDKs can't reliably detect the end of a UI event transaction. If a user clicks a button multiple times, we thought it makes sense not to finish the ongoing transaction cause it doesn't mark the finish point of it, while a different event most likely does. We can reconsider this behavior, though. Now that I think about it again, I think the same behavior as Scenario: Same UI element with different event would make more sense.

@0Calories
Copy link
Contributor

I do think that Scenario: Same UI element with different event makes more sense for both of these cases!

@romtsn on the topic of transaction quota being consumed by users who could rage click, I agree this is a valid concern, but I was thinking that user interaction transactions would be sampled at a much lower rate to prevent this problem. We haven't yet thought into how this would tie into DS, but at the very least I was thinking we could have an SDK level sample rate for interaction transactions that could be configurable, but would default to a low rate like 0.05

Also, child-less transactions should definitely be discarded — I don't think they'd be useful even for INP.

@romtsn
Copy link
Member

romtsn commented Mar 1, 2023

Also, child-less transactions should definitely be discarded — I don't think they'd be useful even for INP.

I think @k-fish mentioned that we actually should still capture them in case INP is under the bad threshold. I think it makes sense, because if there are some operations triggered by the user interaction that we don't capture as spans (some heavy animations, or just some computation on the main thread, etc.), it would still contribute to bad INP, despite being child-less. But Kevan to confirm.

@krystofwoldrich
Copy link
Contributor Author

krystofwoldrich commented Mar 2, 2023

Let's move the UI Event Transactions changes to the develop docs so this PR is not blocked.

@k-fish
Copy link
Member

k-fish commented Mar 2, 2023

Sorry for the late response 🙏

finish the previous transaction as cancelled, if a user clicks on the same button again

I like this, since that's exactly what's happening, who knows if a rage click on a slow loading interaction kills the INP interaction? It's good to have them split up instead of multiple actions (click etc.) inside the same transaction.

I think @k-fish mentioned that we actually should still capture them in case INP is under the bad threshold

Yes 100%, if it's the INP interaction transaction we have to send it in since otherwise we won't be properly collecting that measurement, and it's a good indication we should have spans there. For other span-less interactions I don't think it matters as much since they aren't very interesting, ideally if the browser is reporting that it's a long delay between action and paint, even if it doesn't have a long task or http request it still means something is happening that might be concern, so we might want to revisit this later, but for now this works (letting the child-less INP interaction through).

edit: sorry clicked enter which closed this prematurely 😆

Aside:

  • Having to collect the transaction because of INP is yet another indication we should probably try to allow ingesting metrics without transactions in the future, since it would be nice to not have to always make this decision to send the transaction if it's otherwise poorly actionable (no spans)

@philipphofmann
Copy link
Member

I created an issue to change this behaviour on Android and iOS getsentry/team-mobile#85

@krystofwoldrich
Copy link
Contributor Author

Can someone review this? It's blocking this RN PR:

@romtsn
Copy link
Member

romtsn commented Mar 6, 2023

ideally if the browser is reporting that it's a long delay between action and paint, even if it doesn't have a long task or http request it still means something is happening that might be concern

Agree! On mobile we could actually already point people to profiles and from there it should be rather clear what's going on, even if there are no child spans.

@AbhiPrasad AbhiPrasad changed the title feat(idletransaction): Expose idleTimeout management functions feat(tracing): Expose idleTimeout management functions Mar 7, 2023
@krystofwoldrich
Copy link
Contributor Author

Thank you 🙂

@krystofwoldrich krystofwoldrich changed the title feat(tracing): Expose idleTimeout management functions feat(tracing): Expose cancelIdleTimeout and add option to make it permanent Mar 7, 2023
@krystofwoldrich krystofwoldrich enabled auto-merge (squash) March 7, 2023 15:10
@krystofwoldrich krystofwoldrich merged commit 5e4e719 into develop Mar 7, 2023
@krystofwoldrich krystofwoldrich deleted the kw-ui-idle-transaction branch March 7, 2023 15:31
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

6 participants