@tiledesk/tiledesk-whatsapp-connector 0.1.40 → 0.1.42
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/index.js +130 -201
- package/logs/app.log +4 -0
- package/package.json +3 -2
- package/template/configure.html +2 -1
- package/template/css/configure.css +2 -1
- package/test/test_translate_whatsapp.js +1 -1
- package/tiledesk/KVBaseMongo.js +13 -18
- package/tiledesk/MessageHandler.js +3 -4
- package/tiledesk/TiledeskAppsClient.js +5 -9
- package/tiledesk/TiledeskBotTester.js +6 -5
- package/tiledesk/TiledeskChannel.js +16 -23
- package/tiledesk/TiledeskSubscriptionClient.js +3 -5
- package/tiledesk/TiledeskWhatsapp.js +14 -18
- package/tiledesk/TiledeskWhatsappTranslator.js +4 -8
- package/winston.js +41 -0
package/index.js
CHANGED
|
@@ -9,6 +9,7 @@ const path = require('path');
|
|
|
9
9
|
const pjson = require('./package.json');
|
|
10
10
|
const { v4: uuidv4 } = require('uuid');
|
|
11
11
|
const cors = require('cors');
|
|
12
|
+
var winston = require('./winston');
|
|
12
13
|
|
|
13
14
|
// tiledesk clients
|
|
14
15
|
//const { TiledeskClient } = require('@tiledesk/tiledesk-client');
|
|
@@ -23,7 +24,7 @@ const { TiledeskBotTester } = require('./tiledesk/TiledeskBotTester');
|
|
|
23
24
|
// mongo
|
|
24
25
|
const { KVBaseMongo } = require('./tiledesk/KVBaseMongo');
|
|
25
26
|
const kvbase_collection = 'kvstore';
|
|
26
|
-
const db = new KVBaseMongo(
|
|
27
|
+
const db = new KVBaseMongo(kvbase_collection);
|
|
27
28
|
|
|
28
29
|
// mongo old
|
|
29
30
|
//const { KVBaseMongo } = require('@tiledesk/tiledesk-kvbasemongo')
|
|
@@ -46,7 +47,6 @@ let APPS_API_URL = null;
|
|
|
46
47
|
let REDIS_HOST = null;
|
|
47
48
|
let REDIS_PORT = null;
|
|
48
49
|
let REDIS_PASSWORD = null;
|
|
49
|
-
let log = false;
|
|
50
50
|
|
|
51
51
|
// Handlebars register helpers
|
|
52
52
|
handlebars.registerHelper('isEqual', (a, b) => {
|
|
@@ -63,6 +63,8 @@ router.get('/', async (req, res) => {
|
|
|
63
63
|
|
|
64
64
|
router.get('/detail', async (req, res) => {
|
|
65
65
|
|
|
66
|
+
winston.verbose("(wab) /detail")
|
|
67
|
+
|
|
66
68
|
let projectId = req.query.project_id;
|
|
67
69
|
let token = req.query.token;
|
|
68
70
|
let app_id = req.query.app_id;
|
|
@@ -76,7 +78,6 @@ router.get('/detail', async (req, res) => {
|
|
|
76
78
|
}
|
|
77
79
|
|
|
78
80
|
readHTMLFile('/detail.html', (err, html) => {
|
|
79
|
-
if (err) { console.log("(wab) error read html file: ", err); }
|
|
80
81
|
var template = handlebars.compile(html);
|
|
81
82
|
var replacements = {
|
|
82
83
|
app_version: pjson.version,
|
|
@@ -92,11 +93,13 @@ router.get('/detail', async (req, res) => {
|
|
|
92
93
|
|
|
93
94
|
router.post('/install', async (req, res) => {
|
|
94
95
|
|
|
96
|
+
winston.verbose("(wab) /install")
|
|
97
|
+
|
|
95
98
|
let project_id = req.body.project_id;
|
|
96
99
|
let app_id = req.body.app_id;
|
|
97
100
|
let token = req.body.token;
|
|
98
101
|
|
|
99
|
-
|
|
102
|
+
winston.debug("(wab) Install app " + app_id + " for project id " + project_id);
|
|
100
103
|
let installation_info = {
|
|
101
104
|
project_id: project_id,
|
|
102
105
|
app_id: app_id,
|
|
@@ -105,18 +108,11 @@ router.post('/install', async (req, res) => {
|
|
|
105
108
|
|
|
106
109
|
const appClient = new TiledeskAppsClient({ APPS_API_URL: APPS_API_URL });
|
|
107
110
|
appClient.install(installation_info).then((installation) => {
|
|
108
|
-
|
|
109
|
-
if (log) {
|
|
110
|
-
console.log("(wab) installation response: ", installation);
|
|
111
|
-
}
|
|
111
|
+
winston.debug("(wab) installation response: " + installation);
|
|
112
112
|
|
|
113
113
|
let installed = true;
|
|
114
114
|
|
|
115
115
|
readHTMLFile('/detail.html', (err, html) => {
|
|
116
|
-
if (err) {
|
|
117
|
-
console.log("(wab) error read html file: ", err);
|
|
118
|
-
}
|
|
119
|
-
|
|
120
116
|
var template = handlebars.compile(html);
|
|
121
117
|
var replacements = {
|
|
122
118
|
app_version: pjson.version,
|
|
@@ -130,13 +126,15 @@ router.post('/install', async (req, res) => {
|
|
|
130
126
|
})
|
|
131
127
|
|
|
132
128
|
}).catch((err) => {
|
|
133
|
-
|
|
129
|
+
winston.error("(wab) installation error: " + err.data)
|
|
134
130
|
res.send("An error occurred during the installation");
|
|
135
131
|
})
|
|
136
132
|
|
|
137
133
|
})
|
|
138
134
|
|
|
139
135
|
router.post('/uninstall', async (req, res) => {
|
|
136
|
+
|
|
137
|
+
winston.verbose("(wab) /uninstall");
|
|
140
138
|
let project_id = req.body.project_id;
|
|
141
139
|
let app_id = req.body.app_id;
|
|
142
140
|
let token = req.body.token;
|
|
@@ -144,17 +142,11 @@ router.post('/uninstall', async (req, res) => {
|
|
|
144
142
|
const appClient = new TiledeskAppsClient({ APPS_API_URL: APPS_API_URL });
|
|
145
143
|
appClient.uninstall(project_id, app_id).then((response) => {
|
|
146
144
|
|
|
147
|
-
|
|
148
|
-
console.log("(wab) uninstallation response: ", response);
|
|
149
|
-
}
|
|
145
|
+
winston.debug("(wab) uninstallation response: " + response);
|
|
150
146
|
|
|
151
147
|
let installed = false;
|
|
152
148
|
|
|
153
149
|
readHTMLFile('/detail.html', (err, html) => {
|
|
154
|
-
if (err) {
|
|
155
|
-
console.log("(wab) error read html file: ", err);
|
|
156
|
-
}
|
|
157
|
-
|
|
158
150
|
var template = handlebars.compile(html);
|
|
159
151
|
var replacements = {
|
|
160
152
|
app_version: pjson.version,
|
|
@@ -168,16 +160,14 @@ router.post('/uninstall', async (req, res) => {
|
|
|
168
160
|
})
|
|
169
161
|
|
|
170
162
|
}).catch((err) => {
|
|
171
|
-
|
|
163
|
+
winston.error("(wab) uninsallation error: " + err.data)
|
|
172
164
|
res.send("An error occurred during the uninstallation");
|
|
173
165
|
})
|
|
174
166
|
})
|
|
175
167
|
|
|
176
168
|
router.get('/configure', async (req, res) => {
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
console.log("(wab) /configure query: ", req.query);
|
|
180
|
-
}
|
|
169
|
+
|
|
170
|
+
winston.verbose("(wab) /configure");
|
|
181
171
|
|
|
182
172
|
let projectId = "";
|
|
183
173
|
let token = "";
|
|
@@ -188,26 +178,18 @@ router.get('/configure', async (req, res) => {
|
|
|
188
178
|
let proxy_url = BASE_URL + "/webhook/" + projectId;
|
|
189
179
|
|
|
190
180
|
let CONTENT_KEY = "whatsapp-" + projectId;
|
|
191
|
-
|
|
181
|
+
|
|
192
182
|
let settings = await db.get(CONTENT_KEY);
|
|
193
|
-
|
|
194
|
-
console.log("(wab) settings: ", settings);
|
|
195
|
-
}
|
|
183
|
+
winston.debug("(wab) settings: " + settings);
|
|
196
184
|
|
|
197
185
|
// get departments
|
|
198
186
|
const tdChannel = new TiledeskChannel({ settings: { project_id: projectId, token: token }, API_URL: API_URL })
|
|
199
187
|
let departments = await tdChannel.getDepartments(token);
|
|
200
|
-
|
|
201
|
-
if (log) {
|
|
202
|
-
}
|
|
188
|
+
winston.debug("(wab) found " + departments.length + " departments")
|
|
203
189
|
|
|
204
190
|
if (settings) {
|
|
205
191
|
|
|
206
192
|
readHTMLFile('/configure.html', (err, html) => {
|
|
207
|
-
if (err) {
|
|
208
|
-
console.log("(wab) error read html file: ", err);
|
|
209
|
-
}
|
|
210
|
-
|
|
211
193
|
var template = handlebars.compile(html);
|
|
212
194
|
var replacements = {
|
|
213
195
|
app_version: pjson.version,
|
|
@@ -230,7 +212,7 @@ router.get('/configure', async (req, res) => {
|
|
|
230
212
|
readHTMLFile('/configure.html', (err, html) => {
|
|
231
213
|
|
|
232
214
|
if (err) {
|
|
233
|
-
|
|
215
|
+
winston.error("(wab) error read html file: " + err);
|
|
234
216
|
}
|
|
235
217
|
|
|
236
218
|
var template = handlebars.compile(html);
|
|
@@ -249,10 +231,8 @@ router.get('/configure', async (req, res) => {
|
|
|
249
231
|
})
|
|
250
232
|
|
|
251
233
|
router.post('/update', async (req, res) => {
|
|
252
|
-
|
|
253
|
-
|
|
254
|
-
console.log("(wab) body: ", req.body);
|
|
255
|
-
}
|
|
234
|
+
|
|
235
|
+
winston.verbose("(wab) /update");
|
|
256
236
|
|
|
257
237
|
let projectId = req.body.project_id;
|
|
258
238
|
let token = req.body.token;
|
|
@@ -268,7 +248,7 @@ router.post('/update', async (req, res) => {
|
|
|
268
248
|
// get departments
|
|
269
249
|
const tdChannel = new TiledeskChannel({ settings: { project_id: projectId, token: token }, API_URL: API_URL })
|
|
270
250
|
let departments = await tdChannel.getDepartments(token);
|
|
271
|
-
|
|
251
|
+
|
|
272
252
|
if (settings) {
|
|
273
253
|
|
|
274
254
|
settings.wab_token = wab_token;
|
|
@@ -278,10 +258,6 @@ router.post('/update', async (req, res) => {
|
|
|
278
258
|
await db.set(CONTENT_KEY, settings);
|
|
279
259
|
|
|
280
260
|
readHTMLFile('/configure.html', (err, html) => {
|
|
281
|
-
if (err) {
|
|
282
|
-
console.log("(wab) error read html file: ", err);
|
|
283
|
-
}
|
|
284
|
-
|
|
285
261
|
var template = handlebars.compile(html);
|
|
286
262
|
var replacements = {
|
|
287
263
|
app_version: pjson.version,
|
|
@@ -301,7 +277,7 @@ router.post('/update', async (req, res) => {
|
|
|
301
277
|
|
|
302
278
|
} else {
|
|
303
279
|
|
|
304
|
-
const tdClient = new TiledeskSubscriptionClient({ API_URL: API_URL, project_id: projectId, token: token
|
|
280
|
+
const tdClient = new TiledeskSubscriptionClient({ API_URL: API_URL, project_id: projectId, token: token })
|
|
305
281
|
|
|
306
282
|
const subscription_info = {
|
|
307
283
|
target: BASE_URL + "/tiledesk",
|
|
@@ -318,9 +294,7 @@ router.post('/update', async (req, res) => {
|
|
|
318
294
|
// promise
|
|
319
295
|
tdClient.subscribe(subscription_info).then((data) => {
|
|
320
296
|
let subscription = data;
|
|
321
|
-
|
|
322
|
-
console.log("\n(wab) Subscription: ", subscription)
|
|
323
|
-
}
|
|
297
|
+
winston.debug("\n(wab) Subscription: " + subscription)
|
|
324
298
|
|
|
325
299
|
let settings = {
|
|
326
300
|
project_id: projectId,
|
|
@@ -337,10 +311,6 @@ router.post('/update', async (req, res) => {
|
|
|
337
311
|
//let cnt = db.get(CONTENT_KEY);
|
|
338
312
|
|
|
339
313
|
readHTMLFile('/configure.html', (err, html) => {
|
|
340
|
-
if (err) {
|
|
341
|
-
console.log("(wab) error read html file: ", err);
|
|
342
|
-
}
|
|
343
|
-
|
|
344
314
|
var template = handlebars.compile(html);
|
|
345
315
|
var replacements = {
|
|
346
316
|
app_version: pjson.version,
|
|
@@ -361,10 +331,6 @@ router.post('/update', async (req, res) => {
|
|
|
361
331
|
}).catch((err) => {
|
|
362
332
|
|
|
363
333
|
readHTMLFile('/configure.html', (err, html) => {
|
|
364
|
-
if (err) {
|
|
365
|
-
console.log("(wab) error read html file: ", err);
|
|
366
|
-
}
|
|
367
|
-
|
|
368
334
|
var template = handlebars.compile(html);
|
|
369
335
|
var replacements = {
|
|
370
336
|
app_version: pjson.version,
|
|
@@ -383,10 +349,8 @@ router.post('/update', async (req, res) => {
|
|
|
383
349
|
})
|
|
384
350
|
|
|
385
351
|
router.post('/disconnect', async (req, res) => {
|
|
386
|
-
|
|
387
|
-
|
|
388
|
-
console.log("(wab) body: ", req.body)
|
|
389
|
-
}
|
|
352
|
+
|
|
353
|
+
winston.verbose("(wab) /disconnect")
|
|
390
354
|
|
|
391
355
|
let projectId = req.body.project_id;
|
|
392
356
|
let token = req.body.token;
|
|
@@ -395,15 +359,15 @@ router.post('/disconnect', async (req, res) => {
|
|
|
395
359
|
|
|
396
360
|
let CONTENT_KEY = "whatsapp-" + projectId;
|
|
397
361
|
await db.remove(CONTENT_KEY);
|
|
398
|
-
|
|
362
|
+
winston.verbose("(wab) Content deleted.");
|
|
399
363
|
|
|
400
364
|
let proxy_url = BASE_URL + "/webhook/" + projectId;
|
|
401
365
|
|
|
402
|
-
const tdClient = new TiledeskSubscriptionClient({ API_URL: API_URL, project_id: projectId, token: token
|
|
366
|
+
const tdClient = new TiledeskSubscriptionClient({ API_URL: API_URL, project_id: projectId, token: token })
|
|
403
367
|
// get departments
|
|
404
368
|
const tdChannel = new TiledeskChannel({ settings: { project_id: projectId, token: token }, API_URL: API_URL })
|
|
405
369
|
let departments = await tdChannel.getDepartments(token);
|
|
406
|
-
|
|
370
|
+
|
|
407
371
|
/*
|
|
408
372
|
// callback
|
|
409
373
|
tdClient.unsubsribe(projectId, subscriptionId, (err, data) => {
|
|
@@ -414,11 +378,6 @@ router.post('/disconnect', async (req, res) => {
|
|
|
414
378
|
tdClient.unsubscribe(subscriptionId).then((data) => {
|
|
415
379
|
|
|
416
380
|
readHTMLFile('/configure.html', (err, html) => {
|
|
417
|
-
|
|
418
|
-
if (err) {
|
|
419
|
-
console.log("(wab) error read html file: ", err);
|
|
420
|
-
}
|
|
421
|
-
|
|
422
381
|
var template = handlebars.compile(html);
|
|
423
382
|
var replacements = {
|
|
424
383
|
app_version: pjson.version,
|
|
@@ -432,16 +391,13 @@ router.post('/disconnect', async (req, res) => {
|
|
|
432
391
|
})
|
|
433
392
|
|
|
434
393
|
}).catch((err) => {
|
|
435
|
-
|
|
394
|
+
winston.error("(wab) unsubscribe error: " + err);
|
|
436
395
|
})
|
|
437
396
|
|
|
438
397
|
})
|
|
439
398
|
|
|
440
399
|
router.post('/tiledesk', async (req, res) => {
|
|
441
|
-
|
|
442
|
-
if (log) {
|
|
443
|
-
console.log("(wab) tiledeskChannelMessage: ", JSON.stringify(req.body.payload));
|
|
444
|
-
}
|
|
400
|
+
winston.verbose("(wab) Message received from Tiledesk")
|
|
445
401
|
|
|
446
402
|
var tiledeskChannelMessage = req.body.payload;
|
|
447
403
|
var projectId = req.body.payload.id_project;
|
|
@@ -461,32 +417,30 @@ router.post('/tiledesk', async (req, res) => {
|
|
|
461
417
|
var sender_id = req.body.payload.sender;
|
|
462
418
|
|
|
463
419
|
if (sender_id.indexOf("wab") > -1) {
|
|
464
|
-
|
|
420
|
+
winston.verbose("(wab) Skip same sender");
|
|
465
421
|
return res.sendStatus(200);
|
|
466
422
|
}
|
|
467
423
|
|
|
468
424
|
if (attributes && attributes.subtype === "info") {
|
|
469
|
-
|
|
425
|
+
winston.verbose("(wab) Skip subtype (info)");
|
|
470
426
|
return res.sendStatus(200);
|
|
471
427
|
}
|
|
472
428
|
|
|
473
429
|
if (attributes && attributes.subtype === 'info/support') {
|
|
474
|
-
|
|
430
|
+
winston.verbose("(wab) Skip subtype: " + attributes.subtype);
|
|
475
431
|
return res.sendStatus(200);
|
|
476
432
|
}
|
|
477
433
|
|
|
478
434
|
let recipient_id = tiledeskChannelMessage.recipient;
|
|
479
435
|
let whatsapp_receiver = recipient_id.substring(recipient_id.lastIndexOf("-") + 1);
|
|
480
436
|
let phone_number_id = recipient_id.substring(recipient_id.lastIndexOf("wab-") + 4, recipient_id.lastIndexOf("-"));
|
|
481
|
-
|
|
482
|
-
|
|
483
|
-
|
|
484
|
-
|
|
485
|
-
|
|
486
|
-
|
|
487
|
-
|
|
488
|
-
console.log("(wab) phone_number_id: ", phone_number_id)
|
|
489
|
-
}
|
|
437
|
+
|
|
438
|
+
winston.debug("(wab) text: " + text);
|
|
439
|
+
winston.debug("(wab) attributes: " + attributes)
|
|
440
|
+
winston.debug("(wab) tiledesk sender_id: " + sender_id);
|
|
441
|
+
winston.debug("(wab) recipient_id: " + recipient_id);
|
|
442
|
+
winston.debug("(wab) whatsapp_receiver: " + whatsapp_receiver);
|
|
443
|
+
winston.debug("(wab) phone_number_id: " + phone_number_id)
|
|
490
444
|
|
|
491
445
|
const messageHandler = new MessageHandler({ tiledeskChannelMessage: tiledeskChannelMessage });
|
|
492
446
|
const tlr = new TiledeskWhatsappTranslator();
|
|
@@ -497,30 +451,28 @@ router.post('/tiledesk', async (req, res) => {
|
|
|
497
451
|
// message
|
|
498
452
|
if (command.type === "message") {
|
|
499
453
|
let tiledeskCommandMessage = await messageHandler.generateMessageObject(command);
|
|
500
|
-
|
|
501
|
-
console.log("(wab) message generated from commanf: ", JSON.stringify(tiledeskCommandMessage))
|
|
502
|
-
}
|
|
454
|
+
winston.debug("(wab) message generated from command: " + tiledeskCommandMessage)
|
|
503
455
|
|
|
504
456
|
let whatsappJsonMessage = await tlr.toWhatsapp(tiledeskCommandMessage, whatsapp_receiver);
|
|
505
|
-
|
|
457
|
+
winston.verbose("(wab) 🟢 whatsappJsonMessage" + whatsappJsonMessage)
|
|
506
458
|
|
|
507
459
|
if (whatsappJsonMessage) {
|
|
508
460
|
const twClient = new TiledeskWhatsapp({ token: settings.wab_token, GRAPH_URL: GRAPH_URL });
|
|
509
461
|
twClient.sendMessage(phone_number_id, whatsappJsonMessage).then((response) => {
|
|
510
|
-
|
|
462
|
+
winston.verbose("(wab) Message sent to WhatsApp! " + response.status + " " + response.statusText);
|
|
511
463
|
i += 1;
|
|
512
464
|
if (i < commands.length) {
|
|
513
465
|
execute(commands[i]);
|
|
514
466
|
} else {
|
|
515
|
-
|
|
467
|
+
winston.debug("(wab) End of commands")
|
|
516
468
|
}
|
|
517
469
|
}).catch((err) => {
|
|
518
|
-
|
|
470
|
+
winston.error("(wab) send message error: " + err);
|
|
519
471
|
})
|
|
520
472
|
} else {
|
|
521
|
-
|
|
473
|
+
winston.error("(wab) WhatsappJsonMessage is undefined!")
|
|
522
474
|
}
|
|
523
|
-
|
|
475
|
+
|
|
524
476
|
}
|
|
525
477
|
|
|
526
478
|
//wait
|
|
@@ -530,7 +482,7 @@ router.post('/tiledesk', async (req, res) => {
|
|
|
530
482
|
if (i < commands.length) {
|
|
531
483
|
execute(commands[i]);
|
|
532
484
|
} else {
|
|
533
|
-
|
|
485
|
+
winston.debug("(wab) End of commands")
|
|
534
486
|
}
|
|
535
487
|
}, command.time)
|
|
536
488
|
}
|
|
@@ -538,26 +490,26 @@ router.post('/tiledesk', async (req, res) => {
|
|
|
538
490
|
execute(commands[0]);
|
|
539
491
|
}
|
|
540
492
|
|
|
541
|
-
else if (tiledeskChannelMessage.text
|
|
493
|
+
else if (tiledeskChannelMessage.text || tiledeskChannelMessage.metadata) {
|
|
542
494
|
|
|
543
495
|
let whatsappJsonMessage = await tlr.toWhatsapp(tiledeskChannelMessage, whatsapp_receiver);
|
|
544
|
-
|
|
496
|
+
winston.verbose("(wab) 🟢 whatsappJsonMessage" + whatsappJsonMessage)
|
|
545
497
|
|
|
546
498
|
if (whatsappJsonMessage) {
|
|
547
499
|
const twClient = new TiledeskWhatsapp({ token: settings.wab_token, GRAPH_URL: GRAPH_URL });
|
|
548
|
-
|
|
500
|
+
|
|
549
501
|
twClient.sendMessage(phone_number_id, whatsappJsonMessage).then((response) => {
|
|
550
|
-
|
|
502
|
+
winston.verbose("(wab) Message sent to WhatsApp! " + response.status + " " + response.statusText);
|
|
551
503
|
}).catch((err) => {
|
|
552
|
-
|
|
504
|
+
winston.error("(wab) error send message: " + err);
|
|
553
505
|
})
|
|
554
|
-
|
|
506
|
+
|
|
555
507
|
} else {
|
|
556
|
-
|
|
508
|
+
winston.error("(wab) Whatsapp Json Message is undefined!")
|
|
557
509
|
}
|
|
558
|
-
|
|
510
|
+
|
|
559
511
|
} else {
|
|
560
|
-
|
|
512
|
+
winston.debug("(wab) no command, no text --> skip")
|
|
561
513
|
}
|
|
562
514
|
|
|
563
515
|
return res.send(200);
|
|
@@ -566,13 +518,12 @@ router.post('/tiledesk', async (req, res) => {
|
|
|
566
518
|
// Endpoint for Whatsapp Business
|
|
567
519
|
// Accepts POST requests at /webhook endpoint
|
|
568
520
|
router.post("/webhook/:project_id", async (req, res) => {
|
|
569
|
-
|
|
521
|
+
|
|
570
522
|
// Parse the request body from the POST
|
|
571
523
|
let projectId = req.params.project_id;
|
|
572
|
-
|
|
524
|
+
winston.verbose("(wab) Message received from WhatsApp");
|
|
573
525
|
|
|
574
526
|
// Check the Incoming webhook message
|
|
575
|
-
// console.log("\n***Body: ", JSON.stringify(req.body, null, 2));
|
|
576
527
|
// info on WhatsApp text message payload: https://developers.facebook.com/docs/whatsapp/cloud-api/webhooks/payload-examples#text-messages
|
|
577
528
|
if (req.body.object) {
|
|
578
529
|
if (
|
|
@@ -583,13 +534,8 @@ router.post("/webhook/:project_id", async (req, res) => {
|
|
|
583
534
|
req.body.entry[0].changes[0].value.messages[0]
|
|
584
535
|
) {
|
|
585
536
|
|
|
586
|
-
console.log("(wab) Message received from WhatsApp");
|
|
587
|
-
if (log) {
|
|
588
|
-
console.log("\n(wab) body: ", JSON.stringify(req.body));
|
|
589
|
-
}
|
|
590
|
-
|
|
591
537
|
if (req.body.entry[0].changes[0].value.messages[0].type == "system") {
|
|
592
|
-
|
|
538
|
+
winston.verbos("(wab) Skip system message")
|
|
593
539
|
return res.sendStatus(200);
|
|
594
540
|
}
|
|
595
541
|
|
|
@@ -597,11 +543,10 @@ router.post("/webhook/:project_id", async (req, res) => {
|
|
|
597
543
|
|
|
598
544
|
let CONTENT_KEY = "whatsapp-" + projectId;
|
|
599
545
|
let settings = await db.get(CONTENT_KEY);
|
|
600
|
-
|
|
601
|
-
|
|
602
|
-
}
|
|
546
|
+
winston.debug("(wab) settings: " + settings);
|
|
547
|
+
|
|
603
548
|
if (!settings) {
|
|
604
|
-
|
|
549
|
+
winston.verbose("(wab) No settings found. Exit..");
|
|
605
550
|
return res.sendStatus(200);
|
|
606
551
|
}
|
|
607
552
|
|
|
@@ -609,26 +554,23 @@ router.post("/webhook/:project_id", async (req, res) => {
|
|
|
609
554
|
const tdChannel = new TiledeskChannel({ settings: settings, API_URL: API_URL })
|
|
610
555
|
|
|
611
556
|
// Initialize conversation with chatbot
|
|
612
|
-
if (whatsappChannelMessage.text && whatsappChannelMessage.text.body.startsWith("#td")) {
|
|
557
|
+
if (whatsappChannelMessage.text && whatsappChannelMessage.text.body.startsWith("#td")) {
|
|
613
558
|
|
|
614
559
|
let code = whatsappChannelMessage.text.body.split(' ')[0];
|
|
615
|
-
console.log("(wab) test code: ", code)
|
|
616
560
|
|
|
617
|
-
const bottester = new TiledeskBotTester({project_id: projectId, redis_client: redis_client, db: db, tdChannel: tdChannel, tlr: tlr});
|
|
561
|
+
const bottester = new TiledeskBotTester({ project_id: projectId, redis_client: redis_client, db: db, tdChannel: tdChannel, tlr: tlr });
|
|
618
562
|
bottester.startBotConversation(req.body, code).then((result) => {
|
|
619
|
-
|
|
620
|
-
|
|
621
|
-
console.log("(wab) result: ", result);
|
|
622
|
-
}
|
|
563
|
+
winston.verbose("(wab) test conversation started");
|
|
564
|
+
winston.debug("(wab) startBotConversation result: " + result);
|
|
623
565
|
}).catch((err) => {
|
|
624
|
-
|
|
566
|
+
winston.error("(wab) start test onversation error: " + err);
|
|
625
567
|
})
|
|
626
568
|
|
|
627
|
-
|
|
569
|
+
// Standard message
|
|
628
570
|
} else {
|
|
629
|
-
|
|
571
|
+
|
|
630
572
|
let firstname = req.body.entry[0].changes[0].value.contacts[0].profile.name;
|
|
631
|
-
|
|
573
|
+
|
|
632
574
|
let message_info = {
|
|
633
575
|
channel: "whatsapp",
|
|
634
576
|
whatsapp: {
|
|
@@ -638,93 +580,91 @@ router.post("/webhook/:project_id", async (req, res) => {
|
|
|
638
580
|
lastname: " "
|
|
639
581
|
}
|
|
640
582
|
}
|
|
641
|
-
|
|
583
|
+
|
|
642
584
|
let tiledeskJsonMessage;
|
|
643
|
-
|
|
585
|
+
|
|
644
586
|
if ((whatsappChannelMessage.type == 'text')) {
|
|
645
|
-
|
|
587
|
+
winston.debug("(wab) message type: text")
|
|
646
588
|
tiledeskJsonMessage = await tlr.toTiledesk(whatsappChannelMessage, firstname);
|
|
647
589
|
}
|
|
648
|
-
|
|
590
|
+
|
|
649
591
|
else if (whatsappChannelMessage.type == 'interactive') {
|
|
650
|
-
|
|
592
|
+
winston.debug("(wab) message type: interactive")
|
|
651
593
|
tiledeskJsonMessage = await tlr.toTiledesk(whatsappChannelMessage, firstname);
|
|
652
594
|
}
|
|
653
595
|
|
|
654
596
|
else if ((whatsappChannelMessage.type == 'image') || (whatsappChannelMessage.type == 'video') || (whatsappChannelMessage.type == 'document')) {
|
|
655
597
|
let media;
|
|
656
598
|
const util = new TiledeskWhatsapp({ token: settings.wab_token, GRAPH_URL: GRAPH_URL })
|
|
657
|
-
|
|
599
|
+
|
|
658
600
|
if (whatsappChannelMessage.type == 'image') {
|
|
659
601
|
media = whatsappChannelMessage.image;
|
|
660
602
|
const filename = await util.downloadMedia(media.id);
|
|
661
603
|
if (!filename) {
|
|
662
|
-
|
|
604
|
+
winston.debug("(wab) Unable to download media with id " + media.id + ". Message not sent.");
|
|
663
605
|
return res.status(500).send({ success: false, error: "unable to download media" })
|
|
664
606
|
}
|
|
665
607
|
let file_path = path.join(__dirname, 'tmp', filename);
|
|
666
|
-
|
|
608
|
+
|
|
667
609
|
const image_url = await util.uploadMedia(file_path, "images");
|
|
668
|
-
|
|
669
|
-
|
|
610
|
+
winston.debug("(wab) image_url: " + image_url)
|
|
611
|
+
|
|
670
612
|
tiledeskJsonMessage = await tlr.toTiledesk(whatsappChannelMessage, firstname, image_url);
|
|
671
613
|
}
|
|
672
|
-
|
|
614
|
+
|
|
673
615
|
if (whatsappChannelMessage.type == 'video') {
|
|
674
616
|
media = whatsappChannelMessage.video;
|
|
675
|
-
|
|
617
|
+
|
|
676
618
|
const filename = await util.downloadMedia(media.id);
|
|
677
619
|
if (!filename) {
|
|
678
|
-
|
|
620
|
+
winston.debug("(wab) Unable to download media with id " + media.id + ". Message not sent.");
|
|
679
621
|
return res.status(500).send({ success: false, error: "unable to download media" })
|
|
680
622
|
}
|
|
681
623
|
let file_path = path.join(__dirname, 'tmp', filename);
|
|
682
|
-
|
|
624
|
+
|
|
683
625
|
const media_url = await util.uploadMedia(file_path, "files");
|
|
684
|
-
|
|
685
|
-
|
|
626
|
+
winston.debug("(wab) media_url: " + media_url)
|
|
627
|
+
|
|
686
628
|
tiledeskJsonMessage = await tlr.toTiledesk(whatsappChannelMessage, firstname, media_url);
|
|
687
629
|
}
|
|
688
|
-
|
|
630
|
+
|
|
689
631
|
if (whatsappChannelMessage.type == 'document') {
|
|
690
632
|
media = whatsappChannelMessage.document;
|
|
691
|
-
|
|
633
|
+
|
|
692
634
|
const filename = await util.downloadMedia(media.id);
|
|
693
635
|
if (!filename) {
|
|
694
|
-
|
|
636
|
+
winston.debug("(wab) Unable to download media with id " + media.id + ". Message not sent.");
|
|
695
637
|
return res.status(500).send({ success: false, error: "unable to download media" })
|
|
696
638
|
}
|
|
697
639
|
let file_path = path.join(__dirname, 'tmp', filename);
|
|
698
|
-
|
|
640
|
+
|
|
699
641
|
const media_url = await util.uploadMedia(file_path, "files");
|
|
700
|
-
|
|
701
|
-
|
|
642
|
+
winston.debug("(wab) media_url: " + media_url)
|
|
643
|
+
|
|
702
644
|
tiledeskJsonMessage = await tlr.toTiledesk(whatsappChannelMessage, firstname, media_url);
|
|
703
645
|
}
|
|
704
|
-
|
|
646
|
+
|
|
705
647
|
} else {
|
|
706
648
|
// unsupported. Try anyway to send something.
|
|
707
|
-
|
|
649
|
+
winston.debug("(wab) unsupported message")
|
|
708
650
|
}
|
|
709
651
|
|
|
710
652
|
if (tiledeskJsonMessage) {
|
|
711
|
-
|
|
653
|
+
winston.verbose("(wab) 🟠 tiledeskJsonMessage: " + tiledeskJsonMessage);
|
|
712
654
|
const response = await tdChannel.send(tiledeskJsonMessage, message_info, settings.department_id);
|
|
713
|
-
|
|
714
|
-
|
|
715
|
-
console.log("(wab) response: ", response)
|
|
716
|
-
}
|
|
655
|
+
winston.verbose("(wab) Message sent to Tiledesk!")
|
|
656
|
+
winston.debug("(wab) response: " + response)
|
|
717
657
|
} else {
|
|
718
|
-
|
|
658
|
+
winston.verbose("(wab) tiledeskJsonMessage is undefined")
|
|
719
659
|
}
|
|
720
|
-
|
|
660
|
+
|
|
721
661
|
}
|
|
722
|
-
}
|
|
723
|
-
res.sendStatus(200);
|
|
724
|
-
|
|
662
|
+
}
|
|
663
|
+
res.sendStatus(200);
|
|
664
|
+
|
|
725
665
|
} else {
|
|
726
666
|
// Return a '404 Not Found' if event is not from a WhatsApp API
|
|
727
|
-
|
|
667
|
+
winston.verbose("(wab) event not from whatsapp")
|
|
728
668
|
res.sendStatus(404);
|
|
729
669
|
}
|
|
730
670
|
});
|
|
@@ -736,8 +676,8 @@ router.get("/webhook/:project_id", async (req, res) => {
|
|
|
736
676
|
* UPDATE YOUR VERIFY TOKEN
|
|
737
677
|
*This will be the Verify Token value when you set up webhook
|
|
738
678
|
**/
|
|
739
|
-
|
|
740
|
-
|
|
679
|
+
winston.verbose("(wab) Verify the webhook... ");
|
|
680
|
+
winston.debug("(wab) req.query: " + req.query);
|
|
741
681
|
|
|
742
682
|
// Parse params from the webhook verification request
|
|
743
683
|
let mode = req.query["hub.mode"];
|
|
@@ -749,31 +689,25 @@ router.get("/webhook/:project_id", async (req, res) => {
|
|
|
749
689
|
let settings = await db.get(CONTENT_KEY);
|
|
750
690
|
|
|
751
691
|
if (!settings || !settings.verify_token) {
|
|
752
|
-
|
|
692
|
+
winston.error("(wab) No settings found! Unable to verify token.")
|
|
753
693
|
res.sendStatus(403);
|
|
754
694
|
} else {
|
|
755
695
|
let VERIFY_TOKEN = settings.verify_token;
|
|
756
696
|
|
|
757
|
-
if (log) {
|
|
758
|
-
console.log("token: ", token);
|
|
759
|
-
console.log("verify token: ", VERIFY_TOKEN);
|
|
760
|
-
}
|
|
761
|
-
|
|
762
697
|
// Check if a token and mode were sent
|
|
763
698
|
if (mode && token) {
|
|
764
699
|
// Check the mode and token sent are correct
|
|
765
700
|
if (mode === "subscribe" && token === VERIFY_TOKEN) {
|
|
766
|
-
|
|
767
701
|
// Respond with 200 OK and challenge token from the request
|
|
768
|
-
|
|
702
|
+
winston.verbose("(wab) Webhook verified");
|
|
769
703
|
res.status(200).send(challenge);
|
|
770
704
|
} else {
|
|
771
705
|
// Responds with '403 Forbidden' if verify tokens do not match
|
|
772
|
-
|
|
706
|
+
winston.error("(wab) mode is not 'subscribe' or token do not match");
|
|
773
707
|
res.sendStatus(403);
|
|
774
708
|
}
|
|
775
709
|
} else {
|
|
776
|
-
|
|
710
|
+
winston.error("(wab) mode or token undefined");
|
|
777
711
|
res.status(400).send("impossible to verify the webhook: mode or token undefined.")
|
|
778
712
|
}
|
|
779
713
|
|
|
@@ -784,8 +718,8 @@ router.get("/webhook/:project_id", async (req, res) => {
|
|
|
784
718
|
|
|
785
719
|
router.post("/newtest", async (req, res) => {
|
|
786
720
|
|
|
787
|
-
|
|
788
|
-
|
|
721
|
+
winston.verbose("(wab) initializing new test..");
|
|
722
|
+
|
|
789
723
|
let project_id = req.body.project_id;
|
|
790
724
|
let bot_id = req.body.bot_id;
|
|
791
725
|
|
|
@@ -798,17 +732,17 @@ router.post("/newtest", async (req, res) => {
|
|
|
798
732
|
let key = "bottest:" + short_uid;
|
|
799
733
|
|
|
800
734
|
if (!redis_client) {
|
|
801
|
-
return res.status(500).send({ message: "Test it out on Whatsapp not available. Redis not ready."})
|
|
735
|
+
return res.status(500).send({ message: "Test it out on Whatsapp not available. Redis not ready." })
|
|
802
736
|
}
|
|
803
737
|
|
|
804
738
|
await redis_client.set(key, JSON.stringify(info), 'EX', 604800);
|
|
805
739
|
redis_client.get(key, (err, value) => {
|
|
806
740
|
if (err) {
|
|
807
|
-
|
|
808
|
-
return res.status(500).send({success: "false", message: "Testing info could not be saved"});
|
|
741
|
+
winston.error("(wab) redis get err: " + err)
|
|
742
|
+
return res.status(500).send({ success: "false", message: "Testing info could not be saved" });
|
|
809
743
|
} else {
|
|
810
|
-
|
|
811
|
-
return res.status(200).send({short_uid: short_uid});
|
|
744
|
+
winston.debug("(wab) new test initialized with id: " + short_uid)
|
|
745
|
+
return res.status(200).send({ short_uid: short_uid });
|
|
812
746
|
}
|
|
813
747
|
})
|
|
814
748
|
|
|
@@ -819,7 +753,7 @@ router.post("/newtest", async (req, res) => {
|
|
|
819
753
|
// *****************************
|
|
820
754
|
|
|
821
755
|
async function startApp(settings, callback) {
|
|
822
|
-
|
|
756
|
+
winston.info("(wab) Starting Whatsapp App")
|
|
823
757
|
|
|
824
758
|
if (!settings.MONGODB_URL) {
|
|
825
759
|
throw new Error("settings.MONGODB_URL is mandatory");
|
|
@@ -829,28 +763,28 @@ async function startApp(settings, callback) {
|
|
|
829
763
|
throw new Error("settings.API_URL is mandatory");
|
|
830
764
|
} else {
|
|
831
765
|
API_URL = settings.API_URL;
|
|
832
|
-
|
|
766
|
+
winston.info("(wab) API_URL: " + API_URL);
|
|
833
767
|
}
|
|
834
768
|
|
|
835
769
|
if (!settings.BASE_URL) {
|
|
836
770
|
throw new Error("settings.BASE_URL is mandatory");
|
|
837
771
|
} else {
|
|
838
772
|
BASE_URL = settings.BASE_URL;
|
|
839
|
-
|
|
773
|
+
winston.info("(wab) BASE_URL: " + BASE_URL);
|
|
840
774
|
}
|
|
841
775
|
|
|
842
776
|
if (!settings.GRAPH_URL) {
|
|
843
777
|
throw new Error("settings.GRAPH_URL is mandatory");
|
|
844
778
|
} else {
|
|
845
779
|
GRAPH_URL = settings.GRAPH_URL;
|
|
846
|
-
|
|
780
|
+
winston.info("(wab) GRAPH_URL: " + GRAPH_URL);
|
|
847
781
|
}
|
|
848
782
|
|
|
849
783
|
if (!settings.APPS_API_URL) {
|
|
850
784
|
throw new Error("settings.APPS_API_URL is mandatory");
|
|
851
785
|
} else {
|
|
852
786
|
APPS_API_URL = settings.APPS_API_URL;
|
|
853
|
-
|
|
787
|
+
winston.info("(wab) APPS_API_URL: " + APPS_API_URL);
|
|
854
788
|
}
|
|
855
789
|
|
|
856
790
|
if (settings.REDIS_HOST && settings.REDIS_PORT) {
|
|
@@ -859,16 +793,12 @@ async function startApp(settings, callback) {
|
|
|
859
793
|
REDIS_PASSWORD = settings.REDIS_PASSWORD;
|
|
860
794
|
connectRedis();
|
|
861
795
|
} else {
|
|
862
|
-
|
|
863
|
-
}
|
|
864
|
-
|
|
865
|
-
if (settings.log) {
|
|
866
|
-
log = settings.log;
|
|
796
|
+
winston.info("(wab) Missing redis parameters --> Test it out on WhatsApp disabled");
|
|
867
797
|
}
|
|
868
798
|
|
|
869
799
|
db.connect(settings.MONGODB_URL, () => {
|
|
870
|
-
|
|
871
|
-
|
|
800
|
+
winston.info("(wab) KVBaseMongo successfully connected.");
|
|
801
|
+
|
|
872
802
|
if (callback) {
|
|
873
803
|
callback();
|
|
874
804
|
}
|
|
@@ -879,26 +809,25 @@ function connectRedis() {
|
|
|
879
809
|
redis_client = redis.createClient({
|
|
880
810
|
host: REDIS_HOST,
|
|
881
811
|
port: REDIS_PORT,
|
|
882
|
-
password: REDIS_PASSWORD
|
|
812
|
+
password: REDIS_PASSWORD
|
|
883
813
|
});
|
|
884
814
|
|
|
885
815
|
redis_client.on('error', err => {
|
|
886
|
-
|
|
816
|
+
winston.info('(wab) Connect Redis Error ' + err);
|
|
887
817
|
})
|
|
888
818
|
/*
|
|
889
819
|
redis_client.on('connect', () => {
|
|
890
|
-
|
|
820
|
+
winston.info('Redis Connected!'); // Connected!
|
|
891
821
|
});
|
|
892
822
|
*/
|
|
893
823
|
redis_client.on('ready', () => {
|
|
894
|
-
|
|
824
|
+
winston.info("(wab) Redis ready!")
|
|
895
825
|
})
|
|
896
826
|
//await redis_client.connect(); // only for v4
|
|
897
827
|
|
|
898
828
|
}
|
|
899
829
|
|
|
900
830
|
function readHTMLFile(templateName, callback) {
|
|
901
|
-
//console.log("Reading file: ", templateName)
|
|
902
831
|
fs.readFile(__dirname + '/template' + templateName, { encoding: 'utf-8' },
|
|
903
832
|
function(err, html) {
|
|
904
833
|
if (err) {
|