說明
使用 chrome.storage
API 儲存、擷取及追蹤使用者資料的變更。
權限
storage
總覽
Storage API 提供特定擴充功能專用的方法來保存使用者資料和狀態。這與網路平台的儲存 API (IndexedDB 和 Storage) 類似,但是專為滿足擴充功能儲存需求而設計。以下是幾項主要功能:
- 所有擴充功能結構定義 (包括擴充功能服務 Worker 和內容指令碼) 都可存取 Storage API。
- JSON 序列化值會儲存為物件屬性。
- Storage API 與大量讀取和寫入作業非同步。
- 即使使用者清除快取和瀏覽記錄,這些資料仍會保留。
- 即使使用分割無痕模式,已儲存的設定仍會保持有效。
- 包含企業政策的專屬唯讀代管儲存空間區域。
雖然擴充功能可在某些內容 (彈出式視窗和其他 HTML 網頁) 中使用 [Storage
][mdn-storage] 介面 (可從 window.localStorage
存取),但我們並不推薦你這麼做的原因如下:
- 擴充功能的 Service Worker 無法存取
Storage
。 - 內容指令碼與代管網頁共用儲存空間。
- 使用者清除瀏覽記錄時,無法透過
Storage
介面儲存的資料會遺失。
如何將網路儲存空間 API 中的資料移至擴充功能儲存空間 API,以便從 Service Worker 進行以下操作:
- 使用轉換處理常式和 [
onMessage
][on-message] 處理常式建立畫面外文件。 - 將轉換日常安排新增至螢幕外文件。
- 在擴充功能 Service Worker 中,檢查資料為
chrome.storage
。 - 如果找不到資料,請 [create][create-offscreen],在畫面外的文件呼叫 [
sendMessage()
][send-message] 以啟動轉換日常安排。 - 在畫面外文件的
onMessage
處理常式中,呼叫轉換處理常式。
而 Web Storage API 在擴充功能中的運作方式也有一些細微差異。詳情請參閱 [儲存空間和 Cookie][儲存空間與 Cookie] 一文。
儲存空間區域
Storage API 分為以下四個值區 (「儲存區域」):
storage.local
- 資料會儲存在本機,並在擴充功能移除時清除。配額限制大約為 10 MB,但您可以要求
"unlimitedStorage"
權限來提高配額。請考慮用於儲存大量資料。
storage.sync
- 啟用同步功能後,資料會同步到使用者登入的所有 Chrome 瀏覽器。停用後的運作方式將與
storage.local
類似。Chrome 會在瀏覽器離線時將資料儲存在本機,並於重新連線後繼續同步處理。配額限制為每個項目約 100 KB 和 8 KB。因此,建議您使用這項功能保留不同瀏覽器的使用者設定。
- storage.session
- 將瀏覽器工作階段期間的記憶體保存在記憶體中。根據預設,內容指令碼不會顯示此行為,但您可以設定
chrome.storage.session.setAccessLevel()
來變更這項行為。配額限制約為 10 MB。建議使用 Cloud Shell 儲存 Service Worker 執行作業的全域變數。
- storage.managed
- 管理員可以使用結構定義和企業政策,在受管理的環境中指定支援的擴充功能設定。這個儲存空間區域處於唯讀狀態。
資訊清單
如要使用 Storage API,請在擴充功能資訊清單中宣告 "storage"
權限。例如:
{
"name": "My extension",
...
"permissions": [
"storage"
],
...
}
用量
以下範例說明 local
、sync
和 session
儲存空間區域:
storage.local
chrome.storage.local.set({ key: value }).then(() => {
console.log("Value is set");
});
chrome.storage.local.get(["key"]).then((result) => {
console.log("Value currently is " + result.key);
});
storage.sync
chrome.storage.sync.set({ key: value }).then(() => {
console.log("Value is set");
});
chrome.storage.sync.get(["key"]).then((result) => {
console.log("Value currently is " + result.key);
});
storage.session
chrome.storage.session.set({ key: value }).then(() => {
console.log("Value was set");
});
chrome.storage.session.get(["key"]).then((result) => {
console.log("Value currently is " + result.key);
});
如要進一步瞭解 managed
儲存空間區域,請參閱儲存空間區域資訊清單。
儲存空間和節流限制
請不要誤以為「新增至 Storage API」就是裝在大卡車的地方。增加儲存空間就像在管線中放東西一樣。管道中可能已含有材料,甚至可能填滿。新增至儲存空間時,請務必假設,到實際記錄工作之間會有延遲。
如要進一步瞭解儲存空間區域限制,以及用量超出上限會有什麼影響,請參閱 sync
、local
和 session
的配額資訊。
用途
以下各節說明 Storage API 的常見用途。
同步回應儲存空間更新
如要追蹤儲存空間的變更,您可以在其 onChanged
事件中新增事件監聽器。如果儲存空間有任何變動,就會觸發該事件。程式碼範例會監聽這些變更:
background.js:
chrome.storage.onChanged.addListener((changes, namespace) => {
for (let [key, { oldValue, newValue }] of Object.entries(changes)) {
console.log(
`Storage key "${key}" in namespace "${namespace}" changed.`,
`Old value was "${oldValue}", new value is "${newValue}".`
);
}
});
我們可以更進一步實踐這個想法在此範例中,我們提供選項頁面,可讓使用者切換「偵錯模式」(這裡並未顯示實作)。選項頁面會立即將新設定儲存到 storage.sync
,而 Service Worker 則會盡快使用 storage.onChanged
套用設定。
options.html:
<!-- type="module" allows you to use top level await -->
<script defer src="options.js" type="module"></script>
<form id="optionsForm">
<label for="debug">
<input type="checkbox" name="debug" id="debug">
Enable debug mode
</label>
</form>
options.js:
// In-page cache of the user's options
const options = {};
const optionsForm = document.getElementById("optionsForm");
// Immediately persist options changes
optionsForm.debug.addEventListener("change", (event) => {
options.debug = event.target.checked;
chrome.storage.sync.set({ options });
});
// Initialize the form with the user's option settings
const data = await chrome.storage.sync.get("options");
Object.assign(options, data.options);
optionsForm.debug.checked = Boolean(options.debug);
background.js:
function setDebugMode() { /* ... */ }
// Watch for changes to the user's options & apply them
chrome.storage.onChanged.addListener((changes, area) => {
if (area === 'sync' && changes.options?.newValue) {
const debugMode = Boolean(changes.options.newValue.debug);
console.log('enable debug mode?', debugMode);
setDebugMode(debugMode);
}
});
從儲存空間的非同步預先載入
由於 Service Worker 並非隨時執行,因此 Manifest V3 擴充功能有時必須在執行事件處理常式之前,以非同步方式從儲存空間載入資料。為執行這項作業,下列程式碼片段使用非同步 action.onClicked
事件處理常式,該處理常式會等待 storageCache
全域填入,再執行其邏輯。
background.js:
// Where we will expose all the data we retrieve from storage.sync.
const storageCache = { count: 0 };
// Asynchronously retrieve data from storage.sync, then cache it.
const initStorageCache = chrome.storage.sync.get().then((items) => {
// Copy the data retrieved from storage into storageCache.
Object.assign(storageCache, items);
});
chrome.action.onClicked.addListener(async (tab) => {
try {
await initStorageCache;
} catch (e) {
// Handle error that occurred during storage initialization.
}
// Normal action handler logic.
storageCache.count++;
storageCache.lastTabId = tab.id;
chrome.storage.sync.set(storageCache);
});
擴充功能範例
如要查看 Storage API 的其他示範,請參考下列任何範例:
類型
AccessLevel
儲存空間區域的存取層級。
列舉
"TRUSTED_CONTEXTS"
指定來自擴充功能本身的結構定義。
"TRUSTED_AND_UNTRUSTED_CONTEXTS"
指定來自擴充功能外的結構定義。
StorageArea
屬性
-
onChanged
事件<functionvoidvoid>
Chrome 73 以上版本一或多個項目變更時觸發。
onChanged.addListener
函式如下所示:(callback: function) => {...}
-
回呼
功能
callback
參數如下所示:(changes: object) => void
-
變更
物件
-
-
-
關閉
void
Promise從儲存空間移除所有項目。
clear
函式如下所示:(callback?: function) => {...}
-
回呼
函式選用
callback
參數如下所示:() => void
-
returns
Promise<void>
Chrome 88 以上版本Promise 僅支援 Manifest V3 以上版本,其他平台就必須使用回呼。
-
-
get
void
Promise從儲存空間取得一或多個項目。
get
函式如下所示:(keys?: string | string[] | object, callback?: function) => {...}
-
金鑰
string | string[] | object optional
要取得的單一鍵、要取得的鍵清單,或指定預設值的字典 (請參閱物件說明)。空白的清單或物件會傳回空的結果物件。傳入
null
,即可取得儲存空間的完整內容。 -
回呼
函式選用
callback
參數如下所示:(items: object) => void
-
items
物件
內含項目的鍵/值對應項目。
-
-
returns
Promise<object>
Chrome 88 以上版本Promise 僅支援 Manifest V3 以上版本,其他平台就必須使用回呼。
-
-
getBytesInUse
void
Promise取得一或多個項目正在使用的空間量 (以位元組為單位)。
getBytesInUse
函式如下所示:(keys?: string | string[], callback?: function) => {...}
-
金鑰
string | string[] 選填
用來取得總用量的單一鍵或鍵清單。空白清單會傳回 0。傳入
null
即可取得所有儲存空間的總用量。 -
回呼
函式選用
callback
參數如下所示:(bytesInUse: number) => void
-
bytesInUse
號碼
儲存空間中使用的空間量,以位元組為單位。
-
-
returns
Promise<number>
Chrome 88 以上版本Promise 僅支援 Manifest V3 以上版本,其他平台就必須使用回呼。
-
-
remove
void
Promise從儲存空間中移除一或多個項目。
remove
函式如下所示:(keys: string | string[], callback?: function) => {...}
-
金鑰
string | string[]
列出要移除的單一鍵或項目的按鍵清單。
-
回呼
函式選用
callback
參數如下所示:() => void
-
returns
Promise<void>
Chrome 88 以上版本Promise 僅支援 Manifest V3 以上版本,其他平台就必須使用回呼。
-
-
set
void
Promise設定多個項目。
set
函式如下所示:(items: object, callback?: function) => {...}
-
items
物件
物件,可為每個鍵/值組合提供更新儲存空間所用的物件。儲存空間中的任何其他鍵/值組合不會受到影響。
數字等原始值會正常序列化。含有
typeof
"object"
和"function"
的值通常會序列化為{}
,但Array
除外 (會正常序列化)、Date
和Regex
(使用其String
表示法序列化)。 -
回呼
函式選用
callback
參數如下所示:() => void
-
returns
Promise<void>
Chrome 88 以上版本Promise 僅支援 Manifest V3 以上版本,其他平台就必須使用回呼。
-
-
setAccessLevel
void
Promise Chrome 102 以上版本設定儲存區域所需的存取層級。只會預設為可信任的結構定義。
setAccessLevel
函式如下所示:(accessOptions: object, callback?: function) => {...}
-
accessOptions
物件
-
accessLevel
儲存空間區域的存取層級。
-
-
回呼
函式選用
callback
參數如下所示:() => void
-
returns
Promise<void>
Promise 僅支援 Manifest V3 以上版本,其他平台就必須使用回呼。
-
StorageChange
屬性
-
newValue
任何選填
項目的新值 (如果有的話)。
-
oldValue
任何選填
項目的舊值 (如有舊值)。
屬性
local
local
儲存區域中的項目是每部機器的本機檔案。
類型
StorageArea 和物件
屬性
-
QUOTA_BYTES
10485760
可儲存在本機儲存空間中的資料大小上限 (以位元組為單位),這是根據每個值加上每個鍵長度的 JSON 字串值測量而得。如果擴充功能具備
unlimitedStorage
權限,系統會忽略這個值。會導致立即超過這項限制的更新作業立即失敗,並在使用回呼時設定runtime.lastError
;如果使用 async/await,則拒絕 Promise。
managed
managed
儲存空間區域中的項目是由網域管理員設定的企業政策所設定,擴充功能為唯讀狀態;嘗試修改這個命名空間會導致錯誤。如要進一步瞭解如何設定政策,請參閱「儲存空間區域資訊清單」。
類型
session
session
儲存空間區域中的項目會儲存在記憶體中,不會保存至磁碟。
類型
StorageArea 和物件
屬性
-
QUOTA_BYTES
10485760
可儲存在記憶體中的資料大小上限 (以位元組為單位),這是根據每個值和鍵的動態分配記憶體用量估計值計算得出。會導致立即超過這項限制的更新作業立即失敗,並在使用回呼或 Promise 遭拒時設定
runtime.lastError
。
sync
「sync
」儲存區域中的項目會使用 Chrome 同步功能同步處理。
類型
StorageArea 和物件
屬性
-
MAX_ITEMS
512
可儲存在同步儲存空間的項目數量上限。導致超出這項限制的更新會立即失敗,且在使用回呼或 Promise 遭拒時設定
runtime.lastError
。 -
MAX_SUSTAINED_WRITE_OPERATIONS_PER_MINUTE
1000000
已淘汰storage.sync API 不再有持續寫入作業配額。
-
MAX_WRITE_OPERATIONS_PER_HOUR
1800
每小時可執行的
set
、remove
或clear
作業數量上限。上限為每 2 秒 1 次,低於短期的寫入上限;會導致立即超過這項限制的更新作業立即失敗,並在使用回呼或 Promise 遭拒時設定
runtime.lastError
。 -
MAX_WRITE_OPERATIONS_PER_MINUTE
120
每分鐘可執行的
set
、remove
或clear
作業數量上限。也就是每秒 2 次,在較短的期間內,提供高於每小時寫入的總處理量。會導致立即超過這項限制的更新作業立即失敗,並在使用回呼或 Promise 遭拒時設定
runtime.lastError
。 -
QUOTA_BYTES
102400
可儲存在同步儲存空間中的資料總量 (以位元組為單位),這是根據每個值加上每個鍵長度的 JSON 字串計算而得。會導致立即超過這項限制的更新作業立即失敗,並在使用回呼或 Promise 遭拒時設定
runtime.lastError
。 -
QUOTA_BYTES_PER_ITEM
8192
同步儲存空間中每個項目的大小上限 (以位元組為單位),根據其值及其金鑰長度的 JSON 字串長度計算而得。如果項目含有超過這個上限的項目,更新會立即失敗,且在使用回呼或 Promise 遭拒時設定
runtime.lastError
。
活動
onChanged
chrome.storage.onChanged.addListener(
callback: function,
)
一或多個項目變更時觸發。
參數
-
回呼
功能
callback
參數如下所示:(changes: object, areaName: string) => void
-
變更
物件
-
areaName
字串
-