2 回答

TA貢獻1796條經驗 獲得超7個贊
我會建議你使用localStorage
這個具有相當好的存儲容量。
您僅限于其中的字符串,因此您需要將所有內容與 JSON 相互轉換以獲得最佳結果。
你存儲什么取決于你。我將創建一個具有各種屬性的對象,例如當前滾動高度、上次請求的索引和一個數組,其中包含您到目前為止從 AJAX 中提取的所有內容(以及您在頁面加載時創建的所有內容)。如果您要在多個頁面上使用此邏輯,或者只是更改每頁的鍵,您可能還想存儲它所在的頁面。但是,如果您共享一個密鑰,您也可以完全跳過對您已經擁有的數據的 AJAX 調用,并且您認為自己的業務邏輯是“新鮮的”。
下面是一些示例代碼。如果您按下開始按鈕并讓它運行幾秒鐘,您將看到列表隨著時間戳而增長。如果您隨后刷新頁面,所有內容仍將存在。
首先,一些 HTML 讓我們工作,一個開始和停止的按鈕以及我們將寫入的列表。
<button id="start">Start</button>
<button id="stop">Stop</button>
<ul id="list">
</ul>
然后是 JS,內聯注釋應該可以解釋一切:
// This is the interval key, used when stopping the interval code
let iv;
const cache_key = 'my-cache-key';
function stop() {
? ? window.clearInterval( iv );
}
function start() {
? ? iv = window.setInterval( tick, 1000 );
}
function makeLi( text ) {
? ? const li = document.createElement( 'li' );
? ? li.appendChild( document.createTextNode( text ) );
? ? return li;
}
// Run once a second
function tick() {
? ? // Create a timestamp
? ? const ts = new Date().getTime();
? ? // Store it to local session
? ? store( ts );
? ? // Append to our list
? ? const ul = document.getElementById( 'list' );
? ? ul.appendChild( makeLi( ts ) );
}
function store( text ) {
? ? // See if we have our key
? ? let items = window.localStorage.getItem( cache_key );
? ? // Parse it as JSON or set it to an empty array to start
? ? if ( items ) {
? ? ? ? items = JSON.parse( items );
? ? } else {
? ? ? ? items = [];
? ? }
? ? // Append our current key
? ? items.push( text );
? ? // Push it back
? ? window.localStorage.setItem( cache_key, JSON.stringify( items ) );
}
// One page load, recreate all items
function load() {
? ? const ul = document.getElementById( 'list' );
? ? let items = window.localStorage.getItem( cache_key );
? ? if ( !items ) {
? ? ? ? return;
? ? }
? ? items = JSON.parse( items );
? ? items
? ? ? ? .forEach(
? ? ? ? ? ? ( item ) => {
? ? ? ? ? ? ? ? ul.appendChild( makeLi( item ) )
? ? ? ? ? ? }
? ? ? ? );
}
// Click handlers for the button
document.getElementById( 'start' ).addEventListener( 'click', start );
document.getElementById( 'stop' ).addEventListener( 'click', stop );
// Reload anything previously stored on page refresh
window.addEventListener( 'load', load );
至于你在本地存儲中存儲什么,這取決于。如果您的 DOM 很復雜但很短,您可以存儲它outerHTML的,但這有點難看。相反,我會存儲您從 AJAX 收到的用于創建對象的最少字段數。
此外,無論您存儲什么,我都建議在您的對象上有一個名為“版本”之類的屬性,并且每當您向 AJAX 邏輯引入新功能時手動增加它。這樣,如果有人帶著不再有意義的數據返回您的頁面,您的應用程序可以檢測到它并將其丟棄。
這個示例應用程序存儲一個非常簡單的數組,但就像我說的,您可能想要存儲一個對象并且您還想要執行驗證和清理,就像您在 AJAX 中所做的那樣。
編輯
我還應該補充一點,您需要確保您的圖像等資源在未來緩存過期,以便從本地緩存中獲得額外的站點速度。
根據我的評論,這個網站(已有 4 年歷史)表示 97.6% 的人啟用了本地存儲,所以我絕對會使用它,因為降級只是“最新的”,這仍然是一個不錯的體驗。
如果您在參考站點上打開您的開發人員工具,您可以檢查本地存儲的應用程序部分,您會在那里找到我正在談論的版本。

TA貢獻1890條經驗 獲得超9個贊
這個問題太寬泛了,但由于它不能在有賞金的情況下關閉,所以我不妨用同樣寬泛的答案來回答。
你真的需要這個嗎?為什么不在新標簽頁中打開全尺寸圖片?或者為什么不離開頁面就打開它們?如果您想要后退/前進功能,您可以使用History API 。您將盡可能節省所有流量。此外,在顯示全尺寸圖像時,您可以允許用戶使用箭頭鍵和其他一些很酷的員工在全尺寸圖像之間移動。
關于
但我認為這不是一個好主意,因為加載大量這樣的內容會影響性能
正確的緩存 - 不是真的。圖像不會被重新加載...當然,如果您通過 url 加載它們而不是以其他一些奇怪的方式加載它們。
關于問題的標題:我們真的應該談論重建狀態而不是恢復狀態。因為對于這個:
您能否保留使用 ajax 的頁面的動態內容,以便在用戶返回時恢復?
答案是:“不,你不能”。不是因為它完全不可能,而是因為你肯定會失敗。要存檔此目標,您需要
在每次更改時將應用程序的每個變量序列化。包括有關 DOM 動態更改的信息。
并非所有東西都易于序列化:
Promise
s、WeakMap
s、Symbol
s、具有循環引用的數據等。接下來,您需要將它們反序列化回來。這也可能是一個挑戰。特別是,如果在序列化和反序列化之間服務器端發生了一些變化。(可能扔掉所有東西重新開始更容易)
此外,您還需要決定是否應該這樣做。例如,如果用戶在一個月后訪問您的頁面——您真的要顯示一個月前的狀態嗎?
但如果我們談論存儲一些重要變量并從中重新創建狀態,那么答案是:“是的,它一直在發生”。
在客戶端存儲數據有不同的方法(甚至是數據庫!),在服務器端存儲數據更是如此。
他們都適合自己的場景。在不知道這些情況的情況下很難說什么是最好的方法。
但在這種特殊情況下,您只需要存儲 1 或 2 個變量。而使用 cookie 可能是最好的選擇。雖然現在如果您使用 cookie,您需要顯示一些煩人的消息。由于歐盟 cookie 指令。但它們易于使用,例如,如果您決定在一個月后向用戶呈現一個全新的狀態,您只需要為 cookie 設置到期日期,而如果您使用
localStorage
.在這個顯然不是商業站點的地方,可能不需要服務器端存儲。
- 2 回答
- 0 關注
- 133 瀏覽
添加回答
舉報