简体   繁体   English

Google Analytics,跟踪页面卸载事件

[英]Google Analytics, track page unload event

I'm trying to accomplish tracking an event when a user leaves the page with Google Analytics (analytics.js).当用户使用 Google Analytics (analytics.js) 离开页面时,我试图完成对事件的跟踪。 Though it is unknown how the user will leave, it may be because of an external link or just closing the tab.虽然不知道用户将如何离开,但可能是因为外部链接或只是关闭了选项卡。 So my thought was to hook onto the beforeunload or unload event and then:所以我的想法是挂钩 beforeunload 或 unload 事件,然后:

window.addEventListener("beforeunload", function() {
    ga('send', 'event', 'some', 'other', 'data');
});

Now my question is, will the request to the GA server be synchronous or can I somehow force that behaviour with the hitCallback property?现在我的问题是,对 GA 服务器的请求是同步的还是我可以以某种方式使用hitCallback属性强制这种行为? If that is not possible, how else can I achieve this?如果这是不可能的,我还能如何实现这一目标? Preferably without having to set a timeout or fixed waiting time for the user!最好无需为用户设置超时或固定等待时间!

There is a way to make sure the request will be sent to GA.有一种方法可以确保将请求发送到 GA。 Simo Ahava wrote a very good blog post titled - Simo Ahava 写了一篇非常好的博客文章,标题为——
" Leverage useBeacon And beforeunload In Google Analytics ". 利用 useBeacon 和 beforeunload 在 Google Analytics 中”。

Utilizing the brilliant sendBeacon solution.利用出色的sendBeacon解决方案。 Here's quote which addresses the selected answer of this question:这是引用此问题的选定答案的引文:

User agents will typically ignore asynchronous XMLHttpRequests made in an unload handler.用户代理通常会忽略在卸载处理程序中生成的异步 XMLHttpRequest。 To solve this problem, analytics and diagnostics code will typically make a synchronous XMLHttpRequest in an unload or beforeunload handler to submit the data.为了解决这个问题,分析和诊断代码通常会在 unload 或 beforeunload 处理程序中生成一个同步的 XMLHttpRequest 来提交数据。 The synchronous XMLHttpRequest forces the User Agent to delay unloading the document, and makes the next navigation appear to be slower.同步 XMLHttpRequest 强制用户代理延迟卸载文档,并使下一个导航看起来更慢。 There is nothing the next page can do to avoid this perception of poor page load performance.下一页无法避免这种页面加载性能不佳的感觉。

There are other techniques used to ensure that data is submitted.还有其他技术可用于确保提交数据。 One such technique is to delay the unload in order to submit data by creating an Image element and setting its src attribute within the unload handler.其中一种技术是通过创建 Image 元素并在卸载处理程序中设置其 src 属性来延迟卸载以提交数据。 As most user agents will delay the unload to complete the pending image load, data can be submitted during the unload.由于大多数用户代理会延迟卸载以完成挂起的图像加载,因此可以在卸载期间提交数据。 Another technique is to create a no-op loop for several seconds within the unload handler to delay the unload and submit data to a server.另一种技术是在卸载处理程序中创建一个持续几秒钟的无操作循环,以延迟卸载并将数据提交到服务器。

Not only do these techniques represent poor coding patterns, some of them are unreliable and also result in the perception of poor page load performance for the next navigation.这些技术不仅代表糟糕的编码模式,其中一些技术也不可靠,还会导致下一次导航的页面加载性能不佳。

The request will not be synchronous, GA tracking calls never are.请求不会同步,GA 跟踪调用永远不会同步。

The only way to ensure the call completes is to make sure the page stays open long enough - for an event on a link you would normally do this with a timeout potentially combined with a hitCallback, as you mentioned.确保调用完成的唯一方法是确保页面保持打开的时间足够长 - 对于链接上的事件,您通常会使用超时来执行此操作,这可能与您提到的 hitCallback 结合使用。

The only way to keep a window open when the user closes a tab is to return a value from your beforeunload handler, which will prompt a "Confirm Navigation" alert.当用户关闭选项卡时保持窗口打开的唯一方法是从您的 beforeunload 处理程序返回一个值,这将提示“确认导航”警报。 That would be a really bad solution just to track a GA event, obviously.显然,仅仅为了跟踪 GA 事件,这将是一个非常糟糕的解决方案。

Set transport to beacon , with ga : 使用gatransport设置beacon

window.addEventListener("beforeunload", function() {
    ga('send', 'event', 'page_unload', 'bye bye', {transport: 'beacon'});
});

Or transport_type to beacon , with gtag :transport_typebeacon ,使用gtag

window.addEventListener("beforeunload", function() {
  gtag('event', 'page_unload', {
    'event_category': 'my cat',
    'event_label': 'my label',
    'transport_type': 'beacon'  // <--- important part here
  });
});

For what is worth, beacon should become the default transport mode anyway.无论如何,信标应该成为默认的传输模式。 As of 2020-09 :截至2020-09 年

Currently, gtag.js only uses navigator.sendBeacon if the transport mechanism is set to 'beacon'.目前,如果传输机制设置为“信标”,gtag.js 仅使用 navigator.sendBeacon。 However, in the future, gtag.js will likely switch to using 'beacon' as the default mechanism in browsers that support it.但是,在未来,gtag.js 可能会在支持它的浏览器中切换到使用“信标”作为默认机制。

As pointed out by tomconnors, this does NOT work.正如 tomconnors 所指出的,这不起作用。 I'm leaving the answer to help warn anyone thinking about doing it this way.我留下答案是为了帮助警告任何考虑这样做的人。 Beacon transport is probably the way to go, but wasn't widely supported at the time of the original answer.信标传输可能是要走的路,但在最初的答案时并没有得到广泛支持。

You can wait for a hit to be sent to Google Analytics in the page onunload , but it does require a busy loop.您可以在onunload页面中等待将onunload发送到 Google Analytics,但这确实需要一个繁忙的循环。 In my case this did not delay user navigation, as the page was a popup window that is dedicated to a webapp.就我而言,这并没有延迟用户导航,因为该页面是专用于 web 应用程序的弹出窗口。 I'd be more concerned about doing this inline with normal web page navigation.我会更关心在普通网页导航中执行此操作。 Still, I had to take 2 showers to get the filth off after committing code with a busy loop.尽管如此,在使用繁忙的循环提交代码后,我不得不洗两次澡才能清除污垢。

var MAX_WAIT_MS = 1000;
var _waitForFinalHit = false;

function recordFinalHit() {
    _waitForFinalHit = true;

    ga('send', 'event', 'some', 'other', 'data', {
        'hitCallback': function() {
            _waitForFinalHit = false;
        }
    });
}

function waitForFinalHit() {
    var waitStart = new Date().getTime();
    while (_waitForFinalHit
        && (new Date().getTime() - waitStart < MAX_WAIT_MS)) { }
}

function myOnUnload() {
    recordFinalHit();
    // Do your other final stuff here...
    waitForFinalHit();
}

window.onunload = myOnUnload;

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM