@opra/sqb 0.17.0 → 0.17.2

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.
@@ -34,7 +34,7 @@ var SQBAdapter;
34
34
  options.include = args.include?.length ? args.include : undefined;
35
35
  }
36
36
  if (resource instanceof common_1.Collection && args.filter) {
37
- options.filter = (0, transform_filter_js_1.default)(resource, args.filter);
37
+ options.filter = (0, transform_filter_js_1.default)(args.filter);
38
38
  }
39
39
  if (operation === 'findMany') {
40
40
  options.sort = args.sort?.length ? args.sort : undefined;
@@ -3,8 +3,13 @@ Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.SqbCollectionResource = void 0;
4
4
  const tslib_1 = require("tslib");
5
5
  const common_1 = require("@opra/common");
6
+ const core_1 = require("@opra/core");
6
7
  const sqb_adapter_js_1 = require("./sqb-adapter.js");
7
- class SqbCollectionResource {
8
+ // noinspection TypeScriptAbstractClassConstructorCanBeMadeProtected
9
+ class SqbCollectionResource extends core_1.CollectionResourceBase {
10
+ constructor(options) {
11
+ super(options);
12
+ }
8
13
  async create(ctx) {
9
14
  const prepared = sqb_adapter_js_1.SQBAdapter.transformRequest(ctx.request);
10
15
  const service = await this.getService(ctx);
@@ -40,14 +45,14 @@ class SqbCollectionResource {
40
45
  const service = await this.getService(ctx);
41
46
  if (prepared.options.count) {
42
47
  const [items, count] = await Promise.all([
43
- service.findAll(prepared.options),
48
+ service.findMany(prepared.options),
44
49
  service.count(prepared.options)
45
50
  ]);
46
51
  ctx.response.count = count;
47
52
  return items;
48
53
  }
49
54
  else
50
- return service.with(ctx).findAll(prepared.options);
55
+ return service.with(ctx).findMany(prepared.options);
51
56
  }
52
57
  }
53
58
  tslib_1.__decorate([
@@ -33,8 +33,8 @@ class SqbEntityService {
33
33
  await this._onError(e);
34
34
  throw e;
35
35
  }
36
- if (out && this.onTransformRow)
37
- out = this.onTransformRow(out);
36
+ if (out && this.transformData)
37
+ out = this.transformData(out);
38
38
  if (!out)
39
39
  throw new Error('"create" operation returned no result!');
40
40
  return out;
@@ -72,8 +72,8 @@ class SqbEntityService {
72
72
  await this._onError(e);
73
73
  throw e;
74
74
  }
75
- if (out && this.onTransformRow)
76
- out = this.onTransformRow(out);
75
+ if (out && this.transformData)
76
+ out = this.transformData(out);
77
77
  return out;
78
78
  }
79
79
  async findOne(options) {
@@ -87,25 +87,25 @@ class SqbEntityService {
87
87
  await this._onError(e);
88
88
  throw e;
89
89
  }
90
- if (out && this.onTransformRow)
91
- out = this.onTransformRow(out);
90
+ if (out && this.transformData)
91
+ out = this.transformData(out);
92
92
  return out;
93
93
  }
94
- async findAll(options) {
94
+ async findMany(options) {
95
95
  const conn = await this.getConnection();
96
96
  const repo = conn.getRepository(this.typeClass);
97
97
  let items;
98
98
  try {
99
- items = await repo.findAll(options);
99
+ items = await repo.findMany(options);
100
100
  }
101
101
  catch (e) {
102
102
  await this._onError(e);
103
103
  throw e;
104
104
  }
105
- if (items.length && this.onTransformRow) {
105
+ if (items.length && this.transformData) {
106
106
  const newItems = [];
107
107
  for (const item of items) {
108
- const v = this.onTransformRow(item);
108
+ const v = this.transformData(item);
109
109
  if (v)
110
110
  newItems.push(v);
111
111
  }
@@ -135,8 +135,8 @@ class SqbEntityService {
135
135
  await this._onError(e);
136
136
  throw e;
137
137
  }
138
- if (out && this.onTransformRow)
139
- out = this.onTransformRow(out);
138
+ if (out && this.transformData)
139
+ out = this.transformData(out);
140
140
  return out;
141
141
  }
142
142
  async updateMany(data, options) {
@@ -1,18 +1,40 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  const tslib_1 = require("tslib");
4
+ require("@opra/core");
4
5
  const common_1 = require("@opra/common");
5
6
  const sqb = tslib_1.__importStar(require("@sqb/builder"));
6
- function transformFilter(resource, str) {
7
- const ast = typeof str === 'string' ? (0, common_1.parseFilter)(str) : str;
7
+ function transformFilter(ast) {
8
8
  if (!ast)
9
9
  return;
10
- resource.normalizeFilter(ast);
11
- if (ast instanceof common_1.ComparisonExpression) {
12
- if (!(ast.left instanceof common_1.QualifiedIdentifier && ast.left.field))
13
- throw new TypeError(`Unsupported filter query. Left side should be a data field.`);
14
- const left = sqb.Field(ast.left.value);
15
- const right = transformFilter(resource, ast.right);
10
+ if (ast instanceof common_1.OpraFilter.QualifiedIdentifier) {
11
+ return sqb.Field(ast.value);
12
+ }
13
+ if (ast instanceof common_1.OpraFilter.NumberLiteral ||
14
+ ast instanceof common_1.OpraFilter.StringLiteral ||
15
+ ast instanceof common_1.OpraFilter.BooleanLiteral ||
16
+ ast instanceof common_1.OpraFilter.NullLiteral ||
17
+ ast instanceof common_1.OpraFilter.DateLiteral ||
18
+ ast instanceof common_1.OpraFilter.TimeLiteral) {
19
+ return ast.value;
20
+ }
21
+ if (ast instanceof common_1.OpraFilter.ArrayExpression) {
22
+ return ast.items.map(transformFilter);
23
+ }
24
+ if (ast instanceof common_1.OpraFilter.NegativeExpression) {
25
+ return sqb.Not(transformFilter(ast.expression));
26
+ }
27
+ if (ast instanceof common_1.OpraFilter.LogicalExpression) {
28
+ if (ast.op === 'or')
29
+ return sqb.Or(...ast.items.map(transformFilter));
30
+ return sqb.And(...ast.items.map(transformFilter));
31
+ }
32
+ if (ast instanceof common_1.OpraFilter.ParenthesizedExpression) {
33
+ return transformFilter(ast.expression);
34
+ }
35
+ if (ast instanceof common_1.OpraFilter.ComparisonExpression) {
36
+ const left = transformFilter(ast.left);
37
+ const right = transformFilter(ast.right);
16
38
  switch (ast.op) {
17
39
  case '=':
18
40
  return sqb.Eq(left, right);
@@ -31,39 +53,17 @@ function transformFilter(resource, str) {
31
53
  case '!in':
32
54
  return sqb.Nin(left, right);
33
55
  case 'like':
34
- return sqb.Like(left, right);
56
+ return sqb.Like(left, String(right).replace(/\*/, '%'));
35
57
  case 'ilike':
36
- return sqb.Ilike(left, right);
58
+ return sqb.Ilike(left, String(right).replace(/\*/, '%'));
37
59
  case '!like':
38
- return sqb.NotLike(left, right);
60
+ return sqb.NotLike(left, String(right).replace(/\*/, '%'));
39
61
  case '!ilike':
40
- return sqb.NotILike(left, right);
62
+ return sqb.NotILike(left, String(right).replace(/\*/, '%'));
41
63
  default:
42
64
  throw new Error(`ComparisonExpression operator (${ast.op}) not implemented yet`);
43
65
  }
44
66
  }
45
- if (ast instanceof common_1.QualifiedIdentifier) {
46
- return ast.value;
47
- }
48
- if (ast instanceof common_1.NumberLiteral ||
49
- ast instanceof common_1.StringLiteral ||
50
- ast instanceof common_1.BooleanLiteral ||
51
- ast instanceof common_1.NullLiteral ||
52
- ast instanceof common_1.DateLiteral ||
53
- ast instanceof common_1.TimeLiteral) {
54
- return ast.value;
55
- }
56
- if (ast instanceof common_1.ArrayExpression) {
57
- return ast.items.map(i => transformFilter(resource, i));
58
- }
59
- if (ast instanceof common_1.LogicalExpression) {
60
- if (ast.op === 'or')
61
- return sqb.Or(...ast.items.map((i => transformFilter(resource, i))));
62
- return sqb.And(...ast.items.map((i => transformFilter(resource, i))));
63
- }
64
- if (ast instanceof common_1.ParenthesesExpression) {
65
- return transformFilter(resource, ast.expression);
66
- }
67
- throw new Error(`${ast.type} is not implemented yet`);
67
+ throw new Error(`${ast.kind} is not implemented yet`);
68
68
  }
69
69
  exports.default = transformFilter;
@@ -30,7 +30,7 @@ export var SQBAdapter;
30
30
  options.include = args.include?.length ? args.include : undefined;
31
31
  }
32
32
  if (resource instanceof Collection && args.filter) {
33
- options.filter = _transformFilter(resource, args.filter);
33
+ options.filter = _transformFilter(args.filter);
34
34
  }
35
35
  if (operation === 'findMany') {
36
36
  options.sort = args.sort?.length ? args.sort : undefined;
@@ -1,7 +1,12 @@
1
1
  import { __decorate, __metadata } from "tslib";
2
2
  import { Collection } from '@opra/common';
3
+ import { CollectionResourceBase } from '@opra/core';
3
4
  import { SQBAdapter } from './sqb-adapter.js';
4
- export class SqbCollectionResource {
5
+ // noinspection TypeScriptAbstractClassConstructorCanBeMadeProtected
6
+ export class SqbCollectionResource extends CollectionResourceBase {
7
+ constructor(options) {
8
+ super(options);
9
+ }
5
10
  async create(ctx) {
6
11
  const prepared = SQBAdapter.transformRequest(ctx.request);
7
12
  const service = await this.getService(ctx);
@@ -37,14 +42,14 @@ export class SqbCollectionResource {
37
42
  const service = await this.getService(ctx);
38
43
  if (prepared.options.count) {
39
44
  const [items, count] = await Promise.all([
40
- service.findAll(prepared.options),
45
+ service.findMany(prepared.options),
41
46
  service.count(prepared.options)
42
47
  ]);
43
48
  ctx.response.count = count;
44
49
  return items;
45
50
  }
46
51
  else
47
- return service.with(ctx).findAll(prepared.options);
52
+ return service.with(ctx).findMany(prepared.options);
48
53
  }
49
54
  }
50
55
  __decorate([
@@ -30,8 +30,8 @@ export class SqbEntityService {
30
30
  await this._onError(e);
31
31
  throw e;
32
32
  }
33
- if (out && this.onTransformRow)
34
- out = this.onTransformRow(out);
33
+ if (out && this.transformData)
34
+ out = this.transformData(out);
35
35
  if (!out)
36
36
  throw new Error('"create" operation returned no result!');
37
37
  return out;
@@ -69,8 +69,8 @@ export class SqbEntityService {
69
69
  await this._onError(e);
70
70
  throw e;
71
71
  }
72
- if (out && this.onTransformRow)
73
- out = this.onTransformRow(out);
72
+ if (out && this.transformData)
73
+ out = this.transformData(out);
74
74
  return out;
75
75
  }
76
76
  async findOne(options) {
@@ -84,25 +84,25 @@ export class SqbEntityService {
84
84
  await this._onError(e);
85
85
  throw e;
86
86
  }
87
- if (out && this.onTransformRow)
88
- out = this.onTransformRow(out);
87
+ if (out && this.transformData)
88
+ out = this.transformData(out);
89
89
  return out;
90
90
  }
91
- async findAll(options) {
91
+ async findMany(options) {
92
92
  const conn = await this.getConnection();
93
93
  const repo = conn.getRepository(this.typeClass);
94
94
  let items;
95
95
  try {
96
- items = await repo.findAll(options);
96
+ items = await repo.findMany(options);
97
97
  }
98
98
  catch (e) {
99
99
  await this._onError(e);
100
100
  throw e;
101
101
  }
102
- if (items.length && this.onTransformRow) {
102
+ if (items.length && this.transformData) {
103
103
  const newItems = [];
104
104
  for (const item of items) {
105
- const v = this.onTransformRow(item);
105
+ const v = this.transformData(item);
106
106
  if (v)
107
107
  newItems.push(v);
108
108
  }
@@ -132,8 +132,8 @@ export class SqbEntityService {
132
132
  await this._onError(e);
133
133
  throw e;
134
134
  }
135
- if (out && this.onTransformRow)
136
- out = this.onTransformRow(out);
135
+ if (out && this.transformData)
136
+ out = this.transformData(out);
137
137
  return out;
138
138
  }
139
139
  async updateMany(data, options) {
@@ -1,15 +1,37 @@
1
- import { ArrayExpression, BooleanLiteral, ComparisonExpression, DateLiteral, LogicalExpression, NullLiteral, NumberLiteral, ParenthesesExpression, parseFilter, QualifiedIdentifier, StringLiteral, TimeLiteral } from '@opra/common';
1
+ import '@opra/core';
2
+ import { OpraFilter } from '@opra/common';
2
3
  import * as sqb from '@sqb/builder';
3
- export default function transformFilter(resource, str) {
4
- const ast = typeof str === 'string' ? parseFilter(str) : str;
4
+ export default function transformFilter(ast) {
5
5
  if (!ast)
6
6
  return;
7
- resource.normalizeFilter(ast);
8
- if (ast instanceof ComparisonExpression) {
9
- if (!(ast.left instanceof QualifiedIdentifier && ast.left.field))
10
- throw new TypeError(`Unsupported filter query. Left side should be a data field.`);
11
- const left = sqb.Field(ast.left.value);
12
- const right = transformFilter(resource, ast.right);
7
+ if (ast instanceof OpraFilter.QualifiedIdentifier) {
8
+ return sqb.Field(ast.value);
9
+ }
10
+ if (ast instanceof OpraFilter.NumberLiteral ||
11
+ ast instanceof OpraFilter.StringLiteral ||
12
+ ast instanceof OpraFilter.BooleanLiteral ||
13
+ ast instanceof OpraFilter.NullLiteral ||
14
+ ast instanceof OpraFilter.DateLiteral ||
15
+ ast instanceof OpraFilter.TimeLiteral) {
16
+ return ast.value;
17
+ }
18
+ if (ast instanceof OpraFilter.ArrayExpression) {
19
+ return ast.items.map(transformFilter);
20
+ }
21
+ if (ast instanceof OpraFilter.NegativeExpression) {
22
+ return sqb.Not(transformFilter(ast.expression));
23
+ }
24
+ if (ast instanceof OpraFilter.LogicalExpression) {
25
+ if (ast.op === 'or')
26
+ return sqb.Or(...ast.items.map(transformFilter));
27
+ return sqb.And(...ast.items.map(transformFilter));
28
+ }
29
+ if (ast instanceof OpraFilter.ParenthesizedExpression) {
30
+ return transformFilter(ast.expression);
31
+ }
32
+ if (ast instanceof OpraFilter.ComparisonExpression) {
33
+ const left = transformFilter(ast.left);
34
+ const right = transformFilter(ast.right);
13
35
  switch (ast.op) {
14
36
  case '=':
15
37
  return sqb.Eq(left, right);
@@ -28,38 +50,16 @@ export default function transformFilter(resource, str) {
28
50
  case '!in':
29
51
  return sqb.Nin(left, right);
30
52
  case 'like':
31
- return sqb.Like(left, right);
53
+ return sqb.Like(left, String(right).replace(/\*/, '%'));
32
54
  case 'ilike':
33
- return sqb.Ilike(left, right);
55
+ return sqb.Ilike(left, String(right).replace(/\*/, '%'));
34
56
  case '!like':
35
- return sqb.NotLike(left, right);
57
+ return sqb.NotLike(left, String(right).replace(/\*/, '%'));
36
58
  case '!ilike':
37
- return sqb.NotILike(left, right);
59
+ return sqb.NotILike(left, String(right).replace(/\*/, '%'));
38
60
  default:
39
61
  throw new Error(`ComparisonExpression operator (${ast.op}) not implemented yet`);
40
62
  }
41
63
  }
42
- if (ast instanceof QualifiedIdentifier) {
43
- return ast.value;
44
- }
45
- if (ast instanceof NumberLiteral ||
46
- ast instanceof StringLiteral ||
47
- ast instanceof BooleanLiteral ||
48
- ast instanceof NullLiteral ||
49
- ast instanceof DateLiteral ||
50
- ast instanceof TimeLiteral) {
51
- return ast.value;
52
- }
53
- if (ast instanceof ArrayExpression) {
54
- return ast.items.map(i => transformFilter(resource, i));
55
- }
56
- if (ast instanceof LogicalExpression) {
57
- if (ast.op === 'or')
58
- return sqb.Or(...ast.items.map((i => transformFilter(resource, i))));
59
- return sqb.And(...ast.items.map((i => transformFilter(resource, i))));
60
- }
61
- if (ast instanceof ParenthesesExpression) {
62
- return transformFilter(resource, ast.expression);
63
- }
64
- throw new Error(`${ast.type} is not implemented yet`);
64
+ throw new Error(`${ast.kind} is not implemented yet`);
65
65
  }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@opra/sqb",
3
- "version": "0.17.0",
3
+ "version": "0.17.2",
4
4
  "description": "Opra SQB adapter package",
5
5
  "author": "Panates",
6
6
  "license": "MIT",
@@ -30,15 +30,15 @@
30
30
  },
31
31
  "devDependencies": {
32
32
  "@faker-js/faker": "^7.6.0",
33
- "@sqb/builder": "^4.8.2",
34
- "@sqb/connect": "^4.8.2",
35
- "@sqb/postgres": "^4.8.2",
33
+ "@sqb/builder": "^4.9.0",
34
+ "@sqb/connect": "^4.9.0",
35
+ "@sqb/postgres": "^4.9.0",
36
36
  "postgresql-client": "^2.5.5",
37
37
  "ts-gems": "^2.3.0"
38
38
  },
39
39
  "peerDependencies": {
40
- "@opra/core": "^0.17.0",
41
- "@sqb/connect": ">= 4.8.2"
40
+ "@opra/core": "^0.17.2",
41
+ "@sqb/connect": ">= 4.9.0"
42
42
  },
43
43
  "type": "module",
44
44
  "types": "types/index.d.ts",
@@ -1,14 +1,19 @@
1
1
  import { Maybe } from 'ts-gems';
2
2
  import { PartialOutput } from '@opra/common';
3
- import { RequestContext } from '@opra/core';
3
+ import { CollectionResourceBase, RequestContext } from '@opra/core';
4
4
  import { SqbEntityService } from './sqb-entity-service.js';
5
- export declare abstract class SqbCollectionResource<T> {
6
- create(ctx: RequestContext): Promise<PartialOutput<T>>;
5
+ export declare namespace SqbCollectionResource {
6
+ interface Options extends CollectionResourceBase.Options {
7
+ }
8
+ }
9
+ export declare abstract class SqbCollectionResource<T, TOutput = PartialOutput<T>> extends CollectionResourceBase {
10
+ constructor(options?: SqbCollectionResource.Options);
11
+ create(ctx: RequestContext): Promise<TOutput>;
7
12
  delete(ctx: RequestContext): Promise<boolean>;
8
13
  deleteMany(ctx: RequestContext): Promise<number>;
9
- find(ctx: RequestContext): Promise<Maybe<PartialOutput<T>>>;
10
- update(ctx: RequestContext): Promise<Maybe<PartialOutput<T>>>;
14
+ find(ctx: RequestContext): Promise<Maybe<TOutput>>;
15
+ update(ctx: RequestContext): Promise<Maybe<TOutput>>;
11
16
  updateMany(ctx: RequestContext): Promise<number>;
12
- findMany(ctx: RequestContext): Promise<PartialOutput<T>[]>;
13
- abstract getService(ctx: RequestContext): SqbEntityService<T> | Promise<SqbEntityService<T>>;
17
+ findMany(ctx: RequestContext): Promise<TOutput[]>;
18
+ abstract getService(ctx: RequestContext): SqbEntityService<T, TOutput> | Promise<SqbEntityService<T, TOutput>>;
14
19
  }
@@ -19,7 +19,7 @@ export declare class SqbEntityService<T, TOutput = PartialOutput<T>> {
19
19
  deleteMany(options?: Repository.DestroyOptions): Promise<number>;
20
20
  find(keyValue: any, options?: Repository.FindOptions): Promise<Maybe<TOutput>>;
21
21
  findOne(options?: Repository.FindOneOptions): Promise<Maybe<TOutput>>;
22
- findAll(options?: Repository.FindManyOptions): Promise<TOutput[]>;
22
+ findMany(options?: Repository.FindManyOptions): Promise<TOutput[]>;
23
23
  exists(options?: Repository.ExistsOptions): Promise<boolean>;
24
24
  update(keyValue: any, data: EntityInput<T>, options?: Repository.UpdateOptions): Promise<Maybe<TOutput>>;
25
25
  updateMany(data: PartialInput<T>, options?: Repository.UpdateManyOptions): Promise<number>;
@@ -27,5 +27,5 @@ export declare class SqbEntityService<T, TOutput = PartialOutput<T>> {
27
27
  protected _onError(error: unknown): Promise<void>;
28
28
  protected getConnection(): SqbConnection | SqbClient | Promise<SqbConnection | SqbClient>;
29
29
  protected onError?(error: unknown): void | Promise<void>;
30
- protected onTransformRow?(row: TOutput): TOutput;
30
+ protected transformData?(row: TOutput): TOutput;
31
31
  }
@@ -1,2 +1,3 @@
1
- import { Collection, Expression } from '@opra/common';
2
- export default function transformFilter(resource: Collection, str: string | Expression | undefined): any;
1
+ import '@opra/core';
2
+ import { OpraFilter } from '@opra/common';
3
+ export default function transformFilter(ast: OpraFilter.Expression | undefined): any;