@autofleet/sadot 0.0.1-beta.9 → 0.0.2-beta

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 (145) hide show
  1. package/dist/jest.config.d.ts +12 -0
  2. package/dist/src/api/index.d.ts +2 -0
  3. package/dist/{api → src/api}/index.js +0 -1
  4. package/dist/src/api/v1/definition/index.d.ts +2 -0
  5. package/dist/{api → src/api}/v1/definition/index.js +23 -27
  6. package/dist/src/api/v1/definition/validations.d.ts +2 -0
  7. package/dist/{api → src/api}/v1/definition/validations.js +10 -10
  8. package/dist/src/api/v1/errors.d.ts +2 -0
  9. package/dist/{api → src/api}/v1/errors.js +0 -1
  10. package/dist/src/api/v1/index.d.ts +2 -0
  11. package/dist/{api → src/api}/v1/index.js +1 -2
  12. package/dist/src/errors/index.d.ts +16 -0
  13. package/dist/src/errors/index.js +45 -0
  14. package/dist/src/events/index.d.ts +4 -0
  15. package/dist/{events → src/events}/index.js +21 -2
  16. package/dist/src/hooks/create.d.ts +9 -0
  17. package/dist/{hooks → src/hooks}/create.js +14 -17
  18. package/dist/src/hooks/enrich.d.ts +5 -0
  19. package/dist/src/hooks/enrich.js +118 -0
  20. package/dist/src/hooks/find.d.ts +1 -0
  21. package/dist/src/hooks/find.js +29 -0
  22. package/dist/src/hooks/index.d.ts +6 -0
  23. package/dist/{hooks → src/hooks}/index.js +2 -2
  24. package/dist/src/hooks/update.d.ts +9 -0
  25. package/dist/{hooks → src/hooks}/update.js +7 -22
  26. package/dist/src/hooks/workaround.d.ts +10 -0
  27. package/dist/{hooks → src/hooks}/workaround.js +3 -13
  28. package/dist/src/index.d.ts +11 -0
  29. package/dist/src/index.js +105 -0
  30. package/dist/src/models/CustomFieldDefinition.d.ts +23 -0
  31. package/dist/{models → src/models}/CustomFieldDefinition.js +22 -18
  32. package/dist/src/models/CustomFieldValue.d.ts +15 -0
  33. package/dist/{models → src/models}/CustomFieldValue.js +24 -40
  34. package/dist/src/models/index.d.ts +8 -0
  35. package/dist/src/models/index.js +87 -0
  36. package/dist/src/models/tests/AssociatedTestModel.d.ts +12 -0
  37. package/dist/{models → src/models}/tests/AssociatedTestModel.js +0 -1
  38. package/dist/src/models/tests/TestModel.d.ts +11 -0
  39. package/dist/{models → src/models}/tests/TestModel.js +0 -1
  40. package/dist/src/repository/definition.d.ts +17 -0
  41. package/dist/src/repository/definition.js +80 -0
  42. package/dist/src/repository/value.d.ts +24 -0
  43. package/dist/{repository → src/repository}/value.js +22 -30
  44. package/dist/src/tests/api/test-api.d.ts +2 -0
  45. package/dist/{tests → src/tests}/api/test-api.js +12 -22
  46. package/dist/src/tests/helpers/database-config.d.ts +15 -0
  47. package/dist/{tests → src/tests}/helpers/database-config.js +0 -1
  48. package/dist/src/tests/helpers/index.d.ts +2 -0
  49. package/dist/src/tests/helpers/index.js +18 -0
  50. package/dist/src/tests/mocks/definition.mock.d.ts +37 -0
  51. package/dist/{tests/mocks/index.js → src/tests/mocks/definition.mock.js} +20 -17
  52. package/dist/src/tests/mocks/events.mock.d.ts +3 -0
  53. package/dist/{tests → src/tests}/mocks/events.mock.js +0 -1
  54. package/dist/src/tests/mocks/testModel.d.ts +12 -0
  55. package/dist/{tests → src/tests}/mocks/testModel.js +4 -14
  56. package/dist/src/types/definition/index.d.ts +23 -0
  57. package/dist/{types → src/types}/definition/index.js +0 -1
  58. package/dist/src/types/index.d.ts +13 -0
  59. package/dist/{types → src/types}/index.js +0 -1
  60. package/dist/src/types/value/index.d.ts +15 -0
  61. package/dist/{types → src/types}/value/index.js +0 -1
  62. package/dist/src/utils/constants/index.d.ts +1 -0
  63. package/dist/src/utils/constants/index.js +5 -0
  64. package/dist/src/utils/db/index.d.ts +4 -0
  65. package/dist/{utils → src/utils}/db/index.js +8 -1
  66. package/dist/src/utils/logger/index.d.ts +2 -0
  67. package/dist/{utils → src/utils}/logger/index.js +2 -2
  68. package/dist/src/utils/validations/custom-fields.d.ts +2 -0
  69. package/dist/{utils → src/utils}/validations/custom-fields.js +0 -1
  70. package/dist/src/utils/validations/custom.d.ts +15 -0
  71. package/dist/src/utils/validations/custom.js +42 -0
  72. package/dist/src/utils/validations/index.d.ts +2 -0
  73. package/dist/{utils → src/utils}/validations/index.js +0 -1
  74. package/dist/src/utils/validations/type.d.ts +18 -0
  75. package/dist/src/utils/validations/type.js +50 -0
  76. package/dist/src/utils/validations/validators.d.ts +12 -0
  77. package/dist/src/utils/validations/validators.js +33 -0
  78. package/package.json +3 -1
  79. package/src/api/v1/definition/index.ts +15 -8
  80. package/src/api/v1/definition/validations.ts +11 -25
  81. package/src/api/v1/index.ts +1 -1
  82. package/src/errors/index.ts +42 -0
  83. package/src/events/index.ts +23 -1
  84. package/src/hooks/create.ts +7 -3
  85. package/src/hooks/enrich.ts +125 -0
  86. package/src/hooks/find.ts +2 -101
  87. package/src/hooks/index.ts +2 -1
  88. package/src/hooks/update.ts +2 -15
  89. package/src/index.ts +52 -17
  90. package/src/models/CustomFieldDefinition.ts +23 -16
  91. package/src/models/CustomFieldValue.ts +7 -7
  92. package/src/models/index.ts +72 -16
  93. package/src/repository/definition.ts +26 -33
  94. package/src/repository/value.ts +4 -2
  95. package/src/tests/mocks/{index.ts → definition.mock.ts} +2 -4
  96. package/src/types/index.ts +4 -6
  97. package/src/utils/constants/index.ts +2 -0
  98. package/src/utils/db/index.ts +7 -0
  99. package/src/utils/logger/index.ts +3 -1
  100. package/src/utils/validations/custom.ts +26 -44
  101. package/src/utils/validations/type.ts +23 -6
  102. package/src/utils/validations/validators.ts +34 -0
  103. package/tsconfig.json +9 -25
  104. package/dist/api/index.js.map +0 -1
  105. package/dist/api/v1/definition/index.js.map +0 -1
  106. package/dist/api/v1/definition/validations.js.map +0 -1
  107. package/dist/api/v1/errors.js.map +0 -1
  108. package/dist/api/v1/index.js.map +0 -1
  109. package/dist/events/index.js.map +0 -1
  110. package/dist/hooks/create.js.map +0 -1
  111. package/dist/hooks/find.js +0 -136
  112. package/dist/hooks/find.js.map +0 -1
  113. package/dist/hooks/index.js.map +0 -1
  114. package/dist/hooks/update.js.map +0 -1
  115. package/dist/hooks/workaround.js.map +0 -1
  116. package/dist/index.js +0 -81
  117. package/dist/index.js.map +0 -1
  118. package/dist/models/CustomFieldDefinition.js.map +0 -1
  119. package/dist/models/CustomFieldValue.js.map +0 -1
  120. package/dist/models/index.js +0 -50
  121. package/dist/models/index.js.map +0 -1
  122. package/dist/models/tests/AssociatedTestModel.js.map +0 -1
  123. package/dist/models/tests/TestModel.js.map +0 -1
  124. package/dist/repository/definition.js +0 -101
  125. package/dist/repository/definition.js.map +0 -1
  126. package/dist/repository/value.js.map +0 -1
  127. package/dist/tests/api/test-api.js.map +0 -1
  128. package/dist/tests/helpers/database-config.js.map +0 -1
  129. package/dist/tests/helpers/index.js +0 -28
  130. package/dist/tests/helpers/index.js.map +0 -1
  131. package/dist/tests/mocks/events.mock.js.map +0 -1
  132. package/dist/tests/mocks/index.js.map +0 -1
  133. package/dist/tests/mocks/testModel.js.map +0 -1
  134. package/dist/tsconfig.tsbuildinfo +0 -1
  135. package/dist/types/definition/index.js.map +0 -1
  136. package/dist/types/index.js.map +0 -1
  137. package/dist/types/value/index.js.map +0 -1
  138. package/dist/utils/db/index.js.map +0 -1
  139. package/dist/utils/logger/index.js.map +0 -1
  140. package/dist/utils/validations/custom-fields.js.map +0 -1
  141. package/dist/utils/validations/custom.js +0 -59
  142. package/dist/utils/validations/custom.js.map +0 -1
  143. package/dist/utils/validations/index.js.map +0 -1
  144. package/dist/utils/validations/type.js +0 -32
  145. package/dist/utils/validations/type.js.map +0 -1
@@ -0,0 +1,12 @@
1
+ export const testEnvironment: string;
2
+ export const roots: string[];
3
+ export const transform: {
4
+ '^.+\\.tsx?$': string;
5
+ };
6
+ export const testRegex: string;
7
+ export const moduleFileExtensions: string[];
8
+ export namespace coverageThreshold {
9
+ namespace global {
10
+ const lines: number;
11
+ }
12
+ }
@@ -0,0 +1,2 @@
1
+ declare const router: import("express-serve-static-core").Router;
2
+ export default router;
@@ -9,4 +9,3 @@ const v1_1 = __importDefault(require("./v1"));
9
9
  const router = (0, express_1.Router)({ mergeParams: true });
10
10
  router.use('/v1', v1_1.default);
11
11
  exports.default = router;
12
- //# sourceMappingURL=index.js.map
@@ -0,0 +1,2 @@
1
+ declare const router: import("express-serve-static-core").Router;
2
+ export default router;
@@ -22,15 +22,6 @@ var __importStar = (this && this.__importStar) || function (mod) {
22
22
  __setModuleDefault(result, mod);
23
23
  return result;
24
24
  };
25
- var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
26
- function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
27
- return new (P || (P = Promise))(function (resolve, reject) {
28
- function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
29
- function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
30
- function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
31
- step((generator = generator.apply(thisArg, _arguments || [])).next());
32
- });
33
- };
34
25
  var __importDefault = (this && this.__importDefault) || function (mod) {
35
26
  return (mod && mod.__esModule) ? mod : { "default": mod };
36
27
  };
@@ -47,26 +38,29 @@ const toPascalCase = (str) => str.replace(/(^\w|-\w)/g, (subStr) => subStr.repla
47
38
  /**
48
39
  * Create
49
40
  */
50
- router.post('/', (req, res) => __awaiter(void 0, void 0, void 0, function* () {
41
+ router.post('/', async (req, res) => {
51
42
  const { modelName } = req.params;
52
43
  const modelType = toPascalCase(modelName);
53
44
  try {
54
- const validatedPayload = yield (0, validations_1.validateCustomFieldDefinitionCreation)(Object.assign(Object.assign({}, req.body), { modelType }));
55
- const customFieldDefinition = yield DefinitionRepo.create(validatedPayload);
45
+ const validatedPayload = await (0, validations_1.validateCustomFieldDefinitionCreation)(req.body);
46
+ const customFieldDefinition = await DefinitionRepo.create({
47
+ ...validatedPayload,
48
+ modelType,
49
+ });
56
50
  return res.status(201).json(customFieldDefinition);
57
51
  }
58
52
  catch (err) {
59
53
  logger_1.default.error('Failed to create custom field definition', err);
60
54
  return (0, errors_2.default)(err, res, { message: `Error in create ${ENTITY} request` });
61
55
  }
62
- }));
56
+ });
63
57
  /**
64
58
  * Get by id
65
59
  */
66
- router.get('/:customFieldDefinitionId', (req, res) => __awaiter(void 0, void 0, void 0, function* () {
60
+ router.get('/:customFieldDefinitionId', async (req, res) => {
67
61
  const { customFieldDefinitionId } = req.params;
68
62
  try {
69
- const customFieldDefinition = yield DefinitionRepo.findById(customFieldDefinitionId);
63
+ const customFieldDefinition = await DefinitionRepo.findById(customFieldDefinitionId);
70
64
  if (!customFieldDefinition) {
71
65
  throw new errors_1.ResourceNotFoundError();
72
66
  }
@@ -76,47 +70,49 @@ router.get('/:customFieldDefinitionId', (req, res) => __awaiter(void 0, void 0,
76
70
  logger_1.default.error('Failed to fetch custom field definition', err);
77
71
  return (0, errors_2.default)(err, res, { message: `Error in get ${ENTITY} request` });
78
72
  }
79
- }));
73
+ });
80
74
  /**
81
75
  * Get all
82
76
  */
83
- router.get('/', (req, res) => __awaiter(void 0, void 0, void 0, function* () {
77
+ router.get('/', async (req, res) => {
84
78
  const { modelName } = req.params;
79
+ const { entityIds } = req.query;
85
80
  const modelType = toPascalCase(modelName);
86
81
  try {
87
- const customFieldDefinitions = yield DefinitionRepo.findAll({
88
- modelType,
89
- }, { withDisabled: true });
82
+ const where = { modelType };
83
+ if (entityIds?.length > 0) {
84
+ where.entityId = entityIds;
85
+ }
86
+ const customFieldDefinitions = await DefinitionRepo.findAll({ ...where }, { withDisabled: true });
90
87
  return res.json(customFieldDefinitions);
91
88
  }
92
89
  catch (err) {
93
90
  logger_1.default.error('Failed to fetch custom field definitions', err);
94
91
  return (0, errors_2.default)(err, res, { message: `Error in get all ${ENTITY} request` });
95
92
  }
96
- }));
93
+ });
97
94
  /**
98
95
  * Update
99
96
  */
100
- router.patch('/:customFieldDefinitionId', (req, res) => __awaiter(void 0, void 0, void 0, function* () {
97
+ router.patch('/:customFieldDefinitionId', async (req, res) => {
101
98
  const { customFieldDefinitionId, modelName } = req.params;
102
99
  const modelType = toPascalCase(modelName);
103
100
  try {
104
101
  // eslint-disable-next-line max-len
105
- const validatedPayload = yield (0, validations_1.validateCustomFieldDefinitionUpdate)(req.body);
106
- const customFieldDefinition = yield DefinitionRepo.findByWhere({
102
+ const validatedPayload = await (0, validations_1.validateCustomFieldDefinitionUpdate)(req.body);
103
+ const customFieldDefinition = await DefinitionRepo.findByWhere({
107
104
  id: customFieldDefinitionId,
108
105
  modelType,
109
106
  });
110
107
  if (!customFieldDefinition) {
111
108
  throw new errors_1.ResourceNotFoundError();
112
109
  }
113
- const updatedCustomFieldDefinition = yield DefinitionRepo.update(customFieldDefinitionId, validatedPayload);
110
+ const updatedCustomFieldDefinition = await DefinitionRepo.update(customFieldDefinitionId, { ...validatedPayload, modelType });
114
111
  return res.status(200).json(updatedCustomFieldDefinition);
115
112
  }
116
113
  catch (err) {
117
114
  logger_1.default.error('Failed to patch custom field definition', err);
118
115
  return (0, errors_2.default)(err, res, { message: `Error in update ${ENTITY} request` });
119
116
  }
120
- }));
117
+ });
121
118
  exports.default = router;
122
- //# sourceMappingURL=index.js.map
@@ -0,0 +1,2 @@
1
+ export declare const validateCustomFieldDefinitionCreation: (payload: any) => any;
2
+ export declare const validateCustomFieldDefinitionUpdate: (payload: any) => any;
@@ -5,26 +5,27 @@ var __importDefault = (this && this.__importDefault) || function (mod) {
5
5
  Object.defineProperty(exports, "__esModule", { value: true });
6
6
  exports.validateCustomFieldDefinitionUpdate = exports.validateCustomFieldDefinitionCreation = void 0;
7
7
  const joi_1 = __importDefault(require("@hapi/joi"));
8
- const CustomFieldDefinition_1 = require("../../../models/CustomFieldDefinition");
8
+ const type_1 = require("../../../utils/validations/type");
9
+ const ValidationSchema = joi_1.default.when('fieldType', {
10
+ is: type_1.CustomFieldDefinitionType.SELECT,
11
+ then: joi_1.default.array().items(joi_1.default.string()).min(1).unique(),
12
+ otherwise: joi_1.default.any(),
13
+ });
9
14
  const CustomFieldDefinitionCreationSchema = joi_1.default.object({
10
15
  name: joi_1.default.string().required(),
11
16
  displayName: joi_1.default.string().required(),
12
- validation: joi_1.default.object().required(),
13
- fieldType: joi_1.default.string().valid(CustomFieldDefinition_1.CustomFieldDefinitionType.BOOLEAN, CustomFieldDefinition_1.CustomFieldDefinitionType.NUMBER, CustomFieldDefinition_1.CustomFieldDefinitionType.DATE, CustomFieldDefinition_1.CustomFieldDefinitionType.DATETIME, CustomFieldDefinition_1.CustomFieldDefinitionType.TEXT, CustomFieldDefinition_1.CustomFieldDefinitionType.IMAGE, CustomFieldDefinition_1.CustomFieldDefinitionType.ENUM).required(),
17
+ validation: ValidationSchema,
18
+ fieldType: joi_1.default.string().valid(...Object.values(type_1.CustomFieldDefinitionType)).required(),
14
19
  entityId: joi_1.default.string().guid().required(),
15
20
  entityType: joi_1.default.string().required(),
16
- modelType: joi_1.default.string().required(),
17
21
  description: joi_1.default.string(),
18
22
  required: joi_1.default.boolean(),
19
23
  disabled: joi_1.default.boolean(),
20
24
  });
21
25
  const CustomFieldDefinitionUpdateSchema = joi_1.default.object({
22
26
  displayName: joi_1.default.string(),
23
- validation: joi_1.default.object(),
24
- fieldType: joi_1.default.string().valid(CustomFieldDefinition_1.CustomFieldDefinitionType.BOOLEAN, CustomFieldDefinition_1.CustomFieldDefinitionType.NUMBER, CustomFieldDefinition_1.CustomFieldDefinitionType.DATE, CustomFieldDefinition_1.CustomFieldDefinitionType.DATETIME, CustomFieldDefinition_1.CustomFieldDefinitionType.TEXT, CustomFieldDefinition_1.CustomFieldDefinitionType.IMAGE, CustomFieldDefinition_1.CustomFieldDefinitionType.ENUM),
25
- entityId: joi_1.default.string().guid(),
26
- entityType: joi_1.default.string(),
27
- modelType: joi_1.default.string(),
27
+ validation: ValidationSchema,
28
+ fieldType: joi_1.default.string().valid(...Object.values(type_1.CustomFieldDefinitionType)),
28
29
  description: joi_1.default.string(),
29
30
  required: joi_1.default.boolean(),
30
31
  disabled: joi_1.default.boolean(),
@@ -33,4 +34,3 @@ const validateCustomFieldDefinitionCreation = (payload) => CustomFieldDefinition
33
34
  exports.validateCustomFieldDefinitionCreation = validateCustomFieldDefinitionCreation;
34
35
  const validateCustomFieldDefinitionUpdate = (payload) => CustomFieldDefinitionUpdateSchema.validateAsync(payload, { abortEarly: false });
35
36
  exports.validateCustomFieldDefinitionUpdate = validateCustomFieldDefinitionUpdate;
36
- //# sourceMappingURL=validations.js.map
@@ -0,0 +1,2 @@
1
+ declare const _default: (err: any, res: any, additionalData?: {}) => any;
2
+ export default _default;
@@ -13,4 +13,3 @@ exports.default = (err, res, additionalData = {}) => {
13
13
  }
14
14
  return (0, errors_1.handleError)(error, res, additionalData);
15
15
  };
16
- //# sourceMappingURL=errors.js.map
@@ -0,0 +1,2 @@
1
+ declare const router: import("express-serve-static-core").Router;
2
+ export default router;
@@ -6,6 +6,5 @@ Object.defineProperty(exports, "__esModule", { value: true });
6
6
  const express_1 = require("express");
7
7
  const definition_1 = __importDefault(require("./definition"));
8
8
  const router = (0, express_1.Router)({ mergeParams: true });
9
- router.use('/:modelName/custom-field-definitions', definition_1.default);
9
+ router.use('/custom-field-definitions/:modelName', definition_1.default);
10
10
  exports.default = router;
11
- //# sourceMappingURL=index.js.map
@@ -0,0 +1,16 @@
1
+ import { BadRequest } from '@autofleet/errors';
2
+ export declare class MissingRequiredCustomFieldError extends BadRequest {
3
+ constructor(missingFields: string[]);
4
+ }
5
+ export declare class UnsupportedCustomFieldTypeError extends BadRequest {
6
+ constructor(fieldType: string);
7
+ }
8
+ export declare class UnsupportedCustomValidationError extends BadRequest {
9
+ constructor(fieldType: string);
10
+ }
11
+ export declare class InvalidValueError extends BadRequest {
12
+ constructor(value: any, fieldType: string);
13
+ }
14
+ export declare class MissingDefinitionError extends BadRequest {
15
+ constructor(fieldNames: string[]);
16
+ }
@@ -0,0 +1,45 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.MissingDefinitionError = exports.InvalidValueError = exports.UnsupportedCustomValidationError = exports.UnsupportedCustomFieldTypeError = exports.MissingRequiredCustomFieldError = void 0;
4
+ /* eslint-disable max-classes-per-file */
5
+ const errors_1 = require("@autofleet/errors");
6
+ class MissingRequiredCustomFieldError extends errors_1.BadRequest {
7
+ constructor(missingFields) {
8
+ const err = new Error(`The following custom fields are required: ${missingFields.join(',')}`);
9
+ super([err], null, missingFields);
10
+ this.message = 'MISSING_REQUIRED_CUSTOM_FIELDS';
11
+ }
12
+ }
13
+ exports.MissingRequiredCustomFieldError = MissingRequiredCustomFieldError;
14
+ class UnsupportedCustomFieldTypeError extends errors_1.BadRequest {
15
+ constructor(fieldType) {
16
+ const err = new Error(`Type "${fieldType}" is not supported`);
17
+ super([err], null, null);
18
+ this.message = 'UNSUPPORTED_CUSTOM_FIELD_TYPE';
19
+ }
20
+ }
21
+ exports.UnsupportedCustomFieldTypeError = UnsupportedCustomFieldTypeError;
22
+ class UnsupportedCustomValidationError extends errors_1.BadRequest {
23
+ constructor(fieldType) {
24
+ const err = new Error(`Validation for "${fieldType}" is not supported`);
25
+ super([err], null, null);
26
+ this.message = 'UNSUPPORTED_CUSTOM_VALIDATION_TYPE';
27
+ }
28
+ }
29
+ exports.UnsupportedCustomValidationError = UnsupportedCustomValidationError;
30
+ class InvalidValueError extends errors_1.BadRequest {
31
+ constructor(value, fieldType) {
32
+ const err = new Error(`Invalid "${fieldType}" value ${JSON.stringify(value)}`);
33
+ super([err], null, null);
34
+ this.message = 'INVALID_VALUE';
35
+ }
36
+ }
37
+ exports.InvalidValueError = InvalidValueError;
38
+ class MissingDefinitionError extends errors_1.BadRequest {
39
+ constructor(fieldNames) {
40
+ const err = new Error(`Missing custom field definition for field ${fieldNames.join(',')}`);
41
+ super([err], null, null);
42
+ this.message = 'MISSING_DEFINITION';
43
+ }
44
+ }
45
+ exports.MissingDefinitionError = MissingDefinitionError;
@@ -0,0 +1,4 @@
1
+ import Events from '@autofleet/events';
2
+ declare const events: Events;
3
+ export declare const sendDimEvent: (instance: any) => void;
4
+ export default events;
@@ -7,6 +7,19 @@ exports.sendDimEvent = void 0;
7
7
  const events_1 = __importDefault(require("@autofleet/events"));
8
8
  const logger_1 = __importDefault(require("../utils/logger"));
9
9
  const events = new events_1.default({ logger: logger_1.default });
10
+ const KEYS_TO_CONVERT = ['value'];
11
+ const stringifyBools = (savedObject, keysToConvert) => {
12
+ if (Object.keys(savedObject).some((key) => keysToConvert.includes(key))) {
13
+ const objectToReturn = { ...savedObject };
14
+ keysToConvert.forEach((key) => {
15
+ if (typeof savedObject[key] === 'boolean') {
16
+ objectToReturn[key] = savedObject[key].toString();
17
+ }
18
+ });
19
+ return objectToReturn;
20
+ }
21
+ return savedObject;
22
+ };
10
23
  const modelTableMapping = {
11
24
  CustomFieldDefinition: {
12
25
  tableName: 'dim_custom_field_definition',
@@ -20,9 +33,15 @@ const modelTableMapping = {
20
33
  const sendDimEvent = (instance) => {
21
34
  const mapping = modelTableMapping[instance.constructor.name];
22
35
  if (mapping) {
23
- events.sendObject(mapping.tableName, mapping.eventVersion, instance.get());
36
+ let objectToSend = instance.get();
37
+ try {
38
+ objectToSend = stringifyBools(instance.get(), KEYS_TO_CONVERT);
39
+ }
40
+ catch (err) {
41
+ logger_1.default.error('Failed to convert booleans in dim event payload', err);
42
+ }
43
+ events.sendObject(mapping.tableName, mapping.eventVersion, objectToSend);
24
44
  }
25
45
  };
26
46
  exports.sendDimEvent = sendDimEvent;
27
47
  exports.default = events;
28
- //# sourceMappingURL=index.js.map
@@ -0,0 +1,9 @@
1
+ /**
2
+ * A hook to create the custom fields when updating a model (more then one instance).
3
+ */
4
+ export declare const beforeBulkCreate: (options: any) => void;
5
+ /**
6
+ * A hook to create the custom fields when updating a model instance.
7
+ * TODO - cleanup if update fail
8
+ */
9
+ export declare const beforeCreate: (scopeAttributes: string[]) => (instance: any, options: any) => Promise<void>;
@@ -22,19 +22,15 @@ var __importStar = (this && this.__importStar) || function (mod) {
22
22
  __setModuleDefault(result, mod);
23
23
  return result;
24
24
  };
25
- var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
26
- function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
27
- return new (P || (P = Promise))(function (resolve, reject) {
28
- function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
29
- function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
30
- function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
31
- step((generator = generator.apply(thisArg, _arguments || [])).next());
32
- });
25
+ var __importDefault = (this && this.__importDefault) || function (mod) {
26
+ return (mod && mod.__esModule) ? mod : { "default": mod };
33
27
  };
34
28
  Object.defineProperty(exports, "__esModule", { value: true });
35
29
  exports.beforeCreate = exports.beforeBulkCreate = void 0;
30
+ const logger_1 = __importDefault(require("../utils/logger"));
36
31
  const ValueRepo = __importStar(require("../repository/value"));
37
32
  const DefinitionRepo = __importStar(require("../repository/definition"));
33
+ const errors_1 = require("../errors");
38
34
  /**
39
35
  * A hook to create the custom fields when updating a model (more then one instance).
40
36
  */
@@ -48,26 +44,27 @@ exports.beforeBulkCreate = beforeBulkCreate;
48
44
  * A hook to create the custom fields when updating a model instance.
49
45
  * TODO - cleanup if update fail
50
46
  */
51
- const beforeCreate = (scopeAttributes) => (instance, options) => __awaiter(void 0, void 0, void 0, function* () {
47
+ const beforeCreate = (scopeAttributes) => async (instance, options) => {
48
+ logger_1.default.debug('sadot - before create hook');
52
49
  const { fields } = options;
53
50
  const modelType = instance.constructor.name;
54
51
  const identifiers = scopeAttributes.map((attribute) => instance[attribute]);
55
52
  // get all model's required definitions
56
- const requiredFieldsNames = yield DefinitionRepo.getRequiredFields(modelType, instance.id, identifiers);
53
+ const requiredFieldsNames = await DefinitionRepo.getRequiredFields(modelType, instance.id, identifiers);
57
54
  const customFieldsIdx = fields.indexOf('customFields');
58
55
  const { customFields } = instance;
59
56
  if (customFieldsIdx > -1 && customFields) {
60
57
  const fieldsNames = Object.keys(customFields);
61
- if (requiredFieldsNames.some((name) => !fieldsNames.includes(name))) {
62
- throw new Error('some fields are required');
58
+ const missingFields = requiredFieldsNames.filter((name) => !fieldsNames.includes(name));
59
+ if (missingFields?.length > 0) {
60
+ throw new errors_1.MissingRequiredCustomFieldError(missingFields);
63
61
  }
64
- yield ValueRepo.updateValues(modelType, instance.id, identifiers, customFields, { transaction: options.transaction });
62
+ await ValueRepo.updateValues(modelType, instance.id, identifiers, customFields, { transaction: options.transaction });
65
63
  // eslint-disable-next-line no-param-reassign
66
64
  fields.splice(customFieldsIdx, 1);
67
65
  }
68
- else if ((requiredFieldsNames === null || requiredFieldsNames === void 0 ? void 0 : requiredFieldsNames.length) > 0) {
69
- throw new Error('some fields are required');
66
+ else if (requiredFieldsNames?.length > 0) {
67
+ throw new errors_1.MissingRequiredCustomFieldError(requiredFieldsNames);
70
68
  }
71
- });
69
+ };
72
70
  exports.beforeCreate = beforeCreate;
73
- //# sourceMappingURL=create.js.map
@@ -0,0 +1,5 @@
1
+ /**
2
+ * A hook to attach the custom fields when fetching a model instances.
3
+ */
4
+ declare const enrichResults: (modelType: string, scopeAttributes: string[]) => (instancesOrInstance: any | any[], options: any) => Promise<void>;
5
+ export default enrichResults;
@@ -0,0 +1,118 @@
1
+ "use strict";
2
+ var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
3
+ if (k2 === undefined) k2 = k;
4
+ var desc = Object.getOwnPropertyDescriptor(m, k);
5
+ if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
6
+ desc = { enumerable: true, get: function() { return m[k]; } };
7
+ }
8
+ Object.defineProperty(o, k2, desc);
9
+ }) : (function(o, m, k, k2) {
10
+ if (k2 === undefined) k2 = k;
11
+ o[k2] = m[k];
12
+ }));
13
+ var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
14
+ Object.defineProperty(o, "default", { enumerable: true, value: v });
15
+ }) : function(o, v) {
16
+ o["default"] = v;
17
+ });
18
+ var __importStar = (this && this.__importStar) || function (mod) {
19
+ if (mod && mod.__esModule) return mod;
20
+ var result = {};
21
+ if (mod != null) for (var k in mod) if (k !== "default" && Object.prototype.hasOwnProperty.call(mod, k)) __createBinding(result, mod, k);
22
+ __setModuleDefault(result, mod);
23
+ return result;
24
+ };
25
+ var __importDefault = (this && this.__importDefault) || function (mod) {
26
+ return (mod && mod.__esModule) ? mod : { "default": mod };
27
+ };
28
+ Object.defineProperty(exports, "__esModule", { value: true });
29
+ /* eslint-disable no-param-reassign */
30
+ const ValueRepo = __importStar(require("../repository/value"));
31
+ const DefinitionRepo = __importStar(require("../repository/definition"));
32
+ const logger_1 = __importDefault(require("../utils/logger"));
33
+ /**
34
+ * Serialize custom fields value into the format of {[name] -> [fieldData]}
35
+ */
36
+ const serializeCustomFields = (customFieldValues, customFieldDefinitionsHash) => {
37
+ const customFields = customFieldValues.reduce((acc, cfv) => ({
38
+ ...acc,
39
+ ...(customFieldDefinitionsHash[cfv.customFieldDefinitionId]
40
+ && { [customFieldDefinitionsHash[cfv.customFieldDefinitionId].name]: cfv.value }),
41
+ }), {});
42
+ return customFields;
43
+ };
44
+ /**
45
+ * A hook to attach the custom fields when fetching a model instances.
46
+ */
47
+ const enrichResults = (modelType, scopeAttributes) => async (instancesOrInstance, options) => {
48
+ if (options.originalAttributes?.length > 0
49
+ && !options.originalAttributes?.includes?.('customFields')) {
50
+ return;
51
+ }
52
+ const primaryKey = 'id';
53
+ let instances = Array.isArray(instancesOrInstance)
54
+ ? instancesOrInstance
55
+ : [instancesOrInstance];
56
+ instances = instances.filter(Boolean);
57
+ const identifiers = instances.map((instance) => scopeAttributes
58
+ .map((attr) => instance[attr])).flat();
59
+ const uniqueIdentifiers = [...new Set(identifiers)].filter(Boolean);
60
+ const identifierCustomFieldDefinitionsMapping = uniqueIdentifiers.reduce((map, identifier) => ({
61
+ ...map,
62
+ [identifier]: [],
63
+ }), {});
64
+ const customFieldDefinitions = await DefinitionRepo.findByEntityIds(modelType, uniqueIdentifiers, { transaction: options.transaction });
65
+ const definitionsMap = customFieldDefinitions.reduce((map, definition) => ({
66
+ ...map,
67
+ [definition.id]: definition,
68
+ }), {});
69
+ customFieldDefinitions.forEach((cfd) => {
70
+ identifierCustomFieldDefinitionsMapping[cfd.entityId].push(cfd);
71
+ });
72
+ // Get the values per instates ids:
73
+ const instancesIds = instances.map((i) => i[primaryKey]);
74
+ const customFieldValues = await ValueRepo.findValuesByModelIds(instancesIds, { transaction: options.transaction });
75
+ // Group fields by modelId
76
+ const valuesGroupByInstance = customFieldValues.reduce((acc, v) => {
77
+ const { modelId } = v;
78
+ if (!acc[modelId]) {
79
+ acc[modelId] = [];
80
+ }
81
+ acc[modelId].push(v);
82
+ return acc;
83
+ }, {});
84
+ // Attach custom fields to the instances
85
+ instances.forEach((instance) => {
86
+ const customFields = {};
87
+ const { id } = instance;
88
+ const instanceValues = valuesGroupByInstance[id];
89
+ if (instanceValues) {
90
+ const serializedCustomFields = serializeCustomFields(instanceValues, definitionsMap);
91
+ Object.assign(customFields, serializedCustomFields);
92
+ }
93
+ scopeAttributes.forEach((attribute) => {
94
+ const identifier = instance[attribute];
95
+ const entityCustomFieldDefinitions = identifierCustomFieldDefinitionsMapping[identifier];
96
+ if (entityCustomFieldDefinitions?.length > 0) {
97
+ entityCustomFieldDefinitions.forEach((customFieldDefinition) => {
98
+ if (customFields[customFieldDefinition.name] === undefined) {
99
+ customFields[customFieldDefinition.name] = null;
100
+ }
101
+ });
102
+ }
103
+ });
104
+ if (customFields && Object.keys(customFields).length > 0) {
105
+ logger_1.default.info('sadot - enrichResults - customFields', customFields);
106
+ instance.customFields = customFields;
107
+ }
108
+ else {
109
+ logger_1.default.info('sadot - enrichResults - no customFields');
110
+ }
111
+ options.attributesToRemove?.forEach?.((attribute) => {
112
+ delete instance.dataValues?.[attribute];
113
+ // if raw:
114
+ delete instance?.[attribute];
115
+ });
116
+ });
117
+ };
118
+ exports.default = enrichResults;
@@ -0,0 +1 @@
1
+ export declare const beforeFind: (scopeAttributes: string[]) => (options: any) => void;
@@ -0,0 +1,29 @@
1
+ "use strict";
2
+ var __importDefault = (this && this.__importDefault) || function (mod) {
3
+ return (mod && mod.__esModule) ? mod : { "default": mod };
4
+ };
5
+ Object.defineProperty(exports, "__esModule", { value: true });
6
+ exports.beforeFind = void 0;
7
+ /* eslint-disable no-param-reassign */
8
+ const logger_1 = __importDefault(require("../utils/logger"));
9
+ const doScopeAttributesMissing = (scopeAttributes, queryAttributes) => {
10
+ const attributes = scopeAttributes
11
+ .filter((attribute) => !queryAttributes.includes(attribute));
12
+ if (!queryAttributes.includes?.('id')) {
13
+ attributes.push('id');
14
+ }
15
+ return attributes;
16
+ };
17
+ // eslint-disable-next-line import/prefer-default-export
18
+ const beforeFind = (scopeAttributes) => (options) => {
19
+ const { attributes: queryAttributes } = options;
20
+ if (queryAttributes?.includes('customFields')) {
21
+ const missingScopeAttributes = doScopeAttributesMissing(scopeAttributes, queryAttributes);
22
+ logger_1.default.debug('sadot - before find hook');
23
+ if (missingScopeAttributes?.length > 0) {
24
+ queryAttributes.push(...missingScopeAttributes);
25
+ options.attributesToRemove = missingScopeAttributes;
26
+ }
27
+ }
28
+ };
29
+ exports.beforeFind = beforeFind;
@@ -0,0 +1,6 @@
1
+ import enrichResults from './enrich';
2
+ import { beforeFind } from './find';
3
+ import { beforeBulkUpdate, beforeUpdate } from './update';
4
+ import { beforeBulkCreate, beforeCreate } from './create';
5
+ import workaround from './workaround';
6
+ export { enrichResults, beforeFind, beforeBulkUpdate, beforeUpdate, beforeBulkCreate, beforeCreate, workaround, };
@@ -4,8 +4,9 @@ var __importDefault = (this && this.__importDefault) || function (mod) {
4
4
  };
5
5
  Object.defineProperty(exports, "__esModule", { value: true });
6
6
  exports.workaround = exports.beforeCreate = exports.beforeBulkCreate = exports.beforeUpdate = exports.beforeBulkUpdate = exports.beforeFind = exports.enrichResults = void 0;
7
+ const enrich_1 = __importDefault(require("./enrich"));
8
+ exports.enrichResults = enrich_1.default;
7
9
  const find_1 = require("./find");
8
- Object.defineProperty(exports, "enrichResults", { enumerable: true, get: function () { return find_1.enrichResults; } });
9
10
  Object.defineProperty(exports, "beforeFind", { enumerable: true, get: function () { return find_1.beforeFind; } });
10
11
  const update_1 = require("./update");
11
12
  Object.defineProperty(exports, "beforeBulkUpdate", { enumerable: true, get: function () { return update_1.beforeBulkUpdate; } });
@@ -15,4 +16,3 @@ Object.defineProperty(exports, "beforeBulkCreate", { enumerable: true, get: func
15
16
  Object.defineProperty(exports, "beforeCreate", { enumerable: true, get: function () { return create_1.beforeCreate; } });
16
17
  const workaround_1 = __importDefault(require("./workaround"));
17
18
  exports.workaround = workaround_1.default;
18
- //# sourceMappingURL=index.js.map
@@ -0,0 +1,9 @@
1
+ /**
2
+ * A hook to update the custom fields when updating a model (more then one instance).
3
+ */
4
+ export declare const beforeBulkUpdate: (options: any) => void;
5
+ /**
6
+ * A hook to update the custom fields when updating a model instance.
7
+ * TODO - cleanup if update fail
8
+ */
9
+ export declare const beforeUpdate: (scopeAttributes: string[]) => (instance: any, options: any) => Promise<void>;
@@ -22,19 +22,13 @@ var __importStar = (this && this.__importStar) || function (mod) {
22
22
  __setModuleDefault(result, mod);
23
23
  return result;
24
24
  };
25
- var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
26
- function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
27
- return new (P || (P = Promise))(function (resolve, reject) {
28
- function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
29
- function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
30
- function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
31
- step((generator = generator.apply(thisArg, _arguments || [])).next());
32
- });
25
+ var __importDefault = (this && this.__importDefault) || function (mod) {
26
+ return (mod && mod.__esModule) ? mod : { "default": mod };
33
27
  };
34
28
  Object.defineProperty(exports, "__esModule", { value: true });
35
29
  exports.beforeUpdate = exports.beforeBulkUpdate = void 0;
30
+ const logger_1 = __importDefault(require("../utils/logger"));
36
31
  const ValueRepo = __importStar(require("../repository/value"));
37
- const DefinitionRepo = __importStar(require("../repository/definition"));
38
32
  /**
39
33
  * A hook to update the custom fields when updating a model (more then one instance).
40
34
  */
@@ -48,26 +42,17 @@ exports.beforeBulkUpdate = beforeBulkUpdate;
48
42
  * A hook to update the custom fields when updating a model instance.
49
43
  * TODO - cleanup if update fail
50
44
  */
51
- const beforeUpdate = (scopeAttributes) => (instance, options) => __awaiter(void 0, void 0, void 0, function* () {
45
+ const beforeUpdate = (scopeAttributes) => async (instance, options) => {
46
+ logger_1.default.debug('sadot - before update hook');
52
47
  const { fields } = options;
53
48
  const modelType = instance.constructor.name;
54
49
  const identifiers = scopeAttributes.map((attribute) => instance[attribute]);
55
- // get all model's required definitions
56
- const requiredNullFieldsNames = yield DefinitionRepo.getRequiredFields(modelType, instance.id, identifiers, true);
57
50
  const customFieldsIdx = fields.indexOf('customFields');
58
51
  if (customFieldsIdx > -1) {
59
52
  const { customFields } = instance;
60
- const fieldsNames = Object.keys(customFields);
61
- if (requiredNullFieldsNames.some((name) => !fieldsNames.includes(name))) {
62
- throw new Error('some fields are required');
63
- }
64
- yield ValueRepo.updateValues(modelType, instance.id, identifiers, customFields, { transaction: options.transaction });
53
+ await ValueRepo.updateValues(modelType, instance.id, identifiers, customFields, { transaction: options.transaction });
65
54
  // eslint-disable-next-line no-param-reassign
66
55
  fields.splice(customFieldsIdx, 1);
67
56
  }
68
- else if ((requiredNullFieldsNames === null || requiredNullFieldsNames === void 0 ? void 0 : requiredNullFieldsNames.length) > 0) {
69
- throw new Error('some fields are required');
70
- }
71
- });
57
+ };
72
58
  exports.beforeUpdate = beforeUpdate;
73
- //# sourceMappingURL=update.js.map