【问题标题】:Detecting if a user has left the site [duplicate]检测用户是否离开网站[重复]
【发布时间】:2013-06-17 00:52:08
【问题描述】:

我目前正在开发一个使用 aspx 的网站,我需要检测并记录用户是否即将离开该网站。

如果可能,它将需要捕获以下所有内容,如果用户:

  • 点击浏览器的后退或前进按钮
  • 点击浏览器关闭按钮
  • 点击标签关闭按钮
  • 导航到新网站

【问题讨论】:

  • 你有没有尝试过?
  • “如果用户即将离开网站...”你肯定需要通灵师吗?
  • 这个post 展示了如何在每个页面上进行检查。
  • @T.J.Crowder 他可以使用一种使用网络摄像头的面部检测来检查用户是否看起来快乐......

标签: c# javascript jquery asp.net browser


【解决方案1】:

如果远程可行,请更改要求,因为这会导致不太理想的用户体验。

至少在某些浏览器上,您可以从 onbeforeunload 处理程序执行 同步 ajax 请求,以向您的服务器发送用户正在离开页面的信息:

window.onbeforeunload = function() {
    $.ajax({
        url:   "/path/to/page",
        data:  {/* ...stuff... */,
        async: false // <== Option is being removed soon
    });
};

我说这是一个糟糕的用户体验的原因是,由于 ajax 调用是同步,它会阻止它们,并且在某些浏览器上相当侵入(整个事情在等待请求时锁定去完成)。这也是为什么它可能不是可靠的跨浏览器。

jQuery 团队将在某个时候从ajax 中删除async 选项。它仍然存在于底层的 XMLHttpRequest 对象中,因此当发生这种情况时,您可以直接使用它。


用户离开网站的事实在网络服务器日志中已经很明显了,尽管您无法确定他们在最终页面上停留了多长时间。如果“他们在最后一页上花了多长时间”是非常重要的信息,而不是在他们离开时阻止他们(并且依赖于可能不是完全可靠的跨浏览器的东西),你当它们仍在页面上时,可以使用背景“ping”。随着时间的推移,最好将 ping 间隔越来越远。

例如,当页面加载时:

(function($) {
    var SECOND = 1000;
    var MINUTE = 60000;
    var arrived = +new Date();
    var pingTimes = {
        0:      10 * SECOND, // Every 10 seconds in first minute
        1:      30 * SECOND, // Every 30 seconds in second minute
        2:      45 * SECOND, // Every 45 seconds in third minute
        other:  60 * SECOND, // Every minute otherwise
        long:   10 * MINUTE  // Every 10 minutes if they've been here a long time
    };

    nextPing();

    function ping() {
        $.ajax({
            url:     "/path/to/ping/page",
            method:  "POST",
            success: nextPing,
            error:   nextPing
        });
    }

    function nextPing() {
        var elapsed, pingTime;

        // Get the # of full minutes they've been here
        elapsed = Math.floor((new Date() - arrived) / MINUTE);

        // If it's been a long time, use `pingTimes.long`.
        // Otherwise, use the time from the table or the default.
        pingTime = elapsed > 15 * MINUTE ? pingTimes.long : (pingTimes[elapsed] || pingTimes.other);

        setTimeout(ping, pingTime);
    }

})(jQuery);

【讨论】:

  • 这并没有像你建议的那样在 FF 上真正起作用:> 作为一种解决方法:stackoverflow.com/a/17188743/1414562 对不起,丑陋的黑客或使用提示消息跨度>
  • 顺便说一句,async false 仅适用于 DOC 之后的延迟对象,我仍然不知道这是否意味着 jqXHR 的选项仍将被支持
  • @roasted:我的印象是“不是”。
  • @roasted:对 Firefox 有好处! :-)
猜你喜欢
  • 2015-01-10
  • 2018-02-12
  • 1970-01-01
  • 1970-01-01
  • 2021-09-20
  • 2016-02-29
  • 2011-05-01
  • 1970-01-01
  • 2011-03-14
相关资源
最近更新 更多