@drax/crud-back 3.18.0 → 3.20.0

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 (83) hide show
  1. package/dist/crud-saved-query/controllers/CrudSavedQueryController.js +22 -0
  2. package/dist/crud-saved-query/factory/services/CrudSavedQueryServiceFactory.js +27 -0
  3. package/dist/crud-saved-query/interfaces/ICrudSavedQuery.js +1 -0
  4. package/dist/crud-saved-query/interfaces/ICrudSavedQueryRepository.js +1 -0
  5. package/dist/crud-saved-query/models/CrudSavedQueryModel.js +40 -0
  6. package/dist/crud-saved-query/permissions/CrudSavedQueryPermissions.js +10 -0
  7. package/dist/crud-saved-query/repository/mongo/CrudSavedQueryMongoRepository.js +12 -0
  8. package/dist/crud-saved-query/repository/sqlite/CrudSavedQuerySqliteRepository.js +29 -0
  9. package/dist/crud-saved-query/routes/CrudSavedQueryRoutes.js +20 -0
  10. package/dist/crud-saved-query/schemas/CrudSavedQuerySchema.js +36 -0
  11. package/dist/crud-saved-query/services/CrudSavedQueryService.js +8 -0
  12. package/dist/index.js +11 -1
  13. package/dist/modules/crud-saved-query/controllers/CrudSavedQueryController.js +23 -0
  14. package/dist/modules/crud-saved-query/factory/services/CrudSavedQueryServiceFactory.js +27 -0
  15. package/dist/modules/crud-saved-query/interfaces/ICrudSavedQuery.js +1 -0
  16. package/dist/modules/crud-saved-query/interfaces/ICrudSavedQueryRepository.js +1 -0
  17. package/dist/modules/crud-saved-query/models/CrudSavedQueryModel.js +40 -0
  18. package/dist/modules/crud-saved-query/permissions/CrudSavedQueryPermissions.js +14 -0
  19. package/dist/modules/crud-saved-query/repository/mongo/CrudSavedQueryMongoRepository.js +12 -0
  20. package/dist/modules/crud-saved-query/repository/sqlite/CrudSavedQuerySqliteRepository.js +29 -0
  21. package/dist/modules/crud-saved-query/routes/CrudSavedQueryRoutes.js +20 -0
  22. package/dist/modules/crud-saved-query/schemas/CrudSavedQuerySchema.js +36 -0
  23. package/dist/modules/crud-saved-query/services/CrudSavedQueryService.js +8 -0
  24. package/package.json +3 -3
  25. package/src/crud-saved-query/controllers/CrudSavedQueryController.ts +32 -0
  26. package/src/crud-saved-query/factory/services/CrudSavedQueryServiceFactory.ts +41 -0
  27. package/src/crud-saved-query/interfaces/ICrudSavedQuery.ts +20 -0
  28. package/src/crud-saved-query/interfaces/ICrudSavedQueryRepository.ts +7 -0
  29. package/src/crud-saved-query/models/CrudSavedQueryModel.ts +54 -0
  30. package/src/crud-saved-query/permissions/CrudSavedQueryPermissions.ts +10 -0
  31. package/src/crud-saved-query/repository/mongo/CrudSavedQueryMongoRepository.ts +19 -0
  32. package/src/crud-saved-query/repository/sqlite/CrudSavedQuerySqliteRepository.ts +34 -0
  33. package/src/crud-saved-query/routes/CrudSavedQueryRoutes.ts +31 -0
  34. package/src/crud-saved-query/schemas/CrudSavedQuerySchema.ts +41 -0
  35. package/src/crud-saved-query/services/CrudSavedQueryService.ts +13 -0
  36. package/src/index.ts +19 -0
  37. package/tsconfig.tsbuildinfo +1 -1
  38. package/types/crud-saved-query/controllers/CrudSavedQueryController.d.ts +11 -0
  39. package/types/crud-saved-query/controllers/CrudSavedQueryController.d.ts.map +1 -0
  40. package/types/crud-saved-query/factory/services/CrudSavedQueryServiceFactory.d.ts +8 -0
  41. package/types/crud-saved-query/factory/services/CrudSavedQueryServiceFactory.d.ts.map +1 -0
  42. package/types/crud-saved-query/interfaces/ICrudSavedQuery.d.ts +18 -0
  43. package/types/crud-saved-query/interfaces/ICrudSavedQuery.d.ts.map +1 -0
  44. package/types/crud-saved-query/interfaces/ICrudSavedQueryRepository.d.ts +6 -0
  45. package/types/crud-saved-query/interfaces/ICrudSavedQueryRepository.d.ts.map +1 -0
  46. package/types/crud-saved-query/models/CrudSavedQueryModel.d.ts +15 -0
  47. package/types/crud-saved-query/models/CrudSavedQueryModel.d.ts.map +1 -0
  48. package/types/crud-saved-query/permissions/CrudSavedQueryPermissions.d.ts +10 -0
  49. package/types/crud-saved-query/permissions/CrudSavedQueryPermissions.d.ts.map +1 -0
  50. package/types/crud-saved-query/repository/mongo/CrudSavedQueryMongoRepository.d.ts +9 -0
  51. package/types/crud-saved-query/repository/mongo/CrudSavedQueryMongoRepository.d.ts.map +1 -0
  52. package/types/crud-saved-query/repository/sqlite/CrudSavedQuerySqliteRepository.d.ts +20 -0
  53. package/types/crud-saved-query/repository/sqlite/CrudSavedQuerySqliteRepository.d.ts.map +1 -0
  54. package/types/crud-saved-query/routes/CrudSavedQueryRoutes.d.ts +4 -0
  55. package/types/crud-saved-query/routes/CrudSavedQueryRoutes.d.ts.map +1 -0
  56. package/types/crud-saved-query/schemas/CrudSavedQuerySchema.d.ts +63 -0
  57. package/types/crud-saved-query/schemas/CrudSavedQuerySchema.d.ts.map +1 -0
  58. package/types/crud-saved-query/services/CrudSavedQueryService.d.ts +10 -0
  59. package/types/crud-saved-query/services/CrudSavedQueryService.d.ts.map +1 -0
  60. package/types/index.d.ts +9 -1
  61. package/types/index.d.ts.map +1 -1
  62. package/types/modules/crud-saved-query/controllers/CrudSavedQueryController.d.ts +11 -0
  63. package/types/modules/crud-saved-query/controllers/CrudSavedQueryController.d.ts.map +1 -0
  64. package/types/modules/crud-saved-query/factory/services/CrudSavedQueryServiceFactory.d.ts +8 -0
  65. package/types/modules/crud-saved-query/factory/services/CrudSavedQueryServiceFactory.d.ts.map +1 -0
  66. package/types/modules/crud-saved-query/interfaces/ICrudSavedQuery.d.ts +18 -0
  67. package/types/modules/crud-saved-query/interfaces/ICrudSavedQuery.d.ts.map +1 -0
  68. package/types/modules/crud-saved-query/interfaces/ICrudSavedQueryRepository.d.ts +6 -0
  69. package/types/modules/crud-saved-query/interfaces/ICrudSavedQueryRepository.d.ts.map +1 -0
  70. package/types/modules/crud-saved-query/models/CrudSavedQueryModel.d.ts +15 -0
  71. package/types/modules/crud-saved-query/models/CrudSavedQueryModel.d.ts.map +1 -0
  72. package/types/modules/crud-saved-query/permissions/CrudSavedQueryPermissions.d.ts +14 -0
  73. package/types/modules/crud-saved-query/permissions/CrudSavedQueryPermissions.d.ts.map +1 -0
  74. package/types/modules/crud-saved-query/repository/mongo/CrudSavedQueryMongoRepository.d.ts +9 -0
  75. package/types/modules/crud-saved-query/repository/mongo/CrudSavedQueryMongoRepository.d.ts.map +1 -0
  76. package/types/modules/crud-saved-query/repository/sqlite/CrudSavedQuerySqliteRepository.d.ts +20 -0
  77. package/types/modules/crud-saved-query/repository/sqlite/CrudSavedQuerySqliteRepository.d.ts.map +1 -0
  78. package/types/modules/crud-saved-query/routes/CrudSavedQueryRoutes.d.ts +4 -0
  79. package/types/modules/crud-saved-query/routes/CrudSavedQueryRoutes.d.ts.map +1 -0
  80. package/types/modules/crud-saved-query/schemas/CrudSavedQuerySchema.d.ts +63 -0
  81. package/types/modules/crud-saved-query/schemas/CrudSavedQuerySchema.d.ts.map +1 -0
  82. package/types/modules/crud-saved-query/services/CrudSavedQueryService.d.ts +10 -0
  83. package/types/modules/crud-saved-query/services/CrudSavedQueryService.d.ts.map +1 -0
@@ -0,0 +1,22 @@
1
+ import AbstractFastifyController from "../../controllers/AbstractFastifyController.js";
2
+ import CrudSavedQueryServiceFactory from "../factory/services/CrudSavedQueryServiceFactory.js";
3
+ import CrudSavedQueryPermissions from "../permissions/CrudSavedQueryPermissions.js";
4
+ class CrudSavedQueryController extends AbstractFastifyController {
5
+ constructor() {
6
+ super(CrudSavedQueryServiceFactory.instance, CrudSavedQueryPermissions);
7
+ this.tenantField = "tenant";
8
+ this.userField = "user";
9
+ this.tenantFilter = true;
10
+ this.tenantSetter = true;
11
+ this.tenantAssert = true;
12
+ this.userSetter = true;
13
+ this.userAssert = true;
14
+ this.userFilter = false;
15
+ }
16
+ async preRead(request, filters) {
17
+ filters.push({ field: "shared", operator: "eq", value: true, orGroup: "crudSavedQueryVisibility" }, { field: this.userField, operator: "eq", value: request.rbac.userId, orGroup: "crudSavedQueryVisibility" });
18
+ return filters;
19
+ }
20
+ }
21
+ export default CrudSavedQueryController;
22
+ export { CrudSavedQueryController };
@@ -0,0 +1,27 @@
1
+ import { COMMON, CommonConfig, DraxConfig } from "@drax/common-back";
2
+ import CrudSavedQueryMongoRepository from "../../repository/mongo/CrudSavedQueryMongoRepository.js";
3
+ import CrudSavedQuerySqliteRepository from "../../repository/sqlite/CrudSavedQuerySqliteRepository.js";
4
+ import { CrudSavedQueryService } from "../../services/CrudSavedQueryService.js";
5
+ import { CrudSavedQueryBaseSchema, CrudSavedQuerySchema } from "../../schemas/CrudSavedQuerySchema.js";
6
+ class CrudSavedQueryServiceFactory {
7
+ static get instance() {
8
+ if (!CrudSavedQueryServiceFactory.service) {
9
+ let repository;
10
+ switch (DraxConfig.getOrLoad(CommonConfig.DbEngine)) {
11
+ case COMMON.DB_ENGINES.MONGODB:
12
+ repository = new CrudSavedQueryMongoRepository();
13
+ break;
14
+ case COMMON.DB_ENGINES.SQLITE:
15
+ repository = new CrudSavedQuerySqliteRepository(DraxConfig.getOrLoad(CommonConfig.SqliteDbFile), false);
16
+ repository.build();
17
+ break;
18
+ default:
19
+ throw new Error("DraxConfig.DB_ENGINE must be one of " + Object.values(COMMON.DB_ENGINES).join(", "));
20
+ }
21
+ CrudSavedQueryServiceFactory.service = new CrudSavedQueryService(repository, CrudSavedQueryBaseSchema, CrudSavedQuerySchema);
22
+ }
23
+ return CrudSavedQueryServiceFactory.service;
24
+ }
25
+ }
26
+ export default CrudSavedQueryServiceFactory;
27
+ export { CrudSavedQueryServiceFactory };
@@ -0,0 +1,40 @@
1
+ import { mongoose } from "@drax/common-back";
2
+ import mongoosePaginate from "mongoose-paginate-v2";
3
+ const FieldFilterSchema = new mongoose.Schema({
4
+ field: { type: String, required: true },
5
+ operator: { type: String, required: false, default: "eq" },
6
+ value: { type: mongoose.Schema.Types.Mixed, required: false },
7
+ orGroup: { type: String, required: false }
8
+ }, { _id: false });
9
+ const DynamicFilterSchema = new mongoose.Schema({
10
+ default: { type: mongoose.Schema.Types.Mixed, required: false },
11
+ label: { type: String, required: false },
12
+ name: { type: String, required: true },
13
+ operator: { type: String, required: false, default: "eq" },
14
+ type: { type: String, required: false, default: "string" },
15
+ permission: { type: String, required: false },
16
+ value: { type: mongoose.Schema.Types.Mixed, required: false },
17
+ ref: { type: String, required: false },
18
+ refDisplay: { type: String, required: false },
19
+ enum: { type: [mongoose.Schema.Types.Mixed], required: false }
20
+ }, { _id: false, strict: false });
21
+ const CrudSavedQuerySchema = new mongoose.Schema({
22
+ entity: { type: String, required: true, index: true },
23
+ name: { type: String, required: true, index: true },
24
+ shared: { type: Boolean, required: false, default: false, index: true },
25
+ columns: [{ type: String, required: true }],
26
+ staticFilters: { type: [FieldFilterSchema], required: false, default: [] },
27
+ dynamicFilters: { type: [DynamicFilterSchema], required: false, default: [] },
28
+ tenant: { type: mongoose.Schema.Types.ObjectId, ref: "Tenant", required: false, index: true },
29
+ user: { type: mongoose.Schema.Types.ObjectId, ref: "User", required: false, index: true }
30
+ }, { timestamps: true });
31
+ CrudSavedQuerySchema.index({ entity: 1, name: 1, tenant: 1, user: 1 });
32
+ CrudSavedQuerySchema.plugin(mongoosePaginate);
33
+ CrudSavedQuerySchema.virtual("id").get(function () {
34
+ return this._id.toString();
35
+ });
36
+ CrudSavedQuerySchema.set("toJSON", { getters: true, virtuals: true });
37
+ CrudSavedQuerySchema.set("toObject", { getters: true, virtuals: true });
38
+ const CrudSavedQueryModel = mongoose.model("CrudSavedQuery", CrudSavedQuerySchema, "CrudSavedQuery");
39
+ export { CrudSavedQuerySchema, CrudSavedQueryModel };
40
+ export default CrudSavedQueryModel;
@@ -0,0 +1,10 @@
1
+ var CrudSavedQueryPermissions;
2
+ (function (CrudSavedQueryPermissions) {
3
+ CrudSavedQueryPermissions["Create"] = "crudSavedQuery:create";
4
+ CrudSavedQueryPermissions["Update"] = "crudSavedQuery:update";
5
+ CrudSavedQueryPermissions["Delete"] = "crudSavedQuery:delete";
6
+ CrudSavedQueryPermissions["View"] = "crudSavedQuery:view";
7
+ CrudSavedQueryPermissions["Manage"] = "crudSavedQuery:manage";
8
+ })(CrudSavedQueryPermissions || (CrudSavedQueryPermissions = {}));
9
+ export { CrudSavedQueryPermissions };
10
+ export default CrudSavedQueryPermissions;
@@ -0,0 +1,12 @@
1
+ import AbstractMongoRepository from "../../../repository/AbstractMongoRepository.js";
2
+ import { CrudSavedQueryModel } from "../../models/CrudSavedQueryModel.js";
3
+ class CrudSavedQueryMongoRepository extends AbstractMongoRepository {
4
+ constructor() {
5
+ super();
6
+ this._model = CrudSavedQueryModel;
7
+ this._searchFields = ["name", "entity"];
8
+ this._populateFields = ["tenant", "user"];
9
+ }
10
+ }
11
+ export default CrudSavedQueryMongoRepository;
12
+ export { CrudSavedQueryMongoRepository };
@@ -0,0 +1,29 @@
1
+ import AbstractSqliteRepository from "../../../repository/AbstractSqliteRepository.js";
2
+ class CrudSavedQuerySqliteRepository extends AbstractSqliteRepository {
3
+ constructor() {
4
+ super(...arguments);
5
+ this.tableName = "CrudSavedQuery";
6
+ this.searchFields = ["name", "entity"];
7
+ this.booleanFields = ["shared"];
8
+ this.jsonFields = ["columns", "staticFilters", "dynamicFilters"];
9
+ this.identifier = "_id";
10
+ this.populateFields = [
11
+ { field: "tenant", table: "Tenant", identifier: "_id" },
12
+ { field: "user", table: "User", identifier: "_id" }
13
+ ];
14
+ this.tableFields = [
15
+ { name: "entity", type: "TEXT", unique: false, primary: false },
16
+ { name: "name", type: "TEXT", unique: false, primary: false },
17
+ { name: "shared", type: "INTEGER", unique: false, primary: false },
18
+ { name: "columns", type: "TEXT", unique: false, primary: false },
19
+ { name: "staticFilters", type: "TEXT", unique: false, primary: false },
20
+ { name: "dynamicFilters", type: "TEXT", unique: false, primary: false },
21
+ { name: "tenant", type: "TEXT", unique: false, primary: false },
22
+ { name: "user", type: "TEXT", unique: false, primary: false },
23
+ { name: "createdAt", type: "TEXT", unique: false, primary: false },
24
+ { name: "updatedAt", type: "TEXT", unique: false, primary: false }
25
+ ];
26
+ }
27
+ }
28
+ export default CrudSavedQuerySqliteRepository;
29
+ export { CrudSavedQuerySqliteRepository };
@@ -0,0 +1,20 @@
1
+ import CrudSavedQueryController from "../controllers/CrudSavedQueryController.js";
2
+ import { CrudSchemaBuilder } from "../../builders/CrudSchemaBuilder.js";
3
+ import { CrudSavedQuerySchema, CrudSavedQueryBaseSchema } from "../schemas/CrudSavedQuerySchema.js";
4
+ async function CrudSavedQueryFastifyRoutes(fastify, options) {
5
+ const controller = new CrudSavedQueryController();
6
+ const schemas = new CrudSchemaBuilder(CrudSavedQuerySchema, CrudSavedQueryBaseSchema, CrudSavedQueryBaseSchema, "CrudSavedQuery", "openapi-3.0", ["crud-saved-queries"]);
7
+ fastify.get("/api/crud-saved-queries", { schema: schemas.paginateSchema }, (req, rep) => controller.paginate(req, rep));
8
+ fastify.get("/api/crud-saved-queries/find", { schema: schemas.findSchema }, (req, rep) => controller.find(req, rep));
9
+ fastify.get("/api/crud-saved-queries/search", { schema: schemas.searchSchema }, (req, rep) => controller.search(req, rep));
10
+ fastify.get("/api/crud-saved-queries/:id", { schema: schemas.findByIdSchema }, (req, rep) => controller.findById(req, rep));
11
+ fastify.get("/api/crud-saved-queries/find-one", { schema: schemas.findOneSchema }, (req, rep) => controller.findOne(req, rep));
12
+ fastify.get("/api/crud-saved-queries/find-by/:field/:value", { schema: schemas.findBySchema }, (req, rep) => controller.findBy(req, rep));
13
+ fastify.get("/api/crud-saved-queries/find-one-by/:field/:value", { schema: schemas.findOneBySchema }, (req, rep) => controller.findOneBy(req, rep));
14
+ fastify.post("/api/crud-saved-queries", { schema: schemas.createSchema }, (req, rep) => controller.create(req, rep));
15
+ fastify.put("/api/crud-saved-queries/:id", { schema: schemas.updateSchema }, (req, rep) => controller.update(req, rep));
16
+ fastify.patch("/api/crud-saved-queries/:id", { schema: schemas.updateSchema }, (req, rep) => controller.updatePartial(req, rep));
17
+ fastify.delete("/api/crud-saved-queries/:id", { schema: schemas.deleteSchema }, (req, rep) => controller.delete(req, rep));
18
+ }
19
+ export default CrudSavedQueryFastifyRoutes;
20
+ export { CrudSavedQueryFastifyRoutes };
@@ -0,0 +1,36 @@
1
+ import { z } from "zod";
2
+ const CrudSavedQueryFieldFilterSchema = z.object({
3
+ field: z.string().min(1, "validation.required"),
4
+ operator: z.string().optional().default("eq"),
5
+ value: z.any().optional().nullable(),
6
+ orGroup: z.string().optional()
7
+ });
8
+ const CrudSavedQueryDynamicFilterSchema = z.object({
9
+ default: z.any().optional().nullable(),
10
+ label: z.string().optional(),
11
+ name: z.string().min(1, "validation.required"),
12
+ operator: z.string().optional().default("eq"),
13
+ type: z.string().optional().default("string"),
14
+ permission: z.string().optional(),
15
+ value: z.any().optional().nullable(),
16
+ ref: z.string().optional(),
17
+ refDisplay: z.string().optional(),
18
+ enum: z.array(z.any()).optional()
19
+ }).catchall(z.any());
20
+ const CrudSavedQueryBaseSchema = z.object({
21
+ entity: z.string().min(1, "validation.required"),
22
+ name: z.string().min(1, "validation.required"),
23
+ shared: z.boolean().optional().default(false),
24
+ columns: z.array(z.string()).optional().default([]),
25
+ staticFilters: z.array(CrudSavedQueryFieldFilterSchema).optional().default([]),
26
+ dynamicFilters: z.array(CrudSavedQueryDynamicFilterSchema).optional().default([]),
27
+ tenant: z.coerce.string().optional().nullable(),
28
+ user: z.coerce.string().optional().nullable()
29
+ });
30
+ const CrudSavedQuerySchema = CrudSavedQueryBaseSchema.extend({
31
+ _id: z.coerce.string(),
32
+ tenant: z.object({ _id: z.coerce.string(), name: z.string() }).nullable().optional(),
33
+ user: z.object({ _id: z.coerce.string(), username: z.string() }).nullable().optional()
34
+ });
35
+ export default CrudSavedQuerySchema;
36
+ export { CrudSavedQuerySchema, CrudSavedQueryBaseSchema };
@@ -0,0 +1,8 @@
1
+ import AbstractService from "../../services/AbstractService.js";
2
+ class CrudSavedQueryService extends AbstractService {
3
+ constructor(repository, baseSchema, fullSchema) {
4
+ super(repository, baseSchema, fullSchema);
5
+ }
6
+ }
7
+ export default CrudSavedQueryService;
8
+ export { CrudSavedQueryService };
package/dist/index.js CHANGED
@@ -15,6 +15,14 @@ import { GroupByQuerySchema } from "./schemas/GroupBySchema.js";
15
15
  import { ExportBodyResponseSchema } from "./schemas/ExportBodyResponseSchema.js";
16
16
  import { ErrorBodyResponseSchema, ValidationErrorBodyResponseSchema } from "./schemas/ErrorBodyResponseSchema.js";
17
17
  import { CrudSchemaBuilder } from "./builders/CrudSchemaBuilder.js";
18
+ import CrudSavedQueryFastifyRoutes from "./crud-saved-query/routes/CrudSavedQueryRoutes.js";
19
+ import { CrudSavedQueryController } from "./crud-saved-query/controllers/CrudSavedQueryController.js";
20
+ import { CrudSavedQueryService } from "./crud-saved-query/services/CrudSavedQueryService.js";
21
+ import { CrudSavedQueryServiceFactory } from "./crud-saved-query/factory/services/CrudSavedQueryServiceFactory.js";
22
+ import CrudSavedQueryMongoRepository from "./crud-saved-query/repository/mongo/CrudSavedQueryMongoRepository.js";
23
+ import CrudSavedQuerySqliteRepository from "./crud-saved-query/repository/sqlite/CrudSavedQuerySqliteRepository.js";
24
+ import CrudSavedQueryPermissions from "./crud-saved-query/permissions/CrudSavedQueryPermissions.js";
25
+ import { CrudSavedQueryModel, CrudSavedQuerySchema } from "./crud-saved-query/models/CrudSavedQueryModel.js";
18
26
  export {
19
27
  //CRUD
20
28
  AbstractMongoRepository, AbstractSqliteRepository, AbstractService, AbstractFastifyController,
@@ -23,4 +31,6 @@ CrudEventEmitter,
23
31
  //Schemas
24
32
  IdParamSchema, DeleteBodyResponseSchema, PaginateBodyResponseSchema, PaginateQuerySchema, FindQuerySchema, GroupByQuerySchema, SearchQuerySchema, FindByParamSchema, ErrorBodyResponseSchema, ValidationErrorBodyResponseSchema, ExportBodyResponseSchema,
25
33
  //Builder
26
- CrudSchemaBuilder, };
34
+ CrudSchemaBuilder,
35
+ //Crud saved queries
36
+ CrudSavedQueryFastifyRoutes, CrudSavedQueryController, CrudSavedQueryService, CrudSavedQueryServiceFactory, CrudSavedQueryMongoRepository, CrudSavedQuerySqliteRepository, CrudSavedQueryPermissions, CrudSavedQueryModel, CrudSavedQuerySchema, };
@@ -0,0 +1,23 @@
1
+ import AbstractFastifyController from "../../../controllers/AbstractFastifyController.js";
2
+ import CrudSavedQueryServiceFactory from "../factory/services/CrudSavedQueryServiceFactory.js";
3
+ import CrudSavedQueryPermissions from "../permissions/CrudSavedQueryPermissions.js";
4
+ class CrudSavedQueryController extends AbstractFastifyController {
5
+ constructor() {
6
+ super(CrudSavedQueryServiceFactory.instance, CrudSavedQueryPermissions);
7
+ this.tenantField = "tenant";
8
+ this.userField = "user";
9
+ this.tenantFilter = true;
10
+ this.tenantSetter = true;
11
+ this.tenantAssert = true;
12
+ this.userSetter = true;
13
+ this.userAssert = true;
14
+ }
15
+ async preRead(request, filters) {
16
+ if (!request.rbac.hasSomePermission([this.permission.All, this.permission.ViewAll]) && request.rbac.userId) {
17
+ filters.push({ field: "shared", operator: "eq", value: true, orGroup: "crudSavedQueryVisibility" }, { field: this.userField, operator: "eq", value: request.rbac.userId, orGroup: "crudSavedQueryVisibility" });
18
+ }
19
+ return filters;
20
+ }
21
+ }
22
+ export default CrudSavedQueryController;
23
+ export { CrudSavedQueryController };
@@ -0,0 +1,27 @@
1
+ import { COMMON, CommonConfig, DraxConfig } from "@drax/common-back";
2
+ import CrudSavedQueryMongoRepository from "../../repository/mongo/CrudSavedQueryMongoRepository.js";
3
+ import CrudSavedQuerySqliteRepository from "../../repository/sqlite/CrudSavedQuerySqliteRepository.js";
4
+ import { CrudSavedQueryService } from "../../services/CrudSavedQueryService.js";
5
+ import { CrudSavedQueryBaseSchema, CrudSavedQuerySchema } from "../../schemas/CrudSavedQuerySchema.js";
6
+ class CrudSavedQueryServiceFactory {
7
+ static get instance() {
8
+ if (!CrudSavedQueryServiceFactory.service) {
9
+ let repository;
10
+ switch (DraxConfig.getOrLoad(CommonConfig.DbEngine)) {
11
+ case COMMON.DB_ENGINES.MONGODB:
12
+ repository = new CrudSavedQueryMongoRepository();
13
+ break;
14
+ case COMMON.DB_ENGINES.SQLITE:
15
+ repository = new CrudSavedQuerySqliteRepository(DraxConfig.getOrLoad(CommonConfig.SqliteDbFile), false);
16
+ repository.build();
17
+ break;
18
+ default:
19
+ throw new Error("DraxConfig.DB_ENGINE must be one of " + Object.values(COMMON.DB_ENGINES).join(", "));
20
+ }
21
+ CrudSavedQueryServiceFactory.service = new CrudSavedQueryService(repository, CrudSavedQueryBaseSchema, CrudSavedQuerySchema);
22
+ }
23
+ return CrudSavedQueryServiceFactory.service;
24
+ }
25
+ }
26
+ export default CrudSavedQueryServiceFactory;
27
+ export { CrudSavedQueryServiceFactory };
@@ -0,0 +1,40 @@
1
+ import { mongoose } from "@drax/common-back";
2
+ import mongoosePaginate from "mongoose-paginate-v2";
3
+ const FieldFilterSchema = new mongoose.Schema({
4
+ field: { type: String, required: true },
5
+ operator: { type: String, required: false, default: "eq" },
6
+ value: { type: mongoose.Schema.Types.Mixed, required: false },
7
+ orGroup: { type: String, required: false }
8
+ }, { _id: false });
9
+ const DynamicFilterSchema = new mongoose.Schema({
10
+ default: { type: mongoose.Schema.Types.Mixed, required: false },
11
+ label: { type: String, required: false },
12
+ name: { type: String, required: true },
13
+ operator: { type: String, required: false, default: "eq" },
14
+ type: { type: String, required: false, default: "string" },
15
+ permission: { type: String, required: false },
16
+ value: { type: mongoose.Schema.Types.Mixed, required: false },
17
+ ref: { type: String, required: false },
18
+ refDisplay: { type: String, required: false },
19
+ enum: { type: [mongoose.Schema.Types.Mixed], required: false }
20
+ }, { _id: false, strict: false });
21
+ const CrudSavedQuerySchema = new mongoose.Schema({
22
+ entity: { type: String, required: true, index: true },
23
+ name: { type: String, required: true, index: true },
24
+ shared: { type: Boolean, required: false, default: false, index: true },
25
+ columns: [{ type: String, required: true }],
26
+ staticFilters: { type: [FieldFilterSchema], required: false, default: [] },
27
+ dynamicFilters: { type: [DynamicFilterSchema], required: false, default: [] },
28
+ tenant: { type: mongoose.Schema.Types.ObjectId, ref: "Tenant", required: false, index: true },
29
+ user: { type: mongoose.Schema.Types.ObjectId, ref: "User", required: false, index: true }
30
+ }, { timestamps: true });
31
+ CrudSavedQuerySchema.index({ entity: 1, name: 1, tenant: 1, user: 1 });
32
+ CrudSavedQuerySchema.plugin(mongoosePaginate);
33
+ CrudSavedQuerySchema.virtual("id").get(function () {
34
+ return this._id.toString();
35
+ });
36
+ CrudSavedQuerySchema.set("toJSON", { getters: true, virtuals: true });
37
+ CrudSavedQuerySchema.set("toObject", { getters: true, virtuals: true });
38
+ const CrudSavedQueryModel = mongoose.model("CrudSavedQuery", CrudSavedQuerySchema, "CrudSavedQuery");
39
+ export { CrudSavedQuerySchema, CrudSavedQueryModel };
40
+ export default CrudSavedQueryModel;
@@ -0,0 +1,14 @@
1
+ var CrudSavedQueryPermissions;
2
+ (function (CrudSavedQueryPermissions) {
3
+ CrudSavedQueryPermissions["Create"] = "crudSavedQuery:create";
4
+ CrudSavedQueryPermissions["Update"] = "crudSavedQuery:update";
5
+ CrudSavedQueryPermissions["Delete"] = "crudSavedQuery:delete";
6
+ CrudSavedQueryPermissions["View"] = "crudSavedQuery:view";
7
+ CrudSavedQueryPermissions["Manage"] = "crudSavedQuery:manage";
8
+ CrudSavedQueryPermissions["All"] = "crudSavedQuery:all";
9
+ CrudSavedQueryPermissions["ViewAll"] = "crudSavedQuery:viewAll";
10
+ CrudSavedQueryPermissions["UpdateAll"] = "crudSavedQuery:updateAll";
11
+ CrudSavedQueryPermissions["DeleteAll"] = "crudSavedQuery:deleteAll";
12
+ })(CrudSavedQueryPermissions || (CrudSavedQueryPermissions = {}));
13
+ export { CrudSavedQueryPermissions };
14
+ export default CrudSavedQueryPermissions;
@@ -0,0 +1,12 @@
1
+ import AbstractMongoRepository from "../../../../repository/AbstractMongoRepository.js";
2
+ import { CrudSavedQueryModel } from "../../models/CrudSavedQueryModel.js";
3
+ class CrudSavedQueryMongoRepository extends AbstractMongoRepository {
4
+ constructor() {
5
+ super();
6
+ this._model = CrudSavedQueryModel;
7
+ this._searchFields = ["name", "entity"];
8
+ this._populateFields = ["tenant", "user"];
9
+ }
10
+ }
11
+ export default CrudSavedQueryMongoRepository;
12
+ export { CrudSavedQueryMongoRepository };
@@ -0,0 +1,29 @@
1
+ import AbstractSqliteRepository from "../../../../repository/AbstractSqliteRepository.js";
2
+ class CrudSavedQuerySqliteRepository extends AbstractSqliteRepository {
3
+ constructor() {
4
+ super(...arguments);
5
+ this.tableName = "CrudSavedQuery";
6
+ this.searchFields = ["name", "entity"];
7
+ this.booleanFields = ["shared"];
8
+ this.jsonFields = ["columns", "staticFilters", "dynamicFilters"];
9
+ this.identifier = "_id";
10
+ this.populateFields = [
11
+ { field: "tenant", table: "Tenant", identifier: "_id" },
12
+ { field: "user", table: "User", identifier: "_id" }
13
+ ];
14
+ this.tableFields = [
15
+ { name: "entity", type: "TEXT", unique: false, primary: false },
16
+ { name: "name", type: "TEXT", unique: false, primary: false },
17
+ { name: "shared", type: "INTEGER", unique: false, primary: false },
18
+ { name: "columns", type: "TEXT", unique: false, primary: false },
19
+ { name: "staticFilters", type: "TEXT", unique: false, primary: false },
20
+ { name: "dynamicFilters", type: "TEXT", unique: false, primary: false },
21
+ { name: "tenant", type: "TEXT", unique: false, primary: false },
22
+ { name: "user", type: "TEXT", unique: false, primary: false },
23
+ { name: "createdAt", type: "TEXT", unique: false, primary: false },
24
+ { name: "updatedAt", type: "TEXT", unique: false, primary: false }
25
+ ];
26
+ }
27
+ }
28
+ export default CrudSavedQuerySqliteRepository;
29
+ export { CrudSavedQuerySqliteRepository };
@@ -0,0 +1,20 @@
1
+ import CrudSavedQueryController from "../controllers/CrudSavedQueryController.js";
2
+ import { CrudSchemaBuilder } from "../../../builders/CrudSchemaBuilder.js";
3
+ import { CrudSavedQuerySchema, CrudSavedQueryBaseSchema } from "../schemas/CrudSavedQuerySchema.js";
4
+ async function CrudSavedQueryFastifyRoutes(fastify, options) {
5
+ const controller = new CrudSavedQueryController();
6
+ const schemas = new CrudSchemaBuilder(CrudSavedQuerySchema, CrudSavedQueryBaseSchema, CrudSavedQueryBaseSchema, "CrudSavedQuery", "openapi-3.0", ["crud-saved-queries"]);
7
+ fastify.get("/api/crud-saved-queries", { schema: schemas.paginateSchema }, (req, rep) => controller.paginate(req, rep));
8
+ fastify.get("/api/crud-saved-queries/find", { schema: schemas.findSchema }, (req, rep) => controller.find(req, rep));
9
+ fastify.get("/api/crud-saved-queries/search", { schema: schemas.searchSchema }, (req, rep) => controller.search(req, rep));
10
+ fastify.get("/api/crud-saved-queries/:id", { schema: schemas.findByIdSchema }, (req, rep) => controller.findById(req, rep));
11
+ fastify.get("/api/crud-saved-queries/find-one", { schema: schemas.findOneSchema }, (req, rep) => controller.findOne(req, rep));
12
+ fastify.get("/api/crud-saved-queries/find-by/:field/:value", { schema: schemas.findBySchema }, (req, rep) => controller.findBy(req, rep));
13
+ fastify.get("/api/crud-saved-queries/find-one-by/:field/:value", { schema: schemas.findOneBySchema }, (req, rep) => controller.findOneBy(req, rep));
14
+ fastify.post("/api/crud-saved-queries", { schema: schemas.createSchema }, (req, rep) => controller.create(req, rep));
15
+ fastify.put("/api/crud-saved-queries/:id", { schema: schemas.updateSchema }, (req, rep) => controller.update(req, rep));
16
+ fastify.patch("/api/crud-saved-queries/:id", { schema: schemas.updateSchema }, (req, rep) => controller.updatePartial(req, rep));
17
+ fastify.delete("/api/crud-saved-queries/:id", { schema: schemas.deleteSchema }, (req, rep) => controller.delete(req, rep));
18
+ }
19
+ export default CrudSavedQueryFastifyRoutes;
20
+ export { CrudSavedQueryFastifyRoutes };
@@ -0,0 +1,36 @@
1
+ import { z } from "zod";
2
+ const CrudSavedQueryFieldFilterSchema = z.object({
3
+ field: z.string().min(1, "validation.required"),
4
+ operator: z.string().optional().default("eq"),
5
+ value: z.any().optional().nullable(),
6
+ orGroup: z.string().optional()
7
+ });
8
+ const CrudSavedQueryDynamicFilterSchema = z.object({
9
+ default: z.any().optional().nullable(),
10
+ label: z.string().optional(),
11
+ name: z.string().min(1, "validation.required"),
12
+ operator: z.string().optional().default("eq"),
13
+ type: z.string().optional().default("string"),
14
+ permission: z.string().optional(),
15
+ value: z.any().optional().nullable(),
16
+ ref: z.string().optional(),
17
+ refDisplay: z.string().optional(),
18
+ enum: z.array(z.any()).optional()
19
+ }).catchall(z.any());
20
+ const CrudSavedQueryBaseSchema = z.object({
21
+ entity: z.string().min(1, "validation.required"),
22
+ name: z.string().min(1, "validation.required"),
23
+ shared: z.boolean().optional().default(false),
24
+ columns: z.array(z.string()).optional().default([]),
25
+ staticFilters: z.array(CrudSavedQueryFieldFilterSchema).optional().default([]),
26
+ dynamicFilters: z.array(CrudSavedQueryDynamicFilterSchema).optional().default([]),
27
+ tenant: z.coerce.string().optional().nullable(),
28
+ user: z.coerce.string().optional().nullable()
29
+ });
30
+ const CrudSavedQuerySchema = CrudSavedQueryBaseSchema.extend({
31
+ _id: z.coerce.string(),
32
+ tenant: z.object({ _id: z.coerce.string(), name: z.string() }).nullable().optional(),
33
+ user: z.object({ _id: z.coerce.string(), username: z.string() }).nullable().optional()
34
+ });
35
+ export default CrudSavedQuerySchema;
36
+ export { CrudSavedQuerySchema, CrudSavedQueryBaseSchema };
@@ -0,0 +1,8 @@
1
+ import AbstractService from "../../../services/AbstractService.js";
2
+ class CrudSavedQueryService extends AbstractService {
3
+ constructor(repository, baseSchema, fullSchema) {
4
+ super(repository, baseSchema, fullSchema);
5
+ }
6
+ }
7
+ export default CrudSavedQueryService;
8
+ export { CrudSavedQueryService };
package/package.json CHANGED
@@ -3,7 +3,7 @@
3
3
  "publishConfig": {
4
4
  "access": "public"
5
5
  },
6
- "version": "3.18.0",
6
+ "version": "3.20.0",
7
7
  "description": "Crud utils across modules",
8
8
  "main": "dist/index.js",
9
9
  "types": "types/index.d.ts",
@@ -25,7 +25,7 @@
25
25
  "@drax/common-back": "^3.18.0",
26
26
  "@drax/common-share": "^3.0.0",
27
27
  "@drax/identity-share": "^3.15.0",
28
- "@drax/media-back": "^3.18.0",
28
+ "@drax/media-back": "^3.20.0",
29
29
  "@graphql-tools/load-files": "^7.0.0",
30
30
  "@graphql-tools/merge": "^9.0.4",
31
31
  "mongoose": "^8.23.0",
@@ -47,5 +47,5 @@
47
47
  "typescript": "^5.9.3",
48
48
  "vitest": "^3.2.4"
49
49
  },
50
- "gitHead": "c7709f3912ba1f8ae6a7e78376e17d50b32cfa7d"
50
+ "gitHead": "6d4aea4d05133be679166e398ec6a3ae61503d9e"
51
51
  }
@@ -0,0 +1,32 @@
1
+ import AbstractFastifyController from "../../controllers/AbstractFastifyController.js";
2
+ import CrudSavedQueryServiceFactory from "../factory/services/CrudSavedQueryServiceFactory.js";
3
+ import CrudSavedQueryPermissions from "../permissions/CrudSavedQueryPermissions.js";
4
+ import type {IDraxFieldFilter} from "@drax/crud-share";
5
+ import type {ICrudSavedQuery, ICrudSavedQueryBase} from "../interfaces/ICrudSavedQuery";
6
+ import type {CustomRequest} from "../../controllers/AbstractFastifyController";
7
+
8
+ class CrudSavedQueryController extends AbstractFastifyController<ICrudSavedQuery, ICrudSavedQueryBase, ICrudSavedQueryBase> {
9
+ constructor() {
10
+ super(CrudSavedQueryServiceFactory.instance, CrudSavedQueryPermissions);
11
+ this.tenantField = "tenant";
12
+ this.userField = "user";
13
+ this.tenantFilter = true;
14
+ this.tenantSetter = true;
15
+ this.tenantAssert = true;
16
+ this.userSetter = true;
17
+ this.userAssert = true;
18
+ this.userFilter = false
19
+ }
20
+
21
+ async preRead(request: CustomRequest, filters: IDraxFieldFilter[]): Promise<IDraxFieldFilter[]> {
22
+ filters.push(
23
+ {field: "shared", operator: "eq", value: true, orGroup: "crudSavedQueryVisibility"},
24
+ {field: this.userField, operator: "eq", value: request.rbac.userId, orGroup: "crudSavedQueryVisibility"}
25
+ );
26
+
27
+ return filters;
28
+ }
29
+ }
30
+
31
+ export default CrudSavedQueryController;
32
+ export {CrudSavedQueryController};
@@ -0,0 +1,41 @@
1
+ import {COMMON, CommonConfig, DraxConfig} from "@drax/common-back";
2
+ import CrudSavedQueryMongoRepository from "../../repository/mongo/CrudSavedQueryMongoRepository.js";
3
+ import CrudSavedQuerySqliteRepository from "../../repository/sqlite/CrudSavedQuerySqliteRepository.js";
4
+ import {CrudSavedQueryService} from "../../services/CrudSavedQueryService.js";
5
+ import {CrudSavedQueryBaseSchema, CrudSavedQuerySchema} from "../../schemas/CrudSavedQuerySchema.js";
6
+ import type {ICrudSavedQueryRepository} from "../../interfaces/ICrudSavedQueryRepository";
7
+
8
+ class CrudSavedQueryServiceFactory {
9
+ private static service: CrudSavedQueryService;
10
+
11
+ public static get instance(): CrudSavedQueryService {
12
+ if (!CrudSavedQueryServiceFactory.service) {
13
+ let repository: ICrudSavedQueryRepository;
14
+
15
+ switch (DraxConfig.getOrLoad(CommonConfig.DbEngine)) {
16
+ case COMMON.DB_ENGINES.MONGODB:
17
+ repository = new CrudSavedQueryMongoRepository();
18
+ break;
19
+ case COMMON.DB_ENGINES.SQLITE:
20
+ repository = new CrudSavedQuerySqliteRepository(
21
+ DraxConfig.getOrLoad(CommonConfig.SqliteDbFile),
22
+ false
23
+ );
24
+ repository.build();
25
+ break;
26
+ default:
27
+ throw new Error("DraxConfig.DB_ENGINE must be one of " + Object.values(COMMON.DB_ENGINES).join(", "));
28
+ }
29
+
30
+ CrudSavedQueryServiceFactory.service = new CrudSavedQueryService(
31
+ repository,
32
+ CrudSavedQueryBaseSchema,
33
+ CrudSavedQuerySchema
34
+ );
35
+ }
36
+ return CrudSavedQueryServiceFactory.service;
37
+ }
38
+ }
39
+
40
+ export default CrudSavedQueryServiceFactory;
41
+ export {CrudSavedQueryServiceFactory};
@@ -0,0 +1,20 @@
1
+ import type {IDraxFieldFilter, IEntityCrudFilter} from "@drax/crud-share/dist";
2
+
3
+ interface ICrudSavedQueryBase {
4
+ entity: string
5
+ name: string
6
+ shared?: boolean
7
+ columns: string[]
8
+ staticFilters: IDraxFieldFilter[]
9
+ dynamicFilters: IEntityCrudFilter[]
10
+ tenant?: any
11
+ user?: any
12
+ createdAt?: Date
13
+ updatedAt?: Date
14
+ }
15
+
16
+ interface ICrudSavedQuery extends ICrudSavedQueryBase {
17
+ _id: string
18
+ }
19
+
20
+ export type {ICrudSavedQuery, ICrudSavedQueryBase};
@@ -0,0 +1,7 @@
1
+ import type {IDraxCrudRepository} from "@drax/crud-share";
2
+ import type {ICrudSavedQuery, ICrudSavedQueryBase} from "./ICrudSavedQuery";
3
+
4
+ interface ICrudSavedQueryRepository extends IDraxCrudRepository<ICrudSavedQuery, ICrudSavedQueryBase, ICrudSavedQueryBase> {
5
+ }
6
+
7
+ export {ICrudSavedQueryRepository};