@sqb/connect 4.12.0 → 4.12.1

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/cjs/index.js CHANGED
@@ -38,4 +38,5 @@ Object.defineProperty(exports, "isColumnField", { enumerable: true, get: functio
38
38
  Object.defineProperty(exports, "isEmbeddedField", { enumerable: true, get: function () { return orm_helper_js_1.isEmbeddedField; } });
39
39
  Object.defineProperty(exports, "isAssociationField", { enumerable: true, get: function () { return orm_helper_js_1.isAssociationField; } });
40
40
  Object.defineProperty(exports, "isEntityClass", { enumerable: true, get: function () { return orm_helper_js_1.isEntityClass; } });
41
+ tslib_1.__exportStar(require("./orm/util/parse-fields-projection.js"), exports);
41
42
  tslib_1.__exportStar(require("./orm/backward.js"), exports);
@@ -53,7 +53,7 @@ async function joinAssociation(joinInfos, association, parentAlias, innerJoin) {
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)();
@@ -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)
@@ -2,7 +2,12 @@
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.Column = void 0;
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
+ exports.Column = Column;
10
+ Column[orm_const_js_1.DECORATOR_FACTORY] = function (arg0) {
6
11
  return (target, propertyKey) => {
7
12
  if (typeof propertyKey !== 'string')
8
13
  throw new Error('Symbol properties are not accepted');
@@ -19,5 +24,4 @@ function Column(arg0) {
19
24
  }
20
25
  entity_metadata_js_1.EntityMetadata.defineColumnField(entity, propertyKey, options);
21
26
  };
22
- }
23
- exports.Column = Column;
27
+ };
@@ -1,5 +1,6 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.REPOSITORY_KEY = exports.ENTITY_METADATA_KEY = void 0;
3
+ exports.DECORATOR_FACTORY = exports.REPOSITORY_KEY = exports.ENTITY_METADATA_KEY = void 0;
4
4
  exports.ENTITY_METADATA_KEY = Symbol.for('SQB_ENTITY_METADATA');
5
5
  exports.REPOSITORY_KEY = Symbol.for('SQB_REPOSITORY');
6
+ exports.DECORATOR_FACTORY = Symbol.for('decorator.factory');
@@ -41,15 +41,16 @@ class Repository extends (0, strict_typed_events_1.TypedEventEmitterClass)(stric
41
41
  return this._exists(keyValue, { ...options, connection });
42
42
  }, options);
43
43
  }
44
+ existsOne(options) {
45
+ return this._execute(async (connection) => {
46
+ return this._existsOne({ ...options, connection });
47
+ }, options);
48
+ }
44
49
  count(options) {
45
50
  return this._execute(async (connection) => {
46
51
  return this._count({ ...options, connection });
47
52
  }, options);
48
53
  }
49
- /** @deprecated - Use findById instead */
50
- find(keyValue, options) {
51
- return this.findById(keyValue, options);
52
- }
53
54
  findById(keyValue, options) {
54
55
  return this._execute(async (connection) => {
55
56
  return this._find(keyValue, { ...options, connection });
@@ -132,11 +133,25 @@ class Repository extends (0, strict_typed_events_1.TypedEventEmitterClass)(stric
132
133
  else
133
134
  filter.push(options.filter);
134
135
  }
135
- return !!(await count_command_js_1.CountCommand.execute({
136
+ return this._existsOne({
137
+ ...options,
138
+ filter,
139
+ });
140
+ }
141
+ async _existsOne(options) {
142
+ const filter = [];
143
+ if (options && options.filter) {
144
+ if (Array.isArray(options.filter))
145
+ filter.push(...options.filter);
146
+ else
147
+ filter.push(options.filter);
148
+ }
149
+ const resp = await find_command_js_1.FindCommand.execute({
136
150
  ...options,
137
151
  filter,
138
152
  entity: this._entity,
139
- }));
153
+ });
154
+ return resp.length > 0;
140
155
  }
141
156
  async _count(options) {
142
157
  return count_command_js_1.CountCommand.execute({
@@ -0,0 +1,66 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.parseFieldsProjection = exports.FieldsProjection = void 0;
4
+ const fast_tokenizer_1 = require("fast-tokenizer");
5
+ const FIELD_PATTERN = /^([+-])?([a-z_$]\w*)$/i;
6
+ const NO_DOT_BRACKET_PATTERN = /[^.]\(/g;
7
+ class FieldsProjection {
8
+ }
9
+ exports.FieldsProjection = FieldsProjection;
10
+ (function (FieldsProjection) {
11
+ class Item {
12
+ }
13
+ FieldsProjection.Item = Item;
14
+ })(FieldsProjection || (exports.FieldsProjection = FieldsProjection = {}));
15
+ function parseFieldsProjection(projection, keepCase) {
16
+ const arr = Array.isArray(projection) ? projection : [projection];
17
+ if (!(arr && arr.length))
18
+ return;
19
+ const out = new FieldsProjection();
20
+ for (let s of arr) {
21
+ if (!keepCase)
22
+ s = s.toLowerCase();
23
+ parse(s, out);
24
+ }
25
+ return out;
26
+ }
27
+ exports.parseFieldsProjection = parseFieldsProjection;
28
+ function parse(input, target) {
29
+ /** Add dot before brackets which is required to split fields */
30
+ input = input.replace(NO_DOT_BRACKET_PATTERN, s => {
31
+ return s.charAt(0) + '.' + s.substring(1);
32
+ });
33
+ const fields = (0, fast_tokenizer_1.splitString)(input, {
34
+ delimiters: '.',
35
+ brackets: true,
36
+ keepBrackets: false,
37
+ });
38
+ for (let i = 0; i < fields.length; i++) {
39
+ const f = fields[i];
40
+ if (f.includes(',')) {
41
+ const subFields = (0, fast_tokenizer_1.splitString)(f, {
42
+ delimiters: ',',
43
+ brackets: true,
44
+ keepBrackets: true,
45
+ });
46
+ for (const n of subFields) {
47
+ parse(n, target);
48
+ }
49
+ continue;
50
+ }
51
+ const m = FIELD_PATTERN.exec(f);
52
+ /* istanbul ignore next */
53
+ if (!m)
54
+ throw new TypeError(`Invalid field path (${input})`);
55
+ const fieldName = m[2];
56
+ const treeItem = (target[fieldName] = target[fieldName] || new FieldsProjection.Item());
57
+ if (m[1])
58
+ treeItem.sign = m[1];
59
+ if (i === fields.length - 1) {
60
+ delete treeItem.projection;
61
+ }
62
+ else {
63
+ target = treeItem.projection = treeItem.projection || new FieldsProjection();
64
+ }
65
+ }
66
+ }
package/esm/index.js CHANGED
@@ -28,4 +28,5 @@ export * from './orm/decorators/link.decorator.js';
28
28
  export * from './orm/decorators/primarykey.decorator.js';
29
29
  export * from './orm/decorators/transform.decorator.js';
30
30
  export { isColumnField, isEmbeddedField, isAssociationField, isEntityClass } from './orm/util/orm.helper.js';
31
+ export * from './orm/util/parse-fields-projection.js';
31
32
  export * from './orm/backward.js';
@@ -47,7 +47,7 @@ export async function joinAssociation(joinInfos, association, parentAlias, inner
47
47
  }
48
48
  export async function prepareFilter(entityDef, filter, trgOp, tableAlias = 'T') {
49
49
  let srcOp;
50
- if (isLogicalOperator(filter))
50
+ if (isLogicalOperator(filter) && filter._operatorType === trgOp._operatorType)
51
51
  srcOp = filter;
52
52
  else {
53
53
  srcOp = And();
@@ -1,9 +1,9 @@
1
1
  import { And, In, Param, Select } from '@sqb/builder';
2
- import { Entity } from '../decorators/entity.decorator.js';
3
2
  import { AssociationNode } from '../model/association-node.js';
4
3
  import { EmbeddedFieldMetadata } from '../model/embedded-field-metadata.js';
5
4
  import { EntityMetadata } from '../model/entity-metadata.js';
6
5
  import { isAssociationField, isColumnField, isEmbeddedField } from '../util/orm.helper.js';
6
+ import { parseFieldsProjection } from '../util/parse-fields-projection.js';
7
7
  import { joinAssociationGetLast, prepareFilter } from './command.helper.js';
8
8
  import { RowConverter } from './row-converter.js';
9
9
  const SORT_ORDER_PATTERN = /^([-+])?(.*)$/;
@@ -53,9 +53,7 @@ export class FindCommand {
53
53
  maxEagerFetch: args.maxEagerFetch,
54
54
  });
55
55
  await command.addFields({
56
- pick: args.pick,
57
- include: args.include,
58
- omit: args.omit,
56
+ projection: args.projection,
59
57
  sort: args.sort,
60
58
  });
61
59
  if (args.filter)
@@ -68,22 +66,10 @@ export class FindCommand {
68
66
  const tableAlias = opts.tableAlias || this.resultAlias;
69
67
  const entity = opts.entity || this._getEntityFromAlias(tableAlias);
70
68
  const converter = opts.converter || this.converter;
71
- const _pick = opts.pick ? opts.pick.map(x => x.toLowerCase()) : undefined;
72
- const _omit = opts.omit ? opts.omit.map(x => x.toLowerCase()) : undefined;
73
- const _include = opts.include ? opts.include.map(x => x.toLowerCase()) : undefined;
74
- let requestedFields;
75
- if (_pick)
76
- requestedFields = [..._pick];
77
- else {
78
- requestedFields = Entity.getFieldNames(entity.ctor).reduce((a, x) => {
79
- const f = Entity.getField(entity.ctor, x);
80
- if (f && !f.exclusive)
81
- a.push(x.toLowerCase());
82
- return a;
83
- }, []);
84
- }
85
- if (_include)
86
- requestedFields.push(..._include);
69
+ const projection = typeof opts.projection === 'string' || Array.isArray(opts.projection)
70
+ ? parseFieldsProjection(opts.projection)
71
+ : opts.projection;
72
+ const defaultFields = !projection || !Object.values(projection).find(p => !p.sign);
87
73
  const sortFields = opts.sort && opts.sort.length ? opts.sort.map(x => x.toLowerCase()) : undefined;
88
74
  const prefix = opts.prefix || '';
89
75
  const suffix = opts.suffix || '';
@@ -92,12 +78,16 @@ export class FindCommand {
92
78
  if (!col || col.hidden)
93
79
  continue;
94
80
  const colNameLower = col.name.toLowerCase();
95
- // Ignore field if in excluded list
96
- if (_omit && _omit.includes(colNameLower))
97
- continue;
98
- // Check if field request list
99
- if (!requestedFields.find((x) => x === colNameLower || x.startsWith(colNameLower + '.')))
81
+ const p = projection?.[colNameLower];
82
+ if (
83
+ /** Ignore if field is omitted */
84
+ p?.sign === '-' ||
85
+ /** Ignore if default fields and field is not in projection */
86
+ (!defaultFields && !p) ||
87
+ /** Ignore if default fields enabled and fields is exclusive */
88
+ (defaultFields && col.exclusive && !p)) {
100
89
  continue;
90
+ }
101
91
  // Add field to select list if field is a column
102
92
  if (isColumnField(col)) {
103
93
  const fieldAlias = this._selectColumn(tableAlias, col, prefix, suffix);
@@ -122,9 +112,7 @@ export class FindCommand {
122
112
  entity: typ,
123
113
  prefix: col.fieldNamePrefix,
124
114
  suffix: col.fieldNameSuffix,
125
- pick: _pick?.includes(colNameLower) ? undefined : extractSubFields(colNameLower, _pick),
126
- include: extractSubFields(colNameLower, _include),
127
- omit: extractSubFields(colNameLower, _omit),
115
+ projection: p?.projection,
128
116
  sort: extractSubFields(colNameLower, sortFields),
129
117
  });
130
118
  continue;
@@ -142,9 +130,7 @@ export class FindCommand {
142
130
  tableAlias: joinInfo.joinAlias,
143
131
  converter: subConverter,
144
132
  entity: joinInfo.targetEntity,
145
- pick: _pick?.includes(colNameLower) ? undefined : extractSubFields(colNameLower, _pick),
146
- include: extractSubFields(colNameLower, _include),
147
- omit: extractSubFields(colNameLower, _omit),
133
+ projection: p?.projection,
148
134
  sort: extractSubFields(colNameLower, sortFields),
149
135
  });
150
136
  continue;
@@ -164,9 +150,7 @@ export class FindCommand {
164
150
  await findCommand.filter(In(targetCol.name, Param(parentField)));
165
151
  const sort = sortFields && extractSubFields(colNameLower, sortFields);
166
152
  await findCommand.addFields({
167
- pick: _pick?.includes(colNameLower) ? undefined : extractSubFields(colNameLower, _pick),
168
- include: extractSubFields(colNameLower, _include),
169
- omit: extractSubFields(colNameLower, _omit),
153
+ projection: p?.projection,
170
154
  sort,
171
155
  });
172
156
  if (sort)
@@ -1,5 +1,9 @@
1
1
  import { EntityMetadata } from '../model/entity-metadata.js';
2
+ import { DECORATOR_FACTORY } from '../orm.const.js';
2
3
  export function Column(arg0) {
4
+ return Column[DECORATOR_FACTORY](arg0);
5
+ }
6
+ Column[DECORATOR_FACTORY] = function (arg0) {
3
7
  return (target, propertyKey) => {
4
8
  if (typeof propertyKey !== 'string')
5
9
  throw new Error('Symbol properties are not accepted');
@@ -16,4 +20,4 @@ export function Column(arg0) {
16
20
  }
17
21
  EntityMetadata.defineColumnField(entity, propertyKey, options);
18
22
  };
19
- }
23
+ };
@@ -1,2 +1,3 @@
1
1
  export const ENTITY_METADATA_KEY = Symbol.for('SQB_ENTITY_METADATA');
2
2
  export const REPOSITORY_KEY = Symbol.for('SQB_REPOSITORY');
3
+ export const DECORATOR_FACTORY = Symbol.for('decorator.factory');
@@ -38,15 +38,16 @@ export class Repository extends TypedEventEmitterClass(AsyncEventEmitter) {
38
38
  return this._exists(keyValue, { ...options, connection });
39
39
  }, options);
40
40
  }
41
+ existsOne(options) {
42
+ return this._execute(async (connection) => {
43
+ return this._existsOne({ ...options, connection });
44
+ }, options);
45
+ }
41
46
  count(options) {
42
47
  return this._execute(async (connection) => {
43
48
  return this._count({ ...options, connection });
44
49
  }, options);
45
50
  }
46
- /** @deprecated - Use findById instead */
47
- find(keyValue, options) {
48
- return this.findById(keyValue, options);
49
- }
50
51
  findById(keyValue, options) {
51
52
  return this._execute(async (connection) => {
52
53
  return this._find(keyValue, { ...options, connection });
@@ -129,11 +130,25 @@ export class Repository extends TypedEventEmitterClass(AsyncEventEmitter) {
129
130
  else
130
131
  filter.push(options.filter);
131
132
  }
132
- return !!(await CountCommand.execute({
133
+ return this._existsOne({
134
+ ...options,
135
+ filter,
136
+ });
137
+ }
138
+ async _existsOne(options) {
139
+ const filter = [];
140
+ if (options && options.filter) {
141
+ if (Array.isArray(options.filter))
142
+ filter.push(...options.filter);
143
+ else
144
+ filter.push(options.filter);
145
+ }
146
+ const resp = await FindCommand.execute({
133
147
  ...options,
134
148
  filter,
135
149
  entity: this._entity,
136
- }));
150
+ });
151
+ return resp.length > 0;
137
152
  }
138
153
  async _count(options) {
139
154
  return CountCommand.execute({
@@ -0,0 +1,61 @@
1
+ import { splitString } from 'fast-tokenizer';
2
+ const FIELD_PATTERN = /^([+-])?([a-z_$]\w*)$/i;
3
+ const NO_DOT_BRACKET_PATTERN = /[^.]\(/g;
4
+ export class FieldsProjection {
5
+ }
6
+ (function (FieldsProjection) {
7
+ class Item {
8
+ }
9
+ FieldsProjection.Item = Item;
10
+ })(FieldsProjection || (FieldsProjection = {}));
11
+ export function parseFieldsProjection(projection, keepCase) {
12
+ const arr = Array.isArray(projection) ? projection : [projection];
13
+ if (!(arr && arr.length))
14
+ return;
15
+ const out = new FieldsProjection();
16
+ for (let s of arr) {
17
+ if (!keepCase)
18
+ s = s.toLowerCase();
19
+ parse(s, out);
20
+ }
21
+ return out;
22
+ }
23
+ function parse(input, target) {
24
+ /** Add dot before brackets which is required to split fields */
25
+ input = input.replace(NO_DOT_BRACKET_PATTERN, s => {
26
+ return s.charAt(0) + '.' + s.substring(1);
27
+ });
28
+ const fields = splitString(input, {
29
+ delimiters: '.',
30
+ brackets: true,
31
+ keepBrackets: false,
32
+ });
33
+ for (let i = 0; i < fields.length; i++) {
34
+ const f = fields[i];
35
+ if (f.includes(',')) {
36
+ const subFields = splitString(f, {
37
+ delimiters: ',',
38
+ brackets: true,
39
+ keepBrackets: true,
40
+ });
41
+ for (const n of subFields) {
42
+ parse(n, target);
43
+ }
44
+ continue;
45
+ }
46
+ const m = FIELD_PATTERN.exec(f);
47
+ /* istanbul ignore next */
48
+ if (!m)
49
+ throw new TypeError(`Invalid field path (${input})`);
50
+ const fieldName = m[2];
51
+ const treeItem = (target[fieldName] = target[fieldName] || new FieldsProjection.Item());
52
+ if (m[1])
53
+ treeItem.sign = m[1];
54
+ if (i === fields.length - 1) {
55
+ delete treeItem.projection;
56
+ }
57
+ else {
58
+ target = treeItem.projection = treeItem.projection || new FieldsProjection();
59
+ }
60
+ }
61
+ }
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "@sqb/connect",
3
3
  "description": "Multi-dialect database connection framework written with TypeScript",
4
- "version": "4.12.0",
4
+ "version": "4.12.1",
5
5
  "author": "Panates",
6
6
  "contributors": [
7
7
  "Eray Hanoglu <e.hanoglu@panates.com>",
@@ -25,16 +25,18 @@
25
25
  "build:esm": "tsc -b tsconfig-build-esm.json",
26
26
  "postbuild": "cp README.md package.json ../../LICENSE ../../build/connect && cp ../../package.cjs.json ../../build/connect/cjs/package.json",
27
27
  "lint": "eslint . --max-warnings=0",
28
+ "lint:fix": "eslint . --max-warnings=0 --fix",
29
+ "format": "prettier . --write --log-level=warn",
28
30
  "test": "jest",
29
31
  "cover": "jest --collect-coverage",
30
32
  "clean": "npm run clean:src | npm run clean:dist | npm run clean:cover",
31
33
  "clean:src": "ts-cleanup -s src --all",
32
34
  "clean:dist": "rimraf ../../build/connectt",
33
- "clean:cover": "rimraf ../../coverage/connect",
34
- "format": "prettier . --write --log-level=warn"
35
+ "clean:cover": "rimraf ../../coverage/connect"
35
36
  },
36
37
  "dependencies": {
37
38
  "debug": "^4.3.5",
39
+ "fast-tokenizer": "^1.3.0",
38
40
  "lightning-pool": "^4.2.2",
39
41
  "lodash": "^4.17.21",
40
42
  "power-tasks": "^1.7.3",
@@ -47,10 +49,11 @@
47
49
  },
48
50
  "devDependencies": {
49
51
  "@types/debug": "^4.1.12",
50
- "@types/lodash": "^4.17.4"
52
+ "@types/lodash": "^4.17.5",
53
+ "postgresql-client": "^2.11.2"
51
54
  },
52
55
  "peerDependencies": {
53
- "@sqb/builder": "^4.12.0",
56
+ "@sqb/builder": "^4.12.1",
54
57
  "reflect-metadata": "^0.2.2"
55
58
  },
56
59
  "engines": {
package/types/index.d.ts CHANGED
@@ -28,4 +28,5 @@ export * from './orm/decorators/link.decorator.js';
28
28
  export * from './orm/decorators/primarykey.decorator.js';
29
29
  export * from './orm/decorators/transform.decorator.js';
30
30
  export { isColumnField, isEmbeddedField, isAssociationField, isEntityClass } from './orm/util/orm.helper.js';
31
+ export * from './orm/util/parse-fields-projection.js';
31
32
  export * from './orm/backward.js';
@@ -2,6 +2,7 @@ import { SqbConnection } from '../../client/sqb-connection.js';
2
2
  import { AssociationNode } from '../model/association-node.js';
3
3
  import { EntityMetadata } from '../model/entity-metadata.js';
4
4
  import { Repository } from '../repository.class.js';
5
+ import { FieldsProjection } from '../util/parse-fields-projection.js';
5
6
  import { RowConverter } from './row-converter.js';
6
7
  export type FindCommandArgs = {
7
8
  entity: EntityMetadata;
@@ -29,9 +30,7 @@ export declare class FindCommand {
29
30
  tableAlias?: string;
30
31
  converter?: RowConverter;
31
32
  entity?: EntityMetadata;
32
- pick?: string[];
33
- omit?: string[];
34
- include?: string[];
33
+ projection?: FieldsProjection | string | string[];
35
34
  sort?: string[];
36
35
  prefix?: string;
37
36
  suffix?: string;
@@ -2,3 +2,4 @@ import { DataType } from '@sqb/builder';
2
2
  import { ColumnFieldOptions } from '../model/column-field-metadata.js';
3
3
  export declare function Column(type?: DataType): PropertyDecorator;
4
4
  export declare function Column(options?: ColumnFieldOptions): PropertyDecorator;
5
+ export declare namespace Column { }
@@ -10,7 +10,7 @@ export interface FieldMetadata {
10
10
  hidden?: boolean;
11
11
  /**
12
12
  * Indicates whether or not to include this field by default when making queries.
13
- * If this set to "true" the field must be requested using "include" or "pick" option.
13
+ * If this set to "true" the field must be requested using "projection" option.
14
14
  */
15
15
  exclusive?: boolean;
16
16
  }
@@ -1,2 +1,3 @@
1
1
  export declare const ENTITY_METADATA_KEY: unique symbol;
2
2
  export declare const REPOSITORY_KEY: unique symbol;
3
+ export declare const DECORATOR_FACTORY: unique symbol;
@@ -6,9 +6,7 @@ import { SqbConnection } from '../client/sqb-connection.js';
6
6
  import { QueryRequest, TransactionFunction } from '../client/types.js';
7
7
  import { EntityMetadata } from './model/entity-metadata.js';
8
8
  interface Projection {
9
- pick?: string[];
10
- omit?: string[];
11
- include?: string[];
9
+ projection?: string | string[];
12
10
  }
13
11
  interface Filtering {
14
12
  filter?: LogicalOperator | LogicalOperator[] | object | object[];
@@ -31,7 +29,7 @@ export declare namespace Repository {
31
29
  }
32
30
  interface FindOptions extends CommandOptions, Projection, Filtering {
33
31
  }
34
- interface FindOneOptions extends CommandOptions, Projection, Filtering {
32
+ interface FindOneOptions extends FindOptions {
35
33
  sort?: string[];
36
34
  offset?: number;
37
35
  }
@@ -44,6 +42,8 @@ export declare namespace Repository {
44
42
  }
45
43
  interface UpdateOptions extends CommandOptions, Projection, Filtering {
46
44
  }
45
+ interface UpdateOnlyOptions extends CommandOptions, Filtering {
46
+ }
47
47
  interface UpdateManyOptions extends CommandOptions, Filtering {
48
48
  }
49
49
  }
@@ -63,16 +63,15 @@ export declare class Repository<T> extends Repository_base {
63
63
  create(values: PartialDTO<T>, options?: Repository.CreateOptions): Promise<PartialDTO<T>>;
64
64
  createOnly(values: PartialDTO<T>, options?: StrictOmit<Repository.CreateOptions, keyof Projection>): Promise<void>;
65
65
  exists(keyValue: any | Record<string, any>, options?: Repository.ExistsOptions): Promise<boolean>;
66
+ existsOne(options?: Repository.ExistsOptions): Promise<boolean>;
66
67
  count(options?: Repository.CountOptions): Promise<number>;
67
- /** @deprecated - Use findById instead */
68
- find(keyValue: any | Record<string, any>, options?: Repository.FindOptions): Promise<PartialDTO<T> | undefined>;
69
68
  findById(keyValue: any | Record<string, any>, options?: Repository.FindOptions): Promise<PartialDTO<T> | undefined>;
70
69
  findOne(options?: Repository.FindOneOptions): Promise<PartialDTO<T> | undefined>;
71
70
  findMany(options?: Repository.FindManyOptions): Promise<PartialDTO<T>[]>;
72
71
  delete(keyValue: any | Record<string, any>, options?: Repository.DeleteOptions): Promise<boolean>;
73
72
  deleteMany(options?: Repository.DeleteManyOptions): Promise<number>;
74
73
  update(keyValue: any | Record<string, any>, values: PatchDTO<T>, options?: Repository.UpdateOptions): Promise<PartialDTO<T> | undefined>;
75
- updateOnly(keyValue: any | Record<string, any>, values: PatchDTO<T>, options?: StrictOmit<Repository.UpdateOptions, keyof Projection>): Promise<boolean>;
74
+ updateOnly(keyValue: any | Record<string, any>, values: PatchDTO<T>, options?: Repository.UpdateOnlyOptions): Promise<boolean>;
76
75
  updateMany(values: PartialDTO<T>, options?: Repository.UpdateManyOptions): Promise<number>;
77
76
  protected _execute(fn: TransactionFunction, opts?: Repository.CommandOptions): Promise<any>;
78
77
  protected _create(values: PartialDTO<T>, options: Repository.CreateOptions & {
@@ -82,6 +81,9 @@ export declare class Repository<T> extends Repository_base {
82
81
  protected _exists(keyValue: any | Record<string, any>, options: Repository.ExistsOptions & {
83
82
  connection: SqbConnection;
84
83
  }): Promise<boolean>;
84
+ protected _existsOne(options: Repository.ExistsOptions & {
85
+ connection: SqbConnection;
86
+ }): Promise<boolean>;
85
87
  protected _count(options: Repository.CountOptions & {
86
88
  connection: SqbConnection;
87
89
  }): Promise<number>;
@@ -0,0 +1,10 @@
1
+ export declare class FieldsProjection {
2
+ [key: string]: FieldsProjection.Item;
3
+ }
4
+ export declare namespace FieldsProjection {
5
+ class Item {
6
+ sign?: string;
7
+ projection?: FieldsProjection;
8
+ }
9
+ }
10
+ export declare function parseFieldsProjection(projection: string | string[], keepCase?: boolean): FieldsProjection | undefined;