@ductape/sdk 0.0.3-beta8 → 0.0.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/api/services/appApi.service.d.ts +3 -1
- package/dist/api/services/appApi.service.js +41 -2
- package/dist/api/services/appApi.service.js.map +1 -1
- package/dist/api/services/processorApi.service.d.ts +5 -1
- package/dist/api/services/processorApi.service.js +18 -0
- package/dist/api/services/processorApi.service.js.map +1 -1
- package/dist/api/services/productsApi.service.d.ts +2 -1
- package/dist/api/services/productsApi.service.js +2 -2
- package/dist/api/services/productsApi.service.js.map +1 -1
- package/dist/api/services/userApi.service.d.ts +2 -1
- package/dist/api/services/userApi.service.js +1 -1
- package/dist/api/services/userApi.service.js.map +1 -1
- package/dist/api/services/webhooksApi.service.d.ts +4 -1
- package/dist/api/services/webhooksApi.service.js +6 -3
- package/dist/api/services/webhooksApi.service.js.map +1 -1
- package/dist/api/services/workspaceApi.service.d.ts +2 -1
- package/dist/api/services/workspaceApi.service.js +1 -1
- package/dist/api/services/workspaceApi.service.js.map +1 -1
- package/dist/api/urls.d.ts +2 -0
- package/dist/api/urls.js +3 -1
- package/dist/api/urls.js.map +1 -1
- package/dist/api/utils/cache.utils.d.ts +3 -0
- package/dist/api/utils/cache.utils.js +18 -0
- package/dist/api/utils/cache.utils.js.map +1 -0
- package/dist/apps/services/app.service.d.ts +3 -3
- package/dist/apps/services/app.service.js +153 -75
- package/dist/apps/services/app.service.js.map +1 -1
- package/dist/apps/utils/objects.utils.d.ts +1 -1
- package/dist/apps/utils/objects.utils.js +5 -3
- package/dist/apps/utils/objects.utils.js.map +1 -1
- package/dist/apps/validators/joi-validators/create.appWebhook.validator.js +1 -1
- package/dist/apps/validators/joi-validators/create.appWebhook.validator.js.map +1 -1
- package/dist/apps/validators/joi-validators/create.appWebhookEvent.validator.js +1 -0
- package/dist/apps/validators/joi-validators/create.appWebhookEvent.validator.js.map +1 -1
- package/dist/apps/validators/joi-validators/update.appAction.validator.d.ts +2 -2
- package/dist/apps/validators/joi-validators/update.appAction.validator.js +11 -11
- package/dist/apps/validators/joi-validators/update.appAction.validator.js.map +1 -1
- package/dist/apps/validators/joi-validators/update.appWebhookEvent.validator.js +2 -0
- package/dist/apps/validators/joi-validators/update.appWebhookEvent.validator.js.map +1 -1
- package/dist/clients/webhooks.client.d.ts +2 -1
- package/dist/clients/webhooks.client.js +2 -2
- package/dist/clients/webhooks.client.js.map +1 -1
- package/dist/imports/imports.service.d.ts +2 -3
- package/dist/imports/imports.service.js +4 -45
- package/dist/imports/imports.service.js.map +1 -1
- package/dist/imports/imports.types.d.ts +238 -0
- package/dist/imports/repos/openApi.repo.d.ts +5 -11
- package/dist/imports/repos/openApi.repo.js +77 -27
- package/dist/imports/repos/openApi.repo.js.map +1 -1
- package/dist/imports/repos/postmanV21.repo.js +1 -1
- package/dist/imports/repos/postmanV21.repo.js.map +1 -1
- package/dist/index.d.ts +25 -7
- package/dist/index.js +61 -6
- package/dist/index.js.map +1 -1
- package/dist/inputs/validators/inputs.validator.parse.js +1 -0
- package/dist/inputs/validators/inputs.validator.parse.js.map +1 -1
- package/dist/logs/logs.service.d.ts +1 -1
- package/dist/logs/logs.types.d.ts +3 -0
- package/dist/logs/logs.types.js.map +1 -1
- package/dist/processor/services/fallback.service.d.ts +0 -1
- package/dist/processor/services/fallback.service.js +0 -16
- package/dist/processor/services/fallback.service.js.map +1 -1
- package/dist/processor/services/processor.service.d.ts +53 -14
- package/dist/processor/services/processor.service.js +429 -152
- package/dist/processor/services/processor.service.js.map +1 -1
- package/dist/processor/services/quota.service.d.ts +6 -13
- package/dist/processor/services/quota.service.js +12 -3
- package/dist/processor/services/quota.service.js.map +1 -1
- package/dist/processor/utils/processor.utils.d.ts +3 -230
- package/dist/processor/utils/processor.utils.js +133 -118
- package/dist/processor/utils/processor.utils.js.map +1 -1
- package/dist/products/services/products.service.d.ts +22 -6
- package/dist/products/services/products.service.js +348 -146
- package/dist/products/services/products.service.js.map +1 -1
- package/dist/products/utils/functions.utils.d.ts +1 -0
- package/dist/products/utils/functions.utils.js +11 -0
- package/dist/products/utils/functions.utils.js.map +1 -1
- package/dist/products/validators/index.d.ts +3 -1
- package/dist/products/validators/index.js +5 -1
- package/dist/products/validators/index.js.map +1 -1
- package/dist/products/validators/joi-validators/create.productFallback.validator.js +7 -1
- package/dist/products/validators/joi-validators/create.productFallback.validator.js.map +1 -1
- package/dist/products/validators/joi-validators/create.productFeature.validator.js +2 -0
- package/dist/products/validators/joi-validators/create.productFeature.validator.js.map +1 -1
- package/dist/products/validators/joi-validators/create.productQuota.validator.js +10 -2
- package/dist/products/validators/joi-validators/create.productQuota.validator.js.map +1 -1
- package/dist/products/validators/joi-validators/create.userAuth.validator.d.ts +3 -0
- package/dist/products/validators/joi-validators/create.userAuth.validator.js +47 -0
- package/dist/products/validators/joi-validators/create.userAuth.validator.js.map +1 -0
- package/dist/products/validators/joi-validators/update.dataValue.validator.d.ts +1 -1
- package/dist/products/validators/joi-validators/update.dataValue.validator.js +3 -2
- package/dist/products/validators/joi-validators/update.dataValue.validator.js.map +1 -1
- package/dist/products/validators/joi-validators/update.productFallback.validator.js +7 -2
- package/dist/products/validators/joi-validators/update.productFallback.validator.js.map +1 -1
- package/dist/products/validators/joi-validators/update.productFeature.validator.js +2 -0
- package/dist/products/validators/joi-validators/update.productFeature.validator.js.map +1 -1
- package/dist/products/validators/joi-validators/update.productQuota.validator.js +12 -7
- package/dist/products/validators/joi-validators/update.productQuota.validator.js.map +1 -1
- package/dist/products/validators/joi-validators/update.userAuth.validator.d.ts +3 -0
- package/dist/products/validators/joi-validators/update.userAuth.validator.js +47 -0
- package/dist/products/validators/joi-validators/update.userAuth.validator.js.map +1 -0
- package/dist/test/test.import.openapi.d.ts +1 -0
- package/dist/test/test.import.openapi.js +76 -0
- package/dist/test/test.import.openapi.js.map +1 -0
- package/dist/test/test.logs.js +1 -2
- package/dist/test/test.logs.js.map +1 -1
- package/dist/types/appBuilder.types.d.ts +19 -1
- package/dist/types/enums.d.ts +6 -0
- package/dist/types/enums.js +8 -1
- package/dist/types/enums.js.map +1 -1
- package/dist/types/index.types.d.ts +0 -1
- package/dist/types/processor.types.d.ts +26 -0
- package/dist/types/processor.types.js.map +1 -1
- package/dist/types/productsBuilder.types.d.ts +20 -7
- package/dist/types/productsBuilder.types.js.map +1 -1
- package/package.json +6 -2
|
@@ -40,16 +40,18 @@ const update_productNotificationMessage_validator_1 = __importDefault(require(".
|
|
|
40
40
|
const create_productNotification_validator_1 = require("../validators/joi-validators/create.productNotification.validator");
|
|
41
41
|
const functions_utils_1 = require("../utils/functions.utils");
|
|
42
42
|
const objects_utils_2 = require("../../apps/utils/objects.utils");
|
|
43
|
+
const webhooksApi_service_1 = require("../../api/services/webhooksApi.service");
|
|
43
44
|
class ProductsBuilderService {
|
|
44
|
-
constructor({ workspace_id, public_key, user_id, token, env_type }) {
|
|
45
|
+
constructor({ workspace_id, public_key, user_id, token, env_type, redis_client }) {
|
|
45
46
|
this.workspace_id = workspace_id;
|
|
46
47
|
this.public_key = public_key;
|
|
47
48
|
this.user_id = user_id;
|
|
48
49
|
this.token = token;
|
|
49
|
-
this.userApi = new userApi_service_1.UserApiService(env_type);
|
|
50
|
-
this.productApi = new productsApi_service_1.ProductsApiService(env_type);
|
|
51
|
-
this.workspaceApi = new workspaceApi_service_1.WorkspaceApiService(env_type);
|
|
52
|
-
this.
|
|
50
|
+
this.userApi = new userApi_service_1.UserApiService(env_type, redis_client);
|
|
51
|
+
this.productApi = new productsApi_service_1.ProductsApiService(env_type, redis_client);
|
|
52
|
+
this.workspaceApi = new workspaceApi_service_1.WorkspaceApiService(env_type, redis_client);
|
|
53
|
+
this.webhooksApi = new webhooksApi_service_1.WebhooksApiService(env_type);
|
|
54
|
+
this.appApi = new appApi_service_1.AppApiService(env_type, redis_client);
|
|
53
55
|
this.inputsService = new inputs_service_1.default();
|
|
54
56
|
this.thirdPartyApps = [];
|
|
55
57
|
}
|
|
@@ -190,6 +192,59 @@ class ProductsBuilderService {
|
|
|
190
192
|
}
|
|
191
193
|
return this.product;
|
|
192
194
|
}
|
|
195
|
+
async createSession(data) {
|
|
196
|
+
try {
|
|
197
|
+
// TODO: figure out a way to check if this has run before, halt if it has
|
|
198
|
+
if (!this.fetchSession(data.tag)) {
|
|
199
|
+
await validators_1.CreateProductSessionSchema.validateAsync(data);
|
|
200
|
+
data.schema_data = (await this.inputsService.parseJson({
|
|
201
|
+
data: data.schema,
|
|
202
|
+
expected: inputs_types_1.ExpectedValues.PARSESAMPLE,
|
|
203
|
+
category: enums_1.Categories.DATA,
|
|
204
|
+
}));
|
|
205
|
+
await this.productApi.updateProduct(this.product_id, Object.assign(Object.assign({}, data), { component: enums_1.ProductComponents.SESSION, action: enums_1.RequestAction.CREATE }), this.getUserAccess());
|
|
206
|
+
await this.initializeProduct(this.product_id);
|
|
207
|
+
}
|
|
208
|
+
}
|
|
209
|
+
catch (e) {
|
|
210
|
+
throw e;
|
|
211
|
+
}
|
|
212
|
+
}
|
|
213
|
+
async updateSession(tag, data) {
|
|
214
|
+
try {
|
|
215
|
+
const auth = this.fetchSession(tag);
|
|
216
|
+
if (!auth) {
|
|
217
|
+
throw new Error(`Session ${tag} not found`);
|
|
218
|
+
}
|
|
219
|
+
//const { _id } = auth;
|
|
220
|
+
await validators_1.UpdateProductSessionSchema.validateAsync(data); // Change to update;
|
|
221
|
+
if (data.tag && this.fetchEnv(data.tag) && data.tag !== tag) {
|
|
222
|
+
throw new Error(`tag ${data.tag} is in use`); // TODO: also check on the backend
|
|
223
|
+
}
|
|
224
|
+
if (!data.tag) {
|
|
225
|
+
data.tag = tag;
|
|
226
|
+
}
|
|
227
|
+
if (data.schema) {
|
|
228
|
+
data.schema_data = (await this.inputsService.parseJson({
|
|
229
|
+
data: data.schema,
|
|
230
|
+
expected: inputs_types_1.ExpectedValues.PARSESAMPLE,
|
|
231
|
+
category: enums_1.Categories.DATA,
|
|
232
|
+
}));
|
|
233
|
+
}
|
|
234
|
+
await this.productApi.updateProduct(this.product_id, Object.assign(Object.assign({}, Object.assign(Object.assign({}, auth), data)), { component: enums_1.ProductComponents.SESSION, action: enums_1.RequestAction.UPDATE }), this.getUserAccess());
|
|
235
|
+
await this.initializeProduct(this.product_id);
|
|
236
|
+
}
|
|
237
|
+
catch (e) {
|
|
238
|
+
throw e;
|
|
239
|
+
}
|
|
240
|
+
}
|
|
241
|
+
fetchSession(tag) {
|
|
242
|
+
var _a;
|
|
243
|
+
return (_a = this.product.sessions) === null || _a === void 0 ? void 0 : _a.find((auth) => auth.tag === tag);
|
|
244
|
+
}
|
|
245
|
+
fetchSessions() {
|
|
246
|
+
return this.product.sessions;
|
|
247
|
+
}
|
|
193
248
|
async createMessageBrokerTopic(data, throwErrorIfExists = false) {
|
|
194
249
|
try {
|
|
195
250
|
if (!data.tag) {
|
|
@@ -277,15 +332,15 @@ class ProductsBuilderService {
|
|
|
277
332
|
throw new Error(`Message Broker ${messageBrokerTag} not found`);
|
|
278
333
|
return messageBroker.topics;
|
|
279
334
|
}
|
|
280
|
-
async validateQuotaFallbackInputAndOutput(data) {
|
|
335
|
+
async validateQuotaFallbackInputAndOutput(data, type) {
|
|
281
336
|
const input = data.input;
|
|
282
337
|
await Promise.all(data.options.map(async (d, index) => {
|
|
283
|
-
await this.validateQuotaFallbackInput(d, input);
|
|
338
|
+
await this.validateQuotaFallbackInput(d, input, type);
|
|
284
339
|
const pastOutput = index > 0 ? data.options[index - 1].output : null;
|
|
285
|
-
await this.validateQuotaFallbackOutput(d, pastOutput, input);
|
|
340
|
+
await this.validateQuotaFallbackOutput(d, pastOutput, input, type);
|
|
286
341
|
}));
|
|
287
342
|
}
|
|
288
|
-
async validateQuotaFallbackInput(option, input) {
|
|
343
|
+
async validateQuotaFallbackInput(option, input, type) {
|
|
289
344
|
if (option.type === productsBuilder_types_1.FeatureEventTypes.ACTION) {
|
|
290
345
|
const _a = await this.fetchThirdPartyAppByAccessTag(option.app), { version } = _a, appData = __rest(_a, ["version"]);
|
|
291
346
|
if (!appData) {
|
|
@@ -297,55 +352,170 @@ class ProductsBuilderService {
|
|
|
297
352
|
if (!appData) {
|
|
298
353
|
throw new Error(`Action ${option.event} not found in ${option.app} version ${version}`);
|
|
299
354
|
}
|
|
300
|
-
await this.validateActionDataInput({ input }, action, option.input, 0, 0);
|
|
355
|
+
//await this.validateActionDataInput({ input }, action, option.input, 0, 0);
|
|
356
|
+
// const keyValues = traverseObject(input.option);
|
|
357
|
+
//query
|
|
358
|
+
this.checkActionQuotaFallbackInput(action.query, option.input.query, input, 'query');
|
|
359
|
+
//headers
|
|
360
|
+
this.checkActionQuotaFallbackInput(action.headers, option.input.headers, input, 'headers');
|
|
361
|
+
// params
|
|
362
|
+
this.checkActionQuotaFallbackInput(action.params, option.input.params, input, 'params');
|
|
363
|
+
//body
|
|
364
|
+
this.checkActionQuotaFallbackInput(action.body, option.input.body, input, 'body');
|
|
301
365
|
}
|
|
302
366
|
else {
|
|
303
367
|
const feature = this.fetchFeature(option.event);
|
|
304
368
|
if (!feature) {
|
|
305
369
|
throw new Error(`Feature ${option.event} not found`);
|
|
306
370
|
}
|
|
307
|
-
(0,
|
|
308
|
-
|
|
371
|
+
const map = (0, functions_utils_1.convertInputToValueMap)(feature.input);
|
|
372
|
+
(0, objects_utils_2.validateObjectKeys)(map, option.input, '', 'option input', 'feature input definition');
|
|
373
|
+
}
|
|
374
|
+
const keyValues = (0, objects_utils_1.traverseObject)(option.input);
|
|
375
|
+
this.checkKeyValuesInput(keyValues, input, type);
|
|
376
|
+
this.isQuotaFallbackInput = false;
|
|
377
|
+
}
|
|
378
|
+
checkKeyValuesInput(keyValues, input, type) {
|
|
379
|
+
for (let keyValue of keyValues) {
|
|
380
|
+
const { key, value } = keyValue;
|
|
381
|
+
if (!String(value).startsWith('$')) {
|
|
382
|
+
}
|
|
383
|
+
else if (String(value).startsWith('$Auth{')) {
|
|
384
|
+
// TODO: validate auth input later
|
|
385
|
+
}
|
|
386
|
+
else if (String(value).startsWith('$') && !String(value).startsWith('$Input{')) {
|
|
387
|
+
this.checkFuncArgsForInputs(String(value).trim(), input, type);
|
|
388
|
+
}
|
|
389
|
+
else if (!String(value).startsWith('$Input{')) {
|
|
390
|
+
throw new Error(`Feature input ${value} is invalid, all feature Inputs are expected to start with $Input{}`);
|
|
391
|
+
}
|
|
392
|
+
else {
|
|
393
|
+
this.checkInput(String(value).trim(), input, type);
|
|
394
|
+
}
|
|
395
|
+
}
|
|
396
|
+
}
|
|
397
|
+
checkActionQuotaFallbackInput(sample, obj, featureInput, type) {
|
|
398
|
+
const data = (0, objects_utils_1.traverseObject)(obj);
|
|
399
|
+
//compare obj keys to sample keys
|
|
400
|
+
(0, objects_utils_2.validateObjectKeys)(sample.sample ? JSON.parse(String(sample.sample)) : {}, obj, '', `action ${type} input`, `action ${type} input sample`);
|
|
401
|
+
// check if values in data can be found inside featureInput
|
|
402
|
+
this.checkKeyValuesInput(data, featureInput, type);
|
|
403
|
+
}
|
|
404
|
+
checkFuncArgsForInputs(value, input, type) {
|
|
405
|
+
const isFunc = (0, functions_utils_1.startsWithFunctionAndEndsWithParen)(value);
|
|
406
|
+
if (!isFunc) {
|
|
407
|
+
throw new Error(`Invalid function call ${value}`);
|
|
408
|
+
}
|
|
409
|
+
const funcArgs = (0, functions_utils_1.extractFunctionAndArgs)(value);
|
|
410
|
+
if (funcArgs && funcArgs.args.length) {
|
|
411
|
+
funcArgs.args.map((arg) => {
|
|
412
|
+
const args = arg.trim().split(',');
|
|
413
|
+
args.map((argz) => {
|
|
414
|
+
const arg = argz.trim();
|
|
415
|
+
if (arg.startsWith('$') && !arg.startsWith('$Input{')) {
|
|
416
|
+
this.checkFuncArgsForInputs(arg, input, type);
|
|
417
|
+
}
|
|
418
|
+
else if (arg.startsWith('$Input{')) {
|
|
419
|
+
this.checkInput(arg, input, type);
|
|
420
|
+
}
|
|
421
|
+
});
|
|
422
|
+
});
|
|
423
|
+
}
|
|
424
|
+
}
|
|
425
|
+
checkInput(value, input, type) {
|
|
426
|
+
const stages = this.extractStages(value);
|
|
427
|
+
if (stages.length > 1) {
|
|
428
|
+
throw new Error(`Invalid input ${value}, nested locators not allowed in $Input`);
|
|
429
|
+
}
|
|
430
|
+
if (!input[stages[0]]) {
|
|
431
|
+
throw new Error(`${value} not found in ${type} input definition`);
|
|
432
|
+
}
|
|
433
|
+
}
|
|
434
|
+
async validateQuotaFallbackOutput(option, pastResponse, input, type) {
|
|
435
|
+
if (pastResponse) {
|
|
436
|
+
(0, objects_utils_2.validateObjectKeys)(option.output, pastResponse, `previous outputs`, `${option.event} ${type} output`);
|
|
437
|
+
}
|
|
438
|
+
if (option.type === productsBuilder_types_1.FeatureEventTypes.ACTION) {
|
|
439
|
+
const _a = await this.fetchThirdPartyAppByAccessTag(option.app), { version } = _a, appData = __rest(_a, ["version"]);
|
|
440
|
+
if (!appData) {
|
|
441
|
+
throw new Error(`App ${option.app} not found`);
|
|
442
|
+
}
|
|
443
|
+
const { actions } = appData.versions.find((data) => data.tag === version);
|
|
444
|
+
const action = actions.find((data) => data.tag === option.event);
|
|
445
|
+
if (!appData) {
|
|
446
|
+
throw new Error(`Action ${event} not found in ${option.app} version ${version}`);
|
|
447
|
+
}
|
|
448
|
+
const response = action.responses.find((item) => item.success === true);
|
|
449
|
+
// fetch success result
|
|
450
|
+
if (!response) {
|
|
451
|
+
throw new Error(`event ${event} does not have a success response`);
|
|
452
|
+
}
|
|
453
|
+
// validate that each output item starts with response or Input and then validate the stages are valid;
|
|
454
|
+
}
|
|
455
|
+
else {
|
|
456
|
+
// fetch feature
|
|
457
|
+
const feature = this.fetchFeature(option.event);
|
|
458
|
+
if (!feature) {
|
|
459
|
+
throw new Error(`Feature ${option.event} not found`);
|
|
460
|
+
}
|
|
461
|
+
const { output } = feature;
|
|
462
|
+
const keyValues = (0, objects_utils_1.traverseObject)(option.output);
|
|
309
463
|
for (let keyValue of keyValues) {
|
|
310
464
|
const { key, value } = keyValue;
|
|
311
|
-
if (!value.startsWith('$
|
|
312
|
-
|
|
465
|
+
if (!value.startsWith('$')) {
|
|
466
|
+
}
|
|
467
|
+
else if (value.startsWith('$') && !value.startsWith('$Response{') && !value.startsWith('$Input')) {
|
|
468
|
+
this.checkFuncArgsForResponse(value.trim(), output, input, type);
|
|
469
|
+
}
|
|
470
|
+
else if (!value.startsWith('$Response{') && !value.startsWith('$Input{')) {
|
|
471
|
+
throw new Error(`Feature output ${value} is invalid, all feature outputs for ${type} are expected to start with $Response or $Input{}`);
|
|
472
|
+
}
|
|
473
|
+
else if (value.startsWith('$Response')) {
|
|
474
|
+
this.checkResponse(value.trim(), output, input, type);
|
|
475
|
+
}
|
|
476
|
+
else if (value.startsWith('$Input')) {
|
|
477
|
+
this.checkInput(value, input, type);
|
|
313
478
|
}
|
|
314
479
|
}
|
|
315
480
|
}
|
|
316
|
-
|
|
481
|
+
// validate that each response matches the expected format
|
|
482
|
+
/**await this.validateActionResponse(response, res)*/
|
|
317
483
|
}
|
|
318
|
-
|
|
319
|
-
|
|
320
|
-
|
|
321
|
-
|
|
322
|
-
input: Record<string, IFeatureInput>,*/
|
|
323
|
-
option, pastResponse, input) {
|
|
324
|
-
/*const { version, ...appData } = await this.fetchThirdPartyAppByAccessTag(option.app);
|
|
325
|
-
|
|
326
|
-
if (!appData) {
|
|
327
|
-
throw new Error(`App ${option.app} not found`);
|
|
328
|
-
}
|
|
329
|
-
|
|
330
|
-
const { actions } = appData.versions.find((data) => data.tag === version);
|
|
331
|
-
|
|
332
|
-
const action = actions.find((data) => data.tag === option.event);
|
|
333
|
-
|
|
334
|
-
if (!appData) {
|
|
335
|
-
throw new Error(`Action ${event} not found in ${option.app} version ${version}`);
|
|
484
|
+
checkFuncArgsForResponse(value, output, input, type) {
|
|
485
|
+
const isFunc = (0, functions_utils_1.startsWithFunctionAndEndsWithParen)(value);
|
|
486
|
+
if (!isFunc) {
|
|
487
|
+
throw new Error(`Invalid function call ${value}`);
|
|
336
488
|
}
|
|
337
|
-
|
|
338
|
-
|
|
489
|
+
const funcArgs = (0, functions_utils_1.extractFunctionAndArgs)(value);
|
|
490
|
+
if (funcArgs && funcArgs.args.length) {
|
|
491
|
+
funcArgs.args.map((arg) => {
|
|
492
|
+
const args = arg.trim().split(',');
|
|
493
|
+
args.map((argz) => {
|
|
494
|
+
const arg = argz.trim();
|
|
495
|
+
if (arg.startsWith('$') && !arg.startsWith('$Response{') && !arg.startsWith('$Input{')) {
|
|
496
|
+
this.checkFuncArgsForResponse(arg, output, input, type);
|
|
497
|
+
}
|
|
498
|
+
else if (arg.startsWith('$Response{')) {
|
|
499
|
+
this.checkResponse(arg, output, input, type);
|
|
500
|
+
}
|
|
501
|
+
else if (arg.startsWith('$Input{')) {
|
|
502
|
+
this.checkInput(arg, input, type);
|
|
503
|
+
}
|
|
504
|
+
});
|
|
505
|
+
});
|
|
339
506
|
}
|
|
340
|
-
|
|
341
|
-
|
|
342
|
-
|
|
343
|
-
|
|
344
|
-
|
|
345
|
-
|
|
507
|
+
}
|
|
508
|
+
checkResponse(value, output, input, type) {
|
|
509
|
+
const stages = this.extractStages(value);
|
|
510
|
+
let current = output;
|
|
511
|
+
for (const stage of stages) {
|
|
512
|
+
if (current && typeof current === 'object' && stage in current) {
|
|
513
|
+
current = current[stage];
|
|
514
|
+
}
|
|
515
|
+
else {
|
|
516
|
+
throw new Error(`${value} not found in ${type} response definition`);
|
|
517
|
+
}
|
|
346
518
|
}
|
|
347
|
-
|
|
348
|
-
await this.validateActionResponse(response, res)*/
|
|
349
519
|
}
|
|
350
520
|
async createQuota(data) {
|
|
351
521
|
try {
|
|
@@ -354,27 +524,32 @@ class ProductsBuilderService {
|
|
|
354
524
|
}
|
|
355
525
|
if (!this.fetchQuota(data.tag)) {
|
|
356
526
|
await validators_1.CreateProductQuotaSchema.validateAsync(data);
|
|
357
|
-
await this.validateQuotaFallbackInputAndOutput(data);
|
|
527
|
+
await this.validateQuotaFallbackInputAndOutput(data, 'quota');
|
|
358
528
|
data.total_quota = 0;
|
|
359
529
|
data.total_init = 0;
|
|
360
530
|
await Promise.all(data.options.map(async (d) => {
|
|
361
531
|
data.total_quota += d.quota;
|
|
362
|
-
|
|
363
|
-
|
|
364
|
-
|
|
365
|
-
|
|
366
|
-
const version = app.versions.find((version) => version.tag === app.version);
|
|
367
|
-
const action = version.actions.find((action) => action.tag === d.event);
|
|
368
|
-
if (!action) {
|
|
369
|
-
throw new Error(`Cannot find action ${d.event} on app ${app.tag} version ${app.version}`);
|
|
370
|
-
}
|
|
371
|
-
if (d.healthcheck) {
|
|
372
|
-
const action = version.actions.find((action) => action.tag === d.healthcheck);
|
|
373
|
-
if (!d.check_interval) {
|
|
374
|
-
d.check_interval = 10000;
|
|
532
|
+
if (d.type === productsBuilder_types_1.FeatureEventTypes.ACTION) {
|
|
533
|
+
const app = await this.fetchThirdPartyAppByAccessTag(d.app);
|
|
534
|
+
if (!app) {
|
|
535
|
+
throw new Error(`App with access tag ${d.app} not found`);
|
|
375
536
|
}
|
|
537
|
+
const version = app.versions.find((version) => version.tag === app.version);
|
|
538
|
+
const action = version.actions.find((action) => action.tag === d.event);
|
|
376
539
|
if (!action) {
|
|
377
|
-
throw new Error(`Cannot find
|
|
540
|
+
throw new Error(`Cannot find action ${d.event} on app ${app.tag} version ${app.version}`);
|
|
541
|
+
}
|
|
542
|
+
if (d.healthcheck) {
|
|
543
|
+
const action = version.actions.find((action) => action.tag === d.healthcheck);
|
|
544
|
+
if (!d.check_interval) {
|
|
545
|
+
d.check_interval = 10000;
|
|
546
|
+
}
|
|
547
|
+
if (!action) {
|
|
548
|
+
throw new Error(`Cannot find healthcheck action ${d.healthcheck} on app ${app.tag} version ${app.version}`);
|
|
549
|
+
}
|
|
550
|
+
if (action.headers.data.length > 0 || action.body.data.length > 0 || action.params.data.length > 0 || action.query.data.length > 0) {
|
|
551
|
+
throw new Error('Healthcheck action is expected to have no headers, body, params or query');
|
|
552
|
+
}
|
|
378
553
|
}
|
|
379
554
|
}
|
|
380
555
|
d.last_checked = new Date();
|
|
@@ -383,15 +558,61 @@ class ProductsBuilderService {
|
|
|
383
558
|
}));
|
|
384
559
|
await this.productApi.updateProduct(this.product_id, Object.assign(Object.assign({}, data), { component: enums_1.ProductComponents.QUOTA, action: enums_1.RequestAction.CREATE }), this.getUserAccess());
|
|
385
560
|
}
|
|
561
|
+
}
|
|
562
|
+
catch (e) {
|
|
563
|
+
throw e;
|
|
564
|
+
}
|
|
565
|
+
}
|
|
566
|
+
async updateQuota(tag, data) {
|
|
567
|
+
try {
|
|
568
|
+
const quota = this.fetchQuota(tag);
|
|
569
|
+
if (quota) {
|
|
570
|
+
await validators_1.UpdateProductQuotaSchema.validateAsync(data);
|
|
571
|
+
if (data.options) {
|
|
572
|
+
await this.validateQuotaFallbackInputAndOutput(data, 'quota');
|
|
573
|
+
data.total_quota = 0;
|
|
574
|
+
data.total_init = 0;
|
|
575
|
+
data.tag = tag;
|
|
576
|
+
await Promise.all(data.options.map(async (d) => {
|
|
577
|
+
data.total_quota += d.quota;
|
|
578
|
+
if (d.type === productsBuilder_types_1.FeatureEventTypes.ACTION) {
|
|
579
|
+
const app = await this.fetchThirdPartyAppByAccessTag(d.app);
|
|
580
|
+
if (!app) {
|
|
581
|
+
throw new Error(`App with access tag ${d.app} not found`);
|
|
582
|
+
}
|
|
583
|
+
const version = app.versions.find((version) => version.tag === app.version);
|
|
584
|
+
const action = version.actions.find((action) => action.tag === d.event);
|
|
585
|
+
if (!action) {
|
|
586
|
+
throw new Error(`Cannot find action ${d.event} on app ${app.tag} version ${app.version}`);
|
|
587
|
+
}
|
|
588
|
+
if (d.healthcheck) {
|
|
589
|
+
const action = version.actions.find((action) => action.tag === d.healthcheck);
|
|
590
|
+
if (!d.check_interval) {
|
|
591
|
+
d.check_interval = 10000;
|
|
592
|
+
}
|
|
593
|
+
if (!action) {
|
|
594
|
+
throw new Error(`Cannot find healthcheck action ${d.healthcheck} on app ${app.tag} version ${app.version}`);
|
|
595
|
+
}
|
|
596
|
+
if (action.headers.data.length > 0 || action.body.data.length > 0 || action.params.data.length > 0 || action.query.data.length > 0) {
|
|
597
|
+
throw new Error('Healthcheck action is expected to have no headers, body, params or query');
|
|
598
|
+
}
|
|
599
|
+
}
|
|
600
|
+
}
|
|
601
|
+
d.last_checked = new Date();
|
|
602
|
+
d.provider_status = productsBuilder_types_1.ProviderStatus.AVAILABLE;
|
|
603
|
+
d.last_available = true;
|
|
604
|
+
}));
|
|
605
|
+
}
|
|
606
|
+
await this.productApi.updateProduct(this.product_id, Object.assign(Object.assign(Object.assign({}, quota), data), { component: enums_1.ProductComponents.QUOTA, action: enums_1.RequestAction.UPDATE }), this.getUserAccess());
|
|
607
|
+
}
|
|
386
608
|
else {
|
|
387
|
-
throw new Error(`Quota with tag ${data.tag}
|
|
609
|
+
throw new Error(`Quota with tag ${data.tag} not found`);
|
|
388
610
|
}
|
|
389
611
|
}
|
|
390
612
|
catch (e) {
|
|
391
613
|
throw e;
|
|
392
614
|
}
|
|
393
615
|
}
|
|
394
|
-
async updateQuota(tag, data) { }
|
|
395
616
|
fetchQuota(tag) {
|
|
396
617
|
return this.fetchQuotas().find((data) => data.tag === tag);
|
|
397
618
|
}
|
|
@@ -403,26 +624,31 @@ class ProductsBuilderService {
|
|
|
403
624
|
if (!data.tag) {
|
|
404
625
|
throw new Error('tag field is required');
|
|
405
626
|
}
|
|
406
|
-
if (!this.
|
|
627
|
+
if (!this.fetchFallback(data.tag)) {
|
|
407
628
|
await validators_1.CreateProductFallbackSchema.validateAsync(data);
|
|
408
|
-
await this.validateQuotaFallbackInputAndOutput(data);
|
|
629
|
+
await this.validateQuotaFallbackInputAndOutput(data, 'fallback');
|
|
409
630
|
await Promise.all(data.options.map(async (d) => {
|
|
410
|
-
|
|
411
|
-
|
|
412
|
-
|
|
413
|
-
|
|
414
|
-
const version = app.versions.find((version) => version.tag === app.version);
|
|
415
|
-
const action = version.actions.find((action) => action.tag === d.event);
|
|
416
|
-
if (!action) {
|
|
417
|
-
throw new Error(`Cannot find action ${d.event} on app ${app.tag} version ${app.version}`);
|
|
418
|
-
}
|
|
419
|
-
if (d.healthcheck) {
|
|
420
|
-
const action = version.actions.find((action) => action.tag === d.healthcheck);
|
|
421
|
-
if (!d.check_interval) {
|
|
422
|
-
d.check_interval = 10000;
|
|
631
|
+
if (d.type === productsBuilder_types_1.FeatureEventTypes.ACTION) {
|
|
632
|
+
const app = await this.fetchThirdPartyAppByAccessTag(d.app);
|
|
633
|
+
if (!app) {
|
|
634
|
+
throw new Error(`App with access tag ${d.app} not found`);
|
|
423
635
|
}
|
|
636
|
+
const version = app.versions.find((version) => version.tag === app.version);
|
|
637
|
+
const action = version.actions.find((action) => action.tag === d.event);
|
|
424
638
|
if (!action) {
|
|
425
|
-
throw new Error(`Cannot find
|
|
639
|
+
throw new Error(`Cannot find action ${d.event} on app ${app.tag} version ${app.version}`);
|
|
640
|
+
}
|
|
641
|
+
if (d.healthcheck) {
|
|
642
|
+
const action = version.actions.find((action) => action.tag === d.healthcheck);
|
|
643
|
+
if (!d.check_interval) {
|
|
644
|
+
d.check_interval = 10000;
|
|
645
|
+
}
|
|
646
|
+
if (!action) {
|
|
647
|
+
throw new Error(`Cannot find healthcheck action ${d.healthcheck} on app ${app.tag} version ${app.version}`);
|
|
648
|
+
}
|
|
649
|
+
if (action.headers.data.length > 0 || action.body.data.length > 0 || action.params.data.length > 0 || action.query.data.length > 0) {
|
|
650
|
+
throw new Error('Healthcheck action is expected to have no headers, body, params or query');
|
|
651
|
+
}
|
|
426
652
|
}
|
|
427
653
|
}
|
|
428
654
|
d.last_checked = new Date();
|
|
@@ -431,83 +657,57 @@ class ProductsBuilderService {
|
|
|
431
657
|
}));
|
|
432
658
|
await this.productApi.updateProduct(this.product_id, Object.assign(Object.assign({}, data), { component: enums_1.ProductComponents.FALLBACK, action: enums_1.RequestAction.CREATE }), this.getUserAccess());
|
|
433
659
|
}
|
|
434
|
-
else {
|
|
435
|
-
throw new Error(`Quota with tag ${data.tag} already exists`);
|
|
436
|
-
}
|
|
437
660
|
}
|
|
438
661
|
catch (e) {
|
|
439
662
|
throw e;
|
|
440
663
|
}
|
|
441
664
|
}
|
|
442
665
|
async updateFallback(tag, data) {
|
|
443
|
-
|
|
444
|
-
|
|
445
|
-
|
|
446
|
-
|
|
447
|
-
|
|
448
|
-
|
|
449
|
-
|
|
450
|
-
|
|
451
|
-
|
|
452
|
-
|
|
666
|
+
try {
|
|
667
|
+
const fallback = this.fetchFallback(tag);
|
|
668
|
+
if (fallback) {
|
|
669
|
+
await validators_1.UpdateProductFallbackSchema.validateAsync(data);
|
|
670
|
+
if (data.options) {
|
|
671
|
+
await this.validateQuotaFallbackInputAndOutput(data, 'fallback');
|
|
672
|
+
data.tag = tag;
|
|
673
|
+
await Promise.all(data.options.map(async (d) => {
|
|
674
|
+
if (d.type === productsBuilder_types_1.FeatureEventTypes.ACTION) {
|
|
675
|
+
const app = await this.fetchThirdPartyAppByAccessTag(d.app);
|
|
676
|
+
if (!app) {
|
|
677
|
+
throw new Error(`App with access tag ${d.app} not found`);
|
|
678
|
+
}
|
|
679
|
+
const version = app.versions.find((version) => version.tag === app.version);
|
|
680
|
+
const action = version.actions.find((action) => action.tag === d.event);
|
|
681
|
+
if (!action) {
|
|
682
|
+
throw new Error(`Cannot find action ${d.event} on app ${app.tag} version ${app.version}`);
|
|
683
|
+
}
|
|
684
|
+
if (d.healthcheck) {
|
|
685
|
+
const action = version.actions.find((action) => action.tag === d.healthcheck);
|
|
686
|
+
if (!d.check_interval) {
|
|
687
|
+
d.check_interval = 10000;
|
|
688
|
+
}
|
|
689
|
+
if (!action) {
|
|
690
|
+
throw new Error(`Cannot find healthcheck action ${d.healthcheck} on app ${app.tag} version ${app.version}`);
|
|
691
|
+
}
|
|
692
|
+
if (action.headers.data.length > 0 || action.body.data.length > 0 || action.params.data.length > 0 || action.query.data.length > 0) {
|
|
693
|
+
throw new Error('Healthcheck action is expected to have no headers, body, params or query');
|
|
694
|
+
}
|
|
695
|
+
}
|
|
696
|
+
}
|
|
697
|
+
d.last_checked = new Date();
|
|
698
|
+
d.provider_status = productsBuilder_types_1.ProviderStatus.AVAILABLE;
|
|
699
|
+
d.last_available = true;
|
|
700
|
+
}));
|
|
701
|
+
}
|
|
702
|
+
await this.productApi.updateProduct(this.product_id, Object.assign(Object.assign(Object.assign({}, fallback), data), { component: enums_1.ProductComponents.FALLBACK, action: enums_1.RequestAction.UPDATE }), this.getUserAccess());
|
|
453
703
|
}
|
|
454
|
-
|
|
455
|
-
|
|
456
|
-
data.tag = tag;
|
|
704
|
+
else {
|
|
705
|
+
throw new Error(`Fallback with tag ${data.tag} not found`);
|
|
457
706
|
}
|
|
458
|
-
|
|
459
|
-
|
|
460
|
-
|
|
461
|
-
|
|
462
|
-
|
|
463
|
-
await Promise.all(data.options.map(async (d) => {
|
|
464
|
-
|
|
465
|
-
const app = await this.fetchThirdPartyAppByAccessTag(d.app);
|
|
466
|
-
|
|
467
|
-
if (!app) {
|
|
468
|
-
throw new Error(`App with access tag ${d.app} not found`)
|
|
469
|
-
}
|
|
470
|
-
|
|
471
|
-
const version = app.versions.find((version) => version.tag === app.version);
|
|
472
|
-
const action = version.actions.find((action) => action.tag === d.event)
|
|
473
|
-
|
|
474
|
-
if (!action) {
|
|
475
|
-
throw new Error(`Cannot find action ${d.event} on app ${app.tag} version ${app.version}`)
|
|
476
|
-
}
|
|
477
|
-
|
|
478
|
-
if (d.healthcheck) {
|
|
479
|
-
const action = version.actions.find((action) => action.tag === d.healthcheck)
|
|
480
|
-
|
|
481
|
-
if (!d.check_interval) {
|
|
482
|
-
d.check_interval = 10000;
|
|
483
|
-
}
|
|
484
|
-
|
|
485
|
-
if (!action) {
|
|
486
|
-
throw new Error(`Cannot find healthcheck action ${d.healthcheck} on app ${app.tag} version ${app.version}`)
|
|
487
|
-
}
|
|
488
|
-
}
|
|
489
|
-
|
|
490
|
-
d.last_checked = new Date();
|
|
491
|
-
d.provider_status = ProviderStatus.AVAILABLE;
|
|
492
|
-
d.last_available = true;
|
|
493
|
-
}))
|
|
494
|
-
|
|
495
|
-
await this.productApi.updateProduct(
|
|
496
|
-
this.product_id,
|
|
497
|
-
{
|
|
498
|
-
...data,
|
|
499
|
-
component: ProductComponents.FALLBACK,
|
|
500
|
-
},
|
|
501
|
-
this.getUserAccess(),
|
|
502
|
-
);
|
|
503
|
-
|
|
504
|
-
} else {
|
|
505
|
-
throw new Error(`Quota with tag ${data.tag} already exists`)
|
|
506
|
-
}
|
|
507
|
-
|
|
508
|
-
} catch (e) {
|
|
509
|
-
throw e;
|
|
510
|
-
}*/
|
|
707
|
+
}
|
|
708
|
+
catch (e) {
|
|
709
|
+
throw e;
|
|
710
|
+
}
|
|
511
711
|
}
|
|
512
712
|
fetchFallback(tag) {
|
|
513
713
|
return this.fetchFallbacks().find((data) => data.tag === tag);
|
|
@@ -960,6 +1160,8 @@ class ProductsBuilderService {
|
|
|
960
1160
|
throw new Error(`App with access tag ${access_tag} not found`);
|
|
961
1161
|
}
|
|
962
1162
|
const version = app.versions.find((version) => version.tag === app.version);
|
|
1163
|
+
const status = await this.webhooksApi.fetchWebhooks({ access_tag, app_tag: app.tag, version: app.version }, this.getUserAccess());
|
|
1164
|
+
console.log(status);
|
|
963
1165
|
if (!version) {
|
|
964
1166
|
throw new Error(`Required app version not found`);
|
|
965
1167
|
}
|
|
@@ -1206,7 +1408,7 @@ class ProductsBuilderService {
|
|
|
1206
1408
|
if (!notificationTag || !messageTag) {
|
|
1207
1409
|
throw new Error(`tag is expected to be defined as "notification_tag:message_tag"`);
|
|
1208
1410
|
}
|
|
1209
|
-
const notification = this.
|
|
1411
|
+
const notification = this.fetchNotification(notificationTag);
|
|
1210
1412
|
if (!notification)
|
|
1211
1413
|
throw new Error(`Notification ${notificationTag} not found`);
|
|
1212
1414
|
const message = notification.messages.find((data) => data.tag === messageTag);
|