@sqb/connect 4.12.0 → 4.13.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.
Files changed (65) hide show
  1. package/cjs/client/cursor.js +1 -1
  2. package/cjs/client/extensions.js +38 -11
  3. package/cjs/client/helpers.js +7 -6
  4. package/cjs/client/sqb-client.js +2 -2
  5. package/cjs/client/sqb-connection.js +7 -4
  6. package/cjs/index.js +19 -20
  7. package/cjs/orm/backward.js +5 -5
  8. package/cjs/orm/commands/command.helper.js +39 -11
  9. package/cjs/orm/commands/create.command.js +2 -1
  10. package/cjs/orm/commands/find.command.js +21 -35
  11. package/cjs/orm/commands/row-converter.js +5 -10
  12. package/cjs/orm/decorators/column.decorator.js +6 -3
  13. package/cjs/orm/decorators/embedded.decorator.js +1 -2
  14. package/cjs/orm/decorators/entity.decorator.js +1 -2
  15. package/cjs/orm/decorators/events.decorator.js +6 -7
  16. package/cjs/orm/decorators/foreignkey.decorator.js +1 -2
  17. package/cjs/orm/decorators/index.decorator.js +1 -2
  18. package/cjs/orm/decorators/link.decorator.js +7 -5
  19. package/cjs/orm/decorators/primarykey.decorator.js +3 -3
  20. package/cjs/orm/decorators/transform.decorator.js +2 -3
  21. package/cjs/orm/model/association.js +9 -11
  22. package/cjs/orm/model/entity-metadata.js +4 -2
  23. package/cjs/orm/orm.const.js +2 -1
  24. package/cjs/orm/repository.class.js +31 -36
  25. package/cjs/orm/util/apply-mixins.js +3 -3
  26. package/cjs/orm/util/extract-keyvalues.js +7 -5
  27. package/cjs/orm/util/orm.helper.js +8 -12
  28. package/cjs/orm/util/parse-fields-projection.js +64 -0
  29. package/cjs/orm/util/serialize-field.js +1 -2
  30. package/esm/client/cursor.js +1 -1
  31. package/esm/client/extensions.js +36 -8
  32. package/esm/client/helpers.js +2 -0
  33. package/esm/client/sqb-client.js +3 -3
  34. package/esm/client/sqb-connection.js +7 -4
  35. package/esm/index.js +18 -17
  36. package/esm/orm/commands/command.helper.js +36 -7
  37. package/esm/orm/commands/create.command.js +2 -1
  38. package/esm/orm/commands/find.command.js +21 -35
  39. package/esm/orm/commands/row-converter.js +5 -10
  40. package/esm/orm/decorators/column.decorator.js +5 -1
  41. package/esm/orm/decorators/link.decorator.js +6 -3
  42. package/esm/orm/decorators/primarykey.decorator.js +2 -1
  43. package/esm/orm/model/association.js +9 -11
  44. package/esm/orm/model/entity-metadata.js +4 -2
  45. package/esm/orm/orm.const.js +1 -0
  46. package/esm/orm/repository.class.js +31 -36
  47. package/esm/orm/util/apply-mixins.js +2 -1
  48. package/esm/orm/util/extract-keyvalues.js +6 -3
  49. package/esm/orm/util/orm.helper.js +2 -6
  50. package/esm/orm/util/parse-fields-projection.js +59 -0
  51. package/package.json +10 -6
  52. package/types/client/adapter.d.ts +1 -1
  53. package/types/client/cursor-stream.d.ts +0 -1
  54. package/types/client/extensions.d.ts +14 -3
  55. package/types/client/sqb-client.d.ts +1 -1
  56. package/types/client/sqb-connection.d.ts +1 -1
  57. package/types/client/types.d.ts +1 -1
  58. package/types/index.d.ts +18 -17
  59. package/types/orm/commands/find.command.d.ts +3 -4
  60. package/types/orm/commands/row-converter.d.ts +1 -1
  61. package/types/orm/decorators/column.decorator.d.ts +1 -0
  62. package/types/orm/model/field-metadata.d.ts +1 -1
  63. package/types/orm/orm.const.d.ts +1 -0
  64. package/types/orm/repository.class.d.ts +11 -8
  65. package/types/orm/util/parse-fields-projection.d.ts +10 -0
@@ -180,7 +180,7 @@ class Cursor extends (0, strict_typed_events_1.TypedEventEmitterClass)(strict_ty
180
180
  throw new Error('To move cursor back, it needs cache to be enabled');
181
181
  const _this = this;
182
182
  await this._taskQueue
183
- .enqueue(async function () {
183
+ .enqueue(async () => {
184
184
  /* If moving backward */
185
185
  if (step < 0) {
186
186
  /* Seek cache */
@@ -1,14 +1,41 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.unRegisterAdapter = exports.registerAdapter = exports.adapters = void 0;
4
- exports.adapters = [];
5
- function registerAdapter(adapter) {
6
- if (!adapter.driver)
7
- throw new TypeError('A DatabaseAdapter must contain "driver" property');
8
- exports.adapters.push(adapter);
3
+ exports.AdapterRegistry = void 0;
4
+ class AdapterRegistry {
5
+ static get size() {
6
+ return this.adapters.length;
7
+ }
8
+ static register(...adapters) {
9
+ for (const adapter of adapters) {
10
+ if (!adapter.driver)
11
+ throw new TypeError('A DatabaseAdapter must contain "driver" property');
12
+ this.adapters.push(adapter);
13
+ }
14
+ }
15
+ static forEach(callback, thisArg) {
16
+ return this.adapters.forEach(callback, thisArg);
17
+ }
18
+ static items() {
19
+ return this.adapters.values();
20
+ }
21
+ static unRegister(...extensions) {
22
+ this.adapters = extensions.filter(x => !extensions.includes(x));
23
+ }
24
+ static getAll(dialect) {
25
+ return this.adapters.filter(x => x.dialect === dialect);
26
+ }
27
+ static get(index) {
28
+ return this.adapters[index];
29
+ }
30
+ static findDialect(dialect) {
31
+ return this.adapters.find(x => x.dialect === dialect);
32
+ }
33
+ static findDriver(dialect) {
34
+ return this.adapters.find(x => x.driver === dialect);
35
+ }
36
+ static has(extension) {
37
+ return !!this.adapters.find(x => x === extension);
38
+ }
9
39
  }
10
- exports.registerAdapter = registerAdapter;
11
- function unRegisterAdapter(...adapter) {
12
- exports.adapters = exports.adapters.filter(x => !adapter.includes(x));
13
- }
14
- exports.unRegisterAdapter = unRegisterAdapter;
40
+ exports.AdapterRegistry = AdapterRegistry;
41
+ AdapterRegistry.adapters = [];
@@ -1,6 +1,10 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.callFetchHooks = exports.normalizeRowsToArrayRows = exports.normalizeRowsToObjectRows = exports.wrapAdapterFields = exports.applyNamingStrategy = void 0;
3
+ exports.applyNamingStrategy = applyNamingStrategy;
4
+ exports.wrapAdapterFields = wrapAdapterFields;
5
+ exports.normalizeRowsToObjectRows = normalizeRowsToObjectRows;
6
+ exports.normalizeRowsToArrayRows = normalizeRowsToArrayRows;
7
+ exports.callFetchHooks = callFetchHooks;
4
8
  const putil_varhelpers_1 = require("putil-varhelpers");
5
9
  const field_info_map_js_1 = require("./field-info-map.js");
6
10
  function applyNamingStrategy(value, namingStrategy) {
@@ -19,13 +23,14 @@ function applyNamingStrategy(value, namingStrategy) {
19
23
  if (!value.match(/[a-z]/))
20
24
  return (0, putil_varhelpers_1.pascalCase)(value.toLowerCase());
21
25
  return (0, putil_varhelpers_1.pascalCase)(value);
26
+ default:
27
+ break;
22
28
  }
23
29
  }
24
30
  else if (typeof namingStrategy === 'function')
25
31
  return namingStrategy(value);
26
32
  return value;
27
33
  }
28
- exports.applyNamingStrategy = applyNamingStrategy;
29
34
  function wrapAdapterFields(oldFields, fieldNaming) {
30
35
  const mapFieldInfo = (f, index) => {
31
36
  const name = applyNamingStrategy(f.fieldName, fieldNaming);
@@ -43,15 +48,12 @@ function wrapAdapterFields(oldFields, fieldNaming) {
43
48
  });
44
49
  return result;
45
50
  }
46
- exports.wrapAdapterFields = wrapAdapterFields;
47
51
  function normalizeRowsToObjectRows(fields, rowType, oldRows, options) {
48
52
  return normalizeRows(fields, rowType, oldRows, { ...options, objectRows: true });
49
53
  }
50
- exports.normalizeRowsToObjectRows = normalizeRowsToObjectRows;
51
54
  function normalizeRowsToArrayRows(fields, rowType, oldRows, options) {
52
55
  return normalizeRows(fields, rowType, oldRows, { ...options, objectRows: false });
53
56
  }
54
- exports.normalizeRowsToArrayRows = normalizeRowsToArrayRows;
55
57
  function normalizeRows(fields, rowType, oldRows, options) {
56
58
  const ignoreNulls = options.ignoreNulls && options.objectRows;
57
59
  const transform = options.transform;
@@ -130,4 +132,3 @@ function callFetchHooks(rows, request) {
130
132
  }
131
133
  }
132
134
  }
133
- exports.callFetchHooks = callFetchHooks;
@@ -20,12 +20,12 @@ class SqbClient extends (0, strict_typed_events_1.TypedEventEmitterClass)(strict
20
20
  throw new TypeError('Configuration object required');
21
21
  let adapter;
22
22
  if (config.driver) {
23
- adapter = extensions_js_1.adapters.find(x => x.driver === config.driver);
23
+ adapter = extensions_js_1.AdapterRegistry.findDriver(config.driver);
24
24
  if (!adapter)
25
25
  throw new Error(`No database adapter registered for "${config.driver}" driver`);
26
26
  }
27
27
  else if (config.dialect) {
28
- adapter = extensions_js_1.adapters.find(x => x.dialect === config.dialect);
28
+ adapter = extensions_js_1.AdapterRegistry.findDialect(config.dialect);
29
29
  if (!adapter)
30
30
  throw new Error(`No database adapter registered for "${config.dialect}" dialect`);
31
31
  }
@@ -2,12 +2,12 @@
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.SqbConnection = void 0;
4
4
  const tslib_1 = require("tslib");
5
+ const builder_1 = require("@sqb/builder");
5
6
  const assert_1 = tslib_1.__importDefault(require("assert"));
6
7
  const debug_1 = tslib_1.__importDefault(require("debug"));
7
8
  const power_tasks_1 = require("power-tasks");
8
9
  const putil_varhelpers_1 = require("putil-varhelpers");
9
10
  const strict_typed_events_1 = require("strict-typed-events");
10
- const builder_1 = require("@sqb/builder");
11
11
  const entity_metadata_js_1 = require("../orm/model/entity-metadata.js");
12
12
  const repository_class_js_1 = require("../orm/repository.class.js");
13
13
  const cursor_js_1 = require("./cursor.js");
@@ -191,8 +191,9 @@ class SqbConnection extends (0, strict_typed_events_1.TypedEventEmitterClass)(st
191
191
  async setSavepoint(savepoint) {
192
192
  if (!this._intlcon)
193
193
  throw new Error('Can not call setSavepoint() on a released connection');
194
- if (typeof this._intlcon.setSavepoint !== 'function')
194
+ if (typeof this._intlcon.setSavepoint !== 'function') {
195
195
  throw new Error(this.client.driver + ' does not support setSavepoint method');
196
+ }
196
197
  if (!this.inTransaction)
197
198
  await this.startTransaction();
198
199
  await this._intlcon.setSavepoint(savepoint);
@@ -201,16 +202,18 @@ class SqbConnection extends (0, strict_typed_events_1.TypedEventEmitterClass)(st
201
202
  async releaseSavepoint(savepoint) {
202
203
  if (!this._intlcon)
203
204
  throw new Error('Can not call releaseSavepoint() on a released connection');
204
- if (typeof this._intlcon.releaseSavepoint !== 'function')
205
+ if (typeof this._intlcon.releaseSavepoint !== 'function') {
205
206
  throw new Error(this.client.driver + ' does not support releaseSavepoint method');
207
+ }
206
208
  await this._intlcon.releaseSavepoint(savepoint);
207
209
  this.emit('release-savepoint');
208
210
  }
209
211
  async rollbackSavepoint(savepoint) {
210
212
  if (!this._intlcon)
211
213
  throw new Error('Can not call rollbackSavepoint() on a released connection');
212
- if (typeof this._intlcon.rollbackSavepoint !== 'function')
214
+ if (typeof this._intlcon.rollbackSavepoint !== 'function') {
213
215
  throw new Error(this.client.driver + ' does not support rollbackSavepoint method');
216
+ }
214
217
  await this._intlcon.rollbackSavepoint(savepoint);
215
218
  this.emit('rollback-savepoint');
216
219
  }
package/cjs/index.js CHANGED
@@ -1,29 +1,16 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.isEntityClass = exports.isAssociationField = exports.isEmbeddedField = exports.isColumnField = exports.unRegisterAdapter = exports.registerAdapter = void 0;
3
+ exports.isEntityClass = exports.isEmbeddedField = exports.isColumnField = exports.isAssociationField = void 0;
4
4
  const tslib_1 = require("tslib");
5
5
  require("reflect-metadata");
6
- tslib_1.__exportStar(require("./client/types.js"), exports);
7
6
  tslib_1.__exportStar(require("./client/adapter.js"), exports);
7
+ tslib_1.__exportStar(require("./client/cursor.js"), exports);
8
+ tslib_1.__exportStar(require("./client/extensions.js"), exports);
8
9
  tslib_1.__exportStar(require("./client/sqb-client.js"), exports);
9
10
  tslib_1.__exportStar(require("./client/sqb-connection.js"), exports);
10
- tslib_1.__exportStar(require("./client/cursor.js"), exports);
11
- var extensions_js_1 = require("./client/extensions.js");
12
- Object.defineProperty(exports, "registerAdapter", { enumerable: true, get: function () { return extensions_js_1.registerAdapter; } });
13
- Object.defineProperty(exports, "unRegisterAdapter", { enumerable: true, get: function () { return extensions_js_1.unRegisterAdapter; } });
14
- tslib_1.__exportStar(require("./orm/orm.type.js"), exports);
15
- tslib_1.__exportStar(require("./orm/orm.const.js"), exports);
11
+ tslib_1.__exportStar(require("./client/types.js"), exports);
12
+ tslib_1.__exportStar(require("./orm/backward.js"), exports);
16
13
  tslib_1.__exportStar(require("./orm/base-entity.js"), exports);
17
- tslib_1.__exportStar(require("./orm/repository.class.js"), exports);
18
- tslib_1.__exportStar(require("./orm/model/entity-metadata.js"), exports);
19
- tslib_1.__exportStar(require("./orm/model/field-metadata.js"), exports);
20
- tslib_1.__exportStar(require("./orm/model/column-field-metadata.js"), exports);
21
- tslib_1.__exportStar(require("./orm/model/embedded-field-metadata.js"), exports);
22
- tslib_1.__exportStar(require("./orm/model/association-field-metadata.js"), exports);
23
- tslib_1.__exportStar(require("./orm/model/association.js"), exports);
24
- tslib_1.__exportStar(require("./orm/model/association-node.js"), exports);
25
- tslib_1.__exportStar(require("./orm/model/index-metadata.js"), exports);
26
- tslib_1.__exportStar(require("./orm/model/link-chain.js"), exports);
27
14
  tslib_1.__exportStar(require("./orm/decorators/column.decorator.js"), exports);
28
15
  tslib_1.__exportStar(require("./orm/decorators/embedded.decorator.js"), exports);
29
16
  tslib_1.__exportStar(require("./orm/decorators/entity.decorator.js"), exports);
@@ -33,9 +20,21 @@ tslib_1.__exportStar(require("./orm/decorators/index.decorator.js"), exports);
33
20
  tslib_1.__exportStar(require("./orm/decorators/link.decorator.js"), exports);
34
21
  tslib_1.__exportStar(require("./orm/decorators/primarykey.decorator.js"), exports);
35
22
  tslib_1.__exportStar(require("./orm/decorators/transform.decorator.js"), exports);
23
+ tslib_1.__exportStar(require("./orm/model/association.js"), exports);
24
+ tslib_1.__exportStar(require("./orm/model/association-field-metadata.js"), exports);
25
+ tslib_1.__exportStar(require("./orm/model/association-node.js"), exports);
26
+ tslib_1.__exportStar(require("./orm/model/column-field-metadata.js"), exports);
27
+ tslib_1.__exportStar(require("./orm/model/embedded-field-metadata.js"), exports);
28
+ tslib_1.__exportStar(require("./orm/model/entity-metadata.js"), exports);
29
+ tslib_1.__exportStar(require("./orm/model/field-metadata.js"), exports);
30
+ tslib_1.__exportStar(require("./orm/model/index-metadata.js"), exports);
31
+ tslib_1.__exportStar(require("./orm/model/link-chain.js"), exports);
32
+ tslib_1.__exportStar(require("./orm/orm.const.js"), exports);
33
+ tslib_1.__exportStar(require("./orm/orm.type.js"), exports);
34
+ tslib_1.__exportStar(require("./orm/repository.class.js"), exports);
36
35
  var orm_helper_js_1 = require("./orm/util/orm.helper.js");
36
+ Object.defineProperty(exports, "isAssociationField", { enumerable: true, get: function () { return orm_helper_js_1.isAssociationField; } });
37
37
  Object.defineProperty(exports, "isColumnField", { enumerable: true, get: function () { return orm_helper_js_1.isColumnField; } });
38
38
  Object.defineProperty(exports, "isEmbeddedField", { enumerable: true, get: function () { return orm_helper_js_1.isEmbeddedField; } });
39
- Object.defineProperty(exports, "isAssociationField", { enumerable: true, get: function () { return orm_helper_js_1.isAssociationField; } });
40
39
  Object.defineProperty(exports, "isEntityClass", { enumerable: true, get: function () { return orm_helper_js_1.isEntityClass; } });
41
- tslib_1.__exportStar(require("./orm/backward.js"), exports);
40
+ tslib_1.__exportStar(require("./orm/util/parse-fields-projection.js"), exports);
@@ -1,24 +1,24 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.UnionEntity = exports.PickEntity = exports.OmitEntity = exports.mixinEntities = exports.getNonAssociationElementNames = exports.getUpdateColumnNames = exports.getInsertColumnNames = void 0;
3
+ exports.UnionEntity = exports.PickEntity = exports.OmitEntity = void 0;
4
+ exports.getInsertColumnNames = getInsertColumnNames;
5
+ exports.getUpdateColumnNames = getUpdateColumnNames;
6
+ exports.getNonAssociationElementNames = getNonAssociationElementNames;
7
+ exports.mixinEntities = mixinEntities;
4
8
  const entity_decorator_js_1 = require("./decorators/entity.decorator.js");
5
9
  function getInsertColumnNames(ctor) {
6
10
  return entity_decorator_js_1.Entity.getInsertColumnNames(ctor);
7
11
  }
8
- exports.getInsertColumnNames = getInsertColumnNames;
9
12
  function getUpdateColumnNames(ctor) {
10
13
  return entity_decorator_js_1.Entity.getUpdateColumnNames(ctor);
11
14
  }
12
- exports.getUpdateColumnNames = getUpdateColumnNames;
13
15
  function getNonAssociationElementNames(ctor) {
14
16
  return entity_decorator_js_1.Entity.getNonAssociationFieldNames(ctor);
15
17
  }
16
- exports.getNonAssociationElementNames = getNonAssociationElementNames;
17
18
  function mixinEntities(derivedCtor, ...bases) {
18
19
  // @ts-ignore
19
20
  return entity_decorator_js_1.Entity.mixin(derivedCtor, ...bases);
20
21
  }
21
- exports.mixinEntities = mixinEntities;
22
22
  exports.OmitEntity = entity_decorator_js_1.Entity.Omit;
23
23
  exports.PickEntity = entity_decorator_js_1.Entity.Pick;
24
24
  exports.UnionEntity = entity_decorator_js_1.Entity.Union;
@@ -1,6 +1,9 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.prepareFilter = exports.joinAssociation = exports.joinAssociationGetLast = exports.joinAssociationGetFirst = void 0;
3
+ exports.joinAssociationGetFirst = joinAssociationGetFirst;
4
+ exports.joinAssociationGetLast = joinAssociationGetLast;
5
+ exports.joinAssociation = joinAssociation;
6
+ exports.prepareFilter = prepareFilter;
4
7
  const builder_1 = require("@sqb/builder");
5
8
  const embedded_field_metadata_js_1 = require("../model/embedded-field-metadata.js");
6
9
  const entity_metadata_js_1 = require("../model/entity-metadata.js");
@@ -9,12 +12,10 @@ async function joinAssociationGetFirst(joinInfos, association, parentAlias, inne
9
12
  const joins = await joinAssociation(joinInfos, association, parentAlias, innerJoin);
10
13
  return joins[0];
11
14
  }
12
- exports.joinAssociationGetFirst = joinAssociationGetFirst;
13
15
  async function joinAssociationGetLast(joinInfos, association, parentAlias, innerJoin) {
14
16
  const joins = await joinAssociation(joinInfos, association, parentAlias, innerJoin);
15
17
  return joins[joins.length - 1];
16
18
  }
17
- exports.joinAssociationGetLast = joinAssociationGetLast;
18
19
  async function joinAssociation(joinInfos, association, parentAlias, innerJoin) {
19
20
  let joinInfo;
20
21
  let node = association;
@@ -50,10 +51,9 @@ async function joinAssociation(joinInfos, association, parentAlias, innerJoin) {
50
51
  }
51
52
  return result;
52
53
  }
53
- exports.joinAssociation = joinAssociation;
54
54
  async function prepareFilter(entityDef, filter, trgOp, tableAlias = 'T') {
55
55
  let srcOp;
56
- if ((0, builder_1.isLogicalOperator)(filter))
56
+ if ((0, builder_1.isLogicalOperator)(filter) && filter._operatorType === trgOp._operatorType)
57
57
  srcOp = filter;
58
58
  else {
59
59
  srcOp = (0, builder_1.And)();
@@ -62,6 +62,7 @@ async function prepareFilter(entityDef, filter, trgOp, tableAlias = 'T') {
62
62
  else
63
63
  srcOp.add(filter);
64
64
  }
65
+ const associationPathCache = {};
65
66
  for (const item of srcOp._items) {
66
67
  if ((0, builder_1.isLogicalOperator)(item)) {
67
68
  const ctor = Object.getPrototypeOf(item).constructor;
@@ -80,19 +81,34 @@ async function prepareFilter(entityDef, filter, trgOp, tableAlias = 'T') {
80
81
  let _curPrefix = '';
81
82
  let _curSuffix = '';
82
83
  let subSelect;
83
- for (let i = 0; i < l; i++) {
84
+ let currentOp = trgOp;
85
+ let i = 0;
86
+ const parentPath = itemPath
87
+ .slice(0, l - 2)
88
+ .join('.')
89
+ .toLowerCase();
90
+ const cached = associationPathCache[parentPath];
91
+ if (cached) {
92
+ /** Jump to last item */
93
+ i = l - 1;
94
+ _curEntity = cached._curEntity;
95
+ _curAlias = cached._curAlias;
96
+ currentOp = cached.currentOp;
97
+ }
98
+ for (i; i < l; i++) {
84
99
  pt = itemPath[i];
85
100
  const col = entity_metadata_js_1.EntityMetadata.getField(_curEntity, pt);
86
101
  if (!col)
87
102
  throw new Error(`Unknown property (${item._left}) defined in filter`);
88
- // if last item on path
103
+ /** if last item on path */
89
104
  if (i === l - 1) {
90
105
  if (!(0, orm_helper_js_1.isColumnField)(col))
91
106
  throw new Error(`Invalid column expression (${item._left}) defined in filter`);
92
107
  const ctor = Object.getPrototypeOf(item).constructor;
93
- trgOp.add(new ctor((0, builder_1.Field)(_curAlias + '.' + _curPrefix + col.fieldName + _curSuffix, col.dataType, col.isArray), item._right));
108
+ currentOp.add(new ctor((0, builder_1.Field)(_curAlias + '.' + _curPrefix + col.fieldName + _curSuffix, col.dataType, col.isArray), item._right));
94
109
  }
95
110
  else {
111
+ /** if not last item on path */
96
112
  if ((0, orm_helper_js_1.isColumnField)(col))
97
113
  throw new Error(`Invalid column (${item._left}) defined in filter`);
98
114
  if ((0, orm_helper_js_1.isEmbeddedField)(col)) {
@@ -110,8 +126,13 @@ async function prepareFilter(entityDef, filter, trgOp, tableAlias = 'T') {
110
126
  const targetCol = await col.association.resolveTargetProperty();
111
127
  subSelect = (0, builder_1.Select)((0, builder_1.Raw)('1')).from(_curEntity.tableName + ' K');
112
128
  subSelect.where((0, builder_1.Eq)((0, builder_1.Field)('K.' + targetCol.fieldName, targetCol.dataType, targetCol.isArray), (0, builder_1.Field)(tableAlias + '.' + keyCol.fieldName, keyCol.dataType, keyCol.isArray)));
113
- trgOp.add((0, builder_1.Exists)(subSelect));
114
- trgOp = subSelect._where;
129
+ currentOp.add((0, builder_1.Exists)(subSelect));
130
+ if (currentOp._operatorType !== builder_1.OperatorType.and) {
131
+ currentOp = builder_1.op.or();
132
+ subSelect.where(currentOp);
133
+ }
134
+ else
135
+ currentOp = subSelect._where;
115
136
  if (col.association.conditions) {
116
137
  await prepareFilter(_curEntity, col.association.conditions, trgOp, 'K');
117
138
  }
@@ -130,6 +151,14 @@ async function prepareFilter(entityDef, filter, trgOp, tableAlias = 'T') {
130
151
  _curAlias = joinAlias;
131
152
  node = node.next;
132
153
  }
154
+ /** If next path is the last one */
155
+ if (i === l - 2) {
156
+ associationPathCache[parentPath] = {
157
+ _curEntity,
158
+ _curAlias,
159
+ currentOp,
160
+ };
161
+ }
133
162
  }
134
163
  }
135
164
  continue;
@@ -138,4 +167,3 @@ async function prepareFilter(entityDef, filter, trgOp, tableAlias = 'T') {
138
167
  trgOp.add(item);
139
168
  }
140
169
  }
141
- exports.prepareFilter = prepareFilter;
@@ -63,8 +63,9 @@ class CreateCommand {
63
63
  if (typeof col.serialize === 'function')
64
64
  v = col.serialize(v, col.name);
65
65
  if (v == null) {
66
- if (col.notNull && !col.autoGenerated)
66
+ if (col.notNull && !col.autoGenerated) {
67
67
  throw new Error(`${entity.name}.${col.name} is required and can't be null`);
68
+ }
68
69
  continue;
69
70
  }
70
71
  column_field_metadata_js_1.ColumnFieldMetadata.checkEnumValue(col, v);
@@ -2,11 +2,11 @@
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.FindCommand = void 0;
4
4
  const builder_1 = require("@sqb/builder");
5
- const entity_decorator_js_1 = require("../decorators/entity.decorator.js");
6
5
  const association_node_js_1 = require("../model/association-node.js");
7
6
  const embedded_field_metadata_js_1 = require("../model/embedded-field-metadata.js");
8
7
  const entity_metadata_js_1 = require("../model/entity-metadata.js");
9
8
  const orm_helper_js_1 = require("../util/orm.helper.js");
9
+ const parse_fields_projection_js_1 = require("../util/parse-fields-projection.js");
10
10
  const command_helper_js_1 = require("./command.helper.js");
11
11
  const row_converter_js_1 = require("./row-converter.js");
12
12
  const SORT_ORDER_PATTERN = /^([-+])?(.*)$/;
@@ -56,9 +56,7 @@ class FindCommand {
56
56
  maxEagerFetch: args.maxEagerFetch,
57
57
  });
58
58
  await command.addFields({
59
- pick: args.pick,
60
- include: args.include,
61
- omit: args.omit,
59
+ projection: args.projection,
62
60
  sort: args.sort,
63
61
  });
64
62
  if (args.filter)
@@ -71,22 +69,10 @@ class FindCommand {
71
69
  const tableAlias = opts.tableAlias || this.resultAlias;
72
70
  const entity = opts.entity || this._getEntityFromAlias(tableAlias);
73
71
  const converter = opts.converter || this.converter;
74
- const _pick = opts.pick ? opts.pick.map(x => x.toLowerCase()) : undefined;
75
- const _omit = opts.omit ? opts.omit.map(x => x.toLowerCase()) : undefined;
76
- const _include = opts.include ? opts.include.map(x => x.toLowerCase()) : undefined;
77
- let requestedFields;
78
- if (_pick)
79
- requestedFields = [..._pick];
80
- else {
81
- requestedFields = entity_decorator_js_1.Entity.getFieldNames(entity.ctor).reduce((a, x) => {
82
- const f = entity_decorator_js_1.Entity.getField(entity.ctor, x);
83
- if (f && !f.exclusive)
84
- a.push(x.toLowerCase());
85
- return a;
86
- }, []);
87
- }
88
- if (_include)
89
- requestedFields.push(..._include);
72
+ const projection = typeof opts.projection === 'string' || Array.isArray(opts.projection)
73
+ ? (0, parse_fields_projection_js_1.parseFieldsProjection)(opts.projection)
74
+ : opts.projection;
75
+ const defaultFields = !projection || !Object.values(projection).find(p => !p.sign);
90
76
  const sortFields = opts.sort && opts.sort.length ? opts.sort.map(x => x.toLowerCase()) : undefined;
91
77
  const prefix = opts.prefix || '';
92
78
  const suffix = opts.suffix || '';
@@ -95,12 +81,16 @@ class FindCommand {
95
81
  if (!col || col.hidden)
96
82
  continue;
97
83
  const colNameLower = col.name.toLowerCase();
98
- // Ignore field if in excluded list
99
- if (_omit && _omit.includes(colNameLower))
100
- continue;
101
- // Check if field request list
102
- if (!requestedFields.find((x) => x === colNameLower || x.startsWith(colNameLower + '.')))
84
+ const p = projection?.[colNameLower];
85
+ if (
86
+ /** Ignore if field is omitted */
87
+ p?.sign === '-' ||
88
+ /** Ignore if default fields and field is not in projection */
89
+ (!defaultFields && !p) ||
90
+ /** Ignore if default fields enabled and fields is exclusive */
91
+ (defaultFields && col.exclusive && !p)) {
103
92
  continue;
93
+ }
104
94
  // Add field to select list if field is a column
105
95
  if ((0, orm_helper_js_1.isColumnField)(col)) {
106
96
  const fieldAlias = this._selectColumn(tableAlias, col, prefix, suffix);
@@ -125,9 +115,7 @@ class FindCommand {
125
115
  entity: typ,
126
116
  prefix: col.fieldNamePrefix,
127
117
  suffix: col.fieldNameSuffix,
128
- pick: _pick?.includes(colNameLower) ? undefined : extractSubFields(colNameLower, _pick),
129
- include: extractSubFields(colNameLower, _include),
130
- omit: extractSubFields(colNameLower, _omit),
118
+ projection: p?.projection,
131
119
  sort: extractSubFields(colNameLower, sortFields),
132
120
  });
133
121
  continue;
@@ -145,9 +133,7 @@ class FindCommand {
145
133
  tableAlias: joinInfo.joinAlias,
146
134
  converter: subConverter,
147
135
  entity: joinInfo.targetEntity,
148
- pick: _pick?.includes(colNameLower) ? undefined : extractSubFields(colNameLower, _pick),
149
- include: extractSubFields(colNameLower, _include),
150
- omit: extractSubFields(colNameLower, _omit),
136
+ projection: p?.projection,
151
137
  sort: extractSubFields(colNameLower, sortFields),
152
138
  });
153
139
  continue;
@@ -167,9 +153,7 @@ class FindCommand {
167
153
  await findCommand.filter((0, builder_1.In)(targetCol.name, (0, builder_1.Param)(parentField)));
168
154
  const sort = sortFields && extractSubFields(colNameLower, sortFields);
169
155
  await findCommand.addFields({
170
- pick: _pick?.includes(colNameLower) ? undefined : extractSubFields(colNameLower, _pick),
171
- include: extractSubFields(colNameLower, _include),
172
- omit: extractSubFields(colNameLower, _omit),
156
+ projection: p?.projection,
173
157
  sort,
174
158
  });
175
159
  if (sort)
@@ -263,16 +247,18 @@ class FindCommand {
263
247
  if (args.offset)
264
248
  query.offset(args.offset);
265
249
  // joins must be added last
266
- if (this._joins)
250
+ if (this._joins) {
267
251
  for (const j of this._joins) {
268
252
  query.join(j.join);
269
253
  }
254
+ }
270
255
  // Execute query
271
256
  const resp = await args.connection.execute(query, {
272
257
  params: args?.params,
273
258
  fetchRows: args?.limit,
274
259
  objectRows: false,
275
260
  cursor: false,
261
+ prettyPrint: args.prettyPrint,
276
262
  });
277
263
  // Create objects
278
264
  if (resp.rows && resp.fields) {
@@ -2,15 +2,9 @@
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.RowConverter = void 0;
4
4
  const builder_1 = require("@sqb/builder");
5
- const isValueProperty = (prop) => {
6
- return prop.fieldAlias && !prop.converter;
7
- };
8
- const isObjectProperty = (prop) => {
9
- return prop.converter && !prop.findCommand;
10
- };
11
- const isNestedProperty = (prop) => {
12
- return prop.converter && prop.findCommand;
13
- };
5
+ const isValueProperty = (prop) => prop.fieldAlias && !prop.converter;
6
+ const isObjectProperty = (prop) => prop.converter && !prop.findCommand;
7
+ const isNestedProperty = (prop) => prop.converter && prop.findCommand;
14
8
  class RowConverter {
15
9
  constructor(resultType, parent) {
16
10
  this.resultType = resultType;
@@ -153,8 +147,9 @@ class RowConverter {
153
147
  }
154
148
  },
155
149
  });
156
- if (r.length > findCommand.maxEagerFetch)
150
+ if (r.length > findCommand.maxEagerFetch) {
157
151
  throw new Error(`Number of returning rows for "${propKey}" exceeds maxEagerFetch limit`);
152
+ }
158
153
  for (let i = 0; i < result.length; i++) {
159
154
  const row = rows[i];
160
155
  let obj = result[i];
@@ -1,8 +1,12 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.Column = void 0;
3
+ exports.Column = Column;
4
4
  const entity_metadata_js_1 = require("../model/entity-metadata.js");
5
+ const orm_const_js_1 = require("../orm.const.js");
5
6
  function Column(arg0) {
7
+ return Column[orm_const_js_1.DECORATOR_FACTORY](arg0);
8
+ }
9
+ Column[orm_const_js_1.DECORATOR_FACTORY] = function (arg0) {
6
10
  return (target, propertyKey) => {
7
11
  if (typeof propertyKey !== 'string')
8
12
  throw new Error('Symbol properties are not accepted');
@@ -19,5 +23,4 @@ function Column(arg0) {
19
23
  }
20
24
  entity_metadata_js_1.EntityMetadata.defineColumnField(entity, propertyKey, options);
21
25
  };
22
- }
23
- exports.Column = Column;
26
+ };
@@ -1,6 +1,6 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.Embedded = void 0;
3
+ exports.Embedded = Embedded;
4
4
  const entity_metadata_js_1 = require("../model/entity-metadata.js");
5
5
  function Embedded(type, options) {
6
6
  return (target, propertyKey) => {
@@ -13,4 +13,3 @@ function Embedded(type, options) {
13
13
  entity_metadata_js_1.EntityMetadata.defineEmbeddedField(entity, propertyKey, type, options);
14
14
  };
15
15
  }
16
- exports.Embedded = Embedded;
@@ -1,6 +1,6 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.Entity = void 0;
3
+ exports.Entity = Entity;
4
4
  const entity_metadata_js_1 = require("../model/entity-metadata.js");
5
5
  const apply_mixins_js_1 = require("../util/apply-mixins.js");
6
6
  function Entity(options) {
@@ -15,7 +15,6 @@ function Entity(options) {
15
15
  entity.comment = opts.comment;
16
16
  };
17
17
  }
18
- exports.Entity = Entity;
19
18
  (function (Entity) {
20
19
  Entity.getMetadata = entity_metadata_js_1.EntityMetadata.get;
21
20
  Entity.getOwnMetadata = entity_metadata_js_1.EntityMetadata.getOwn;