Skip to content

Commit

Permalink
new method for system settings
Browse files Browse the repository at this point in the history
  • Loading branch information
shubhvjain committed Dec 20, 2024
1 parent cce3802 commit f6efbfa
Show file tree
Hide file tree
Showing 3 changed files with 55 additions and 82 deletions.
2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"name": "beanbagdb",
"version": "0.5.72",
"version": "0.5.75",
"description": "A JS library to introduce a schema layer to a No-SQL local database",
"main": "src/index.js",
"module": "src/index.js",
Expand Down
125 changes: 52 additions & 73 deletions src/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -277,7 +277,7 @@ export class BeanBagDB {
}

try {
let new_log_doc = this._get_blank_doc("system_setting")
let new_log_doc = this._get_blank_doc("system_log")
new_log_doc.data = {text,data:{steps},time:this.util_get_now_unix_timestamp(),app:app_data.meta.name}
await this.db_api.insert(new_log_doc);
console.log("init logged")
Expand All @@ -288,78 +288,6 @@ export class BeanBagDB {
}


/**
* Updates a setting document if it already exists in the database or creates a new document
* Inserts or updates a setting in the system settings schema.
*
* This method either:
* - Updates an existing document if the setting with the given `name` already exists in the database.
* - Inserts a new document if no matching setting is found.
*
* If the setting exists and the `value` is an array, the behavior depends on the `on_update_array` key:
* - `"append"`: Appends the new value to the existing array.
* - `"update"`: Replaces the current array with the new value.
*
* @async
* @param {string} name - The name of the setting to insert or update.
* @param {object} new_data - The new data to insert or update.
* @param {*} new_data.value - The value to insert or update.
* @param {string} [new_data.on_update_array] - Optional behavior for handling arrays, either "append" or "update".
* @param {object} [schema={}] - Optional schema to validate the data against (currently not implemented).
* @returns {Promise<object>} - The updated or newly inserted document.
* @throws {Error} - Throws an error if `new_data` or `new_data.value` is not provided, or if `on_update_array` is invalid.
*/
async save_setting_doc(name, new_data, schema = {}) {
// TODO implement schema check
if (!new_data) {
throw new Error("No data provided");
}
if (!new_data.value) {
throw new Error("No value provided");
}

let doc_search = await this.db_api.search({
selector: { schema: "system_setting", "data.name": name },
});
if (doc_search.docs.length > 0) {
// doc already exists, check schema and update it : if it exists then it's value already exists and can be
let doc = { ...doc_search.docs[0] };
if (Array.isArray(doc.data.value)) {
let append_type = doc.data.on_update_array;
if (append_type == "append") {
doc["data"]["value"].push(new_data.value);
} else if (append_type == "update") {
doc["data"]["value"] = new_data.value;
} else {
throw new Error("Invalid on update array value");
}
} else {
doc["data"]["value"] = new_data.value;
}
// finally update it
doc["meta"]["updated_on"] = this.util_get_now_unix_timestamp();
await this.db_api.update(doc);
return doc;
} else {
// doc does not exists, generate a new one
let new_val = { value: new_data.value };

if (new_data.on_update_array) {
// this indicates the provided value is initial value inside the array
new_val.value = [new_data.value];
new_val.on_update_array = new_data.on_update_array;
}
let new_doc = this._get_blank_doc("system_setting");
new_doc["data"] = {
name: name,
...new_val,
};
let d = await this.db_api.insert(new_doc);
return d;
}
}


/**
* Adds indexes for all the schemas in the data base. This is important to make search faster. This must be done every time a new schema is introduced in the database
*/
Expand Down Expand Up @@ -594,6 +522,49 @@ export class BeanBagDB {
}


/**
* Check if the setting with the given name exists. New record created if not found. If found data is updated based on the updated_mode and the data type of the existing data
* If existing value is an array, and update_mode is append "value" is appended to the current value array.
* if existing value is an object, update_mode "append" will update fields that exists in the new object,
* for both data types, new value is replaced in update_mode : "replace"
* @param {string} name The name of the setting
* @param {object} value Value to be modified
* @param {string} mode
*/
async modify_setting(name,value,update_mode){
if(!name||!value||!update_mode){
throw new DocUpdateError("All 3 inputs (setting name, value and update_mode) are required")
}
let doc_search = await this.db_api.search({
selector: { schema: "system_setting", "data.name": name },
});

if (!["append", "update"].includes(update_mode)) {
throw new DocUpdateError("Invalid update_mode");
}

if (doc_search.docs.length > 0) {
// doc already exists,
let doc = { ...doc_search.docs[0] };
if (Array.isArray(value)) {
doc.data.value = update_mode === "append" ? [...value, new_data] : new_data; // "update" mode replaces the value
} else {
doc.data.value = update_mode === "append" ? { ...value, ...new_data } : new_data; // "update" mode replaces the value
}
// finally update it
doc["meta"]["updated_on"] = this.util_get_now_unix_timestamp();
// caution : db api is being used directly
await this.db_api.update(doc);
return doc;

} else {
// doc does not exists, generate a new one
let new_doc = {value, name};
let d = await this.create("system_setting",new_doc)
return d;
}
}

/**
* Deletes a document from the database by its ID.
*
Expand Down Expand Up @@ -732,6 +703,14 @@ export class BeanBagDB {
//////////////// simple directed graph ////////////////////////
//////////////////////////////////////////////////////////

/**
* To add an edge between 2 nodes in the system wide simple directed graph.
* @param {object} node1
* @param {object} node2
* @param {string} edge_name
* @param {*} edge_label
* @returns
*/
async create_edge(node1,node2,edge_name,edge_label=""){
this._check_ready_to_use();
if(!edge_name){throw new ValidationError("edge_name required")}
Expand Down
10 changes: 2 additions & 8 deletions src/system_schema.js
Original file line number Diff line number Diff line change
Expand Up @@ -144,7 +144,7 @@ export const default_app = {
},
},
{
version:0.60,
version:0.65,
system_generated:true,
description:"The system relies on these settings for proper functioning or enabling optional features.",
name: "system_setting",
Expand All @@ -160,13 +160,7 @@ export const default_app = {
pattern: "^[a-zA-Z][a-zA-Z0-9_]*$",
},
value: {
type: ["string", "number", "boolean", "array"]
},
on_update_array:{
type:"string",
default:"replace",
description:"Special operation only for updating Arrays. Either replace it or append new elements to it. Cannot be edited",
enum:["replace","append"],
type: ["array","object"]
}
},
},
Expand Down

0 comments on commit f6efbfa

Please sign in to comment.