@drax/crud-back 0.11.5 → 0.12.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (74) hide show
  1. package/dist/builders/CrudSchemaBuilder.js +349 -0
  2. package/dist/controllers/AbstractFastifyController.js +105 -176
  3. package/dist/index.js +15 -1
  4. package/dist/regexs/QueryFilterRegex.js +3 -0
  5. package/dist/repository/AbstractMongoRepository.js +114 -28
  6. package/dist/repository/AbstractSqliteRepository.js +131 -41
  7. package/dist/schemas/DeleteBodyResponseSchema.js +9 -0
  8. package/dist/schemas/ErrorBodyResponseSchema.js +16 -0
  9. package/dist/schemas/ExportBodyResponseSchema.js +9 -0
  10. package/dist/schemas/FindBySchema.js +6 -0
  11. package/dist/schemas/FindSchema.js +9 -0
  12. package/dist/schemas/IdParamSchema.js +6 -0
  13. package/dist/schemas/PaginateBodySchema.js +20 -0
  14. package/dist/schemas/PaginateSchema.js +17 -0
  15. package/dist/schemas/SearchSchema.js +5 -0
  16. package/dist/services/AbstractService.js +8 -5
  17. package/dist/zod/DeleteBodySchema.js +6 -0
  18. package/dist/zod/IdParamSchema.js +6 -0
  19. package/dist/zod/PaginateBodySchema.js +20 -0
  20. package/package.json +7 -6
  21. package/src/builders/CrudSchemaBuilder.ts +420 -0
  22. package/src/controllers/AbstractFastifyController.ts +149 -165
  23. package/src/index.ts +28 -0
  24. package/src/regexs/QueryFilterRegex.ts +4 -0
  25. package/src/repository/AbstractMongoRepository.ts +153 -40
  26. package/src/repository/AbstractSqliteRepository.ts +196 -72
  27. package/src/schemas/DeleteBodyResponseSchema.ts +12 -0
  28. package/src/schemas/ErrorBodyResponseSchema.ts +20 -0
  29. package/src/schemas/ExportBodyResponseSchema.ts +12 -0
  30. package/src/schemas/FindBySchema.ts +9 -0
  31. package/src/schemas/FindSchema.ts +13 -0
  32. package/src/schemas/IdParamSchema.ts +9 -0
  33. package/src/schemas/PaginateSchema.ts +21 -0
  34. package/src/schemas/SearchSchema.ts +8 -0
  35. package/src/services/AbstractService.ts +42 -33
  36. package/tsconfig.tsbuildinfo +1 -1
  37. package/types/builders/CrudSchemaBuilder.d.ts +2401 -0
  38. package/types/builders/CrudSchemaBuilder.d.ts.map +1 -0
  39. package/types/controllers/AbstractFastifyController.d.ts +6 -1
  40. package/types/controllers/AbstractFastifyController.d.ts.map +1 -1
  41. package/types/index.d.ts +10 -1
  42. package/types/index.d.ts.map +1 -1
  43. package/types/regexs/QueryFilterRegex.d.ts +4 -0
  44. package/types/regexs/QueryFilterRegex.d.ts.map +1 -0
  45. package/types/repository/AbstractMongoRepository.d.ts +6 -3
  46. package/types/repository/AbstractMongoRepository.d.ts.map +1 -1
  47. package/types/repository/AbstractSqliteRepository.d.ts +23 -8
  48. package/types/repository/AbstractSqliteRepository.d.ts.map +1 -1
  49. package/types/schemas/DeleteBodyResponseSchema.d.ts +20 -0
  50. package/types/schemas/DeleteBodyResponseSchema.d.ts.map +1 -0
  51. package/types/schemas/ErrorBodyResponseSchema.d.ts +60 -0
  52. package/types/schemas/ErrorBodyResponseSchema.d.ts.map +1 -0
  53. package/types/schemas/ExportBodyResponseSchema.d.ts +20 -0
  54. package/types/schemas/ExportBodyResponseSchema.d.ts.map +1 -0
  55. package/types/schemas/FindBySchema.d.ts +13 -0
  56. package/types/schemas/FindBySchema.d.ts.map +1 -0
  57. package/types/schemas/FindSchema.d.ts +19 -0
  58. package/types/schemas/FindSchema.d.ts.map +1 -0
  59. package/types/schemas/IdParamSchema.d.ts +11 -0
  60. package/types/schemas/IdParamSchema.d.ts.map +1 -0
  61. package/types/schemas/PaginateBodySchema.d.ts +61 -0
  62. package/types/schemas/PaginateBodySchema.d.ts.map +1 -0
  63. package/types/schemas/PaginateSchema.d.ts +41 -0
  64. package/types/schemas/PaginateSchema.d.ts.map +1 -0
  65. package/types/schemas/SearchSchema.d.ts +10 -0
  66. package/types/schemas/SearchSchema.d.ts.map +1 -0
  67. package/types/services/AbstractService.d.ts +5 -5
  68. package/types/services/AbstractService.d.ts.map +1 -1
  69. package/types/zod/DeleteBodySchema.d.ts +11 -0
  70. package/types/zod/DeleteBodySchema.d.ts.map +1 -0
  71. package/types/zod/IdParamSchema.d.ts +11 -0
  72. package/types/zod/IdParamSchema.d.ts.map +1 -0
  73. package/types/zod/PaginateBodySchema.d.ts +61 -0
  74. package/types/zod/PaginateBodySchema.d.ts.map +1 -0
package/package.json CHANGED
@@ -3,7 +3,7 @@
3
3
  "publishConfig": {
4
4
  "access": "public"
5
5
  },
6
- "version": "0.11.5",
6
+ "version": "0.12.1",
7
7
  "description": "Crud utils across modules",
8
8
  "main": "dist/index.js",
9
9
  "types": "types/index.d.ts",
@@ -22,13 +22,14 @@
22
22
  "author": "Cristian Incarnato & Drax Team",
23
23
  "license": "ISC",
24
24
  "dependencies": {
25
- "@drax/common-back": "^0.11.3",
26
- "@drax/common-share": "^0.11.3",
27
- "@drax/identity-share": "^0.11.5",
28
- "@drax/media-back": "^0.11.5",
25
+ "@drax/common-back": "^0.12.1",
26
+ "@drax/common-share": "^0.12.1",
27
+ "@drax/identity-share": "^0.12.1",
28
+ "@drax/media-back": "^0.12.1",
29
29
  "@graphql-tools/load-files": "^7.0.0",
30
30
  "@graphql-tools/merge": "^9.0.4",
31
31
  "mongoose": "^8.6.3",
32
+ "mongoose-lean-virtuals": "^1.1.0",
32
33
  "mongoose-paginate-v2": "^1.8.3"
33
34
  },
34
35
  "peerDependencies": {
@@ -44,5 +45,5 @@
44
45
  "tsc-alias": "^1.8.10",
45
46
  "typescript": "^5.6.2"
46
47
  },
47
- "gitHead": "e67f10f0af29468c9d30f16135cfdbdff166d916"
48
+ "gitHead": "76fd366e12449f5f605662197f985a28d98058a2"
48
49
  }
@@ -0,0 +1,420 @@
1
+ import z from 'zod';
2
+ import { zodToJsonSchema } from 'zod-to-json-schema';
3
+ import type { Targets } from 'zod-to-json-schema';
4
+ import {
5
+ IdParamSchema,
6
+ DeleteBodyResponseSchema,
7
+ PaginateQuerySchema,
8
+ PaginateBodyResponseSchema,
9
+ FindQuerySchema,
10
+ SearchQuerySchema,
11
+ FindByParamSchema,
12
+ ErrorBodyResponseSchema,
13
+ ValidationErrorBodyResponseSchema,
14
+ ExportBodyResponseSchema
15
+ } from '../index.js';
16
+
17
+ export class CrudSchemaBuilder<T extends z.ZodObject<z.ZodRawShape>, TCreate extends z.ZodObject<z.ZodRawShape>, TUpdate extends z.ZodObject<z.ZodRawShape>> {
18
+ private entitySchema: T;
19
+ private entityCreateSchema: TCreate;
20
+ private entityUpdateSchema: TUpdate;
21
+ private entityName: string;
22
+ private tags: string[];
23
+ private target: Targets = 'openApi3'; //"jsonSchema7" | "jsonSchema2019-09" | "openApi3" | "openAi"
24
+
25
+ constructor(entitySchema: T, entityCreateSchema: TCreate, entityUpdateSchema: TUpdate, entityName: string, target:Targets = 'openApi3', tags: string[] = []) {
26
+ this.entitySchema = entitySchema;
27
+ this.entityCreateSchema = entityCreateSchema;
28
+ this.entityUpdateSchema = entityUpdateSchema;
29
+ this.entityName = entityName;
30
+ this.tags = tags
31
+ this.target = target
32
+ }
33
+
34
+ get getTags(){
35
+ if(this.tags.length > 0){
36
+ return {tags: this.tags}
37
+ }
38
+ return []
39
+ }
40
+
41
+ get jsonEntityCreateSchema(){
42
+ return zodToJsonSchema(this.entityCreateSchema, {target: this.target})
43
+ }
44
+
45
+ get jsonEntityUpdateSchema(){
46
+ return zodToJsonSchema(this.entityUpdateSchema, {target: this.target})
47
+ }
48
+
49
+ get jsonEntitySchema() {
50
+ return zodToJsonSchema(this.entitySchema, {target: this.target})
51
+ }
52
+
53
+ get jsonEntityArraySchema() {
54
+ return zodToJsonSchema(z.array(this.entitySchema), {target: this.target})
55
+ }
56
+
57
+ get jsonExportBodyResponse() {
58
+ return zodToJsonSchema(ExportBodyResponseSchema, {target: this.target})
59
+ }
60
+
61
+ get jsonErrorBodyResponse() {
62
+ return zodToJsonSchema(ErrorBodyResponseSchema, {target: this.target})
63
+ }
64
+
65
+ get jsonValidationErrorBodyResponse() {
66
+ return zodToJsonSchema(ValidationErrorBodyResponseSchema, {target: this.target})
67
+ }
68
+
69
+ get jsonFindQuerySchema(){
70
+ return zodToJsonSchema(FindQuerySchema, {target: this.target})
71
+ }
72
+
73
+ get jsonSearchQuerySchema(){
74
+ return zodToJsonSchema(SearchQuerySchema, {target: this.target})
75
+ }
76
+
77
+ get jsonPaginateQuerySchema(){
78
+ return zodToJsonSchema(PaginateQuerySchema, {target: this.target})
79
+ }
80
+
81
+ get jsonDeleteBodyResponseSchema(){
82
+ return zodToJsonSchema(DeleteBodyResponseSchema, {target: this.target})
83
+ }
84
+
85
+ get jsonFindByParamSchema(){
86
+ return zodToJsonSchema(FindByParamSchema, {target: this.target})
87
+ }
88
+
89
+ get jsonPaginateBodyResponseSchema(){
90
+ return zodToJsonSchema(PaginateBodyResponseSchema.extend({
91
+ items: z.array(this.entitySchema)
92
+ }), {target: this.target})
93
+ }
94
+
95
+ get jsonIdParamSchema(){
96
+ return zodToJsonSchema(IdParamSchema, {target: this.target})
97
+ }
98
+
99
+ /**
100
+ * Get JSON schema for export
101
+ */
102
+ get exportSchema(){
103
+ return {
104
+ ...(this.getTags),
105
+ query: this.jsonFindQuerySchema,
106
+ response: {
107
+ 200: this.jsonExportBodyResponse,
108
+ 400: this.jsonErrorBodyResponse,
109
+ 401: this.jsonErrorBodyResponse,
110
+ 403: this.jsonErrorBodyResponse,
111
+ 500: this.jsonErrorBodyResponse
112
+ }
113
+ };
114
+ }
115
+
116
+ /**
117
+ * Get JSON schema for finding an entity by ID
118
+ */
119
+ get findByIdSchema() {
120
+ return {
121
+ ...(this.getTags),
122
+ params: this.jsonIdParamSchema,
123
+ response: {
124
+ 200: this.jsonEntitySchema,
125
+ 400: this.jsonErrorBodyResponse,
126
+ 401: this.jsonErrorBodyResponse,
127
+ 403: this.jsonErrorBodyResponse,
128
+ 500: this.jsonErrorBodyResponse
129
+ }
130
+ };
131
+ }
132
+
133
+ /**
134
+ * Get JSON schema for finding an entity by IDs
135
+ */
136
+ get findByIdsSchema() {
137
+ return {
138
+ ...(this.getTags),
139
+ params: zodToJsonSchema(z.object({
140
+ ids: z.string().regex(/^[^,]+(,[^,]+)*$/, "Debe ser una lista de valores separados por coma sin comas consecutivas")
141
+ }), {target: this.target}),
142
+ response: {
143
+ 200: this.jsonEntityArraySchema,
144
+ 400: this.jsonErrorBodyResponse,
145
+ 401: this.jsonErrorBodyResponse,
146
+ 403: this.jsonErrorBodyResponse,
147
+ 500: this.jsonErrorBodyResponse
148
+ }
149
+ };
150
+ }
151
+
152
+ /**
153
+ * Get JSON schema for search an entity
154
+ */
155
+ get searchSchema() {
156
+ return {
157
+ ...(this.getTags),
158
+ query: this.jsonSearchQuerySchema,
159
+ response: {
160
+ 200: this.jsonEntityArraySchema,
161
+ 400: this.jsonErrorBodyResponse,
162
+ 401: this.jsonErrorBodyResponse,
163
+ 403: this.jsonErrorBodyResponse,
164
+ 500: this.jsonErrorBodyResponse
165
+ }
166
+ }
167
+ }
168
+
169
+ /**
170
+ * Get JSON schema for find entities
171
+ */
172
+ get findSchema() {
173
+ return {
174
+ ...(this.getTags),
175
+ query: this.jsonFindQuerySchema,
176
+ response: {
177
+ 200: this.jsonEntityArraySchema,
178
+ 400: this.jsonErrorBodyResponse,
179
+ 401: this.jsonErrorBodyResponse,
180
+ 403: this.jsonErrorBodyResponse,
181
+ 500: this.jsonErrorBodyResponse
182
+ }
183
+ }
184
+ }
185
+
186
+ /**
187
+ * Get JSON schema for find one entity
188
+ */
189
+ get findOneSchema() {
190
+ return {
191
+ ...(this.getTags),
192
+ params: this.jsonFindQuerySchema,
193
+ response: {
194
+ 200: this.jsonEntitySchema,
195
+ 400: this.jsonErrorBodyResponse,
196
+ 401: this.jsonErrorBodyResponse,
197
+ 403: this.jsonErrorBodyResponse,
198
+ 500: this.jsonErrorBodyResponse
199
+ }
200
+ };
201
+ }
202
+
203
+ /**
204
+ * Get JSON schema for findBy entities
205
+ */
206
+ get findBySchema() {
207
+ return {
208
+ ...(this.getTags),
209
+ params: this.jsonFindByParamSchema,
210
+ response: {
211
+ 200: this.jsonEntityArraySchema,
212
+ 401: this.jsonErrorBodyResponse,
213
+ 403: this.jsonErrorBodyResponse,
214
+ 500: this.jsonErrorBodyResponse
215
+ }
216
+ };
217
+ }
218
+
219
+ /**
220
+ * Get JSON schema for findBy entities
221
+ */
222
+ get findOneBySchema() {
223
+ return {
224
+ ...(this.getTags),
225
+ params: this.jsonFindByParamSchema,
226
+ response: {
227
+ 200: this.jsonEntitySchema,
228
+ 401: this.jsonErrorBodyResponse,
229
+ 403: this.jsonErrorBodyResponse,
230
+ 500: this.jsonErrorBodyResponse
231
+ }
232
+ };
233
+ }
234
+
235
+ /**
236
+ * Get JSON schema for paginating entities
237
+ */
238
+ get paginateSchema() {
239
+ return {
240
+ ...(this.getTags),
241
+ query: this.jsonPaginateQuerySchema,
242
+ response: {
243
+ 200: this.jsonPaginateBodyResponseSchema,
244
+ 400: this.jsonErrorBodyResponse,
245
+ 401: this.jsonErrorBodyResponse,
246
+ 403: this.jsonErrorBodyResponse,
247
+ 500: this.jsonErrorBodyResponse
248
+ }
249
+ };
250
+ }
251
+
252
+ /**
253
+ * Get JSON schema for all entities
254
+ */
255
+ get allSchema() {
256
+ return {
257
+ ...(this.getTags),
258
+ response: {
259
+ 200: this.jsonEntityArraySchema,
260
+ 401: this.jsonErrorBodyResponse,
261
+ 403: this.jsonErrorBodyResponse,
262
+ 500: this.jsonErrorBodyResponse
263
+ }
264
+ };
265
+ }
266
+
267
+ /**
268
+ * Get JSON schema for creating an entity
269
+ */
270
+ get createSchema() {
271
+ return {
272
+ ...(this.getTags),
273
+ body: this.jsonEntityCreateSchema,
274
+ response: {
275
+ 200: this.jsonEntitySchema,
276
+ 401: this.jsonErrorBodyResponse,
277
+ 403: this.jsonErrorBodyResponse,
278
+ 422: this.jsonValidationErrorBodyResponse,
279
+ 500: this.jsonErrorBodyResponse
280
+ }
281
+ };
282
+ }
283
+
284
+ /**
285
+ * Get JSON schema for updating an entity
286
+ */
287
+ get updateSchema() {
288
+ return {
289
+ ...(this.getTags),
290
+ params: this.jsonIdParamSchema,
291
+ body: this.jsonEntityUpdateSchema,
292
+ response: {
293
+ 200: this.jsonEntitySchema,
294
+ 401: this.jsonErrorBodyResponse,
295
+ 403: this.jsonErrorBodyResponse,
296
+ 422: this.jsonValidationErrorBodyResponse,
297
+ 500: this.jsonErrorBodyResponse
298
+ }
299
+ };
300
+ }
301
+
302
+ /**
303
+ * Get JSON schema for updating an entity
304
+ */
305
+ get updatePartialSchema() {
306
+ return {
307
+ ...(this.getTags),
308
+ params: this.jsonIdParamSchema,
309
+ body: zodToJsonSchema(this.entityUpdateSchema.partial(), {target: this.target}),
310
+ response: {
311
+ 200: this.jsonEntitySchema,
312
+ 401: this.jsonErrorBodyResponse,
313
+ 403: this.jsonErrorBodyResponse,
314
+ 422: this.jsonValidationErrorBodyResponse,
315
+ 500: this.jsonErrorBodyResponse
316
+ }
317
+ };
318
+ }
319
+
320
+ /**
321
+ * Get JSON schema for deleting an entity
322
+ */
323
+ get deleteSchema() {
324
+ return {
325
+ ...(this.getTags),
326
+ params: this.jsonIdParamSchema,
327
+ response: {
328
+ 200: this.jsonDeleteBodyResponseSchema,
329
+ 400: this.jsonErrorBodyResponse,
330
+ 401: this.jsonErrorBodyResponse,
331
+ 403: this.jsonErrorBodyResponse,
332
+ 500: this.jsonErrorBodyResponse
333
+ }
334
+ };
335
+ }
336
+
337
+
338
+
339
+ /**
340
+ * Generate route builder function for Fastify with configurable endpoints
341
+ * @param options Configuration options for route generation
342
+ * @param basePath Base API path for the entity
343
+ */
344
+ generateRoutes(
345
+ options: {
346
+ paginate?: boolean;
347
+ all?: boolean;
348
+ export?: boolean;
349
+ search?: boolean;
350
+ findById?: boolean;
351
+ create?: boolean;
352
+ update?: boolean;
353
+ delete?: boolean;
354
+ } = {
355
+ paginate: true,
356
+ all: true,
357
+ export: true,
358
+ search: true,
359
+ findById: true,
360
+ create: true,
361
+ update: true,
362
+ delete: true
363
+ },
364
+ basePath: string = `/api/${this.entityName.toLowerCase()}s`
365
+ ) {
366
+ return (fastify, controller) => {
367
+ // Get all entities with pagination
368
+ if (options.paginate !== false) {
369
+ fastify.get(basePath, {
370
+ schema: this.paginateSchema
371
+ }, (req, rep) => controller.paginate(req, rep));
372
+ }
373
+
374
+ // Get all entities without pagination
375
+ if (options.all !== false) {
376
+ fastify.get(`${basePath}/all`, (req, rep) => controller.all(req, rep));
377
+ }
378
+
379
+ // Export entities
380
+ if (options.export !== false) {
381
+ fastify.get(`${basePath}/export`, (req, rep) => controller.export(req, rep));
382
+ }
383
+
384
+ // Search entities
385
+ if (options.search !== false) {
386
+ fastify.get(`${basePath}/search`, (req, rep) => controller.search(req, rep));
387
+ }
388
+
389
+ // Get entity by ID
390
+ if (options.findById !== false) {
391
+ fastify.get(`${basePath}/:id`, {
392
+ schema: this.findByIdSchema
393
+ }, (req, rep) => controller.findById(req, rep));
394
+ }
395
+
396
+ // Create entity
397
+ if (options.create !== false) {
398
+ fastify.post(basePath, {
399
+ schema: this.createSchema
400
+ }, (req, rep) => controller.create(req, rep));
401
+ }
402
+
403
+ // Update entity
404
+ if (options.update !== false) {
405
+ fastify.put(`${basePath}/:id`, {
406
+ schema: this.updateSchema
407
+ }, (req, rep) => controller.update(req, rep));
408
+ }
409
+
410
+ // Delete entity
411
+ if (options.delete !== false) {
412
+ fastify.delete(`${basePath}/:id`, {
413
+ schema: this.deleteSchema
414
+ }, (req, rep) => controller.delete(req, rep));
415
+ }
416
+ };
417
+ }
418
+ }
419
+
420
+ export default CrudSchemaBuilder