@naturalcycles/db-lib 8.27.0 → 8.28.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.
@@ -13,12 +13,11 @@ import { CommonDaoCfg, CommonDaoCreateOptions, CommonDaoOptions, CommonDaoSaveOp
13
13
  export declare class CommonDao<BM extends Partial<ObjectWithId>, DBM extends ObjectWithId = Saved<BM>, TM = BM> {
14
14
  cfg: CommonDaoCfg<BM, DBM, TM>;
15
15
  constructor(cfg: CommonDaoCfg<BM, DBM, TM>);
16
- create(input: Partial<BM>, opt?: CommonDaoOptions): Saved<BM>;
16
+ create(part: Partial<BM>, opt?: CommonDaoOptions): Saved<BM>;
17
17
  getById(id: undefined, opt?: CommonDaoOptions): Promise<null>;
18
18
  getById(id?: string, opt?: CommonDaoOptions): Promise<Saved<BM> | null>;
19
- getByIdOrCreate(id: string, bmToCreate: Partial<BM>, opt?: CommonDaoOptions): Promise<Saved<BM>>;
20
- getByIdOrEmpty(id: string, opt?: CommonDaoOptions): Promise<Saved<BM>>;
21
- getByIdAsDBMOrEmpty(id: string, opt?: CommonDaoOptions): Promise<DBM>;
19
+ getByIdOrEmpty(id: string, part: Partial<BM>, opt?: CommonDaoOptions): Promise<Saved<BM>>;
20
+ getByIdAsDBMOrEmpty(id: string, part: Partial<BM>, opt?: CommonDaoOptions): Promise<DBM>;
22
21
  getByIdAsDBM(id: undefined, opt?: CommonDaoOptions): Promise<null>;
23
22
  getByIdAsDBM(id?: string, opt?: CommonDaoOptions): Promise<DBM | null>;
24
23
  getByIdAsTM(id: undefined, opt?: CommonDaoOptions): Promise<null>;
@@ -44,8 +44,8 @@ class CommonDao {
44
44
  };
45
45
  }
46
46
  // CREATE
47
- create(input, opt = {}) {
48
- let bm = this.cfg.hooks.beforeCreate(input);
47
+ create(part, opt = {}) {
48
+ let bm = this.cfg.hooks.beforeCreate(part);
49
49
  bm = this.validateAndConvert(bm, this.cfg.bmSchema, db_model_1.DBModelType.BM, opt);
50
50
  // If no SCHEMA - return as is
51
51
  return this.assignIdCreatedUpdated(bm, opt);
@@ -71,23 +71,17 @@ class CommonDao {
71
71
  this.logResult(started, op, bm, table);
72
72
  return bm || null;
73
73
  }
74
- async getByIdOrCreate(id, bmToCreate, opt) {
74
+ async getByIdOrEmpty(id, part, opt) {
75
75
  const bm = await this.getById(id, opt);
76
76
  if (bm)
77
77
  return bm;
78
- return this.create({ ...bmToCreate, id }, opt);
78
+ return this.create({ ...part, id }, opt);
79
79
  }
80
- async getByIdOrEmpty(id, opt) {
81
- const bm = await this.getById(id, opt);
82
- if (bm)
83
- return bm;
84
- return this.create({ id }, opt);
85
- }
86
- async getByIdAsDBMOrEmpty(id, opt) {
80
+ async getByIdAsDBMOrEmpty(id, part, opt) {
87
81
  const dbm = await this.getByIdAsDBM(id, opt);
88
82
  if (dbm)
89
83
  return dbm;
90
- const bm = this.create({ id }, opt);
84
+ const bm = this.create({ ...part, id }, opt);
91
85
  return await this.bmToDBM(bm, opt);
92
86
  }
93
87
  async getByIdAsDBM(id, opt = {}) {
@@ -458,7 +452,7 @@ class CommonDao {
458
452
  */
459
453
  async patch(id, patch, opt = {}) {
460
454
  return await this.save({
461
- ...(await this.getByIdOrCreate(id, patch, opt)),
455
+ ...(await this.getByIdOrEmpty(id, patch, opt)),
462
456
  ...patch,
463
457
  }, opt);
464
458
  }
@@ -4,7 +4,7 @@ import { CommonDB } from '../common.db';
4
4
  import { CommonDBCreateOptions, CommonDBOptions, CommonDBSaveOptions } from '../db.model';
5
5
  export declare type CommonDaoCreateIdHook<BM, DBM> = (obj: DBM | BM) => string;
6
6
  export declare type CommonDaoParseNaturalIdHook<DBM> = (id: string) => Partial<DBM>;
7
- export declare type CommonDaoBeforeCreateHook<BM> = (bm: Partial<BM>) => BM;
7
+ export declare type CommonDaoBeforeCreateHook<BM> = (bm: Partial<BM>) => Partial<BM>;
8
8
  export declare type CommonDaoBeforeDBMValidateHook<DBM> = (dbm: Partial<DBM>) => Partial<DBM>;
9
9
  export declare type CommonDaoBeforeDBMToBMHook<BM, DBM> = (dbm: DBM) => Partial<BM> | Promise<Partial<BM>>;
10
10
  export declare type CommonDaoBeforeBMToDBMHook<BM, DBM> = (bm: BM) => Partial<DBM> | Promise<Partial<DBM>>;
@@ -21,8 +21,9 @@ export interface CommonKeyValueDaoCfg<T> {
21
21
  */
22
22
  logStarted?: boolean;
23
23
  hooks?: {
24
- mapValueToBuffer(v: T): Promise<Buffer>;
25
- mapBufferToValue(b: Buffer): Promise<T>;
24
+ mapValueToBuffer?: (v: T) => Promise<Buffer>;
25
+ mapBufferToValue?: (b: Buffer) => Promise<T>;
26
+ beforeCreate?: (v: Partial<T>) => Partial<T>;
26
27
  };
27
28
  }
28
29
  export declare class CommonKeyValueDao<T> {
@@ -30,7 +31,10 @@ export declare class CommonKeyValueDao<T> {
30
31
  constructor(cfg: CommonKeyValueDaoCfg<T>);
31
32
  ping(): Promise<void>;
32
33
  createTable(opt?: CommonDBCreateOptions): Promise<void>;
34
+ create(input?: Partial<T>): T;
33
35
  getById(id?: string): Promise<T | null>;
36
+ getByIdOrEmpty(id: string, part?: Partial<T>): Promise<T>;
37
+ patch(id: string, patch: Partial<T>): Promise<T>;
34
38
  getByIds(ids: string[]): Promise<KeyValueTuple<string, T>[]>;
35
39
  save(id: string, value: T): Promise<void>;
36
40
  saveBatch(entries: KeyValueTuple<string, T>[]): Promise<void>;
@@ -15,12 +15,34 @@ class CommonKeyValueDao {
15
15
  async createTable(opt = {}) {
16
16
  await this.cfg.db.createTable(this.cfg.table, opt);
17
17
  }
18
+ create(input = {}) {
19
+ return {
20
+ ...this.cfg.hooks?.beforeCreate?.(input),
21
+ };
22
+ }
18
23
  async getById(id) {
19
24
  if (!id)
20
25
  return null;
21
26
  const [r] = await this.getByIds([id]);
22
27
  return r?.[1] || null;
23
28
  }
29
+ async getByIdOrEmpty(id, part = {}) {
30
+ const [r] = await this.getByIds([id]);
31
+ if (r)
32
+ return r[1];
33
+ return {
34
+ ...this.cfg.hooks?.beforeCreate?.({}),
35
+ ...part,
36
+ };
37
+ }
38
+ async patch(id, patch) {
39
+ const v = {
40
+ ...(await this.getByIdOrEmpty(id)),
41
+ ...patch,
42
+ };
43
+ await this.save(id, v);
44
+ return v;
45
+ }
24
46
  async getByIds(ids) {
25
47
  const entries = await this.cfg.db.getByIds(this.cfg.table, ids);
26
48
  if (!this.cfg.hooks?.mapBufferToValue)
package/package.json CHANGED
@@ -43,7 +43,7 @@
43
43
  "engines": {
44
44
  "node": ">=14.15"
45
45
  },
46
- "version": "8.27.0",
46
+ "version": "8.28.0",
47
47
  "description": "Lowest Common Denominator API to supported Databases",
48
48
  "keywords": [
49
49
  "db",
@@ -13,7 +13,7 @@ import { CommonDBCreateOptions, CommonDBOptions, CommonDBSaveOptions } from '../
13
13
  // Hook DBM, BM, TM types should follow this exact order
14
14
  export type CommonDaoCreateIdHook<BM, DBM> = (obj: DBM | BM) => string
15
15
  export type CommonDaoParseNaturalIdHook<DBM> = (id: string) => Partial<DBM>
16
- export type CommonDaoBeforeCreateHook<BM> = (bm: Partial<BM>) => BM
16
+ export type CommonDaoBeforeCreateHook<BM> = (bm: Partial<BM>) => Partial<BM>
17
17
  export type CommonDaoBeforeDBMValidateHook<DBM> = (dbm: Partial<DBM>) => Partial<DBM>
18
18
  export type CommonDaoBeforeDBMToBMHook<BM, DBM> = (dbm: DBM) => Partial<BM> | Promise<Partial<BM>>
19
19
  export type CommonDaoBeforeBMToDBMHook<BM, DBM> = (bm: BM) => Partial<DBM> | Promise<Partial<DBM>>
@@ -88,8 +88,8 @@ export class CommonDao<
88
88
  }
89
89
 
90
90
  // CREATE
91
- create(input: Partial<BM>, opt: CommonDaoOptions = {}): Saved<BM> {
92
- let bm = this.cfg.hooks!.beforeCreate!(input)
91
+ create(part: Partial<BM>, opt: CommonDaoOptions = {}): Saved<BM> {
92
+ let bm = this.cfg.hooks!.beforeCreate!(part) as BM
93
93
  bm = this.validateAndConvert(bm, this.cfg.bmSchema, DBModelType.BM, opt)
94
94
 
95
95
  // If no SCHEMA - return as is
@@ -124,29 +124,18 @@ export class CommonDao<
124
124
  return bm || null
125
125
  }
126
126
 
127
- async getByIdOrCreate(
128
- id: string,
129
- bmToCreate: Partial<BM>,
130
- opt?: CommonDaoOptions,
131
- ): Promise<Saved<BM>> {
132
- const bm = await this.getById(id, opt)
133
- if (bm) return bm
134
-
135
- return this.create({ ...bmToCreate, id }, opt)
136
- }
137
-
138
- async getByIdOrEmpty(id: string, opt?: CommonDaoOptions): Promise<Saved<BM>> {
127
+ async getByIdOrEmpty(id: string, part: Partial<BM>, opt?: CommonDaoOptions): Promise<Saved<BM>> {
139
128
  const bm = await this.getById(id, opt)
140
129
  if (bm) return bm
141
130
 
142
- return this.create({ id } as Partial<BM>, opt)
131
+ return this.create({ ...part, id }, opt)
143
132
  }
144
133
 
145
- async getByIdAsDBMOrEmpty(id: string, opt?: CommonDaoOptions): Promise<DBM> {
134
+ async getByIdAsDBMOrEmpty(id: string, part: Partial<BM>, opt?: CommonDaoOptions): Promise<DBM> {
146
135
  const dbm = await this.getByIdAsDBM(id, opt)
147
136
  if (dbm) return dbm
148
137
 
149
- const bm: BM = this.create({ id } as Partial<BM>, opt) as any
138
+ const bm: BM = this.create({ ...part, id }, opt) as any
150
139
  return await this.bmToDBM(bm, opt)
151
140
  }
152
141
 
@@ -614,7 +603,7 @@ export class CommonDao<
614
603
  ): Promise<Saved<BM>> {
615
604
  return await this.save(
616
605
  {
617
- ...(await this.getByIdOrCreate(id, patch, opt)),
606
+ ...(await this.getByIdOrEmpty(id, patch, opt)),
618
607
  ...patch,
619
608
  } as any,
620
609
  opt,
@@ -26,8 +26,9 @@ export interface CommonKeyValueDaoCfg<T> {
26
26
  logStarted?: boolean
27
27
 
28
28
  hooks?: {
29
- mapValueToBuffer(v: T): Promise<Buffer>
30
- mapBufferToValue(b: Buffer): Promise<T>
29
+ mapValueToBuffer?: (v: T) => Promise<Buffer>
30
+ mapBufferToValue?: (b: Buffer) => Promise<T>
31
+ beforeCreate?: (v: Partial<T>) => Partial<T>
31
32
  }
32
33
  }
33
34
 
@@ -45,19 +46,46 @@ export class CommonKeyValueDao<T> {
45
46
  await this.cfg.db.createTable(this.cfg.table, opt)
46
47
  }
47
48
 
49
+ create(input: Partial<T> = {}): T {
50
+ return {
51
+ ...this.cfg.hooks?.beforeCreate?.(input),
52
+ } as T
53
+ }
54
+
48
55
  async getById(id?: string): Promise<T | null> {
49
56
  if (!id) return null
50
57
  const [r] = await this.getByIds([id])
51
58
  return r?.[1] || null
52
59
  }
53
60
 
61
+ async getByIdOrEmpty(id: string, part: Partial<T> = {}): Promise<T> {
62
+ const [r] = await this.getByIds([id])
63
+ if (r) return r[1]
64
+
65
+ return {
66
+ ...this.cfg.hooks?.beforeCreate?.({}),
67
+ ...part,
68
+ } as T
69
+ }
70
+
71
+ async patch(id: string, patch: Partial<T>): Promise<T> {
72
+ const v: T = {
73
+ ...(await this.getByIdOrEmpty(id)),
74
+ ...patch,
75
+ }
76
+
77
+ await this.save(id, v)
78
+
79
+ return v
80
+ }
81
+
54
82
  async getByIds(ids: string[]): Promise<KeyValueTuple<string, T>[]> {
55
83
  const entries = await this.cfg.db.getByIds(this.cfg.table, ids)
56
84
  if (!this.cfg.hooks?.mapBufferToValue) return entries as any
57
85
 
58
86
  return await pMap(entries, async ([id, buf]) => [
59
87
  id,
60
- await this.cfg.hooks!.mapBufferToValue(buf),
88
+ await this.cfg.hooks!.mapBufferToValue!(buf),
61
89
  ])
62
90
  }
63
91
 
@@ -73,7 +101,7 @@ export class CommonKeyValueDao<T> {
73
101
  } else {
74
102
  bufferEntries = await pMap(entries, async ([id, v]) => [
75
103
  id,
76
- await this.cfg.hooks!.mapValueToBuffer(v),
104
+ await this.cfg.hooks!.mapValueToBuffer!(v),
77
105
  ])
78
106
  }
79
107
 
@@ -100,7 +128,7 @@ export class CommonKeyValueDao<T> {
100
128
  // todo: consider it when readableMap supports `errorMode: SUPPRESS`
101
129
  // readableMap(this.cfg.db.streamValues(this.cfg.table, limit), async buf => await this.cfg.hooks!.mapBufferToValue(buf))
102
130
  return this.cfg.db.streamValues(this.cfg.table, limit).pipe(
103
- transformMap(async buf => await this.cfg.hooks!.mapBufferToValue(buf), {
131
+ transformMap(async buf => await this.cfg.hooks!.mapBufferToValue!(buf), {
104
132
  errorMode: ErrorMode.SUPPRESS, // cause .pipe cannot propagate errors
105
133
  }),
106
134
  )
@@ -112,7 +140,7 @@ export class CommonKeyValueDao<T> {
112
140
  }
113
141
 
114
142
  return this.cfg.db.streamEntries(this.cfg.table, limit).pipe(
115
- transformMap(async ([id, buf]) => [id, await this.cfg.hooks!.mapBufferToValue(buf)], {
143
+ transformMap(async ([id, buf]) => [id, await this.cfg.hooks!.mapBufferToValue!(buf)], {
116
144
  errorMode: ErrorMode.SUPPRESS, // cause .pipe cannot propagate errors
117
145
  }),
118
146
  )