blob: 6d5ab409cb03edf5e35ce909a54a80711c1f4906 [file] [log] [blame]
/**
* @license
* Copyright 2022 Google LLC
* SPDX-License-Identifier: Apache-2.0
*/
export interface GerritServiceWorkerState {
latestUpdateTimestampMs: number;
allowBrowserNotificationsPreference: boolean;
}
const SERVICE_WORKER_DB = 'service-worker-db-1';
// Object store - kind of table that holds objects
// https://developer.mozilla.org/en-US/docs/Web/API/IDBObjectStore
const SERVICE_WORKER_STORE = 'states';
// Service Worker State needs just 1 entry in object store which is rewritten
// every time state is saved. This entry has SERVICE_WORKER_STATE_ID.
const SERVICE_WORKER_STATE_ID = 1;
function getServiceWorkerDB(): Promise<IDBDatabase> {
return new Promise((resolve, reject) => {
const request = indexedDB.open(SERVICE_WORKER_DB);
request.onsuccess = () => resolve(request.result);
request.onerror = reject;
request.onblocked = reject;
// Event is fired when an attempt was made to open a database with a version
// higher than its current version.
// https://developer.mozilla.org/en-US/docs/Web/API/IDBOpenDBRequest/upgradeneeded_event
// It's mainly used to create object stores.
// https://web.dev/indexeddb/#creating-object-stores
request.onupgradeneeded = () => {
const db = request.result;
if (db.objectStoreNames.contains(SERVICE_WORKER_STORE)) return;
const states = db.createObjectStore(SERVICE_WORKER_STORE, {
keyPath: 'id',
});
states.createIndex('states_id_unique', 'id', {unique: true});
};
});
}
export async function putServiceWorkerState(state: GerritServiceWorkerState) {
const db = await getServiceWorkerDB();
const tx = db.transaction(SERVICE_WORKER_STORE, 'readwrite');
const store = tx.objectStore(SERVICE_WORKER_STORE);
store.put({...state, id: SERVICE_WORKER_STATE_ID});
return new Promise<void>(resolve => {
tx.oncomplete = () => resolve();
});
}
export async function getServiceWorkerState(): Promise<GerritServiceWorkerState> {
const db = await getServiceWorkerDB();
const tx = db.transaction(SERVICE_WORKER_STORE, 'readonly');
const store = tx.objectStore(SERVICE_WORKER_STORE);
return new Promise((resolve, reject) => {
const request = store.get(SERVICE_WORKER_STATE_ID);
request.onsuccess = () => resolve(request.result);
request.onerror = reject;
});
}