將數據儲存在裝置上
漸進式 Web Apps (PWA) 提供強大的選項,可在本機儲存數據,讓使用者即使在網路連線變得不穩定或離線時仍能繼續工作。
PWA 有數種方式可以在裝置上儲存數據,例如本機記憶體、快取 API 或 IndexedDB。
下表描述不同的選項,本文的其餘部分會針對每個選項深入瞭解詳細數據和使用案例。
記憶體選項 | 描述 |
---|---|
Web 記憶體 | Web 記憶體有兩種類型:工作階段和本機。 Web 記憶體很適合用來儲存來自您應用程式前端程式代碼的少量數據。 數據會結構化為索引鍵/值組,且僅適用於目前的應用程式來源。 在工作階段記憶體的情況下,會在工作階段結束時清除資料,例如當應用程式關閉時,或當使用者流覽至相同視窗或索引標籤中的另一個來源時。本機記憶體會持續存在,直到應用程式移除數據為止。 |
IndexedDB | IndexedDB 是用來儲存大量結構化數據的 API。 API 是異步的,而且可以從應用程式的前端程式代碼和服務背景工作程式代碼使用。 使用 IndexedDB API 在用戶端或二進位數據上儲存大量的結構化數據,例如加密的媒體物件或檔案。 |
快取 | 快取 API 可用來管理快取的資源。 快取 API 是以承諾為基礎,可讓開發人員儲存和擷取許多 Web 資源,例如 HTML、CSS、JavaScript、影像、JSON 等等。 快取 API 通常會在服務背景工作角色的內容中使用,但也適用於您應用程式的前端程式代碼。 |
檔案系統存取 | 檔系統存取 API 可讓您的 PWA 讀取使用者裝置上的檔案和資料夾,並將變更儲存回給它們。 |
注意:請勿使用 WebSQL 或應用程式快取。 雖然這兩種是其他兩種瀏覽器儲存機制,但兩者都已被取代。 請使用 IndexedDB,而不是 WebSQL。 請使用快取 API,而不是應用程式快取。
Web 記憶體
Web 記憶體適用於將少量字串資料儲存在用戶的裝置上。 Web 記憶體的索引鍵/值組系統的簡單性可讓您輕鬆使用。
Web 記憶體只能在應用程式的主線程中同步運作。 這表示 Web 記憶體無法在服務工作者內使用,而大量使用 Web 記憶體可能會對您的應用程式造成效能問題。
每種類型的 Web 記憶體、工作階段和本機都會維護為個別的數據存放區,與建立它的網域隔離。
-
sessionStorage
只會在會話期間保存 ,例如,當瀏覽器開啟時,包括重新整理頁面的時間。 -
localStorage
會保存到應用程式程式代碼、使用者或瀏覽器移除資料為止。
下列程式代碼示範如何使用 localStorage
,這類似於 sessionStorage
的使用方式:
const browserInformation = {
name: 'Microsoft Edge',
version: 108
};
localStorage.setItem('browser', JSON.stringify(browserInformation));
上述程式代碼會使用 setItem()
方法將 JavaScript 物件儲存為 中的 localStorage
JSON 字串,並指派等於 browser
的索引鍵。 您可以使用 方法從 localStorage
中擷取資訊, getItem()
如下所示:
const value = localStorage.getItem('browser');
const browserInformation = JSON.parse(value);
若要深入瞭解,請參閱 MDN 上的 Web 記憶體 API 。
IndexedDB
IndexedDB 是一種異步 API,可用來儲存結構化數據,可用於應用程式的前端程式代碼或服務背景工作程序代碼。 使用 IndexedDB API 在用戶端或二進位數據上儲存大量的結構化數據,例如加密的媒體物件或檔案。
IndexedDB 是將資料儲存在 PWA 中的最佳選項,因為使用 API 並不會封鎖主線程來使應用程式變慢,而且可以從應用程式的前端程式代碼和服務背景工作角色使用。
使用 IndexedDB 比使用 Web 記憶體更複雜,而且需要下列步驟來儲存資料:
- 使用
window.indexedDB.open()
函式開啟資料庫。 - 使用 函式,在資料庫中建立
IDBDatabase.createObjectStore()
物件存放區。 - 使用
IDBDatabase.transaction()
函式啟動交易以儲存數據。 - 藉由接聽事件,等候作業完成。
若要深入瞭解並檢視程式代碼範例,請參閱在 MDN 上 使用 IndexedDB 。
快取
快取 API 是一種系統,可在應用程式的前端程式代碼或服務背景工作角色中儲存和擷取網路要求和回應。 它可用來將影像和檔案等資產儲存在用戶裝置的本機。 這可讓您的應用程式即使在離線時也能運作,或藉由減少轉譯應用程式所需的網路要求數目來改善其效能。
下列代碼段示範如何在服務背景工作角色中接聽 fetch
事件,並使用快取 API 儲存來自伺服器的回應:
self.addEventListener("fetch", event => {
async function cacheAndReturnRequest() {
// Get the response from the server.
const fetchResponse = await fetch(event.request.url);
// Open the app's cache.
const cache = await caches.open("cache-name");
// Put the response in cache.
cache.put(event.request.url, fetchResponse.clone());
// And return the response.
return fetchResponse.
}
event.respondWith(cacheAndReturnRequest());
});
若要探索其他有用的快取 API 案例,請參閱 使用服務背景工作角色來管理網路要求。
檔案系統存取
檔案系統存取 API 可讓您的應用程式以類似原生應用程式的方式存取使用者裝置上的檔案。 它可以用來建立可讀取和寫入檔案的應用程式,例如文字或影像編輯器。
若要從使用者的裝置開啟檔案,請使用 函式 showOpenFilePicker()
:
openFileButton.addEventListener("click", async () => {
const fileHandles = await window.showOpenFilePicker();
});
若要深入瞭解,請參閱 MDN 上的 Window.showOpenFilePicker () 。
檔系統存取 API 也可以與 PWA 檔案處理功能結合,將您的應用程式註冊為特定檔類型的處理程式,因而對用戶感覺更原生。 若要深入瞭解,請 參閱處理漸進式 Web Apps 中的檔案。
原始私人文件系統存取 API 是文件系統存取 API 的變化,旨在為使用者提供更多隱私權。 它也允許應用程式存取使用者裝置上的檔案,但只能在應用程式來源私人的特定目錄記憶體取檔案。 此外,此 API 的目的並不是要讓使用者使用其檔案總管輕鬆存取私人目錄。
若要從原始私人文件系統開啟檔案,請使用 navigator.storage
承諾型 API:
// Get the origin-private directory handle.
const root = await navigator.storage.getDirectory();
// Get the handle for a file in the directory.
const fileHandle = await root.getFileHandle("my-file.txt");
儲存配額
在 Microsoft Edge 中,本機和會話記憶體限製為每個記憶體約 5 MB。
其他類型的數據記憶體,例如 IndexedDB、快取 API 或原始私人文件系統存取 API,最多可以使用裝置上總磁碟空間的 60%。 例如,如果您的應用程式執行所在的裝置有 64 GB 的磁碟,Microsoft Edge 可讓您的應用程式儲存最多 38 GB 的數據。
請注意,裝置上實際可用的可用空間可能小於 60% 的儲存配額。 例如,如果您的應用程式執行所在的裝置有 64GB 的磁碟,但操作系統和其他檔案已使用 50GB,即使記憶體配額仍為 38 GB,您的應用程式也只能儲存 14 GB 的數據。
您可以使用 navigator.storage.estimate()
來詢問記憶體管理員 API 應用程式來源的記憶體配額為何,以及其已使用量。 若要深入瞭解,請參閱 MDN 上的 StorageManager.estimate () 。
嘗試儲存超過可用或允許的數據,會導致 JavaScript 錯誤。 您的程式代碼應該使用語 try...catch
句來攔截此錯誤。 下列代碼段示範如何在使用 Web 記憶體儲存資料時攔截超出的配額錯誤:
try {
localStorage.setItem('foo', 'bar');
} catch (e) {
// Code that handles the lack of storage space.
}
數據收回
當使用者的裝置在可用磁碟空間上開始不足,也稱為 儲存壓力時,Microsoft Edge 將會開始收回非持續性數據。
這表示使用快取 API、IndexedDB、原始私人文件系統存取 API 或 Web 儲存體儲存的應用程式數據可能會遭到收回。
根據預設,您的應用程式儲存的數據不會被視為持續性,而且可能會在記憶體壓力時遭到收回。 如果您的應用程式儲存重要數據,請使用 navigator.storage.persist()
函式讓應用程式的記憶體永續性。 永續性記憶體只能由使用者清除。 若要深入瞭解,請參閱 MDN 上的 StorageManager.persist () 。