crud-query-parser 0.0.2 → 0.1.0
Sign up to get free protection for your applications and to get access to all the features.
- package/README.md +37 -11
- package/dist/adapters/typeorm/index.d.mts +104 -10
- package/dist/adapters/typeorm/index.d.ts +104 -10
- 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/{parsed-request-where.builder-DME55XmN.d.ts → crud-request-where.builder-B5241Aht.d.ts} +7 -7
- package/dist/{parsed-request-where.builder-DRZUAxu4.d.mts → crud-request-where.builder-BwWLx0Bh.d.mts} +7 -7
- package/dist/{crud-request-CvDKp6Iy.d.mts → crud-request-x16CuDRF.d.mts} +1 -0
- package/dist/{crud-request-CvDKp6Iy.d.ts → crud-request-x16CuDRF.d.ts} +1 -0
- package/dist/filters/index.d.mts +11 -2
- package/dist/filters/index.d.ts +11 -2
- package/dist/filters/index.js +1 -1
- package/dist/filters/index.js.map +1 -1
- package/dist/filters/index.mjs +1 -1
- package/dist/filters/index.mjs.map +1 -1
- package/dist/helpers/nestjs/index.d.mts +2 -2
- package/dist/helpers/nestjs/index.d.ts +2 -2
- package/dist/helpers/nestjs/index.js.map +1 -1
- package/dist/helpers/nestjs/index.mjs.map +1 -1
- package/dist/index.d.mts +4 -4
- package/dist/index.d.ts +4 -4
- 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 +34 -9
- package/dist/parsers/crud/index.d.ts +34 -9
- 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/{query-adapter-Vebxws3V.d.ts → query-adapter-CEcyFcWr.d.ts} +1 -1
- package/dist/{query-adapter-BliD9hJN.d.mts → query-adapter-CeTK3yxp.d.mts} +1 -1
- package/dist/{request-parser-WaQBZsYG.d.mts → request-parser-BMkszvGr.d.mts} +1 -1
- package/dist/{request-parser-B-fK5GnP.d.ts → request-parser-BxVulcsX.d.ts} +1 -1
- package/package.json +133 -118
@@ -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 { Alias } from 'typeorm/query-builder/Alias';\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 { FieldPath } from '../../models/field-path';\r\nimport { ensureArray, ensureEmpty, getOffset, isValid } from '../../utils/functions';\r\nimport { pathEquals, pathGetBaseAndName, 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 * What it will do when it finds invalid fields.\r\n *\r\n * By default, `select` and `order` will ignore invalid fields, and `where` will deny invalid fields.\r\n */\r\n invalidFields?: {\r\n /**\r\n * What it will do when it finds invalid fields in `select`.\r\n *\r\n * If \"ignore\", it will remove invalid fields\r\n * If \"deny\", it will throw an exception for invalid fields\r\n * If \"allow-unsafe\", it will not validate any fields. Unsafe: this can allow SQL injection\r\n * If undefined, it will default to \"ignore\"\r\n */\r\n select?: 'ignore' | 'deny' | 'allow-unsafe';\r\n\r\n /**\r\n * What it will do when it finds invalid fields in `order`.\r\n *\r\n * If \"ignore\", it will remove invalid fields\r\n * If \"deny\", it will throw an exception for invalid fields\r\n * If \"allow-unsafe\", it will not validate any fields. Unsafe: this can allow SQL injection\r\n * If undefined, it will default to \"ignore\"\r\n */\r\n order?: 'ignore' | 'deny' | 'allow-unsafe';\r\n\r\n /**\r\n * What it will do when it finds invalid fields in `order`.\r\n *\r\n * If \"ignore\", it will remove invalid fields\r\n * If \"deny\", it will throw an exception for invalid fields\r\n * If \"allow-unsafe\", it will not validate any fields. Unsafe: this can allow SQL injection\r\n * If undefined, it will default to \"deny\"\r\n */\r\n where?: 'ignore' | 'deny' | 'allow-unsafe';\r\n }\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 offset = getOffset(request.offset, request.limit, request.page);\r\n\r\n const fullQuery = this.createBaseQuery(qb, request);\r\n const paginatedQuery = this.paginateQuery(fullQuery.clone(), request, offset);\r\n\r\n const data = await paginatedQuery.getMany();\r\n const total = await fullQuery.getCount();\r\n\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 const mainAlias = qb.expressionMap.mainAlias;\r\n\r\n if (!mainAlias)\r\n throw new Error('No main alias found in query builder');\r\n\r\n this.adaptSelect(qb, mainAlias, query.select);\r\n this.adaptRelations(qb, mainAlias, query.relations, query.select);\r\n this.adaptWhere(mainAlias, query.relations, qb, query.where, false, paramsDefined, isILikeEnabled);\r\n this.adaptOrder(qb, mainAlias, query.relations, 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 * @param offset The parsed query offset\r\n */\r\n protected paginateQuery<E extends ObjectLiteral>(qb: SelectQueryBuilder<E>, query: CrudRequest, offset?: number): SelectQueryBuilder<E> {\r\n return qb.limit(query.limit).offset(offset);\r\n }\r\n\r\n /**\r\n * Adapts a select\r\n *\r\n * @param qb The query builder\r\n * @param alias The base alias\r\n * @param select The parsed select fields\r\n */\r\n protected adaptSelect<E extends ObjectLiteral>(\r\n qb: SelectQueryBuilder<E>,\r\n alias: Alias,\r\n select: ParsedRequestSelect,\r\n ): 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\r\n .filter(f => f.field.length === 1)\r\n .filter(f => this.validateField(alias, f.field, 'select'));\r\n\r\n qb.select(fields.map(s => [alias.name, ...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 baseAlias The base alias\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>(\r\n qb: SelectQueryBuilder<E>,\r\n baseAlias: Alias,\r\n relations: CrudRequestRelation[],\r\n select: ParsedRequestSelect,\r\n ): void {\r\n for (const relation of relations) {\r\n const path = [baseAlias.name, ...relation.field].join('.');\r\n const alias = relation.alias || [baseAlias.name, ...relation.field].join('_');\r\n\r\n const fields = select\r\n .filter(f => pathHasBase(f.field, relation.field))\r\n .filter(f => this.validateField(baseAlias, f.field, 'select'));\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 alias The base alias\r\n * @param relations The list of relations\r\n * @param ordering The parsed ordering\r\n */\r\n protected adaptOrder<E extends ObjectLiteral>(\r\n qb: SelectQueryBuilder<E>,\r\n alias: Alias,\r\n relations: CrudRequestRelation[],\r\n ordering: CrudRequestOrder[],\r\n ): void {\r\n for (const order of ordering) {\r\n if (!this.validateField(alias, order.field, 'order'))\r\n continue;\r\n\r\n const [fieldBase, fieldName] = pathGetBaseAndName(order.field);\r\n const aliasName = this.getFieldAlias(alias, relations, fieldBase);\r\n\r\n const path = aliasName + '.' + fieldName;\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 relations The list of relations\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: Alias,\r\n relations: CrudRequestRelation[],\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, relations, 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, relations, wqb, item, false, params, isILikeEnabled))\r\n ));\r\n } else if (where.field) {\r\n if (!this.validateField(alias, where.field, 'where'))\r\n return;\r\n\r\n const param = this.createParam(params, where.field);\r\n const query = this.mapWhereOperators(alias, relations, 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 * Checks whether the field is valid\r\n *\r\n * @param alias The base alias\r\n * @param path The field path\r\n * @param source The source where the field validation comes from\r\n */\r\n protected validateField(alias: Alias, path: FieldPath, source: 'select' | 'order' | 'where'): boolean {\r\n const isValid = this.isFieldValid(alias, path);\r\n\r\n if (isValid)\r\n return true;\r\n\r\n const defaults = {\r\n select: 'ignore',\r\n order: 'ignore',\r\n where: 'deny',\r\n };\r\n\r\n const rule = this.options.invalidFields?.[source] || defaults[source];\r\n\r\n if (rule === 'ignore')\r\n return false;\r\n\r\n if (rule === 'allow-unsafe')\r\n return true;\r\n\r\n if (rule === 'deny')\r\n throw new Error(`${source} field \"${path.join('.')}\" is invalid.`);\r\n\r\n return false;\r\n }\r\n\r\n /**\r\n * Checks whether the field is valid\r\n *\r\n * @param alias The base alias\r\n * @param path The field path\r\n */\r\n protected isFieldValid(alias: Alias, path: FieldPath): boolean {\r\n if (path.length === 0)\r\n return false;\r\n\r\n let metadata = alias.metadata;\r\n\r\n const relationPath = [...path];\r\n const field = relationPath.pop()!;\r\n\r\n for (const part of relationPath) {\r\n const relation = metadata.findRelationWithPropertyPath(part);\r\n\r\n if (!relation)\r\n return false;\r\n\r\n metadata = relation.inverseEntityMetadata;\r\n }\r\n\r\n const column = metadata.findColumnWithPropertyPathStrict(field);\r\n\r\n return !!column;\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 relations The list of relations\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: Alias,\r\n relations: CrudRequestRelation[],\r\n where: CrudRequestWhereField,\r\n param: string,\r\n isILikeEnabled: boolean,\r\n ): { where: string, params: ObjectLiteral } {\r\n const [pathBase, pathField] = pathGetBaseAndName(where.field);\r\n const fieldAlias = this.getFieldAlias(alias, relations, pathBase);\r\n\r\n const field = fieldAlias + '.' + pathField;\r\n\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 ensureEmpty('IS NULL operator', value);\r\n\r\n return { where: `${field} IS NULL`, params: {} };\r\n\r\n case CrudRequestWhereOperator.NOT_NULL:\r\n ensureEmpty('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 /**\r\n * Gets a field alias based on its base path\r\n *\r\n * @param alias The query main alias\r\n * @param relations The relations\r\n * @param base The base path\r\n */\r\n protected getFieldAlias(alias: Alias, relations: CrudRequestRelation[], base: string[]): string {\r\n if (base.length === 0)\r\n return alias.name;\r\n\r\n const relation = relations.find(r => pathEquals(r.field, base));\r\n\r\n if (relation && relation.alias)\r\n return relation.alias;\r\n\r\n return [alias.name, ...base].join('_');\r\n }\r\n\r\n /**\r\n * Creates an ILIKE expression that works on all databases\r\n *\r\n * @param isILikeEnabled Whether ILIKE is supported\r\n * @param field The field name\r\n * @param not Whether the expression is inverted\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 /**\r\n * Checks whether ILIKE expressions are available for the current database\r\n *\r\n * @param qb The query builder\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 ensureEmpty(fieldName: string, data: any) {\r\n if (isValid(data) && data !== true)\r\n throw new Error(`${fieldName} must be true, null or undefined`);\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\nexport function getOffset(offset: number | undefined, limit?: number, page?: number): number {\r\n return offset ?? (limit && page ? limit * page : 0);\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\r\n/**\r\n * Breaks a path into the base part and the field name part\r\n *\r\n * @param path The full path\r\n */\r\nexport function pathGetBaseAndName(path: string[]): [string[], string] {\r\n if (path.length === 0)\r\n throw new Error('Cannot break an empty path');\r\n\r\n const base = [...path];\r\n const name = base.pop()!;\r\n\r\n return [base, name];\r\n}\r\n\r\n\r\n/**\r\n * Gets the last part of the path: the field name\r\n *\r\n * @param path The full path\r\n */\r\nexport function pathGetFieldName(path: string[]): string {\r\n return path[path.length - 1];\r\n}\r\n"],"mappings":"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","names":["Brackets","ensureArray","fieldName","data","minLength","__name","ensureEmpty","isValid","value","getOffset","offset","limit","page","pathEquals","path1","path2","p1","i","__name","pathHasBase","path","base","start","i","__name","pathGetBaseAndName","name","TypeOrmQueryAdapter","options","__name","qb","query","request","offset","getOffset","fullQuery","data","total","limit","count","page","pageCount","paramsDefined","isILikeEnabled","mainAlias","alias","select","fields","f","baseAlias","relations","relation","path","pathHasBase","ordering","order","fieldBase","fieldName","pathGetBaseAndName","where","or","params","addWhere","Brackets","wqb","item","param","field","name","iteration","source","defaults","rule","metadata","relationPath","part","pathBase","pathField","operator","value","ensureArray","arr","ensureEmpty","base","r","pathEquals","not","ilikeEnabled","isValid","type"]}
|
package/dist/{parsed-request-where.builder-DME55XmN.d.ts → crud-request-where.builder-B5241Aht.d.ts}
RENAMED
@@ -1,20 +1,20 @@
|
|
1
|
-
import { e as CrudRequestWhereAND, f as CrudRequestWhereOR, i as CrudRequestWhereOperator, h as CrudRequestWhereValueType, d as CrudRequestWhere } from './crud-request-
|
1
|
+
import { e as CrudRequestWhereAND, f as CrudRequestWhereOR, i as CrudRequestWhereOperator, h as CrudRequestWhereValueType, d as CrudRequestWhere } from './crud-request-x16CuDRF.js';
|
2
2
|
|
3
3
|
/**
|
4
4
|
* A helper class that makes it easier to create a CrudRequestWhere
|
5
5
|
*/
|
6
|
-
declare class
|
6
|
+
declare class CrudRequestWhereBuilder {
|
7
7
|
private readonly where;
|
8
8
|
private readonly parent?;
|
9
|
-
constructor(where?: CrudRequestWhereAND | CrudRequestWhereOR, parent?:
|
9
|
+
constructor(where?: CrudRequestWhereAND | CrudRequestWhereOR, parent?: CrudRequestWhereBuilder | undefined);
|
10
10
|
/**
|
11
11
|
* Adds an AND bracket
|
12
12
|
*/
|
13
|
-
addAnd():
|
13
|
+
addAnd(): CrudRequestWhereBuilder;
|
14
14
|
/**
|
15
15
|
* Adds an OR bracket
|
16
16
|
*/
|
17
|
-
addOr():
|
17
|
+
addOr(): CrudRequestWhereBuilder;
|
18
18
|
/**
|
19
19
|
* Adds a field comparison
|
20
20
|
*
|
@@ -22,11 +22,11 @@ declare class ParsedRequestWhereBuilder {
|
|
22
22
|
* @param operator The comparison operator
|
23
23
|
* @param value The value to compare
|
24
24
|
*/
|
25
|
-
addField(field: string[], operator: CrudRequestWhereOperator, value: CrudRequestWhereValueType):
|
25
|
+
addField(field: string[], operator: CrudRequestWhereOperator, value: CrudRequestWhereValueType | CrudRequestWhereValueType[]): CrudRequestWhereBuilder;
|
26
26
|
/**
|
27
27
|
* Constructs the final where condition
|
28
28
|
*/
|
29
29
|
build(): CrudRequestWhere;
|
30
30
|
}
|
31
31
|
|
32
|
-
export {
|
32
|
+
export { CrudRequestWhereBuilder as C };
|
@@ -1,20 +1,20 @@
|
|
1
|
-
import { e as CrudRequestWhereAND, f as CrudRequestWhereOR, i as CrudRequestWhereOperator, h as CrudRequestWhereValueType, d as CrudRequestWhere } from './crud-request-
|
1
|
+
import { e as CrudRequestWhereAND, f as CrudRequestWhereOR, i as CrudRequestWhereOperator, h as CrudRequestWhereValueType, d as CrudRequestWhere } from './crud-request-x16CuDRF.mjs';
|
2
2
|
|
3
3
|
/**
|
4
4
|
* A helper class that makes it easier to create a CrudRequestWhere
|
5
5
|
*/
|
6
|
-
declare class
|
6
|
+
declare class CrudRequestWhereBuilder {
|
7
7
|
private readonly where;
|
8
8
|
private readonly parent?;
|
9
|
-
constructor(where?: CrudRequestWhereAND | CrudRequestWhereOR, parent?:
|
9
|
+
constructor(where?: CrudRequestWhereAND | CrudRequestWhereOR, parent?: CrudRequestWhereBuilder | undefined);
|
10
10
|
/**
|
11
11
|
* Adds an AND bracket
|
12
12
|
*/
|
13
|
-
addAnd():
|
13
|
+
addAnd(): CrudRequestWhereBuilder;
|
14
14
|
/**
|
15
15
|
* Adds an OR bracket
|
16
16
|
*/
|
17
|
-
addOr():
|
17
|
+
addOr(): CrudRequestWhereBuilder;
|
18
18
|
/**
|
19
19
|
* Adds a field comparison
|
20
20
|
*
|
@@ -22,11 +22,11 @@ declare class ParsedRequestWhereBuilder {
|
|
22
22
|
* @param operator The comparison operator
|
23
23
|
* @param value The value to compare
|
24
24
|
*/
|
25
|
-
addField(field: string[], operator: CrudRequestWhereOperator, value: CrudRequestWhereValueType):
|
25
|
+
addField(field: string[], operator: CrudRequestWhereOperator, value: CrudRequestWhereValueType | CrudRequestWhereValueType[]): CrudRequestWhereBuilder;
|
26
26
|
/**
|
27
27
|
* Constructs the final where condition
|
28
28
|
*/
|
29
29
|
build(): CrudRequestWhere;
|
30
30
|
}
|
31
31
|
|
32
|
-
export {
|
32
|
+
export { CrudRequestWhereBuilder as C };
|
@@ -78,6 +78,7 @@ interface CrudRequest {
|
|
78
78
|
where: CrudRequestWhere;
|
79
79
|
limit?: number;
|
80
80
|
offset?: number;
|
81
|
+
page?: number;
|
81
82
|
}
|
82
83
|
|
83
84
|
export { type CrudRequestFields as C, type FieldPath as F, type ParsedRequestSelect as P, type CrudRequestRelation as a, type CrudRequestOrder as b, type CrudRequest as c, type CrudRequestWhere as d, type CrudRequestWhereAND as e, type CrudRequestWhereOR as f, type CrudRequestWhereField as g, type CrudRequestWhereValueType as h, CrudRequestWhereOperator as i };
|
@@ -78,6 +78,7 @@ interface CrudRequest {
|
|
78
78
|
where: CrudRequestWhere;
|
79
79
|
limit?: number;
|
80
80
|
offset?: number;
|
81
|
+
page?: number;
|
81
82
|
}
|
82
83
|
|
83
84
|
export { type CrudRequestFields as C, type FieldPath as F, type ParsedRequestSelect as P, type CrudRequestRelation as a, type CrudRequestOrder as b, type CrudRequest as c, type CrudRequestWhere as d, type CrudRequestWhereAND as e, type CrudRequestWhereOR as f, type CrudRequestWhereField as g, type CrudRequestWhereValueType as h, CrudRequestWhereOperator as i };
|
package/dist/filters/index.d.mts
CHANGED
@@ -1,4 +1,4 @@
|
|
1
|
-
import { c as CrudRequest, d as CrudRequestWhere } from '../crud-request-
|
1
|
+
import { c as CrudRequest, d as CrudRequestWhere } from '../crud-request-x16CuDRF.mjs';
|
2
2
|
|
3
3
|
/**
|
4
4
|
* Ensures a condition is always applied to the query
|
@@ -8,6 +8,15 @@ import { c as CrudRequest, d as CrudRequestWhere } from '../crud-request-CvDKp6I
|
|
8
8
|
*/
|
9
9
|
declare function ensureCondition(request: CrudRequest, condition: CrudRequestWhere): CrudRequest;
|
10
10
|
|
11
|
+
/**
|
12
|
+
* Ensures a condition is always applied to the query
|
13
|
+
*
|
14
|
+
* @param request The parsed request
|
15
|
+
* @param entity The property that need to be applied
|
16
|
+
* @param basePath The field path prefix
|
17
|
+
*/
|
18
|
+
declare function ensureEqCondition<T extends Record<string, any>>(request: CrudRequest, entity: Partial<T>, basePath?: string[]): CrudRequest;
|
19
|
+
|
11
20
|
/**
|
12
21
|
* Ensures that the limit will be set following a maximum rule
|
13
22
|
*
|
@@ -34,4 +43,4 @@ declare function filterProperties(request: CrudRequest, allowedProperties: strin
|
|
34
43
|
*/
|
35
44
|
declare function filterRelations(request: CrudRequest, allowedRelations: string[]): CrudRequest;
|
36
45
|
|
37
|
-
export { ensureCondition, ensureLimit, filterProperties, filterRelations };
|
46
|
+
export { ensureCondition, ensureEqCondition, ensureLimit, filterProperties, filterRelations };
|
package/dist/filters/index.d.ts
CHANGED
@@ -1,4 +1,4 @@
|
|
1
|
-
import { c as CrudRequest, d as CrudRequestWhere } from '../crud-request-
|
1
|
+
import { c as CrudRequest, d as CrudRequestWhere } from '../crud-request-x16CuDRF.js';
|
2
2
|
|
3
3
|
/**
|
4
4
|
* Ensures a condition is always applied to the query
|
@@ -8,6 +8,15 @@ import { c as CrudRequest, d as CrudRequestWhere } from '../crud-request-CvDKp6I
|
|
8
8
|
*/
|
9
9
|
declare function ensureCondition(request: CrudRequest, condition: CrudRequestWhere): CrudRequest;
|
10
10
|
|
11
|
+
/**
|
12
|
+
* Ensures a condition is always applied to the query
|
13
|
+
*
|
14
|
+
* @param request The parsed request
|
15
|
+
* @param entity The property that need to be applied
|
16
|
+
* @param basePath The field path prefix
|
17
|
+
*/
|
18
|
+
declare function ensureEqCondition<T extends Record<string, any>>(request: CrudRequest, entity: Partial<T>, basePath?: string[]): CrudRequest;
|
19
|
+
|
11
20
|
/**
|
12
21
|
* Ensures that the limit will be set following a maximum rule
|
13
22
|
*
|
@@ -34,4 +43,4 @@ declare function filterProperties(request: CrudRequest, allowedProperties: strin
|
|
34
43
|
*/
|
35
44
|
declare function filterRelations(request: CrudRequest, allowedRelations: string[]): CrudRequest;
|
36
45
|
|
37
|
-
export { ensureCondition, ensureLimit, filterProperties, filterRelations };
|
46
|
+
export { ensureCondition, ensureEqCondition, ensureLimit, filterProperties, filterRelations };
|
package/dist/filters/index.js
CHANGED
@@ -1,2 +1,2 @@
|
|
1
|
-
"use strict";var
|
1
|
+
"use strict";var l=Object.defineProperty;var c=Object.getOwnPropertyDescriptor;var _=Object.getOwnPropertyNames;var N=Object.prototype.hasOwnProperty;var o=(n,e)=>l(n,"name",{value:e,configurable:!0});var R=(n,e)=>{for(var i in e)l(n,i,{get:e[i],enumerable:!0})},T=(n,e,i,t)=>{if(e&&typeof e=="object"||typeof e=="function")for(let r of _(e))!N.call(n,r)&&r!==i&&l(n,r,{get:()=>e[r],enumerable:!(t=c(e,r))||t.enumerable});return n};var E=n=>T(l({},"__esModule",{value:!0}),n);var L={};R(L,{ensureCondition:()=>d,ensureEqCondition:()=>m,ensureLimit:()=>a,filterProperties:()=>x,filterRelations:()=>C});module.exports=E(L);function d(n,e){return n.where.and?{...n,where:{and:[...n.where.and,e]}}:{...n,where:{and:[e,n.where]}}}o(d,"ensureCondition");function m(n,e,i=[]){for(let t of Object.keys(e)){if(typeof e[t]=="object"&&!Array.isArray(e[t])){n=m(n,e[t],[...i,t]);continue}n=d(n,{field:[...i,t],operator:"eq",value:e[t]})}return n}o(m,"ensureEqCondition");function a(n,e,i){return{...n,limit:Math.min(Math.max(n.limit??e,1),i)}}o(a,"ensureLimit");function x(n,e){let i=n.select;i.length===0?i=e.map(f=>({field:f.split(".")})):i=n.select.filter(f=>e.includes(f.field.join(".")));let t=u(n.where,e),r=n.order.filter(f=>e.includes(f.field.join("."))),s=n.relations.filter(f=>e.includes(f.field.join(".")));return{...n,select:i,where:t,order:r,relations:s}}o(x,"filterProperties");function u(n,e){return n.or?{or:n.or.map(i=>u(i,e))}:n.and?{and:n.and.map(i=>u(i,e))}:n.field&&!e.includes(n.field.join("."))?{and:[]}:n}o(u,"filterPropertyAccessWhere");function C(n,e){let i=n.relations.filter(t=>e.includes(t.field.join(".")));return{...n,relations:i}}o(C,"filterRelations");0&&(module.exports={ensureCondition,ensureEqCondition,ensureLimit,filterProperties,filterRelations});
|
2
2
|
//# sourceMappingURL=index.js.map
|
@@ -1 +1 @@
|
|
1
|
-
{"version":3,"sources":["../../src/filters/index.ts","../../src/filters/conditions/ensureCondition.ts","../../src/filters/limit/ensureLimit.ts","../../src/filters/property/filterProperties.ts","../../src/filters/property/filterRelations.ts"],"sourcesContent":["\r\nexport * from './conditions/ensureCondition';\r\nexport * from './limit/ensureLimit';\r\nexport * from './property/filterProperties';\r\nexport * from './property/filterRelations';\r\n","import { CrudRequest } from '../../models/crud-request';\r\nimport { CrudRequestWhere } from '../../models/crud-request-where';\r\n\r\n/**\r\n * Ensures a condition is always applied to the query\r\n *\r\n * @param request The parsed request\r\n * @param condition The condition that needs to be applied\r\n */\r\nexport function ensureCondition(request: CrudRequest, condition: CrudRequestWhere): CrudRequest {\r\n // If there is already an \"AND\" condition, we'll just append to that\r\n if (request.where.and) {\r\n return {\r\n ...request,\r\n where: {\r\n and: [\r\n ...request.where.and,\r\n condition,\r\n ]\r\n }\r\n }\r\n }\r\n\r\n return {\r\n ...request,\r\n where: {\r\n and: [\r\n condition,\r\n request.where,\r\n ],\r\n },\r\n };\r\n}\r\n","import { CrudRequest } from '../../models/crud-request';\r\n\r\n/**\r\n * Ensures that the limit will be set following a maximum rule\r\n *\r\n * @param request The parsed request\r\n * @param defaultLimit The default limit number\r\n * @param maxLimit The maximum allowed limit number\r\n */\r\nexport function ensureLimit(request: CrudRequest, defaultLimit: number, maxLimit: number): CrudRequest {\r\n return {\r\n ...request,\r\n limit: Math.min(Math.max(request.limit ?? defaultLimit, 1), maxLimit),\r\n };\r\n}\r\n","import { CrudRequest } from '../../models/crud-request';\r\nimport { CrudRequestWhere } from '../../models/crud-request-where';\r\n\r\n/**\r\n * Filters access to an allowlist of properties and relations.\r\n * No selecting, filtering, sorting and joining can be done on a property that is not listed.\r\n *\r\n * @param request The parsed request\r\n * @param allowedProperties The list of properties (in case of a field path, separated by dot) that will be allowed\r\n */\r\nexport function filterProperties(\r\n request: CrudRequest,\r\n allowedProperties: string[],\r\n): CrudRequest {\r\n let select = request.select;\r\n\r\n if (select.length === 0) {\r\n select = allowedProperties.map(prop => ({ field: prop.split('.') }));\r\n } else {\r\n select = request.select.filter(item => allowedProperties.includes(item.field.join('.')));\r\n }\r\n\r\n const where = filterPropertyAccessWhere(request.where, allowedProperties);\r\n\r\n const order = request.order.filter(item => allowedProperties.includes(item.field.join('.')));\r\n\r\n // TODO allow relations by the first part of field paths\r\n const relations = request.relations.filter(item => allowedProperties.includes(item.field.join('.')));\r\n\r\n return {\r\n ...request,\r\n select,\r\n where,\r\n order,\r\n relations,\r\n };\r\n}\r\n\r\nfunction filterPropertyAccessWhere(\r\n where: CrudRequestWhere,\r\n allowedProperties: string[],\r\n): CrudRequestWhere {\r\n if (where.or) {\r\n return {\r\n or: where.or.map(w => filterPropertyAccessWhere(w, allowedProperties)),\r\n };\r\n }\r\n\r\n if (where.and) {\r\n return {\r\n and: where.and.map(w => filterPropertyAccessWhere(w, allowedProperties)),\r\n };\r\n }\r\n\r\n if (where.field) {\r\n // We'll return an empty AND where if the field is not allowed\r\n if (!allowedProperties.includes(where.field.join('.')))\r\n return { and: [] };\r\n }\r\n\r\n return where;\r\n}\r\n\r\n","import { CrudRequest } from '../../models/crud-request';\r\n\r\n/**\r\n * Filters access to an allowlist of relations.\r\n *\r\n * @param request The parsed request\r\n * @param allowedRelations The list of relations (in case of a field path, separated by dot) that will be allowed\r\n */\r\nexport function filterRelations(\r\n request: CrudRequest,\r\n allowedRelations: string[],\r\n): CrudRequest {\r\n const relations = request.relations.filter(item => allowedRelations.includes(item.field.join('.')));\r\n\r\n return {\r\n ...request,\r\n relations,\r\n };\r\n}\r\n"],"mappings":"4dAAA,IAAAA,EAAA,GAAAC,EAAAD,EAAA,qBAAAE,EAAA,gBAAAC,EAAA,qBAAAC,EAAA,oBAAAC,IAAA,eAAAC,
|
1
|
+
{"version":3,"sources":["../../src/filters/index.ts","../../src/filters/conditions/ensureCondition.ts","../../src/filters/conditions/ensureEqCondition.ts","../../src/filters/limit/ensureLimit.ts","../../src/filters/property/filterProperties.ts","../../src/filters/property/filterRelations.ts"],"sourcesContent":["\r\nexport * from './conditions/ensureCondition';\r\nexport * from './conditions/ensureEqCondition';\r\nexport * from './limit/ensureLimit';\r\nexport * from './property/filterProperties';\r\nexport * from './property/filterRelations';\r\n","import { CrudRequest } from '../../models/crud-request';\r\nimport { CrudRequestWhere } from '../../models/crud-request-where';\r\n\r\n/**\r\n * Ensures a condition is always applied to the query\r\n *\r\n * @param request The parsed request\r\n * @param condition The condition that needs to be applied\r\n */\r\nexport function ensureCondition(request: CrudRequest, condition: CrudRequestWhere): CrudRequest {\r\n // If there is already an \"AND\" condition, we'll just append to that\r\n if (request.where.and) {\r\n return {\r\n ...request,\r\n where: {\r\n and: [\r\n ...request.where.and,\r\n condition,\r\n ]\r\n }\r\n }\r\n }\r\n\r\n return {\r\n ...request,\r\n where: {\r\n and: [\r\n condition,\r\n request.where,\r\n ],\r\n },\r\n };\r\n}\r\n","import { CrudRequest } from '../../models/crud-request';\r\nimport { ensureCondition } from './ensureCondition';\r\nimport { CrudRequestWhereOperator } from '../../models/crud-request-where';\r\n\r\n/**\r\n * Ensures a condition is always applied to the query\r\n *\r\n * @param request The parsed request\r\n * @param entity The property that need to be applied\r\n * @param basePath The field path prefix\r\n */\r\nexport function ensureEqCondition<T extends Record<string, any>>(request: CrudRequest, entity: Partial<T>, basePath: string[] = []): CrudRequest {\r\n for (const key of Object.keys(entity)) {\r\n if (typeof entity[key] === 'object' && !Array.isArray(entity[key])) {\r\n request = ensureEqCondition(request, entity[key], [...basePath, key]);\r\n continue;\r\n }\r\n\r\n request = ensureCondition(request, {\r\n field: [...basePath, key],\r\n operator: CrudRequestWhereOperator.EQ,\r\n value: entity[key],\r\n });\r\n }\r\n\r\n return request;\r\n}\r\n","import { CrudRequest } from '../../models/crud-request';\r\n\r\n/**\r\n * Ensures that the limit will be set following a maximum rule\r\n *\r\n * @param request The parsed request\r\n * @param defaultLimit The default limit number\r\n * @param maxLimit The maximum allowed limit number\r\n */\r\nexport function ensureLimit(request: CrudRequest, defaultLimit: number, maxLimit: number): CrudRequest {\r\n return {\r\n ...request,\r\n limit: Math.min(Math.max(request.limit ?? defaultLimit, 1), maxLimit),\r\n };\r\n}\r\n","import { CrudRequest } from '../../models/crud-request';\r\nimport { CrudRequestWhere } from '../../models/crud-request-where';\r\n\r\n/**\r\n * Filters access to an allowlist of properties and relations.\r\n * No selecting, filtering, sorting and joining can be done on a property that is not listed.\r\n *\r\n * @param request The parsed request\r\n * @param allowedProperties The list of properties (in case of a field path, separated by dot) that will be allowed\r\n */\r\nexport function filterProperties(\r\n request: CrudRequest,\r\n allowedProperties: string[],\r\n): CrudRequest {\r\n let select = request.select;\r\n\r\n if (select.length === 0) {\r\n select = allowedProperties.map(prop => ({ field: prop.split('.') }));\r\n } else {\r\n select = request.select.filter(item => allowedProperties.includes(item.field.join('.')));\r\n }\r\n\r\n const where = filterPropertyAccessWhere(request.where, allowedProperties);\r\n\r\n const order = request.order.filter(item => allowedProperties.includes(item.field.join('.')));\r\n\r\n // TODO allow relations by the first part of field paths\r\n const relations = request.relations.filter(item => allowedProperties.includes(item.field.join('.')));\r\n\r\n return {\r\n ...request,\r\n select,\r\n where,\r\n order,\r\n relations,\r\n };\r\n}\r\n\r\nfunction filterPropertyAccessWhere(\r\n where: CrudRequestWhere,\r\n allowedProperties: string[],\r\n): CrudRequestWhere {\r\n if (where.or) {\r\n return {\r\n or: where.or.map(w => filterPropertyAccessWhere(w, allowedProperties)),\r\n };\r\n }\r\n\r\n if (where.and) {\r\n return {\r\n and: where.and.map(w => filterPropertyAccessWhere(w, allowedProperties)),\r\n };\r\n }\r\n\r\n if (where.field) {\r\n // We'll return an empty AND where if the field is not allowed\r\n if (!allowedProperties.includes(where.field.join('.')))\r\n return { and: [] };\r\n }\r\n\r\n return where;\r\n}\r\n\r\n","import { CrudRequest } from '../../models/crud-request';\r\n\r\n/**\r\n * Filters access to an allowlist of relations.\r\n *\r\n * @param request The parsed request\r\n * @param allowedRelations The list of relations (in case of a field path, separated by dot) that will be allowed\r\n */\r\nexport function filterRelations(\r\n request: CrudRequest,\r\n allowedRelations: string[],\r\n): CrudRequest {\r\n const relations = request.relations.filter(item => allowedRelations.includes(item.field.join('.')));\r\n\r\n return {\r\n ...request,\r\n relations,\r\n };\r\n}\r\n"],"mappings":"4dAAA,IAAAA,EAAA,GAAAC,EAAAD,EAAA,qBAAAE,EAAA,sBAAAC,EAAA,gBAAAC,EAAA,qBAAAC,EAAA,oBAAAC,IAAA,eAAAC,EAAAP,GCSO,SAASQ,EAAgBC,EAAsBC,EAA0C,CAE9F,OAAID,EAAQ,MAAM,IACT,CACL,GAAGA,EACH,MAAO,CACL,IAAK,CACH,GAAGA,EAAQ,MAAM,IACjBC,CACF,CACF,CACF,EAGK,CACL,GAAGD,EACH,MAAO,CACL,IAAK,CACHC,EACAD,EAAQ,KACV,CACF,CACF,CACF,CAvBgBE,EAAAH,EAAA,mBCET,SAASI,EAAiDC,EAAsBC,EAAoBC,EAAqB,CAAC,EAAgB,CAC/I,QAAWC,KAAO,OAAO,KAAKF,CAAM,EAAG,CACrC,GAAI,OAAOA,EAAOE,CAAG,GAAM,UAAY,CAAC,MAAM,QAAQF,EAAOE,CAAG,CAAC,EAAG,CAClEH,EAAUD,EAAkBC,EAASC,EAAOE,CAAG,EAAG,CAAC,GAAGD,EAAUC,CAAG,CAAC,EACpE,QACF,CAEAH,EAAUI,EAAgBJ,EAAS,CACjC,MAAO,CAAC,GAAGE,EAAUC,CAAG,EACxB,cACA,MAAOF,EAAOE,CAAG,CACnB,CAAC,CACH,CAEA,OAAOH,CACT,CAfgBK,EAAAN,EAAA,qBCFT,SAASO,EAAYC,EAAsBC,EAAsBC,EAA+B,CACrG,MAAO,CACL,GAAGF,EACH,MAAO,KAAK,IAAI,KAAK,IAAIA,EAAQ,OAASC,EAAc,CAAC,EAAGC,CAAQ,CACtE,CACF,CALgBC,EAAAJ,EAAA,eCCT,SAASK,EACdC,EACAC,EACa,CACb,IAAIC,EAASF,EAAQ,OAEjBE,EAAO,SAAW,EACpBA,EAASD,EAAkB,IAAIE,IAAS,CAAE,MAAOA,EAAK,MAAM,GAAG,CAAE,EAAE,EAEnED,EAASF,EAAQ,OAAO,OAAOI,GAAQH,EAAkB,SAASG,EAAK,MAAM,KAAK,GAAG,CAAC,CAAC,EAGzF,IAAMC,EAAQC,EAA0BN,EAAQ,MAAOC,CAAiB,EAElEM,EAAQP,EAAQ,MAAM,OAAOI,GAAQH,EAAkB,SAASG,EAAK,MAAM,KAAK,GAAG,CAAC,CAAC,EAGrFI,EAAYR,EAAQ,UAAU,OAAOI,GAAQH,EAAkB,SAASG,EAAK,MAAM,KAAK,GAAG,CAAC,CAAC,EAEnG,MAAO,CACL,GAAGJ,EACH,OAAAE,EACA,MAAAG,EACA,MAAAE,EACA,UAAAC,CACF,CACF,CA1BgBC,EAAAV,EAAA,oBA4BhB,SAASO,EACPD,EACAJ,EACkB,CAClB,OAAII,EAAM,GACD,CACL,GAAIA,EAAM,GAAG,IAAIK,GAAKJ,EAA0BI,EAAGT,CAAiB,CAAC,CACvE,EAGEI,EAAM,IACD,CACL,IAAKA,EAAM,IAAI,IAAIK,GAAKJ,EAA0BI,EAAGT,CAAiB,CAAC,CACzE,EAGEI,EAAM,OAEJ,CAACJ,EAAkB,SAASI,EAAM,MAAM,KAAK,GAAG,CAAC,EAC5C,CAAE,IAAK,CAAC,CAAE,EAGdA,CACT,CAvBSI,EAAAH,EAAA,6BC9BF,SAASK,EACdC,EACAC,EACa,CACb,IAAMC,EAAYF,EAAQ,UAAU,OAAOG,GAAQF,EAAiB,SAASE,EAAK,MAAM,KAAK,GAAG,CAAC,CAAC,EAElG,MAAO,CACL,GAAGH,EACH,UAAAE,CACF,CACF,CAVgBE,EAAAL,EAAA","names":["filters_exports","__export","ensureCondition","ensureEqCondition","ensureLimit","filterProperties","filterRelations","__toCommonJS","ensureCondition","request","condition","__name","ensureEqCondition","request","entity","basePath","key","ensureCondition","__name","ensureLimit","request","defaultLimit","maxLimit","__name","filterProperties","request","allowedProperties","select","prop","item","where","filterPropertyAccessWhere","order","relations","__name","w","filterRelations","request","allowedRelations","relations","item","__name"]}
|
package/dist/filters/index.mjs
CHANGED
@@ -1,2 +1,2 @@
|
|
1
|
-
var
|
1
|
+
var m=Object.defineProperty;var t=(n,e)=>m(n,"name",{value:e,configurable:!0});function l(n,e){return n.where.and?{...n,where:{and:[...n.where.and,e]}}:{...n,where:{and:[e,n.where]}}}t(l,"ensureCondition");function s(n,e,i=[]){for(let o of Object.keys(e)){if(typeof e[o]=="object"&&!Array.isArray(e[o])){n=s(n,e[o],[...i,o]);continue}n=l(n,{field:[...i,o],operator:"eq",value:e[o]})}return n}t(s,"ensureEqCondition");function L(n,e,i){return{...n,limit:Math.min(Math.max(n.limit??e,1),i)}}t(L,"ensureLimit");function S(n,e){let i=n.select;i.length===0?i=e.map(r=>({field:r.split(".")})):i=n.select.filter(r=>e.includes(r.field.join(".")));let o=f(n.where,e),d=n.order.filter(r=>e.includes(r.field.join("."))),u=n.relations.filter(r=>e.includes(r.field.join(".")));return{...n,select:i,where:o,order:d,relations:u}}t(S,"filterProperties");function f(n,e){return n.or?{or:n.or.map(i=>f(i,e))}:n.and?{and:n.and.map(i=>f(i,e))}:n.field&&!e.includes(n.field.join("."))?{and:[]}:n}t(f,"filterPropertyAccessWhere");function v(n,e){let i=n.relations.filter(o=>e.includes(o.field.join(".")));return{...n,relations:i}}t(v,"filterRelations");export{l as ensureCondition,s as ensureEqCondition,L as ensureLimit,S as filterProperties,v as filterRelations};
|
2
2
|
//# sourceMappingURL=index.mjs.map
|
@@ -1 +1 @@
|
|
1
|
-
{"version":3,"sources":["../../src/filters/conditions/ensureCondition.ts","../../src/filters/limit/ensureLimit.ts","../../src/filters/property/filterProperties.ts","../../src/filters/property/filterRelations.ts"],"sourcesContent":["import { CrudRequest } from '../../models/crud-request';\r\nimport { CrudRequestWhere } from '../../models/crud-request-where';\r\n\r\n/**\r\n * Ensures a condition is always applied to the query\r\n *\r\n * @param request The parsed request\r\n * @param condition The condition that needs to be applied\r\n */\r\nexport function ensureCondition(request: CrudRequest, condition: CrudRequestWhere): CrudRequest {\r\n // If there is already an \"AND\" condition, we'll just append to that\r\n if (request.where.and) {\r\n return {\r\n ...request,\r\n where: {\r\n and: [\r\n ...request.where.and,\r\n condition,\r\n ]\r\n }\r\n }\r\n }\r\n\r\n return {\r\n ...request,\r\n where: {\r\n and: [\r\n condition,\r\n request.where,\r\n ],\r\n },\r\n };\r\n}\r\n","import { CrudRequest } from '../../models/crud-request';\r\n\r\n/**\r\n * Ensures that the limit will be set following a maximum rule\r\n *\r\n * @param request The parsed request\r\n * @param defaultLimit The default limit number\r\n * @param maxLimit The maximum allowed limit number\r\n */\r\nexport function ensureLimit(request: CrudRequest, defaultLimit: number, maxLimit: number): CrudRequest {\r\n return {\r\n ...request,\r\n limit: Math.min(Math.max(request.limit ?? defaultLimit, 1), maxLimit),\r\n };\r\n}\r\n","import { CrudRequest } from '../../models/crud-request';\r\nimport { CrudRequestWhere } from '../../models/crud-request-where';\r\n\r\n/**\r\n * Filters access to an allowlist of properties and relations.\r\n * No selecting, filtering, sorting and joining can be done on a property that is not listed.\r\n *\r\n * @param request The parsed request\r\n * @param allowedProperties The list of properties (in case of a field path, separated by dot) that will be allowed\r\n */\r\nexport function filterProperties(\r\n request: CrudRequest,\r\n allowedProperties: string[],\r\n): CrudRequest {\r\n let select = request.select;\r\n\r\n if (select.length === 0) {\r\n select = allowedProperties.map(prop => ({ field: prop.split('.') }));\r\n } else {\r\n select = request.select.filter(item => allowedProperties.includes(item.field.join('.')));\r\n }\r\n\r\n const where = filterPropertyAccessWhere(request.where, allowedProperties);\r\n\r\n const order = request.order.filter(item => allowedProperties.includes(item.field.join('.')));\r\n\r\n // TODO allow relations by the first part of field paths\r\n const relations = request.relations.filter(item => allowedProperties.includes(item.field.join('.')));\r\n\r\n return {\r\n ...request,\r\n select,\r\n where,\r\n order,\r\n relations,\r\n };\r\n}\r\n\r\nfunction filterPropertyAccessWhere(\r\n where: CrudRequestWhere,\r\n allowedProperties: string[],\r\n): CrudRequestWhere {\r\n if (where.or) {\r\n return {\r\n or: where.or.map(w => filterPropertyAccessWhere(w, allowedProperties)),\r\n };\r\n }\r\n\r\n if (where.and) {\r\n return {\r\n and: where.and.map(w => filterPropertyAccessWhere(w, allowedProperties)),\r\n };\r\n }\r\n\r\n if (where.field) {\r\n // We'll return an empty AND where if the field is not allowed\r\n if (!allowedProperties.includes(where.field.join('.')))\r\n return { and: [] };\r\n }\r\n\r\n return where;\r\n}\r\n\r\n","import { CrudRequest } from '../../models/crud-request';\r\n\r\n/**\r\n * Filters access to an allowlist of relations.\r\n *\r\n * @param request The parsed request\r\n * @param allowedRelations The list of relations (in case of a field path, separated by dot) that will be allowed\r\n */\r\nexport function filterRelations(\r\n request: CrudRequest,\r\n allowedRelations: string[],\r\n): CrudRequest {\r\n const relations = request.relations.filter(item => allowedRelations.includes(item.field.join('.')));\r\n\r\n return {\r\n ...request,\r\n relations,\r\n };\r\n}\r\n"],"mappings":"+EASO,SAASA,EAAgBC,EAAsBC,EAA0C,CAE9F,OAAID,EAAQ,MAAM,IACT,CACL,GAAGA,EACH,MAAO,CACL,IAAK,CACH,GAAGA,EAAQ,MAAM,IACjBC,CACF,CACF,CACF,EAGK,CACL,GAAGD,EACH,MAAO,CACL,IAAK,CACHC,EACAD,EAAQ,KACV,CACF,CACF,CACF,CAvBgBE,EAAAH,EAAA,
|
1
|
+
{"version":3,"sources":["../../src/filters/conditions/ensureCondition.ts","../../src/filters/conditions/ensureEqCondition.ts","../../src/filters/limit/ensureLimit.ts","../../src/filters/property/filterProperties.ts","../../src/filters/property/filterRelations.ts"],"sourcesContent":["import { CrudRequest } from '../../models/crud-request';\r\nimport { CrudRequestWhere } from '../../models/crud-request-where';\r\n\r\n/**\r\n * Ensures a condition is always applied to the query\r\n *\r\n * @param request The parsed request\r\n * @param condition The condition that needs to be applied\r\n */\r\nexport function ensureCondition(request: CrudRequest, condition: CrudRequestWhere): CrudRequest {\r\n // If there is already an \"AND\" condition, we'll just append to that\r\n if (request.where.and) {\r\n return {\r\n ...request,\r\n where: {\r\n and: [\r\n ...request.where.and,\r\n condition,\r\n ]\r\n }\r\n }\r\n }\r\n\r\n return {\r\n ...request,\r\n where: {\r\n and: [\r\n condition,\r\n request.where,\r\n ],\r\n },\r\n };\r\n}\r\n","import { CrudRequest } from '../../models/crud-request';\r\nimport { ensureCondition } from './ensureCondition';\r\nimport { CrudRequestWhereOperator } from '../../models/crud-request-where';\r\n\r\n/**\r\n * Ensures a condition is always applied to the query\r\n *\r\n * @param request The parsed request\r\n * @param entity The property that need to be applied\r\n * @param basePath The field path prefix\r\n */\r\nexport function ensureEqCondition<T extends Record<string, any>>(request: CrudRequest, entity: Partial<T>, basePath: string[] = []): CrudRequest {\r\n for (const key of Object.keys(entity)) {\r\n if (typeof entity[key] === 'object' && !Array.isArray(entity[key])) {\r\n request = ensureEqCondition(request, entity[key], [...basePath, key]);\r\n continue;\r\n }\r\n\r\n request = ensureCondition(request, {\r\n field: [...basePath, key],\r\n operator: CrudRequestWhereOperator.EQ,\r\n value: entity[key],\r\n });\r\n }\r\n\r\n return request;\r\n}\r\n","import { CrudRequest } from '../../models/crud-request';\r\n\r\n/**\r\n * Ensures that the limit will be set following a maximum rule\r\n *\r\n * @param request The parsed request\r\n * @param defaultLimit The default limit number\r\n * @param maxLimit The maximum allowed limit number\r\n */\r\nexport function ensureLimit(request: CrudRequest, defaultLimit: number, maxLimit: number): CrudRequest {\r\n return {\r\n ...request,\r\n limit: Math.min(Math.max(request.limit ?? defaultLimit, 1), maxLimit),\r\n };\r\n}\r\n","import { CrudRequest } from '../../models/crud-request';\r\nimport { CrudRequestWhere } from '../../models/crud-request-where';\r\n\r\n/**\r\n * Filters access to an allowlist of properties and relations.\r\n * No selecting, filtering, sorting and joining can be done on a property that is not listed.\r\n *\r\n * @param request The parsed request\r\n * @param allowedProperties The list of properties (in case of a field path, separated by dot) that will be allowed\r\n */\r\nexport function filterProperties(\r\n request: CrudRequest,\r\n allowedProperties: string[],\r\n): CrudRequest {\r\n let select = request.select;\r\n\r\n if (select.length === 0) {\r\n select = allowedProperties.map(prop => ({ field: prop.split('.') }));\r\n } else {\r\n select = request.select.filter(item => allowedProperties.includes(item.field.join('.')));\r\n }\r\n\r\n const where = filterPropertyAccessWhere(request.where, allowedProperties);\r\n\r\n const order = request.order.filter(item => allowedProperties.includes(item.field.join('.')));\r\n\r\n // TODO allow relations by the first part of field paths\r\n const relations = request.relations.filter(item => allowedProperties.includes(item.field.join('.')));\r\n\r\n return {\r\n ...request,\r\n select,\r\n where,\r\n order,\r\n relations,\r\n };\r\n}\r\n\r\nfunction filterPropertyAccessWhere(\r\n where: CrudRequestWhere,\r\n allowedProperties: string[],\r\n): CrudRequestWhere {\r\n if (where.or) {\r\n return {\r\n or: where.or.map(w => filterPropertyAccessWhere(w, allowedProperties)),\r\n };\r\n }\r\n\r\n if (where.and) {\r\n return {\r\n and: where.and.map(w => filterPropertyAccessWhere(w, allowedProperties)),\r\n };\r\n }\r\n\r\n if (where.field) {\r\n // We'll return an empty AND where if the field is not allowed\r\n if (!allowedProperties.includes(where.field.join('.')))\r\n return { and: [] };\r\n }\r\n\r\n return where;\r\n}\r\n\r\n","import { CrudRequest } from '../../models/crud-request';\r\n\r\n/**\r\n * Filters access to an allowlist of relations.\r\n *\r\n * @param request The parsed request\r\n * @param allowedRelations The list of relations (in case of a field path, separated by dot) that will be allowed\r\n */\r\nexport function filterRelations(\r\n request: CrudRequest,\r\n allowedRelations: string[],\r\n): CrudRequest {\r\n const relations = request.relations.filter(item => allowedRelations.includes(item.field.join('.')));\r\n\r\n return {\r\n ...request,\r\n relations,\r\n };\r\n}\r\n"],"mappings":"+EASO,SAASA,EAAgBC,EAAsBC,EAA0C,CAE9F,OAAID,EAAQ,MAAM,IACT,CACL,GAAGA,EACH,MAAO,CACL,IAAK,CACH,GAAGA,EAAQ,MAAM,IACjBC,CACF,CACF,CACF,EAGK,CACL,GAAGD,EACH,MAAO,CACL,IAAK,CACHC,EACAD,EAAQ,KACV,CACF,CACF,CACF,CAvBgBE,EAAAH,EAAA,mBCET,SAASI,EAAiDC,EAAsBC,EAAoBC,EAAqB,CAAC,EAAgB,CAC/I,QAAWC,KAAO,OAAO,KAAKF,CAAM,EAAG,CACrC,GAAI,OAAOA,EAAOE,CAAG,GAAM,UAAY,CAAC,MAAM,QAAQF,EAAOE,CAAG,CAAC,EAAG,CAClEH,EAAUD,EAAkBC,EAASC,EAAOE,CAAG,EAAG,CAAC,GAAGD,EAAUC,CAAG,CAAC,EACpE,QACF,CAEAH,EAAUI,EAAgBJ,EAAS,CACjC,MAAO,CAAC,GAAGE,EAAUC,CAAG,EACxB,cACA,MAAOF,EAAOE,CAAG,CACnB,CAAC,CACH,CAEA,OAAOH,CACT,CAfgBK,EAAAN,EAAA,qBCFT,SAASO,EAAYC,EAAsBC,EAAsBC,EAA+B,CACrG,MAAO,CACL,GAAGF,EACH,MAAO,KAAK,IAAI,KAAK,IAAIA,EAAQ,OAASC,EAAc,CAAC,EAAGC,CAAQ,CACtE,CACF,CALgBC,EAAAJ,EAAA,eCCT,SAASK,EACdC,EACAC,EACa,CACb,IAAIC,EAASF,EAAQ,OAEjBE,EAAO,SAAW,EACpBA,EAASD,EAAkB,IAAIE,IAAS,CAAE,MAAOA,EAAK,MAAM,GAAG,CAAE,EAAE,EAEnED,EAASF,EAAQ,OAAO,OAAOI,GAAQH,EAAkB,SAASG,EAAK,MAAM,KAAK,GAAG,CAAC,CAAC,EAGzF,IAAMC,EAAQC,EAA0BN,EAAQ,MAAOC,CAAiB,EAElEM,EAAQP,EAAQ,MAAM,OAAOI,GAAQH,EAAkB,SAASG,EAAK,MAAM,KAAK,GAAG,CAAC,CAAC,EAGrFI,EAAYR,EAAQ,UAAU,OAAOI,GAAQH,EAAkB,SAASG,EAAK,MAAM,KAAK,GAAG,CAAC,CAAC,EAEnG,MAAO,CACL,GAAGJ,EACH,OAAAE,EACA,MAAAG,EACA,MAAAE,EACA,UAAAC,CACF,CACF,CA1BgBC,EAAAV,EAAA,oBA4BhB,SAASO,EACPD,EACAJ,EACkB,CAClB,OAAII,EAAM,GACD,CACL,GAAIA,EAAM,GAAG,IAAIK,GAAKJ,EAA0BI,EAAGT,CAAiB,CAAC,CACvE,EAGEI,EAAM,IACD,CACL,IAAKA,EAAM,IAAI,IAAIK,GAAKJ,EAA0BI,EAAGT,CAAiB,CAAC,CACzE,EAGEI,EAAM,OAEJ,CAACJ,EAAkB,SAASI,EAAM,MAAM,KAAK,GAAG,CAAC,EAC5C,CAAE,IAAK,CAAC,CAAE,EAGdA,CACT,CAvBSI,EAAAH,EAAA,6BC9BF,SAASK,EACdC,EACAC,EACa,CACb,IAAMC,EAAYF,EAAQ,UAAU,OAAOG,GAAQF,EAAiB,SAASE,EAAK,MAAM,KAAK,GAAG,CAAC,CAAC,EAElG,MAAO,CACL,GAAGH,EACH,UAAAE,CACF,CACF,CAVgBE,EAAAL,EAAA","names":["ensureCondition","request","condition","__name","ensureEqCondition","request","entity","basePath","key","ensureCondition","__name","ensureLimit","request","defaultLimit","maxLimit","__name","filterProperties","request","allowedProperties","select","prop","item","where","filterPropertyAccessWhere","order","relations","__name","w","filterRelations","request","allowedRelations","relations","item","__name"]}
|
@@ -1,7 +1,7 @@
|
|
1
1
|
import * as _nestjs_common from '@nestjs/common';
|
2
2
|
import { Type } from '@nestjs/common';
|
3
|
-
import { a as RequestParser } from '../../request-parser-
|
4
|
-
import '../../crud-request-
|
3
|
+
import { a as RequestParser } from '../../request-parser-BMkszvGr.mjs';
|
4
|
+
import '../../crud-request-x16CuDRF.mjs';
|
5
5
|
|
6
6
|
declare const CRUD_QUERY_PARSER = "crud-query-parser";
|
7
7
|
/**
|
@@ -1,7 +1,7 @@
|
|
1
1
|
import * as _nestjs_common from '@nestjs/common';
|
2
2
|
import { Type } from '@nestjs/common';
|
3
|
-
import { a as RequestParser } from '../../request-parser-
|
4
|
-
import '../../crud-request-
|
3
|
+
import { a as RequestParser } from '../../request-parser-BxVulcsX.js';
|
4
|
+
import '../../crud-request-x16CuDRF.js';
|
5
5
|
|
6
6
|
declare const CRUD_QUERY_PARSER = "crud-query-parser";
|
7
7
|
/**
|
@@ -1 +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,
|
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\nimport { RequestParser } from '../../models/request-parser';\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 extends RequestParser>(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,0BCI5F,IAAMC,GAAY,IAAM,CAC7B,GAAI,CACF,MAAO,SAAQ,iBAAiB,EAAE,QACpC,MAAgB,CACd,OAAQC,GACC,IAAM,CAAC,CAElB,CACF,GAAG,EAEI,SAASC,EAAwCC,EAA8C,CACpG,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,0BDpBT,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"]}
|
@@ -1 +1 @@
|
|
1
|
-
{"version":3,"sources":["../../../src/helpers/nestjs/decorators.ts","../../../src/helpers/nestjs/utils.ts"],"sourcesContent":["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":"oUAAA,OAAS,mBAAAA,EAAiB,wBAAAC,EAAwC,UAAAC,EAAQ,eAAAC,MAAyB,
|
1
|
+
{"version":3,"sources":["../../../src/helpers/nestjs/decorators.ts","../../../src/helpers/nestjs/utils.ts"],"sourcesContent":["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\nimport { RequestParser } from '../../models/request-parser';\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 extends RequestParser>(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":"oUAAA,OAAS,mBAAAA,EAAiB,wBAAAC,EAAwC,UAAAC,EAAQ,eAAAC,MAAyB,iBCI5F,IAAMC,GAAY,IAAM,CAC7B,GAAI,CACF,MAAO,GAAQ,iBAAiB,EAAE,QACpC,MAAgB,CACd,OAAQC,GACC,IAAM,CAAC,CAElB,CACF,GAAG,EAEI,SAASC,EAAwCC,EAA8C,CACpG,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,0BDpBT,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,OAAOE,EACLC,EAAYT,EAAmBG,CAAM,EACrC,GAAGE,CACL,CACF,CAbgBK,EAAAT,EAAA,QAkBT,IAAMU,EAAmBC,EAC9B,CAACC,EAA2CC,IAA0B,CACpE,IAAMC,EAAUD,EAAI,aAAa,EAAE,WAAW,EACxCX,EAASU,EAAOT,EAAeS,CAAI,EAAIG,EAAsCF,EAAKd,CAAiB,EAEzG,OAAKG,EAWEA,EAAO,MAAMY,EAAQ,KAAK,GAV/B,IAAIE,EAAO,kBAAkB,EAAE,KAAK,yFAAyF,EAEtH,CACL,MAAO,CAAE,IAAK,CAAC,CAAE,EACjB,OAAQ,CAAC,EACT,MAAO,CAAC,EACR,UAAW,CAAC,CACd,EAIJ,CACF","names":["applyDecorators","createParamDecorator","Logger","SetMetadata","ApiQuery","options","createInstance","data","__name","getMetadataFromContext","context","key","targets","target","CRUD_QUERY_PARSER","Crud","parserContract","parser","createInstance","openApi","param","ApiQuery","applyDecorators","SetMetadata","__name","ParseCrudRequest","createParamDecorator","data","ctx","request","getMetadataFromContext","Logger"]}
|
package/dist/index.d.mts
CHANGED
@@ -1,4 +1,4 @@
|
|
1
|
-
export { G as GetManyResult, Q as QueryAdapter } from './query-adapter-
|
2
|
-
export { R as RequestParamValue, a as RequestParser } from './request-parser-
|
3
|
-
export { c as CrudRequest, C as CrudRequestFields, b as CrudRequestOrder, a as CrudRequestRelation, d as CrudRequestWhere, e as CrudRequestWhereAND, g as CrudRequestWhereField, f as CrudRequestWhereOR, i as CrudRequestWhereOperator, h as CrudRequestWhereValueType, F as FieldPath, P as ParsedRequestSelect } from './crud-request-
|
4
|
-
export {
|
1
|
+
export { G as GetManyResult, Q as QueryAdapter } from './query-adapter-CeTK3yxp.mjs';
|
2
|
+
export { R as RequestParamValue, a as RequestParser } from './request-parser-BMkszvGr.mjs';
|
3
|
+
export { c as CrudRequest, C as CrudRequestFields, b as CrudRequestOrder, a as CrudRequestRelation, d as CrudRequestWhere, e as CrudRequestWhereAND, g as CrudRequestWhereField, f as CrudRequestWhereOR, i as CrudRequestWhereOperator, h as CrudRequestWhereValueType, F as FieldPath, P as ParsedRequestSelect } from './crud-request-x16CuDRF.mjs';
|
4
|
+
export { C as CrudRequestWhereBuilder } from './crud-request-where.builder-BwWLx0Bh.mjs';
|
package/dist/index.d.ts
CHANGED
@@ -1,4 +1,4 @@
|
|
1
|
-
export { G as GetManyResult, Q as QueryAdapter } from './query-adapter-
|
2
|
-
export { R as RequestParamValue, a as RequestParser } from './request-parser-
|
3
|
-
export { c as CrudRequest, C as CrudRequestFields, b as CrudRequestOrder, a as CrudRequestRelation, d as CrudRequestWhere, e as CrudRequestWhereAND, g as CrudRequestWhereField, f as CrudRequestWhereOR, i as CrudRequestWhereOperator, h as CrudRequestWhereValueType, F as FieldPath, P as ParsedRequestSelect } from './crud-request-
|
4
|
-
export {
|
1
|
+
export { G as GetManyResult, Q as QueryAdapter } from './query-adapter-CEcyFcWr.js';
|
2
|
+
export { R as RequestParamValue, a as RequestParser } from './request-parser-BxVulcsX.js';
|
3
|
+
export { c as CrudRequest, C as CrudRequestFields, b as CrudRequestOrder, a as CrudRequestRelation, d as CrudRequestWhere, e as CrudRequestWhereAND, g as CrudRequestWhereField, f as CrudRequestWhereOR, i as CrudRequestWhereOperator, h as CrudRequestWhereValueType, F as FieldPath, P as ParsedRequestSelect } from './crud-request-x16CuDRF.js';
|
4
|
+
export { C as CrudRequestWhereBuilder } from './crud-request-where.builder-B5241Aht.js';
|
package/dist/index.js
CHANGED
@@ -1,2 +1,2 @@
|
|
1
|
-
"use strict";var l=Object.defineProperty;var
|
1
|
+
"use strict";var l=Object.defineProperty;var d=Object.getOwnPropertyDescriptor;var R=Object.getOwnPropertyNames;var E=Object.prototype.hasOwnProperty;var o=(r,e)=>l(r,"name",{value:e,configurable:!0});var W=(r,e)=>{for(var n in e)l(r,n,{get:e[n],enumerable:!0})},V=(r,e,n,i)=>{if(e&&typeof e=="object"||typeof e=="function")for(let u of R(e))!E.call(r,u)&&u!==n&&l(r,u,{get:()=>e[u],enumerable:!(i=d(e,u))||i.enumerable});return r};var f=r=>V(l({},"__esModule",{value:!0}),r);var O={};W(O,{CrudRequestWhereBuilder:()=>a,CrudRequestWhereOperator:()=>T});module.exports=f(O);var T=(t=>(t.EQ="eq",t.NEQ="neq",t.GT="gt",t.GTE="gte",t.LT="lt",t.LTE="lte",t.STARTS="starts",t.ENDS="ends",t.CONTAINS="contains",t.NOT_CONTAINS="not_contains",t.IN="in",t.NOT_IN="not_in",t.BETWEEN="between",t.IS_NULL="is_null",t.NOT_NULL="not_null",t.EQ_LOWER="eq_lower",t.NEQ_LOWER="neq_lower",t.STARTS_LOWER="starts_lower",t.ENDS_LOWER="ends_lower",t.CONTAINS_LOWER="contains_lower",t.NOT_CONTAINS_LOWER="not_contains_lower",t.IN_LOWER="in_lower",t.NOT_IN_LOWER="not_in_lower",t))(T||{});function p(r,e){if(e!=null&&!(typeof e=="number"||typeof e=="string"||typeof e=="boolean")&&!(e instanceof Date))throw new Error(`${r} must be a string, number, boolean or null`)}o(p,"ensurePrimitive");function s(r,e,n=0){if(!Array.isArray(e)||e.length<n)throw new Error(`${r} must be an array with at least ${n} items`);return e}o(s,"ensureArray");function h(r,e){if(y(e)&&e!==!0)throw new Error(`${r} must be true, null or undefined`)}o(h,"ensureEmpty");function y(r){return r!=null}o(y,"isValid");var N={eq:"primitive",neq:"primitive",gt:"primitive",lt:"primitive",gte:"primitive",lte:"primitive",starts:"primitive",ends:"primitive",contains:"primitive",not_contains:"primitive",in:"array",not_in:"array",between:"array",is_null:"empty",not_null:"empty",eq_lower:"primitive",neq_lower:"primitive",starts_lower:"primitive",ends_lower:"primitive",contains_lower:"primitive",not_contains_lower:"primitive",in_lower:"primitive",not_in_lower:"primitive"};function I(r){let e=N[r.operator],n="The value of the operator "+r.operator;if(e==="primitive"){p(n,r.value);return}if(e==="array"){s(n,r.value).forEach(u=>p(n+" children",u));return}if(e==="empty"){h(n,r.value);return}}o(I,"validateWhereField");var a=class r{constructor(e={and:[]},n){this.where=e;this.parent=n}static{o(this,"CrudRequestWhereBuilder")}addAnd(){if(!this.where.or)return this;let e={and:[]},n=new r(e,this);return this.where.or.push(e),n}addOr(){if(!this.where.and)return this;let e={or:[]},n=new r(e,this);return this.where.and.push(e),n}addField(e,n,i){let u={field:e,operator:n,value:i};if(I(u),this.where.and)this.where.and.push(u);else if(this.where.or)this.where.or.push(u);else throw new Error("Invalid where");return this}build(){return this.parent?this.parent.build():this.where}};0&&(module.exports={CrudRequestWhereBuilder,CrudRequestWhereOperator});
|
2
2
|
//# sourceMappingURL=index.js.map
|
package/dist/index.js.map
CHANGED
@@ -1 +1 @@
|
|
1
|
-
{"version":3,"sources":["../src/index.ts","../src/models/crud-request-where.ts","../src/utils/parsed-request-where.builder.ts"],"sourcesContent":["// Models\r\nexport * from './models/query-adapter';\r\nexport * from './models/request-parser';\r\n\r\nexport * from './models/get-many-result';\r\nexport * from './models/field-path';\r\nexport * from './models/crud-request';\r\nexport * from './models/crud-request-where';\r\n\r\n// Utilities\r\nexport * from './utils/parsed-request-where.builder';\r\n\r\n","import { FieldPath } from './field-path';\r\n\r\nexport type CrudRequestWhere = CrudRequestWhereAND | CrudRequestWhereOR | CrudRequestWhereField;\r\n\r\nexport interface CrudRequestWhereAND {\r\n field?: never;\r\n or?: never;\r\n and: CrudRequestWhere[];\r\n}\r\n\r\nexport interface CrudRequestWhereOR {\r\n field?: never;\r\n or: CrudRequestWhere[];\r\n and?: never;\r\n}\r\n\r\nexport interface CrudRequestWhereField {\r\n\r\n /**\r\n * Field path\r\n *\r\n * For post.category.name, this would be [\"post\", \"category\", \"name\"]\r\n */\r\n field: FieldPath;\r\n\r\n /**\r\n * The operator of the comparison\r\n */\r\n operator: CrudRequestWhereOperator;\r\n\r\n /**\r\n * The value to compare\r\n */\r\n value: CrudRequestWhereValueType | CrudRequestWhereValueType[];\r\n\r\n or?: never;\r\n and?: never;\r\n}\r\n\r\nexport type CrudRequestWhereValueType = string | number | boolean | Date | null | undefined;\r\n\r\nexport enum CrudRequestWhereOperator {\r\n EQ = 'eq',\r\n NEQ = 'neq',\r\n GT = 'gt',\r\n GTE = 'gte',\r\n LT = 'lt',\r\n LTE = 'lte',\r\n STARTS = 'starts',\r\n ENDS = 'ends',\r\n CONTAINS = 'contains',\r\n NOT_CONTAINS = 'not_contains',\r\n IN = 'in',\r\n NOT_IN = 'not_in',\r\n BETWEEN = 'between',\r\n IS_NULL = 'is_null',\r\n NOT_NULL = 'not_null',\r\n EQ_LOWER = 'eq_lower',\r\n NEQ_LOWER = 'neq_lower',\r\n STARTS_LOWER = 'starts_lower',\r\n ENDS_LOWER = 'ends_lower',\r\n CONTAINS_LOWER = 'contains_lower',\r\n NOT_CONTAINS_LOWER = 'not_contains_lower',\r\n IN_LOWER = 'in_lower',\r\n NOT_IN_LOWER = 'not_in_lower',\r\n}\r\n","import {\r\n CrudRequestWhere,\r\n CrudRequestWhereAND,\r\n CrudRequestWhereField,\r\n CrudRequestWhereOperator,\r\n CrudRequestWhereOR,\r\n CrudRequestWhereValueType\r\n} from '../models/crud-request-where';\r\n\r\n/**\r\n * A helper class that makes it easier to create a CrudRequestWhere\r\n */\r\nexport class ParsedRequestWhereBuilder {\r\n\r\n constructor(\r\n private readonly where: CrudRequestWhereAND | CrudRequestWhereOR = { and: [] },\r\n private readonly parent?: ParsedRequestWhereBuilder,\r\n ) { }\r\n\r\n /**\r\n * Adds an AND bracket\r\n */\r\n public addAnd(): ParsedRequestWhereBuilder {\r\n if (!this.where.or) {\r\n return this;\r\n }\r\n\r\n const inside: CrudRequestWhereAND = { and: [] };\r\n const builder = new ParsedRequestWhereBuilder(inside, this);\r\n\r\n this.where.or.push(inside);\r\n\r\n return builder;\r\n }\r\n\r\n /**\r\n * Adds an OR bracket\r\n */\r\n public addOr(): ParsedRequestWhereBuilder {\r\n if (!this.where.and) {\r\n return this;\r\n }\r\n\r\n const inside: CrudRequestWhereOR = { or: [] };\r\n const builder = new ParsedRequestWhereBuilder(inside, this);\r\n\r\n this.where.and.push(inside);\r\n\r\n return builder;\r\n }\r\n\r\n /**\r\n * Adds a field comparison\r\n *\r\n * @param field The field path\r\n * @param operator The comparison operator\r\n * @param value The value to compare\r\n */\r\n public addField(field: string[], operator: CrudRequestWhereOperator, value: CrudRequestWhereValueType): ParsedRequestWhereBuilder {\r\n const whereField: CrudRequestWhereField = {\r\n field,\r\n operator,\r\n value,\r\n };\r\n\r\n if (this.where.and) {\r\n this.where.and.push(whereField);\r\n } else if (this.where.or) {\r\n this.where.or.push(whereField);\r\n } else {\r\n throw new Error('Invalid where');\r\n }\r\n\r\n return this;\r\n }\r\n\r\n /**\r\n * Constructs the final where condition\r\n */\r\n public build(): CrudRequestWhere {\r\n if (this.parent) {\r\n return this.parent.build();\r\n }\r\n\r\n return this.where;\r\n }\r\n\r\n}\r\n"],"mappings":"4dAAA,IAAAA,EAAA,GAAAC,EAAAD,EAAA,8BAAAE,EAAA,8BAAAC,IAAA,eAAAC,EAAAJ,GCyCO,IAAKK,OACVA,EAAA,GAAK,KACLA,EAAA,IAAM,MACNA,EAAA,GAAK,KACLA,EAAA,IAAM,MACNA,EAAA,GAAK,KACLA,EAAA,IAAM,MACNA,EAAA,OAAS,SACTA,EAAA,KAAO,OACPA,EAAA,SAAW,WACXA,EAAA,aAAe,eACfA,EAAA,GAAK,KACLA,EAAA,OAAS,SACTA,EAAA,QAAU,UACVA,EAAA,QAAU,UACVA,EAAA,SAAW,WACXA,EAAA,SAAW,WACXA,EAAA,UAAY,YACZA,EAAA,aAAe,eACfA,EAAA,WAAa,aACbA,EAAA,eAAiB,iBACjBA,EAAA,mBAAqB,qBACrBA,EAAA,SAAW,WACXA,EAAA,aAAe,eAvBLA,OAAA,IC7BL,IAAMC,EAAN,MAAMC,CAA0B,CAErC,YACmBC,EAAkD,CAAE,IAAK,CAAC,CAAE,EAC5DC,EACjB,CAFiB,WAAAD,EACA,YAAAC,CACf,CAjBN,MAYuC,CAAAC,EAAA,kCAU9B,QAAoC,CACzC,GAAI,CAAC,KAAK,MAAM,GACd,OAAO,KAGT,IAAMC,EAA8B,CAAE,IAAK,CAAC,CAAE,EACxCC,EAAU,IAAIL,EAA0BI,EAAQ,IAAI,EAE1D,YAAK,MAAM,GAAG,KAAKA,CAAM,EAElBC,CACT,CAKO,OAAmC,CACxC,GAAI,CAAC,KAAK,MAAM,IACd,OAAO,KAGT,IAAMD,EAA6B,CAAE,GAAI,CAAC,CAAE,EACtCC,EAAU,IAAIL,EAA0BI,EAAQ,IAAI,EAE1D,YAAK,MAAM,IAAI,KAAKA,CAAM,EAEnBC,CACT,CASO,SAASC,EAAiBC,EAAoCC,EAA6D,CAChI,IAAMC,EAAoC,CACxC,MAAAH,EACA,SAAAC,EACA,MAAAC,CACF,EAEA,GAAI,KAAK,MAAM,IACb,KAAK,MAAM,IAAI,KAAKC,CAAU,UACrB,KAAK,MAAM,GACpB,KAAK,MAAM,GAAG,KAAKA,CAAU,MAE7B,OAAM,IAAI,MAAM,eAAe,EAGjC,OAAO,IACT,CAKO,OAA0B,CAC/B,OAAI,KAAK,OACA,KAAK,OAAO,MAAM,EAGpB,KAAK,KACd,CAEF","names":["src_exports","__export","CrudRequestWhereOperator","ParsedRequestWhereBuilder","__toCommonJS","CrudRequestWhereOperator","ParsedRequestWhereBuilder","_ParsedRequestWhereBuilder","where","parent","__name","inside","builder","field","operator","value","whereField"]}
|
1
|
+
{"version":3,"sources":["../src/index.ts","../src/models/crud-request-where.ts","../src/utils/functions.ts","../src/utils/where.ts","../src/utils/crud-request-where.builder.ts"],"sourcesContent":["// Models\r\nexport * from './models/query-adapter';\r\nexport * from './models/request-parser';\r\n\r\nexport * from './models/get-many-result';\r\nexport * from './models/field-path';\r\nexport * from './models/crud-request';\r\nexport * from './models/crud-request-where';\r\n\r\n// Utilities\r\nexport * from './utils/crud-request-where.builder';\r\n\r\n","import { FieldPath } from './field-path';\r\n\r\nexport type CrudRequestWhere = CrudRequestWhereAND | CrudRequestWhereOR | CrudRequestWhereField;\r\n\r\nexport interface CrudRequestWhereAND {\r\n field?: never;\r\n or?: never;\r\n and: CrudRequestWhere[];\r\n}\r\n\r\nexport interface CrudRequestWhereOR {\r\n field?: never;\r\n or: CrudRequestWhere[];\r\n and?: never;\r\n}\r\n\r\nexport interface CrudRequestWhereField {\r\n\r\n /**\r\n * Field path\r\n *\r\n * For post.category.name, this would be [\"post\", \"category\", \"name\"]\r\n */\r\n field: FieldPath;\r\n\r\n /**\r\n * The operator of the comparison\r\n */\r\n operator: CrudRequestWhereOperator;\r\n\r\n /**\r\n * The value to compare\r\n */\r\n value: CrudRequestWhereValueType | CrudRequestWhereValueType[];\r\n\r\n or?: never;\r\n and?: never;\r\n}\r\n\r\nexport type CrudRequestWhereValueType = string | number | boolean | Date | null | undefined;\r\n\r\nexport enum CrudRequestWhereOperator {\r\n EQ = 'eq',\r\n NEQ = 'neq',\r\n GT = 'gt',\r\n GTE = 'gte',\r\n LT = 'lt',\r\n LTE = 'lte',\r\n STARTS = 'starts',\r\n ENDS = 'ends',\r\n CONTAINS = 'contains',\r\n NOT_CONTAINS = 'not_contains',\r\n IN = 'in',\r\n NOT_IN = 'not_in',\r\n BETWEEN = 'between',\r\n IS_NULL = 'is_null',\r\n NOT_NULL = 'not_null',\r\n EQ_LOWER = 'eq_lower',\r\n NEQ_LOWER = 'neq_lower',\r\n STARTS_LOWER = 'starts_lower',\r\n ENDS_LOWER = 'ends_lower',\r\n CONTAINS_LOWER = 'contains_lower',\r\n NOT_CONTAINS_LOWER = 'not_contains_lower',\r\n IN_LOWER = 'in_lower',\r\n NOT_IN_LOWER = 'not_in_lower',\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 ensureEmpty(fieldName: string, data: any) {\r\n if (isValid(data) && data !== true)\r\n throw new Error(`${fieldName} must be true, null or undefined`);\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\nexport function getOffset(offset: number | undefined, limit?: number, page?: number): number {\r\n return offset ?? (limit && page ? limit * page : 0);\r\n}\r\n","import { CrudRequestWhereField, CrudRequestWhereOperator } from '../models/crud-request-where';\r\nimport { ensureArray, ensureEmpty, ensurePrimitive } from './functions';\r\n\r\nexport enum WhereOperatorValueType {\r\n PRIMITIVE = 'primitive',\r\n ARRAY = 'array',\r\n EMPTY = 'empty'\r\n}\r\n\r\nconst operatorValueTypes: Record<CrudRequestWhereOperator, WhereOperatorValueType> = {\r\n [CrudRequestWhereOperator.EQ]: WhereOperatorValueType.PRIMITIVE,\r\n [CrudRequestWhereOperator.NEQ]: WhereOperatorValueType.PRIMITIVE,\r\n [CrudRequestWhereOperator.GT]: WhereOperatorValueType.PRIMITIVE,\r\n [CrudRequestWhereOperator.LT]: WhereOperatorValueType.PRIMITIVE,\r\n [CrudRequestWhereOperator.GTE]: WhereOperatorValueType.PRIMITIVE,\r\n [CrudRequestWhereOperator.LTE]: WhereOperatorValueType.PRIMITIVE,\r\n [CrudRequestWhereOperator.STARTS]: WhereOperatorValueType.PRIMITIVE,\r\n [CrudRequestWhereOperator.ENDS]: WhereOperatorValueType.PRIMITIVE,\r\n [CrudRequestWhereOperator.CONTAINS]: WhereOperatorValueType.PRIMITIVE,\r\n [CrudRequestWhereOperator.NOT_CONTAINS]: WhereOperatorValueType.PRIMITIVE,\r\n [CrudRequestWhereOperator.IN]: WhereOperatorValueType.ARRAY,\r\n [CrudRequestWhereOperator.NOT_IN]: WhereOperatorValueType.ARRAY,\r\n [CrudRequestWhereOperator.BETWEEN]: WhereOperatorValueType.ARRAY,\r\n [CrudRequestWhereOperator.IS_NULL]: WhereOperatorValueType.EMPTY,\r\n [CrudRequestWhereOperator.NOT_NULL]: WhereOperatorValueType.EMPTY,\r\n [CrudRequestWhereOperator.EQ_LOWER]: WhereOperatorValueType.PRIMITIVE,\r\n [CrudRequestWhereOperator.NEQ_LOWER]: WhereOperatorValueType.PRIMITIVE,\r\n [CrudRequestWhereOperator.STARTS_LOWER]: WhereOperatorValueType.PRIMITIVE,\r\n [CrudRequestWhereOperator.ENDS_LOWER]: WhereOperatorValueType.PRIMITIVE,\r\n [CrudRequestWhereOperator.CONTAINS_LOWER]: WhereOperatorValueType.PRIMITIVE,\r\n [CrudRequestWhereOperator.NOT_CONTAINS_LOWER]: WhereOperatorValueType.PRIMITIVE,\r\n [CrudRequestWhereOperator.IN_LOWER]: WhereOperatorValueType.PRIMITIVE,\r\n [CrudRequestWhereOperator.NOT_IN_LOWER]: WhereOperatorValueType.PRIMITIVE,\r\n};\r\n\r\nexport function getWhereOperatorValueType(op: CrudRequestWhereOperator): WhereOperatorValueType {\r\n return operatorValueTypes[op];\r\n}\r\n\r\nexport function validateWhereField(where: CrudRequestWhereField): void {\r\n const type = operatorValueTypes[where.operator];\r\n const name = 'The value of the operator ' + where.operator;\r\n\r\n if (type === WhereOperatorValueType.PRIMITIVE) {\r\n ensurePrimitive(name, where.value);\r\n\r\n return;\r\n }\r\n\r\n if (type === WhereOperatorValueType.ARRAY) {\r\n const items = ensureArray(name, where.value);\r\n\r\n items.forEach(item => ensurePrimitive(name + ' children', item));\r\n\r\n return;\r\n }\r\n\r\n if (type === WhereOperatorValueType.EMPTY) {\r\n ensureEmpty(name, where.value);\r\n\r\n return;\r\n }\r\n}\r\n","import {\r\n CrudRequestWhere,\r\n CrudRequestWhereAND,\r\n CrudRequestWhereField,\r\n CrudRequestWhereOperator,\r\n CrudRequestWhereOR,\r\n CrudRequestWhereValueType\r\n} from '../models/crud-request-where';\r\nimport { validateWhereField } from './where';\r\n\r\n/**\r\n * A helper class that makes it easier to create a CrudRequestWhere\r\n */\r\nexport class CrudRequestWhereBuilder {\r\n\r\n constructor(\r\n private readonly where: CrudRequestWhereAND | CrudRequestWhereOR = { and: [] },\r\n private readonly parent?: CrudRequestWhereBuilder,\r\n ) { }\r\n\r\n /**\r\n * Adds an AND bracket\r\n */\r\n public addAnd(): CrudRequestWhereBuilder {\r\n if (!this.where.or) {\r\n return this;\r\n }\r\n\r\n const inside: CrudRequestWhereAND = { and: [] };\r\n const builder = new CrudRequestWhereBuilder(inside, this);\r\n\r\n this.where.or.push(inside);\r\n\r\n return builder;\r\n }\r\n\r\n /**\r\n * Adds an OR bracket\r\n */\r\n public addOr(): CrudRequestWhereBuilder {\r\n if (!this.where.and) {\r\n return this;\r\n }\r\n\r\n const inside: CrudRequestWhereOR = { or: [] };\r\n const builder = new CrudRequestWhereBuilder(inside, this);\r\n\r\n this.where.and.push(inside);\r\n\r\n return builder;\r\n }\r\n\r\n /**\r\n * Adds a field comparison\r\n *\r\n * @param field The field path\r\n * @param operator The comparison operator\r\n * @param value The value to compare\r\n */\r\n public addField(\r\n field: string[],\r\n operator: CrudRequestWhereOperator,\r\n value: CrudRequestWhereValueType | CrudRequestWhereValueType[],\r\n ): CrudRequestWhereBuilder {\r\n const whereField: CrudRequestWhereField = {\r\n field,\r\n operator,\r\n value,\r\n };\r\n\r\n validateWhereField(whereField);\r\n\r\n if (this.where.and) {\r\n this.where.and.push(whereField);\r\n } else if (this.where.or) {\r\n this.where.or.push(whereField);\r\n } else {\r\n throw new Error('Invalid where');\r\n }\r\n\r\n return this;\r\n }\r\n\r\n /**\r\n * Constructs the final where condition\r\n */\r\n public build(): CrudRequestWhere {\r\n if (this.parent) {\r\n return this.parent.build();\r\n }\r\n\r\n return this.where;\r\n }\r\n\r\n}\r\n"],"mappings":"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","names":["src_exports","__export","CrudRequestWhereBuilder","CrudRequestWhereOperator","__toCommonJS","CrudRequestWhereOperator","ensurePrimitive","fieldName","data","__name","ensureArray","minLength","ensureEmpty","isValid","value","operatorValueTypes","validateWhereField","where","type","operatorValueTypes","name","ensurePrimitive","ensureArray","item","ensureEmpty","__name","CrudRequestWhereBuilder","_CrudRequestWhereBuilder","where","parent","__name","inside","builder","field","operator","value","whereField","validateWhereField"]}
|
package/dist/index.mjs
CHANGED
@@ -1,2 +1,2 @@
|
|
1
|
-
var
|
1
|
+
var I=Object.defineProperty;var u=(t,e)=>I(t,"name",{value:e,configurable:!0});var T=(r=>(r.EQ="eq",r.NEQ="neq",r.GT="gt",r.GTE="gte",r.LT="lt",r.LTE="lte",r.STARTS="starts",r.ENDS="ends",r.CONTAINS="contains",r.NOT_CONTAINS="not_contains",r.IN="in",r.NOT_IN="not_in",r.BETWEEN="between",r.IS_NULL="is_null",r.NOT_NULL="not_null",r.EQ_LOWER="eq_lower",r.NEQ_LOWER="neq_lower",r.STARTS_LOWER="starts_lower",r.ENDS_LOWER="ends_lower",r.CONTAINS_LOWER="contains_lower",r.NOT_CONTAINS_LOWER="not_contains_lower",r.IN_LOWER="in_lower",r.NOT_IN_LOWER="not_in_lower",r))(T||{});function i(t,e){if(e!=null&&!(typeof e=="number"||typeof e=="string"||typeof e=="boolean")&&!(e instanceof Date))throw new Error(`${t} must be a string, number, boolean or null`)}u(i,"ensurePrimitive");function p(t,e,n=0){if(!Array.isArray(e)||e.length<n)throw new Error(`${t} must be an array with at least ${n} items`);return e}u(p,"ensureArray");function a(t,e){if(d(e)&&e!==!0)throw new Error(`${t} must be true, null or undefined`)}u(a,"ensureEmpty");function d(t){return t!=null}u(d,"isValid");var R={eq:"primitive",neq:"primitive",gt:"primitive",lt:"primitive",gte:"primitive",lte:"primitive",starts:"primitive",ends:"primitive",contains:"primitive",not_contains:"primitive",in:"array",not_in:"array",between:"array",is_null:"empty",not_null:"empty",eq_lower:"primitive",neq_lower:"primitive",starts_lower:"primitive",ends_lower:"primitive",contains_lower:"primitive",not_contains_lower:"primitive",in_lower:"primitive",not_in_lower:"primitive"};function s(t){let e=R[t.operator],n="The value of the operator "+t.operator;if(e==="primitive"){i(n,t.value);return}if(e==="array"){p(n,t.value).forEach(o=>i(n+" children",o));return}if(e==="empty"){a(n,t.value);return}}u(s,"validateWhereField");var h=class t{constructor(e={and:[]},n){this.where=e;this.parent=n}static{u(this,"CrudRequestWhereBuilder")}addAnd(){if(!this.where.or)return this;let e={and:[]},n=new t(e,this);return this.where.or.push(e),n}addOr(){if(!this.where.and)return this;let e={or:[]},n=new t(e,this);return this.where.and.push(e),n}addField(e,n,l){let o={field:e,operator:n,value:l};if(s(o),this.where.and)this.where.and.push(o);else if(this.where.or)this.where.or.push(o);else throw new Error("Invalid where");return this}build(){return this.parent?this.parent.build():this.where}};export{h as CrudRequestWhereBuilder,T as CrudRequestWhereOperator};
|
2
2
|
//# sourceMappingURL=index.mjs.map
|