crud-query-parser 0.0.1 → 0.0.3
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.
Potentially problematic release.
This version of crud-query-parser might be problematic. Click here for more details.
- package/README.md +32 -11
- package/dist/adapters/typeorm/index.d.mts +22 -5
- package/dist/adapters/typeorm/index.d.ts +22 -5
- package/dist/adapters/typeorm/index.js +1 -1
- package/dist/adapters/typeorm/index.js.map +1 -1
- package/dist/adapters/typeorm/index.mjs +1 -1
- package/dist/adapters/typeorm/index.mjs.map +1 -1
- package/dist/crud-request-where.builder-D60W-QEd.d.ts +32 -0
- package/dist/crud-request-where.builder-mP8y-fQp.d.mts +32 -0
- package/dist/helpers/nestjs/index.d.mts +18 -0
- package/dist/helpers/nestjs/index.d.ts +18 -0
- package/dist/helpers/nestjs/index.js +2 -0
- package/dist/helpers/nestjs/index.js.map +1 -0
- package/dist/helpers/nestjs/index.mjs +2 -0
- package/dist/helpers/nestjs/index.mjs.map +1 -0
- package/dist/index.d.mts +2 -1
- package/dist/index.d.ts +2 -1
- package/dist/index.js +1 -1
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +1 -1
- package/dist/index.mjs.map +1 -1
- package/dist/parsers/crud/index.d.mts +5 -2
- package/dist/parsers/crud/index.d.ts +5 -2
- package/dist/parsers/crud/index.js +1 -1
- package/dist/parsers/crud/index.js.map +1 -1
- package/dist/parsers/crud/index.mjs +1 -1
- package/dist/parsers/crud/index.mjs.map +1 -1
- package/dist/request-parser-B-fK5GnP.d.ts +31 -0
- package/dist/request-parser-WaQBZsYG.d.mts +31 -0
- package/package.json +28 -2
- package/dist/parsed-request-where.builder-CTGRmvAX.d.ts +0 -42
- package/dist/parsed-request-where.builder-LCWNWCt6.d.mts +0 -42
package/README.md
CHANGED
@@ -5,14 +5,9 @@ This library parses HTTP requests and converts them to TypeORM query builders, a
|
|
5
5
|
## Install
|
6
6
|
|
7
7
|
```sh
|
8
|
-
npm install
|
8
|
+
npm install crud-query-parser
|
9
9
|
```
|
10
10
|
|
11
|
-
### Other modules
|
12
|
-
|
13
|
-
- `@crud-query-parser/typeorm`: TypeORM adapter
|
14
|
-
- `@crud-query-parser/nestjs`: NestJS utilities
|
15
|
-
|
16
11
|
## Usage
|
17
12
|
|
18
13
|
You have to pick a request parser and a query adapter.
|
@@ -40,12 +35,15 @@ console.log(result);
|
|
40
35
|
|
41
36
|
### CRUD
|
42
37
|
|
43
|
-
|
38
|
+
The CRUD parser is an implementation of the `@nestjsx/crud` [query params format](https://github.com/nestjsx/crud/wiki/Requests#query-params).
|
44
39
|
|
45
40
|
```ts
|
46
41
|
import { CrudRequestParser } from 'crud-query-parser/parsers/crud';
|
47
42
|
|
48
43
|
const parser = new CrudRequestParser();
|
44
|
+
|
45
|
+
// Then, you have to pass a query string object to it
|
46
|
+
// const crudRequest = parser.parse(request.query);
|
49
47
|
```
|
50
48
|
|
51
49
|
## Database adapters
|
@@ -59,7 +57,8 @@ import { TypeormQueryAdapter } from 'crud-query-parser/adapters/typeorm';
|
|
59
57
|
|
60
58
|
const adapter = new TypeormQueryAdapter();
|
61
59
|
|
62
|
-
//
|
60
|
+
// Then, you can pass a query builder to it:
|
61
|
+
// const result = adapter.getMany(repository.createQueryBuilder(), crudRequest);
|
63
62
|
```
|
64
63
|
|
65
64
|
## Helpers
|
@@ -74,15 +73,37 @@ Sample code:
|
|
74
73
|
@Controller('users')
|
75
74
|
export class UserController {
|
76
75
|
|
76
|
+
constructor(
|
77
|
+
private service: UserService,
|
78
|
+
) {}
|
79
|
+
|
77
80
|
@Get()
|
78
|
-
@Crud(CrudRequestParser)
|
79
|
-
public async getMany(@ParseCrudRequest() crudRequest: CrudRequest) {
|
81
|
+
@Crud(CrudRequestParser) // <- You specify which parser to use
|
82
|
+
public async getMany(@ParseCrudRequest() crudRequest: CrudRequest) { // <- The request query will be automatically parsed
|
80
83
|
return this.service.getMany(crudRequest);
|
81
84
|
}
|
82
85
|
|
83
86
|
}
|
84
87
|
```
|
85
88
|
|
89
|
+
```ts
|
90
|
+
@Injectable()
|
91
|
+
export class UserService {
|
92
|
+
|
93
|
+
protected crudAdapter = new TypeormQueryAdapter();
|
94
|
+
|
95
|
+
constructor(
|
96
|
+
@InjectRepository(UserEntity)
|
97
|
+
private repository: Repository<UserEntity>,
|
98
|
+
) {}
|
99
|
+
|
100
|
+
public async getMany(crudRequest: CrudRequest) {
|
101
|
+
return await this.crudAdapter.getMany(this.repository.createQueryBuilder(), crudRequest);
|
102
|
+
}
|
103
|
+
|
104
|
+
}
|
105
|
+
```
|
106
|
+
|
86
107
|
## Filters
|
87
108
|
|
88
109
|
You may need to filter what the user can or cannot query. You can modify the `CrudRequest` object as needed.
|
@@ -100,7 +121,7 @@ import { ensureCondition } from 'crud-query-parser/filters';
|
|
100
121
|
|
101
122
|
crudRequest = ensureCondition(crudRequest, {
|
102
123
|
field: ['isActive'],
|
103
|
-
operator:
|
124
|
+
operator: CrudRequestWhereOperator.EQ,
|
104
125
|
value: true,
|
105
126
|
});
|
106
127
|
```
|
@@ -2,10 +2,20 @@ import { SelectQueryBuilder, ObjectLiteral, WhereExpressionBuilder } from 'typeo
|
|
2
2
|
import { Q as QueryAdapter, G as GetManyResult } from '../../query-adapter-BliD9hJN.mjs';
|
3
3
|
import { c as CrudRequest, P as ParsedRequestSelect, a as CrudRequestRelation, b as CrudRequestOrder, d as CrudRequestWhere, g as CrudRequestWhereField } from '../../crud-request-CvDKp6Iy.mjs';
|
4
4
|
|
5
|
+
interface TypeOrmQueryAdapterOptions {
|
6
|
+
/**
|
7
|
+
* Whether it will use ILIKE for case-insensitive operations.
|
8
|
+
*
|
9
|
+
* If undefined, it will be enabled by default for postgres and aurora-postgres databases
|
10
|
+
*/
|
11
|
+
ilike?: boolean;
|
12
|
+
}
|
5
13
|
/**
|
6
14
|
* Adapts queries to TypeORM query builder object
|
7
15
|
*/
|
8
|
-
declare class
|
16
|
+
declare class TypeOrmQueryAdapter implements QueryAdapter<SelectQueryBuilder<any>, ObjectLiteral> {
|
17
|
+
private readonly options;
|
18
|
+
constructor(options?: TypeOrmQueryAdapterOptions);
|
9
19
|
/**
|
10
20
|
* @inheritDoc
|
11
21
|
*/
|
@@ -44,8 +54,9 @@ declare class TypeormQueryAdapter implements QueryAdapter<SelectQueryBuilder<any
|
|
44
54
|
*
|
45
55
|
* @param qb The query builder
|
46
56
|
* @param relations The parsed relation list
|
57
|
+
* @param select The parsed select fields
|
47
58
|
*/
|
48
|
-
protected adaptRelations<E extends ObjectLiteral>(qb: SelectQueryBuilder<E>, relations: CrudRequestRelation[]): void;
|
59
|
+
protected adaptRelations<E extends ObjectLiteral>(qb: SelectQueryBuilder<E>, relations: CrudRequestRelation[], select: ParsedRequestSelect): void;
|
49
60
|
/**
|
50
61
|
* Adapts the order by list
|
51
62
|
*
|
@@ -56,12 +67,14 @@ declare class TypeormQueryAdapter implements QueryAdapter<SelectQueryBuilder<any
|
|
56
67
|
/**
|
57
68
|
* Adapts a where condition
|
58
69
|
*
|
70
|
+
* @param alias The query builder alias
|
59
71
|
* @param qb The query builder
|
60
72
|
* @param where The quere condition
|
61
73
|
* @param or Whether this where condition is AND/OR
|
62
74
|
* @param params The registered parameter name list
|
75
|
+
* @param isILikeEnabled Whether the ILIKE operator can be used
|
63
76
|
*/
|
64
|
-
protected adaptWhere(qb: WhereExpressionBuilder, where: CrudRequestWhere, or: boolean, params: string[]): void;
|
77
|
+
protected adaptWhere(alias: string, qb: WhereExpressionBuilder, where: CrudRequestWhere, or: boolean, params: string[], isILikeEnabled: boolean): void;
|
65
78
|
/**
|
66
79
|
* Creates a query parameter name based on a field
|
67
80
|
*
|
@@ -72,13 +85,17 @@ declare class TypeormQueryAdapter implements QueryAdapter<SelectQueryBuilder<any
|
|
72
85
|
/**
|
73
86
|
* Maps where operators to a pseudo-SQL statement and a parameter map
|
74
87
|
*
|
88
|
+
* @param alias The query builder alias
|
75
89
|
* @param where The where condition
|
76
90
|
* @param param The parameter name
|
91
|
+
* @param isILikeEnabled Whether the ILIKE operator can be used
|
77
92
|
*/
|
78
|
-
protected mapWhereOperators(where: CrudRequestWhereField, param: string): {
|
93
|
+
protected mapWhereOperators(alias: string, where: CrudRequestWhereField, param: string, isILikeEnabled: boolean): {
|
79
94
|
where: string;
|
80
95
|
params: ObjectLiteral;
|
81
96
|
};
|
97
|
+
protected createLowerLike(isILikeEnabled: boolean, field: string, not?: boolean): string;
|
98
|
+
protected isILikeEnabled(qb: SelectQueryBuilder<any>): boolean;
|
82
99
|
}
|
83
100
|
|
84
|
-
export {
|
101
|
+
export { TypeOrmQueryAdapter, type TypeOrmQueryAdapterOptions };
|
@@ -2,10 +2,20 @@ import { SelectQueryBuilder, ObjectLiteral, WhereExpressionBuilder } from 'typeo
|
|
2
2
|
import { Q as QueryAdapter, G as GetManyResult } from '../../query-adapter-Vebxws3V.js';
|
3
3
|
import { c as CrudRequest, P as ParsedRequestSelect, a as CrudRequestRelation, b as CrudRequestOrder, d as CrudRequestWhere, g as CrudRequestWhereField } from '../../crud-request-CvDKp6Iy.js';
|
4
4
|
|
5
|
+
interface TypeOrmQueryAdapterOptions {
|
6
|
+
/**
|
7
|
+
* Whether it will use ILIKE for case-insensitive operations.
|
8
|
+
*
|
9
|
+
* If undefined, it will be enabled by default for postgres and aurora-postgres databases
|
10
|
+
*/
|
11
|
+
ilike?: boolean;
|
12
|
+
}
|
5
13
|
/**
|
6
14
|
* Adapts queries to TypeORM query builder object
|
7
15
|
*/
|
8
|
-
declare class
|
16
|
+
declare class TypeOrmQueryAdapter implements QueryAdapter<SelectQueryBuilder<any>, ObjectLiteral> {
|
17
|
+
private readonly options;
|
18
|
+
constructor(options?: TypeOrmQueryAdapterOptions);
|
9
19
|
/**
|
10
20
|
* @inheritDoc
|
11
21
|
*/
|
@@ -44,8 +54,9 @@ declare class TypeormQueryAdapter implements QueryAdapter<SelectQueryBuilder<any
|
|
44
54
|
*
|
45
55
|
* @param qb The query builder
|
46
56
|
* @param relations The parsed relation list
|
57
|
+
* @param select The parsed select fields
|
47
58
|
*/
|
48
|
-
protected adaptRelations<E extends ObjectLiteral>(qb: SelectQueryBuilder<E>, relations: CrudRequestRelation[]): void;
|
59
|
+
protected adaptRelations<E extends ObjectLiteral>(qb: SelectQueryBuilder<E>, relations: CrudRequestRelation[], select: ParsedRequestSelect): void;
|
49
60
|
/**
|
50
61
|
* Adapts the order by list
|
51
62
|
*
|
@@ -56,12 +67,14 @@ declare class TypeormQueryAdapter implements QueryAdapter<SelectQueryBuilder<any
|
|
56
67
|
/**
|
57
68
|
* Adapts a where condition
|
58
69
|
*
|
70
|
+
* @param alias The query builder alias
|
59
71
|
* @param qb The query builder
|
60
72
|
* @param where The quere condition
|
61
73
|
* @param or Whether this where condition is AND/OR
|
62
74
|
* @param params The registered parameter name list
|
75
|
+
* @param isILikeEnabled Whether the ILIKE operator can be used
|
63
76
|
*/
|
64
|
-
protected adaptWhere(qb: WhereExpressionBuilder, where: CrudRequestWhere, or: boolean, params: string[]): void;
|
77
|
+
protected adaptWhere(alias: string, qb: WhereExpressionBuilder, where: CrudRequestWhere, or: boolean, params: string[], isILikeEnabled: boolean): void;
|
65
78
|
/**
|
66
79
|
* Creates a query parameter name based on a field
|
67
80
|
*
|
@@ -72,13 +85,17 @@ declare class TypeormQueryAdapter implements QueryAdapter<SelectQueryBuilder<any
|
|
72
85
|
/**
|
73
86
|
* Maps where operators to a pseudo-SQL statement and a parameter map
|
74
87
|
*
|
88
|
+
* @param alias The query builder alias
|
75
89
|
* @param where The where condition
|
76
90
|
* @param param The parameter name
|
91
|
+
* @param isILikeEnabled Whether the ILIKE operator can be used
|
77
92
|
*/
|
78
|
-
protected mapWhereOperators(where: CrudRequestWhereField, param: string): {
|
93
|
+
protected mapWhereOperators(alias: string, where: CrudRequestWhereField, param: string, isILikeEnabled: boolean): {
|
79
94
|
where: string;
|
80
95
|
params: ObjectLiteral;
|
81
96
|
};
|
97
|
+
protected createLowerLike(isILikeEnabled: boolean, field: string, not?: boolean): string;
|
98
|
+
protected isILikeEnabled(qb: SelectQueryBuilder<any>): boolean;
|
82
99
|
}
|
83
100
|
|
84
|
-
export {
|
101
|
+
export { TypeOrmQueryAdapter, type TypeOrmQueryAdapterOptions };
|
@@ -1,2 +1,2 @@
|
|
1
|
-
"use strict";var
|
1
|
+
"use strict";var E=Object.defineProperty;var T=Object.getOwnPropertyDescriptor;var g=Object.getOwnPropertyNames;var O=Object.prototype.hasOwnProperty;var c=(o,t)=>E(o,"name",{value:t,configurable:!0});var _=(o,t)=>{for(var r in t)E(o,r,{get:t[r],enumerable:!0})},w=(o,t,r,e)=>{if(t&&typeof t=="object"||typeof t=="function")for(let i of g(t))!O.call(o,i)&&i!==r&&E(o,i,{get:()=>t[i],enumerable:!(e=T(t,i))||e.enumerable});return o};var S=o=>w(E({},"__esModule",{value:!0}),o);var R={};_(R,{TypeOrmQueryAdapter:()=>N});module.exports=S(R);var h=require("typeorm");function d(o,t,r=0){if(!Array.isArray(t)||t.length<r)throw new Error(`${o} must be an array with at least ${r} items`);return t}c(d,"ensureArray");function f(o,t){if(t)throw new Error(`${o} must be null`)}c(f,"ensureFalsy");function L(o){return o!=null}c(L,"isValid");function $(o,t){return o.length-1!==t.length?!1:t.every((r,e)=>o[e]===r)}c($,"pathHasBase");var N=class{constructor(t={}){this.options=t}static{c(this,"TypeOrmQueryAdapter")}build(t,r){return t=this.createBaseQuery(t,r),t=this.paginateQuery(t,r),t}async getOne(t,r){return await this.createBaseQuery(t,r).getOne()??null}async getMany(t,r){let e=this.createBaseQuery(t,r),s=await this.paginateQuery(e.clone(),r).getMany(),a=await e.getCount(),n=r.offset??0,l=r.limit??a,u=s.length,p=Math.floor(n/l)+1,y=Math.ceil(a/l);return{data:s,count:u,page:p,pageCount:y,total:a}}createBaseQuery(t,r){let e=[],i=this.isILikeEnabled(t);return this.adaptSelect(t,r.select),this.adaptRelations(t,r.relations,r.select),this.adaptWhere(t.alias,t,r.where,!1,e,i),this.adaptOrder(t,r.order),t}paginateQuery(t,r){return t.limit(r.limit).offset(r.offset)}adaptSelect(t,r){if(r.length===0)return;let e=r.filter(i=>i.field.length===1);t.select(e.map(i=>[t.alias,...i.field].join(".")))}adaptRelations(t,r,e){for(let i of r){let s=[t.alias,...i.field].join("."),a=i.alias||s.replace(".","_"),n=e.filter(l=>$(l.field,i.field));n.length===0?t.leftJoinAndSelect(s,a):(t.leftJoin(s,a),t.addSelect(n.map(l=>[a,l.field[l.field.length-1]].join("."))))}}adaptOrder(t,r){for(let e of r){let i=[t.alias,...e.field].join(".");t.addOrderBy(i,e.order)}}adaptWhere(t,r,e,i,s,a){let n=(i?r.orWhere:r.andWhere).bind(r);if(e.or&&e.or.length>0)n(new h.Brackets(l=>e.or.forEach(u=>this.adaptWhere(t,l,u,!0,s,a))));else if(e.and&&e.and.length>0)n(new h.Brackets(l=>e.and.forEach(u=>this.adaptWhere(t,l,u,!1,s,a))));else if(e.field){let l=this.createParam(s,e.field),u=this.mapWhereOperators(t,e,l,a);n(u.where,u.params)}}createParam(t,r){let e=r.length>0?r[r.length-1]:"",i,s=0;do i="req_"+e+"_"+s,s++;while(t.includes(i));return t.push(i),i}mapWhereOperators(t,r,e,i){let s=[t,...r.field].join("."),a=r.operator,n=r.value;switch(a){case"eq":return{where:`${s} = :${e}`,params:{[e]:n}};case"neq":return{where:`${s} != :${e}`,params:{[e]:n}};case"gt":return{where:`${s} > :${e}`,params:{[e]:n}};case"gte":return{where:`${s} >= :${e}`,params:{[e]:n}};case"lt":return{where:`${s} < :${e}`,params:{[e]:n}};case"lte":return{where:`${s} <= :${e}`,params:{[e]:n}};case"starts":return{where:`${s} LIKE :${e}`,params:{[e]:`${n}%`}};case"ends":return{where:`${s} LIKE :${e}`,params:{[e]:`%${n}`}};case"contains":return{where:`${s} LIKE :${e}`,params:{[e]:`%${n}%`}};case"not_contains":return{where:`${s} NOT LIKE :${e}`,params:{[e]:`%${n}%`}};case"in":return n=d("IN operator",n,1),{where:`${s} IN (:...${e})`,params:{[e]:n}};case"not_in":return n=d("NOT IN operator",n,1),{where:`${s} NOT IN (:...${e})`,params:{[e]:n}};case"between":let l=d("BETWEEN operator",n,2);return{where:`${s} BETWEEN :${e}_start AND :${e}_end`,params:{[`${e}_start`]:l[0],[`${e}_end`]:l[1]}};case"is_null":return f("IS NULL operator",n),{where:`${s} IS NULL`,params:{}};case"not_null":return f("NOT NULL operator",n),{where:`${s} IS NOT NULL`,params:{}};case"eq_lower":return{where:`LOWER(${s}) = :${e}`,params:{[e]:n}};case"neq_lower":return{where:`LOWER(${s}) != :${e}`,params:{[e]:n}};case"starts_lower":return{where:`${this.createLowerLike(i,s)} :${e}`,params:{[e]:`${n}%`}};case"ends_lower":return{where:`${this.createLowerLike(i,s)} :${e}`,params:{[e]:`%${n}`}};case"contains_lower":return{where:`${this.createLowerLike(i,s)} :${e}`,params:{[e]:`%${n}%`}};case"not_contains_lower":return{where:`${this.createLowerLike(i,s,!0)} :${e}`,params:{[e]:`%${n}%`}};case"in_lower":return d("IN operator",n,1),{where:`LOWER(${s}) IN (...:${e})`,params:{[e]:n}};case"not_in_lower":return d("NOT IN operator",n,1),{where:`LOWER(${s}) NOT IN (...:${e})`,params:{[e]:n}};default:throw new Error(`Unknown operator "${a}"`)}}createLowerLike(t,r,e=!1){return t?e?`${r} NOT ILIKE`:`${r} ILIKE`:e?`LOWER(${r}) NOT LIKE`:`LOWER(${r}) LIKE`}isILikeEnabled(t){let r=this.options.ilike;if(L(r))return r;let e=t.connection.options.type;return e==="postgres"||e==="aurora-postgres"}};0&&(module.exports={TypeOrmQueryAdapter});
|
2
2
|
//# sourceMappingURL=index.js.map
|
@@ -1 +1 @@
|
|
1
|
-
{"version":3,"sources":["../../../src/adapters/typeorm/index.ts","../../../src/adapters/typeorm/typeorm.query-adapter.ts","../../../src/utils/functions.ts"],"sourcesContent":["\r\nexport * from './typeorm.query-adapter';\r\n","import { Brackets, ObjectLiteral, SelectQueryBuilder, WhereExpressionBuilder } from 'typeorm';\r\nimport { QueryAdapter } from '../../models/query-adapter';\r\nimport {\r\n CrudRequest,\r\n CrudRequestOrder,\r\n CrudRequestRelation,\r\n ParsedRequestSelect\r\n} from '../../models/crud-request';\r\nimport {\r\n CrudRequestWhere,\r\n CrudRequestWhereField,\r\n CrudRequestWhereOperator\r\n} from '../../models/crud-request-where';\r\nimport { GetManyResult } from '../../models/get-many-result';\r\nimport { ensureArray, ensureFalsy } from '../../utils/functions';\r\n\r\n/**\r\n * Adapts queries to TypeORM query builder object\r\n */\r\nexport class TypeormQueryAdapter implements QueryAdapter<SelectQueryBuilder<any>, ObjectLiteral> {\r\n\r\n /**\r\n * @inheritDoc\r\n */\r\n public build<E extends ObjectLiteral>(qb: SelectQueryBuilder<E>, query: CrudRequest): SelectQueryBuilder<E> {\r\n qb = this.createBaseQuery(qb, query);\r\n qb = this.paginateQuery(qb, query);\r\n\r\n return qb;\r\n }\r\n\r\n /**\r\n * @inheritDoc\r\n */\r\n public async getOne<E extends ObjectLiteral>(qb: SelectQueryBuilder<E | any>, request: CrudRequest): Promise<E | null> {\r\n const query = this.createBaseQuery(qb, request);\r\n const entity = await query.getOne();\r\n\r\n return entity ?? null;\r\n }\r\n\r\n /**\r\n * @inheritDoc\r\n */\r\n public async getMany<E extends ObjectLiteral>(qb: SelectQueryBuilder<E | any>, request: CrudRequest): Promise<GetManyResult<E>> {\r\n const fullQuery = this.createBaseQuery(qb, request);\r\n const paginatedQuery = this.paginateQuery(fullQuery.clone(), request);\r\n\r\n const data = await paginatedQuery.getMany();\r\n const total = await fullQuery.getCount();\r\n\r\n const offset = request.offset ?? 0;\r\n const limit = request.limit ?? total;\r\n\r\n const count = data.length;\r\n const page = Math.floor(offset / limit) + 1;\r\n const pageCount = Math.ceil(total / limit);\r\n\r\n return {\r\n data,\r\n count,\r\n page,\r\n pageCount,\r\n total,\r\n };\r\n }\r\n\r\n /**\r\n * Creates a query filtered from the parsed request\r\n *\r\n * @param qb The base query builder\r\n * @param query The parsed query\r\n */\r\n protected createBaseQuery<E extends ObjectLiteral>(qb: SelectQueryBuilder<E>, query: CrudRequest): SelectQueryBuilder<E> {\r\n const paramsDefined: string[] = [];\r\n\r\n this.adaptSelect(qb, query.select);\r\n this.adaptRelations(qb, query.relations);\r\n this.adaptWhere(qb, query.where, false, paramsDefined);\r\n this.adaptOrder(qb, query.order);\r\n\r\n return qb;\r\n }\r\n\r\n /**\r\n * Paginates a query based on the parsed request\r\n *\r\n * @param qb The query builder\r\n * @param query The parsed query\r\n */\r\n protected paginateQuery<E extends ObjectLiteral>(qb: SelectQueryBuilder<E>, query: CrudRequest): SelectQueryBuilder<E> {\r\n return qb.limit(query.limit).offset(query.offset);\r\n }\r\n\r\n /**\r\n * Adapts a select\r\n *\r\n * @param qb The query builder\r\n * @param select The parsed select fields\r\n */\r\n protected adaptSelect<E extends ObjectLiteral>(qb: SelectQueryBuilder<E>, select: ParsedRequestSelect): void {\r\n qb.addSelect(select.map(s => s.field.join('.')));\r\n }\r\n\r\n /**\r\n * Adapts the join relation list\r\n *\r\n * @param qb The query builder\r\n * @param relations The parsed relation list\r\n */\r\n protected adaptRelations<E extends ObjectLiteral>(qb: SelectQueryBuilder<E>, relations: CrudRequestRelation[]): void {\r\n for (const relation of relations) {\r\n const path = relation.field.join('.');\r\n const alias = relation.alias || path.replace('.', '_');\r\n\r\n qb.leftJoin(path, alias);\r\n }\r\n }\r\n\r\n /**\r\n * Adapts the order by list\r\n *\r\n * @param qb The query builder\r\n * @param ordering The parsed ordering\r\n */\r\n protected adaptOrder<E extends ObjectLiteral>(qb: SelectQueryBuilder<E>, ordering: CrudRequestOrder[]): void {\r\n for (const order of ordering) {\r\n const path = order.field.join('.');\r\n\r\n qb.addOrderBy(path, order.order);\r\n }\r\n }\r\n\r\n /**\r\n * Adapts a where condition\r\n *\r\n * @param qb The query builder\r\n * @param where The quere condition\r\n * @param or Whether this where condition is AND/OR\r\n * @param params The registered parameter name list\r\n */\r\n protected adaptWhere(qb: WhereExpressionBuilder, where: CrudRequestWhere, or: boolean, params: string[]): void {\r\n const addWhere = (or ? qb.orWhere : qb.andWhere).bind(qb);\r\n\r\n if (where.or && where.or.length > 0) {\r\n addWhere(new Brackets(\r\n wqb => where.or!.forEach(item => this.adaptWhere(wqb, item, true, params))\r\n ));\r\n } else if (where.and && where.and.length > 0) {\r\n addWhere(new Brackets(\r\n wqb => where.and!.forEach(item => this.adaptWhere(wqb, item, false, params))\r\n ));\r\n } else if (where.field) {\r\n const param = this.createParam(params, where.field);\r\n const query = this.mapWhereOperators(where as CrudRequestWhereField, param);\r\n\r\n addWhere(query.where, query.params);\r\n }\r\n }\r\n\r\n /**\r\n * Creates a query parameter name based on a field\r\n *\r\n * @param paramsDefined The array the parameter will be registered onto\r\n * @param field The field path\r\n */\r\n protected createParam(paramsDefined: string[], field: string[]): string {\r\n const name = field.length > 0 ? field[field.length - 1] : '';\r\n let param: string;\r\n let iteration: number = 0;\r\n\r\n do {\r\n param = 'req_' + name + '_' + iteration;\r\n iteration++;\r\n } while (paramsDefined.includes(param));\r\n\r\n paramsDefined.push(param);\r\n return param;\r\n }\r\n\r\n /**\r\n * Maps where operators to a pseudo-SQL statement and a parameter map\r\n *\r\n * @param where The where condition\r\n * @param param The parameter name\r\n */\r\n protected mapWhereOperators(where: CrudRequestWhereField, param: string): { where: string, params: ObjectLiteral } {\r\n const field = where.field.join('.');\r\n const operator = where.operator;\r\n let value: unknown = where.value;\r\n\r\n switch (operator) {\r\n case CrudRequestWhereOperator.EQ:\r\n return { where: `${field} = :${param}`, params: { [param]: value } };\r\n\r\n case CrudRequestWhereOperator.NEQ:\r\n return { where: `${field} != :${param}`, params: { [param]: value } };\r\n\r\n case CrudRequestWhereOperator.GT:\r\n return { where: `${field} > :${param}`, params: { [param]: value } };\r\n\r\n case CrudRequestWhereOperator.GTE:\r\n return { where: `${field} >= :${param}`, params: { [param]: value } };\r\n\r\n case CrudRequestWhereOperator.LT:\r\n return { where: `${field} < :${param}`, params: { [param]: value } };\r\n\r\n case CrudRequestWhereOperator.LTE:\r\n return { where: `${field} <= :${param}`, params: { [param]: value } };\r\n\r\n case CrudRequestWhereOperator.STARTS:\r\n return { where: `${field} LIKE :${param}`, params: { [param]: `${value}%` } };\r\n\r\n case CrudRequestWhereOperator.ENDS:\r\n return { where: `${field} LIKE :${param}`, params: { [param]: `%${value}` } };\r\n\r\n case CrudRequestWhereOperator.CONTAINS:\r\n return { where: `${field} LIKE :${param}`, params: { [param]: `%${value}%` } };\r\n\r\n case CrudRequestWhereOperator.NOT_CONTAINS:\r\n return { where: `${field} NOT LIKE :${param}`, params: { [param]: `%${value}%` } };\r\n\r\n case CrudRequestWhereOperator.IN:\r\n value = ensureArray('IN operator', value, 1);\r\n\r\n return { where: `${field} IN (:...${param})`, params: { [param]: value } };\r\n\r\n case CrudRequestWhereOperator.NOT_IN:\r\n value = ensureArray('NOT IN operator', value, 1);\r\n\r\n return { where: `${field} NOT IN (:...${param})`, params: { [param]: value } };\r\n\r\n case CrudRequestWhereOperator.BETWEEN:\r\n const arr = ensureArray('BETWEEN operator', value, 2);\r\n\r\n return {\r\n where: `${field} BETWEEN :${param}_start AND :${param}_end`,\r\n params: { [`${param}_start`]: arr[0], [`${param}_end`]: arr[1] },\r\n };\r\n\r\n case CrudRequestWhereOperator.IS_NULL:\r\n ensureFalsy('IS NULL operator', value);\r\n\r\n return { where: `${field} IS NULL`, params: {} };\r\n\r\n case CrudRequestWhereOperator.NOT_NULL:\r\n ensureFalsy('NOT NULL operator', value);\r\n\r\n return { where: `${field} IS NOT NULL`, params: {} };\r\n\r\n case CrudRequestWhereOperator.EQ_LOWER:\r\n return { where: `LOWER(${field}) = :${param}`, params: { [param]: value } };\r\n\r\n case CrudRequestWhereOperator.NEQ_LOWER:\r\n return { where: `LOWER(${field}) != :${param}`, params: { [param]: value } };\r\n\r\n case CrudRequestWhereOperator.STARTS_LOWER:\r\n return { where: `LOWER(${field}) LIKE :${param}`, params: { [param]: `${value}%` } };\r\n\r\n case CrudRequestWhereOperator.ENDS_LOWER:\r\n return { where: `LOWER(${field}) LIKE :${param}`, params: { [param]: `%${value}` } };\r\n\r\n case CrudRequestWhereOperator.CONTAINS_LOWER:\r\n return { where: `${field} LIKE :${param}`, params: { [param]: `%${value}%` } };\r\n\r\n case CrudRequestWhereOperator.NOT_CONTAINS_LOWER:\r\n return { where: `${field} NOT LIKE :${param}`, params: { [param]: `%${value}%` } };\r\n\r\n case CrudRequestWhereOperator.IN_LOWER:\r\n ensureArray('IN operator', value, 1);\r\n\r\n return { where: `${field} IN (...:${param})`, params: { [param]: value } };\r\n\r\n case CrudRequestWhereOperator.NOT_IN_LOWER:\r\n ensureArray('NOT IN operator', value, 1);\r\n\r\n return { where: `${field} NOT IN (...:${param})`, params: { [param]: value } };\r\n\r\n default:\r\n throw new Error(`Unknown operator \"${operator}\"`);\r\n }\r\n }\r\n\r\n}\r\n","import { CrudRequestFields } from '../models/crud-request';\r\n\r\n/*export function setFieldByPath<T>(obj: ParsedRequestFields<T>, field: string, value: T): void {\r\n const parts = field.split('.');\r\n\r\n while (parts.length > 1) {\r\n const name = parts.shift();\r\n\r\n if (!Array.isArray(obj[name]))\r\n obj[name] = {};\r\n\r\n obj = obj[name] as ParsedRequestFields<T>;\r\n }\r\n\r\n obj[parts.shift()] = value;\r\n}*/\r\n\r\nexport function ensureArray<T>(fieldName: string, data: T[] | any, minLength: number = 0): T[] {\r\n if (!Array.isArray(data) || data.length < minLength)\r\n throw new Error(`${fieldName} must be an array with at least ${minLength} items`);\r\n\r\n return data;\r\n}\r\n\r\nexport function ensureFalsy(fieldName: string, data: any) {\r\n if (data)\r\n throw new Error(`${fieldName} must be null`);\r\n}\r\n\r\nexport function isValid(value: any): value is object {\r\n return value !== null && value !== undefined;\r\n}\r\n"],"mappings":"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","names":["typeorm_exports","__export","TypeormQueryAdapter","__toCommonJS","import_typeorm","ensureArray","fieldName","data","minLength","__name","ensureFalsy","TypeormQueryAdapter","__name","qb","query","request","fullQuery","data","total","offset","limit","count","page","pageCount","paramsDefined","select","s","relations","relation","path","alias","ordering","order","where","or","params","addWhere","wqb","item","param","field","name","iteration","operator","value","ensureArray","arr","ensureFalsy"]}
|
1
|
+
{"version":3,"sources":["../../../src/adapters/typeorm/index.ts","../../../src/adapters/typeorm/typeorm.query-adapter.ts","../../../src/utils/functions.ts","../../../src/utils/field-path.ts"],"sourcesContent":["\r\nexport * from './typeorm.query-adapter';\r\n","import { Brackets, ObjectLiteral, SelectQueryBuilder, WhereExpressionBuilder } from 'typeorm';\r\nimport { QueryAdapter } from '../../models/query-adapter';\r\nimport { CrudRequest, CrudRequestOrder, CrudRequestRelation, ParsedRequestSelect } from '../../models/crud-request';\r\nimport { CrudRequestWhere, CrudRequestWhereField, CrudRequestWhereOperator } from '../../models/crud-request-where';\r\nimport { GetManyResult } from '../../models/get-many-result';\r\nimport { ensureArray, ensureFalsy, isValid } from '../../utils/functions';\r\nimport { pathHasBase } from '../../utils/field-path';\r\n\r\nexport interface TypeOrmQueryAdapterOptions {\r\n /**\r\n * Whether it will use ILIKE for case-insensitive operations.\r\n *\r\n * If undefined, it will be enabled by default for postgres and aurora-postgres databases\r\n */\r\n ilike?: boolean;\r\n}\r\n\r\n/**\r\n * Adapts queries to TypeORM query builder object\r\n */\r\nexport class TypeOrmQueryAdapter implements QueryAdapter<SelectQueryBuilder<any>, ObjectLiteral> {\r\n\r\n constructor(\r\n private readonly options: TypeOrmQueryAdapterOptions = {},\r\n ) {}\r\n\r\n /**\r\n * @inheritDoc\r\n */\r\n public build<E extends ObjectLiteral>(qb: SelectQueryBuilder<E>, query: CrudRequest): SelectQueryBuilder<E> {\r\n qb = this.createBaseQuery(qb, query);\r\n qb = this.paginateQuery(qb, query);\r\n\r\n return qb;\r\n }\r\n\r\n /**\r\n * @inheritDoc\r\n */\r\n public async getOne<E extends ObjectLiteral>(qb: SelectQueryBuilder<E | any>, request: CrudRequest): Promise<E | null> {\r\n const query = this.createBaseQuery(qb, request);\r\n const entity = await query.getOne();\r\n\r\n return entity ?? null;\r\n }\r\n\r\n /**\r\n * @inheritDoc\r\n */\r\n public async getMany<E extends ObjectLiteral>(qb: SelectQueryBuilder<E | any>, request: CrudRequest): Promise<GetManyResult<E>> {\r\n const fullQuery = this.createBaseQuery(qb, request);\r\n const paginatedQuery = this.paginateQuery(fullQuery.clone(), request);\r\n\r\n const data = await paginatedQuery.getMany();\r\n const total = await fullQuery.getCount();\r\n\r\n const offset = request.offset ?? 0;\r\n const limit = request.limit ?? total;\r\n\r\n const count = data.length;\r\n const page = Math.floor(offset / limit) + 1;\r\n const pageCount = Math.ceil(total / limit);\r\n\r\n return {\r\n data,\r\n count,\r\n page,\r\n pageCount,\r\n total,\r\n };\r\n }\r\n\r\n /**\r\n * Creates a query filtered from the parsed request\r\n *\r\n * @param qb The base query builder\r\n * @param query The parsed query\r\n */\r\n protected createBaseQuery<E extends ObjectLiteral>(qb: SelectQueryBuilder<E>, query: CrudRequest): SelectQueryBuilder<E> {\r\n const paramsDefined: string[] = [];\r\n const isILikeEnabled = this.isILikeEnabled(qb);\r\n\r\n this.adaptSelect(qb, query.select);\r\n this.adaptRelations(qb, query.relations, query.select);\r\n this.adaptWhere(qb.alias, qb, query.where, false, paramsDefined, isILikeEnabled);\r\n this.adaptOrder(qb, query.order);\r\n\r\n return qb;\r\n }\r\n\r\n /**\r\n * Paginates a query based on the parsed request\r\n *\r\n * @param qb The query builder\r\n * @param query The parsed query\r\n */\r\n protected paginateQuery<E extends ObjectLiteral>(qb: SelectQueryBuilder<E>, query: CrudRequest): SelectQueryBuilder<E> {\r\n return qb.limit(query.limit).offset(query.offset);\r\n }\r\n\r\n /**\r\n * Adapts a select\r\n *\r\n * @param qb The query builder\r\n * @param select The parsed select fields\r\n */\r\n protected adaptSelect<E extends ObjectLiteral>(qb: SelectQueryBuilder<E>, select: ParsedRequestSelect): void {\r\n if (select.length === 0)\r\n return;\r\n\r\n // Only fields that are one level deep\r\n const fields = select.filter(f => f.field.length === 1);\r\n\r\n qb.select(fields.map(s => [qb.alias, ...s.field].join('.')));\r\n }\r\n\r\n /**\r\n * Adapts the join relation list\r\n *\r\n * @param qb The query builder\r\n * @param relations The parsed relation list\r\n * @param select The parsed select fields\r\n */\r\n protected adaptRelations<E extends ObjectLiteral>(qb: SelectQueryBuilder<E>, relations: CrudRequestRelation[], select: ParsedRequestSelect): void {\r\n for (const relation of relations) {\r\n const path = [qb.alias, ...relation.field].join('.');\r\n const alias = relation.alias || path.replace('.', '_');\r\n\r\n const fields = select.filter(f => pathHasBase(f.field, relation.field));\r\n\r\n if (fields.length === 0) {\r\n qb.leftJoinAndSelect(path, alias);\r\n } else {\r\n qb.leftJoin(path, alias);\r\n qb.addSelect(fields.map(f => [alias, f.field[f.field.length - 1]].join('.')));\r\n }\r\n }\r\n }\r\n\r\n /**\r\n * Adapts the order by list\r\n *\r\n * @param qb The query builder\r\n * @param ordering The parsed ordering\r\n */\r\n protected adaptOrder<E extends ObjectLiteral>(qb: SelectQueryBuilder<E>, ordering: CrudRequestOrder[]): void {\r\n for (const order of ordering) {\r\n const path = [qb.alias, ...order.field].join('.');\r\n\r\n qb.addOrderBy(path, order.order);\r\n }\r\n }\r\n\r\n /**\r\n * Adapts a where condition\r\n *\r\n * @param alias The query builder alias\r\n * @param qb The query builder\r\n * @param where The quere condition\r\n * @param or Whether this where condition is AND/OR\r\n * @param params The registered parameter name list\r\n * @param isILikeEnabled Whether the ILIKE operator can be used\r\n */\r\n protected adaptWhere(\r\n alias: string,\r\n qb: WhereExpressionBuilder,\r\n where: CrudRequestWhere,\r\n or: boolean,\r\n params: string[],\r\n isILikeEnabled: boolean,\r\n ): void {\r\n const addWhere = (or ? qb.orWhere : qb.andWhere).bind(qb);\r\n\r\n if (where.or && where.or.length > 0) {\r\n addWhere(new Brackets(\r\n wqb => where.or!.forEach(item => this.adaptWhere(alias, wqb, item, true, params, isILikeEnabled))\r\n ));\r\n } else if (where.and && where.and.length > 0) {\r\n addWhere(new Brackets(\r\n wqb => where.and!.forEach(item => this.adaptWhere(alias, wqb, item, false, params, isILikeEnabled))\r\n ));\r\n } else if (where.field) {\r\n const param = this.createParam(params, where.field);\r\n const query = this.mapWhereOperators(alias, where as CrudRequestWhereField, param, isILikeEnabled);\r\n\r\n addWhere(query.where, query.params);\r\n }\r\n }\r\n\r\n /**\r\n * Creates a query parameter name based on a field\r\n *\r\n * @param paramsDefined The array the parameter will be registered onto\r\n * @param field The field path\r\n */\r\n protected createParam(paramsDefined: string[], field: string[]): string {\r\n const name = field.length > 0 ? field[field.length - 1] : '';\r\n let param: string;\r\n let iteration: number = 0;\r\n\r\n do {\r\n param = 'req_' + name + '_' + iteration;\r\n iteration++;\r\n } while (paramsDefined.includes(param));\r\n\r\n paramsDefined.push(param);\r\n return param;\r\n }\r\n\r\n /**\r\n * Maps where operators to a pseudo-SQL statement and a parameter map\r\n *\r\n * @param alias The query builder alias\r\n * @param where The where condition\r\n * @param param The parameter name\r\n * @param isILikeEnabled Whether the ILIKE operator can be used\r\n */\r\n protected mapWhereOperators(\r\n alias: string,\r\n where: CrudRequestWhereField,\r\n param: string,\r\n isILikeEnabled: boolean,\r\n ): { where: string, params: ObjectLiteral } {\r\n const field = [alias, ...where.field].join('.');\r\n const operator = where.operator;\r\n let value: unknown = where.value;\r\n\r\n switch (operator) {\r\n case CrudRequestWhereOperator.EQ:\r\n return { where: `${field} = :${param}`, params: { [param]: value } };\r\n\r\n case CrudRequestWhereOperator.NEQ:\r\n return { where: `${field} != :${param}`, params: { [param]: value } };\r\n\r\n case CrudRequestWhereOperator.GT:\r\n return { where: `${field} > :${param}`, params: { [param]: value } };\r\n\r\n case CrudRequestWhereOperator.GTE:\r\n return { where: `${field} >= :${param}`, params: { [param]: value } };\r\n\r\n case CrudRequestWhereOperator.LT:\r\n return { where: `${field} < :${param}`, params: { [param]: value } };\r\n\r\n case CrudRequestWhereOperator.LTE:\r\n return { where: `${field} <= :${param}`, params: { [param]: value } };\r\n\r\n case CrudRequestWhereOperator.STARTS:\r\n return { where: `${field} LIKE :${param}`, params: { [param]: `${value}%` } };\r\n\r\n case CrudRequestWhereOperator.ENDS:\r\n return { where: `${field} LIKE :${param}`, params: { [param]: `%${value}` } };\r\n\r\n case CrudRequestWhereOperator.CONTAINS:\r\n return { where: `${field} LIKE :${param}`, params: { [param]: `%${value}%` } };\r\n\r\n case CrudRequestWhereOperator.NOT_CONTAINS:\r\n return { where: `${field} NOT LIKE :${param}`, params: { [param]: `%${value}%` } };\r\n\r\n case CrudRequestWhereOperator.IN:\r\n value = ensureArray('IN operator', value, 1);\r\n\r\n return { where: `${field} IN (:...${param})`, params: { [param]: value } };\r\n\r\n case CrudRequestWhereOperator.NOT_IN:\r\n value = ensureArray('NOT IN operator', value, 1);\r\n\r\n return { where: `${field} NOT IN (:...${param})`, params: { [param]: value } };\r\n\r\n case CrudRequestWhereOperator.BETWEEN:\r\n const arr = ensureArray('BETWEEN operator', value, 2);\r\n\r\n return {\r\n where: `${field} BETWEEN :${param}_start AND :${param}_end`,\r\n params: { [`${param}_start`]: arr[0], [`${param}_end`]: arr[1] },\r\n };\r\n\r\n case CrudRequestWhereOperator.IS_NULL:\r\n ensureFalsy('IS NULL operator', value);\r\n\r\n return { where: `${field} IS NULL`, params: {} };\r\n\r\n case CrudRequestWhereOperator.NOT_NULL:\r\n ensureFalsy('NOT NULL operator', value);\r\n\r\n return { where: `${field} IS NOT NULL`, params: {} };\r\n\r\n case CrudRequestWhereOperator.EQ_LOWER:\r\n return { where: `LOWER(${field}) = :${param}`, params: { [param]: value } };\r\n\r\n case CrudRequestWhereOperator.NEQ_LOWER:\r\n return { where: `LOWER(${field}) != :${param}`, params: { [param]: value } };\r\n\r\n case CrudRequestWhereOperator.STARTS_LOWER:\r\n return { where: `${this.createLowerLike(isILikeEnabled, field)} :${param}`, params: { [param]: `${value}%` } };\r\n\r\n case CrudRequestWhereOperator.ENDS_LOWER:\r\n return { where: `${this.createLowerLike(isILikeEnabled, field)} :${param}`, params: { [param]: `%${value}` } };\r\n\r\n case CrudRequestWhereOperator.CONTAINS_LOWER:\r\n return { where: `${this.createLowerLike(isILikeEnabled, field)} :${param}`, params: { [param]: `%${value}%` } };\r\n\r\n case CrudRequestWhereOperator.NOT_CONTAINS_LOWER:\r\n return { where: `${this.createLowerLike(isILikeEnabled, field, true)} :${param}`, params: { [param]: `%${value}%` } };\r\n\r\n case CrudRequestWhereOperator.IN_LOWER:\r\n ensureArray('IN operator', value, 1);\r\n\r\n return { where: `LOWER(${field}) IN (...:${param})`, params: { [param]: value } };\r\n\r\n case CrudRequestWhereOperator.NOT_IN_LOWER:\r\n ensureArray('NOT IN operator', value, 1);\r\n\r\n return { where: `LOWER(${field}) NOT IN (...:${param})`, params: { [param]: value } };\r\n\r\n default:\r\n throw new Error(`Unknown operator \"${operator}\"`);\r\n }\r\n }\r\n\r\n protected createLowerLike(isILikeEnabled: boolean, field: string, not: boolean = false): string {\r\n if (isILikeEnabled)\r\n return not ? `${field} NOT ILIKE` : `${field} ILIKE`;\r\n\r\n return not ? `LOWER(${field}) NOT LIKE` : `LOWER(${field}) LIKE`;\r\n }\r\n\r\n protected isILikeEnabled(qb: SelectQueryBuilder<any>): boolean {\r\n const ilikeEnabled = this.options.ilike;\r\n\r\n if (isValid(ilikeEnabled))\r\n return ilikeEnabled;\r\n\r\n const type = qb.connection.options.type;\r\n return type === 'postgres' || type === 'aurora-postgres';\r\n }\r\n\r\n}\r\n","import { CrudRequestFields } from '../models/crud-request';\r\n\r\n/*export function setFieldByPath<T>(obj: ParsedRequestFields<T>, field: string, value: T): void {\r\n const parts = field.split('.');\r\n\r\n while (parts.length > 1) {\r\n const name = parts.shift();\r\n\r\n if (!Array.isArray(obj[name]))\r\n obj[name] = {};\r\n\r\n obj = obj[name] as ParsedRequestFields<T>;\r\n }\r\n\r\n obj[parts.shift()] = value;\r\n}*/\r\n\r\nexport function ensurePrimitive(fieldName: string, data: any) {\r\n if (data === null || data === undefined)\r\n return;\r\n\r\n if (typeof data === 'number' || typeof data === 'string' || typeof data === 'boolean')\r\n return;\r\n\r\n if (data instanceof Date)\r\n return;\r\n\r\n throw new Error(`${fieldName} must be a string, number, boolean or null`);\r\n}\r\n\r\nexport function ensureArray<T>(fieldName: string, data: T[] | any, minLength: number = 0): T[] {\r\n if (!Array.isArray(data) || data.length < minLength)\r\n throw new Error(`${fieldName} must be an array with at least ${minLength} items`);\r\n\r\n return data;\r\n}\r\n\r\nexport function ensureFalsy(fieldName: string, data: any) {\r\n if (data)\r\n throw new Error(`${fieldName} must be null`);\r\n}\r\n\r\nexport function isValid<T>(value: T | undefined | null): value is T {\r\n return value !== null && value !== undefined;\r\n}\r\n","/**\r\n * Checks whether two field paths are equal\r\n *\r\n * E.g. [\"path\", \"to\", \"field\"] is equal to [\"path\", \"to\", \"field\"] but not [\"something\", \"else\"]\r\n */\r\nexport function pathEquals(path1: string[], path2: string[]): boolean {\r\n if (path1.length !== path2.length)\r\n return false;\r\n\r\n return path1.every((p1, i) => path2[i] === p1);\r\n}\r\n\r\n/**\r\n * Checks whether a path starts with another path.\r\n *\r\n * E.g. [\"path\", \"to\", \"field\"] starts with [\"path\"] or [\"path\", \"to\"] but not [\"something\", \"else\"]\r\n */\r\nexport function pathStartsWith(path: string[], start: string[]): boolean {\r\n if (path.length < start.length)\r\n return false;\r\n\r\n return start.every((start, i) => path[i] === start);\r\n}\r\n\r\n/**\r\n * Checks whether the base of a path matches.\r\n *\r\n * E.g. [\"path\", \"to\", \"field\"] has a base of [\"path\", \"to\"] but not [\"path\"]\r\n */\r\nexport function pathHasBase(path: string[], base: string[]): boolean {\r\n if (path.length - 1 !== base.length)\r\n return false;\r\n\r\n return base.every((start, i) => path[i] === start);\r\n}\r\n"],"mappings":"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","names":["typeorm_exports","__export","TypeOrmQueryAdapter","__toCommonJS","import_typeorm","ensureArray","fieldName","data","minLength","__name","ensureFalsy","isValid","value","pathHasBase","path","base","start","i","__name","TypeOrmQueryAdapter","options","__name","qb","query","request","fullQuery","data","total","offset","limit","count","page","pageCount","paramsDefined","isILikeEnabled","select","fields","f","s","relations","relation","path","alias","pathHasBase","ordering","order","where","or","params","addWhere","wqb","item","param","field","name","iteration","operator","value","ensureArray","arr","ensureFalsy","not","ilikeEnabled","isValid","type"]}
|
@@ -1,2 +1,2 @@
|
|
1
|
-
var
|
1
|
+
var y=Object.defineProperty;var c=(a,t)=>y(a,"name",{value:t,configurable:!0});import{Brackets as N}from"typeorm";function d(a,t,r=0){if(!Array.isArray(t)||t.length<r)throw new Error(`${a} must be an array with at least ${r} items`);return t}c(d,"ensureArray");function E(a,t){if(t)throw new Error(`${a} must be null`)}c(E,"ensureFalsy");function f(a){return a!=null}c(f,"isValid");function h(a,t){return a.length-1!==t.length?!1:t.every((r,e)=>a[e]===r)}c(h,"pathHasBase");var L=class{constructor(t={}){this.options=t}static{c(this,"TypeOrmQueryAdapter")}build(t,r){return t=this.createBaseQuery(t,r),t=this.paginateQuery(t,r),t}async getOne(t,r){return await this.createBaseQuery(t,r).getOne()??null}async getMany(t,r){let e=this.createBaseQuery(t,r),s=await this.paginateQuery(e.clone(),r).getMany(),l=await e.getCount(),n=r.offset??0,o=r.limit??l,u=s.length,$=Math.floor(n/o)+1,p=Math.ceil(l/o);return{data:s,count:u,page:$,pageCount:p,total:l}}createBaseQuery(t,r){let e=[],i=this.isILikeEnabled(t);return this.adaptSelect(t,r.select),this.adaptRelations(t,r.relations,r.select),this.adaptWhere(t.alias,t,r.where,!1,e,i),this.adaptOrder(t,r.order),t}paginateQuery(t,r){return t.limit(r.limit).offset(r.offset)}adaptSelect(t,r){if(r.length===0)return;let e=r.filter(i=>i.field.length===1);t.select(e.map(i=>[t.alias,...i.field].join(".")))}adaptRelations(t,r,e){for(let i of r){let s=[t.alias,...i.field].join("."),l=i.alias||s.replace(".","_"),n=e.filter(o=>h(o.field,i.field));n.length===0?t.leftJoinAndSelect(s,l):(t.leftJoin(s,l),t.addSelect(n.map(o=>[l,o.field[o.field.length-1]].join("."))))}}adaptOrder(t,r){for(let e of r){let i=[t.alias,...e.field].join(".");t.addOrderBy(i,e.order)}}adaptWhere(t,r,e,i,s,l){let n=(i?r.orWhere:r.andWhere).bind(r);if(e.or&&e.or.length>0)n(new N(o=>e.or.forEach(u=>this.adaptWhere(t,o,u,!0,s,l))));else if(e.and&&e.and.length>0)n(new N(o=>e.and.forEach(u=>this.adaptWhere(t,o,u,!1,s,l))));else if(e.field){let o=this.createParam(s,e.field),u=this.mapWhereOperators(t,e,o,l);n(u.where,u.params)}}createParam(t,r){let e=r.length>0?r[r.length-1]:"",i,s=0;do i="req_"+e+"_"+s,s++;while(t.includes(i));return t.push(i),i}mapWhereOperators(t,r,e,i){let s=[t,...r.field].join("."),l=r.operator,n=r.value;switch(l){case"eq":return{where:`${s} = :${e}`,params:{[e]:n}};case"neq":return{where:`${s} != :${e}`,params:{[e]:n}};case"gt":return{where:`${s} > :${e}`,params:{[e]:n}};case"gte":return{where:`${s} >= :${e}`,params:{[e]:n}};case"lt":return{where:`${s} < :${e}`,params:{[e]:n}};case"lte":return{where:`${s} <= :${e}`,params:{[e]:n}};case"starts":return{where:`${s} LIKE :${e}`,params:{[e]:`${n}%`}};case"ends":return{where:`${s} LIKE :${e}`,params:{[e]:`%${n}`}};case"contains":return{where:`${s} LIKE :${e}`,params:{[e]:`%${n}%`}};case"not_contains":return{where:`${s} NOT LIKE :${e}`,params:{[e]:`%${n}%`}};case"in":return n=d("IN operator",n,1),{where:`${s} IN (:...${e})`,params:{[e]:n}};case"not_in":return n=d("NOT IN operator",n,1),{where:`${s} NOT IN (:...${e})`,params:{[e]:n}};case"between":let o=d("BETWEEN operator",n,2);return{where:`${s} BETWEEN :${e}_start AND :${e}_end`,params:{[`${e}_start`]:o[0],[`${e}_end`]:o[1]}};case"is_null":return E("IS NULL operator",n),{where:`${s} IS NULL`,params:{}};case"not_null":return E("NOT NULL operator",n),{where:`${s} IS NOT NULL`,params:{}};case"eq_lower":return{where:`LOWER(${s}) = :${e}`,params:{[e]:n}};case"neq_lower":return{where:`LOWER(${s}) != :${e}`,params:{[e]:n}};case"starts_lower":return{where:`${this.createLowerLike(i,s)} :${e}`,params:{[e]:`${n}%`}};case"ends_lower":return{where:`${this.createLowerLike(i,s)} :${e}`,params:{[e]:`%${n}`}};case"contains_lower":return{where:`${this.createLowerLike(i,s)} :${e}`,params:{[e]:`%${n}%`}};case"not_contains_lower":return{where:`${this.createLowerLike(i,s,!0)} :${e}`,params:{[e]:`%${n}%`}};case"in_lower":return d("IN operator",n,1),{where:`LOWER(${s}) IN (...:${e})`,params:{[e]:n}};case"not_in_lower":return d("NOT IN operator",n,1),{where:`LOWER(${s}) NOT IN (...:${e})`,params:{[e]:n}};default:throw new Error(`Unknown operator "${l}"`)}}createLowerLike(t,r,e=!1){return t?e?`${r} NOT ILIKE`:`${r} ILIKE`:e?`LOWER(${r}) NOT LIKE`:`LOWER(${r}) LIKE`}isILikeEnabled(t){let r=this.options.ilike;if(f(r))return r;let e=t.connection.options.type;return e==="postgres"||e==="aurora-postgres"}};export{L as TypeOrmQueryAdapter};
|
2
2
|
//# sourceMappingURL=index.mjs.map
|
@@ -1 +1 @@
|
|
1
|
-
{"version":3,"sources":["../../../src/adapters/typeorm/typeorm.query-adapter.ts","../../../src/utils/functions.ts"],"sourcesContent":["import { Brackets, ObjectLiteral, SelectQueryBuilder, WhereExpressionBuilder } from 'typeorm';\r\nimport { QueryAdapter } from '../../models/query-adapter';\r\nimport {\r\n CrudRequest,\r\n CrudRequestOrder,\r\n CrudRequestRelation,\r\n ParsedRequestSelect\r\n} from '../../models/crud-request';\r\nimport {\r\n CrudRequestWhere,\r\n CrudRequestWhereField,\r\n CrudRequestWhereOperator\r\n} from '../../models/crud-request-where';\r\nimport { GetManyResult } from '../../models/get-many-result';\r\nimport { ensureArray, ensureFalsy } from '../../utils/functions';\r\n\r\n/**\r\n * Adapts queries to TypeORM query builder object\r\n */\r\nexport class TypeormQueryAdapter implements QueryAdapter<SelectQueryBuilder<any>, ObjectLiteral> {\r\n\r\n /**\r\n * @inheritDoc\r\n */\r\n public build<E extends ObjectLiteral>(qb: SelectQueryBuilder<E>, query: CrudRequest): SelectQueryBuilder<E> {\r\n qb = this.createBaseQuery(qb, query);\r\n qb = this.paginateQuery(qb, query);\r\n\r\n return qb;\r\n }\r\n\r\n /**\r\n * @inheritDoc\r\n */\r\n public async getOne<E extends ObjectLiteral>(qb: SelectQueryBuilder<E | any>, request: CrudRequest): Promise<E | null> {\r\n const query = this.createBaseQuery(qb, request);\r\n const entity = await query.getOne();\r\n\r\n return entity ?? null;\r\n }\r\n\r\n /**\r\n * @inheritDoc\r\n */\r\n public async getMany<E extends ObjectLiteral>(qb: SelectQueryBuilder<E | any>, request: CrudRequest): Promise<GetManyResult<E>> {\r\n const fullQuery = this.createBaseQuery(qb, request);\r\n const paginatedQuery = this.paginateQuery(fullQuery.clone(), request);\r\n\r\n const data = await paginatedQuery.getMany();\r\n const total = await fullQuery.getCount();\r\n\r\n const offset = request.offset ?? 0;\r\n const limit = request.limit ?? total;\r\n\r\n const count = data.length;\r\n const page = Math.floor(offset / limit) + 1;\r\n const pageCount = Math.ceil(total / limit);\r\n\r\n return {\r\n data,\r\n count,\r\n page,\r\n pageCount,\r\n total,\r\n };\r\n }\r\n\r\n /**\r\n * Creates a query filtered from the parsed request\r\n *\r\n * @param qb The base query builder\r\n * @param query The parsed query\r\n */\r\n protected createBaseQuery<E extends ObjectLiteral>(qb: SelectQueryBuilder<E>, query: CrudRequest): SelectQueryBuilder<E> {\r\n const paramsDefined: string[] = [];\r\n\r\n this.adaptSelect(qb, query.select);\r\n this.adaptRelations(qb, query.relations);\r\n this.adaptWhere(qb, query.where, false, paramsDefined);\r\n this.adaptOrder(qb, query.order);\r\n\r\n return qb;\r\n }\r\n\r\n /**\r\n * Paginates a query based on the parsed request\r\n *\r\n * @param qb The query builder\r\n * @param query The parsed query\r\n */\r\n protected paginateQuery<E extends ObjectLiteral>(qb: SelectQueryBuilder<E>, query: CrudRequest): SelectQueryBuilder<E> {\r\n return qb.limit(query.limit).offset(query.offset);\r\n }\r\n\r\n /**\r\n * Adapts a select\r\n *\r\n * @param qb The query builder\r\n * @param select The parsed select fields\r\n */\r\n protected adaptSelect<E extends ObjectLiteral>(qb: SelectQueryBuilder<E>, select: ParsedRequestSelect): void {\r\n qb.addSelect(select.map(s => s.field.join('.')));\r\n }\r\n\r\n /**\r\n * Adapts the join relation list\r\n *\r\n * @param qb The query builder\r\n * @param relations The parsed relation list\r\n */\r\n protected adaptRelations<E extends ObjectLiteral>(qb: SelectQueryBuilder<E>, relations: CrudRequestRelation[]): void {\r\n for (const relation of relations) {\r\n const path = relation.field.join('.');\r\n const alias = relation.alias || path.replace('.', '_');\r\n\r\n qb.leftJoin(path, alias);\r\n }\r\n }\r\n\r\n /**\r\n * Adapts the order by list\r\n *\r\n * @param qb The query builder\r\n * @param ordering The parsed ordering\r\n */\r\n protected adaptOrder<E extends ObjectLiteral>(qb: SelectQueryBuilder<E>, ordering: CrudRequestOrder[]): void {\r\n for (const order of ordering) {\r\n const path = order.field.join('.');\r\n\r\n qb.addOrderBy(path, order.order);\r\n }\r\n }\r\n\r\n /**\r\n * Adapts a where condition\r\n *\r\n * @param qb The query builder\r\n * @param where The quere condition\r\n * @param or Whether this where condition is AND/OR\r\n * @param params The registered parameter name list\r\n */\r\n protected adaptWhere(qb: WhereExpressionBuilder, where: CrudRequestWhere, or: boolean, params: string[]): void {\r\n const addWhere = (or ? qb.orWhere : qb.andWhere).bind(qb);\r\n\r\n if (where.or && where.or.length > 0) {\r\n addWhere(new Brackets(\r\n wqb => where.or!.forEach(item => this.adaptWhere(wqb, item, true, params))\r\n ));\r\n } else if (where.and && where.and.length > 0) {\r\n addWhere(new Brackets(\r\n wqb => where.and!.forEach(item => this.adaptWhere(wqb, item, false, params))\r\n ));\r\n } else if (where.field) {\r\n const param = this.createParam(params, where.field);\r\n const query = this.mapWhereOperators(where as CrudRequestWhereField, param);\r\n\r\n addWhere(query.where, query.params);\r\n }\r\n }\r\n\r\n /**\r\n * Creates a query parameter name based on a field\r\n *\r\n * @param paramsDefined The array the parameter will be registered onto\r\n * @param field The field path\r\n */\r\n protected createParam(paramsDefined: string[], field: string[]): string {\r\n const name = field.length > 0 ? field[field.length - 1] : '';\r\n let param: string;\r\n let iteration: number = 0;\r\n\r\n do {\r\n param = 'req_' + name + '_' + iteration;\r\n iteration++;\r\n } while (paramsDefined.includes(param));\r\n\r\n paramsDefined.push(param);\r\n return param;\r\n }\r\n\r\n /**\r\n * Maps where operators to a pseudo-SQL statement and a parameter map\r\n *\r\n * @param where The where condition\r\n * @param param The parameter name\r\n */\r\n protected mapWhereOperators(where: CrudRequestWhereField, param: string): { where: string, params: ObjectLiteral } {\r\n const field = where.field.join('.');\r\n const operator = where.operator;\r\n let value: unknown = where.value;\r\n\r\n switch (operator) {\r\n case CrudRequestWhereOperator.EQ:\r\n return { where: `${field} = :${param}`, params: { [param]: value } };\r\n\r\n case CrudRequestWhereOperator.NEQ:\r\n return { where: `${field} != :${param}`, params: { [param]: value } };\r\n\r\n case CrudRequestWhereOperator.GT:\r\n return { where: `${field} > :${param}`, params: { [param]: value } };\r\n\r\n case CrudRequestWhereOperator.GTE:\r\n return { where: `${field} >= :${param}`, params: { [param]: value } };\r\n\r\n case CrudRequestWhereOperator.LT:\r\n return { where: `${field} < :${param}`, params: { [param]: value } };\r\n\r\n case CrudRequestWhereOperator.LTE:\r\n return { where: `${field} <= :${param}`, params: { [param]: value } };\r\n\r\n case CrudRequestWhereOperator.STARTS:\r\n return { where: `${field} LIKE :${param}`, params: { [param]: `${value}%` } };\r\n\r\n case CrudRequestWhereOperator.ENDS:\r\n return { where: `${field} LIKE :${param}`, params: { [param]: `%${value}` } };\r\n\r\n case CrudRequestWhereOperator.CONTAINS:\r\n return { where: `${field} LIKE :${param}`, params: { [param]: `%${value}%` } };\r\n\r\n case CrudRequestWhereOperator.NOT_CONTAINS:\r\n return { where: `${field} NOT LIKE :${param}`, params: { [param]: `%${value}%` } };\r\n\r\n case CrudRequestWhereOperator.IN:\r\n value = ensureArray('IN operator', value, 1);\r\n\r\n return { where: `${field} IN (:...${param})`, params: { [param]: value } };\r\n\r\n case CrudRequestWhereOperator.NOT_IN:\r\n value = ensureArray('NOT IN operator', value, 1);\r\n\r\n return { where: `${field} NOT IN (:...${param})`, params: { [param]: value } };\r\n\r\n case CrudRequestWhereOperator.BETWEEN:\r\n const arr = ensureArray('BETWEEN operator', value, 2);\r\n\r\n return {\r\n where: `${field} BETWEEN :${param}_start AND :${param}_end`,\r\n params: { [`${param}_start`]: arr[0], [`${param}_end`]: arr[1] },\r\n };\r\n\r\n case CrudRequestWhereOperator.IS_NULL:\r\n ensureFalsy('IS NULL operator', value);\r\n\r\n return { where: `${field} IS NULL`, params: {} };\r\n\r\n case CrudRequestWhereOperator.NOT_NULL:\r\n ensureFalsy('NOT NULL operator', value);\r\n\r\n return { where: `${field} IS NOT NULL`, params: {} };\r\n\r\n case CrudRequestWhereOperator.EQ_LOWER:\r\n return { where: `LOWER(${field}) = :${param}`, params: { [param]: value } };\r\n\r\n case CrudRequestWhereOperator.NEQ_LOWER:\r\n return { where: `LOWER(${field}) != :${param}`, params: { [param]: value } };\r\n\r\n case CrudRequestWhereOperator.STARTS_LOWER:\r\n return { where: `LOWER(${field}) LIKE :${param}`, params: { [param]: `${value}%` } };\r\n\r\n case CrudRequestWhereOperator.ENDS_LOWER:\r\n return { where: `LOWER(${field}) LIKE :${param}`, params: { [param]: `%${value}` } };\r\n\r\n case CrudRequestWhereOperator.CONTAINS_LOWER:\r\n return { where: `${field} LIKE :${param}`, params: { [param]: `%${value}%` } };\r\n\r\n case CrudRequestWhereOperator.NOT_CONTAINS_LOWER:\r\n return { where: `${field} NOT LIKE :${param}`, params: { [param]: `%${value}%` } };\r\n\r\n case CrudRequestWhereOperator.IN_LOWER:\r\n ensureArray('IN operator', value, 1);\r\n\r\n return { where: `${field} IN (...:${param})`, params: { [param]: value } };\r\n\r\n case CrudRequestWhereOperator.NOT_IN_LOWER:\r\n ensureArray('NOT IN operator', value, 1);\r\n\r\n return { where: `${field} NOT IN (...:${param})`, params: { [param]: value } };\r\n\r\n default:\r\n throw new Error(`Unknown operator \"${operator}\"`);\r\n }\r\n }\r\n\r\n}\r\n","import { CrudRequestFields } from '../models/crud-request';\r\n\r\n/*export function setFieldByPath<T>(obj: ParsedRequestFields<T>, field: string, value: T): void {\r\n const parts = field.split('.');\r\n\r\n while (parts.length > 1) {\r\n const name = parts.shift();\r\n\r\n if (!Array.isArray(obj[name]))\r\n obj[name] = {};\r\n\r\n obj = obj[name] as ParsedRequestFields<T>;\r\n }\r\n\r\n obj[parts.shift()] = value;\r\n}*/\r\n\r\nexport function ensureArray<T>(fieldName: string, data: T[] | any, minLength: number = 0): T[] {\r\n if (!Array.isArray(data) || data.length < minLength)\r\n throw new Error(`${fieldName} must be an array with at least ${minLength} items`);\r\n\r\n return data;\r\n}\r\n\r\nexport function ensureFalsy(fieldName: string, data: any) {\r\n if (data)\r\n throw new Error(`${fieldName} must be null`);\r\n}\r\n\r\nexport function isValid(value: any): value is object {\r\n return value !== null && value !== undefined;\r\n}\r\n"],"mappings":"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","names":["Brackets","ensureArray","fieldName","data","minLength","__name","ensureFalsy","TypeormQueryAdapter","__name","qb","query","request","fullQuery","data","total","offset","limit","count","page","pageCount","paramsDefined","select","s","relations","relation","path","alias","ordering","order","where","or","params","addWhere","Brackets","wqb","item","param","field","name","iteration","operator","value","ensureArray","arr","ensureFalsy"]}
|
1
|
+
{"version":3,"sources":["../../../src/adapters/typeorm/typeorm.query-adapter.ts","../../../src/utils/functions.ts","../../../src/utils/field-path.ts"],"sourcesContent":["import { Brackets, ObjectLiteral, SelectQueryBuilder, WhereExpressionBuilder } from 'typeorm';\r\nimport { QueryAdapter } from '../../models/query-adapter';\r\nimport { CrudRequest, CrudRequestOrder, CrudRequestRelation, ParsedRequestSelect } from '../../models/crud-request';\r\nimport { CrudRequestWhere, CrudRequestWhereField, CrudRequestWhereOperator } from '../../models/crud-request-where';\r\nimport { GetManyResult } from '../../models/get-many-result';\r\nimport { ensureArray, ensureFalsy, isValid } from '../../utils/functions';\r\nimport { pathHasBase } from '../../utils/field-path';\r\n\r\nexport interface TypeOrmQueryAdapterOptions {\r\n /**\r\n * Whether it will use ILIKE for case-insensitive operations.\r\n *\r\n * If undefined, it will be enabled by default for postgres and aurora-postgres databases\r\n */\r\n ilike?: boolean;\r\n}\r\n\r\n/**\r\n * Adapts queries to TypeORM query builder object\r\n */\r\nexport class TypeOrmQueryAdapter implements QueryAdapter<SelectQueryBuilder<any>, ObjectLiteral> {\r\n\r\n constructor(\r\n private readonly options: TypeOrmQueryAdapterOptions = {},\r\n ) {}\r\n\r\n /**\r\n * @inheritDoc\r\n */\r\n public build<E extends ObjectLiteral>(qb: SelectQueryBuilder<E>, query: CrudRequest): SelectQueryBuilder<E> {\r\n qb = this.createBaseQuery(qb, query);\r\n qb = this.paginateQuery(qb, query);\r\n\r\n return qb;\r\n }\r\n\r\n /**\r\n * @inheritDoc\r\n */\r\n public async getOne<E extends ObjectLiteral>(qb: SelectQueryBuilder<E | any>, request: CrudRequest): Promise<E | null> {\r\n const query = this.createBaseQuery(qb, request);\r\n const entity = await query.getOne();\r\n\r\n return entity ?? null;\r\n }\r\n\r\n /**\r\n * @inheritDoc\r\n */\r\n public async getMany<E extends ObjectLiteral>(qb: SelectQueryBuilder<E | any>, request: CrudRequest): Promise<GetManyResult<E>> {\r\n const fullQuery = this.createBaseQuery(qb, request);\r\n const paginatedQuery = this.paginateQuery(fullQuery.clone(), request);\r\n\r\n const data = await paginatedQuery.getMany();\r\n const total = await fullQuery.getCount();\r\n\r\n const offset = request.offset ?? 0;\r\n const limit = request.limit ?? total;\r\n\r\n const count = data.length;\r\n const page = Math.floor(offset / limit) + 1;\r\n const pageCount = Math.ceil(total / limit);\r\n\r\n return {\r\n data,\r\n count,\r\n page,\r\n pageCount,\r\n total,\r\n };\r\n }\r\n\r\n /**\r\n * Creates a query filtered from the parsed request\r\n *\r\n * @param qb The base query builder\r\n * @param query The parsed query\r\n */\r\n protected createBaseQuery<E extends ObjectLiteral>(qb: SelectQueryBuilder<E>, query: CrudRequest): SelectQueryBuilder<E> {\r\n const paramsDefined: string[] = [];\r\n const isILikeEnabled = this.isILikeEnabled(qb);\r\n\r\n this.adaptSelect(qb, query.select);\r\n this.adaptRelations(qb, query.relations, query.select);\r\n this.adaptWhere(qb.alias, qb, query.where, false, paramsDefined, isILikeEnabled);\r\n this.adaptOrder(qb, query.order);\r\n\r\n return qb;\r\n }\r\n\r\n /**\r\n * Paginates a query based on the parsed request\r\n *\r\n * @param qb The query builder\r\n * @param query The parsed query\r\n */\r\n protected paginateQuery<E extends ObjectLiteral>(qb: SelectQueryBuilder<E>, query: CrudRequest): SelectQueryBuilder<E> {\r\n return qb.limit(query.limit).offset(query.offset);\r\n }\r\n\r\n /**\r\n * Adapts a select\r\n *\r\n * @param qb The query builder\r\n * @param select The parsed select fields\r\n */\r\n protected adaptSelect<E extends ObjectLiteral>(qb: SelectQueryBuilder<E>, select: ParsedRequestSelect): void {\r\n if (select.length === 0)\r\n return;\r\n\r\n // Only fields that are one level deep\r\n const fields = select.filter(f => f.field.length === 1);\r\n\r\n qb.select(fields.map(s => [qb.alias, ...s.field].join('.')));\r\n }\r\n\r\n /**\r\n * Adapts the join relation list\r\n *\r\n * @param qb The query builder\r\n * @param relations The parsed relation list\r\n * @param select The parsed select fields\r\n */\r\n protected adaptRelations<E extends ObjectLiteral>(qb: SelectQueryBuilder<E>, relations: CrudRequestRelation[], select: ParsedRequestSelect): void {\r\n for (const relation of relations) {\r\n const path = [qb.alias, ...relation.field].join('.');\r\n const alias = relation.alias || path.replace('.', '_');\r\n\r\n const fields = select.filter(f => pathHasBase(f.field, relation.field));\r\n\r\n if (fields.length === 0) {\r\n qb.leftJoinAndSelect(path, alias);\r\n } else {\r\n qb.leftJoin(path, alias);\r\n qb.addSelect(fields.map(f => [alias, f.field[f.field.length - 1]].join('.')));\r\n }\r\n }\r\n }\r\n\r\n /**\r\n * Adapts the order by list\r\n *\r\n * @param qb The query builder\r\n * @param ordering The parsed ordering\r\n */\r\n protected adaptOrder<E extends ObjectLiteral>(qb: SelectQueryBuilder<E>, ordering: CrudRequestOrder[]): void {\r\n for (const order of ordering) {\r\n const path = [qb.alias, ...order.field].join('.');\r\n\r\n qb.addOrderBy(path, order.order);\r\n }\r\n }\r\n\r\n /**\r\n * Adapts a where condition\r\n *\r\n * @param alias The query builder alias\r\n * @param qb The query builder\r\n * @param where The quere condition\r\n * @param or Whether this where condition is AND/OR\r\n * @param params The registered parameter name list\r\n * @param isILikeEnabled Whether the ILIKE operator can be used\r\n */\r\n protected adaptWhere(\r\n alias: string,\r\n qb: WhereExpressionBuilder,\r\n where: CrudRequestWhere,\r\n or: boolean,\r\n params: string[],\r\n isILikeEnabled: boolean,\r\n ): void {\r\n const addWhere = (or ? qb.orWhere : qb.andWhere).bind(qb);\r\n\r\n if (where.or && where.or.length > 0) {\r\n addWhere(new Brackets(\r\n wqb => where.or!.forEach(item => this.adaptWhere(alias, wqb, item, true, params, isILikeEnabled))\r\n ));\r\n } else if (where.and && where.and.length > 0) {\r\n addWhere(new Brackets(\r\n wqb => where.and!.forEach(item => this.adaptWhere(alias, wqb, item, false, params, isILikeEnabled))\r\n ));\r\n } else if (where.field) {\r\n const param = this.createParam(params, where.field);\r\n const query = this.mapWhereOperators(alias, where as CrudRequestWhereField, param, isILikeEnabled);\r\n\r\n addWhere(query.where, query.params);\r\n }\r\n }\r\n\r\n /**\r\n * Creates a query parameter name based on a field\r\n *\r\n * @param paramsDefined The array the parameter will be registered onto\r\n * @param field The field path\r\n */\r\n protected createParam(paramsDefined: string[], field: string[]): string {\r\n const name = field.length > 0 ? field[field.length - 1] : '';\r\n let param: string;\r\n let iteration: number = 0;\r\n\r\n do {\r\n param = 'req_' + name + '_' + iteration;\r\n iteration++;\r\n } while (paramsDefined.includes(param));\r\n\r\n paramsDefined.push(param);\r\n return param;\r\n }\r\n\r\n /**\r\n * Maps where operators to a pseudo-SQL statement and a parameter map\r\n *\r\n * @param alias The query builder alias\r\n * @param where The where condition\r\n * @param param The parameter name\r\n * @param isILikeEnabled Whether the ILIKE operator can be used\r\n */\r\n protected mapWhereOperators(\r\n alias: string,\r\n where: CrudRequestWhereField,\r\n param: string,\r\n isILikeEnabled: boolean,\r\n ): { where: string, params: ObjectLiteral } {\r\n const field = [alias, ...where.field].join('.');\r\n const operator = where.operator;\r\n let value: unknown = where.value;\r\n\r\n switch (operator) {\r\n case CrudRequestWhereOperator.EQ:\r\n return { where: `${field} = :${param}`, params: { [param]: value } };\r\n\r\n case CrudRequestWhereOperator.NEQ:\r\n return { where: `${field} != :${param}`, params: { [param]: value } };\r\n\r\n case CrudRequestWhereOperator.GT:\r\n return { where: `${field} > :${param}`, params: { [param]: value } };\r\n\r\n case CrudRequestWhereOperator.GTE:\r\n return { where: `${field} >= :${param}`, params: { [param]: value } };\r\n\r\n case CrudRequestWhereOperator.LT:\r\n return { where: `${field} < :${param}`, params: { [param]: value } };\r\n\r\n case CrudRequestWhereOperator.LTE:\r\n return { where: `${field} <= :${param}`, params: { [param]: value } };\r\n\r\n case CrudRequestWhereOperator.STARTS:\r\n return { where: `${field} LIKE :${param}`, params: { [param]: `${value}%` } };\r\n\r\n case CrudRequestWhereOperator.ENDS:\r\n return { where: `${field} LIKE :${param}`, params: { [param]: `%${value}` } };\r\n\r\n case CrudRequestWhereOperator.CONTAINS:\r\n return { where: `${field} LIKE :${param}`, params: { [param]: `%${value}%` } };\r\n\r\n case CrudRequestWhereOperator.NOT_CONTAINS:\r\n return { where: `${field} NOT LIKE :${param}`, params: { [param]: `%${value}%` } };\r\n\r\n case CrudRequestWhereOperator.IN:\r\n value = ensureArray('IN operator', value, 1);\r\n\r\n return { where: `${field} IN (:...${param})`, params: { [param]: value } };\r\n\r\n case CrudRequestWhereOperator.NOT_IN:\r\n value = ensureArray('NOT IN operator', value, 1);\r\n\r\n return { where: `${field} NOT IN (:...${param})`, params: { [param]: value } };\r\n\r\n case CrudRequestWhereOperator.BETWEEN:\r\n const arr = ensureArray('BETWEEN operator', value, 2);\r\n\r\n return {\r\n where: `${field} BETWEEN :${param}_start AND :${param}_end`,\r\n params: { [`${param}_start`]: arr[0], [`${param}_end`]: arr[1] },\r\n };\r\n\r\n case CrudRequestWhereOperator.IS_NULL:\r\n ensureFalsy('IS NULL operator', value);\r\n\r\n return { where: `${field} IS NULL`, params: {} };\r\n\r\n case CrudRequestWhereOperator.NOT_NULL:\r\n ensureFalsy('NOT NULL operator', value);\r\n\r\n return { where: `${field} IS NOT NULL`, params: {} };\r\n\r\n case CrudRequestWhereOperator.EQ_LOWER:\r\n return { where: `LOWER(${field}) = :${param}`, params: { [param]: value } };\r\n\r\n case CrudRequestWhereOperator.NEQ_LOWER:\r\n return { where: `LOWER(${field}) != :${param}`, params: { [param]: value } };\r\n\r\n case CrudRequestWhereOperator.STARTS_LOWER:\r\n return { where: `${this.createLowerLike(isILikeEnabled, field)} :${param}`, params: { [param]: `${value}%` } };\r\n\r\n case CrudRequestWhereOperator.ENDS_LOWER:\r\n return { where: `${this.createLowerLike(isILikeEnabled, field)} :${param}`, params: { [param]: `%${value}` } };\r\n\r\n case CrudRequestWhereOperator.CONTAINS_LOWER:\r\n return { where: `${this.createLowerLike(isILikeEnabled, field)} :${param}`, params: { [param]: `%${value}%` } };\r\n\r\n case CrudRequestWhereOperator.NOT_CONTAINS_LOWER:\r\n return { where: `${this.createLowerLike(isILikeEnabled, field, true)} :${param}`, params: { [param]: `%${value}%` } };\r\n\r\n case CrudRequestWhereOperator.IN_LOWER:\r\n ensureArray('IN operator', value, 1);\r\n\r\n return { where: `LOWER(${field}) IN (...:${param})`, params: { [param]: value } };\r\n\r\n case CrudRequestWhereOperator.NOT_IN_LOWER:\r\n ensureArray('NOT IN operator', value, 1);\r\n\r\n return { where: `LOWER(${field}) NOT IN (...:${param})`, params: { [param]: value } };\r\n\r\n default:\r\n throw new Error(`Unknown operator \"${operator}\"`);\r\n }\r\n }\r\n\r\n protected createLowerLike(isILikeEnabled: boolean, field: string, not: boolean = false): string {\r\n if (isILikeEnabled)\r\n return not ? `${field} NOT ILIKE` : `${field} ILIKE`;\r\n\r\n return not ? `LOWER(${field}) NOT LIKE` : `LOWER(${field}) LIKE`;\r\n }\r\n\r\n protected isILikeEnabled(qb: SelectQueryBuilder<any>): boolean {\r\n const ilikeEnabled = this.options.ilike;\r\n\r\n if (isValid(ilikeEnabled))\r\n return ilikeEnabled;\r\n\r\n const type = qb.connection.options.type;\r\n return type === 'postgres' || type === 'aurora-postgres';\r\n }\r\n\r\n}\r\n","import { CrudRequestFields } from '../models/crud-request';\r\n\r\n/*export function setFieldByPath<T>(obj: ParsedRequestFields<T>, field: string, value: T): void {\r\n const parts = field.split('.');\r\n\r\n while (parts.length > 1) {\r\n const name = parts.shift();\r\n\r\n if (!Array.isArray(obj[name]))\r\n obj[name] = {};\r\n\r\n obj = obj[name] as ParsedRequestFields<T>;\r\n }\r\n\r\n obj[parts.shift()] = value;\r\n}*/\r\n\r\nexport function ensurePrimitive(fieldName: string, data: any) {\r\n if (data === null || data === undefined)\r\n return;\r\n\r\n if (typeof data === 'number' || typeof data === 'string' || typeof data === 'boolean')\r\n return;\r\n\r\n if (data instanceof Date)\r\n return;\r\n\r\n throw new Error(`${fieldName} must be a string, number, boolean or null`);\r\n}\r\n\r\nexport function ensureArray<T>(fieldName: string, data: T[] | any, minLength: number = 0): T[] {\r\n if (!Array.isArray(data) || data.length < minLength)\r\n throw new Error(`${fieldName} must be an array with at least ${minLength} items`);\r\n\r\n return data;\r\n}\r\n\r\nexport function ensureFalsy(fieldName: string, data: any) {\r\n if (data)\r\n throw new Error(`${fieldName} must be null`);\r\n}\r\n\r\nexport function isValid<T>(value: T | undefined | null): value is T {\r\n return value !== null && value !== undefined;\r\n}\r\n","/**\r\n * Checks whether two field paths are equal\r\n *\r\n * E.g. [\"path\", \"to\", \"field\"] is equal to [\"path\", \"to\", \"field\"] but not [\"something\", \"else\"]\r\n */\r\nexport function pathEquals(path1: string[], path2: string[]): boolean {\r\n if (path1.length !== path2.length)\r\n return false;\r\n\r\n return path1.every((p1, i) => path2[i] === p1);\r\n}\r\n\r\n/**\r\n * Checks whether a path starts with another path.\r\n *\r\n * E.g. [\"path\", \"to\", \"field\"] starts with [\"path\"] or [\"path\", \"to\"] but not [\"something\", \"else\"]\r\n */\r\nexport function pathStartsWith(path: string[], start: string[]): boolean {\r\n if (path.length < start.length)\r\n return false;\r\n\r\n return start.every((start, i) => path[i] === start);\r\n}\r\n\r\n/**\r\n * Checks whether the base of a path matches.\r\n *\r\n * E.g. [\"path\", \"to\", \"field\"] has a base of [\"path\", \"to\"] but not [\"path\"]\r\n */\r\nexport function pathHasBase(path: string[], base: string[]): boolean {\r\n if (path.length - 1 !== base.length)\r\n return false;\r\n\r\n return base.every((start, i) => path[i] === start);\r\n}\r\n"],"mappings":"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","names":["Brackets","ensureArray","fieldName","data","minLength","__name","ensureFalsy","isValid","value","pathHasBase","path","base","start","i","__name","TypeOrmQueryAdapter","options","__name","qb","query","request","fullQuery","data","total","offset","limit","count","page","pageCount","paramsDefined","isILikeEnabled","select","fields","f","s","relations","relation","path","alias","pathHasBase","ordering","order","where","or","params","addWhere","Brackets","wqb","item","param","field","name","iteration","operator","value","ensureArray","arr","ensureFalsy","not","ilikeEnabled","isValid","type"]}
|
@@ -0,0 +1,32 @@
|
|
1
|
+
import { e as CrudRequestWhereAND, f as CrudRequestWhereOR, i as CrudRequestWhereOperator, h as CrudRequestWhereValueType, d as CrudRequestWhere } from './crud-request-CvDKp6Iy.js';
|
2
|
+
|
3
|
+
/**
|
4
|
+
* A helper class that makes it easier to create a CrudRequestWhere
|
5
|
+
*/
|
6
|
+
declare class CrudRequestWhereBuilder {
|
7
|
+
private readonly where;
|
8
|
+
private readonly parent?;
|
9
|
+
constructor(where?: CrudRequestWhereAND | CrudRequestWhereOR, parent?: CrudRequestWhereBuilder | undefined);
|
10
|
+
/**
|
11
|
+
* Adds an AND bracket
|
12
|
+
*/
|
13
|
+
addAnd(): CrudRequestWhereBuilder;
|
14
|
+
/**
|
15
|
+
* Adds an OR bracket
|
16
|
+
*/
|
17
|
+
addOr(): CrudRequestWhereBuilder;
|
18
|
+
/**
|
19
|
+
* Adds a field comparison
|
20
|
+
*
|
21
|
+
* @param field The field path
|
22
|
+
* @param operator The comparison operator
|
23
|
+
* @param value The value to compare
|
24
|
+
*/
|
25
|
+
addField(field: string[], operator: CrudRequestWhereOperator, value: CrudRequestWhereValueType | CrudRequestWhereValueType[]): CrudRequestWhereBuilder;
|
26
|
+
/**
|
27
|
+
* Constructs the final where condition
|
28
|
+
*/
|
29
|
+
build(): CrudRequestWhere;
|
30
|
+
}
|
31
|
+
|
32
|
+
export { CrudRequestWhereBuilder as C };
|
@@ -0,0 +1,32 @@
|
|
1
|
+
import { e as CrudRequestWhereAND, f as CrudRequestWhereOR, i as CrudRequestWhereOperator, h as CrudRequestWhereValueType, d as CrudRequestWhere } from './crud-request-CvDKp6Iy.mjs';
|
2
|
+
|
3
|
+
/**
|
4
|
+
* A helper class that makes it easier to create a CrudRequestWhere
|
5
|
+
*/
|
6
|
+
declare class CrudRequestWhereBuilder {
|
7
|
+
private readonly where;
|
8
|
+
private readonly parent?;
|
9
|
+
constructor(where?: CrudRequestWhereAND | CrudRequestWhereOR, parent?: CrudRequestWhereBuilder | undefined);
|
10
|
+
/**
|
11
|
+
* Adds an AND bracket
|
12
|
+
*/
|
13
|
+
addAnd(): CrudRequestWhereBuilder;
|
14
|
+
/**
|
15
|
+
* Adds an OR bracket
|
16
|
+
*/
|
17
|
+
addOr(): CrudRequestWhereBuilder;
|
18
|
+
/**
|
19
|
+
* Adds a field comparison
|
20
|
+
*
|
21
|
+
* @param field The field path
|
22
|
+
* @param operator The comparison operator
|
23
|
+
* @param value The value to compare
|
24
|
+
*/
|
25
|
+
addField(field: string[], operator: CrudRequestWhereOperator, value: CrudRequestWhereValueType | CrudRequestWhereValueType[]): CrudRequestWhereBuilder;
|
26
|
+
/**
|
27
|
+
* Constructs the final where condition
|
28
|
+
*/
|
29
|
+
build(): CrudRequestWhere;
|
30
|
+
}
|
31
|
+
|
32
|
+
export { CrudRequestWhereBuilder as C };
|
@@ -0,0 +1,18 @@
|
|
1
|
+
import * as _nestjs_common from '@nestjs/common';
|
2
|
+
import { Type } from '@nestjs/common';
|
3
|
+
import { a as RequestParser } from '../../request-parser-WaQBZsYG.mjs';
|
4
|
+
import '../../crud-request-CvDKp6Iy.mjs';
|
5
|
+
|
6
|
+
declare const CRUD_QUERY_PARSER = "crud-query-parser";
|
7
|
+
/**
|
8
|
+
* Defines which parser will be used for parsing the request
|
9
|
+
*
|
10
|
+
* @param parserContract The parser that will be used
|
11
|
+
*/
|
12
|
+
declare function Crud(parserContract: RequestParser | Type<RequestParser>): MethodDecorator & ClassDecorator;
|
13
|
+
/**
|
14
|
+
* A parameter decorator that converts the query string into a `CrudRequest` object
|
15
|
+
*/
|
16
|
+
declare const ParseCrudRequest: (...dataOrPipes: (RequestParser | Type<RequestParser> | _nestjs_common.PipeTransform<any, any> | Type<_nestjs_common.PipeTransform<any, any>>)[]) => ParameterDecorator;
|
17
|
+
|
18
|
+
export { CRUD_QUERY_PARSER, Crud, ParseCrudRequest };
|
@@ -0,0 +1,18 @@
|
|
1
|
+
import * as _nestjs_common from '@nestjs/common';
|
2
|
+
import { Type } from '@nestjs/common';
|
3
|
+
import { a as RequestParser } from '../../request-parser-B-fK5GnP.js';
|
4
|
+
import '../../crud-request-CvDKp6Iy.js';
|
5
|
+
|
6
|
+
declare const CRUD_QUERY_PARSER = "crud-query-parser";
|
7
|
+
/**
|
8
|
+
* Defines which parser will be used for parsing the request
|
9
|
+
*
|
10
|
+
* @param parserContract The parser that will be used
|
11
|
+
*/
|
12
|
+
declare function Crud(parserContract: RequestParser | Type<RequestParser>): MethodDecorator & ClassDecorator;
|
13
|
+
/**
|
14
|
+
* A parameter decorator that converts the query string into a `CrudRequest` object
|
15
|
+
*/
|
16
|
+
declare const ParseCrudRequest: (...dataOrPipes: (RequestParser | Type<RequestParser> | _nestjs_common.PipeTransform<any, any> | Type<_nestjs_common.PipeTransform<any, any>>)[]) => ParameterDecorator;
|
17
|
+
|
18
|
+
export { CRUD_QUERY_PARSER, Crud, ParseCrudRequest };
|
@@ -0,0 +1,2 @@
|
|
1
|
+
"use strict";var u=Object.defineProperty;var f=Object.getOwnPropertyDescriptor;var P=Object.getOwnPropertyNames;var m=Object.prototype.hasOwnProperty;var a=(e,r)=>u(e,"name",{value:r,configurable:!0});var q=(e,r)=>{for(var t in r)u(e,t,{get:r[t],enumerable:!0})},R=(e,r,t,o)=>{if(r&&typeof r=="object"||typeof r=="function")for(let n of P(r))!m.call(e,n)&&n!==t&&u(e,n,{get:()=>r[n],enumerable:!(o=f(r,n))||o.enumerable});return e};var x=e=>R(u({},"__esModule",{value:!0}),e);var T={};q(T,{CRUD_QUERY_PARSER:()=>i,Crud:()=>y,ParseCrudRequest:()=>C});module.exports=x(T);var s=require("@nestjs/common");var c=(()=>{try{return require("@nestjs/swagger").ApiQuery}catch{return r=>()=>{}}})();function p(e){if(typeof e=="function")return new e;if(typeof e=="object")return e}a(p,"createInstance");function d(e,r){let t=[e.getHandler(),e.getClass()];for(let o of t){let n=Reflect.getMetadata(r,o);if(n)return n}}a(d,"getMetadataFromContext");var i="crud-query-parser";function y(e){let r=p(e);if(!r)throw new Error("The request parser passed to @Crud() is invalid");let t=r.getOpenAPIParameters().map(o=>c(o));return(0,s.applyDecorators)((0,s.SetMetadata)(i,r),...t)}a(y,"Crud");var C=(0,s.createParamDecorator)((e,r)=>{let t=r.switchToHttp().getRequest(),o=e?p(e):d(r,i);return o?o.parse(t.query):(new s.Logger("ParseCrudRequest").warn("No crud request parser found. Please, define one with @Crud() or pass to @CrudRequest()"),{where:{and:[]},select:[],order:[],relations:[]})});0&&(module.exports={CRUD_QUERY_PARSER,Crud,ParseCrudRequest});
|
2
|
+
//# sourceMappingURL=index.js.map
|
@@ -0,0 +1 @@
|
|
1
|
+
{"version":3,"sources":["../../../src/helpers/nestjs/index.ts","../../../src/helpers/nestjs/decorators.ts","../../../src/helpers/nestjs/utils.ts"],"sourcesContent":["\r\nexport * from './decorators';\r\n","import { applyDecorators, createParamDecorator, ExecutionContext, Logger, SetMetadata, Type } from '@nestjs/common';\r\nimport { RequestParser } from '../../models/request-parser';\r\nimport { ApiQuery, createInstance, getMetadataFromContext } from './utils';\r\n\r\nexport const CRUD_QUERY_PARSER = 'crud-query-parser';\r\n\r\n/**\r\n * Defines which parser will be used for parsing the request\r\n *\r\n * @param parserContract The parser that will be used\r\n */\r\nexport function Crud(parserContract: RequestParser | Type<RequestParser>): MethodDecorator & ClassDecorator {\r\n const parser = createInstance(parserContract);\r\n\r\n if (!parser) {\r\n throw new Error('The request parser passed to @Crud() is invalid');\r\n }\r\n\r\n const openApi = parser.getOpenAPIParameters().map(param => ApiQuery(param));\r\n\r\n return applyDecorators(\r\n SetMetadata(CRUD_QUERY_PARSER, parser),\r\n ...openApi,\r\n );\r\n}\r\n\r\n/**\r\n * A parameter decorator that converts the query string into a `CrudRequest` object\r\n */\r\nexport const ParseCrudRequest = createParamDecorator<RequestParser | Type<RequestParser>>(\r\n (data: RequestParser | Type<RequestParser>, ctx: ExecutionContext) => {\r\n const request = ctx.switchToHttp().getRequest();\r\n const parser = data ? createInstance(data) : getMetadataFromContext<RequestParser>(ctx, CRUD_QUERY_PARSER);\r\n\r\n if (!parser) {\r\n new Logger('ParseCrudRequest').warn(`No crud request parser found. Please, define one with @Crud() or pass to @CrudRequest()`);\r\n\r\n return {\r\n where: { and: [] },\r\n select: [],\r\n order: [],\r\n relations: [],\r\n };\r\n }\r\n\r\n return parser.parse(request.query);\r\n },\r\n);\r\n\r\n","import { ExecutionContext, Type } from '@nestjs/common';\r\nimport { OpenAPIParameter } from '../../models/openapi-parameter';\r\n\r\nexport const ApiQuery = (() => {\r\n try {\r\n return require('@nestjs/swagger').ApiQuery;\r\n } catch (error) {\r\n return (options: OpenAPIParameter): MethodDecorator => {\r\n return () => {};\r\n };\r\n }\r\n})();\r\n\r\nexport function createInstance<T>(data: T | Type<T> | undefined): T | undefined {\r\n if (typeof data === 'function')\r\n return new data();\r\n\r\n if (typeof data === 'object')\r\n return data as T;\r\n\r\n return undefined;\r\n}\r\n\r\nexport function getMetadataFromContext<T>(context: ExecutionContext, key: string): T | undefined {\r\n const targets = [\r\n context.getHandler(),\r\n context.getClass(),\r\n ];\r\n\r\n for (const target of targets) {\r\n const data = Reflect.getMetadata(key, target);\r\n\r\n if (data)\r\n return data;\r\n }\r\n\r\n return undefined;\r\n}\r\n"],"mappings":"4dAAA,IAAAA,EAAA,GAAAC,EAAAD,EAAA,uBAAAE,EAAA,SAAAC,EAAA,qBAAAC,IAAA,eAAAC,EAAAL,GCAA,IAAAM,EAAmG,0BCG5F,IAAMC,GAAY,IAAM,CAC7B,GAAI,CACF,MAAO,SAAQ,iBAAiB,EAAE,QACpC,MAAgB,CACd,OAAQC,GACC,IAAM,CAAC,CAElB,CACF,GAAG,EAEI,SAASC,EAAkBC,EAA8C,CAC9E,GAAI,OAAOA,GAAS,WAClB,OAAO,IAAIA,EAEb,GAAI,OAAOA,GAAS,SAClB,OAAOA,CAGX,CARgBC,EAAAF,EAAA,kBAUT,SAASG,EAA0BC,EAA2BC,EAA4B,CAC/F,IAAMC,EAAU,CACdF,EAAQ,WAAW,EACnBA,EAAQ,SAAS,CACnB,EAEA,QAAWG,KAAUD,EAAS,CAC5B,IAAML,EAAO,QAAQ,YAAYI,EAAKE,CAAM,EAE5C,GAAIN,EACF,OAAOA,CACX,CAGF,CAdgBC,EAAAC,EAAA,0BDnBT,IAAMK,EAAoB,oBAO1B,SAASC,EAAKC,EAAuF,CAC1G,IAAMC,EAASC,EAAeF,CAAc,EAE5C,GAAI,CAACC,EACH,MAAM,IAAI,MAAM,iDAAiD,EAGnE,IAAME,EAAUF,EAAO,qBAAqB,EAAE,IAAIG,GAASC,EAASD,CAAK,CAAC,EAE1E,SAAO,sBACL,eAAYN,EAAmBG,CAAM,EACrC,GAAGE,CACL,CACF,CAbgBG,EAAAP,EAAA,QAkBT,IAAMQ,KAAmB,wBAC9B,CAACC,EAA2CC,IAA0B,CACpE,IAAMC,EAAUD,EAAI,aAAa,EAAE,WAAW,EACxCR,EAASO,EAAON,EAAeM,CAAI,EAAIG,EAAsCF,EAAKX,CAAiB,EAEzG,OAAKG,EAWEA,EAAO,MAAMS,EAAQ,KAAK,GAV/B,IAAI,SAAO,kBAAkB,EAAE,KAAK,yFAAyF,EAEtH,CACL,MAAO,CAAE,IAAK,CAAC,CAAE,EACjB,OAAQ,CAAC,EACT,MAAO,CAAC,EACR,UAAW,CAAC,CACd,EAIJ,CACF","names":["nestjs_exports","__export","CRUD_QUERY_PARSER","Crud","ParseCrudRequest","__toCommonJS","import_common","ApiQuery","options","createInstance","data","__name","getMetadataFromContext","context","key","targets","target","CRUD_QUERY_PARSER","Crud","parserContract","parser","createInstance","openApi","param","ApiQuery","__name","ParseCrudRequest","data","ctx","request","getMetadataFromContext"]}
|