inibase 1.0.0-rc.6 → 1.0.0-rc.8
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 +1 -55
- package/file.ts +70 -26
- package/index.test.ts +8 -2
- package/index.ts +176 -242
- package/package.json +5 -5
- package/utils.server.ts +79 -0
- package/utils.ts +77 -86
package/README.md
CHANGED
|
@@ -8,7 +8,7 @@
|
|
|
8
8
|
|
|
9
9
|
## Features
|
|
10
10
|
|
|
11
|
-
- **Lightweight** 🪶 (~
|
|
11
|
+
- **Lightweight** 🪶 (~80kb)
|
|
12
12
|
- **Minimalist** :white_circle:
|
|
13
13
|
- **TypeScript** :large_blue_diamond:
|
|
14
14
|
- **Super-Fast** :turtle:
|
|
@@ -385,60 +385,6 @@ await db.put("user", { isActive: false });
|
|
|
385
385
|
|
|
386
386
|
</details>
|
|
387
387
|
|
|
388
|
-
## Typescript
|
|
389
|
-
|
|
390
|
-
<details>
|
|
391
|
-
<summary>Schema</summary>
|
|
392
|
-
|
|
393
|
-
```js
|
|
394
|
-
type Schema = Field[];
|
|
395
|
-
type Field = {
|
|
396
|
-
id?: string | number | null | undefined,
|
|
397
|
-
key: string,
|
|
398
|
-
required?: boolean,
|
|
399
|
-
} & (
|
|
400
|
-
| {
|
|
401
|
-
type: Exclude<FieldType, "array" | "object">,
|
|
402
|
-
required?: boolean,
|
|
403
|
-
}
|
|
404
|
-
| {
|
|
405
|
-
type: "array",
|
|
406
|
-
children: FieldType | FieldType[] | Schema,
|
|
407
|
-
}
|
|
408
|
-
| {
|
|
409
|
-
type: "object",
|
|
410
|
-
children: Schema,
|
|
411
|
-
}
|
|
412
|
-
);
|
|
413
|
-
type FieldType =
|
|
414
|
-
| "string"
|
|
415
|
-
| "number"
|
|
416
|
-
| "boolean"
|
|
417
|
-
| "date"
|
|
418
|
-
| "email"
|
|
419
|
-
| "url"
|
|
420
|
-
| "table"
|
|
421
|
-
| "object"
|
|
422
|
-
| "array"
|
|
423
|
-
| "password";
|
|
424
|
-
```
|
|
425
|
-
|
|
426
|
-
</details>
|
|
427
|
-
|
|
428
|
-
<details>
|
|
429
|
-
<summary>Data</summary>
|
|
430
|
-
|
|
431
|
-
```js
|
|
432
|
-
type Data = {
|
|
433
|
-
id?: number | string,
|
|
434
|
-
[key: string]: any,
|
|
435
|
-
created_at?: Date,
|
|
436
|
-
updated_at?: Date,
|
|
437
|
-
};
|
|
438
|
-
```
|
|
439
|
-
|
|
440
|
-
</details>
|
|
441
|
-
|
|
442
388
|
## Roadmap
|
|
443
389
|
|
|
444
390
|
- [x] Actions:
|
package/file.ts
CHANGED
|
@@ -3,7 +3,8 @@ import { open, unlink, rename, stat } from "node:fs/promises";
|
|
|
3
3
|
import { Interface, createInterface } from "node:readline";
|
|
4
4
|
import { parse } from "node:path";
|
|
5
5
|
import { ComparisonOperator, FieldType } from ".";
|
|
6
|
-
import
|
|
6
|
+
import { detectFieldType, isArrayOfArrays, isNumber } from "./utils";
|
|
7
|
+
import { encodeID, decodeID, comparePassword } from "./utils.server";
|
|
7
8
|
|
|
8
9
|
const doesSupportReadLines = () => {
|
|
9
10
|
const [major, minor, patch] = process.versions.node.split(".").map(Number);
|
|
@@ -30,7 +31,13 @@ export const decodeFileName = (fileName: string) => {
|
|
|
30
31
|
};
|
|
31
32
|
|
|
32
33
|
export const encode = (
|
|
33
|
-
input:
|
|
34
|
+
input:
|
|
35
|
+
| string
|
|
36
|
+
| number
|
|
37
|
+
| boolean
|
|
38
|
+
| null
|
|
39
|
+
| (string | number | boolean | null)[],
|
|
40
|
+
secretKey?: string | Buffer
|
|
34
41
|
) => {
|
|
35
42
|
const secureString = (input: string | number | boolean | null) => {
|
|
36
43
|
if (["true", "false"].includes(String(input))) return input ? 1 : 0;
|
|
@@ -45,7 +52,7 @@ export const encode = (
|
|
|
45
52
|
: input;
|
|
46
53
|
};
|
|
47
54
|
return Array.isArray(input)
|
|
48
|
-
?
|
|
55
|
+
? isArrayOfArrays(input)
|
|
49
56
|
? (input as any[])
|
|
50
57
|
.map((_input) => _input.map(secureString).join(","))
|
|
51
58
|
.join("|")
|
|
@@ -56,7 +63,8 @@ export const encode = (
|
|
|
56
63
|
export const decode = (
|
|
57
64
|
input: string | null | number,
|
|
58
65
|
fieldType?: FieldType | FieldType[],
|
|
59
|
-
fieldChildrenType?: FieldType | FieldType[]
|
|
66
|
+
fieldChildrenType?: FieldType | FieldType[],
|
|
67
|
+
secretKey?: string | Buffer
|
|
60
68
|
): string | number | boolean | null | (string | number | null | boolean)[] => {
|
|
61
69
|
if (!fieldType) return null;
|
|
62
70
|
const unSecureString = (input: string) =>
|
|
@@ -69,29 +77,34 @@ export const decode = (
|
|
|
69
77
|
.replaceAll("\\r", "\r") || null;
|
|
70
78
|
if (input === null || input === "") return null;
|
|
71
79
|
if (Array.isArray(fieldType))
|
|
72
|
-
fieldType =
|
|
80
|
+
fieldType = detectFieldType(String(input), fieldType);
|
|
73
81
|
const decodeHelper = (value: string | number | any[]) => {
|
|
74
82
|
if (Array.isArray(value) && fieldType !== "array")
|
|
75
83
|
return value.map(decodeHelper);
|
|
76
84
|
switch (fieldType as FieldType) {
|
|
77
85
|
case "table":
|
|
78
86
|
case "number":
|
|
79
|
-
return
|
|
87
|
+
return isNumber(value) ? Number(value) : null;
|
|
80
88
|
case "boolean":
|
|
81
89
|
return typeof value === "string" ? value === "true" : Boolean(value);
|
|
82
90
|
case "array":
|
|
83
91
|
if (!Array.isArray(value)) return [value];
|
|
92
|
+
|
|
84
93
|
if (fieldChildrenType)
|
|
85
94
|
return value.map(
|
|
86
95
|
(v) =>
|
|
87
96
|
decode(
|
|
88
97
|
v,
|
|
89
98
|
Array.isArray(fieldChildrenType)
|
|
90
|
-
?
|
|
91
|
-
: fieldChildrenType
|
|
99
|
+
? detectFieldType(v, fieldChildrenType)
|
|
100
|
+
: fieldChildrenType,
|
|
101
|
+
undefined,
|
|
102
|
+
secretKey
|
|
92
103
|
) as string | number | boolean | null
|
|
93
104
|
);
|
|
94
105
|
else return value;
|
|
106
|
+
case "id":
|
|
107
|
+
return isNumber(value) ? encodeID(value as number, secretKey) : value;
|
|
95
108
|
default:
|
|
96
109
|
return value;
|
|
97
110
|
}
|
|
@@ -104,6 +117,16 @@ export const decode = (
|
|
|
104
117
|
.split("|")
|
|
105
118
|
.map((_input) => _input.split(",").map(unSecureString))
|
|
106
119
|
: input.split(",").map(unSecureString)
|
|
120
|
+
: input.includes("|")
|
|
121
|
+
? input
|
|
122
|
+
.split("|")
|
|
123
|
+
.map((_input) => [
|
|
124
|
+
_input
|
|
125
|
+
? fieldType === "array"
|
|
126
|
+
? [unSecureString(_input)]
|
|
127
|
+
: unSecureString(_input)
|
|
128
|
+
: null,
|
|
129
|
+
])
|
|
107
130
|
: unSecureString(input)
|
|
108
131
|
: input
|
|
109
132
|
);
|
|
@@ -113,8 +136,20 @@ export const get = async (
|
|
|
113
136
|
filePath: string,
|
|
114
137
|
lineNumbers?: number | number[],
|
|
115
138
|
fieldType?: FieldType | FieldType[],
|
|
116
|
-
fieldChildrenType?: FieldType | FieldType[]
|
|
117
|
-
|
|
139
|
+
fieldChildrenType?: FieldType | FieldType[],
|
|
140
|
+
secretKey?: string | Buffer
|
|
141
|
+
): Promise<
|
|
142
|
+
[
|
|
143
|
+
Record<
|
|
144
|
+
number,
|
|
145
|
+
| string
|
|
146
|
+
| number
|
|
147
|
+
| boolean
|
|
148
|
+
| (string | number | boolean | (string | number | boolean)[])[]
|
|
149
|
+
> | null,
|
|
150
|
+
number
|
|
151
|
+
]
|
|
152
|
+
> => {
|
|
118
153
|
let rl: Interface;
|
|
119
154
|
if (doesSupportReadLines()) rl = (await open(filePath)).readLines();
|
|
120
155
|
else
|
|
@@ -135,12 +170,19 @@ export const get = async (
|
|
|
135
170
|
if (!lineNumbers) {
|
|
136
171
|
for await (const line of rl)
|
|
137
172
|
lineCount++,
|
|
138
|
-
(lines[lineCount] = decode(
|
|
173
|
+
(lines[lineCount] = decode(
|
|
174
|
+
line,
|
|
175
|
+
fieldType,
|
|
176
|
+
fieldChildrenType,
|
|
177
|
+
secretKey
|
|
178
|
+
));
|
|
139
179
|
} else if (lineNumbers === -1) {
|
|
140
180
|
let lastLine: string;
|
|
141
181
|
for await (const line of rl) lineCount++, (lastLine = line);
|
|
142
182
|
if (lastLine)
|
|
143
|
-
lines = {
|
|
183
|
+
lines = {
|
|
184
|
+
[lineCount]: decode(lastLine, fieldType, fieldChildrenType, secretKey),
|
|
185
|
+
};
|
|
144
186
|
} else {
|
|
145
187
|
let lineNumbersArray = [
|
|
146
188
|
...(Array.isArray(lineNumbers) ? lineNumbers : [lineNumbers]),
|
|
@@ -149,13 +191,13 @@ export const get = async (
|
|
|
149
191
|
lineCount++;
|
|
150
192
|
if (!lineNumbersArray.includes(lineCount)) continue;
|
|
151
193
|
const indexOfLineCount = lineNumbersArray.indexOf(lineCount);
|
|
152
|
-
lines[lineCount] = decode(line, fieldType, fieldChildrenType);
|
|
194
|
+
lines[lineCount] = decode(line, fieldType, fieldChildrenType, secretKey);
|
|
153
195
|
lineNumbersArray[indexOfLineCount] = 0;
|
|
154
196
|
if (!lineNumbersArray.filter((lineN) => lineN !== 0).length) break;
|
|
155
197
|
}
|
|
156
198
|
}
|
|
157
199
|
|
|
158
|
-
return lines ?? null;
|
|
200
|
+
return [lines ?? null, lineCount];
|
|
159
201
|
};
|
|
160
202
|
|
|
161
203
|
export const replace = async (
|
|
@@ -169,7 +211,8 @@ export const replace = async (
|
|
|
169
211
|
| Record<
|
|
170
212
|
number,
|
|
171
213
|
string | boolean | number | null | (string | boolean | number | null)[]
|
|
172
|
-
|
|
214
|
+
>,
|
|
215
|
+
secretKey?: string | Buffer
|
|
173
216
|
) => {
|
|
174
217
|
if (await isExists(filePath)) {
|
|
175
218
|
let rl: Interface, writeStream: WriteStream;
|
|
@@ -189,13 +232,14 @@ export const replace = async (
|
|
|
189
232
|
for await (const line of rl) {
|
|
190
233
|
lineCount++;
|
|
191
234
|
writeStream.write(
|
|
192
|
-
(lineCount in replacements
|
|
193
|
-
|
|
235
|
+
(lineCount in replacements
|
|
236
|
+
? encode(replacements[lineCount], secretKey)
|
|
237
|
+
: line) + "\n"
|
|
194
238
|
);
|
|
195
239
|
}
|
|
196
240
|
} else
|
|
197
241
|
for await (const _line of rl)
|
|
198
|
-
writeStream.write(encode(replacements) + "\n");
|
|
242
|
+
writeStream.write(encode(replacements, secretKey) + "\n");
|
|
199
243
|
|
|
200
244
|
writeStream.end();
|
|
201
245
|
} else if (typeof replacements === "object" && !Array.isArray(replacements)) {
|
|
@@ -207,8 +251,9 @@ export const replace = async (
|
|
|
207
251
|
Math.max(...Object.keys(replacements).map(Number)) + 1;
|
|
208
252
|
for (let lineCount = 1; lineCount < largestLinesNumbers; lineCount++) {
|
|
209
253
|
writeStream.write(
|
|
210
|
-
(lineCount in replacements
|
|
211
|
-
|
|
254
|
+
(lineCount in replacements
|
|
255
|
+
? encode(replacements[lineCount], secretKey)
|
|
256
|
+
: "") + "\n"
|
|
212
257
|
);
|
|
213
258
|
}
|
|
214
259
|
writeStream.end();
|
|
@@ -280,7 +325,7 @@ export const search = async (
|
|
|
280
325
|
limit?: number,
|
|
281
326
|
offset?: number,
|
|
282
327
|
readWholeFile?: boolean,
|
|
283
|
-
secretKey?: string
|
|
328
|
+
secretKey?: string | Buffer
|
|
284
329
|
): Promise<
|
|
285
330
|
[
|
|
286
331
|
Record<
|
|
@@ -311,7 +356,7 @@ export const search = async (
|
|
|
311
356
|
fieldChildrenType?: FieldType | FieldType[]
|
|
312
357
|
): boolean => {
|
|
313
358
|
if (Array.isArray(fieldType))
|
|
314
|
-
fieldType =
|
|
359
|
+
fieldType = detectFieldType(String(originalValue), fieldType);
|
|
315
360
|
if (Array.isArray(comparedAtValue) && !["[]", "![]"].includes(operator))
|
|
316
361
|
return comparedAtValue.some((comparedAtValueSingle) =>
|
|
317
362
|
handleComparisonOperator(
|
|
@@ -328,14 +373,13 @@ export const search = async (
|
|
|
328
373
|
case "password":
|
|
329
374
|
return typeof originalValue === "string" &&
|
|
330
375
|
typeof comparedAtValue === "string"
|
|
331
|
-
?
|
|
376
|
+
? comparePassword(originalValue, comparedAtValue)
|
|
332
377
|
: false;
|
|
333
378
|
case "boolean":
|
|
334
379
|
return Number(originalValue) - Number(comparedAtValue) === 0;
|
|
335
380
|
case "id":
|
|
336
381
|
return secretKey && typeof comparedAtValue === "string"
|
|
337
|
-
?
|
|
338
|
-
originalValue
|
|
382
|
+
? decodeID(comparedAtValue as string, secretKey) === originalValue
|
|
339
383
|
: comparedAtValue === originalValue;
|
|
340
384
|
default:
|
|
341
385
|
return originalValue === comparedAtValue;
|
|
@@ -415,7 +459,7 @@ export const search = async (
|
|
|
415
459
|
|
|
416
460
|
for await (const line of rl) {
|
|
417
461
|
lineCount++;
|
|
418
|
-
const decodedLine = decode(line, fieldType, fieldChildrenType);
|
|
462
|
+
const decodedLine = decode(line, fieldType, fieldChildrenType, secretKey);
|
|
419
463
|
if (
|
|
420
464
|
(Array.isArray(operator) &&
|
|
421
465
|
Array.isArray(comparedAtValue) &&
|
package/index.test.ts
CHANGED
|
@@ -197,8 +197,14 @@ const data_2 = [
|
|
|
197
197
|
try {
|
|
198
198
|
// db.setTableSchema("database", schema_2);
|
|
199
199
|
// const DATA = await db.post("database", data_2);
|
|
200
|
-
const DATA = await db.get("database",
|
|
201
|
-
console.log(
|
|
200
|
+
const DATA = await db.get("database", 1);
|
|
201
|
+
console.log(
|
|
202
|
+
JSON.stringify(
|
|
203
|
+
(DATA as Data).tables.find((table: any) => table.slug === "session"),
|
|
204
|
+
null,
|
|
205
|
+
4
|
|
206
|
+
)
|
|
207
|
+
);
|
|
202
208
|
} catch (er) {
|
|
203
209
|
console.log(er);
|
|
204
210
|
}
|