twin-db 1.1.2 → 1.3.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -1,16 +1,15 @@
1
1
  ### Before All
2
- Make sure you're using `"type": "module"` in package.json.<br>
3
2
  Make sure to pass just values that JSON accepts, if not, the values will be changed to `null`.
4
3
  # How to Use?
5
4
  To create a new database make the following step:
6
5
  ```js
7
- import TwinDB from 'twin-db';
6
+ import { TwinDB } from 'twin-db';
8
7
  const database = new TwinDB('db');
9
8
  ```
10
9
  And your database is done.
11
10
  ### You can make various databases too:
12
11
  ```js
13
- import TwinDB from 'twin-db';
12
+ import { TwinDB } from 'twin-db';
14
13
  const database = new TwinDB('db');
15
14
  const coolDatabase = new TwinDB('cool');
16
15
  ```
@@ -90,3 +89,9 @@ database.pull('hobbies', 'cs', 'sleep') // now the hobbies is ["pizza", "valoran
90
89
  `MM/DD/YYYY`<br>
91
90
  04/09/2026 - 1.1.*
92
91
  - Now **sum**, **sub** and **push** sets the value to the value you passed in execution when the path does not exists.
92
+
93
+ 05/03/2026 - 1.2.*
94
+ - Now package doesn't uses eval anymore, providing better security.
95
+
96
+ 06/29/2026 - 1.3.*
97
+ - Added support to require in commonjs.
package/dist/index.cjs ADDED
@@ -0,0 +1,168 @@
1
+ "use strict";
2
+ var __defProp = Object.defineProperty;
3
+ var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
4
+ var __getOwnPropNames = Object.getOwnPropertyNames;
5
+ var __hasOwnProp = Object.prototype.hasOwnProperty;
6
+ var __export = (target, all) => {
7
+ for (var name in all)
8
+ __defProp(target, name, { get: all[name], enumerable: true });
9
+ };
10
+ var __copyProps = (to, from, except, desc) => {
11
+ if (from && typeof from === "object" || typeof from === "function") {
12
+ for (let key of __getOwnPropNames(from))
13
+ if (!__hasOwnProp.call(to, key) && key !== except)
14
+ __defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });
15
+ }
16
+ return to;
17
+ };
18
+ var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
19
+
20
+ // src/index.ts
21
+ var index_exports = {};
22
+ __export(index_exports, {
23
+ TwinDB: () => TwinDB
24
+ });
25
+ module.exports = __toCommonJS(index_exports);
26
+
27
+ // src/structures/database.ts
28
+ var import_fs = require("fs");
29
+ var pathErrorMessage = "The path must be a string or you dont provide a path";
30
+ var TwinDB = class {
31
+ constructor(name = "db") {
32
+ this.path = "database/" + name + ".json";
33
+ this.name = name;
34
+ this.data = {};
35
+ if (!(0, import_fs.existsSync)("database")) (0, import_fs.mkdirSync)("database");
36
+ this.load();
37
+ }
38
+ load() {
39
+ let data;
40
+ try {
41
+ data = (0, import_fs.readFileSync)(this.path, "utf8");
42
+ } catch (e) {
43
+ data = "";
44
+ }
45
+ this.data = data ? JSON.parse(data) : {};
46
+ if (!data)
47
+ (0, import_fs.writeFileSync)(
48
+ this.path,
49
+ JSON.stringify(this.data, null, 2),
50
+ "utf8"
51
+ );
52
+ }
53
+ update(path, value) {
54
+ const keys = path.split(".");
55
+ let current = this.data;
56
+ for (let i = 0; i < keys.length; i++) {
57
+ let key = keys[i];
58
+ if (i === keys.length - 1) {
59
+ current[key] = value;
60
+ break;
61
+ }
62
+ if (typeof current[key] !== "object" || Array.isArray(current[key]) || !current[key]) {
63
+ current[key] = {};
64
+ }
65
+ current = current[key];
66
+ }
67
+ (0, import_fs.writeFileSync)(this.path, JSON.stringify(this.data, null, 2), "utf8");
68
+ return this.data;
69
+ }
70
+ set(path, value) {
71
+ if (!path || typeof path !== "string")
72
+ throw new Error(pathErrorMessage);
73
+ if (value === void 0)
74
+ throw new Error("You must provide a value to update");
75
+ return this.update(path, value);
76
+ }
77
+ get(path) {
78
+ if (!path || typeof path !== "string")
79
+ throw new Error(pathErrorMessage);
80
+ const keys = path.split(".");
81
+ let current = this.data;
82
+ let i = 0;
83
+ for (const key of keys) {
84
+ i++;
85
+ if (i === keys.length) return current[key] ?? null;
86
+ if (typeof current[key] !== "object") return null;
87
+ current = current[key];
88
+ }
89
+ }
90
+ delete(path) {
91
+ if (!path || typeof path !== "string")
92
+ throw new Error(pathErrorMessage);
93
+ const keys = path.split(".");
94
+ const pathExists = this.get(path);
95
+ if (pathExists === null)
96
+ throw new Error("The path does not exists or its value is null");
97
+ this.update(path, null);
98
+ (0, import_fs.writeFileSync)(this.path, JSON.stringify(this.data, null, 2), "utf8");
99
+ return this.data;
100
+ }
101
+ sumOrSub(path, value, type) {
102
+ if (!path || typeof path !== "string")
103
+ throw new Error(pathErrorMessage);
104
+ if (!type || !["sum", "sub"].includes(type))
105
+ throw new Error('The type must be "sum" or "sub"');
106
+ const isSum = type === "sum";
107
+ if (!value || typeof value !== "number")
108
+ throw new Error(
109
+ `The value to ${isSum ? "sum" : "sub"} must be a number`
110
+ );
111
+ let currentValue = this.get(path) || 0;
112
+ if (typeof currentValue !== "number") currentValue = 0;
113
+ return this.update(
114
+ path,
115
+ isSum ? currentValue + value : currentValue - value
116
+ );
117
+ }
118
+ sum(path, value) {
119
+ return this.sumOrSub(path, value, "sum");
120
+ }
121
+ sub(path, value) {
122
+ return this.sumOrSub(path, value, "sub");
123
+ }
124
+ concat(path, value) {
125
+ if (!path || typeof path !== "string")
126
+ throw new Error(pathErrorMessage);
127
+ if (!value || typeof value !== "string")
128
+ throw new Error("You must provide a string value to update");
129
+ const currentValue = this.get(path);
130
+ if (typeof currentValue !== "string")
131
+ throw new Error(
132
+ "The value to concat is not a string or the path does not exists"
133
+ );
134
+ return this.update(path, currentValue + value);
135
+ }
136
+ push(path, ...values) {
137
+ if (!path || typeof path !== "string")
138
+ throw new Error(pathErrorMessage);
139
+ if (!values || values.length === 0)
140
+ throw new Error("You must provide a value to update");
141
+ let currentValue = this.get(path) || [];
142
+ if (!Array.isArray(currentValue)) currentValue = [];
143
+ currentValue.push(...values);
144
+ return this.update(path, currentValue);
145
+ }
146
+ pull(path, ...values) {
147
+ if (!path || typeof path !== "string")
148
+ throw new Error(pathErrorMessage);
149
+ if (!values || values.length === 0)
150
+ throw new Error("You must provide a value to update");
151
+ const currentValue = this.get(path);
152
+ if (!Array.isArray(currentValue))
153
+ throw new Error(
154
+ "The current value of this path is not an array or the path does not exists"
155
+ );
156
+ for (const value of values) {
157
+ const index = currentValue.indexOf(value);
158
+ if (index < 0) continue;
159
+ currentValue.splice(index, 1);
160
+ }
161
+ return this.update(path, currentValue);
162
+ }
163
+ };
164
+ // Annotate the CommonJS export names for ESM import in node:
165
+ 0 && (module.exports = {
166
+ TwinDB
167
+ });
168
+ //# sourceMappingURL=index.cjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../src/index.ts","../src/structures/database.ts"],"sourcesContent":["import { TwinDB } from './structures/database';\n\nexport { TwinDB };","import { readFileSync, writeFileSync, mkdirSync, existsSync } from 'fs';\n\nconst pathErrorMessage = 'The path must be a string or you dont provide a path';\n\nexport class TwinDB {\n public data: Record<string, unknown>;\n public path: string;\n public name: string;\n\n public constructor(name: string = 'db') {\n this.path = 'database/' + name + '.json';\n this.name = name;\n this.data = {};\n\n if (!existsSync('database')) mkdirSync('database');\n this.load();\n }\n\n private load() {\n let data: string;\n try {\n data = readFileSync(this.path, 'utf8');\n } catch (e) {\n data = '';\n }\n this.data = data ? JSON.parse(data) : {};\n\n if (!data)\n writeFileSync(\n this.path,\n JSON.stringify(this.data, null, 2),\n 'utf8',\n );\n }\n\n private update(path: string /*user.info.name*/, value: unknown) {\n const keys = path.split('.');\n\n let current = this.data;\n for (let i = 0; i < keys.length; i++) {\n let key = keys[i];\n\n if (i === keys.length - 1) {\n current[key] = value;\n break;\n } \n \n if (typeof current[key] !== 'object' || Array.isArray(current[key]) || !current[key]) {\n current[key] = {};\n }\n\n current = current[key] as Record<string, unknown>;\n }\n\n writeFileSync(this.path, JSON.stringify(this.data, null, 2), 'utf8');\n\n return this.data;\n }\n\n public set(path: string, value: unknown) {\n if (!path || typeof path !== 'string')\n throw new Error(pathErrorMessage);\n if (value === undefined)\n throw new Error('You must provide a value to update');\n\n return this.update(path, value);\n }\n\n public get(path: string): unknown | null {\n if (!path || typeof path !== 'string')\n throw new Error(pathErrorMessage);\n const keys = path.split('.');\n let current = this.data;\n let i = 0;\n\n for (const key of keys) {\n i++;\n\n if (i === keys.length) return current[key] ?? null;\n\n if (typeof current[key] !== 'object') return null;\n\n current = current[key] as Record<string, unknown>;\n }\n }\n\n public delete(path: string) {\n if (!path || typeof path !== 'string')\n throw new Error(pathErrorMessage);\n const keys = path.split('.');\n const pathExists = this.get(path);\n if (pathExists === null)\n throw new Error('The path does not exists or its value is null');\n\n this.update(path, null);\n\n writeFileSync(this.path, JSON.stringify(this.data, null, 2), 'utf8');\n\n return this.data;\n }\n\n private sumOrSub(path: string, value: number, type: SumOrSub) {\n if (!path || typeof path !== 'string')\n throw new Error(pathErrorMessage);\n if (!type || !['sum', 'sub'].includes(type))\n throw new Error('The type must be \"sum\" or \"sub\"');\n const isSum = type === 'sum';\n if (!value || typeof value !== 'number')\n throw new Error(\n `The value to ${isSum ? 'sum' : 'sub'} must be a number`,\n );\n\n let currentValue = (this.get(path) || 0) as unknown as number;\n if (typeof currentValue !== 'number') currentValue = 0;\n\n return this.update(\n path,\n isSum ? currentValue + value : currentValue - value,\n );\n }\n\n public sum(path: string, value: number) {\n return this.sumOrSub(path, value, 'sum');\n }\n\n public sub(path: string, value: number) {\n return this.sumOrSub(path, value, 'sub');\n }\n\n public concat(path: string, value: string) {\n if (!path || typeof path !== 'string')\n throw new Error(pathErrorMessage);\n if (!value || typeof value !== 'string')\n throw new Error('You must provide a string value to update');\n\n const currentValue = this.get(path);\n if (typeof currentValue !== 'string')\n throw new Error(\n 'The value to concat is not a string or the path does not exists',\n );\n\n return this.update(path, currentValue + value);\n }\n\n public push(path: string, ...values: unknown[]) {\n if (!path || typeof path !== 'string')\n throw new Error(pathErrorMessage);\n if (!values || values.length === 0)\n throw new Error('You must provide a value to update');\n\n let currentValue = (this.get(path) || []) as unknown as unknown[];\n if (!Array.isArray(currentValue)) currentValue = [];\n\n currentValue.push(...values);\n return this.update(path, currentValue);\n }\n\n public pull(path: string, ...values: unknown[]) {\n if (!path || typeof path !== 'string')\n throw new Error(pathErrorMessage);\n if (!values || values.length === 0)\n throw new Error('You must provide a value to update');\n\n const currentValue = this.get(path);\n if (!Array.isArray(currentValue))\n throw new Error(\n 'The current value of this path is not an array or the path does not exists',\n );\n\n for (const value of values) {\n const index = currentValue.indexOf(value);\n if (index < 0) continue;\n\n currentValue.splice(index, 1);\n }\n\n return this.update(path, currentValue);\n }\n}\n\nexport type SumOrSub = 'sum' | 'sub';\n"],"mappings":"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","names":[]}
@@ -0,0 +1,19 @@
1
+ declare class TwinDB {
2
+ data: Record<string, unknown>;
3
+ path: string;
4
+ name: string;
5
+ constructor(name?: string);
6
+ private load;
7
+ private update;
8
+ set(path: string, value: unknown): Record<string, unknown>;
9
+ get(path: string): unknown | null;
10
+ delete(path: string): Record<string, unknown>;
11
+ private sumOrSub;
12
+ sum(path: string, value: number): Record<string, unknown>;
13
+ sub(path: string, value: number): Record<string, unknown>;
14
+ concat(path: string, value: string): Record<string, unknown>;
15
+ push(path: string, ...values: unknown[]): Record<string, unknown>;
16
+ pull(path: string, ...values: unknown[]): Record<string, unknown>;
17
+ }
18
+
19
+ export { TwinDB };
package/dist/index.d.ts CHANGED
@@ -1,2 +1,19 @@
1
- import { TwinDB } from './structures/database';
2
- export default TwinDB;
1
+ declare class TwinDB {
2
+ data: Record<string, unknown>;
3
+ path: string;
4
+ name: string;
5
+ constructor(name?: string);
6
+ private load;
7
+ private update;
8
+ set(path: string, value: unknown): Record<string, unknown>;
9
+ get(path: string): unknown | null;
10
+ delete(path: string): Record<string, unknown>;
11
+ private sumOrSub;
12
+ sum(path: string, value: number): Record<string, unknown>;
13
+ sub(path: string, value: number): Record<string, unknown>;
14
+ concat(path: string, value: string): Record<string, unknown>;
15
+ push(path: string, ...values: unknown[]): Record<string, unknown>;
16
+ pull(path: string, ...values: unknown[]): Record<string, unknown>;
17
+ }
18
+
19
+ export { TwinDB };
package/dist/index.js CHANGED
@@ -1,2 +1,141 @@
1
- import { TwinDB } from './structures/database.js';
2
- export default TwinDB;
1
+ // src/structures/database.ts
2
+ import { readFileSync, writeFileSync, mkdirSync, existsSync } from "fs";
3
+ var pathErrorMessage = "The path must be a string or you dont provide a path";
4
+ var TwinDB = class {
5
+ constructor(name = "db") {
6
+ this.path = "database/" + name + ".json";
7
+ this.name = name;
8
+ this.data = {};
9
+ if (!existsSync("database")) mkdirSync("database");
10
+ this.load();
11
+ }
12
+ load() {
13
+ let data;
14
+ try {
15
+ data = readFileSync(this.path, "utf8");
16
+ } catch (e) {
17
+ data = "";
18
+ }
19
+ this.data = data ? JSON.parse(data) : {};
20
+ if (!data)
21
+ writeFileSync(
22
+ this.path,
23
+ JSON.stringify(this.data, null, 2),
24
+ "utf8"
25
+ );
26
+ }
27
+ update(path, value) {
28
+ const keys = path.split(".");
29
+ let current = this.data;
30
+ for (let i = 0; i < keys.length; i++) {
31
+ let key = keys[i];
32
+ if (i === keys.length - 1) {
33
+ current[key] = value;
34
+ break;
35
+ }
36
+ if (typeof current[key] !== "object" || Array.isArray(current[key]) || !current[key]) {
37
+ current[key] = {};
38
+ }
39
+ current = current[key];
40
+ }
41
+ writeFileSync(this.path, JSON.stringify(this.data, null, 2), "utf8");
42
+ return this.data;
43
+ }
44
+ set(path, value) {
45
+ if (!path || typeof path !== "string")
46
+ throw new Error(pathErrorMessage);
47
+ if (value === void 0)
48
+ throw new Error("You must provide a value to update");
49
+ return this.update(path, value);
50
+ }
51
+ get(path) {
52
+ if (!path || typeof path !== "string")
53
+ throw new Error(pathErrorMessage);
54
+ const keys = path.split(".");
55
+ let current = this.data;
56
+ let i = 0;
57
+ for (const key of keys) {
58
+ i++;
59
+ if (i === keys.length) return current[key] ?? null;
60
+ if (typeof current[key] !== "object") return null;
61
+ current = current[key];
62
+ }
63
+ }
64
+ delete(path) {
65
+ if (!path || typeof path !== "string")
66
+ throw new Error(pathErrorMessage);
67
+ const keys = path.split(".");
68
+ const pathExists = this.get(path);
69
+ if (pathExists === null)
70
+ throw new Error("The path does not exists or its value is null");
71
+ this.update(path, null);
72
+ writeFileSync(this.path, JSON.stringify(this.data, null, 2), "utf8");
73
+ return this.data;
74
+ }
75
+ sumOrSub(path, value, type) {
76
+ if (!path || typeof path !== "string")
77
+ throw new Error(pathErrorMessage);
78
+ if (!type || !["sum", "sub"].includes(type))
79
+ throw new Error('The type must be "sum" or "sub"');
80
+ const isSum = type === "sum";
81
+ if (!value || typeof value !== "number")
82
+ throw new Error(
83
+ `The value to ${isSum ? "sum" : "sub"} must be a number`
84
+ );
85
+ let currentValue = this.get(path) || 0;
86
+ if (typeof currentValue !== "number") currentValue = 0;
87
+ return this.update(
88
+ path,
89
+ isSum ? currentValue + value : currentValue - value
90
+ );
91
+ }
92
+ sum(path, value) {
93
+ return this.sumOrSub(path, value, "sum");
94
+ }
95
+ sub(path, value) {
96
+ return this.sumOrSub(path, value, "sub");
97
+ }
98
+ concat(path, value) {
99
+ if (!path || typeof path !== "string")
100
+ throw new Error(pathErrorMessage);
101
+ if (!value || typeof value !== "string")
102
+ throw new Error("You must provide a string value to update");
103
+ const currentValue = this.get(path);
104
+ if (typeof currentValue !== "string")
105
+ throw new Error(
106
+ "The value to concat is not a string or the path does not exists"
107
+ );
108
+ return this.update(path, currentValue + value);
109
+ }
110
+ push(path, ...values) {
111
+ if (!path || typeof path !== "string")
112
+ throw new Error(pathErrorMessage);
113
+ if (!values || values.length === 0)
114
+ throw new Error("You must provide a value to update");
115
+ let currentValue = this.get(path) || [];
116
+ if (!Array.isArray(currentValue)) currentValue = [];
117
+ currentValue.push(...values);
118
+ return this.update(path, currentValue);
119
+ }
120
+ pull(path, ...values) {
121
+ if (!path || typeof path !== "string")
122
+ throw new Error(pathErrorMessage);
123
+ if (!values || values.length === 0)
124
+ throw new Error("You must provide a value to update");
125
+ const currentValue = this.get(path);
126
+ if (!Array.isArray(currentValue))
127
+ throw new Error(
128
+ "The current value of this path is not an array or the path does not exists"
129
+ );
130
+ for (const value of values) {
131
+ const index = currentValue.indexOf(value);
132
+ if (index < 0) continue;
133
+ currentValue.splice(index, 1);
134
+ }
135
+ return this.update(path, currentValue);
136
+ }
137
+ };
138
+ export {
139
+ TwinDB
140
+ };
141
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../src/structures/database.ts"],"sourcesContent":["import { readFileSync, writeFileSync, mkdirSync, existsSync } from 'fs';\n\nconst pathErrorMessage = 'The path must be a string or you dont provide a path';\n\nexport class TwinDB {\n public data: Record<string, unknown>;\n public path: string;\n public name: string;\n\n public constructor(name: string = 'db') {\n this.path = 'database/' + name + '.json';\n this.name = name;\n this.data = {};\n\n if (!existsSync('database')) mkdirSync('database');\n this.load();\n }\n\n private load() {\n let data: string;\n try {\n data = readFileSync(this.path, 'utf8');\n } catch (e) {\n data = '';\n }\n this.data = data ? JSON.parse(data) : {};\n\n if (!data)\n writeFileSync(\n this.path,\n JSON.stringify(this.data, null, 2),\n 'utf8',\n );\n }\n\n private update(path: string /*user.info.name*/, value: unknown) {\n const keys = path.split('.');\n\n let current = this.data;\n for (let i = 0; i < keys.length; i++) {\n let key = keys[i];\n\n if (i === keys.length - 1) {\n current[key] = value;\n break;\n } \n \n if (typeof current[key] !== 'object' || Array.isArray(current[key]) || !current[key]) {\n current[key] = {};\n }\n\n current = current[key] as Record<string, unknown>;\n }\n\n writeFileSync(this.path, JSON.stringify(this.data, null, 2), 'utf8');\n\n return this.data;\n }\n\n public set(path: string, value: unknown) {\n if (!path || typeof path !== 'string')\n throw new Error(pathErrorMessage);\n if (value === undefined)\n throw new Error('You must provide a value to update');\n\n return this.update(path, value);\n }\n\n public get(path: string): unknown | null {\n if (!path || typeof path !== 'string')\n throw new Error(pathErrorMessage);\n const keys = path.split('.');\n let current = this.data;\n let i = 0;\n\n for (const key of keys) {\n i++;\n\n if (i === keys.length) return current[key] ?? null;\n\n if (typeof current[key] !== 'object') return null;\n\n current = current[key] as Record<string, unknown>;\n }\n }\n\n public delete(path: string) {\n if (!path || typeof path !== 'string')\n throw new Error(pathErrorMessage);\n const keys = path.split('.');\n const pathExists = this.get(path);\n if (pathExists === null)\n throw new Error('The path does not exists or its value is null');\n\n this.update(path, null);\n\n writeFileSync(this.path, JSON.stringify(this.data, null, 2), 'utf8');\n\n return this.data;\n }\n\n private sumOrSub(path: string, value: number, type: SumOrSub) {\n if (!path || typeof path !== 'string')\n throw new Error(pathErrorMessage);\n if (!type || !['sum', 'sub'].includes(type))\n throw new Error('The type must be \"sum\" or \"sub\"');\n const isSum = type === 'sum';\n if (!value || typeof value !== 'number')\n throw new Error(\n `The value to ${isSum ? 'sum' : 'sub'} must be a number`,\n );\n\n let currentValue = (this.get(path) || 0) as unknown as number;\n if (typeof currentValue !== 'number') currentValue = 0;\n\n return this.update(\n path,\n isSum ? currentValue + value : currentValue - value,\n );\n }\n\n public sum(path: string, value: number) {\n return this.sumOrSub(path, value, 'sum');\n }\n\n public sub(path: string, value: number) {\n return this.sumOrSub(path, value, 'sub');\n }\n\n public concat(path: string, value: string) {\n if (!path || typeof path !== 'string')\n throw new Error(pathErrorMessage);\n if (!value || typeof value !== 'string')\n throw new Error('You must provide a string value to update');\n\n const currentValue = this.get(path);\n if (typeof currentValue !== 'string')\n throw new Error(\n 'The value to concat is not a string or the path does not exists',\n );\n\n return this.update(path, currentValue + value);\n }\n\n public push(path: string, ...values: unknown[]) {\n if (!path || typeof path !== 'string')\n throw new Error(pathErrorMessage);\n if (!values || values.length === 0)\n throw new Error('You must provide a value to update');\n\n let currentValue = (this.get(path) || []) as unknown as unknown[];\n if (!Array.isArray(currentValue)) currentValue = [];\n\n currentValue.push(...values);\n return this.update(path, currentValue);\n }\n\n public pull(path: string, ...values: unknown[]) {\n if (!path || typeof path !== 'string')\n throw new Error(pathErrorMessage);\n if (!values || values.length === 0)\n throw new Error('You must provide a value to update');\n\n const currentValue = this.get(path);\n if (!Array.isArray(currentValue))\n throw new Error(\n 'The current value of this path is not an array or the path does not exists',\n );\n\n for (const value of values) {\n const index = currentValue.indexOf(value);\n if (index < 0) continue;\n\n currentValue.splice(index, 1);\n }\n\n return this.update(path, currentValue);\n }\n}\n\nexport type SumOrSub = 'sum' | 'sub';\n"],"mappings":"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","names":[]}
package/package.json CHANGED
@@ -1,18 +1,30 @@
1
1
  {
2
2
  "name": "twin-db",
3
- "version": "1.1.2",
3
+ "version": "1.3.0",
4
4
  "description": "A usefully local database.",
5
5
  "main": "dist/index.js",
6
- "module": "dist/index.js",
6
+ "module": "dist/index.mjs",
7
7
  "types": "dist/index.d.ts",
8
8
  "type": "module",
9
9
  "files": [
10
10
  "dist"
11
11
  ],
12
+ "exports": {
13
+ ".": {
14
+ "import": {
15
+ "types": "./dist/index.d.mts",
16
+ "default": "./dist/index.mjs"
17
+ },
18
+ "require": {
19
+ "types": "./dist/index.d.ts",
20
+ "default": "./dist/index.js"
21
+ }
22
+ }
23
+ },
12
24
  "scripts": {
13
25
  "test": "tsx src/index.ts",
14
26
  "prettier": "npx prettier --write \"**/*.{js,ts}\"",
15
- "build": "npx tsc"
27
+ "build": "npx tsup"
16
28
  },
17
29
  "author": {
18
30
  "name": "Jaelson Kaciel",
@@ -29,7 +41,9 @@
29
41
  ],
30
42
  "license": "MIT",
31
43
  "devDependencies": {
44
+ "@types/node": "^25.6.0",
32
45
  "prettier": "^3.8.1",
46
+ "tsup": "^8.5.1",
33
47
  "tsx": "^4.21.0",
34
48
  "typescript": "^6.0.2"
35
49
  },
@@ -1,18 +0,0 @@
1
- export declare class TwinDB {
2
- data: object;
3
- path: string;
4
- name: string;
5
- constructor(name?: string);
6
- private load;
7
- private update;
8
- set(path: string, value: unknown): Promise<object>;
9
- get(path: string): unknown | null;
10
- delete(path: string): Promise<object>;
11
- private sumOrSub;
12
- sum(path: string, value: number): Promise<object>;
13
- sub(path: string, value: number): Promise<object>;
14
- concat(path: string, value: string): Promise<object>;
15
- push(path: string, ...values: unknown[]): Promise<object>;
16
- pull(path: string, ...values: unknown[]): Promise<object>;
17
- }
18
- export type SumOrSub = 'sum' | 'sub';
@@ -1,133 +0,0 @@
1
- import { readFileSync, writeFileSync, mkdirSync, existsSync } from 'fs';
2
- const pathErrorMessage = 'The path must be a string or you dont provide a path';
3
- export class TwinDB {
4
- data;
5
- path;
6
- name;
7
- constructor(name = 'db') {
8
- this.path = 'database/' + name + '.json';
9
- this.name = name;
10
- if (!existsSync('database'))
11
- mkdirSync('database');
12
- this.load();
13
- }
14
- async load() {
15
- let data;
16
- try {
17
- data = readFileSync(this.path, 'utf8');
18
- }
19
- catch (e) {
20
- data = '';
21
- }
22
- this.data = data ? JSON.parse(data) : {};
23
- if (!data)
24
- writeFileSync(this.path, JSON.stringify(this.data, null, 2), 'utf8');
25
- }
26
- async update(path /*user.info.name*/, value) {
27
- const keys = path.split('.');
28
- if (keys.length > 1)
29
- for (let i = 0; i < keys.length - 1; i++) {
30
- const thisKeys = keys.slice(0, i + 1);
31
- const mappedKeys = thisKeys.map((key) => `['${key}']`);
32
- const searchedValue = await eval('this.data' + mappedKeys.join(''));
33
- if (typeof searchedValue !== 'object')
34
- await eval('this.data' + mappedKeys.join('') + ' = {}');
35
- } // percorre todos os objetos definindo eles como {} para não dar erro abaixo
36
- await eval('this.data' +
37
- keys.map((key) => `['${key}']`).join('') +
38
- ` = ${JSON.stringify(value)}`);
39
- writeFileSync(this.path, JSON.stringify(this.data, null, 2), 'utf8');
40
- return this.data;
41
- }
42
- set(path, value) {
43
- if (!path || typeof path !== 'string')
44
- throw new Error(pathErrorMessage);
45
- if (value === undefined)
46
- throw new Error('You must provide a value to update');
47
- return this.update(path, value);
48
- }
49
- get(path) {
50
- if (!path || typeof path !== 'string')
51
- throw new Error(pathErrorMessage);
52
- const keys = path.split('.');
53
- let current = this.data;
54
- let i = 0;
55
- for (const key of keys) {
56
- i++;
57
- if (i === keys.length)
58
- return current[key] ?? null;
59
- if (typeof current[key] !== 'object')
60
- return null;
61
- current = current[key];
62
- }
63
- }
64
- async delete(path) {
65
- if (!path || typeof path !== 'string')
66
- throw new Error(pathErrorMessage);
67
- const keys = path.split('.');
68
- const pathExists = this.get(path);
69
- if (pathExists === null)
70
- throw new Error('The path does not exists or its value is null');
71
- const success = await eval('delete this.data' + keys.map((key) => `['${key}']`).join(''));
72
- if (!success)
73
- throw new Error('Could not delete the value');
74
- writeFileSync(this.path, JSON.stringify(this.data, null, 2), 'utf8');
75
- return this.data;
76
- }
77
- sumOrSub(path, value, type) {
78
- if (!path || typeof path !== 'string')
79
- throw new Error(pathErrorMessage);
80
- if (!type || !['sum', 'sub'].includes(type))
81
- throw new Error('The type must be "sum" or "sub"');
82
- const isSum = type === 'sum';
83
- if (!value || typeof value !== 'number')
84
- throw new Error(`The value to ${isSum ? 'sum' : 'sub'} must be a number`);
85
- let currentValue = (this.get(path) || 0);
86
- if (typeof currentValue !== 'number')
87
- currentValue = 0;
88
- return this.update(path, isSum ? currentValue + value : currentValue - value);
89
- }
90
- sum(path, value) {
91
- return this.sumOrSub(path, value, 'sum');
92
- }
93
- sub(path, value) {
94
- return this.sumOrSub(path, value, 'sub');
95
- }
96
- concat(path, value) {
97
- if (!path || typeof path !== 'string')
98
- throw new Error(pathErrorMessage);
99
- if (!value || typeof value !== 'string')
100
- throw new Error('You must provide a string value to update');
101
- const currentValue = this.get(path);
102
- if (typeof currentValue !== 'string')
103
- throw new Error('The value to concat is not a string or the path does not exists');
104
- return this.update(path, currentValue + value);
105
- }
106
- push(path, ...values) {
107
- if (!path || typeof path !== 'string')
108
- throw new Error(pathErrorMessage);
109
- if (!values || values.length === 0)
110
- throw new Error('You must provide a value to update');
111
- let currentValue = (this.get(path) || []);
112
- if (!Array.isArray(currentValue))
113
- currentValue = [];
114
- currentValue.push(...values);
115
- return this.update(path, currentValue);
116
- }
117
- pull(path, ...values) {
118
- if (!path || typeof path !== 'string')
119
- throw new Error(pathErrorMessage);
120
- if (!values || values.length === 0)
121
- throw new Error('You must provide a value to update');
122
- const currentValue = this.get(path);
123
- if (!Array.isArray(currentValue))
124
- throw new Error('The value to pull is not an array or the path does not exists');
125
- for (const value of values) {
126
- const index = currentValue.indexOf(value);
127
- if (index < 0)
128
- continue;
129
- currentValue.splice(index, 1);
130
- }
131
- return this.update(path, currentValue);
132
- }
133
- }