@getjones/test-infra 5.2.16 → 5.3.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.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@getjones/test-infra",
3
- "version": "5.2.16",
3
+ "version": "5.3.1",
4
4
  "description": "Providing internal and openapi interface",
5
5
  "main": "src/index.js",
6
6
  "files": [
@@ -7,6 +7,10 @@ module.exports = {
7
7
  on: { isAccountRequirementsEnabled: true },
8
8
  off: { isAccountRequirementsEnabled: false }
9
9
  },
10
+ isWeeklyDigestEnabled: {
11
+ on: { isWeeklyDigestEnabled: true },
12
+ off: { isWeeklyDigestEnabled: false }
13
+ },
10
14
  isPolicyVerificationEnabled: {
11
15
  on: { hasPolicyVerification: true },
12
16
  off: { hasPolicyVerification: false }
package/src/index.js CHANGED
@@ -48,6 +48,7 @@ const getInternalAPI = () => {
48
48
 
49
49
  const threadScheduler = require('./saas/internal-api/thread-scheduler/runner');
50
50
  const schedulerJobRun = require('./saas/internal-api/schedulerJobRun');
51
+ const weeklyDigest = require('./saas/internal-api/weeklyDigest');
51
52
  const certificial = require('./saas/internal-api/certificial');
52
53
  const dbEmails = require('./saas/internal-api/dbEmails/index');
53
54
  const agreement = require('./saas/internal-api/agreement/index');
@@ -89,6 +90,7 @@ const getInternalAPI = () => {
89
90
  sampleCoi,
90
91
  threadScheduler,
91
92
  schedulerJobRun,
93
+ weeklyDigest,
92
94
  certificial,
93
95
  dbEmails,
94
96
  emailCustomization,
@@ -289,6 +289,7 @@ const getAllRecords = async (accountId, context, {
289
289
  sortOrder,
290
290
  pageNum,
291
291
  rowsPerPage,
292
+ digestScope,
292
293
  expectError
293
294
  } = {}) => {
294
295
  const model = new accountDirectoryModels.AllRecordsTableRequestModel({
@@ -304,7 +305,8 @@ const getAllRecords = async (accountId, context, {
304
305
  sortBy,
305
306
  sortOrder,
306
307
  pageNum,
307
- rowsPerPage
308
+ rowsPerPage,
309
+ digestScope
308
310
  });
309
311
 
310
312
  const response = await accountDirectoryAPI.getAllRecords(model, context);
@@ -329,6 +331,7 @@ const selectAllRecords = async (accountId, context, {
329
331
  selectedTagIds,
330
332
  expiryDateFrom,
331
333
  expiryDateTo,
334
+ digestScope,
332
335
  expectError
333
336
  } = {}) => {
334
337
  const model = new accountDirectoryModels.AllRecordsTableRequestModel({
@@ -340,7 +343,8 @@ const selectAllRecords = async (accountId, context, {
340
343
  selectedRequirementIds,
341
344
  selectedTagIds,
342
345
  expiryDateFrom,
343
- expiryDateTo
346
+ expiryDateTo,
347
+ digestScope
344
348
  });
345
349
 
346
350
  const response = await accountDirectoryAPI.selectAllRecords(model, context);
@@ -397,6 +401,7 @@ const exportAllRecords = async (accountId, context, {
397
401
  expiryDateTo,
398
402
  sortBy,
399
403
  sortOrder,
404
+ digestScope,
400
405
  expectError
401
406
  } = {}) => {
402
407
  const model = new accountDirectoryModels.AllRecordsTableRequestModel({
@@ -410,7 +415,8 @@ const exportAllRecords = async (accountId, context, {
410
415
  expiryDateFrom,
411
416
  expiryDateTo,
412
417
  sortBy,
413
- sortOrder
418
+ sortOrder,
419
+ digestScope
414
420
  });
415
421
 
416
422
  const response = await accountDirectoryAPI.exportAllRecords(model, context);
@@ -80,7 +80,8 @@ class AllRecordsTableRequestModel {
80
80
  sortBy = ALL_RECORDS_TABLE_SORT_BY.COMPANY_NAME,
81
81
  sortOrder = 'ASC',
82
82
  pageNum = 1,
83
- rowsPerPage = ROWS_PER_PAGE.TEN
83
+ rowsPerPage = ROWS_PER_PAGE.TEN,
84
+ digestScope = undefined
84
85
  } = {}) {
85
86
  this.accountId = accountId;
86
87
  this.searchTerm = searchTerm;
@@ -95,6 +96,7 @@ class AllRecordsTableRequestModel {
95
96
  this.sortOrder = sortOrder;
96
97
  this.pageNum = pageNum;
97
98
  this.rowsPerPage = rowsPerPage;
99
+ this.digestScope = digestScope;
98
100
  }
99
101
  }
100
102
 
@@ -33,6 +33,7 @@ class UpdateAccountSettingsModel {
33
33
  inviteGapCadence = null,
34
34
  isAcord25SplitExtractionEnabled = false,
35
35
  isCertificialEnabled = false,
36
+ isWeeklyDigestEnabled = false,
36
37
  sampleCoi = {}
37
38
  } = {}
38
39
  ) {
@@ -64,6 +65,7 @@ class UpdateAccountSettingsModel {
64
65
  this.isConfigurableRenewalCadenceEnabled = isConfigurableRenewalCadenceEnabled;
65
66
  this.isAcord25SplitExtractionEnabled = isAcord25SplitExtractionEnabled;
66
67
  this.isCertificialEnabled = isCertificialEnabled;
68
+ this.isWeeklyDigestEnabled = isWeeklyDigestEnabled;
67
69
  this.gapsChat = { ... DEFAULT_GAPS_CHAT, ... gapsChat };
68
70
  this.supportAutomation = { ... DEFAULT_SUPPORT_AUTOMATION, ... supportAutomation };
69
71
  this.sampleCoi = { ... DEFAULT_SAMPLE_COI, ... sampleCoi };
@@ -55,7 +55,15 @@ const EMAIL_SUBJECT = {
55
55
  overrideGapRequestRejected: ({ accountName }) => `${accountName} denied your exception request`,
56
56
  overrideGapRequestApproved: ({ accountName }) => `${accountName} approved your exception request`,
57
57
  timedOverrideExpired: ({ recordCompanyName, requesterName }) => `Override ended - ${recordCompanyName} in ${requesterName}`,
58
- allRecordsExport: 'Jones - All Records Export'
58
+ allRecordsExport: 'Jones - All Records Export',
59
+ weeklyDigest: ({ accountName }) => `Your Weekly updates for ${accountName}`
60
+ };
61
+
62
+ const EMAIL_LINK_REGEX = {
63
+ mailActionButton: /(https:\/\/[a-zA-Z0-9.].*[a-zA-Z.]+\/CheckCustomersInviteLinkJSON\?data=[^"]+)/g,
64
+ sampleCoiDownload: /\/sample-coi\/requirement\/([^/]+)\/download\?source=email/,
65
+ allRecordsExportDownload: /href="(https?:\/\/[^"]+)"/,
66
+ weeklyDigestViewAll: issue => new RegExp(`(https:\\/\\/[^"]+\\/all-records\\?digestIssue=${issue}[^"]*)`)
59
67
  };
60
68
 
61
69
  const EMAIL_POLLING = {
@@ -63,4 +71,4 @@ const EMAIL_POLLING = {
63
71
  expectNoMail: { maxRetries: 3, pollIntervalSeconds: 1 }
64
72
  };
65
73
 
66
- module.exports = { DEFAULT_EMAIL_SENDER, EMAIL_TYPES, EMAIL_SUBJECT, EMAIL_POLLING, tenantUserExtension };
74
+ module.exports = { DEFAULT_EMAIL_SENDER, EMAIL_TYPES, EMAIL_SUBJECT, EMAIL_LINK_REGEX, EMAIL_POLLING, tenantUserExtension };
@@ -62,10 +62,6 @@ const getEmailTextInSubject = (recordCompanyName, emailType, isAfterUpdateRequir
62
62
  return isAfterUpdateRequirements ? `Updated Requirements - ${subject}` : subject;
63
63
  };
64
64
 
65
- const getMailActionButtonUrlRegex = () => {
66
- return /(https:\/\/[a-zA-Z0-9.].*[a-zA-Z.]+\/CheckCustomersInviteLinkJSON\?data=[^"]+)/g;
67
- };
68
-
69
65
  const getEncryptedDataFromLink = (link, { removeLastTwoCharts } = {}) => {
70
66
  const encryptedData = link.split('data=').pop();
71
67
  return removeLastTwoCharts ? encryptedData.slice(0, -2) : encryptedData;
@@ -77,6 +73,5 @@ module.exports = {
77
73
  extractEmailFromNameAndEmailFormat,
78
74
  logRetrievedEmailInfo,
79
75
  getEmailTextInSubject,
80
- getMailActionButtonUrlRegex,
81
76
  getEncryptedDataFromLink
82
77
  };
@@ -66,6 +66,9 @@ module.exports = {
66
66
  requireScope(entityIds, schedulerJobs.CERTIFICIAL_MONITORING);
67
67
  return runSchedulerJob({ jobType: schedulerJobs.CERTIFICIAL_MONITORING, entityIds });
68
68
  },
69
+ runJobForWeeklyDigest: function(entityIds) {
70
+ return runSchedulerJob({ jobType: schedulerJobs.WEEKLY_DIGEST, entityIds });
71
+ },
69
72
  runAllJobsNew: function(entityIds) {
70
73
  return runSchedulerJob({ jobType: schedulerJobs.ALL, entityIds });
71
74
  }
@@ -6,5 +6,6 @@ module.exports = {
6
6
  EXPIRE_TIMED_OVERRIDES: 'EXPIRE_TIMED_OVERRIDES',
7
7
  CERTIFICIAL_ENROLLMENT: 'CERTIFICIAL_ENROLLMENT',
8
8
  CERTIFICIAL_MONITORING: 'CERTIFICIAL_MONITORING',
9
+ WEEKLY_DIGEST: 'WEEKLY_DIGEST',
9
10
  ALL: 'ALL'
10
11
  };
@@ -0,0 +1,32 @@
1
+ const requests = require('../../../../common/requests/cookieAuth/requests');
2
+ const { backendUrl } = require('../../../../env').getEnv();
3
+
4
+ const Endpoints = {
5
+ snapshot: `${backendUrl}/saas/integration-tests/weekly-digest/snapshot`,
6
+ accountSnapshot: accountId => `${backendUrl}/saas/integration-tests/weekly-digest/account/${accountId}/snapshot`,
7
+ run: accountId => `${backendUrl}/saas/integration-tests/weekly-digest/account/${accountId}/run`,
8
+ reportLog: `${backendUrl}/saas/integration-tests/weekly-digest/report-log`
9
+ };
10
+
11
+ const takeAccountSnapshot = (accountId, context) => {
12
+ return requests.postRequestHandler(Endpoints.accountSnapshot(accountId), null, context);
13
+ };
14
+
15
+ const takeAccountsSnapshot = (accountIds, context) => {
16
+ return requests.postRequestHandler(Endpoints.snapshot, { accountIds }, context);
17
+ };
18
+
19
+ const runWeeklyDigest = (accountId, body, context) => {
20
+ return requests.postRequestHandler(Endpoints.run(accountId), body, context);
21
+ };
22
+
23
+ const getWeeklyDigestReports = (accountId, weekStart, context) => {
24
+ return requests.getRequestHandler(Endpoints.reportLog, { accountId, weekStart }, context);
25
+ };
26
+
27
+ module.exports = {
28
+ takeAccountSnapshot,
29
+ takeAccountsSnapshot,
30
+ runWeeklyDigest,
31
+ getWeeklyDigestReports
32
+ };
@@ -0,0 +1,69 @@
1
+ const httpResponseStatusCodes = require('../../../../common/httpResponseStatusCodes.json');
2
+ const timeUtils = require('../../../../common/utils/timeUtils');
3
+
4
+ const authService = require('../../auth/api/auth.service');
5
+ const weeklyDigestApi = require('./weekly.digest.api');
6
+ const { REPORT_STATUS } = require('../consts/weekly.digest.consts');
7
+
8
+ const takeAccountSnapshot = async accountId => {
9
+ const response = await weeklyDigestApi.takeAccountSnapshot(accountId, await authService.getIcsCookie());
10
+
11
+ if (response.status !== httpResponseStatusCodes.OK) {
12
+ throw new Error(`Account snapshot failed for account ${accountId}. Status code: ${response.status}`);
13
+ }
14
+
15
+ return response.data.snapshotId;
16
+ };
17
+
18
+ const takeAccountsSnapshot = async accountIds => {
19
+ const response = await weeklyDigestApi.takeAccountsSnapshot(accountIds, await authService.getIcsCookie());
20
+
21
+ if (response.status !== httpResponseStatusCodes.OK) {
22
+ throw new Error(`Accounts snapshot failed for accounts ${accountIds}. Status code: ${response.status}`);
23
+ }
24
+
25
+ return response.data.snapshotId;
26
+ };
27
+
28
+ // Runs synchronously for next Monday's week, after clearing the account's report-log rows for that week.
29
+ const runWeeklyDigest = async (accountId, { previousRunId, currentRunId }) => {
30
+ const body = { beforeSnapshotId: previousRunId, afterSnapshotId: currentRunId };
31
+ const response = await weeklyDigestApi.runWeeklyDigest(accountId, body, await authService.getIcsCookie());
32
+
33
+ if (response.status !== httpResponseStatusCodes.OK) {
34
+ throw new Error(`Weekly digest run failed for account ${accountId}. Status code: ${response.status}`);
35
+ }
36
+
37
+ return response.data;
38
+ };
39
+
40
+ const getWeeklyDigestReports = async (accountId, weekStart) => {
41
+ const response = await weeklyDigestApi.getWeeklyDigestReports(accountId, weekStart, await authService.getIcsCookie());
42
+
43
+ if (response.status !== httpResponseStatusCodes.OK) {
44
+ throw new Error(`Weekly digest reports failed for account ${accountId}. Status code: ${response.status}`);
45
+ }
46
+
47
+ return response.data;
48
+ };
49
+
50
+ // The scheduler endpoint returns before the job runs, so a real-job run has to poll the report log.
51
+ const waitForWeeklyDigestReport = async (accountId, weekStart, userId, { expectedStatus = REPORT_STATUS.SENT, retries = 10 } = {}) => {
52
+ let report;
53
+
54
+ while (report?.reportData.status !== expectedStatus && retries-- > 0) {
55
+ await timeUtils.waitFor(3).seconds;
56
+ const reports = await getWeeklyDigestReports(accountId, weekStart);
57
+ report = reports.find(row => row.userId === userId);
58
+ }
59
+
60
+ return report;
61
+ };
62
+
63
+ module.exports = {
64
+ takeAccountSnapshot,
65
+ takeAccountsSnapshot,
66
+ runWeeklyDigest,
67
+ getWeeklyDigestReports,
68
+ waitForWeeklyDigestReport
69
+ };
@@ -0,0 +1,21 @@
1
+ const REPORT_STATUS = {
2
+ IN_PROGRESS: 'IN_PROGRESS',
3
+ SENT: 'SENT',
4
+ NO_VISIBLE_REQUESTS: 'NO_VISIBLE_REQUESTS'
5
+ };
6
+
7
+ const NEW_ISSUE_TYPE = {
8
+ EXPIRED_LAST_WEEK: 'EXPIRED_LAST_WEEK',
9
+ BECAME_NOT_COMPLIANT: 'BECAME_NOT_COMPLIANT',
10
+ EXPIRING_THIS_WEEK: 'EXPIRING_THIS_WEEK',
11
+ BECAME_NOT_RESPONSIVE: 'BECAME_NOT_RESPONSIVE'
12
+ };
13
+
14
+ const ACTIVITY_TYPE = {
15
+ TIMED_OVERRIDE_ENDING: 'TIMED_OVERRIDE_ENDING',
16
+ EXCEPTION_REQUEST: 'EXCEPTION_REQUEST',
17
+ MENTION: 'MENTION',
18
+ RELATED_DOC: 'RELATED_DOC'
19
+ };
20
+
21
+ module.exports = { REPORT_STATUS, NEW_ISSUE_TYPE, ACTIVITY_TYPE };
@@ -0,0 +1,4 @@
1
+ const services = require('./api/weekly.digest.service');
2
+ const consts = require('./consts/weekly.digest.consts');
3
+
4
+ module.exports = { services, consts };