Frontend Development 9 min read

How to Detect When Users Leave a Page and Safely Send Data

Understanding how to determine whether a user has left or hidden a web page—covering the Page Visibility API, beforeunload/unload events, navigator.sendBeacon, and pagehide/pageshow—enables developers to improve UX, pause resources, and reliably report analytics without sacrificing performance.

JavaScript
JavaScript
JavaScript
How to Detect When Users Leave a Page and Safely Send Data

In modern web development, knowing whether a user is still on the current page is essential for user experience, data analysis, and system performance.

Switch to another browser tab or app (page becomes hidden but not closed).

Minimize the browser window (same as above).

Close the browser tab or the whole browser .

Navigate to a new URL in the current tab .

On mobile, switch to another app or return to the home screen .

Frontend provides several techniques and APIs to detect these scenarios.

Method 1: Page Visibility API (modern preferred)

This standard method detects whether a page is visible to the user, ideal for handling tab switches, window minimization, and similar cases.

Core concepts:

document.hidden

: read‑only property that returns

true

when the page is in the background or minimized, otherwise

false

.

visibilitychange

event: fires on the

document

object when the value of

document.hidden

changes.

Applicable scenarios:

Pause or play video/audio.

Stop or start animations or carousels.

Pause server polling and resume when the page becomes visible again.

Code example:

document.addEventListener('visibilitychange', () => {
  if (document.hidden) {
    // Page became hidden
    console.log('User left the page (tab switch or minimize)');
    // Pause video, animation, etc.
    pauseMyVideo();
  } else {
    // Page became visible
    console.log('User returned to the page');
    // Resume playback
    playMyVideo();
  }
});

Advantages:

Standard, reliable : W3C standard supported by all modern browsers.

Performance‑friendly : Designed to save CPU and battery.

Clear logic : Directly reflects the page’s visibility state.

Disadvantages:

It cannot distinguish a closed tab from a hidden tab; the

visibilitychange

event may fire when the page is hidden, but the reason (switch or close) is unknown.

Method 2: beforeunload and unload events – traditional farewell

These events fire when the user is actually leaving the page (closing, refreshing, or navigating away).

1. beforeunload event

The event triggers just before the window, document, and its resources are unloaded, allowing you to ask the user for confirmation.

Core usage:

Prevent accidental loss of unsaved data; browsers typically show a confirmation dialog.

Code example:

Note: For security reasons, modern browsers do not allow custom text in the confirmation dialog; only a built‑in message is shown.

2. unload event

This event fires after the page has started unloading and is the traditional place for final cleanup.

Code example:

window.addEventListener('unload', () => {
  console.log('User is closing or leaving the page');
  // Warning: operations here may not complete!
  // sendAnalyticsData();
});

Major drawback: The

unload

event is unreliable; browsers do not wait for asynchronous operations (e.g.,

fetch

or

XMLHttpRequest

) to finish, so network requests may be aborted.

Method 3: navigator.sendBeacon() – reliable data reporting

To solve the unreliability of asynchronous requests in

unload

, the W3C introduced the

navigator.sendBeacon()

API.

Core concept:

sendBeacon()

sends a small amount of data asynchronously, and the browser guarantees it will be queued and sent even after the page starts unloading.

Applicable scenario:

Reliably send logs, analytics, or statistics when the user leaves the page.

How to use (often together with unload or pagehide ):

This approach is currently the best practice for sending data during page unload.

Method 4: pagehide and pageshow events – handling back‑forward cache (bfcache)

Modern browsers, especially on mobile, use a back‑forward cache. When a user navigates back, the page may be restored from cache without triggering

unload

. The

pagehide

event fires regardless of bfcache.

Core concepts:

pagehide

event: fires when the user navigates away, whether the page is stored in bfcache or not.

event.persisted

: true if the page is stored in bfcache, false otherwise.

Code example:

window.addEventListener('pagehide', (event) => {
  if (event.persisted) {
    console.log('Page is entering bfcache');
  } else {
    console.log('Page is being unloaded normally');
  }
  // Good time to send a beacon
  navigator.sendBeacon('/log', getAnalyticsData());
});
pagehide

is more reliable than

unload

, especially on mobile, and is recommended for cleanup and data reporting.

Final recommendations

For visibility detection, prefer the Page Visibility API .

For data reporting on exit, use

navigator.sendBeacon()

inside a

pagehide

listener for best compatibility and reliability.

Use

beforeunload

only when necessary to prevent data loss, as it interrupts user interaction.

Avoid

unload

unless you need to run very simple synchronous code; asynchronous network requests are likely to be aborted.

By combining these modern APIs, developers can accurately detect user behavior and build smarter, more user‑friendly experiences without sacrificing performance.

frontendJavaScriptweb performanceapipage visibility
JavaScript
Written by

JavaScript

Provides JavaScript enthusiasts with tutorials and experience sharing on web front‑end technologies, including JavaScript, Node.js, Deno, Vue.js, React, Angular, HTML5, CSS3, and more.

0 followers
Reader feedback

How this landed with the community

login Sign in to like

Rate this article

Was this worth your time?

Sign in to rate
Discussion

0 Comments

Thoughtful readers leave field notes, pushback, and hard-won operational detail here.