arkos 1.3.2-canary.4 → 1.3.3-beta.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +8 -4
- package/dist/cjs/app.js +39 -4
- package/dist/cjs/app.js.map +1 -1
- package/dist/cjs/exports/utils/index.js +5 -25
- package/dist/cjs/exports/utils/index.js.map +1 -1
- package/dist/cjs/modules/auth/auth.controller.js +18 -0
- package/dist/cjs/modules/auth/auth.controller.js.map +1 -1
- package/dist/cjs/modules/auth/auth.router.js +2 -0
- package/dist/cjs/modules/auth/auth.router.js.map +1 -1
- package/dist/cjs/modules/base/base.controller.js +49 -11
- package/dist/cjs/modules/base/base.controller.js.map +1 -1
- package/dist/cjs/modules/base/base.middlewares.js.map +1 -1
- package/dist/cjs/modules/base/base.service.js +108 -0
- package/dist/cjs/modules/base/base.service.js.map +1 -1
- package/dist/cjs/modules/base/types/base.service.types.js.map +1 -1
- package/dist/cjs/modules/base/utils/helpers/base.router.helpers.js +29 -14
- package/dist/cjs/modules/base/utils/helpers/base.router.helpers.js.map +1 -1
- package/dist/cjs/modules/base/utils/helpers/base.service.helpers.js +2 -2
- package/dist/cjs/modules/base/utils/helpers/base.service.helpers.js.map +1 -1
- package/dist/cjs/modules/base/utils/router-validator.js +1 -4
- package/dist/cjs/modules/base/utils/router-validator.js.map +1 -1
- package/dist/cjs/modules/base/utils/service-hooks-manager.js.map +1 -1
- package/dist/cjs/modules/debugger/debugger.service.js +82 -0
- package/dist/cjs/modules/debugger/debugger.service.js.map +1 -0
- package/dist/cjs/modules/debugger/utils/loaded-components-logger.js +55 -0
- package/dist/cjs/modules/debugger/utils/loaded-components-logger.js.map +1 -0
- package/dist/cjs/modules/file-upload/file-upload.controller.js +4 -0
- package/dist/cjs/modules/file-upload/file-upload.controller.js.map +1 -1
- package/dist/cjs/modules/file-upload/file-upload.router.js +3 -1
- package/dist/cjs/modules/file-upload/file-upload.router.js.map +1 -1
- package/dist/cjs/modules/swagger/swagger.router.js +2 -1
- package/dist/cjs/modules/swagger/swagger.router.js.map +1 -1
- package/dist/cjs/modules/swagger/utils/helpers/get-authentication-json-schema-paths.js +2 -1
- package/dist/cjs/modules/swagger/utils/helpers/get-authentication-json-schema-paths.js.map +1 -1
- package/dist/cjs/modules/swagger/utils/helpers/json-schema-generators/generate-class-validator-json-schemas.js +12 -8
- package/dist/cjs/modules/swagger/utils/helpers/json-schema-generators/generate-class-validator-json-schemas.js.map +1 -1
- package/dist/cjs/modules/swagger/utils/helpers/json-schema-generators/prisma-models/generate-prisma-model-main-routes-paths.js +3 -3
- package/dist/cjs/modules/swagger/utils/helpers/json-schema-generators/prisma-models/generate-prisma-model-main-routes-paths.js.map +1 -1
- package/dist/cjs/modules/swagger/utils/helpers/json-schema-generators/prisma-models/generate-prisma-model-parent-routes-paths.js +2 -1
- package/dist/cjs/modules/swagger/utils/helpers/json-schema-generators/prisma-models/generate-prisma-model-parent-routes-paths.js.map +1 -1
- package/dist/cjs/modules/swagger/utils/helpers/missing-json-schemas-generator.js +3 -3
- package/dist/cjs/modules/swagger/utils/helpers/missing-json-schemas-generator.js.map +1 -1
- package/dist/cjs/modules/swagger/utils/helpers/swagger.router.helpers.js.map +1 -1
- package/dist/cjs/server.js +11 -0
- package/dist/cjs/server.js.map +1 -1
- package/dist/cjs/types/arkos-config.js.map +1 -1
- package/dist/cjs/types/index.js.map +1 -1
- package/dist/cjs/utils/cli/generate.js +9 -4
- package/dist/cjs/utils/cli/generate.js.map +1 -1
- package/dist/cjs/utils/cli/prisma-generate.js +1 -2
- package/dist/cjs/utils/cli/prisma-generate.js.map +1 -1
- package/dist/cjs/utils/cli/utils/cli.helpers.js +1 -1
- package/dist/cjs/utils/cli/utils/template-generator/templates/auth-configs-template.js +34 -10
- package/dist/cjs/utils/cli/utils/template-generator/templates/auth-configs-template.js.map +1 -1
- package/dist/cjs/utils/cli/utils/template-generator/templates/controller-template.js +2 -6
- package/dist/cjs/utils/cli/utils/template-generator/templates/controller-template.js.map +1 -1
- package/dist/cjs/utils/cli/utils/template-generator/templates/hooks-template.js +31 -36
- package/dist/cjs/utils/cli/utils/template-generator/templates/hooks-template.js.map +1 -1
- package/dist/cjs/utils/cli/utils/template-generator/templates/middlewares-template.js +0 -2
- package/dist/cjs/utils/cli/utils/template-generator/templates/middlewares-template.js.map +1 -1
- package/dist/cjs/utils/cli/utils/template-generator/templates/query-options-template.js +1 -1
- package/dist/cjs/utils/cli/utils/template-generator/templates/query-options-template.js.map +1 -1
- package/dist/cjs/utils/cli/utils/template-generator/templates/router-template.js +7 -10
- package/dist/cjs/utils/cli/utils/template-generator/templates/router-template.js.map +1 -1
- package/dist/cjs/utils/dynamic-loader.js +11 -2
- package/dist/cjs/utils/dynamic-loader.js.map +1 -1
- package/dist/cjs/utils/features/api.features.js +130 -73
- package/dist/cjs/utils/features/api.features.js.map +1 -1
- package/dist/cjs/utils/helpers/deepmerge.helper.js.map +1 -1
- package/dist/cjs/utils/helpers/prisma.helpers.js +8 -4
- package/dist/cjs/utils/helpers/prisma.helpers.js.map +1 -1
- package/dist/cjs/utils/prisma/prisma-json-schema-generator.js.map +1 -1
- package/dist/cjs/utils/sheu.js +11 -0
- package/dist/cjs/utils/sheu.js.map +1 -1
- package/dist/esm/app.js +6 -4
- package/dist/esm/app.js.map +1 -1
- package/dist/esm/exports/utils/index.js +2 -2
- package/dist/esm/exports/utils/index.js.map +1 -1
- package/dist/esm/modules/auth/auth.controller.js +18 -0
- package/dist/esm/modules/auth/auth.controller.js.map +1 -1
- package/dist/esm/modules/auth/auth.router.js +3 -1
- package/dist/esm/modules/auth/auth.router.js.map +1 -1
- package/dist/esm/modules/base/base.controller.js +49 -11
- package/dist/esm/modules/base/base.controller.js.map +1 -1
- package/dist/esm/modules/base/base.middlewares.js.map +1 -1
- package/dist/esm/modules/base/base.service.js +108 -0
- package/dist/esm/modules/base/base.service.js.map +1 -1
- package/dist/esm/modules/base/types/base.service.types.js.map +1 -1
- package/dist/esm/modules/base/utils/helpers/base.router.helpers.js +29 -15
- package/dist/esm/modules/base/utils/helpers/base.router.helpers.js.map +1 -1
- package/dist/esm/modules/base/utils/helpers/base.service.helpers.js +2 -2
- package/dist/esm/modules/base/utils/helpers/base.service.helpers.js.map +1 -1
- package/dist/esm/modules/base/utils/router-validator.js +1 -4
- package/dist/esm/modules/base/utils/router-validator.js.map +1 -1
- package/dist/esm/modules/base/utils/service-hooks-manager.js.map +1 -1
- package/dist/esm/modules/debugger/debugger.service.js +77 -0
- package/dist/esm/modules/debugger/debugger.service.js.map +1 -0
- package/dist/esm/modules/debugger/utils/loaded-components-logger.js +50 -0
- package/dist/esm/modules/debugger/utils/loaded-components-logger.js.map +1 -0
- package/dist/esm/modules/file-upload/file-upload.controller.js +4 -0
- package/dist/esm/modules/file-upload/file-upload.controller.js.map +1 -1
- package/dist/esm/modules/file-upload/file-upload.router.js +3 -1
- package/dist/esm/modules/file-upload/file-upload.router.js.map +1 -1
- package/dist/esm/modules/swagger/swagger.router.js +2 -1
- package/dist/esm/modules/swagger/swagger.router.js.map +1 -1
- package/dist/esm/modules/swagger/utils/helpers/get-authentication-json-schema-paths.js +2 -1
- package/dist/esm/modules/swagger/utils/helpers/get-authentication-json-schema-paths.js.map +1 -1
- package/dist/esm/modules/swagger/utils/helpers/json-schema-generators/generate-class-validator-json-schemas.js +12 -8
- package/dist/esm/modules/swagger/utils/helpers/json-schema-generators/generate-class-validator-json-schemas.js.map +1 -1
- package/dist/esm/modules/swagger/utils/helpers/json-schema-generators/prisma-models/generate-prisma-model-main-routes-paths.js +3 -3
- package/dist/esm/modules/swagger/utils/helpers/json-schema-generators/prisma-models/generate-prisma-model-main-routes-paths.js.map +1 -1
- package/dist/esm/modules/swagger/utils/helpers/json-schema-generators/prisma-models/generate-prisma-model-parent-routes-paths.js +2 -1
- package/dist/esm/modules/swagger/utils/helpers/json-schema-generators/prisma-models/generate-prisma-model-parent-routes-paths.js.map +1 -1
- package/dist/esm/modules/swagger/utils/helpers/missing-json-schemas-generator.js +3 -3
- package/dist/esm/modules/swagger/utils/helpers/missing-json-schemas-generator.js.map +1 -1
- package/dist/esm/modules/swagger/utils/helpers/swagger.router.helpers.js.map +1 -1
- package/dist/esm/server.js +11 -0
- package/dist/esm/server.js.map +1 -1
- package/dist/esm/types/arkos-config.js.map +1 -1
- package/dist/esm/types/index.js.map +1 -1
- package/dist/esm/utils/cli/generate.js +9 -4
- package/dist/esm/utils/cli/generate.js.map +1 -1
- package/dist/esm/utils/cli/prisma-generate.js +1 -2
- package/dist/esm/utils/cli/prisma-generate.js.map +1 -1
- package/dist/esm/utils/cli/utils/cli.helpers.js +1 -1
- package/dist/esm/utils/cli/utils/template-generator/templates/auth-configs-template.js +34 -10
- package/dist/esm/utils/cli/utils/template-generator/templates/auth-configs-template.js.map +1 -1
- package/dist/esm/utils/cli/utils/template-generator/templates/controller-template.js +2 -6
- package/dist/esm/utils/cli/utils/template-generator/templates/controller-template.js.map +1 -1
- package/dist/esm/utils/cli/utils/template-generator/templates/hooks-template.js +31 -36
- package/dist/esm/utils/cli/utils/template-generator/templates/hooks-template.js.map +1 -1
- package/dist/esm/utils/cli/utils/template-generator/templates/middlewares-template.js +0 -2
- package/dist/esm/utils/cli/utils/template-generator/templates/middlewares-template.js.map +1 -1
- package/dist/esm/utils/cli/utils/template-generator/templates/query-options-template.js +1 -1
- package/dist/esm/utils/cli/utils/template-generator/templates/query-options-template.js.map +1 -1
- package/dist/esm/utils/cli/utils/template-generator/templates/router-template.js +7 -7
- package/dist/esm/utils/cli/utils/template-generator/templates/router-template.js.map +1 -1
- package/dist/esm/utils/dynamic-loader.js +11 -2
- package/dist/esm/utils/dynamic-loader.js.map +1 -1
- package/dist/esm/utils/features/api.features.js +130 -72
- package/dist/esm/utils/features/api.features.js.map +1 -1
- package/dist/esm/utils/helpers/deepmerge.helper.js.map +1 -1
- package/dist/esm/utils/helpers/prisma.helpers.js +8 -4
- package/dist/esm/utils/helpers/prisma.helpers.js.map +1 -1
- package/dist/esm/utils/prisma/prisma-json-schema-generator.js.map +1 -1
- package/dist/esm/utils/sheu.js +11 -0
- package/dist/esm/utils/sheu.js.map +1 -1
- package/dist/types/exports/utils/index.d.ts +2 -2
- package/dist/types/modules/base/base.controller.d.ts +2 -0
- package/dist/types/modules/base/base.service.d.ts +5 -0
- package/dist/types/modules/base/types/base.service.types.d.ts +8 -8
- package/dist/types/modules/base/utils/helpers/base.router.helpers.d.ts +3 -1
- package/dist/types/modules/base/utils/service-hooks-manager.d.ts +1 -1
- package/dist/types/modules/debugger/debugger.service.d.ts +15 -0
- package/dist/types/modules/debugger/utils/loaded-components-logger.d.ts +9 -0
- package/dist/types/types/arkos-config.d.ts +14 -0
- package/dist/types/types/index.d.ts +3 -0
- package/dist/types/utils/dynamic-loader.d.ts +33 -13
- package/dist/types/utils/features/api.features.d.ts +3 -5
- package/dist/types/utils/sheu.d.ts +8 -0
- package/package.json +1 -1
|
@@ -2,6 +2,7 @@ import deepmerge from "../helpers/deepmerge.helper.js";
|
|
|
2
2
|
import { parseQueryParamsWithModifiers } from "../helpers/api.features.helpers.js";
|
|
3
3
|
import AppError from "../../modules/error-handler/utils/app-error.js";
|
|
4
4
|
import { getPrismaInstance } from "../helpers/prisma.helpers.js";
|
|
5
|
+
import debuggerService from "../../modules/debugger/debugger.service.js";
|
|
5
6
|
export default class APIFeatures {
|
|
6
7
|
constructor(req, modelName) {
|
|
7
8
|
this.filters = {};
|
|
@@ -20,82 +21,97 @@ export default class APIFeatures {
|
|
|
20
21
|
"where",
|
|
21
22
|
"prismaQueryOptions",
|
|
22
23
|
"ignoredFields",
|
|
24
|
+
"select",
|
|
25
|
+
"omit",
|
|
23
26
|
];
|
|
24
27
|
if (req) {
|
|
25
28
|
const { filters = "{}", ...restOfQuery } = req.query;
|
|
26
29
|
this.req = req;
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
const { filters = "{}", ...restOfQuery } = req.query;
|
|
37
|
-
this.req = req;
|
|
38
|
-
this.searchParams = deepmerge(parseQueryParamsWithModifiers(restOfQuery), parseQueryParamsWithModifiers(JSON.parse(filters)));
|
|
39
|
-
req.finalPrismaQueryOptions = this.searchParams;
|
|
30
|
+
let parsedFilters = {};
|
|
31
|
+
try {
|
|
32
|
+
parsedFilters = JSON.parse(filters);
|
|
33
|
+
}
|
|
34
|
+
catch (error) {
|
|
35
|
+
throw new AppError("Invalid req.query.filters JSON format", 400);
|
|
36
|
+
}
|
|
37
|
+
this.searchParams = deepmerge(parseQueryParamsWithModifiers(restOfQuery), parseQueryParamsWithModifiers(parsedFilters));
|
|
38
|
+
debuggerService.handleTransformedQueryLog(this.searchParams);
|
|
40
39
|
}
|
|
41
40
|
if (modelName)
|
|
42
41
|
this.modelName = modelName;
|
|
43
42
|
this.filters = { ...this.filters };
|
|
44
|
-
return this;
|
|
45
43
|
}
|
|
46
44
|
filter() {
|
|
47
45
|
if (!this.req)
|
|
48
|
-
throw new Error("Trying to use APIFeatures.filter() without passing request on class constructor or APIFeatures.setup() method.
|
|
46
|
+
throw new Error("Trying to use APIFeatures.filter() without passing request on class constructor or APIFeatures.setup() method.");
|
|
49
47
|
const searchableFields = [];
|
|
50
48
|
const queryObj = { ...this.searchParams };
|
|
51
49
|
this.excludedFields.forEach((el) => delete queryObj[el]);
|
|
50
|
+
const topLevelOR = queryObj.OR;
|
|
51
|
+
const topLevelAND = queryObj.AND;
|
|
52
|
+
delete queryObj.OR;
|
|
53
|
+
delete queryObj.AND;
|
|
52
54
|
const whereObj = { ...this.req.params, ...queryObj };
|
|
53
55
|
const whereLogicalOperatorFilters = Object.keys(whereObj).map((key) => ({
|
|
54
56
|
[key]: whereObj[key],
|
|
55
57
|
}));
|
|
56
|
-
let whereOptions =
|
|
57
|
-
|
|
58
|
+
let whereOptions = {};
|
|
59
|
+
if (whereLogicalOperatorFilters.length > 0) {
|
|
60
|
+
whereOptions = {
|
|
58
61
|
[this.req.query?.filterMode ?? "OR"]: whereLogicalOperatorFilters,
|
|
62
|
+
};
|
|
63
|
+
}
|
|
64
|
+
if (topLevelOR) {
|
|
65
|
+
if (whereOptions.OR) {
|
|
66
|
+
whereOptions.OR = [...whereOptions.OR, ...topLevelOR];
|
|
59
67
|
}
|
|
60
|
-
|
|
68
|
+
else {
|
|
69
|
+
whereOptions.OR = topLevelOR;
|
|
70
|
+
}
|
|
71
|
+
}
|
|
72
|
+
if (topLevelAND) {
|
|
73
|
+
if (whereOptions.AND) {
|
|
74
|
+
whereOptions.AND = [...whereOptions.AND, ...topLevelAND];
|
|
75
|
+
}
|
|
76
|
+
else {
|
|
77
|
+
whereOptions.AND = topLevelAND;
|
|
78
|
+
}
|
|
79
|
+
}
|
|
61
80
|
if (!!this.searchParams.search) {
|
|
62
81
|
const prisma = getPrismaInstance();
|
|
63
|
-
if (this.modelName)
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
}
|
|
82
|
+
if (!this.modelName)
|
|
83
|
+
throw new Error("Model name is required for search functionality");
|
|
84
|
+
if (!prisma[this.modelName] || !prisma[this.modelName].fields)
|
|
85
|
+
throw new Error(`Model '${this.modelName}' not found or has no fields`);
|
|
86
|
+
Object.keys(prisma[this.modelName].fields).forEach((key) => {
|
|
87
|
+
const field = prisma[this.modelName].fields[key];
|
|
88
|
+
if (field?.typeName === "String" &&
|
|
89
|
+
key !== "id" &&
|
|
90
|
+
key !== "password" &&
|
|
91
|
+
!field.isList &&
|
|
92
|
+
!key?.includes?.("Id") &&
|
|
93
|
+
!key?.includes?.("ID")) {
|
|
94
|
+
searchableFields.push({
|
|
95
|
+
[`${key}`]: {
|
|
96
|
+
contains: this.searchParams.search,
|
|
97
|
+
mode: "insensitive",
|
|
98
|
+
},
|
|
99
|
+
});
|
|
100
|
+
}
|
|
101
|
+
});
|
|
102
|
+
if (searchableFields.length > 0) {
|
|
103
|
+
whereOptions = deepmerge({
|
|
104
|
+
OR: searchableFields,
|
|
105
|
+
}, whereOptions);
|
|
106
|
+
}
|
|
83
107
|
}
|
|
84
108
|
const firstMerge = deepmerge({
|
|
85
109
|
where: whereOptions,
|
|
86
110
|
}, this.req.prismaQueryOptions || {});
|
|
87
111
|
this.filters = deepmerge(firstMerge, this.filters);
|
|
112
|
+
this.searchParams = deepmerge(this.searchParams || {}, this.req.prismaQueryOptions || {});
|
|
88
113
|
return this;
|
|
89
114
|
}
|
|
90
|
-
search() {
|
|
91
|
-
if (this.searchParams?.search) {
|
|
92
|
-
this.filters = deepmerge(this.filters, {
|
|
93
|
-
where: {
|
|
94
|
-
OR: [],
|
|
95
|
-
},
|
|
96
|
-
});
|
|
97
|
-
}
|
|
98
|
-
}
|
|
99
115
|
sort() {
|
|
100
116
|
if (this.searchParams.sort) {
|
|
101
117
|
const sortBy = this.searchParams?.sort
|
|
@@ -108,6 +124,9 @@ export default class APIFeatures {
|
|
|
108
124
|
return this;
|
|
109
125
|
}
|
|
110
126
|
limitFields() {
|
|
127
|
+
let finalSelect = {};
|
|
128
|
+
let finalInclude = {};
|
|
129
|
+
let finalOmit = {};
|
|
111
130
|
if (this.searchParams?.fields) {
|
|
112
131
|
const fields = this.searchParams.fields.split(",");
|
|
113
132
|
const regularFields = fields.filter((field) => !field.startsWith("+") && !field.startsWith("-"));
|
|
@@ -117,46 +136,85 @@ export default class APIFeatures {
|
|
|
117
136
|
const excludeFields = fields
|
|
118
137
|
.filter((field) => field.startsWith("-"))
|
|
119
138
|
.map((field) => field.substring(1));
|
|
120
|
-
let selection = {};
|
|
121
139
|
if (regularFields.length > 0) {
|
|
122
|
-
|
|
140
|
+
finalSelect = regularFields.reduce((acc, field) => {
|
|
123
141
|
acc[field] = true;
|
|
124
142
|
return acc;
|
|
125
143
|
}, {});
|
|
126
144
|
}
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
selection[field] = false;
|
|
134
|
-
});
|
|
135
|
-
}
|
|
136
|
-
this.filters = {
|
|
137
|
-
...this.filters,
|
|
138
|
-
select: selection,
|
|
139
|
-
};
|
|
140
|
-
if (this.filters.include) {
|
|
141
|
-
delete this.filters.include;
|
|
142
|
-
}
|
|
145
|
+
includeFields.forEach((field) => {
|
|
146
|
+
finalInclude[field] = true;
|
|
147
|
+
});
|
|
148
|
+
excludeFields.forEach((field) => {
|
|
149
|
+
finalOmit[field] = true;
|
|
150
|
+
});
|
|
143
151
|
}
|
|
152
|
+
if (this.searchParams.include || this.filters.include)
|
|
153
|
+
finalInclude = deepmerge(finalInclude, deepmerge(this.filters?.include || {}, this.searchParams?.include || {}));
|
|
154
|
+
if (this.searchParams.select || this.filters.include)
|
|
155
|
+
finalSelect = deepmerge(finalSelect, deepmerge(this.filters?.select || {}, this.searchParams?.select || {}));
|
|
156
|
+
if (this.searchParams.omit || this.filters.omit)
|
|
157
|
+
finalOmit = deepmerge(finalOmit, deepmerge(this.filters?.omit || {}, this.searchParams?.omit || {}));
|
|
158
|
+
if (Object.keys(finalSelect).length > 0 &&
|
|
159
|
+
Object.keys(finalInclude).length > 0) {
|
|
160
|
+
finalSelect = deepmerge(finalSelect, finalInclude);
|
|
161
|
+
finalInclude = {};
|
|
162
|
+
delete this.filters.include;
|
|
163
|
+
delete this.searchParams.include;
|
|
164
|
+
}
|
|
165
|
+
this._validateNoPasswordExposure(finalSelect, finalInclude, finalOmit);
|
|
166
|
+
if (finalOmit.password === false)
|
|
167
|
+
throw new AppError("Cannot disable password omission protection", 400);
|
|
168
|
+
if (this.modelName?.toLowerCase?.() === "user")
|
|
169
|
+
finalOmit.password = true;
|
|
170
|
+
if (Object.keys(finalSelect).length > 0)
|
|
171
|
+
this.filters.select = finalSelect;
|
|
172
|
+
if (Object.keys(finalInclude).length > 0)
|
|
173
|
+
this.filters.include = finalInclude;
|
|
174
|
+
if (Object.keys(finalOmit).length > 0)
|
|
175
|
+
this.filters.omit = finalOmit;
|
|
144
176
|
if (this.searchParams?.addFields || this.searchParams?.removeFields) {
|
|
145
|
-
throw new AppError("The addFields and removeFields parameters are deprecated.
|
|
177
|
+
throw new AppError("The addFields and removeFields parameters are deprecated.", 400);
|
|
146
178
|
}
|
|
147
179
|
return this;
|
|
148
180
|
}
|
|
181
|
+
_validateNoPasswordExposure(select, include, omit) {
|
|
182
|
+
const checkForPassword = (obj, path = []) => {
|
|
183
|
+
for (const [key, value] of Object.entries(obj)) {
|
|
184
|
+
const currentPath = [...path, key];
|
|
185
|
+
if (key === "password" &&
|
|
186
|
+
(this.modelName?.toLowerCase() === "user" ||
|
|
187
|
+
currentPath.at(-3)?.toLowerCase?.() === "user")) {
|
|
188
|
+
if (value === false)
|
|
189
|
+
throw new AppError("Cannot disable password omission protection", 400, { ...obj }, "CannotExposeUserPassword");
|
|
190
|
+
if (value === true && !omit?.["password"])
|
|
191
|
+
throw new AppError("User password exposure detected", 403, {}, "UserPasswordExposureDetected");
|
|
192
|
+
}
|
|
193
|
+
if (typeof value === "object" &&
|
|
194
|
+
value !== null &&
|
|
195
|
+
!Array.isArray(value)) {
|
|
196
|
+
checkForPassword(value, currentPath);
|
|
197
|
+
}
|
|
198
|
+
}
|
|
199
|
+
};
|
|
200
|
+
checkForPassword(select);
|
|
201
|
+
checkForPassword(include);
|
|
202
|
+
checkForPassword(omit);
|
|
203
|
+
}
|
|
149
204
|
paginate() {
|
|
150
|
-
const
|
|
151
|
-
|
|
152
|
-
|
|
205
|
+
const paginationOptions = (() => {
|
|
206
|
+
if (this.searchParams.limit === "all")
|
|
207
|
+
return {};
|
|
208
|
+
const page = parseInt(this.searchParams.page, 10) || 1;
|
|
209
|
+
const limit = parseInt(this.searchParams.limit, 10) || 30;
|
|
210
|
+
const skip = (page - 1) * limit;
|
|
211
|
+
return { skip, take: limit };
|
|
212
|
+
})();
|
|
153
213
|
this.filters = {
|
|
154
214
|
...this.filters,
|
|
155
|
-
|
|
156
|
-
take: limit,
|
|
215
|
+
...paginationOptions,
|
|
157
216
|
};
|
|
158
217
|
return this;
|
|
159
218
|
}
|
|
160
219
|
}
|
|
161
|
-
export const apiFeatures = new APIFeatures();
|
|
162
220
|
//# sourceMappingURL=api.features.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"api.features.js","sourceRoot":"","sources":["../../../../src/utils/features/api.features.ts"],"names":[],"mappings":"AACA,OAAO,SAAS,MAAM,6BAA6B,CAAC;AACpD,OAAO,EAAE,6BAA6B,EAAE,MAAM,iCAAiC,CAAC;AAChF,OAAO,QAAQ,MAAM,6CAA6C,CAAC;AACnE,OAAO,EAAE,iBAAiB,EAAE,MAAM,2BAA2B,CAAC;AAK9D,MAAM,CAAC,OAAO,OAAO,WAAW;IAuB9B,YAAY,GAAa,EAAE,SAAqB;QAnBhD,YAAO,GAAQ,EAAE,CAAC;QAClB,0BAAqB,GAAQ,EAAE,CAAC;QAEhC,mBAAc,GAAG;YACf,MAAM;YACN,SAAS;YACT,MAAM;YACN,OAAO;YACP,QAAQ;YACR,WAAW;YACX,cAAc;YACd,QAAQ;YACR,SAAS;YACT,YAAY;YACZ,OAAO;YACP,oBAAoB;YACpB,eAAe;SAChB,CAAC;QAGA,IAAI,GAAG,EAAE,CAAC;YACR,MAAM,EAAE,OAAO,GAAG,IAAI,EAAE,GAAG,WAAW,EAAE,GAAG,GAAG,CAAC,KAAK,CAAC;YACrD,IAAI,CAAC,GAAG,GAAG,GAAG,CAAC;YACf,IAAI,CAAC,YAAY,GAAG,SAAS,CAC3B,6BAA6B,CAAC,WAAW,CAAC,EAC1C,6BAA6B,CAAC,IAAI,CAAC,KAAK,CAAC,OAAiB,CAAC,CAAC,CAC7D,CAAC;YACD,GAAW,CAAC,uBAAuB,GAAG,IAAI,CAAC,YAAY,CAAC;QAC3D,CAAC;QAED,IAAI,SAAS;YAAE,IAAI,CAAC,SAAS,GAAG,SAAS,CAAC;QAC1C,IAAI,CAAC,OAAO,GAAG,EAAE,GAAG,IAAI,CAAC,OAAO,EAAE,CAAC;IACrC,CAAC;IAED,KAAK,CAAC,GAAY,EAAE,SAAqB;QACvC,IAAI,GAAG,EAAE,CAAC;YACR,MAAM,EAAE,OAAO,GAAG,IAAI,EAAE,GAAG,WAAW,EAAE,GAAG,GAAG,CAAC,KAAK,CAAC;YACrD,IAAI,CAAC,GAAG,GAAG,GAAG,CAAC;YACf,IAAI,CAAC,YAAY,GAAG,SAAS,CAC3B,6BAA6B,CAAC,WAAW,CAAC,EAC1C,6BAA6B,CAAC,IAAI,CAAC,KAAK,CAAC,OAAiB,CAAC,CAAC,CAC7D,CAAC;YACD,GAAW,CAAC,uBAAuB,GAAG,IAAI,CAAC,YAAY,CAAC;QAC3D,CAAC;QACD,IAAI,SAAS;YAAE,IAAI,CAAC,SAAS,GAAG,SAAS,CAAC;QAC1C,IAAI,CAAC,OAAO,GAAG,EAAE,GAAG,IAAI,CAAC,OAAO,EAAE,CAAC;QAEnC,OAAO,IAAI,CAAC;IACd,CAAC;IAED,MAAM;QACJ,IAAI,CAAC,IAAI,CAAC,GAAG;YACX,MAAM,IAAI,KAAK,CACb,0LAA0L,CAC3L,CAAC;QACJ,MAAM,gBAAgB,GAA0B,EAAE,CAAC;QAEnD,MAAM,QAAQ,GAAG,EAAE,GAAG,IAAI,CAAC,YAAY,EAAE,CAAC;QAE1C,IAAI,CAAC,cAAc,CAAC,OAAO,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC,OAAO,QAAQ,CAAC,EAAE,CAAC,CAAC,CAAC;QAEzD,MAAM,QAAQ,GAAG,EAAE,GAAG,IAAI,CAAC,GAAG,CAAC,MAAM,EAAE,GAAG,QAAQ,EAAE,CAAC;QACrD,MAAM,2BAA2B,GAAG,MAAM,CAAC,IAAI,CAAC,QAAQ,CAAC,CAAC,GAAG,CAAC,CAAC,GAAG,EAAE,EAAE,CAAC,CAAC;YACtE,CAAC,GAAG,CAAC,EAAE,QAAQ,CAAC,GAAG,CAAC;SACrB,CAAC,CAAC,CAAC;QAEJ,IAAI,YAAY,GACd,2BAA2B,CAAC,MAAM,GAAG,CAAC;YACpC,CAAC,CAAC;gBACE,CAAE,IAAI,CAAC,GAAG,CAAC,KAAK,EAAE,UAAqB,IAAI,IAAI,CAAC,EAC9C,2BAA2B;aAC9B;YACH,CAAC,CAAC,EAAE,CAAC;QAET,IAAI,CAAC,CAAC,IAAI,CAAC,YAAY,CAAC,MAAM,EAAE,CAAC;YAC/B,MAAM,MAAM,GAAG,iBAAiB,EAAE,CAAC;YAEnC,IAAI,IAAI,CAAC,SAAS;gBAChB,MAAM,CAAC,IAAI,CAAE,MAAc,CAAC,IAAI,CAAC,SAAS,CAAC,CAAC,MAAM,CAAC,CAAC,OAAO,CAAC,CAAC,GAAG,EAAE,EAAE;oBAClE,MAAM,KAAK,GAAK,MAAc,CAAC,IAAI,CAAC,SAAU,CAAC,CAAC,MAAc,CAAC,GAAG,CAAC,CAAC;oBACpE,IACE,KAAK,EAAE,QAAQ,KAAK,QAAQ;wBAC5B,GAAG,KAAK,IAAI;wBACZ,GAAG,KAAK,UAAU;wBAClB,CAAC,KAAK,CAAC,MAAM;wBACb,CAAC,GAAG,EAAE,QAAQ,EAAE,CAAC,IAAI,CAAC;wBACtB,CAAC,GAAG,EAAE,QAAQ,EAAE,CAAC,IAAI,CAAC,EACtB,CAAC;wBACD,gBAAgB,CAAC,IAAI,CAAC;4BACpB,CAAC,GAAG,GAAG,EAAE,CAAC,EAAE;gCACV,QAAQ,EAAE,IAAI,CAAC,YAAY,CAAC,MAAM;gCAClC,IAAI,EAAE,aAAa;6BACpB;yBACF,CAAC,CAAC;oBACL,CAAC;gBACH,CAAC,CAAC,CAAC;YAEL,YAAY,GAAG,SAAS,CACtB;gBACE,EAAE,EAAE,gBAAgB;aACrB,EACD,YAAY,CACb,CAAC;QACJ,CAAC;QAED,MAAM,UAAU,GAAG,SAAS,CAC1B;YACE,KAAK,EAAE,YAAY;SACpB,EACD,IAAI,CAAC,GAAG,CAAC,kBAAkB,IAAI,EAAE,CAClC,CAAC;QAEF,IAAI,CAAC,OAAO,GAAG,SAAS,CAAC,UAAU,EAAE,IAAI,CAAC,OAAO,CAAC,CAAC;QACnD,OAAO,IAAI,CAAC;IACd,CAAC;IAED,MAAM;QACJ,IAAI,IAAI,CAAC,YAAY,EAAE,MAAM,EAAE,CAAC;YAC9B,IAAI,CAAC,OAAO,GAAG,SAAS,CAAC,IAAI,CAAC,OAAO,EAAE;gBACrC,KAAK,EAAE;oBACL,EAAE,EAAE,EAAE;iBACP;aACF,CAAC,CAAC;QACL,CAAC;IACH,CAAC;IAED,IAAI;QACF,IAAI,IAAI,CAAC,YAAY,CAAC,IAAI,EAAE,CAAC;YAC3B,MAAM,MAAM,GAAG,IAAI,CAAC,YAAY,EAAE,IAAI;gBACpC,EAAE,KAAK,CAAC,GAAG,CAAC;gBACZ,EAAE,GAAG,CAAC,CAAC,KAAa,EAAE,EAAE,CAAC,CAAC;gBACxB,CAAC,KAAK,CAAC,UAAU,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,KAAK,CAAC,SAAS,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,KAAK,CAAC,EAClD,KAAK,CAAC,UAAU,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,KAAK;aACzC,CAAC,CAAC,CAAC;YACN,IAAI,CAAC,OAAO,GAAG,SAAS,CAAC,IAAI,CAAC,OAAO,EAAE,EAAE,OAAO,EAAE,MAAM,EAAE,CAAC,CAAC;QAC9D,CAAC;QAED,OAAO,IAAI,CAAC;IACd,CAAC;IAED,WAAW;QACT,IAAI,IAAI,CAAC,YAAY,EAAE,MAAM,EAAE,CAAC;YAC9B,MAAM,MAAM,GAAG,IAAI,CAAC,YAAY,CAAC,MAAM,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC;YAGnD,MAAM,aAAa,GAAG,MAAM,CAAC,MAAM,CACjC,CAAC,KAAa,EAAE,EAAE,CAAC,CAAC,KAAK,CAAC,UAAU,CAAC,GAAG,CAAC,IAAI,CAAC,KAAK,CAAC,UAAU,CAAC,GAAG,CAAC,CACpE,CAAC;YACF,MAAM,aAAa,GAAG,MAAM;iBACzB,MAAM,CAAC,CAAC,KAAa,EAAE,EAAE,CAAC,KAAK,CAAC,UAAU,CAAC,GAAG,CAAC,CAAC;iBAChD,GAAG,CAAC,CAAC,KAAa,EAAE,EAAE,CAAC,KAAK,CAAC,SAAS,CAAC,CAAC,CAAC,CAAC,CAAC;YAC9C,MAAM,aAAa,GAAG,MAAM;iBACzB,MAAM,CAAC,CAAC,KAAa,EAAE,EAAE,CAAC,KAAK,CAAC,UAAU,CAAC,GAAG,CAAC,CAAC;iBAChD,GAAG,CAAC,CAAC,KAAa,EAAE,EAAE,CAAC,KAAK,CAAC,SAAS,CAAC,CAAC,CAAC,CAAC,CAAC;YAG9C,IAAI,SAAS,GAAwB,EAAE,CAAC;YAGxC,IAAI,aAAa,CAAC,MAAM,GAAG,CAAC,EAAE,CAAC;gBAC7B,SAAS,GAAG,aAAa,CAAC,MAAM,CAC9B,CAAC,GAAwB,EAAE,KAAa,EAAE,EAAE;oBAC1C,GAAG,CAAC,KAAK,CAAC,GAAG,IAAI,CAAC;oBAClB,OAAO,GAAG,CAAC;gBACb,CAAC,EACD,EAAyB,CAC1B,CAAC;YACJ,CAAC;iBAEI,CAAC;gBAEJ,SAAS,GAAG,IAAI,CAAC,OAAO,CAAC,OAAO,IAAI,EAAE,CAAC;gBAGvC,aAAa,CAAC,OAAO,CAAC,CAAC,KAAa,EAAE,EAAE;oBACtC,SAAS,CAAC,KAAK,CAAC,GAAG,IAAI,CAAC;gBAC1B,CAAC,CAAC,CAAC;gBAGH,aAAa,CAAC,OAAO,CAAC,CAAC,KAAa,EAAE,EAAE;oBACtC,SAAS,CAAC,KAAK,CAAC,GAAG,KAAK,CAAC;gBAC3B,CAAC,CAAC,CAAC;YACL,CAAC;YAGD,IAAI,CAAC,OAAO,GAAG;gBACb,GAAG,IAAI,CAAC,OAAO;gBACf,MAAM,EAAE,SAAS;aAClB,CAAC;YAGF,IAAI,IAAI,CAAC,OAAO,CAAC,OAAO,EAAE,CAAC;gBACzB,OAAO,IAAI,CAAC,OAAO,CAAC,OAAO,CAAC;YAC9B,CAAC;QACH,CAAC;QAGD,IAAI,IAAI,CAAC,YAAY,EAAE,SAAS,IAAI,IAAI,CAAC,YAAY,EAAE,YAAY,EAAE,CAAC;YACpE,MAAM,IAAI,QAAQ,CAChB,4GAA4G,EAC5G,GAAG,CACJ,CAAC;QACJ,CAAC;QAED,OAAO,IAAI,CAAC;IACd,CAAC;IAED,QAAQ;QACN,MAAM,IAAI,GAAG,QAAQ,CAAC,IAAI,CAAC,YAAY,CAAC,IAAI,EAAE,EAAE,CAAC,IAAI,CAAC,CAAC;QACvD,MAAM,KAAK,GAAG,QAAQ,CAAC,IAAI,CAAC,YAAY,CAAC,KAAK,EAAE,EAAE,CAAC,IAAI,EAAE,CAAC;QAC1D,MAAM,IAAI,GAAG,CAAC,IAAI,GAAG,CAAC,CAAC,GAAG,KAAK,CAAC;QAEhC,IAAI,CAAC,OAAO,GAAG;YACb,GAAG,IAAI,CAAC,OAAO;YACf,IAAI;YACJ,IAAI,EAAE,KAAK;SACZ,CAAC;QACF,OAAO,IAAI,CAAC;IACd,CAAC;CACF;AAED,MAAM,CAAC,MAAM,WAAW,GAAG,IAAI,WAAW,EAAE,CAAC","sourcesContent":["import { Request } from \"express\";\nimport deepmerge from \"../helpers/deepmerge.helper\";\nimport { parseQueryParamsWithModifiers } from \"../helpers/api.features.helpers\";\nimport AppError from \"../../modules/error-handler/utils/app-error\";\nimport { getPrismaInstance } from \"../helpers/prisma.helpers\";\nimport { ArkosRequest } from \"../../types\";\n\ntype ModelName = string;\n\nexport default class APIFeatures {\n req?: ArkosRequest;\n searchParams: any; // The query string parameters from the request\n searchParamsWithModifiers: any; // The query string parameters from the request\n filters: any = {};\n reqFiltersSearchParam: any = {};\n modelName?: ModelName;\n excludedFields = [\n \"page\",\n \"filters\",\n \"sort\",\n \"limit\",\n \"fields\",\n \"addFields\",\n \"removeFields\",\n \"search\",\n \"include\",\n \"filterMode\",\n \"where\",\n \"prismaQueryOptions\",\n \"ignoredFields\",\n ];\n\n constructor(req?: Request, modelName?: ModelName) {\n if (req) {\n const { filters = \"{}\", ...restOfQuery } = req.query;\n this.req = req;\n this.searchParams = deepmerge(\n parseQueryParamsWithModifiers(restOfQuery),\n parseQueryParamsWithModifiers(JSON.parse(filters as string))\n );\n (req as any).finalPrismaQueryOptions = this.searchParams;\n }\n\n if (modelName) this.modelName = modelName;\n this.filters = { ...this.filters };\n }\n\n setup(req: Request, modelName?: ModelName) {\n if (req) {\n const { filters = \"{}\", ...restOfQuery } = req.query;\n this.req = req;\n this.searchParams = deepmerge(\n parseQueryParamsWithModifiers(restOfQuery),\n parseQueryParamsWithModifiers(JSON.parse(filters as string))\n );\n (req as any).finalPrismaQueryOptions = this.searchParams;\n }\n if (modelName) this.modelName = modelName;\n this.filters = { ...this.filters };\n\n return this;\n }\n\n filter() {\n if (!this.req)\n throw new Error(\n \"Trying to use APIFeatures.filter() without passing request on class constructor or APIFeatures.setup() method. read more about at www.arkosjs.com/docs/advanced-guide/api-features-class\"\n );\n const searchableFields: Record<string, any>[] = [];\n\n const queryObj = { ...this.searchParams };\n\n this.excludedFields.forEach((el) => delete queryObj[el]);\n\n const whereObj = { ...this.req.params, ...queryObj };\n const whereLogicalOperatorFilters = Object.keys(whereObj).map((key) => ({\n [key]: whereObj[key],\n }));\n\n let whereOptions =\n whereLogicalOperatorFilters.length > 0\n ? {\n [(this.req.query?.filterMode as string) ?? \"OR\"]:\n whereLogicalOperatorFilters,\n }\n : {};\n\n if (!!this.searchParams.search) {\n const prisma = getPrismaInstance();\n\n if (this.modelName)\n Object.keys((prisma as any)[this.modelName].fields).forEach((key) => {\n const field = ((prisma as any)[this.modelName!].fields as any)[key];\n if (\n field?.typeName === \"String\" &&\n key !== \"id\" &&\n key !== \"password\" &&\n !field.isList &&\n !key?.includes?.(\"Id\") &&\n !key?.includes?.(\"ID\")\n ) {\n searchableFields.push({\n [`${key}`]: {\n contains: this.searchParams.search,\n mode: \"insensitive\",\n },\n });\n }\n });\n\n whereOptions = deepmerge(\n {\n OR: searchableFields,\n },\n whereOptions\n );\n }\n\n const firstMerge = deepmerge(\n {\n where: whereOptions,\n },\n this.req.prismaQueryOptions || {}\n );\n\n this.filters = deepmerge(firstMerge, this.filters);\n return this;\n }\n\n search() {\n if (this.searchParams?.search) {\n this.filters = deepmerge(this.filters, {\n where: {\n OR: [],\n },\n });\n }\n }\n\n sort() {\n if (this.searchParams.sort) {\n const sortBy = this.searchParams?.sort\n ?.split(\",\")\n ?.map((field: string) => ({\n [field.startsWith(\"-\") ? field.substring(1) : field]:\n field.startsWith(\"-\") ? \"desc\" : \"asc\",\n }));\n this.filters = deepmerge(this.filters, { orderBy: sortBy });\n }\n\n return this;\n }\n\n limitFields() {\n if (this.searchParams?.fields) {\n const fields = this.searchParams.fields.split(\",\");\n\n // Separate fields into includes, excludes, and regular fields\n const regularFields = fields.filter(\n (field: string) => !field.startsWith(\"+\") && !field.startsWith(\"-\")\n );\n const includeFields = fields\n .filter((field: string) => field.startsWith(\"+\"))\n .map((field: string) => field.substring(1));\n const excludeFields = fields\n .filter((field: string) => field.startsWith(\"-\"))\n .map((field: string) => field.substring(1));\n\n // Create selection object based on field type\n let selection: Record<string, any> = {};\n\n // If regular fields exist, use them as the base selection\n if (regularFields.length > 0) {\n selection = regularFields.reduce(\n (acc: Record<string, any>, field: string) => {\n acc[field] = true;\n return acc;\n },\n {} as Record<string, any>\n );\n }\n // Otherwise, use include fields as additions to any existing included fields\n else {\n // Start with current include fields if they exist\n selection = this.filters.include || {};\n\n // Add any explicitly included fields\n includeFields.forEach((field: string) => {\n selection[field] = true;\n });\n\n // Add any explicitly excluded fields\n excludeFields.forEach((field: string) => {\n selection[field] = false;\n });\n }\n\n // Apply the selection to filters\n this.filters = {\n ...this.filters,\n select: selection,\n };\n\n // Remove the include filter as it's now part of select\n if (this.filters.include) {\n delete this.filters.include;\n }\n }\n\n // Remove any references to the now-unused parameters\n if (this.searchParams?.addFields || this.searchParams?.removeFields) {\n throw new AppError(\n \"The addFields and removeFields parameters are deprecated. Please use fields with + and - prefixes instead.\",\n 400\n );\n }\n\n return this;\n }\n\n paginate() {\n const page = parseInt(this.searchParams.page, 10) || 1;\n const limit = parseInt(this.searchParams.limit, 10) || 30;\n const skip = (page - 1) * limit;\n\n this.filters = {\n ...this.filters,\n skip,\n take: limit,\n };\n return this;\n }\n}\n\nexport const apiFeatures = new APIFeatures();\n"]}
|
|
1
|
+
{"version":3,"file":"api.features.js","sourceRoot":"","sources":["../../../../src/utils/features/api.features.ts"],"names":[],"mappings":"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","sourcesContent":["import { Request } from \"express\";\nimport deepmerge from \"../helpers/deepmerge.helper\";\nimport { parseQueryParamsWithModifiers } from \"../helpers/api.features.helpers\";\nimport AppError from \"../../modules/error-handler/utils/app-error\";\nimport { getPrismaInstance } from \"../helpers/prisma.helpers\";\nimport { ArkosRequest } from \"../../types\";\nimport debuggerService from \"../../modules/debugger/debugger.service\";\n\ntype ModelName = string;\n\nexport default class APIFeatures {\n req?: ArkosRequest;\n searchParams: any;\n searchParamsWithModifiers: any;\n filters: Record<string, any> = {};\n reqFiltersSearchParam: any = {};\n modelName?: ModelName;\n excludedFields = [\n \"page\",\n \"filters\",\n \"sort\",\n \"limit\",\n \"fields\",\n \"addFields\",\n \"removeFields\",\n \"search\",\n \"include\",\n \"filterMode\",\n \"where\",\n \"prismaQueryOptions\",\n \"ignoredFields\",\n \"select\",\n \"omit\",\n ];\n\n constructor(req?: Request, modelName?: ModelName) {\n if (req) {\n const { filters = \"{}\", ...restOfQuery } = req.query;\n this.req = req;\n\n let parsedFilters = {};\n try {\n parsedFilters = JSON.parse(filters as string);\n } catch (error) {\n throw new AppError(\"Invalid req.query.filters JSON format\", 400);\n }\n\n this.searchParams = deepmerge(\n parseQueryParamsWithModifiers(restOfQuery),\n parseQueryParamsWithModifiers(parsedFilters)\n );\n\n debuggerService.handleTransformedQueryLog(this.searchParams);\n }\n\n if (modelName) this.modelName = modelName;\n this.filters = { ...this.filters };\n }\n\n filter() {\n if (!this.req)\n throw new Error(\n \"Trying to use APIFeatures.filter() without passing request on class constructor or APIFeatures.setup() method.\"\n );\n\n const searchableFields: Record<string, any>[] = [];\n const queryObj = { ...this.searchParams };\n\n this.excludedFields.forEach((el) => delete queryObj[el]);\n\n const topLevelOR = queryObj.OR;\n const topLevelAND = queryObj.AND;\n delete queryObj.OR;\n delete queryObj.AND;\n\n const whereObj = { ...this.req.params, ...queryObj };\n const whereLogicalOperatorFilters = Object.keys(whereObj).map((key) => ({\n [key]: whereObj[key],\n }));\n\n let whereOptions: any = {};\n\n if (whereLogicalOperatorFilters.length > 0) {\n whereOptions = {\n [(this.req.query?.filterMode as string) ?? \"OR\"]:\n whereLogicalOperatorFilters,\n };\n }\n\n if (topLevelOR) {\n if (whereOptions.OR) {\n whereOptions.OR = [...whereOptions.OR, ...topLevelOR];\n } else {\n whereOptions.OR = topLevelOR;\n }\n }\n\n if (topLevelAND) {\n if (whereOptions.AND) {\n whereOptions.AND = [...whereOptions.AND, ...topLevelAND];\n } else {\n whereOptions.AND = topLevelAND;\n }\n }\n\n if (!!this.searchParams.search) {\n const prisma = getPrismaInstance();\n\n if (!this.modelName)\n throw new Error(\"Model name is required for search functionality\");\n\n if (!prisma[this.modelName] || !prisma[this.modelName].fields)\n throw new Error(`Model '${this.modelName}' not found or has no fields`);\n\n Object.keys((prisma as any)[this.modelName].fields).forEach((key) => {\n const field = ((prisma as any)[this.modelName!].fields as any)[key];\n if (\n field?.typeName === \"String\" &&\n key !== \"id\" &&\n key !== \"password\" &&\n !field.isList &&\n !key?.includes?.(\"Id\") &&\n !key?.includes?.(\"ID\")\n ) {\n searchableFields.push({\n [`${key}`]: {\n contains: this.searchParams.search,\n mode: \"insensitive\",\n },\n });\n }\n });\n\n if (searchableFields.length > 0) {\n whereOptions = deepmerge(\n {\n OR: searchableFields,\n },\n whereOptions\n );\n }\n }\n\n const firstMerge = deepmerge(\n {\n where: whereOptions,\n },\n this.req.prismaQueryOptions || {}\n );\n\n this.filters = deepmerge(firstMerge, this.filters);\n this.searchParams = deepmerge(\n this.searchParams || {},\n this.req.prismaQueryOptions || {}\n );\n\n return this;\n }\n\n sort() {\n if (this.searchParams.sort) {\n const sortBy = this.searchParams?.sort\n ?.split(\",\")\n ?.map((field: string) => ({\n [field.startsWith(\"-\") ? field.substring(1) : field]:\n field.startsWith(\"-\") ? \"desc\" : \"asc\",\n }));\n this.filters = deepmerge(this.filters, { orderBy: sortBy });\n }\n\n return this;\n }\n\n limitFields() {\n let finalSelect: Record<string, any> = {};\n let finalInclude: Record<string, any> = {};\n let finalOmit: Record<string, any> = {};\n\n if (this.searchParams?.fields) {\n const fields = this.searchParams.fields.split(\",\");\n\n const regularFields = fields.filter(\n (field: string) => !field.startsWith(\"+\") && !field.startsWith(\"-\")\n );\n const includeFields = fields\n .filter((field: string) => field.startsWith(\"+\"))\n .map((field: string) => field.substring(1));\n const excludeFields = fields\n .filter((field: string) => field.startsWith(\"-\"))\n .map((field: string) => field.substring(1));\n\n if (regularFields.length > 0) {\n finalSelect = regularFields.reduce(\n (acc: Record<string, any>, field: string) => {\n acc[field] = true;\n return acc;\n },\n {} as Record<string, any>\n );\n }\n\n includeFields.forEach((field: string) => {\n finalInclude[field] = true;\n });\n\n excludeFields.forEach((field: string) => {\n finalOmit[field] = true;\n });\n }\n\n if (this.searchParams.include || this.filters.include)\n finalInclude = deepmerge(\n finalInclude,\n deepmerge(this.filters?.include || {}, this.searchParams?.include || {})\n );\n\n if (this.searchParams.select || this.filters.include)\n finalSelect = deepmerge(\n finalSelect,\n deepmerge(this.filters?.select || {}, this.searchParams?.select || {})\n );\n\n if (this.searchParams.omit || this.filters.omit)\n finalOmit = deepmerge(\n finalOmit,\n deepmerge(this.filters?.omit || {}, this.searchParams?.omit || {})\n );\n\n if (\n Object.keys(finalSelect).length > 0 &&\n Object.keys(finalInclude).length > 0\n ) {\n finalSelect = deepmerge(finalSelect, finalInclude);\n finalInclude = {};\n delete this.filters.include;\n delete this.searchParams.include;\n }\n\n this._validateNoPasswordExposure(finalSelect, finalInclude, finalOmit);\n\n // ALWAYS protect password field in finalOmit\n if (finalOmit.password === false)\n throw new AppError(\"Cannot disable password omission protection\", 400);\n\n if (this.modelName?.toLowerCase?.() === \"user\") finalOmit.password = true;\n\n if (Object.keys(finalSelect).length > 0) this.filters.select = finalSelect;\n\n if (Object.keys(finalInclude).length > 0)\n this.filters.include = finalInclude;\n\n if (Object.keys(finalOmit).length > 0) this.filters.omit = finalOmit;\n\n if (this.searchParams?.addFields || this.searchParams?.removeFields) {\n throw new AppError(\n \"The addFields and removeFields parameters are deprecated.\",\n 400\n );\n }\n\n return this;\n }\n\n private _validateNoPasswordExposure(\n select: Record<string, any>,\n include: Record<string, any>,\n omit: Record<string, any>\n ) {\n const checkForPassword = (\n obj: Record<string, any>,\n path: string[] = []\n ) => {\n for (const [key, value] of Object.entries(obj)) {\n const currentPath = [...path, key];\n\n if (\n key === \"password\" &&\n (this.modelName?.toLowerCase() === \"user\" ||\n currentPath.at(-3)?.toLowerCase?.() === \"user\")\n ) {\n if (value === false)\n throw new AppError(\n \"Cannot disable password omission protection\",\n 400,\n { ...obj },\n \"CannotExposeUserPassword\"\n );\n\n if (value === true && !omit?.[\"password\"])\n throw new AppError(\n \"User password exposure detected\",\n 403,\n {},\n \"UserPasswordExposureDetected\"\n );\n }\n\n if (\n typeof value === \"object\" &&\n value !== null &&\n !Array.isArray(value)\n ) {\n checkForPassword(value, currentPath);\n }\n }\n };\n\n checkForPassword(select);\n checkForPassword(include);\n checkForPassword(omit);\n }\n\n paginate(): APIFeatures {\n const paginationOptions = (() => {\n if (this.searchParams.limit === \"all\") return {};\n\n const page = parseInt(this.searchParams.page, 10) || 1;\n const limit = parseInt(this.searchParams.limit, 10) || 30;\n const skip = (page - 1) * limit;\n\n return { skip, take: limit };\n })();\n\n this.filters = {\n ...this.filters,\n ...paginationOptions,\n };\n return this;\n }\n}\n"]}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"deepmerge.helper.js","sourceRoot":"","sources":["../../../../src/utils/helpers/deepmerge.helper.ts"],"names":[],"mappings":"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
|
|
1
|
+
{"version":3,"file":"deepmerge.helper.js","sourceRoot":"","sources":["../../../../src/utils/helpers/deepmerge.helper.ts"],"names":[],"mappings":"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","sourcesContent":["declare namespace deepmerge {\n export interface Options {\n arrayMerge?(\n target: any[],\n source: any[],\n options?: ArrayMergeOptions\n ): any[];\n clone?: boolean;\n customMerge?: (\n key: string,\n options?: Options\n ) => ((x: any, y: any) => any) | undefined;\n isMergeableObject?(value: object): boolean;\n cloneUnlessOtherwiseSpecified?(value: any, options?: Options): any;\n }\n\n export interface ArrayMergeOptions extends Options {\n cloneUnlessOtherwiseSpecified(value: any, options?: Options): any;\n }\n}\n\nfunction isMergeableObject(value: any): boolean {\n return isNonNullObject(value) && !isSpecial(value);\n}\n\nfunction isNonNullObject(value: any): boolean {\n return !!value && typeof value === \"object\";\n}\n\nfunction isSpecial(value: any): boolean {\n const stringValue = Object.prototype.toString.call(value);\n\n return stringValue === \"[object RegExp]\" || stringValue === \"[object Date]\";\n}\n\nfunction emptyTarget(val: any): any {\n return Array.isArray(val) ? [] : {};\n}\n\nfunction getKeys(target: any): (string | symbol)[] {\n const objectKeys = Object.keys(target);\n const symbolKeys = getEnumerableOwnPropertySymbols(target);\n return [...objectKeys, ...symbolKeys];\n}\n\nfunction getEnumerableOwnPropertySymbols(target: any): symbol[] {\n return Object.getOwnPropertySymbols\n ? Object.getOwnPropertySymbols(target).filter(function (symbol) {\n return Object.propertyIsEnumerable.call(target, symbol);\n })\n : [];\n}\n\nfunction cloneUnlessOtherwiseSpecified(\n value: any,\n options: deepmerge.Options\n): any {\n return options.clone !== false && options.isMergeableObject?.(value)\n ? deepmerge(emptyTarget(value), value, options)\n : value;\n}\n\nfunction defaultArrayMerge(\n target: any[],\n source: any[],\n options: deepmerge.ArrayMergeOptions\n): any[] {\n return target.concat(source).map(function (element) {\n return options.cloneUnlessOtherwiseSpecified(element, options);\n });\n}\n\nfunction getMergeFunction(\n key: string,\n options: deepmerge.Options\n): (x: any, y: any, options?: deepmerge.Options) => any {\n if (!options.customMerge) {\n return deepmerge;\n }\n const customMerge = options.customMerge(key);\n return typeof customMerge === \"function\" ? customMerge : deepmerge;\n}\n\nfunction propertyIsOnObject(object: any, property: string | symbol): boolean {\n try {\n return property in object;\n } catch (_) {\n return false;\n }\n}\n\nfunction propertyIsUnsafe(target: any, key: string | symbol): boolean {\n return (\n propertyIsOnObject(target, key) &&\n !(\n Object.hasOwnProperty.call(target, key) &&\n Object.propertyIsEnumerable.call(target, key)\n )\n );\n}\n\nfunction mergeObject(\n target: any,\n source: any,\n options: deepmerge.Options\n): any {\n const destination: any = {};\n if (options.isMergeableObject?.(target)) {\n getKeys(target).forEach(function (key) {\n destination[key] = options.cloneUnlessOtherwiseSpecified\n ? options.cloneUnlessOtherwiseSpecified(target[key], options)\n : target[key];\n });\n }\n getKeys(source).forEach(function (key) {\n if (propertyIsUnsafe(target, key)) {\n return;\n }\n\n if (\n propertyIsOnObject(target, key) &&\n options.isMergeableObject?.(source[key])\n ) {\n destination[key] = getMergeFunction(key as string, options)(\n target[key],\n source[key],\n options\n );\n } else {\n destination[key] = options.cloneUnlessOtherwiseSpecified\n ? options.cloneUnlessOtherwiseSpecified(source[key], options)\n : source[key];\n }\n });\n return destination;\n}\n\nfunction deepmerge<T>(\n target: Partial<T>,\n source: Partial<T>,\n options?: deepmerge.Options\n): T;\nfunction deepmerge<T1, T2>(\n target: Partial<T1>,\n source: Partial<T2>,\n options?: deepmerge.Options\n): T1 & T2;\nfunction deepmerge(target: any, source: any, options?: deepmerge.Options): any {\n options = options || {};\n\n const mergeOptions: deepmerge.ArrayMergeOptions = {\n arrayMerge: options.arrayMerge || defaultArrayMerge,\n isMergeableObject: options.isMergeableObject || isMergeableObject,\n cloneUnlessOtherwiseSpecified:\n options.cloneUnlessOtherwiseSpecified || cloneUnlessOtherwiseSpecified,\n clone: options.clone,\n customMerge: options.customMerge,\n };\n\n const sourceIsArray = Array.isArray(source);\n const targetIsArray = Array.isArray(target);\n const sourceAndTargetTypesMatch = sourceIsArray === targetIsArray;\n\n if (!sourceAndTargetTypesMatch) {\n return mergeOptions.cloneUnlessOtherwiseSpecified(source, mergeOptions);\n } else if (sourceIsArray) {\n return mergeOptions.arrayMerge?.(target, source, mergeOptions);\n } else {\n return mergeObject(target, source, mergeOptions);\n }\n}\n\nfunction deepmergeAll<T extends Record<string, any> = Record<string, any>>(\n array: ReadonlyArray<T>,\n options?: deepmerge.Options\n): T {\n if (!Array.isArray(array)) {\n throw new Error(\"first argument should be an array\");\n }\n\n return array.reduce((prev, next) => {\n return deepmerge(prev, next, options);\n }, {} as T);\n}\n\ndeepmerge.all = deepmergeAll;\n\nexport default deepmerge;\n"]}
|
|
@@ -2,6 +2,8 @@ import fs from "fs";
|
|
|
2
2
|
import AppError from "../../modules/error-handler/utils/app-error.js";
|
|
3
3
|
import { crd, getUserFileExtension as ext } from "./fs.helpers.js";
|
|
4
4
|
import { importModule } from "./global.helpers.js";
|
|
5
|
+
import prismaSchemaParser from "../prisma/prisma-schema-parser.js";
|
|
6
|
+
import { pascalCase } from "./change-case.helpers.js";
|
|
5
7
|
export let prismaInstance = null;
|
|
6
8
|
export async function loadPrismaModule() {
|
|
7
9
|
if (!prismaInstance) {
|
|
@@ -10,17 +12,19 @@ export async function loadPrismaModule() {
|
|
|
10
12
|
if (!fs.existsSync(prismaPath))
|
|
11
13
|
prismaPath = `${crd()}/src/utils/prisma/index.${ext()}`;
|
|
12
14
|
if (!fs.existsSync(prismaPath))
|
|
13
|
-
throw new Error(`
|
|
15
|
+
throw new Error(`Prisma not found`);
|
|
14
16
|
const prismaModule = await importModule(prismaPath, {
|
|
15
17
|
fixExtension: false,
|
|
16
18
|
});
|
|
17
|
-
prismaInstance = prismaModule.default
|
|
18
|
-
if (!prismaInstance
|
|
19
|
+
prismaInstance = prismaModule.default;
|
|
20
|
+
if (!prismaInstance ||
|
|
21
|
+
typeof prismaInstance[pascalCase(prismaSchemaParser.models?.[0].name)]
|
|
22
|
+
?.findFirst !== "function")
|
|
19
23
|
throw new Error("Prisma not found");
|
|
20
24
|
}
|
|
21
25
|
catch (error) {
|
|
22
26
|
if (error.message === "Prisma not found")
|
|
23
|
-
throw new AppError(`Could not initialize Prisma module. Make sure your prisma instance is exported
|
|
27
|
+
throw new AppError(`Could not initialize Prisma module. Make sure your prisma instance is exported as default under src/utils/prisma/index.${ext()}, read more about Arkos.js Project Structure under https://www.arkosjs.com/docs/getting-started/project-structure#utilities-directory`, 500, {}, "PrismaInstanceNotFound");
|
|
24
28
|
throw error;
|
|
25
29
|
}
|
|
26
30
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"prisma.helpers.js","sourceRoot":"","sources":["../../../../src/utils/helpers/prisma.helpers.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,IAAI,CAAC;AACpB,OAAO,QAAQ,MAAM,6CAA6C,CAAC;AACnE,OAAO,EAAE,GAAG,EAAE,oBAAoB,IAAI,GAAG,EAAE,MAAM,cAAc,CAAC;AAChE,OAAO,EAAE,YAAY,EAAE,MAAM,kBAAkB,CAAC;
|
|
1
|
+
{"version":3,"file":"prisma.helpers.js","sourceRoot":"","sources":["../../../../src/utils/helpers/prisma.helpers.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,IAAI,CAAC;AACpB,OAAO,QAAQ,MAAM,6CAA6C,CAAC;AACnE,OAAO,EAAE,GAAG,EAAE,oBAAoB,IAAI,GAAG,EAAE,MAAM,cAAc,CAAC;AAChE,OAAO,EAAE,YAAY,EAAE,MAAM,kBAAkB,CAAC;AAChD,OAAO,kBAAkB,MAAM,gCAAgC,CAAC;AAChE,OAAO,EAAE,UAAU,EAAE,MAAM,uBAAuB,CAAC;AAEnD,MAAM,CAAC,IAAI,cAAc,GAAQ,IAAI,CAAC;AAEtC,MAAM,CAAC,KAAK,UAAU,gBAAgB;IACpC,IAAI,CAAC,cAAc,EAAE,CAAC;QACpB,IAAI,CAAC;YACH,IAAI,UAAU,GAAG,GAAG,GAAG,EAAE,qBAAqB,GAAG,EAAE,EAAE,CAAC;YAEtD,IAAI,CAAC,EAAE,CAAC,UAAU,CAAC,UAAU,CAAC;gBAC5B,UAAU,GAAG,GAAG,GAAG,EAAE,2BAA2B,GAAG,EAAE,EAAE,CAAC;YAE1D,IAAI,CAAC,EAAE,CAAC,UAAU,CAAC,UAAU,CAAC;gBAAE,MAAM,IAAI,KAAK,CAAC,kBAAkB,CAAC,CAAC;YAEpE,MAAM,YAAY,GAAG,MAAM,YAAY,CAAC,UAAU,EAAE;gBAClD,YAAY,EAAE,KAAK;aACpB,CAAC,CAAC;YACH,cAAc,GAAG,YAAY,CAAC,OAAO,CAAC;YAEtC,IACE,CAAC,cAAc;gBACf,OAAO,cAAc,CAAC,UAAU,CAAC,kBAAkB,CAAC,MAAM,EAAE,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC;oBACpE,EAAE,SAAS,KAAK,UAAU;gBAE5B,MAAM,IAAI,KAAK,CAAC,kBAAkB,CAAC,CAAC;QACxC,CAAC;QAAC,OAAO,KAAU,EAAE,CAAC;YACpB,IAAI,KAAK,CAAC,OAAO,KAAK,kBAAkB;gBACtC,MAAM,IAAI,QAAQ,CAChB,0HAA0H,GAAG,EAAE,uIAAuI,EACtQ,GAAG,EACH,EAAE,EACF,wBAAwB,CACzB,CAAC;YACJ,MAAM,KAAK,CAAC;QACd,CAAC;IACH,CAAC;IACD,OAAO,cAAc,CAAC;AACxB,CAAC;AAED,MAAM,UAAU,iBAAiB;IAC/B,OAAO,cAAc,CAAC;AACxB,CAAC","sourcesContent":["import fs from \"fs\";\nimport AppError from \"../../modules/error-handler/utils/app-error\";\nimport { crd, getUserFileExtension as ext } from \"./fs.helpers\";\nimport { importModule } from \"./global.helpers\";\nimport prismaSchemaParser from \"../prisma/prisma-schema-parser\";\nimport { pascalCase } from \"./change-case.helpers\";\n\nexport let prismaInstance: any = null;\n\nexport async function loadPrismaModule() {\n if (!prismaInstance) {\n try {\n let prismaPath = `${crd()}/src/utils/prisma.${ext()}`;\n\n if (!fs.existsSync(prismaPath))\n prismaPath = `${crd()}/src/utils/prisma/index.${ext()}`;\n\n if (!fs.existsSync(prismaPath)) throw new Error(`Prisma not found`);\n\n const prismaModule = await importModule(prismaPath, {\n fixExtension: false,\n });\n prismaInstance = prismaModule.default;\n\n if (\n !prismaInstance ||\n typeof prismaInstance[pascalCase(prismaSchemaParser.models?.[0].name)]\n ?.findFirst !== \"function\"\n )\n throw new Error(\"Prisma not found\");\n } catch (error: any) {\n if (error.message === \"Prisma not found\")\n throw new AppError(\n `Could not initialize Prisma module. Make sure your prisma instance is exported as default under src/utils/prisma/index.${ext()}, read more about Arkos.js Project Structure under https://www.arkosjs.com/docs/getting-started/project-structure#utilities-directory`,\n 500,\n {},\n \"PrismaInstanceNotFound\"\n );\n throw error;\n }\n }\n return prismaInstance;\n}\n\nexport function getPrismaInstance() {\n return prismaInstance;\n}\n"]}
|