From 8d6e00af0a9d2d2e6219d6e5c581595158bfa9f5 Mon Sep 17 00:00:00 2001 From: A2va <49582555+A2va@users.noreply.github.com> Date: Thu, 26 Dec 2024 16:06:39 +0100 Subject: [PATCH] Add sync feature --- src/Storage/HostStorage.js | 6 +-- src/Storage/PreferenceStorage.js | 6 +-- src/Storage/PrefixStorage.js | 57 ++++++++++++++++++++--------- src/ui-preferences/Preference.js | 7 ++++ src/ui-preferences/preferences.json | 6 +++ 5 files changed, 59 insertions(+), 23 deletions(-) diff --git a/src/Storage/HostStorage.js b/src/Storage/HostStorage.js index b4bcb98..0d27cf8 100644 --- a/src/Storage/HostStorage.js +++ b/src/Storage/HostStorage.js @@ -2,8 +2,8 @@ import {matchesSavedMap, sortMaps} from '../utils'; import PrefixStorage from './PrefixStorage'; class HostStorage extends PrefixStorage { - constructor() { - super(); + constructor(storageArea) { + super(storageArea); this.PREFIX = 'map='; this.SET_KEY = 'host'; } @@ -25,4 +25,4 @@ class HostStorage extends PrefixStorage { } -export default new HostStorage(); +export default new HostStorage('local'); \ No newline at end of file diff --git a/src/Storage/PreferenceStorage.js b/src/Storage/PreferenceStorage.js index 635963c..140110b 100644 --- a/src/Storage/PreferenceStorage.js +++ b/src/Storage/PreferenceStorage.js @@ -1,8 +1,8 @@ import PrefixStorage from './PrefixStorage'; class PreferenceStorage extends PrefixStorage { - constructor() { - super(); + constructor(storageArea) { + super(storageArea); this.PREFIX = 'pref='; } @@ -25,4 +25,4 @@ class PreferenceStorage extends PrefixStorage { } } -export default new PreferenceStorage(); +export default new PreferenceStorage('local'); diff --git a/src/Storage/PrefixStorage.js b/src/Storage/PrefixStorage.js index 9d477a9..3fef4f1 100644 --- a/src/Storage/PrefixStorage.js +++ b/src/Storage/PrefixStorage.js @@ -1,13 +1,37 @@ export default class PrefixStorage { - constructor() { + constructor(storageArea = 'local') { this.PREFIX = ''; // The key to use to get the name of the object when calling set() this.SET_KEY = 'key'; - this.storage = browser.storage.local; + this.storage = browser.storage[storageArea]; + this.storageArea = storageArea; this.listeners = new Map(); } + switchStorage(newStorageArea) { + if (newStorageArea != this.storageArea) { + const oldStorage = this.storage; + + // Get all data from old storage and copy to new storage + oldStorage.get(null).then(results => { + // Filter only items with our prefix + const prefixedData = Object.entries(results) + .filter(([key]) => key.startsWith(this.PREFIX)) + .reduce((obj, [key, value]) => { + obj[key] = value; + return obj; + }, {}); + + // Set data in new storage area + browser.storage[newStorageArea].set(prefixedData); + + this.storageArea = newStorageArea; + this.storage = browser.storage[newStorageArea]; + }); + } + } + /** * Get all keys that have the prefix. * @@ -19,19 +43,18 @@ export default class PrefixStorage { return this.storage.get(null).then((results) => { return this._getNonPrefixedObject(results); }); - } - _getNonPrefixedObject(prefixedObject){ + _getNonPrefixedObject(prefixedObject) { return Object - .keys(prefixedObject) - .filter((key) => key.startsWith(this.PREFIX)) - .reduce((newObject, key) => { - newObject[ - key.replace(this.PREFIX, '') - ] = prefixedObject[key]; - return newObject; - }, {}); + .keys(prefixedObject) + .filter((key) => key.startsWith(this.PREFIX)) + .reduce((newObject, key) => { + newObject[ + key.replace(this.PREFIX, '') + ] = prefixedObject[key]; + return newObject; + }, {}); } async get(key) { @@ -51,7 +74,7 @@ export default class PrefixStorage { if (key === undefined) { throw `Key ${this.SET_KEY} not found in object`; } - return this.storage.set({[`${this.PREFIX}${key}`]: obj}); + return this.storage.set({ [`${this.PREFIX}${key}`]: obj }); } /** @@ -60,7 +83,7 @@ export default class PrefixStorage { */ remove(keys) { keys = Array.isArray(keys) ? keys : [keys]; - return this.storage.remove(keys.map( key => `${this.PREFIX}${key}`)); + return this.storage.remove(keys.map(key => `${this.PREFIX}${key}`)); } /** @@ -76,17 +99,17 @@ export default class PrefixStorage { * @param fn {Function} */ addOnChangedListener(fn) { - if(fn in this.listeners){ + if (fn in this.listeners) { return; } const listener = (changes, area) => { let prefixChanges = this._getNonPrefixedObject(changes); - if(!prefixChanges){ + if (!prefixChanges) { return; } fn(prefixChanges, area); }; - this.listeners[fn]=listener; + this.listeners[fn] = listener; browser.storage.onChanged.addListener(listener); } diff --git a/src/ui-preferences/Preference.js b/src/ui-preferences/Preference.js index 3e0bbae..db0600d 100644 --- a/src/ui-preferences/Preference.js +++ b/src/ui-preferences/Preference.js @@ -1,4 +1,5 @@ import PreferenceStorage from '../Storage/PreferenceStorage'; +import HostStorage from '../Storage/HostStorage'; import template from '!!raw-loader!./templates/Preference.html'; import {createEl, qs} from './utils'; @@ -172,6 +173,12 @@ export default class Preference { */ update() { const newValue = this.get(); + if (this.name == 'sync') { + const storageArea = newValue ? 'sync' : 'local'; + PreferenceStorage.switchStorage(storageArea); + HostStorage.switchStorage(storageArea); + } + return PreferenceStorage.set({ key: this.name, value: newValue, diff --git a/src/ui-preferences/preferences.json b/src/ui-preferences/preferences.json index 3f92f07..acdabe7 100644 --- a/src/ui-preferences/preferences.json +++ b/src/ui-preferences/preferences.json @@ -11,6 +11,12 @@ "label": "Keep old tabs", "description": "After a contained tab has been created, the old won't be closed" }, + { + "type": "bool", + "name": "sync", + "label": "Synchronize configurations", + "description": "Synchronize configurations between all devices" + }, { "type": "group", "name": "defaultContainer",