@crowdin/app-project-module 0.28.11 → 0.29.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 (40) hide show
  1. package/out/handlers/crowdin-file-progress.js +1 -1
  2. package/out/handlers/crowdin-update.js +7 -2
  3. package/out/handlers/crowdin-webhook.js +4 -3
  4. package/out/handlers/integration-update.js +5 -0
  5. package/out/handlers/integration-webhook.js +2 -1
  6. package/out/handlers/main.js +1 -0
  7. package/out/handlers/manifest.js +4 -0
  8. package/out/handlers/settings-save.js +11 -0
  9. package/out/handlers/settings.d.ts +4 -0
  10. package/out/handlers/settings.js +22 -0
  11. package/out/handlers/sync-settings-save.d.ts +2 -2
  12. package/out/handlers/sync-settings-save.js +8 -11
  13. package/out/handlers/sync-settings.js +1 -1
  14. package/out/index.js +8 -1
  15. package/out/middlewares/crowdin-client.js +5 -0
  16. package/out/models/index.d.ts +56 -3
  17. package/out/models/index.js +14 -1
  18. package/out/static/js/dependent.js +1 -2
  19. package/out/storage/index.d.ts +8 -5
  20. package/out/storage/mysql.d.ts +4 -1
  21. package/out/storage/mysql.js +35 -1
  22. package/out/storage/postgre.d.ts +4 -1
  23. package/out/storage/postgre.js +35 -1
  24. package/out/storage/sqlite.d.ts +4 -1
  25. package/out/storage/sqlite.js +33 -1
  26. package/out/util/api/api.d.ts +6 -0
  27. package/out/util/api/api.js +452 -0
  28. package/out/util/api/base.d.ts +7 -0
  29. package/out/util/api/base.js +8 -0
  30. package/out/util/api/components.d.ts +227 -0
  31. package/out/util/api/components.js +228 -0
  32. package/out/util/cron.d.ts +2 -1
  33. package/out/util/cron.js +76 -9
  34. package/out/util/defaults.js +26 -3
  35. package/out/util/file-snapshot.d.ts +7 -0
  36. package/out/util/file-snapshot.js +144 -0
  37. package/out/util/webhooks.d.ts +4 -3
  38. package/out/util/webhooks.js +29 -5
  39. package/out/views/main.handlebars +140 -8
  40. package/package.json +5 -1
@@ -12,7 +12,7 @@ Object.defineProperty(exports, "__esModule", { value: true });
12
12
  const util_1 = require("../util");
13
13
  function handle(config, integration) {
14
14
  return (0, util_1.runAsyncWrapper)((req, res) => __awaiter(this, void 0, void 0, function* () {
15
- const fileId = Number(req.params.fileId);
15
+ const fileId = Number(req.params.fileId || req.body.fileId);
16
16
  (0, util_1.log)(`Loading translation progress for file ${fileId}`, config.logger);
17
17
  if (integration.getFileProgress) {
18
18
  const progress = yield integration.getFileProgress(req.crowdinContext.jwtPayload.context.project_id, req.crowdinApiClient, fileId);
@@ -13,13 +13,18 @@ const util_1 = require("../util");
13
13
  const defaults_1 = require("../util/defaults");
14
14
  function handle(config, integration) {
15
15
  return (0, util_1.runAsyncWrapper)((req, res) => __awaiter(this, void 0, void 0, function* () {
16
- const projectId = req.crowdinContext.jwtPayload.context.project_id;
17
- const uploadTranslations = req.query.uploadTranslations === 'true';
16
+ var _a, _b;
17
+ const projectId = req.crowdinContext.jwtPayload.context.project_id || (req === null || req === void 0 ? void 0 : req.body.projectId);
18
+ const uploadTranslations = req.query.uploadTranslations === 'true' || ((_a = req.body) === null || _a === void 0 ? void 0 : _a.uploadTranslations);
18
19
  (0, util_1.log)(`Updating crowdin project ${projectId}`, config.logger);
19
20
  const rootFolder = yield (0, defaults_1.getRootFolder)(config, integration, req.crowdinApiClient, projectId);
20
21
  if (rootFolder) {
21
22
  (0, util_1.log)(`Updating crowdin files under folder ${rootFolder.id}`, config.logger);
22
23
  }
24
+ // A request via API has a different structure
25
+ if (((_b = config.api) === null || _b === void 0 ? void 0 : _b.default) && req.body.files) {
26
+ req.body = req.body.files;
27
+ }
23
28
  const result = yield integration.updateCrowdin(projectId, req.crowdinApiClient, req.integrationCredentials, req.body, rootFolder, req.integrationSettings, uploadTranslations);
24
29
  let message;
25
30
  if ((0, util_1.isExtendedResultType)(result)) {
@@ -9,6 +9,7 @@ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, ge
9
9
  });
10
10
  };
11
11
  Object.defineProperty(exports, "__esModule", { value: true });
12
+ const models_1 = require("../models");
12
13
  const util_1 = require("../util");
13
14
  const webhooks_1 = require("../util/webhooks");
14
15
  function handle(config, integration) {
@@ -18,7 +19,7 @@ function handle(config, integration) {
18
19
  const webhookUrlParam = req.query[urlParam];
19
20
  let filesToSync;
20
21
  if (webhookUrlParam) {
21
- const { projectId, crowdinClient, preparedIntegrationCredentials, rootFolder, appSettings, syncSettings } = yield (0, webhooks_1.prepareWebhookData)(config, integration, webhookUrlParam, 'crowdin');
22
+ const { projectId, crowdinClient, preparedIntegrationCredentials, rootFolder, appSettings, syncSettings, newFiles, } = yield (0, webhooks_1.prepareWebhookData)(config, integration, webhookUrlParam, models_1.Provider.CROWDIN);
22
23
  if (!crowdinClient) {
23
24
  return res.status(403).send({ error: 'Access denied' });
24
25
  }
@@ -26,12 +27,12 @@ function handle(config, integration) {
26
27
  return res.status(200).send({ message: 'Sync is not configured' });
27
28
  }
28
29
  if ((_b = integration.webhooks) === null || _b === void 0 ? void 0 : _b.crowdinWebhookInterceptor) {
29
- filesToSync = yield integration.webhooks.crowdinWebhookInterceptor(projectId, crowdinClient.client, rootFolder, appSettings, syncSettings, req.body);
30
+ filesToSync = yield integration.webhooks.crowdinWebhookInterceptor(projectId, crowdinClient.client, rootFolder, appSettings, syncSettings, req.body, newFiles);
30
31
  }
31
32
  else {
32
33
  filesToSync = (0, webhooks_1.filterSyncFiles)(req.body.events, JSON.parse(syncSettings.files));
33
34
  }
34
- const result = yield integration.updateIntegration(projectId, crowdinClient.client, preparedIntegrationCredentials, filesToSync, rootFolder, appSettings);
35
+ const result = yield integration.updateIntegration(projectId, crowdinClient.client, preparedIntegrationCredentials, Object.assign(Object.assign({}, filesToSync), newFiles), rootFolder, appSettings);
35
36
  let message;
36
37
  if ((0, util_1.isExtendedResultType)(result)) {
37
38
  message = result.message;
@@ -13,11 +13,16 @@ const util_1 = require("../util");
13
13
  const defaults_1 = require("../util/defaults");
14
14
  function handle(config, integration) {
15
15
  return (0, util_1.runAsyncWrapper)((req, res) => __awaiter(this, void 0, void 0, function* () {
16
+ var _a;
16
17
  (0, util_1.log)('Updating integration data', config.logger);
17
18
  const rootFolder = yield (0, defaults_1.getRootFolder)(config, integration, req.crowdinApiClient, req.crowdinContext.jwtPayload.context.project_id);
18
19
  if (rootFolder) {
19
20
  (0, util_1.log)(`Updating integration data for crowding root folder ${rootFolder.id}`, config.logger);
20
21
  }
22
+ // A request via API has a different structure
23
+ if (((_a = config.api) === null || _a === void 0 ? void 0 : _a.default) && req.body.files) {
24
+ req.body = req.body.files;
25
+ }
21
26
  const result = yield integration.updateIntegration(req.crowdinContext.jwtPayload.context.project_id, req.crowdinApiClient, req.integrationCredentials, req.body, rootFolder, req.integrationSettings);
22
27
  let message;
23
28
  if ((0, util_1.isExtendedResultType)(result)) {
@@ -9,6 +9,7 @@ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, ge
9
9
  });
10
10
  };
11
11
  Object.defineProperty(exports, "__esModule", { value: true });
12
+ const models_1 = require("../models");
12
13
  const util_1 = require("../util");
13
14
  const webhooks_1 = require("../util/webhooks");
14
15
  function handle(config, integration) {
@@ -17,7 +18,7 @@ function handle(config, integration) {
17
18
  const urlParam = (_a = integration.webhooks) === null || _a === void 0 ? void 0 : _a.urlParam;
18
19
  const webhookUrlParam = req.query[urlParam];
19
20
  if (((_b = integration.webhooks) === null || _b === void 0 ? void 0 : _b.integrationWebhookInterceptor) && webhookUrlParam) {
20
- const webhookData = yield (0, webhooks_1.prepareWebhookData)(config, integration, webhookUrlParam, 'integration');
21
+ const webhookData = yield (0, webhooks_1.prepareWebhookData)(config, integration, webhookUrlParam, models_1.Provider.INTEGRATION);
21
22
  if (!webhookData.crowdinClient) {
22
23
  return res.status(403).send({ error: 'Access denied' });
23
24
  }
@@ -44,6 +44,7 @@ function handle(config, integration) {
44
44
  (0, util_1.log)(`Adding configuration fields ${JSON.stringify(configurationFields, null, 2)}`, config.logger);
45
45
  }
46
46
  options.infoModal = integration.infoModal;
47
+ options.syncNewElements = integration.syncNewElements;
47
48
  options.withCronSync = integration.withCronSync;
48
49
  options.webhooks = integration.webhooks
49
50
  ? {
@@ -3,6 +3,7 @@ Object.defineProperty(exports, "__esModule", { value: true });
3
3
  const models_1 = require("../models");
4
4
  const connection_1 = require("../util/connection");
5
5
  const util_1 = require("../util");
6
+ const api_1 = require("../util/api/api");
6
7
  function handle(config) {
7
8
  const modules = {};
8
9
  if (config.projectIntegration) {
@@ -182,6 +183,9 @@ function handle(config) {
182
183
  },
183
184
  ];
184
185
  }
186
+ if (config.api) {
187
+ modules['api'] = (0, api_1.getApiManifest)(config, config.api);
188
+ }
185
189
  const events = {
186
190
  installed: '/installed',
187
191
  uninstall: '/uninstall',
@@ -9,9 +9,12 @@ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, ge
9
9
  });
10
10
  };
11
11
  Object.defineProperty(exports, "__esModule", { value: true });
12
+ const models_1 = require("../models");
12
13
  const storage_1 = require("../storage");
13
14
  const util_1 = require("../util");
14
15
  const webhooks_1 = require("../util/webhooks");
16
+ const file_snapshot_1 = require("../util/file-snapshot");
17
+ const cron_1 = require("../util/cron");
15
18
  function handle(config, integration) {
16
19
  return (0, util_1.runAsyncWrapper)((req, res) => __awaiter(this, void 0, void 0, function* () {
17
20
  const appSettings = req.body.config;
@@ -20,6 +23,14 @@ function handle(config, integration) {
20
23
  if (integration.webhooks) {
21
24
  yield (0, webhooks_1.registerWebhooks)(config, integration, req.crowdinApiClient, req.crowdinContext, req.integrationCredentials, appSettings);
22
25
  }
26
+ if (appSettings['new-crowdin-files']) {
27
+ yield (0, cron_1.createOrUpdateSyncSettings)(config, req, {}, models_1.Provider.CROWDIN, true);
28
+ (0, file_snapshot_1.createOrUpdateFileSnapshot)(config, integration, req, models_1.Provider.CROWDIN);
29
+ }
30
+ if (appSettings['new-integration-files']) {
31
+ yield (0, cron_1.createOrUpdateSyncSettings)(config, req, [], models_1.Provider.INTEGRATION, true);
32
+ (0, file_snapshot_1.createOrUpdateFileSnapshot)(config, integration, req, models_1.Provider.INTEGRATION);
33
+ }
23
34
  res.status(204).end();
24
35
  }), config.onError);
25
36
  }
@@ -0,0 +1,4 @@
1
+ /// <reference types="qs" />
2
+ import { Response } from 'express';
3
+ import { Config } from '../models';
4
+ export default function handle(config: Config): (req: import("express").Request<import("express-serve-static-core").ParamsDictionary, any, any, import("qs").ParsedQs, Record<string, any>>, res: Response<any, Record<string, any>>, next: Function) => void;
@@ -0,0 +1,22 @@
1
+ "use strict";
2
+ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
3
+ function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
4
+ return new (P || (P = Promise))(function (resolve, reject) {
5
+ function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
6
+ function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
7
+ function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
8
+ step((generator = generator.apply(thisArg, _arguments || [])).next());
9
+ });
10
+ };
11
+ Object.defineProperty(exports, "__esModule", { value: true });
12
+ const util_1 = require("../util");
13
+ function handle(config) {
14
+ return (0, util_1.runAsyncWrapper)((req, res) => __awaiter(this, void 0, void 0, function* () {
15
+ let settings = {};
16
+ if (req.integrationSettings) {
17
+ settings = req.integrationSettings;
18
+ }
19
+ res.send(settings);
20
+ }), config.onError);
21
+ }
22
+ exports.default = handle;
@@ -1,4 +1,4 @@
1
1
  /// <reference types="qs" />
2
2
  import { Response } from 'express';
3
- import { Config } from '../models';
4
- export default function handle(config: Config): (req: import("express").Request<import("express-serve-static-core").ParamsDictionary, any, any, import("qs").ParsedQs, Record<string, any>>, res: Response<any, Record<string, any>>, next: Function) => void;
3
+ import { Config, IntegrationLogic } from '../models';
4
+ export default function handle(config: Config, integration: IntegrationLogic): (req: import("express").Request<import("express-serve-static-core").ParamsDictionary, any, any, import("qs").ParsedQs, Record<string, any>>, res: Response<any, Record<string, any>>, next: Function) => void;
@@ -9,19 +9,16 @@ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, ge
9
9
  });
10
10
  };
11
11
  Object.defineProperty(exports, "__esModule", { value: true });
12
- const storage_1 = require("../storage");
13
12
  const util_1 = require("../util");
14
- function handle(config) {
13
+ const file_snapshot_1 = require("../util/file-snapshot");
14
+ const cron_1 = require("../util/cron");
15
+ function handle(config, integration) {
15
16
  return (0, util_1.runAsyncWrapper)((req, res) => __awaiter(this, void 0, void 0, function* () {
16
- const { files, type, provider } = req.body;
17
- const existingSettings = yield (0, storage_1.getStorage)().getSyncSettings(req.crowdinContext.clientId, req.crowdinContext.crowdinId, type, provider);
18
- if (existingSettings) {
19
- (0, util_1.log)(`Updating sync settings for type ${type} and provider ${provider} ${JSON.stringify(files, null, 2)}`, config.logger);
20
- yield (0, storage_1.getStorage)().updateSyncSettings(JSON.stringify(files), req.crowdinContext.clientId, req.crowdinContext.crowdinId, type, provider);
21
- }
22
- else {
23
- (0, util_1.log)(`Saving sync settings for type ${type} and provider ${provider} ${JSON.stringify(files, null, 2)}`, config.logger);
24
- yield (0, storage_1.getStorage)().saveSyncSettings(JSON.stringify(files), req.crowdinContext.clientId, req.crowdinContext.crowdinId, type, provider);
17
+ var _a;
18
+ const { files, provider } = req.body;
19
+ yield (0, cron_1.createOrUpdateSyncSettings)(config, req, files, provider);
20
+ if ((_a = integration.syncNewElements) === null || _a === void 0 ? void 0 : _a[provider]) {
21
+ yield (0, file_snapshot_1.createOrUpdateFileSnapshot)(config, integration, req, provider);
25
22
  }
26
23
  res.status(204).end();
27
24
  }), config.onError);
@@ -14,7 +14,7 @@ const util_1 = require("../util");
14
14
  function handle(config) {
15
15
  return (0, util_1.runAsyncWrapper)((req, res) => __awaiter(this, void 0, void 0, function* () {
16
16
  let files = {};
17
- const provider = req.params.provider;
17
+ const provider = req.params.provider || req.body.provider;
18
18
  (0, util_1.log)(`Loading sync settings for provider ${provider}`, config.logger);
19
19
  const syncSettings = yield (0, storage_1.getStorage)().getSyncSettingsByProvider(req.crowdinContext.clientId, provider);
20
20
  if (syncSettings) {
package/out/index.js CHANGED
@@ -79,6 +79,7 @@ const connection_1 = require("./util/connection");
79
79
  const cron_1 = require("./util/cron");
80
80
  const defaults_1 = require("./util/defaults");
81
81
  const webhooks_1 = require("./util/webhooks");
82
+ const api_1 = require("./util/api/api");
82
83
  var models_2 = require("./models");
83
84
  Object.defineProperty(exports, "Scope", { enumerable: true, get: function () { return models_2.Scope; } });
84
85
  function addCrowdinEndpoints(app, clientConfig) {
@@ -142,7 +143,7 @@ function addCrowdinEndpoints(app, clientConfig) {
142
143
  app.post('/api/crowdin/update', json_response_1.default, (0, crowdin_client_1.default)(config), (0, integration_credentials_1.default)(config, integrationLogic), (0, crowdin_update_1.default)(config, integrationLogic));
143
144
  app.post('/api/integration/update', json_response_1.default, (0, crowdin_client_1.default)(config), (0, integration_credentials_1.default)(config, integrationLogic), (0, integration_update_1.default)(config, integrationLogic));
144
145
  app.get('/api/sync-settings/:provider', json_response_1.default, (0, crowdin_client_1.default)(config), (0, integration_credentials_1.default)(config, integrationLogic), (0, sync_settings_1.default)(config));
145
- app.post('/api/sync-settings', json_response_1.default, (0, crowdin_client_1.default)(config), (0, integration_credentials_1.default)(config, integrationLogic), (0, sync_settings_save_1.default)(config));
146
+ app.post('/api/sync-settings', json_response_1.default, (0, crowdin_client_1.default)(config), (0, integration_credentials_1.default)(config, integrationLogic), (0, sync_settings_save_1.default)(config, integrationLogic));
146
147
  if (integrationLogic.oauthLogin) {
147
148
  app.get((0, defaults_1.getOauthRoute)(integrationLogic), (0, oauth_login_1.default)(config, integrationLogic));
148
149
  app.post('/api/oauth-url', json_response_1.default, (0, crowdin_client_1.default)(config, false, false), (0, oauth_url_1.default)(config, integrationLogic));
@@ -228,6 +229,12 @@ function addCrowdinEndpoints(app, clientConfig) {
228
229
  if (((_f = config.contextMenu) === null || _f === void 0 ? void 0 : _f.uiPath) || ((_g = config.contextMenu) === null || _g === void 0 ? void 0 : _g.formSchema)) {
229
230
  app.use('/context', (0, ui_module_1.default)(config, config.contextMenu.allowUnauthorized), (0, render_ui_module_1.default)(config, config.contextMenu));
230
231
  }
232
+ if (config.api) {
233
+ if (config.api.default) {
234
+ (0, api_1.addDefaultApiEndpoints)(app, config);
235
+ }
236
+ (0, api_1.addSwagerApiDocumentation)(app, config);
237
+ }
231
238
  if (Object.keys(config).some((moduleKey) => {
232
239
  const moduleConfig = config[moduleKey];
233
240
  return typeof moduleConfig === 'object' && moduleConfig.hasOwnProperty('formSchema');
@@ -14,6 +14,7 @@ const crowdin_apps_functions_1 = require("@crowdin/crowdin-apps-functions");
14
14
  const storage_1 = require("../storage");
15
15
  const util_1 = require("../util");
16
16
  const connection_1 = require("../util/connection");
17
+ const api_1 = require("../util/api/api");
17
18
  function prepareCrowdinRequest(jwtToken, config, optional = false, checkSubscriptionExpiration = true) {
18
19
  return __awaiter(this, void 0, void 0, function* () {
19
20
  (0, util_1.log)('Validating jwt token from incoming request', config.logger);
@@ -46,12 +47,16 @@ function prepareCrowdinRequest(jwtToken, config, optional = false, checkSubscrip
46
47
  exports.prepareCrowdinRequest = prepareCrowdinRequest;
47
48
  function handle(config, optional = false, checkSubscriptionExpiration = true) {
48
49
  return (0, util_1.runAsyncWrapper)((req, res, next) => __awaiter(this, void 0, void 0, function* () {
50
+ var _a;
49
51
  const jwtToken = getToken(req);
50
52
  if (!jwtToken) {
51
53
  return res.status(403).send({ error: 'Access denied' });
52
54
  }
53
55
  try {
54
56
  const data = yield prepareCrowdinRequest(jwtToken, config, optional, checkSubscriptionExpiration);
57
+ if ((_a = config.api) === null || _a === void 0 ? void 0 : _a.default) {
58
+ data.context = (0, api_1.updateCrowdinContext)(req, data.context);
59
+ }
55
60
  req.crowdinContext = data.context;
56
61
  if (data.client) {
57
62
  req.crowdinApiClient = data.client;
@@ -104,6 +104,10 @@ export interface ClientConfig extends ImagePath {
104
104
  * reports module
105
105
  */
106
106
  projectReports?: UiModule & ImagePath;
107
+ /**
108
+ * API module
109
+ */
110
+ api?: ApiModule;
107
111
  /**
108
112
  * context menu module
109
113
  */
@@ -235,6 +239,13 @@ export interface IntegrationLogic {
235
239
  * background jobs that will be executed for each crowdin project and user
236
240
  */
237
241
  cronJobs?: CronJob[];
242
+ /**
243
+ * Enable new file sync when syncing via cron or webhook
244
+ */
245
+ syncNewElements?: {
246
+ crowdin: boolean;
247
+ integration: boolean;
248
+ };
238
249
  withCronSync?: {
239
250
  crowdin: boolean;
240
251
  integration: boolean;
@@ -754,12 +765,23 @@ export interface CrowdinAppUtilities {
754
765
  extra: Record<string, any>;
755
766
  }>;
756
767
  }
768
+ export declare enum Provider {
769
+ CROWDIN = "crowdin",
770
+ INTEGRATION = "integration"
771
+ }
757
772
  export interface IntegrationSyncSettings {
758
773
  id: number;
759
774
  files?: any;
760
775
  integrationId: string;
761
776
  crowdinId: string;
762
- provider: 'integration' | 'crowdin';
777
+ provider: Provider;
778
+ }
779
+ export interface IntegrationFilesSnapshot {
780
+ id: number;
781
+ files?: any;
782
+ integrationId: string;
783
+ crowdinId: string;
784
+ provider: Provider;
763
785
  }
764
786
  export interface ImagePath {
765
787
  /**
@@ -767,6 +789,26 @@ export interface ImagePath {
767
789
  */
768
790
  imagePath?: string;
769
791
  }
792
+ export declare enum RequestMethods {
793
+ GET = "GET",
794
+ POST = "POST",
795
+ PUT = "PUT",
796
+ PATCH = "PATCH",
797
+ DELETE = "DELETE"
798
+ }
799
+ export interface ApiEndpoints {
800
+ key: string;
801
+ name: string;
802
+ url: string;
803
+ method: RequestMethods;
804
+ description?: string;
805
+ documentationUrl?: string;
806
+ }
807
+ export interface ApiModule {
808
+ default?: boolean;
809
+ endpoints?: ApiEndpoints[];
810
+ docFile?: string;
811
+ }
770
812
  export interface Logger {
771
813
  enabled: boolean;
772
814
  log?: (message: string) => void;
@@ -785,8 +827,8 @@ export interface Webhooks {
785
827
  urlParam?: string;
786
828
  crowdinWebhooks?: (client: Crowdin, projectId: number, available: boolean, config?: any) => Promise<void>;
787
829
  integrationWebhooks?: (apiCredentials: any, urlParam: string, available: boolean, config?: any, syncSettings?: any) => Promise<void>;
788
- crowdinWebhookInterceptor?: (projectId: number, client: Crowdin, appRootFolder?: SourceFilesModel.Directory, config?: any, syncSettings?: any, webhookRequest?: any) => Promise<UpdateIntegrationRequest>;
789
- integrationWebhookInterceptor?: (projectId: number, client: Crowdin, apiCredentials: any, appRootFolder?: SourceFilesModel.Directory, config?: any, syncSettings?: any, webhookRequest?: any) => Promise<IntegrationFile[]>;
830
+ crowdinWebhookInterceptor?: (projectId: number, client: Crowdin, appRootFolder?: SourceFilesModel.Directory, config?: any, syncSettings?: any, webhookRequest?: any, newFiles?: TreeItem[] | UpdateIntegrationRequest) => Promise<UpdateIntegrationRequest>;
831
+ integrationWebhookInterceptor?: (projectId: number, client: Crowdin, apiCredentials: any, appRootFolder?: SourceFilesModel.Directory, config?: any, syncSettings?: any, webhookRequest?: any, newFiles?: TreeItem[] | UpdateIntegrationRequest) => Promise<IntegrationFile[]>;
790
832
  queueUrl: string;
791
833
  }
792
834
  export declare enum SyncCondition {
@@ -810,4 +852,15 @@ export type WebhookUrlParams = {
810
852
  crowdinId: string;
811
853
  clientId: string;
812
854
  };
855
+ export interface GetAllNewFilesArgs {
856
+ config: Config;
857
+ integration: IntegrationLogic;
858
+ crowdinApiClient: Crowdin;
859
+ crowdinId: string;
860
+ integrationCredentials: any;
861
+ integrationId: string;
862
+ projectId: number;
863
+ integrationSettings: any;
864
+ syncSettings: IntegrationSyncSettings;
865
+ }
813
866
  export {};
@@ -1,6 +1,6 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.SyncType = exports.SyncCondition = exports.ContextOptionsTypes = exports.ContextOptionsLocations = exports.EditorPanelsMode = exports.ProcessFileJobType = exports.SubscriptionInfoType = exports.AccountType = exports.Scope = exports.AuthenticationType = void 0;
3
+ exports.SyncType = exports.SyncCondition = exports.RequestMethods = exports.Provider = exports.ContextOptionsTypes = exports.ContextOptionsLocations = exports.EditorPanelsMode = exports.ProcessFileJobType = exports.SubscriptionInfoType = exports.AccountType = exports.Scope = exports.AuthenticationType = void 0;
4
4
  var AuthenticationType;
5
5
  (function (AuthenticationType) {
6
6
  AuthenticationType["CODE"] = "authorization_code";
@@ -66,6 +66,19 @@ var ContextOptionsTypes;
66
66
  ContextOptionsTypes["NEW_TAB"] = "new_tab";
67
67
  ContextOptionsTypes["REDIRECT"] = "redirect";
68
68
  })(ContextOptionsTypes = exports.ContextOptionsTypes || (exports.ContextOptionsTypes = {}));
69
+ var Provider;
70
+ (function (Provider) {
71
+ Provider["CROWDIN"] = "crowdin";
72
+ Provider["INTEGRATION"] = "integration";
73
+ })(Provider = exports.Provider || (exports.Provider = {}));
74
+ var RequestMethods;
75
+ (function (RequestMethods) {
76
+ RequestMethods["GET"] = "GET";
77
+ RequestMethods["POST"] = "POST";
78
+ RequestMethods["PUT"] = "PUT";
79
+ RequestMethods["PATCH"] = "PATCH";
80
+ RequestMethods["DELETE"] = "DELETE";
81
+ })(RequestMethods = exports.RequestMethods || (exports.RequestMethods = {}));
69
82
  var SyncCondition;
70
83
  (function (SyncCondition) {
71
84
  SyncCondition[SyncCondition["ALL"] = 0] = "ALL";
@@ -3,8 +3,7 @@ document.addEventListener('DOMContentLoaded', () => {
3
3
 
4
4
  if (fields.length > 0) {
5
5
  fields.forEach((field) => {
6
- const conditionString = field.dataset['dependency'].replace(/'/g, '"');
7
- const conditions = JSON.parse(conditionString);
6
+ const conditions = JSON.parse( field.dataset['dependency']);
8
7
  action(field, conditions);
9
8
 
10
9
  const success = check(conditions);
@@ -1,4 +1,4 @@
1
- import { Config, CrowdinCredentials, IntegrationCredentials, IntegrationSyncSettings } from '../models';
1
+ import { Config, CrowdinCredentials, IntegrationCredentials, IntegrationFilesSnapshot, IntegrationSyncSettings, Provider } from '../models';
2
2
  export interface Storage {
3
3
  migrate(): Promise<void>;
4
4
  saveCrowdinCredentials(credentials: CrowdinCredentials): Promise<void>;
@@ -17,11 +17,14 @@ export interface Storage {
17
17
  updateMetadata(id: string, metadata: any): Promise<void>;
18
18
  getMetadata(id: string): Promise<any | undefined>;
19
19
  deleteMetadata(id: string): Promise<void>;
20
- getSyncSettingsByProvider(integrationId: string, provider: string): Promise<IntegrationSyncSettings | undefined>;
20
+ getSyncSettingsByProvider(integrationId: string, provider: Provider): Promise<IntegrationSyncSettings | undefined>;
21
21
  getAllSyncSettingsByType(type: string): Promise<IntegrationSyncSettings[]>;
22
- saveSyncSettings(files: any, integrationId: string, crowdinId: string, type: string, provider: string): Promise<void>;
23
- updateSyncSettings(files: any, integrationId: string, crowdinId: string, type: string, provider: string): Promise<void>;
24
- getSyncSettings(integrationId: string, crowdinId: string, type: string, provider: string): Promise<IntegrationSyncSettings | undefined>;
22
+ saveSyncSettings(files: any, integrationId: string, crowdinId: string, type: string, provider: Provider): Promise<void>;
23
+ updateSyncSettings(files: any, integrationId: string, crowdinId: string, type: string, provider: Provider): Promise<void>;
24
+ getSyncSettings(integrationId: string, crowdinId: string, type: string, provider: Provider): Promise<IntegrationSyncSettings | undefined>;
25
+ saveFilesSnapshot(files: any, integrationId: string, crowdinId: string, provider: Provider): Promise<void>;
26
+ updateFilesSnapshot(files: any, integrationId: string, crowdinId: string, provider: Provider): Promise<void>;
27
+ getFilesSnapshot(integrationId: string, crowdinId: string, provider: Provider): Promise<IntegrationFilesSnapshot | undefined>;
25
28
  }
26
29
  export declare function initialize(config: Config): Promise<void>;
27
30
  export declare function getStorage(): Storage;
@@ -1,5 +1,5 @@
1
1
  import { Storage } from '.';
2
- import { CrowdinCredentials, IntegrationCredentials, IntegrationSyncSettings } from '../models';
2
+ import { CrowdinCredentials, IntegrationCredentials, IntegrationFilesSnapshot, IntegrationSyncSettings } from '../models';
3
3
  export interface MySQLStorageConfig {
4
4
  uri?: string;
5
5
  host?: string;
@@ -39,4 +39,7 @@ export declare class MySQLStorage implements Storage {
39
39
  saveSyncSettings(files: any, integrationId: string, crowdinId: string, type: string, provider: string): Promise<void>;
40
40
  updateSyncSettings(files: any, integrationId: string, crowdinId: string, type: string, provider: string): Promise<void>;
41
41
  getSyncSettings(integrationId: string, crowdinId: string, type: string, provider: string): Promise<IntegrationSyncSettings | undefined>;
42
+ saveFilesSnapshot(files: any, integrationId: string, crowdinId: string, provider: string): Promise<void>;
43
+ updateFilesSnapshot(files: any, integrationId: string, crowdinId: string, provider: string): Promise<void>;
44
+ getFilesSnapshot(integrationId: string, crowdinId: string, provider: string): Promise<IntegrationFilesSnapshot | undefined>;
42
45
  }
@@ -103,6 +103,16 @@ class MySQLStorage {
103
103
  data text
104
104
  )
105
105
  `);
106
+ yield connection.execute(`
107
+ create table if not exists files_snapshot
108
+ (
109
+ id int auto_increment primary key,
110
+ files text,
111
+ integration_id varchar(255) not null,
112
+ crowdin_id varchar(255) not null,
113
+ provider varchar(255) not null
114
+ )
115
+ `);
106
116
  });
107
117
  }
108
118
  saveCrowdinCredentials(credentials) {
@@ -163,6 +173,7 @@ class MySQLStorage {
163
173
  yield connection.execute('DELETE FROM crowdin_credentials where id = ?', [id]);
164
174
  yield connection.execute('DELETE FROM integration_credentials where crowdin_id = ?', [id]);
165
175
  yield connection.execute('DELETE FROM sync_settings WHERE crowdin_id = ?', [id]);
176
+ yield connection.execute('DELETE FROM files_snapshot WHERE crowdin_id = ?', [id]);
166
177
  }));
167
178
  });
168
179
  }
@@ -212,6 +223,7 @@ class MySQLStorage {
212
223
  yield this.executeQuery((connection) => __awaiter(this, void 0, void 0, function* () {
213
224
  yield connection.execute('DELETE FROM integration_credentials where id = ?', [id]);
214
225
  yield connection.execute('DELETE FROM sync_settings where integration_id = ?', [id]);
226
+ yield connection.execute('DELETE FROM files_snapshot where integration_id = ?', [id]);
215
227
  }));
216
228
  });
217
229
  }
@@ -221,6 +233,7 @@ class MySQLStorage {
221
233
  yield this.executeQuery((connection) => __awaiter(this, void 0, void 0, function* () {
222
234
  yield connection.execute('DELETE FROM integration_credentials where crowdin_id = ?', [crowdinId]);
223
235
  yield connection.execute('DELETE FROM sync_settings where crowdin_id = ?', [crowdinId]);
236
+ yield connection.execute('DELETE FROM files_snapshot where crowdin_id = ?', [crowdinId]);
224
237
  }));
225
238
  });
226
239
  }
@@ -287,7 +300,28 @@ class MySQLStorage {
287
300
  return __awaiter(this, void 0, void 0, function* () {
288
301
  yield this.dbPromise;
289
302
  return this.executeQuery((connection) => __awaiter(this, void 0, void 0, function* () {
290
- const [rows] = yield connection.execute('SELECT id, files, integration_id as "integrationId", crowdin_id as "crowdinId", type FROM sync_settings WHERE integration_id = ? AND crowdin_id = ? AND type = ? AND provider = ?', [integrationId, crowdinId, type, provider]);
303
+ const [rows] = yield connection.execute('SELECT id, files, integration_id as "integrationId", crowdin_id as "crowdinId", type, provider FROM sync_settings WHERE integration_id = ? AND crowdin_id = ? AND type = ? AND provider = ?', [integrationId, crowdinId, type, provider]);
304
+ return (rows || [])[0];
305
+ }));
306
+ });
307
+ }
308
+ saveFilesSnapshot(files, integrationId, crowdinId, provider) {
309
+ return __awaiter(this, void 0, void 0, function* () {
310
+ yield this.dbPromise;
311
+ yield this.executeQuery((connection) => connection.execute('INSERT INTO files_snapshot(files, integration_id, crowdin_id, provider) VALUES (?, ?, ?, ?)', [files, integrationId, crowdinId, provider]));
312
+ });
313
+ }
314
+ updateFilesSnapshot(files, integrationId, crowdinId, provider) {
315
+ return __awaiter(this, void 0, void 0, function* () {
316
+ yield this.dbPromise;
317
+ yield this.executeQuery((connection) => connection.execute('UPDATE files_snapshot SET files = ? WHERE integration_id = ? AND crowdin_id = ? AND provider = ?', [files, integrationId, crowdinId, provider]));
318
+ });
319
+ }
320
+ getFilesSnapshot(integrationId, crowdinId, provider) {
321
+ return __awaiter(this, void 0, void 0, function* () {
322
+ yield this.dbPromise;
323
+ return this.executeQuery((connection) => __awaiter(this, void 0, void 0, function* () {
324
+ const [rows] = yield connection.execute('SELECT id, files, integration_id as "integrationId", crowdin_id as "crowdinId" FROM files_snapshot WHERE integration_id = ? AND crowdin_id = ? AND provider = ?', [integrationId, crowdinId, provider]);
291
325
  return (rows || [])[0];
292
326
  }));
293
327
  });
@@ -1,6 +1,6 @@
1
1
  import { Client } from 'pg';
2
2
  import { Storage } from '.';
3
- import { CrowdinCredentials, IntegrationCredentials, IntegrationSyncSettings } from '../models';
3
+ import { CrowdinCredentials, IntegrationCredentials, IntegrationFilesSnapshot, IntegrationSyncSettings } from '../models';
4
4
  export interface PostgreStorageConfig {
5
5
  host?: string;
6
6
  connectionString?: string;
@@ -43,4 +43,7 @@ export declare class PostgreStorage implements Storage {
43
43
  saveSyncSettings(files: any, integrationId: string, crowdinId: string, type: string, provider: string): Promise<void>;
44
44
  updateSyncSettings(files: any, integrationId: string, crowdinId: string, type: string, provider: string): Promise<void>;
45
45
  getSyncSettings(integrationId: string, crowdinId: string, type: string, provider: string): Promise<IntegrationSyncSettings | undefined>;
46
+ saveFilesSnapshot(files: any, integrationId: string, crowdinId: string, provider: string): Promise<void>;
47
+ updateFilesSnapshot(files: any, integrationId: string, crowdinId: string, provider: string): Promise<void>;
48
+ getFilesSnapshot(integrationId: string, crowdinId: string, provider: string): Promise<IntegrationFilesSnapshot | undefined>;
46
49
  }
@@ -99,6 +99,16 @@ class PostgreStorage {
99
99
  data varchar
100
100
  )
101
101
  `);
102
+ yield client.query(`
103
+ create table if not exists files_snapshot
104
+ (
105
+ id serial primary key,
106
+ integration_id varchar not null,
107
+ crowdin_id varchar not null,
108
+ files varchar,
109
+ provider varchar not null
110
+ )
111
+ `);
102
112
  });
103
113
  }
104
114
  saveCrowdinCredentials(credentials) {
@@ -159,6 +169,7 @@ class PostgreStorage {
159
169
  yield client.query('DELETE FROM crowdin_credentials where id = $1', [id]);
160
170
  yield client.query('DELETE FROM integration_credentials where crowdin_id = $1', [id]);
161
171
  yield client.query('DELETE FROM sync_settings WHERE crowdin_id = $1', [id]);
172
+ yield client.query('DELETE FROM files_snapshot WHERE crowdin_id = $1', [id]);
162
173
  }));
163
174
  });
164
175
  }
@@ -208,6 +219,7 @@ class PostgreStorage {
208
219
  yield this.executeQuery((client) => __awaiter(this, void 0, void 0, function* () {
209
220
  yield client.query('DELETE FROM integration_credentials where id = $1', [id]);
210
221
  yield client.query('DELETE FROM sync_settings where integration_id = $1', [id]);
222
+ yield client.query('DELETE FROM files_snapshot where integration_id = $1', [id]);
211
223
  }));
212
224
  });
213
225
  }
@@ -217,6 +229,7 @@ class PostgreStorage {
217
229
  yield this.executeQuery((client) => __awaiter(this, void 0, void 0, function* () {
218
230
  yield client.query('DELETE FROM integration_credentials where crowdin_id = $1', [crowdinId]);
219
231
  yield client.query('DELETE FROM sync_settings where crowdin_id = $1', [crowdinId]);
232
+ yield client.query('DELETE FROM files_snapshot where crowdin_id = $1', [crowdinId]);
220
233
  }));
221
234
  });
222
235
  }
@@ -283,7 +296,28 @@ class PostgreStorage {
283
296
  return __awaiter(this, void 0, void 0, function* () {
284
297
  yield this.dbPromise;
285
298
  return this.executeQuery((client) => __awaiter(this, void 0, void 0, function* () {
286
- const res = yield client.query('SELECT id, files, integration_id as "integrationId", crowdin_id as "crowdinId", type FROM sync_settings WHERE integration_id = $1 AND crowdin_id = $2 AND type = $3 AND provider = $4', [integrationId, crowdinId, type, provider]);
299
+ const res = yield client.query('SELECT id, files, integration_id as "integrationId", crowdin_id as "crowdinId", type, provider FROM sync_settings WHERE integration_id = $1 AND crowdin_id = $2 AND type = $3 AND provider = $4', [integrationId, crowdinId, type, provider]);
300
+ return res === null || res === void 0 ? void 0 : res.rows[0];
301
+ }));
302
+ });
303
+ }
304
+ saveFilesSnapshot(files, integrationId, crowdinId, provider) {
305
+ return __awaiter(this, void 0, void 0, function* () {
306
+ yield this.dbPromise;
307
+ yield this.executeQuery((client) => client.query('INSERT INTO files_snapshot(integration_id, crowdin_id, files, provider) VALUES ($1, $2, $3, $4)', [files, integrationId, crowdinId, provider]));
308
+ });
309
+ }
310
+ updateFilesSnapshot(files, integrationId, crowdinId, provider) {
311
+ return __awaiter(this, void 0, void 0, function* () {
312
+ yield this.dbPromise;
313
+ yield this.executeQuery((client) => client.query('UPDATE files_snapshot SET files = $1 WHERE integration_id = $2 AND crowdin_id = $3 AND provider = $4', [files, integrationId, crowdinId, provider]));
314
+ });
315
+ }
316
+ getFilesSnapshot(integrationId, crowdinId, provider) {
317
+ return __awaiter(this, void 0, void 0, function* () {
318
+ yield this.dbPromise;
319
+ return this.executeQuery((client) => __awaiter(this, void 0, void 0, function* () {
320
+ const res = yield client.query('SELECT id, files, integration_id as "integrationId", crowdin_id as "crowdinId" FROM files_snapshot WHERE integration_id = $1 AND crowdin_id = $2 AND provider = $3', [integrationId, crowdinId, provider]);
287
321
  return res === null || res === void 0 ? void 0 : res.rows[0];
288
322
  }));
289
323
  });