@meltwater/conversations-api-services 1.0.19 → 1.0.21

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 (70) hide show
  1. package/.github/workflows/release.yml +2 -0
  2. package/babel.config.js +18 -0
  3. package/dist/cjs/data-access/http/InstagramVideoClient.js +42 -0
  4. package/dist/cjs/data-access/http/WarpZoneApi.client.js +32 -0
  5. package/dist/cjs/data-access/http/amazonS3.js +44 -0
  6. package/dist/cjs/data-access/http/asset-manager-tvm.client.js +35 -0
  7. package/dist/cjs/data-access/http/companiesApi.client.js +38 -0
  8. package/dist/cjs/data-access/http/credentialsApi.client.js +102 -0
  9. package/dist/cjs/data-access/http/entitlementsApi.client.js +40 -0
  10. package/dist/cjs/data-access/http/facebook.native.js +344 -0
  11. package/dist/cjs/data-access/http/facebookApi.client.js +631 -0
  12. package/dist/cjs/data-access/http/featureToggleApi.client.js +31 -0
  13. package/dist/cjs/data-access/http/identityServices.client.js +97 -0
  14. package/dist/cjs/data-access/http/instagramApi.client.js +428 -0
  15. package/dist/cjs/data-access/http/ir.client.js +242 -0
  16. package/dist/cjs/data-access/http/linkedInApi.client.js +491 -0
  17. package/dist/cjs/data-access/http/masf.client.js +101 -0
  18. package/dist/cjs/data-access/http/tiktok.native.js +162 -0
  19. package/dist/cjs/data-access/http/tiktokApi.client.js +441 -0
  20. package/dist/cjs/data-access/index.js +132 -0
  21. package/dist/cjs/errors/engage-error.js +16 -0
  22. package/dist/cjs/errors/http-error.js +23 -0
  23. package/dist/cjs/lib/applicationTags.helpers.js +30 -0
  24. package/dist/cjs/lib/configuration.js +14 -0
  25. package/dist/cjs/lib/document-action-events.js +12 -0
  26. package/dist/cjs/lib/externalId.helpers.js +19 -0
  27. package/dist/cjs/lib/hidden.helpers.js +13 -0
  28. package/dist/cjs/lib/hiddenComment.helper.js +119 -0
  29. package/dist/cjs/lib/logger.helpers.js +68 -0
  30. package/dist/cjs/lib/logger.js +23 -0
  31. package/dist/cjs/lib/message.helpers.js +58 -0
  32. package/dist/cjs/lib/metrics.helper.js +97 -0
  33. package/dist/esm/data-access/http/InstagramVideoClient.js +34 -0
  34. package/dist/esm/data-access/http/WarpZoneApi.client.js +24 -0
  35. package/dist/esm/data-access/http/amazonS3.js +37 -0
  36. package/dist/esm/data-access/http/asset-manager-tvm.client.js +28 -0
  37. package/dist/esm/data-access/http/companiesApi.client.js +30 -0
  38. package/dist/esm/data-access/http/credentialsApi.client.js +92 -0
  39. package/dist/esm/data-access/http/entitlementsApi.client.js +32 -0
  40. package/dist/esm/data-access/http/facebook.native.js +325 -0
  41. package/dist/esm/data-access/http/facebookApi.client.js +621 -0
  42. package/dist/esm/data-access/http/featureToggleApi.client.js +23 -0
  43. package/dist/esm/data-access/http/identityServices.client.js +89 -0
  44. package/dist/esm/data-access/http/instagramApi.client.js +420 -0
  45. package/dist/esm/data-access/http/ir.client.js +234 -0
  46. package/dist/esm/data-access/http/linkedInApi.client.js +481 -0
  47. package/dist/esm/data-access/http/masf.client.js +93 -0
  48. package/dist/esm/data-access/http/tiktok.native.js +146 -0
  49. package/dist/esm/data-access/http/tiktokApi.client.js +433 -0
  50. package/dist/esm/data-access/index.js +30 -0
  51. package/dist/esm/errors/engage-error.js +9 -0
  52. package/dist/esm/errors/http-error.js +16 -0
  53. package/dist/esm/lib/applicationTags.helpers.js +22 -0
  54. package/dist/esm/lib/configuration.js +8 -0
  55. package/dist/esm/lib/document-action-events.js +6 -0
  56. package/dist/esm/lib/externalId.helpers.js +12 -0
  57. package/dist/esm/lib/hidden.helpers.js +6 -0
  58. package/dist/esm/lib/hiddenComment.helper.js +112 -0
  59. package/dist/esm/lib/logger.helpers.js +60 -0
  60. package/dist/esm/lib/logger.js +16 -0
  61. package/dist/esm/lib/message.helpers.js +52 -0
  62. package/dist/esm/lib/metrics.helper.js +90 -0
  63. package/package.json +14 -4
  64. package/src/data-access/http/facebook.native.js +542 -0
  65. package/src/data-access/http/tiktok.native.js +248 -0
  66. package/src/data-access/index.js +4 -0
  67. package/src/errors/engage-error.js +11 -0
  68. package/src/errors/http-error.js +19 -0
  69. package/src/lib/logger.helpers.js +15 -0
  70. package/src/lib/message.helpers.js +7 -1
@@ -0,0 +1,89 @@
1
+ import superagent from 'superagent';
2
+ import logger from '../../lib/logger.js';
3
+ import configuration from '../../lib/configuration.js';
4
+ import { MeltwaterAttributes } from '../../lib/logger.helpers.js';
5
+ export class IdentityServicesClient {
6
+ constructor(_ref) {
7
+ let {
8
+ companyId,
9
+ services
10
+ } = _ref;
11
+ this.companyId = companyId;
12
+ this.identityServicesUrl = configuration.get('IDENTITY_SERVICES_URL');
13
+ this.authService = services.auth;
14
+ }
15
+ async getById(userId, jwt) {
16
+ let retries = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : 0;
17
+ let user;
18
+ try {
19
+ let resignedToken = await this.authService.getResignedToken(jwt);
20
+ const loggerChild = logger.child({
21
+ [MeltwaterAttributes.USERID]: userId,
22
+ [MeltwaterAttributes.COMPANYID]: this.companyId
23
+ });
24
+ user = await superagent.get(`${this.identityServicesUrl}/users/${userId}`).set('Authorization', resignedToken).set('x-client-name', configuration.get('CLIENT_NAME_HEADER')).then(result => result.body.user);
25
+ } catch (error) {
26
+ if (retries <= 3) {
27
+ loggerChild.error(`getById Failed requesting Identity Services for userId ${userId} retry ${retries}`, error);
28
+ return this.getById(userId, jwt, ++retries);
29
+ } else {
30
+ loggerChild.error(`getById Failed requesting Identity Services app settings for userId ${userId} complete failure`, error);
31
+ }
32
+ return;
33
+ }
34
+ return user;
35
+ }
36
+ async getAllUsers(jwt) {
37
+ let retries = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : 0;
38
+ let users;
39
+ const loggerChild = logger.child({
40
+ [MeltwaterAttributes.COMPANYID]: this.companyId
41
+ });
42
+ try {
43
+ let resignedToken = await this.authService.getResignedToken(jwt);
44
+ users = await superagent.get(`${this.identityServicesUrl}/companies/${this.companyId}/users`).set('Authorization', resignedToken).set('x-client-name', configuration.get('CLIENT_NAME_HEADER')).then(result => result.body.map(record => record.user));
45
+ } catch (error) {
46
+ if (retries <= 3) {
47
+ loggerChild.error(`getAllUsers Failed requesting Identity Services for ${this.companyId} retrying ${retries}`, error);
48
+ return await this.getAllUsers(jwt, ++retries);
49
+ } else {
50
+ loggerChild.error(`getAllUsers Failed requesting Identity Services app settings for companyId ${this.companyId} complete failure`, error);
51
+ }
52
+ return;
53
+ }
54
+ return users;
55
+ }
56
+ async getUsersAppSettings(_ref2) {
57
+ let {
58
+ userIds,
59
+ settingNames,
60
+ jwt
61
+ } = _ref2;
62
+ let retries = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : 0;
63
+ if (!settingNames) {
64
+ return {};
65
+ } else {
66
+ let appSettings;
67
+ try {
68
+ let resignedToken = await this.authService.getResignedToken(jwt);
69
+ appSettings = await superagent.post(`${this.identityServicesUrl}/users/app_settings/batch_get`).set('Authorization', resignedToken).set('x-client-name', configuration.get('CLIENT_NAME_HEADER')).send({
70
+ userIds,
71
+ settingNames: settingNames
72
+ }).then(result => result.body);
73
+ } catch (error) {
74
+ if (retries <= 3) {
75
+ logger.error(`getUsersAppSettings Failed requesting Identity Services app settings for userIds ${userIds} retrying ${retries}`, error);
76
+ return await this.getUsersAppSettings({
77
+ userIds,
78
+ settingNames,
79
+ jwt
80
+ }, ++retries);
81
+ } else {
82
+ logger.error(`getUsersAppSettings Failed requesting Identity Services app settings for userIds ${userIds} complete failure`, error);
83
+ }
84
+ return;
85
+ }
86
+ return appSettings;
87
+ }
88
+ }
89
+ }
@@ -0,0 +1,420 @@
1
+ import superagent from 'superagent';
2
+ import logger from '../../lib/logger.js';
3
+ import { removePrefix } from '../../lib/externalId.helpers.js';
4
+ import assert from 'assert';
5
+ import { CredentialsApiClient } from '../http/credentialsApi.client.js';
6
+ import { MeltwaterAttributes } from '../../lib/logger.helpers.js';
7
+ const INSTAGRAM_URL = 'https://graph.facebook.com';
8
+ export class InstagramApiClient {
9
+ constructor() {
10
+ this.credentialsAPI = new CredentialsApiClient();
11
+ }
12
+ async validate(accessToken, payload) {
13
+ const {
14
+ inReplyToId,
15
+ text
16
+ } = payload;
17
+ assert(accessToken, 'AccessToken is required.');
18
+ assert(inReplyToId, 'inReplyToId is required.');
19
+ assert(text, 'text is required.');
20
+ }
21
+ async requestApi(apiUrl, accessToken, text, documentId, data) {
22
+ let discussionType = arguments.length > 5 && arguments[5] !== undefined ? arguments[5] : 're';
23
+ let adCampaign = arguments.length > 6 && arguments[6] !== undefined ? arguments[6] : undefined;
24
+ let response = {};
25
+ const loggerChild = logger.child({
26
+ [MeltwaterAttributes.DOCUMENTID]: documentId
27
+ });
28
+ try {
29
+ let queryStringArgs = {
30
+ access_token: accessToken
31
+ };
32
+ if (adCampaign) {
33
+ queryStringArgs.ad_id = adCampaign.adAccountId;
34
+ }
35
+ if (text) {
36
+ queryStringArgs[discussionType === 'dm' ? 'text' : 'message'] = text;
37
+ }
38
+ response = await superagent.post(apiUrl).set('Accept', 'application/json').set('Content-Type', 'application/json').query(queryStringArgs).send(data);
39
+ } catch (err) {
40
+ let errorText = '';
41
+ if (err && err.response && err.response.body && err.response.body.error) {
42
+ errorText = `Failed to call instagram api for documentId ${documentId}: ${err.response.body.error.message}`;
43
+ loggerChild.error(errorText);
44
+ } else {
45
+ errorText = `Failed to call instagram api for documentId ${documentId}`;
46
+ loggerChild.error(errorText, err);
47
+ }
48
+ throw new Error(errorText);
49
+ }
50
+ if (response.status !== 200) {
51
+ loggerChild.error(`Failed to call instagram api for documentId ${documentId}`, {
52
+ response: JSON.stringify(response.body)
53
+ });
54
+ let error = new Error(`Failed to call instagram api for documentId ${documentId}`);
55
+ error.code = response.status;
56
+ throw error;
57
+ }
58
+ loggerChild.debug('Instagram Response status', response.status);
59
+ loggerChild.debug('Instagram Response body', JSON.stringify(response.body));
60
+ loggerChild.debug('Instagram Response body.id', response.body.id);
61
+ return response;
62
+ }
63
+ async getLikes(accessToken, payload) {
64
+ let response;
65
+ const {
66
+ externalId,
67
+ documentId
68
+ } = payload;
69
+ const loggerChild = logger.child({
70
+ [MeltwaterAttributes.DOCUMENTID]: documentId
71
+ });
72
+ loggerChild.debug(`Starting to call instagram getPost api for documentId ${documentId}`, {
73
+ payload: JSON.stringify(payload)
74
+ });
75
+ try {
76
+ response = await this.getPost(`${INSTAGRAM_URL}/${removePrefix(externalId)}`, accessToken, 'like_count', documentId);
77
+ loggerChild.info(`Native Instagram API getPost Response for documentId ${documentId}`, {
78
+ status: response.status,
79
+ ok: response.ok
80
+ });
81
+ return response.body;
82
+ } catch (err) {
83
+ loggerChild.error('Error getLikes Instagram', {
84
+ payload: JSON.stringify(payload)
85
+ });
86
+ return 0;
87
+ }
88
+ }
89
+ async mentionRequestApi(apiUrl, accessToken, replayObject, text, documentId) {
90
+ let response = {};
91
+ const loggerChild = logger.child({
92
+ [MeltwaterAttributes.DOCUMENTID]: documentId
93
+ });
94
+ try {
95
+ response = await superagent.post(apiUrl).set('Accept', 'application/json').set('Content-Type', 'application/json').query({
96
+ access_token: accessToken
97
+ }).query(replayObject).query({
98
+ message: text
99
+ }).send();
100
+ } catch (err) {
101
+ let errorText = '';
102
+ if (err && err.response && err.response.body && err.response.body.error) {
103
+ errorText = `Failed to call instagram api for documentId ${documentId}: ${err.response.body.error.message}`;
104
+ loggerChild.error(errorText);
105
+ } else {
106
+ errorText = `Failed to call instagram api for documentId ${documentId}`;
107
+ loggerChild.error(errorText, err);
108
+ }
109
+ throw new Error(errorText);
110
+ }
111
+ if (response.status !== 200) {
112
+ loggerChild.error(`Failed to call instagram api for documentId ${documentId}`, {
113
+ response: JSON.stringify(response.body)
114
+ });
115
+ let error = new Error(`Failed to call instagram api for documentId ${documentId}`);
116
+ error.code = response.status;
117
+ throw error;
118
+ }
119
+ loggerChild.debug('Instagram Response status', response.status);
120
+ loggerChild.debug('Instagram Response body', {
121
+ response: JSON.stringify(response.body)
122
+ });
123
+ loggerChild.debug('Instagram Response body.id', response.body.id);
124
+ return response;
125
+ }
126
+ async hideApi(apiUrl, accessToken, hideStatus, documentId) {
127
+ let response = {};
128
+ const loggerChild = logger.child({
129
+ [MeltwaterAttributes.DOCUMENTID]: documentId
130
+ });
131
+ try {
132
+ response = await superagent.post(apiUrl).set('Accept', 'application/json').set('Content-Type', 'application/json').query({
133
+ access_token: accessToken
134
+ }).query({
135
+ hide: hideStatus
136
+ }).send();
137
+ } catch (err) {
138
+ let errorText = '';
139
+ if (err && err.response && err.response.body) {
140
+ errorText = `Failed to call instagram api for documentId ${documentId}: ${err.response.body.error.message}`;
141
+ loggerChild.error(errorText, err.response.body.error);
142
+ } else {
143
+ errorText = `Failed to call instagram api for documentId ${documentId}`;
144
+ loggerChild.error(errorText, err);
145
+ }
146
+ throw new Error(errorText);
147
+ }
148
+ if (response.status !== 200) {
149
+ loggerChild.error(`Failed to call instagram api for documentId ${documentId}`, {
150
+ response: JSON.stringify(response.body)
151
+ });
152
+ let error = new Error(`Failed to call instagram api for documentId ${documentId}`);
153
+ error.code = response.status;
154
+ throw error;
155
+ }
156
+ loggerChild.debug('Instagram Response status', response.status);
157
+ loggerChild.debug('Instagram Response body', {
158
+ response: JSON.stringify(response.body)
159
+ });
160
+ loggerChild.debug('Instagram Response body.id', response.body.id);
161
+ return response;
162
+ }
163
+ async getPost(apiUrl, accessToken, fields, documentId) {
164
+ let response = {};
165
+ const loggerChild = logger.child({
166
+ [MeltwaterAttributes.DOCUMENTID]: documentId
167
+ });
168
+ try {
169
+ response = await superagent.get(apiUrl).set('Accept', 'application/json').set('Content-Type', 'application/json').query({
170
+ access_token: accessToken
171
+ }).query({
172
+ fields: fields
173
+ }).send();
174
+ } catch (err) {
175
+ let errorText = '';
176
+ if (err && err.response && err.response.body) {
177
+ errorText = `Failed to call instagram api for documentId ${documentId}: ${err.response.body.error.message}`;
178
+ loggerChild.error(errorText, err.response.body.error);
179
+ } else {
180
+ errorText = `Failed to call instagram api for documentId ${documentId}`;
181
+ loggerChild.error(errorText, err);
182
+ }
183
+ throw new Error(errorText);
184
+ }
185
+ if (response.status !== 200) {
186
+ loggerChild.error(`Failed to call instagram api for documentId ${documentId}`, {
187
+ response: JSON.stringify(response.body)
188
+ });
189
+ let error = new Error(`Failed to call instagram api for documentId ${documentId}`);
190
+ error.code = response.status;
191
+ throw error;
192
+ }
193
+ loggerChild.debug('Instagram Response status', response.status);
194
+ loggerChild.debug('Instagram Response body', {
195
+ response: JSON.stringify(response.body)
196
+ });
197
+ loggerChild.debug('Instagram Response body.id', response.body.id);
198
+ return response;
199
+ }
200
+ async comment(accessToken, payload) {
201
+ let response;
202
+ const {
203
+ inReplyToId,
204
+ text,
205
+ documentId,
206
+ isMention,
207
+ sourceId
208
+ } = payload;
209
+ const loggerChild = logger.child({
210
+ [MeltwaterAttributes.DOCUMENTID]: documentId
211
+ });
212
+ loggerChild.debug(`Starting to call instagram comment api for documentId ${documentId}`, {
213
+ payload: JSON.stringify(payload)
214
+ });
215
+ this.validate(accessToken, payload);
216
+ if (isMention) {
217
+ response = await this.mentionRequestApi(`${INSTAGRAM_URL}/${sourceId}/mentions`, accessToken, {
218
+ media_id: removePrefix(inReplyToId)
219
+ }, text, documentId);
220
+ } else {
221
+ response = await this.requestApi(`${INSTAGRAM_URL}/${removePrefix(inReplyToId)}/comments`, accessToken, text, documentId, undefined, 'qt');
222
+ }
223
+ loggerChild.info(`Native Intagram API Publish Comment Response for documentId ${documentId}`, {
224
+ status: response.status,
225
+ ok: response.ok
226
+ });
227
+ return response.body;
228
+ }
229
+ async reply(accessToken, payload) {
230
+ let response;
231
+ const {
232
+ inReplyToId,
233
+ text,
234
+ documentId,
235
+ isMention,
236
+ sourceId,
237
+ threadId,
238
+ adCampaign
239
+ } = payload;
240
+ const loggerChild = logger.child({
241
+ [MeltwaterAttributes.DOCUMENTID]: documentId
242
+ });
243
+ loggerChild.debug(`Starting to call instagram comment api for documentId ${documentId}`, {
244
+ payload: JSON.stringify(payload)
245
+ });
246
+ this.validate(accessToken, payload);
247
+ if (isMention) {
248
+ response = await this.mentionRequestApi(`${INSTAGRAM_URL}/${sourceId}/mentions`, accessToken, {
249
+ media_id: removePrefix(threadId),
250
+ comment_id: removePrefix(inReplyToId)
251
+ }, text, documentId);
252
+ } else {
253
+ response = await this.requestApi(`${INSTAGRAM_URL}/${removePrefix(inReplyToId)}/replies`, accessToken, text, documentId, undefined, 're', adCampaign);
254
+ }
255
+ loggerChild.info(`Native Instagram API Publish Reply Response for documentId ${documentId}`, {
256
+ status: response.status,
257
+ ok: response.ok
258
+ });
259
+ return response.body;
260
+ }
261
+ async publish(document) {
262
+ const {
263
+ documentId,
264
+ body: {
265
+ content: {
266
+ text
267
+ }
268
+ },
269
+ appData: {
270
+ isMention
271
+ },
272
+ metaData: {
273
+ discussionType,
274
+ source: {
275
+ id: sourceId
276
+ },
277
+ inReplyTo: {
278
+ id: inReplyToId,
279
+ profileId,
280
+ threadId
281
+ },
282
+ adCampaign
283
+ },
284
+ systemData: {
285
+ connectionsCredential: credentialId,
286
+ policies: {
287
+ storage: {
288
+ privateTo: companyId
289
+ } = {}
290
+ } = {}
291
+ } = {}
292
+ } = document;
293
+ let payload = {
294
+ documentId,
295
+ credentialId,
296
+ text,
297
+ companyId,
298
+ inReplyToId,
299
+ profileId,
300
+ isMention,
301
+ sourceId,
302
+ threadId,
303
+ adCampaign
304
+ };
305
+ const loggerChild = logger.child({
306
+ [MeltwaterAttributes.DOCUMENTID]: documentId,
307
+ [MeltwaterAttributes.COMPANYID]: companyId,
308
+ [MeltwaterAttributes.CREDENTIALID]: credentialId
309
+ });
310
+ let updatedDocument;
311
+ let apiResponse;
312
+ try {
313
+ const token = await this.credentialsAPI.getToken(payload.credentialId, payload.companyId);
314
+ loggerChild.debug(`finished fetching token for instagram for ${documentId} on company ${companyId} `, {
315
+ payload: JSON.stringify(payload)
316
+ });
317
+ switch (discussionType) {
318
+ case 'qt':
319
+ apiResponse = await this.comment(token.token, payload);
320
+ break;
321
+ case 're':
322
+ apiResponse = await this.reply(token.token, payload);
323
+ break;
324
+ case 'dm':
325
+ // get parent account
326
+ const parentCredentialId = await this.credentialsAPI.getCredentialIdByAccountId(token.parentAccountId, 'facebook');
327
+ if (!parentCredentialId) {
328
+ throw 'Parent account id not found';
329
+ }
330
+
331
+ // get parent
332
+ const parentCredential = await this.credentialsAPI.getToken(parentCredentialId, payload.companyId);
333
+ if (!parentCredential) {
334
+ throw 'Parent account not found';
335
+ }
336
+ apiResponse = await this.privateMessage(parentCredential.token, payload);
337
+ break;
338
+ default:
339
+ throw new Error('Unsupported discussion type');
340
+ }
341
+ } catch (err) {
342
+ loggerChild.error(`${documentId} - exception details`, err);
343
+ }
344
+ return apiResponse;
345
+ }
346
+ async hide(accessToken, payload) {
347
+ let response;
348
+ const {
349
+ externalId,
350
+ documentId
351
+ } = payload;
352
+ const loggerChild = logger.child({
353
+ [MeltwaterAttributes.DOCUMENTID]: documentId
354
+ });
355
+ loggerChild.debug(`Starting to call instagram hide api for documentId ${documentId}`, {
356
+ payload: JSON.stringify(payload)
357
+ });
358
+ response = await this.hideApi(`${INSTAGRAM_URL}/${removePrefix(externalId)}`, accessToken, true, documentId);
359
+ loggerChild.info(`Native Instagram API Hide Response for documentId ${documentId}`, {
360
+ status: response.status,
361
+ ok: response.ok
362
+ });
363
+ return response.body;
364
+ }
365
+ async unhide(accessToken, payload) {
366
+ let response;
367
+ const {
368
+ externalId,
369
+ documentId
370
+ } = payload;
371
+ const loggerChild = logger.child({
372
+ [MeltwaterAttributes.DOCUMENTID]: documentId
373
+ });
374
+ loggerChild.debug(`Starting to call instagram unhide api for documentId ${documentId}`, {
375
+ payload: JSON.stringify(payload)
376
+ });
377
+ response = await this.hideApi(`${INSTAGRAM_URL}/${removePrefix(externalId)}`, accessToken, false, documentId);
378
+ loggerChild.info(`Native Instagram API Unhide Response for documentId ${documentId}`, {
379
+ status: response.status,
380
+ ok: response.ok
381
+ });
382
+ return response.body;
383
+ }
384
+ async privateMessage(accessToken, payload) {
385
+ let response;
386
+ const {
387
+ profileId,
388
+ text,
389
+ documentId,
390
+ isMention,
391
+ sourceId,
392
+ threadId
393
+ } = payload;
394
+ const loggerChild = logger.child({
395
+ [MeltwaterAttributes.DOCUMENTID]: documentId
396
+ });
397
+ loggerChild.debug(`Starting to call instagram private message api for documentId ${documentId}`, {
398
+ payload: JSON.stringify(payload)
399
+ });
400
+ this.validate(accessToken, payload);
401
+ response = await this.requestApi(`${INSTAGRAM_URL}/v10.0/me/messages`, accessToken,
402
+ // this sends in query string leaving out :shrug:
403
+ undefined, documentId, {
404
+ recipient: {
405
+ // not :100: this is right
406
+ id: removePrefix(profileId)
407
+ },
408
+ message: {
409
+ text
410
+ },
411
+ // this apparently allows up to 7 days after message 🤔
412
+ tag: 'HUMAN_AGENT'
413
+ }, 'dm');
414
+ loggerChild.info(`Native Instagram API Publish Private Message Response for documentId ${documentId}`, {
415
+ status: response.status,
416
+ ok: response.ok
417
+ });
418
+ return response.body;
419
+ }
420
+ }