Navigator.sendBeacon() - Web APIs 编辑

The navigator.sendBeacon() method asynchronously sends a small amount of data over HTTP to a web server. It’s intended to be used in combination with the visibilitychange event (but not with the unload and beforeunload events).

Syntax

navigator.sendBeacon(url, data);

Parameters

url
The URL that will receive the data. Can be relative or absolute.
data
A ArrayBuffer, ArrayBufferView, Blob, DOMString, FormData, or URLSearchParams object containing the data to send.

Return values

The sendBeacon() method returns true if the user agent successfully queued the data for transfer. Otherwise, it returns false.

Description

This method is for analytics and diagnostics that send data to a server before the document is unloaded, where sending the data any sooner may miss some possible data collection. For example, which link the user clicked before navigating away and unloading the page.

Ensuring that data has been sent during the unloading of a document has traditionally been difficult, because user agents typically ignore asynchronous XMLHttpRequests made in an unload handler.

Historically, this was addressed with some of the following workarounds to delay the page unload long enough to send data to some URL:

  • Submitting the data with a blocking synchronous XMLHttpRequest call in unload or beforeunload event handlers.
  • Creating an <img> element and setting its src in the unload handler. Most user agents will delay the unload to load the image.
  • Creating a no-op loop for several seconds in the unload handler.

All of these methods block unloading the document, which slows down the next navigation. There is nothing the next page can do to avoid this, so the new page seems slow, even though it's the previous page's fault.

The following example shows theoretical analytics code that attempts to submit data to a server with a synchronous XMLHttpRequest in an unload handler. This results in the next page load to be delayed.

window.addEventListener("unload", function logData() {
  var xhr = new XMLHttpRequest();
  xhr.open("POST", "/log", false); // third parameter of `false` means synchronous
  xhr.send(analyticsData);
});

This is what sendBeacon() replaces. With the sendBeacon() method, the data is transmitted asynchronously when the User Agent has an opportunity to do so, without delaying unload or the next navigation. This solves all of the problems with submission of analytics data:

  • The data is sent reliably
  • It's sent asynchronously
  • It doesn't impact the loading of the next page
  • In addition, the code is simpler to write than any of the older techniques!

unload and beforeunload aren’t the right events to use with sendBeacon. Instead, use visibilitychange. See discussion in the comments at Beacon API is broken — and especially see the article at Don't lose user and app state, use Page Visibility, which explains: Use Page Visibility API and execute its session save-and-restore logic whenever visibilitychange state changes… forget that the other events even exist. Treat every transition to visible as a new session: restore previous state, reset your analytics counters, and so on. Then, when the application transitions to hidden, end the session: save user and app state, beacon your analytics, and perform all other necessary work.

You can use the PageLifecycle.js library to deal with current cross-browser inconsistencies in handling of the visibilitychange event and other related behavior; that library normalizes cross-browser differences in event-firing order so that state changes always occur exactly as expected, consistently in all browsers.

For additional best-practices guidance in detail, see the Page Lifecycle API how-to article.

Specifications

SpecificationStatusComment
Beacon
The definition of 'sendBeacon()' in that specification.
Candidate RecommendationInitial definition

Browser compatibility

BCD tables only load in the browser

See also

  • Don't lose user and app state, use Page Visibility is an article which explains in detail why you should use visibilitychange, not beforeunload/unload:
    Use Page Visibility API and execute its session save-and-restore logic whenever visibilitychange state changes. This is the only event your application can count on… forget that the other events even exist. Treat every transition to visible as a new session: restore previous state, reset your analytics counters, and so on. Then, when the application transitions to hidden, end the session: save user and app state, beacon your analytics, and perform all other necessary work.
  • Page Lifecycle API is a how-to article that gives best-practices guidance on handling page-lifecyle behavior in your web applications.
  • PageLifecycle.js is a JavaScript library (<1K gzipped) that deals with cross-browser inconsistencies in page-lifecyle behavior, enabling you to focus on following the best-practices guidance in the Page Lifecycle API article. It normalizes cross-browser differences in event-firing order so that state changes always occur exactly as outlined in the chart and tables in that article (and do so consistently in all browsers).

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。
列表为空,暂无数据

词条统计

浏览:104 次

字数:9035

最后编辑:7年前

编辑次数:0 次

    我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
    原文