Ajax,后退button和DOM更新

如果JavaScript修改了页面A中的DOM,用户导航到页面B,然后点击返回button返回到页面A.对页面A的DOM的所有修改都将丢失,并向用户显示最初从服务器检索到的版本。

它在stackoverflow,reddit和许多其他受欢迎的网站上以这种方式工作。 (尝试添加testing评论到这个问题,然后导航到不同的页面,并回击button回来 – 你的评论将“消失”)

这是有道理的,但一些网站(apple.com,basecamphq.com等)在某种程度上迫使浏览器为用户提供最新的页面状态。 (去http://www.apple.com/ca/search/?q=ipod ,点击顶部的说下载链接,然后点击返回button – 所有的DOM更新将被保留)

哪里来的不一致?

一个答案:其中, 卸载事件导致后退/前进caching失效

一些浏览器将整个网页的当前状态存储在所谓的“bfcache”或“page cache”中。 这使得他们可以在通过后退和前进button进行导航时非常快速地重新呈现页面,并保留DOM和所有JavaScriptvariables的状态。 但是,当页面包含onunload事件时,这些事件可能会使页面进入非function状态,因此页面不会存储在bfcache中,必须重新加载(但可以从标准caching中加载)从头开始渲染,包括运行所有的onload处理程序。 当通过bfcache返回页面时,DOM保持其先前的状态,而不需要触发onload处理程序(因为页面已经加载)。

请注意,关于Cache-Control和其他HTTP标头,bfcache的行为与标准浏览器caching不同。 在许多情况下,即使浏览器不会将其存储在标准caching中,浏览器也会将该页caching在bfcache中。

jQuery自动将一个卸载事件附加到窗口,所以不幸的是,使用jQuery将使您的页面不能存储在bfcache中,以保存DOM并快速返回/转发 。 [更新:这已在jQuery 1.4中修复,以便它只适用于IE]

  • 有关Firefox bfcache的信息
  • 有关Safari页面caching的信息,以及将来如何卸载事件
  • Opera使用快速历史导航
  • Chrome没有页面caching( [1] , [2] )
  • 使用DOM操作和bfcache进行播放的页面:
    • 这个页面将被存储在常规的caching中
    • 这个页面不会,但仍然会被bfcached

我一直在努力使Chrome浏览器像Safari一样行事,唯一的办法是设置Cache-control: no-store在标题中Cache-control: no-store 。 这会强制浏览器在用户按下后退button时从服务器重新获取页面。 不理想,但比显示一个过时的页面更好。

Facebook通过修改Ajax请求的URL中的哈希标识符来记住页面状态。 这些更改logging在浏览器历史logging中,所以当用户单击后退button时,哈希将更改为之前的内容。 那么这就意味着你将需要一些Javascript来监视已经存在的标识符,并在浏览器改变时作出反应。 Andreas Blixt有一个散列监视脚本可用 。

这与散列(#)符号无关。

如果你想检查苹果的HTTP头,那么只需caching页面即可。

使用URL散列/片段标识符是在依赖于Ajax和DOM更新的Web应用程序中挂钩/logging状态的一种非常常见的方式。

查看真正简单的历史项目的一些想法。 可以监视URL的散列更改,而且rsh会考虑到浏览器的差异。

对于任何遇到Rails问题的人来说,你的问题不是bfcache(我以为是这样) – 这是turbolinksgem。 这是如何删除它。

希望这会节省你一些时间,把你的头靠在墙上。

你正在寻找的是一些types的URL哈希pipe理。 URL中的#仅用于客户端。

当你用JS更改后面的状态时,则更新URL中#号的数据。

此外,您还添加了一些types的轮询,以监视哈希是否已更改,并根据哈希中的新数据加载页面的状态。

看看这个:

http://ajaxpatterns.org/Unique_URLs