Refactor secretariat.js to specify data source origin

global.forget() is currently broken in this commit.
This commit is contained in:
buzz-lightsnack-2007 2024-04-30 23:29:49 +08:00
parent 9ade82ccbe
commit 50d02b8c06

View file

@ -6,65 +6,33 @@ import logging from "/scripts/logging.js";
import texts from "/scripts/mapping/read.js"; import texts from "/scripts/mapping/read.js";
import hash from "/scripts/utils/hash.js"; import hash from "/scripts/utils/hash.js";
/* Read all stored data in the browser cache. /*
Global data storage, which refers to local and synchronized storage
@param {array} DATA_NAME the data name
@param {int} CLOUD determine cloud reading, which is otherwise set to automatic (0)
@param {string} PARAMETER_CHECK Determine which parameter to check via regular expressions.
@return {object} the data
*/ */
export async function read(DATA_NAME, CLOUD = 0) { class global {
// Initialize the selected pref data. /* Read all stored data in the browser cache.
let DATA, DATA_RETURNED;
@param {array} name the data name
@param {int} cloud determines cloud reading, which is otherwise set to automatic (0)
@return {object} the data
*/
static async read(name, cloud = 0) {
/* /*
Get all storage values. Get all storage values.
@param {number} SOURCE the data source @param {number} SOURCE the data source
*/ */
async function read_database(SOURCE = -1) { function pull(SOURCE = -1) {
let data, data_returned; return (chrome.storage[(SOURCE > 0) ? `sync` : `local`].get(null));
async function read_database_local() {
return new Promise((resolve, reject) => {
chrome.storage.local.get(null, function (result) {
if (chrome.runtime.lastError) {
// Something went wrong
reject(new Error(chrome.runtime.lastError));
} else {
// If the key exists, return the value
resolve(result);
}
});
});
} }
async function read_database_sync() { /*
return new Promise((resolve, reject) => { Find a data given its path.
chrome.storage.sync.get(null, function (result) {
if (chrome.runtime.lastError) {
// Something went wrong
reject(new Error(chrome.runtime.lastError));
} else {
// If the key exists, return the value
resolve(result);
}
});
});
}
// Return the data. @param {object} DATA_ALL the data
data_returned = (SOURCE > 0) ? read_database_sync() : read_database_local();
return data_returned;
}
/* Recursively find through each data, returning either that value or null when the object is not found.
@param {dictionary} DATA_ALL the data
@param {object} DATA_PATH the path of the data @param {object} DATA_PATH the path of the data
@return {object} the data
*/ */
function find_data(DATA_ALL, DATA_PATH) { function find(DATA_ALL, DATA_PATH) {
let DATA = DATA_ALL; let DATA = DATA_ALL;
// Pull the data out. // Pull the data out.
@ -77,7 +45,7 @@ export async function read(DATA_NAME, CLOUD = 0) {
// must run if there is actually a parameter to test // must run if there is actually a parameter to test
if (DATA_PATH.length > 0) { if (DATA_PATH.length > 0) {
// Recursively run to make use of the existing data. // Recursively run to make use of the existing data.
DATA = find_data(DATA, DATA_PATH); DATA = find(DATA, DATA_PATH);
}; };
} else { } else {
return null; return null;
@ -85,47 +53,56 @@ export async function read(DATA_NAME, CLOUD = 0) {
// Now return the data. // Now return the data.
return DATA; return DATA;
} };
// Initialize the selected pref data.
let DATA, DATA_RETURNED;
// Convert the entered prefname to an array if it is not one. // Convert the entered prefname to an array if it is not one.
if (!Array.isArray(DATA_NAME) && DATA_NAME != null) { let NAME = (!Array.isArray(name) && name != null)
// Syntax of splitting is by commas. ? String(name).trim().split(`,`)
DATA_NAME = String(DATA_NAME).trim().split(","); : name;
}
switch (CLOUD) {
switch (cloud) {
case 0: case 0:
DATA = {}; DATA_RETURNED = {}; DATA = {}; DATA_RETURNED = {};
DATA[`sync`] = await read((DATA_NAME) ? [...DATA_NAME] : null, 1); DATA[`sync`] = await global.read((NAME) ? [...NAME] : null, 1);
DATA[`local`] = await read((DATA_NAME) ? [...DATA_NAME] : null, -1); DATA[`local`] = await global.read((NAME) ? [...NAME] : null, -1);
// Now return the data. // Now return the data.
DATA_RETURNED[`source`] = (DATA[`sync`] != null) ? `sync` : `local`; DATA_RETURNED[`source`] = (DATA[`sync`] != null) ? `sync` : `local`;
DATA_RETURNED[`value`] = DATA[DATA_RETURNED[`source`]]; DATA_RETURNED[`value`] = DATA[DATA_RETURNED[`source`]];
// Override the data with managed data if available.
if ((NAME != null) ? NAME.length : false) {
DATA[`managed`] = await managed.read((NAME) ? [...NAME] : null);
DATA_RETURNED[`value`] = (DATA[`managed`] != null) ? DATA[`managed`] : DATA_RETURNED[`value`];
};
return DATA_RETURNED[`value`]; return DATA_RETURNED[`value`];
break; break;
default: default:
CLOUD = (CLOUD > 0) ? 1 : -1; cloud = (cloud > 0) ? 1 : -1;
DATA = await read_database(CLOUD); DATA = await pull(cloud);
DATA_RETURNED = (DATA_NAME) ? find_data(DATA, DATA_NAME) : DATA; DATA_RETURNED = (NAME) ? find(DATA, NAME) : DATA;
return(DATA_RETURNED); return(DATA_RETURNED);
break; break;
} };
} };
/* More enhanced searching. /* More enhanced searching.
@param {Array} SOURCE the source of the data @param {Array} SOURCE the source of the data
@param {string} TERM the term to search @param {string} TERM the term to search
@param {Array} ADDITIONAL_PLACES additional places to search @param {Array} ADDITIONAL_PLACES additional places to search
@param {object} OPTIONS the options @param {object} OPTIONS the options
@return {Array} the results @return {Array} the results
*/ */
export async function search(SOURCE, TERM, ADDITIONAL_PLACES, STRICT = 0, OPTIONS = {}) { static async search(SOURCE, TERM, ADDITIONAL_PLACES, STRICT = 0, OPTIONS = {}) {
let DATA = await read(SOURCE, (OPTIONS[`cloud`] != null) ? OPTIONS[`cloud`] : 0); let DATA = await global.read(SOURCE, (OPTIONS[`cloud`] != null) ? OPTIONS[`cloud`] : 0);
let RESULTS; let RESULTS;
if (DATA) { if (DATA) {
@ -141,10 +118,10 @@ export async function search(SOURCE, TERM, ADDITIONAL_PLACES, STRICT = 0, OPTION
// Then, get the additional places. // Then, get the additional places.
if ((ADDITIONAL_PLACES != null ? Array.isArray(ADDITIONAL_PLACES) : false) ? ADDITIONAL_PLACES.length > 0 : false) { if ((ADDITIONAL_PLACES != null ? Array.isArray(ADDITIONAL_PLACES) : false) ? ADDITIONAL_PLACES.length > 0 : false) {
for (let PARAMETER_PRIORITY_NUMBER = 0; PARAMETER_PRIORITY_NUMBER < ADDITIONAL_PLACES.length; PARAMETER_PRIORITY_NUMBER++) { ADDITIONAL_PLACES.forEach((ADDITIONAL_PLACE) => {
// Recursively search // Recursively search
RESULTS = Object.assign({}, RESULTS, search(SOURCE, TERM, ADDITIONAL_PLACES[PARAMETER_PRIORITY_NUMBER], STRICT)); RESULTS = Object.assign({}, RESULTS, global.search(SOURCE, TERM, ADDITIONAL_PLACE, STRICT));
}; })
} }
} else if (((typeof ADDITIONAL_PLACES).includes(`str`) && (ADDITIONAL_PLACES)) ? ADDITIONAL_PLACES.trim() : false) { } else if (((typeof ADDITIONAL_PLACES).includes(`str`) && (ADDITIONAL_PLACES)) ? ADDITIONAL_PLACES.trim() : false) {
// Perform a sequential search on the data. // Perform a sequential search on the data.
@ -199,41 +176,32 @@ export async function search(SOURCE, TERM, ADDITIONAL_PLACES, STRICT = 0, OPTION
} }
return RESULTS; return RESULTS;
} };
/* Write the data on the selected prefname. /* Write the data on the selected prefname.
@param {string} PATH the preference name @param {string} path the preference name
@param {object} DATA the new data to be written @param {object} data the new data to be written
@param {int} CLOUD store in the cloud; otherwise set to automatic @param {int} CLOUD store in the cloud; otherwise set to automatic
@param {object} OPTIONS the options @param {object} OPTIONS the options
*/ */
export async function write(PATH, DATA, CLOUD = -1, OPTIONS = {}) { static async write(path, data, CLOUD = -1, OPTIONS = {}) {
let DATA_INJECTED = {}; let DATA_INJECTED = {};
// Inform the user that saving is in progress. // Inform the user that saving is in progress.
if (((typeof OPTIONS).includes(`obj`) && OPTIONS != null) ? (!(!!OPTIONS[`silent`])) : true) { (((typeof OPTIONS).includes(`obj`) && OPTIONS != null) ? (!(!!OPTIONS[`silent`])) : true)
new logging ((new texts(`saving_current`)).localized, (new texts(`saving_current_message`)).localized, false) ? new logging ((new texts(`saving_current`)).localized, (new texts(`saving_current_message`)).localized, false)
}; : false;
/* Forcibly write the data to chrome database
@param {object} DATA the data
@param {number} CLOUD the storage
*/
const store = async (DATA, CLOUD = 0) => {
// If CLOUD is set to 0, it should automatically determine where the previous source of data was taken from.
return((CLOUD > 0) ? chrome.storage.sync.set(DATA) : chrome.storage.local.set(DATA));
}
/* Appropriately nest and merge the data. /* Appropriately nest and merge the data.
@param {object} EXISTING the original data @param {object} EXISTING the original data
@param {object} PATH the subpath @param {object} PATH the subpath
@param {object} VALUE the value @param {object} VALUE the value
@param {boolean} STRICT determines whether data is to be overridden or merged
@return {object} the updated data @return {object} the updated data
*/ */
function nest(EXISTING, SUBPATH, VALUE) { function nest(EXISTING, SUBPATH, VALUE, STRICT = false) {
let DATABASE = EXISTING; let DATABASE = EXISTING;
// Get the current path. // Get the current path.
@ -242,13 +210,17 @@ export async function write(PATH, DATA, CLOUD = -1, OPTIONS = {}) {
PATH[`target`] = SUBPATH; PATH[`target`] = SUBPATH;
if (PATH[`target`].length > 0) { if (PATH[`target`].length > 0) {
if (DATABASE[PATH[`current`]] == null) { DATABASE[PATH[`current`]] = (DATABASE[PATH[`current`]] == null)
DATABASE[PATH[`current`]] = {}; ? {}
} : DATABASE[PATH[`current`]];
DATABASE[PATH[`current`]] = nest(DATABASE[PATH[`current`]], PATH[`target`], VALUE); DATABASE[PATH[`current`]] = nest(DATABASE[PATH[`current`]], PATH[`target`], VALUE, STRICT);
} else { } else {
DATABASE[PATH[`current`]] = VALUE; // If not strict and the data selected is a dictionary, then merge them.
DATABASE[PATH[`current`]] = (((DATABASE[PATH[`current`]]) ? ((typeof DATABASE[PATH[`current`]]).includes(`obj`) && !Array.isArray(DATABASE[PATH[`current`]])) : false) && !STRICT)
? Object.assign(DATABASE[PATH[`current`]], VALUE)
: VALUE;
} }
// Return the value. // Return the value.
return DATABASE; return DATABASE;
} }
@ -260,7 +232,7 @@ export async function write(PATH, DATA, CLOUD = -1, OPTIONS = {}) {
DATA_CHECK[`state`] = await compare(NAME, DATA); DATA_CHECK[`state`] = await compare(NAME, DATA);
(!DATA_CHECK[`state`]) (!DATA_CHECK[`state`])
? logging.error((new texts(`error_msg_save_failed`)).localized, String(PATH), JSON.stringify(DATA)) ? logging.error((new texts(`error_msg_save_failed`)).localized, String(path), JSON.stringify(DATA))
: ((((typeof OPTIONS).includes(`obj`) && OPTIONS != null) ? (!(!!OPTIONS[`silent`])) : true) : ((((typeof OPTIONS).includes(`obj`) && OPTIONS != null) ? (!(!!OPTIONS[`silent`])) : true)
? new logging (new texts(`saving_done`).localized) ? new logging (new texts(`saving_done`).localized)
: false); : false);
@ -268,25 +240,79 @@ export async function write(PATH, DATA, CLOUD = -1, OPTIONS = {}) {
return (DATA_CHECK[`state`]); return (DATA_CHECK[`state`]);
} }
let DATA_ALL = await read(null, CLOUD); let DATA_ALL;
if ((DATA_ALL != null && (typeof DATA_ALL).includes(`obj`)) ? Object.keys(DATA_ALL).length <= 0 : true) {
DATA_ALL = {};
};
let DATA_NAME = PATH; // Get all data and set a blank value if it doesn't exist yet.
DATA_ALL = await global.read(null, CLOUD);
DATA_ALL = ((DATA_ALL != null && (typeof DATA_ALL).includes(`obj`)) ? Object.keys(DATA_ALL).length <= 0 : true)
? {}
: DATA_ALL;
// Convert the entered prefname to an array if it is not one. // Set the data name.
if (!(typeof SUBPATH).includes(`object`)) { let DATA_NAME = (!(Array.isArray(path)) && path)
// Split what is not an object. ? String(path).trim().split(",")
DATA_NAME = String(PATH).trim().split(","); : path;
}
// Merge! // Merge!
DATA_INJECTED = nest(DATA_ALL, [...DATA_NAME], DATA); DATA_INJECTED = nest(DATA_ALL, [...DATA_NAME], data, (OPTIONS[`strict`] != null) ? OPTIONS[`strict`] : false);
// If cloud is not selected, get where the data is already existent.
(CLOUD == 0 || CLOUD == null)
? (CLOUD = (DATA_ALL[`local`] != null) ? -1 : 1)
: false;
// Write! // Write!
store(DATA_INJECTED, CLOUD); chrome.storage[(CLOUD > 0) ? `sync` : `local`].set(DATA_INJECTED);
return (verify(DATA_NAME, DATA)); return (verify(DATA_NAME, data));
}
/*
Dangerous: Resets a particular data.
@param {string} preference the preference name to delete
@param {string} subpreference the subpreference name to delete
@param {int} CLOUD the storage of the data
@return {boolean} the user's confirmation
*/
static async forget(preference, CLOUD = 0, override = false) {
// Confirm the action.
let CONFIRMATION = override ? override : await logging.confirm();
if (CONFIRMATION) {
if (preference) {
/*
Erase applicable storage from a provider.
@param {string} name the name of the data
@param {int} cloud the usage of cloud storage
*/
async function erase(name, cloud) {
let DATA_NAME = (!(Array.isArray(name))) ? String(name).trim().split(",") : name;
console.log(DATA_NAME, cloud, [...DATA_NAME.slice(0,-1)]);
let DATA = await global.read((DATA_NAME.length > 1) ? [...DATA_NAME.slice(0,-1)] : null, cloud);
console.log(DATA, DATA_NAME, cloud, [...DATA_NAME.slice(0,-1)]);
(((((typeof (DATA)).includes(`obj`) && !Array.isArray(DATA) && DATA != null) ? Object.keys(DATA) : false) ? Object.keys(DATA).includes(DATA_NAME[DATA_NAME.length - 1]) : false))
? delete DATA[DATA_NAME[DATA_NAME.length - 1]]
: false;
await global.write(DATA_NAME.slice(0,-1), DATA, CLOUD, {"strict": true});
}
(CLOUD >= 0) ? await erase(preference, 1) : false;
(CLOUD <= 0) ? await erase(preference, -1) : false;
} else {
// Clear the data storage.
(CLOUD >= 0) ? chrome.storage.sync.clear() : false;
(CLOUD <= 0) ? chrome.storage.local.clear() : false;
}
}
return CONFIRMATION;
}
} }
class session { class session {
@ -376,33 +402,6 @@ class session {
// Write! // Write!
store(DATA[`inject`]); store(DATA[`inject`]);
} }
/* Compare a data against the stored data. Useful when comparing dictionaries.
@param {string} PATH the name
@param {object} DATA the data to compare to
@return {boolean} the result: true is when the data is the same, false otherwise
*/
static async compare(PATH, DATA) {
/* The actual comparison of data. */
async function comparison(DATA_ONE, DATA_TWO) {
let RESULT = true;
// The first round of checking is on the data type.
RESULT = ((typeof DATA_ONE == typeof DATA_TWO) ? ((Array.isArray(DATA_TWO) == Array.isArray(DATA_ONE)) && !((DATA_ONE == null && DATA_TWO != null) || (DATA_ONE != null && DATA_TWO == null))) : false) ? ((typeof DATA_ONE).includes(`obj`) ? (await hash.digest(DATA_ONE, {"output": "Number"}) == await hash.digest(DATA_TWO, {"output": "Number"})) : DATA_ONE == DATA_TWO) : false;
return (RESULT);
}
let COMPARISON = {};
COMPARISON[`test`] = (PATH) ? DATA : DATA[1];
COMPARISON[`against`] = (PATH) ? (await session.read((Array.isArray(PATH)) ? [...PATH] : PATH)) : DATA[0];
COMPARISON[`result`] = comparison(COMPARISON[`against`], COMPARISON[`test`]);
// Return the result.
return (COMPARISON[`result`]);
}
} }
/* /*
@ -432,130 +431,132 @@ export async function compare(PATH, DATA) {
let COMPARISON = {}; let COMPARISON = {};
COMPARISON[`test`] = (PATH) ? DATA : DATA[1]; COMPARISON[`test`] = (PATH) ? DATA : DATA[1];
COMPARISON[`against`] = (PATH) ? (await read((Array.isArray(PATH)) ? [...PATH] : PATH)) : DATA[0]; COMPARISON[`against`] = (PATH) ? (await global.read((Array.isArray(PATH)) ? [...PATH] : PATH)) : DATA[0];
COMPARISON[`result`] = comparison(COMPARISON[`against`], COMPARISON[`test`]); COMPARISON[`result`] = comparison(COMPARISON[`against`], COMPARISON[`test`]);
// Return the result. // Return the result.
return (COMPARISON[`result`]); return (COMPARISON[`result`]);
} }
/* Dangerous: Resets all data or a domain's data. class template {
/* Initialize the storage.
@param {string} preference the preference name to delete @param {dictionary} data this build's managed data
@param {string} subpreference the subpreference name to delete */
@param {int} CLOUD the storage of the data static set(data) {
@return {boolean} the user's confirmation let PREFERENCES = {};
*/ PREFERENCES[`all`] = {};
export async function forget(preference, CLOUD = 0, override = false) {
// Confirm the action.
let forget_action = override ? override : await logging.confirm();
if (forget_action) { ((typeof data).includes(`obj`) && data != null) ? PREFERENCES[`all`][`build`] = data : false;
if (preference) {
let erase = async (CLOUD) => {
if (!(Array.isArray(preference))) {
preference = String(preference).trim().split(",");
};
let DATA = await read((preference.length > 1) ? [...preference.slice(0,-1)] : null, CLOUD);
if (((((typeof (DATA)).includes(`obj`) && !Array.isArray(DATA) && DATA != null) ? Object.keys(DATA) : false) ? Object.keys(DATA).includes((preference.slice(-1))[0]) : false)) {
delete DATA[preference.slice(-1)];
};
await write(preference.slice(0,-1), DATA, CLOUD);
};
if (CLOUD >= 0) {
erase(1);
};
if (CLOUD <= 0) {
erase(-1);
};
} else {
// Clear the data storage.
if (CLOUD >= 0) {
chrome.storage.sync.clear();
}
if (CLOUD <= 0) {
chrome.storage.local.clear();
}
}
}
return forget_action;
}
/* Initialize the storage.
@param {dictionary} data this build's managed data
*/
export function init(data) {
let PREFERENCES_ALL = {};
PREFERENCES_ALL[`build`] = data;
// Read all data. // Read all data.
chrome.storage.managed.get(null, function (DATA_MANAGED) { [`managed`, `local`, `sync`].forEach((SOURCE) => {
PREFERENCES_ALL[`managed`] = DATA_MANAGED; chrome.storage[SOURCE].get(null, (DATA) => {
PREFERENCES[`all`][SOURCE] = DATA;
})
}); });
chrome.storage.local.get(null, function (DATA_LOCAL) { // Merge the data.
PREFERENCES_ALL[`local`] = DATA_LOCAL;
});
chrome.storage.sync.get(null, function (DATA_SYNC) {
PREFERENCES_ALL[`sync`] = DATA_SYNC;
});
// Merge data.
// Managed > Synchronized > Imported > Local // Managed > Synchronized > Imported > Local
managed.reinforce();
if (PREFERENCES_ALL[`managed`]) { // Set the managed preferences.
Object.keys(PREFERENCES_ALL[`managed`]).forEach((item) => { if ((PREFERENCES[`all`][`managed`] && (typeof PREFERENCES[`all`][`managed`]).includes(`obj`) && !Array.isArray(PREFERENCES[`all`][`managed`])) ? Object.keys(PREFERENCES[`all`][`managed`]).length > 0 : false) {
let PREFERENCE = { name: item, existing: false }; Object.keys(PREFERENCES[`all`][`managed`]).forEach((item) => {
let PREFERENCE = {};
PREFERENCE[`name`] = item;
if (PREFERENCES_ALL[`sync`]) { // Get if the data already exists.
PREFERENCE[`existing`] = PREFERENCES_ALL[`sync`].hasOwnProperty( PREFERENCE[`existing`] = (PREFERENCES[`all`][`sync`] && (typeof PREFERENCES[`all`][`sync`]).includes(`obj`))
PREFERENCE[`name`], ? PREFERENCES[`all`][`sync`].hasOwnProperty(PREFERENCE[`name`])
); : false;
}
if (!PREFERENCE[`existing`]) { if (!PREFERENCE[`existing`]) {
// Do not allow synchronized data to interfere with managed data. // Do not allow synchronized data to interfere with managed data.
forget(PREFERENCE[`name`]); global.forget(PREFERENCE[`name`], 0, true);
write( global.write(PREFERENCE[`name`], PREFERENCES_ALL[`managed`][PREFERENCE[`name`]]);
PREFERENCE[`name`],
PREFERENCES_ALL[`managed`][PREFERENCE[`name`]],
);
} }
}); });
} };
// Import build data // Import build data
if (PREFERENCES_ALL[`build`]) { if (PREFERENCES[`all`][`build`]) {
Object.keys(PREFERENCES_ALL[`build`]).forEach((item) => { Object.keys(PREFERENCES[`all`][`build`]).forEach((item) => {
let PREFERENCE = { name: item, existing: false }; let PREFERENCE = { name: item, existing: false };
PREFERENCE[`existing`] = PREFERENCE[`existing`] =
(PREFERENCES_ALL[`sync`] (PREFERENCES[`all`][`sync`]
? PREFERENCES_ALL[`sync`].hasOwnProperty(PREFERENCE[`name`]) ? PREFERENCES[`all`][`sync`].hasOwnProperty(PREFERENCE[`name`])
: false) || : false) ||
(PREFERENCES_ALL[`managed`] (PREFERENCES[`all`][`managed`]
? PREFERENCES_ALL[`managed`].hasOwnProperty(PREFERENCE[`name`]) ? PREFERENCES[`all`][`managed`].hasOwnProperty(PREFERENCE[`name`])
: false) || : false) ||
(PREFERENCES_ALL[`local`] (PREFERENCES[`all`][`local`]
? PREFERENCES_ALL[`local`].hasOwnProperty(PREFERENCE[`local`]) ? PREFERENCES[`all`][`local`].hasOwnProperty(PREFERENCE[`local`])
: false); : false);
if (!PREFERENCE[`existing`]) { (!PREFERENCE[`existing`])
write( ? global.write(PREFERENCE[`name`], PREFERENCES[`all`][`build`][PREFERENCE[`name`]], -1)
PREFERENCE[`name`], : false;
PREFERENCES_ALL[`build`][PREFERENCE[`name`]],
-1,
);
}
}); });
} }
};
}
/*
managed data functions
*/
class managed {
/*
Reinforce managed data.
*/
static reinforce() {
chrome.storage.managed.get(null, (DATA_MANAGED) => {
// Saving the data asynchronously
(Object.keys(DATA_MANAGED)).forEach(async (SOURCE) => {
await write(SOURCE, DATA_MANAGED[SOURCE], -1, {"strict": false});
});
});
}
/*
Read for any applicable managed data.
@param {string} name the name of the data
@return {boolean} the result
*/
static async read(name) {
function find(DATA_ALL, DATA_PATH) {
let DATA = DATA_ALL;
// Pull the data out.
if (DATA_ALL != null && (Array.isArray(DATA_PATH) && DATA_PATH != null) ? DATA_PATH.length > 0 : false) {
let DATA_PATH_SELECTED = String(DATA_PATH.shift()).trim();
// Get the selected data.
DATA = DATA_ALL[DATA_PATH_SELECTED];
// must run if there is actually a parameter to test
if (DATA_PATH.length > 0) {
// Recursively run to make use of the existing data.
DATA = find(DATA, DATA_PATH);
};
} else {
return null;
}
// Now return the data.
return DATA;
}
let DATA = {};
DATA[`all`] = await chrome.storage.managed.get(null);
DATA[`selected`] = ((DATA[`all`] && (typeof DATA[`all`]).includes(`obj`) && !Array.isArray(DATA[`all`])) ? Object.keys(DATA[`all`]).length : false)
? find(DATA[`all`], name)
: null;
return (DATA[`selected`]);
}
} }
/* /*
@ -569,4 +570,4 @@ export function observe(reaction) {
}); });
} }
export {session} export {global, session, template, managed};