web-dev-qa-db-ja.com

Ajax、戻るボタン、DOMの更新

JavaScriptがページAのDOMを変更する場合、ユーザーはページBに移動し、戻るボタンを押してページAに戻ります。ページAのDOMへのすべての変更は失われ、ユーザーはサーバーから最初に取得されたバージョンを提示されます。

Stackoverflow、reddit、その他の多くの人気Webサイトでそのように機能します。 (この質問にテストコメントを追加してから、別のページに移動し、戻るボタンを押して戻ります-コメントは「消えます」)

これは理にかなっていますが、一部のWebサイト(Apple.com、basecamphq.comなど)では、ブラウザにユーザーにページの最新の状態を強制的に提供させています。 ( http://www.Apple.com/ca/search/?q=iPod に移動し、上部の[ダウンロード]リンクをクリックしてから[戻る]ボタンをクリックします-すべてのDOM更新が保持されます)

矛盾はどこから来たのですか?

112
lubos hasko

1つの答え:特に、アンロードイベントにより、バック/フォワードキャッシュが無効になります

一部のブラウザは、Webページ全体の現在の状態をいわゆる「bfcache」または「ページキャッシュ」に保存します。これにより、[戻る]ボタンと[進む]ボタンを使用してナビゲートするときにページを非常に迅速に再レンダリングし、DOMとすべてのJavaScript変数の状態を保持できます。ただし、ページにonunloadイベントが含まれる場合、これらのイベントによりページが機能しない状態になる可能性があるため、ページはbfcacheに保存されず、再読み込みする必要があります(ただし、標準キャッシュから読み込むことができます)。すべてのonloadハンドラーの実行を含む、ゼロからレンダリングされます。 bfcacheを介してページに戻ると、DOMは以前の状態を維持します。onloadハンドラーを起動する必要はありません(ページが既にロードされているため)。

Cache-Controlおよびその他のHTTPヘッダーに関して、bfcacheの動作は標準のブラウザキャッシュとは異なることに注意してください。多くの場合、ブラウザはページを標準キャッシュに保存しなくてもbfcacheにページをキャッシュします。

jQueryは自動的にアンロードイベントをウィンドウにアタッチするため、残念ながらjQueryを使用すると、DOMの保存と早戻し/早送りのためにbfcacheにページが保存されなくなります。 [更新:これはIEにのみ適用されるようにjQuery 1.4で修正されました]

105
Miles

私はSafariのように振る舞うためにChromeを取得しようとしていますが、それが機能することを発見した唯一の方法はCache-control: no-storeヘッダー。これにより、ユーザーが[戻る]ボタンを押すと、ブラウザーはサーバーからページを再取得します。理想的ではありませんが、古いページが表示されるよりはましです。

14
nornagon

これは、ハッシュ(#)記号とは関係ありません。

AppleのHTTPヘッダーを確認する場合は、単にページをキャッシュしています。

3
Luca Matteis

Facebookは、ajaxリクエストのURLのハッシュ識別子を変更することにより、ページの状態を記憶します。これらの変更はブラウザの履歴に記録されるため、ユーザーが戻るボタンをクリックすると、ハッシュは以前の状態に変更されます。そのため、has識別子を監視し、ブラウザによって変更された場合に対応するためにJavascriptが必要になることが暗示されています。 Andreas Blixtにはハッシュ監視スクリプトがあります

3
Josh Stodola

URLハッシュ/フラグメント識別子の使用は、AjaxおよびDOMの更新に依存するWebアプリケーションで状態をフック/記憶する非常に一般的な方法です。

Really Simple History プロジェクトでいくつかのアイデアを確認してください。ハッシュの変更についてURLを監視することは可能ですが、rshはブラウザーの違いを考慮してこれを行います。

2
Peter

Railsで問題が発生している場合、これは-あなたの問題はbfcacheではありません(そうだと思っていました)-それはturbolinks gemです。 ここ はそれを削除する方法です。

うまくいけば、これで時間を節約でき、頭を壁にぶつけることができます。

1
Yuval Karmi

探しているのは、ある種のURLハッシュ管理です。 URLの#はクライアント側専用です。

JSでバックの状態を変更すると、URLの#のデータを更新します。

また、ハッシュが変更されたかどうかを監視し、ハッシュの新しいデータに基づいてページの状態をロードするポーリングのタイプを追加します。

これを見てください:

http://ajaxpatterns.org/Unique_URLs

0
BigBlondeViking