@crowdin/app-project-module 0.93.0 → 0.94.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -14,6 +14,7 @@ export declare const TABLES: {
14
14
  job: string;
15
15
  translation_file_cache: string;
16
16
  unsynced_files: string;
17
+ synced_data: string;
17
18
  };
18
19
  export interface Storage {
19
20
  tables: typeof TABLES;
@@ -58,6 +58,7 @@ exports.TABLES = {
58
58
  job: 'job',
59
59
  translation_file_cache: 'translation_file_cache',
60
60
  unsynced_files: 'unsynced_files',
61
+ synced_data: 'synced_data',
61
62
  };
62
63
  let storage;
63
64
  function initialize(config) {
@@ -44,6 +44,7 @@ export declare class PostgreStorage implements Storage {
44
44
  tableIndexes: TableIndexes;
45
45
  constructor(config: PostgreStorageConfig, directoryPath: string | null);
46
46
  executeQuery<T>(command: (client: Client) => Promise<T>): Promise<T>;
47
+ private hasDumpFiles;
47
48
  migrate(): Promise<void>;
48
49
  alterTables(client: Client): Promise<void>;
49
50
  addColumns(client: Client, newColumns: string[], tableName: string): Promise<void>;
@@ -194,10 +194,18 @@ class PostgreStorage {
194
194
  }));
195
195
  });
196
196
  }
197
+ hasDumpFiles(directoryPath) {
198
+ if (!fs_1.default.existsSync(directoryPath)) {
199
+ return false;
200
+ }
201
+ const [name, extension] = types_1.storageFiles.DUMP.split('%s');
202
+ const files = fs_1.default.readdirSync(directoryPath).filter((file) => file.startsWith(name) && file.endsWith(extension));
203
+ return files.length > 0;
204
+ }
197
205
  migrate() {
198
206
  return __awaiter(this, void 0, void 0, function* () {
199
207
  try {
200
- if (this.directoryPath && fs_1.default.existsSync(this.directoryPath + '/' + types_1.storageFiles.SQLITE)) {
208
+ if (this.directoryPath && this.hasDumpFiles(this.directoryPath)) {
201
209
  yield this.migrateFromSqlite(this.directoryPath);
202
210
  }
203
211
  yield this.executeQuery((client) => this.addTables(client));
@@ -462,7 +462,7 @@
462
462
  <script type="text/javascript">
463
463
  document.body.addEventListener('refreshFilesList', (e) => {
464
464
  if (e.detail.refreshIntegration) {
465
- getIntegrationData(true);
465
+ getIntegrationData({ hardReload: true });
466
466
  } else if (e.detail.refreshCrowdin) {
467
467
  getCrowdinData();
468
468
  }
@@ -473,7 +473,7 @@
473
473
  }
474
474
  {{#if integrationOneLevelFetching}}
475
475
  if (event.detail.componentId === 'integration-files' && event.detail.isOpen) {
476
- getIntegrationData(false, event.detail.id);
476
+ getIntegrationData({ parentId: event.detail.id, recursion: event.detail.recursion });
477
477
  }
478
478
  {{/if}}
479
479
  });
@@ -484,7 +484,7 @@
484
484
  });
485
485
  {{#if integrationSearchListener}}
486
486
  document.body.addEventListener("integrationFilterChange", (event) => {
487
- getIntegrationData(false, 0, event.detail);
487
+ getIntegrationData({ search: event.detail });
488
488
  })
489
489
  {{/if}}
490
490
  const appComponent = document.querySelector('crowdin-simple-integration');
@@ -521,7 +521,7 @@
521
521
  let fileToSync = [];
522
522
 
523
523
  getCrowdinData();
524
- getIntegrationData();
524
+ getIntegrationData({});
525
525
  getActiveJobs();
526
526
 
527
527
  function integrationLogout() {
@@ -588,12 +588,12 @@
588
588
  .finally(() => (appComponent.setAttribute('is-crowdin-loading', false)));
589
589
  }
590
590
 
591
- function getIntegrationData(hardReload = false, parentId = '', search = '', page = 0) {
591
+ function getIntegrationData({ hardReload = false, parentId = '', search = '', page = 0, recursion = false } = {}, recursionState = null) {
592
592
  appComponent.setAttribute('is-integration-loading', true);
593
- checkOrigin()
593
+ return checkOrigin()
594
594
  .then(restParams => fetch(`api/integration/data${restParams}&parent_id=${encodeURIComponent(parentId)}&search=${encodeURIComponent(search)}&page=${page}`))
595
595
  .then(checkResponse)
596
- .then((res) => {
596
+ .then(async (res) => {
597
597
  const files = res.data;
598
598
  const stopPagination = res.stopPagination;
599
599
  const tree = files.map(e => {
@@ -647,12 +647,61 @@
647
647
  const openIds = files.filter(e => !e.type).map(e => e.id);
648
648
  appComponent.setIntegrationOpenedFolders(openIds);
649
649
  }
650
+
651
+ if (recursion) {
652
+ if (!recursionState) {
653
+ recursionState = {
654
+ openedFolders: new Set(),
655
+ calls: 0,
656
+ setLoading(isLoading) {
657
+ appComponent.setAttribute('is-integration-loading', isLoading);
658
+ },
659
+ };
660
+ recursionState.setLoading(true);
661
+ }
662
+
663
+ if (parentId) {
664
+ recursionState.openedFolders.add(parentId);
665
+ }
666
+
667
+ const folderItems = files.filter(isFolder);
668
+
669
+ if (folderItems.length === 0) {
670
+ return Promise.resolve();
671
+ }
672
+
673
+ folderItems.forEach(folder => recursionState.openedFolders.add(folder.id));
674
+
675
+ const currentOpenedFolders = await appComponent.getIntegrationOpenedFolders();
676
+ appComponent.setIntegrationOpenedFolders([...currentOpenedFolders, ...recursionState.openedFolders]);
677
+
678
+ const recursivePromises = folderItems.map(async folder => {
679
+ recursionState.calls++;
680
+
681
+ try {
682
+ return getIntegrationData({ parentId: folder.id, recursion: true }, recursionState);
683
+ } finally {
684
+ recursionState.calls--;
685
+ if (recursionState.calls === 0) {
686
+ recursionState.setLoading(false);
687
+ }
688
+ }
689
+ });
690
+
691
+ return Promise.all(recursivePromises);
692
+ }
650
693
  })
651
694
  {{#or withCronSync webhooks}}
652
695
  .then(() => getSyncSettings('integration'))
653
696
  {{/or}}
654
697
  .catch(e => catchRejection(e, 'Can\'t fetch {{name}} templates'))
655
- .finally(() => (appComponent.setAttribute('is-integration-loading', false)));
698
+ .finally(() => {
699
+ if (!recursionState && !recursion) {
700
+ appComponent.setAttribute('is-integration-loading', false);
701
+ } else if (recursionState && recursionState.calls === 0) {
702
+ appComponent.setAttribute('is-integration-loading', false);
703
+ }
704
+ });
656
705
  }
657
706
 
658
707
  function getSyncSettings(provider) {
@@ -1356,7 +1405,7 @@
1356
1405
  if (!isValidationError) {
1357
1406
  closeModal(settingsModal);
1358
1407
  {{#if reloadOnConfigSave}}
1359
- getIntegrationData(true);
1408
+ getIntegrationData({ hardReload: true });
1360
1409
  getCrowdinData();
1361
1410
  {{/if}}
1362
1411
  }
@@ -1399,7 +1448,7 @@
1399
1448
 
1400
1449
  {{#if integrationPagination}}
1401
1450
  document.body.addEventListener('fileListEnd', (e) => {
1402
- getIntegrationData(false, 0, '', e.detail.page)
1451
+ getIntegrationData({ page: e.detail.page });
1403
1452
  })
1404
1453
  {{/if}}
1405
1454
 
@@ -1799,6 +1848,10 @@
1799
1848
  el.removeAttribute('error');
1800
1849
  el.removeAttribute('error-text');
1801
1850
  }
1851
+
1852
+ function isFolder(e) {
1853
+ return !e.type && (e.nodeType === undefined || e.nodeType === folderType || e.nodeType === branchType);
1854
+ }
1802
1855
  </script>
1803
1856
 
1804
1857
  </html>
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@crowdin/app-project-module",
3
- "version": "0.93.0",
3
+ "version": "0.94.1",
4
4
  "description": "Module that generates for you all common endpoints for serving standalone Crowdin App",
5
5
  "main": "out/index.js",
6
6
  "types": "out/index.d.ts",