umami icon indicating copy to clipboard operation
umami copied to clipboard

Accurate Bounce & Time-on-Site Metrics for Long Single-Page Visits (Heartbeat & Engagement Events Support)

Open gpicron opened this issue 5 months ago • 6 comments

Describe the feature or enhancement

Hi Umami team,

The problem

For many content-driven websites (and especially on single-page apps or landing pages), most user engagement happens on a single page, often the homepage. If a visitor spends several minutes reading, scrolling, and interacting—but does not navigate away or reload—the current Umami analytics engine:

  • Counts the visit as a bounce
  • Records time on page as zero seconds

This is because both bounce and time-on-site metrics are calculated using only pageview events, and do not factor in custom events or signals of engagement.

This results in unrealistically high bounce rates and zero time-on-site for highly engaged visitors, which is misleading for site owners and makes it hard to assess actual user engagement.


Proposed Solution

1. Add a native “heartbeat” mechanism to the JS tracker

  • The Umami tracker could automatically send periodic engagement events (e.g., every 15/30 seconds), but only while there is evidence of user activity—such as scroll, mouse movement, keyboard input, or visibility changes.
  • Heartbeats should stop when the tab is hidden, page is unloaded, or there is no further user activity for N seconds.

2. Upgrade backend logic to count these “engagement” events

  • When calculating bounce rate and time-on-site, sessions with at least one “engagement” (heartbeat and others) event in addition to a pageview should not be counted as bounces.
  • Time-on-site for single-page sessions should be calculated as the interval between the first pageview and the last engagement event (mirroring the way Google Analytics and Matomo allow custom events to break bounces).

3. Add a configuration option

  • Site owners should be able to enable/disable this feature for their sites, so those who want to retain the old behavior (pageviews only) can do so.

4. Document recommended practice

  • The tracker documentation should clearly recommend when and how to use this option (e.g., for blogs, documentation sites, SPAs, etc.), and how it affects metrics.

Benefits

  • Much more accurate bounce rate and time-on-site stats for content-rich or SPA sites
  • No need for JS hacks or artificial “pageview” duplication workarounds
  • Cleaner, more reliable engagement analytics—competitive with GA, Plausible, Matomo, etc.

gpicron avatar Jul 19 '25 11:07 gpicron

We’ve also run into the same situation. Most of our projects are SPAs, and after integrating Umami we noticed extremely high bounce rates.

I still need to investigate further, but I’m wondering:

  • would implementing custom events help Umami treat a session as non-bounce?
  • or maybe by adding a snippet to the SPA to manually fire tracker functions? If so what should be called to register a non-bounce as a workaround for the issue?

maxiride avatar Sep 01 '25 08:09 maxiride

Thanks for bringing up this issue. We do plan to add more accurate time tracking similar to what you described.

mikecao avatar Sep 04 '25 05:09 mikecao

@mikecao what’s the team’s position on adjusting the bounce calculation formula?

Currently, wouldn’t it make more sense to define a bounce as a visit with only a single event (pageview)? On the backend, queries could be refactored to count bounces as visits without any events beyond the initial pageview, which shouldn’t require large code changes if I understood the implementation correctly.

I’d be interested in drafting a PR, but before putting in the effort I’d like to confirm if the team is open to this change.

Ref: https://github.com/umami-software/umami/discussions/2544#discussioncomment-14293538

maxiride avatar Sep 04 '25 07:09 maxiride

@maxiride Yes, we should count further events as a non-bounce.

mikecao avatar Sep 08 '25 03:09 mikecao

any update(especially for heartbeat design like https://developer.matomo.org/guides/tracking-javascript-guide#accurately-measure-the-time-spent-on-each-page )? My visit duration and bounce rate are always 0 and 100%... Also I can help with the PR

Nambers avatar Nov 13 '25 03:11 Nambers

any update(especially for heartbeat design like https://developer.matomo.org/guides/tracking-javascript-guide#accurately-measure-the-time-spent-on-each-page )? My visit duration and bounce rate are always 0 and 100%... Also I can help with the PR

I did make a draft PR https://github.com/umami-software/umami/pull/3614 (before the v3 major update, so it needs a complete review since the v3 release) to introduce a better bounce calculation. I didn't address the heartbeat yet.

maxiride avatar Nov 13 '25 08:11 maxiride