@tiledesk/tiledesk-voice-twilio-connector 0.1.12 → 0.1.14-rc1
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
CHANGED
|
@@ -37,7 +37,6 @@ var redis_client;
|
|
|
37
37
|
|
|
38
38
|
//UTILS
|
|
39
39
|
const CHANNEL_NAME = require('./tiledesk/constants').CHANNEL_NAME
|
|
40
|
-
const TYPE_MESSAGE = require('./tiledesk/constants').TYPE_MESSAGE
|
|
41
40
|
const CALL_STATUS = require('./tiledesk/constants').CALL_STATUS
|
|
42
41
|
const VOICE_NAME = require('./tiledesk/constants').VOICE_NAME
|
|
43
42
|
const VOICE_LANGUAGE = require('./tiledesk/constants').VOICE_LANGUAGE
|
|
@@ -54,6 +53,13 @@ let twilio = require('twilio');
|
|
|
54
53
|
const VoiceResponse = require('twilio').twiml.VoiceResponse;
|
|
55
54
|
const { MessagingResponse } = require('twilio').twiml;
|
|
56
55
|
|
|
56
|
+
let start1= ''
|
|
57
|
+
let time = null;
|
|
58
|
+
|
|
59
|
+
/*UTILS*/
|
|
60
|
+
const utilsMess = require('./tiledesk/utils-message.js')
|
|
61
|
+
const TYPE_MESSAGE = require('./tiledesk/constants').TYPE_MESSAGE
|
|
62
|
+
|
|
57
63
|
router.get("/", async (req, res) => {
|
|
58
64
|
res.send("Welcome to Tiledesk-voice-twilio connector");
|
|
59
65
|
});
|
|
@@ -61,6 +67,7 @@ router.get("/", async (req, res) => {
|
|
|
61
67
|
|
|
62
68
|
// TILEDESK WEBHOOK: message from tiledesk to user (chatbot/agent messagges)
|
|
63
69
|
router.post("/tiledesk", async (req, res) => {
|
|
70
|
+
winston.debug("(vxml) Message received from Tiledesk in projectID: "+ req.body.payload.id_project + ' ---- and text: '+req.body.payload.text )
|
|
64
71
|
let tiledeskMessage = req.body.payload
|
|
65
72
|
let project_id = tiledeskMessage.id_project
|
|
66
73
|
|
|
@@ -73,6 +80,15 @@ router.post("/tiledesk", async (req, res) => {
|
|
|
73
80
|
});
|
|
74
81
|
tdChannel.setProjectId(project_id)
|
|
75
82
|
|
|
83
|
+
/*SKIP INFO MESSAGES*/
|
|
84
|
+
/*SKIP CURRENT USER MESSAGES*/
|
|
85
|
+
if(!utilsMess.messageType(TYPE_MESSAGE.INFO, tiledeskMessage) && !(tiledeskMessage.sender.indexOf("vxml") > -1) ){
|
|
86
|
+
winston.verbose("> whook SAVE MESSAGE TO QUEUE " + JSON.stringify(tiledeskMessage) );
|
|
87
|
+
start1 = new Date().getTime();
|
|
88
|
+
console.log("(WH) time: ", new Date().getTime() - time)
|
|
89
|
+
console.log("(WH) received message: ", tiledeskMessage.text, ' --- at time:', new Date(), start1)
|
|
90
|
+
}
|
|
91
|
+
|
|
76
92
|
await tdChannel.addMessageToQueue(tiledeskMessage)
|
|
77
93
|
|
|
78
94
|
res.send("(vxml) Message received from Voice VXML Proxy");
|
|
@@ -82,7 +98,8 @@ router.post("/tiledesk", async (req, res) => {
|
|
|
82
98
|
|
|
83
99
|
// TWILIO WEBHOOK : message from user to tiledesk
|
|
84
100
|
router.post('/webhook/:id_project', async (req, res) => {
|
|
85
|
-
winston.debug('(voice) called POST /webhook/:id_project ', req.params)
|
|
101
|
+
winston.debug('(voice) called POST /webhook/:id_project '+ new Date(), req.params)
|
|
102
|
+
let start_call = new Date().getTime();
|
|
86
103
|
|
|
87
104
|
let project_id = req.params.id_project;
|
|
88
105
|
let callSid = req.body.CallSid;
|
|
@@ -117,11 +134,14 @@ router.post('/webhook/:id_project', async (req, res) => {
|
|
|
117
134
|
BASE_URL: BASE_URL
|
|
118
135
|
});
|
|
119
136
|
|
|
137
|
+
let start2 = new Date().getTime();
|
|
120
138
|
let user = await tdChannel.signIn(from, settings);
|
|
121
139
|
if(!user){
|
|
122
140
|
res.status(401).send({message: "Cannot able to signIn with current caller phone :" + from});
|
|
123
141
|
return;
|
|
124
142
|
}
|
|
143
|
+
let end2 = new Date().getTime();
|
|
144
|
+
console.log('Time after signIn: ', end2-start2, '[ms]')
|
|
125
145
|
|
|
126
146
|
//let conversation_id = await tdChannel.getConversation(ani, callId, user.token);
|
|
127
147
|
let conversation_id = await tdChannel.generateConversation(from, callSid, user.token);
|
|
@@ -146,7 +166,7 @@ router.post('/webhook/:id_project', async (req, res) => {
|
|
|
146
166
|
|
|
147
167
|
await redis_client.set('tiledesk:vxml:'+callSid+':session', JSON.stringify(session_data), {'EX': 86400});
|
|
148
168
|
|
|
149
|
-
|
|
169
|
+
let start4 = new Date().getTime();
|
|
150
170
|
let tiledeskMessage= {
|
|
151
171
|
text:'/start',
|
|
152
172
|
senderFullname: from,
|
|
@@ -164,7 +184,8 @@ router.post('/webhook/:id_project', async (req, res) => {
|
|
|
164
184
|
if(!message){
|
|
165
185
|
return res.status(503).send({ message: "Bad response: Quota exceeded" })
|
|
166
186
|
}
|
|
167
|
-
|
|
187
|
+
let end4 = new Date().getTime();
|
|
188
|
+
console.log('Time after sent message /start: ', end4-start4, '[ms]')
|
|
168
189
|
|
|
169
190
|
//generate Tiledesk wait message
|
|
170
191
|
let delayTime = await voiceChannel.getNextDelayTimeForCallId(callSid)
|
|
@@ -181,12 +202,17 @@ router.post('/webhook/:id_project', async (req, res) => {
|
|
|
181
202
|
res.set('Content-Type', 'text/xml');
|
|
182
203
|
res.status(200).send(messageToVXML);
|
|
183
204
|
|
|
205
|
+
let end_call = new Date().getTime();
|
|
206
|
+
console.log('Time to responde to /webhook/:id_project : ', end_call-start_call, '[ms]')
|
|
207
|
+
|
|
184
208
|
});
|
|
185
209
|
|
|
186
210
|
|
|
187
211
|
router.post('/nextblock/:callSid/', async(req, res) => {
|
|
188
|
-
|
|
189
|
-
winston.debug("(vxml) called POST /nextblock
|
|
212
|
+
let start_call = new Date()
|
|
213
|
+
winston.debug("(vxml) called POST /nextblock ", req.body);
|
|
214
|
+
winston.debug("(vxml) called POST /nextblock query ", req.query);
|
|
215
|
+
console.log('/nextblock at: ', new Date(), 'with text:', req.body.SpeechResult)
|
|
190
216
|
|
|
191
217
|
let usertext = req.body.SpeechResult;
|
|
192
218
|
let confidence = req.body.Confidence
|
|
@@ -236,18 +262,21 @@ router.post('/nextblock/:callSid/', async(req, res) => {
|
|
|
236
262
|
|
|
237
263
|
let message = {}, queue = []
|
|
238
264
|
queue = await tdChannel.getMessagesFromQueue(conversation_id)
|
|
239
|
-
winston.
|
|
265
|
+
winston.verbose('/NEXT controllo coda--> '+ queue.length + ' ' + usertext)
|
|
240
266
|
if(queue.length === 0 && (usertext === '' || !usertext)){
|
|
241
267
|
winston.debug('QUEUE is empty--> ',queue)
|
|
242
268
|
|
|
243
269
|
//CASE: queue is empty --> generate Tiledesk wait message and manage delayTime
|
|
244
270
|
let delayTime = await voiceChannel.getNextDelayTimeForCallId(callSid)
|
|
271
|
+
console.log('delay /nextblock -->', delayTime)
|
|
245
272
|
message = await tdChannel.generateWaitTdMessage(from, delayTime)
|
|
246
273
|
//update delayIndex for wait command message time
|
|
247
274
|
await voiceChannel.saveDelayIndexForCallId(from)
|
|
248
275
|
|
|
249
276
|
} else if(queue.length > 0 && (usertext === '' || !usertext)){
|
|
250
277
|
|
|
278
|
+
let end1 = new Date().getTime()
|
|
279
|
+
console.log('Time between wh message and /nextblock queue message:', end1-start1, '[ms] (message:', queue[0].text , ') at time', new Date())
|
|
251
280
|
//CASE: queue has at least one message to reproduce --> get message from tiledesk queue and reset delayTime
|
|
252
281
|
message = queue[0]
|
|
253
282
|
winston.debug('QUEUE --> ',queue[0])
|
|
@@ -266,10 +295,14 @@ router.post('/nextblock/:callSid/', async(req, res) => {
|
|
|
266
295
|
type: 'text',
|
|
267
296
|
channel: { name: CHANNEL_NAME }
|
|
268
297
|
};
|
|
298
|
+
let startSend= new Date().getTime()
|
|
269
299
|
let tdMessage = await tdChannel.send(tiledeskMessage, user.token, conversation_id);
|
|
270
300
|
winston.debug("message sent : ", tdMessage);
|
|
301
|
+
let endSend = new Date().getTime();
|
|
302
|
+
console.log('Time to send messagge ( ', usertext, '): ', endSend - startSend, '[ms] at time', new Date())
|
|
271
303
|
//generate Tiledesk wait message
|
|
272
304
|
let delayTime = await voiceChannel.getNextDelayTimeForCallId(callSid)
|
|
305
|
+
console.log('(message sent) delay /nextblock -->', delayTime)
|
|
273
306
|
message = await tdChannel.generateWaitTdMessage(from, delayTime)
|
|
274
307
|
//update delayIndex for wait command message time
|
|
275
308
|
await voiceChannel.saveDelayIndexForCallId(callSid)
|
|
@@ -280,15 +313,101 @@ router.post('/nextblock/:callSid/', async(req, res) => {
|
|
|
280
313
|
let messageToVXML = await tdTranslator.toVXML(message, callSid, vxmlAttributes)
|
|
281
314
|
winston.debug("(voice) VXML to SEND: "+ messageToVXML);
|
|
282
315
|
|
|
316
|
+
let end_call = new Date()
|
|
317
|
+
console.log('Time to responde to /nextblock/:callSid : ', end_call-start_call, '[ms]')
|
|
318
|
+
|
|
283
319
|
// Render the response as XML in reply to the webhook request
|
|
284
320
|
res.set('Content-Type', 'text/xml');
|
|
285
321
|
res.status(200).send(messageToVXML);
|
|
322
|
+
|
|
323
|
+
})
|
|
324
|
+
|
|
325
|
+
router.post('/speechresult/:callSid', async (req, res) => {
|
|
326
|
+
|
|
327
|
+
let startTime = new Date();
|
|
328
|
+
winston.verbose("(vxml) called POST /speechresult ", req.body);
|
|
329
|
+
winston.verbose("(vxml) called POST /speechresult query ", req.query);
|
|
330
|
+
|
|
331
|
+
let usertext = req.body.SpeechResult;
|
|
332
|
+
let confidence = req.body.Confidence
|
|
333
|
+
let callSid = req.params.callSid;
|
|
334
|
+
|
|
335
|
+
let sessionInfo;
|
|
336
|
+
let project_id, conversation_id, user;
|
|
337
|
+
let from, to;
|
|
338
|
+
|
|
339
|
+
let redis_data = await redis_client.get('tiledesk:vxml:'+callSid+':session');
|
|
340
|
+
//let redis_data = await redis_client.hGetAll('tiledesk:vxml:'+callId);
|
|
341
|
+
if (!redis_data) {
|
|
342
|
+
return res.status(500).send({ success: "false", message: "Can't retrive data for callSid ->" + callSid });
|
|
343
|
+
}
|
|
344
|
+
sessionInfo = JSON.parse(redis_data)
|
|
345
|
+
project_id = sessionInfo.project_id;
|
|
346
|
+
from = sessionInfo.from;
|
|
347
|
+
to = sessionInfo.to;
|
|
348
|
+
conversation_id = sessionInfo.conversation_id;
|
|
349
|
+
user = sessionInfo.user;
|
|
350
|
+
|
|
351
|
+
let vxmlAttributes = {
|
|
352
|
+
voiceName: VOICE_NAME,
|
|
353
|
+
voiceLanguage: VOICE_LANGUAGE,
|
|
354
|
+
callSid: callSid,
|
|
355
|
+
};
|
|
356
|
+
|
|
357
|
+
const tdChannel = new TiledeskChannel({
|
|
358
|
+
API_URL: API_URL,
|
|
359
|
+
redis_client: redis_client
|
|
360
|
+
})
|
|
361
|
+
tdChannel.setProjectId(project_id);
|
|
362
|
+
|
|
363
|
+
const tdTranslator = new TiledeskTwilioTranslator({
|
|
364
|
+
BASE_URL: BASE_URL
|
|
365
|
+
});
|
|
366
|
+
|
|
367
|
+
winston.verbose("(vxml) usertext "+usertext);
|
|
368
|
+
let message = {};
|
|
369
|
+
if(usertext){
|
|
370
|
+
let tiledeskMessage= {
|
|
371
|
+
text:usertext,
|
|
372
|
+
senderFullname: from,
|
|
373
|
+
type: 'text',
|
|
374
|
+
channel: { name: CHANNEL_NAME }
|
|
375
|
+
};
|
|
376
|
+
let tdMessage = await tdChannel.send(tiledeskMessage, user.token, conversation_id);
|
|
377
|
+
winston.debug("message sent : ", tdMessage);
|
|
378
|
+
//generate Tiledesk wait message
|
|
379
|
+
let delayTime = await voiceChannel.getNextDelayTimeForCallId(callSid)
|
|
380
|
+
message = await tdChannel.generateWaitTdMessage(from, 50)
|
|
381
|
+
//update delayIndex for wait command message time
|
|
382
|
+
await voiceChannel.saveDelayIndexForCallId(callSid)
|
|
383
|
+
|
|
384
|
+
}else {
|
|
385
|
+
|
|
386
|
+
let delayTime = await voiceChannel.getNextDelayTimeForCallId(callSid)
|
|
387
|
+
message = await tdChannel.generateWaitTdMessage(from, 50)
|
|
388
|
+
//update delayIndex for wait command message time
|
|
389
|
+
await voiceChannel.saveDelayIndexForCallId(from)
|
|
390
|
+
}
|
|
391
|
+
|
|
392
|
+
// convert response to vxml
|
|
393
|
+
let messageToVXML = await tdTranslator.toVXML(message, callSid, vxmlAttributes)
|
|
394
|
+
winston.debug("(voice) VXML to SEND: "+ messageToVXML);
|
|
395
|
+
|
|
396
|
+
let endTime = new Date()
|
|
397
|
+
let diffTIme = endTime - startTime
|
|
398
|
+
winston.verbose("(voice) send response to TWILIO in : " + diffTIme + "ms");
|
|
399
|
+
|
|
400
|
+
// Render the response as XML in reply to the webhook request
|
|
401
|
+
res.set('Content-Type', 'text/xml');
|
|
402
|
+
res.status(200).send(messageToVXML);
|
|
403
|
+
|
|
404
|
+
|
|
286
405
|
})
|
|
287
406
|
|
|
288
407
|
|
|
289
408
|
router.post('/menublock/:callSid', async (req, res) => {
|
|
290
|
-
winston.
|
|
291
|
-
winston.
|
|
409
|
+
winston.verbose("(voice) called POST /menu", req.body);
|
|
410
|
+
winston.verbose("(voice) called POST /menu query" , req.query);
|
|
292
411
|
|
|
293
412
|
let message_text = '';
|
|
294
413
|
let attributes = {};
|
|
@@ -390,7 +509,7 @@ router.post('/menublock/:callSid', async (req, res) => {
|
|
|
390
509
|
});
|
|
391
510
|
|
|
392
511
|
router.post('/handle/:callSid/:event', async (req, res) => {
|
|
393
|
-
winston.
|
|
512
|
+
winston.verbose("(voice) called POST /handle", req.body);
|
|
394
513
|
winston.debug("(voice) called POST /handle query -->", req.query);
|
|
395
514
|
winston.debug("(voice) called POST /handle params-->", req.params);
|
|
396
515
|
|
|
@@ -467,7 +586,7 @@ router.post('/handle/:callSid/:event', async (req, res) => {
|
|
|
467
586
|
|
|
468
587
|
/* ----> catch Event block <----- */
|
|
469
588
|
router.post('/event/:callSid/:event', async(req, res)=> {
|
|
470
|
-
winston.
|
|
589
|
+
winston.verbose("(voice) called POST /event" , req.params);
|
|
471
590
|
winston.debug("(voice) called POST /event query" , req.query);
|
|
472
591
|
winston.debug("(voice) called POST /event body" , req.body);
|
|
473
592
|
|
|
@@ -564,7 +683,7 @@ router.post('/event/:callSid/:event', async(req, res)=> {
|
|
|
564
683
|
|
|
565
684
|
/* ----> catch Twilio Events <----- */
|
|
566
685
|
router.post('/twilio/status',async (req, res) => {
|
|
567
|
-
winston.
|
|
686
|
+
winston.verbose('+++++++++++(voice) called POST twilio/status ', req.body);
|
|
568
687
|
|
|
569
688
|
let event = req.body.CallStatus;
|
|
570
689
|
let callSid = req.body.CallSid;
|
|
@@ -635,7 +754,7 @@ router.post('/twilio/status',async (req, res) => {
|
|
|
635
754
|
})
|
|
636
755
|
|
|
637
756
|
router.post('/twilio/fail',async (req, res) => {
|
|
638
|
-
winston.
|
|
757
|
+
winston.verbose('+++++++++++(voice) called POST twilio/fail ', req.params)
|
|
639
758
|
winston.debug('+++++++++++(voice) called POST twilio/fail ', req.body)
|
|
640
759
|
|
|
641
760
|
res.set('Content-Type', 'text/xml');
|
|
@@ -645,7 +764,7 @@ router.post('/twilio/fail',async (req, res) => {
|
|
|
645
764
|
|
|
646
765
|
/* ----> catch Twilio Events <----- */
|
|
647
766
|
router.post('/record/:callSid/',async (req, res) => {
|
|
648
|
-
winston.
|
|
767
|
+
winston.verbose('+++++++++++(voice) called POST record/:callSid ', req.body);
|
|
649
768
|
|
|
650
769
|
let callSid = req.body.CallSid;
|
|
651
770
|
|
|
@@ -729,7 +848,7 @@ router.post('/record/:callSid/',async (req, res) => {
|
|
|
729
848
|
|
|
730
849
|
|
|
731
850
|
router.get('/addon/transcript', async (req, res) => {
|
|
732
|
-
winston.
|
|
851
|
+
winston.verbose("(vxml) called GET /transcript query-->" , req.query);
|
|
733
852
|
winston.debug("(vxml) called GET /transcript body -->" , req.body);
|
|
734
853
|
|
|
735
854
|
res.status(200).send('ok');
|
|
@@ -738,7 +857,7 @@ router.get('/addon/transcript', async (req, res) => {
|
|
|
738
857
|
|
|
739
858
|
/** --> only for test purpose <-- **/
|
|
740
859
|
router.get('/test', async (req, res) => {
|
|
741
|
-
winston.
|
|
860
|
+
winston.verbose("(vxml) called GET /test" , req.query);
|
|
742
861
|
|
|
743
862
|
let project_id = req.query.id_project;
|
|
744
863
|
let callSid = req.body.CallSid;
|
|
@@ -827,7 +946,7 @@ router.get('/test', async (req, res) => {
|
|
|
827
946
|
type: 'wait',
|
|
828
947
|
time: 0
|
|
829
948
|
},
|
|
830
|
-
{
|
|
949
|
+
/*{
|
|
831
950
|
type: 'settings',
|
|
832
951
|
subType: 'blind_transfer',
|
|
833
952
|
settings: {
|
|
@@ -836,25 +955,26 @@ router.get('/test', async (req, res) => {
|
|
|
836
955
|
falseIntent: "#falseIntenttt",
|
|
837
956
|
trueIntent: "#trueIntennt"
|
|
838
957
|
}
|
|
839
|
-
}
|
|
958
|
+
}*/
|
|
840
959
|
/*{
|
|
841
960
|
type: 'settings',
|
|
842
961
|
subType: 'dtmf_form',
|
|
843
962
|
settings: {
|
|
844
963
|
minDigits: 5,
|
|
845
964
|
maxDigits: 5,
|
|
846
|
-
terminators: "#"
|
|
965
|
+
terminators: "#",
|
|
966
|
+
noInputIntent: "#a",
|
|
967
|
+
noInputTimeout: 2000,
|
|
847
968
|
}
|
|
848
969
|
}*/
|
|
849
|
-
|
|
970
|
+
{
|
|
850
971
|
type: 'settings',
|
|
851
972
|
subType: 'speech_form',
|
|
852
973
|
settings: {
|
|
853
974
|
noInputIntent: "#a",
|
|
854
975
|
noInputTimeout: 2000,
|
|
855
|
-
incompleteSpeechTimeout: 2000
|
|
856
976
|
}
|
|
857
|
-
}
|
|
977
|
+
}
|
|
858
978
|
]
|
|
859
979
|
}
|
|
860
980
|
}
|
package/package.json
CHANGED
package/tiledesk/KVBaseMongo.js
CHANGED
|
@@ -63,8 +63,7 @@ class KVBaseMongo {
|
|
|
63
63
|
return new Promise((resolve, reject) => {
|
|
64
64
|
//this.db.get(k).then(value => {resolve(value)});
|
|
65
65
|
|
|
66
|
-
winston.debug("Searching on " + this.
|
|
67
|
-
winston.verbose("Searching on Collection " + this.KV_COLLECTION + ' for key: ', k)
|
|
66
|
+
winston.debug("Searching on Collection " + this.KV_COLLECTION + ' for key: '+ k)
|
|
68
67
|
|
|
69
68
|
this.db.collection(this.KV_COLLECTION).findOne({ key: k }, function(err, doc) {
|
|
70
69
|
if (err) {
|
|
@@ -73,7 +72,7 @@ class KVBaseMongo {
|
|
|
73
72
|
}
|
|
74
73
|
else {
|
|
75
74
|
if (doc) {
|
|
76
|
-
winston.
|
|
75
|
+
winston.debug("Doc found with key: " + doc.key);
|
|
77
76
|
resolve(doc.value);
|
|
78
77
|
}
|
|
79
78
|
else {
|
|
@@ -179,7 +179,7 @@ class TiledeskChannel {
|
|
|
179
179
|
winston.debug("[TiledeskChannel] send message response: ", response.data);
|
|
180
180
|
return response.data;
|
|
181
181
|
}).catch((err) => {
|
|
182
|
-
winston.error("[TiledeskChannel] send message: ", err);
|
|
182
|
+
winston.error("[TiledeskChannel] send message: ", err.response?.data);
|
|
183
183
|
return null;
|
|
184
184
|
})
|
|
185
185
|
|
|
@@ -213,7 +213,6 @@ class TiledeskChannel {
|
|
|
213
213
|
})
|
|
214
214
|
|
|
215
215
|
const base64 = Buffer.from(stream.data, 'binary').toString('base64');
|
|
216
|
-
console.log('baseeeeeeee', base64)
|
|
217
216
|
return 'text'
|
|
218
217
|
|
|
219
218
|
|
|
@@ -258,17 +257,17 @@ class TiledeskChannel {
|
|
|
258
257
|
|
|
259
258
|
/*SKIP INFO MESSAGES*/
|
|
260
259
|
if(utils.messageType(TYPE_MESSAGE.INFO, message)){
|
|
261
|
-
winston.
|
|
260
|
+
winston.debug("> SKIPPING INFO message: " + JSON.stringify(message) );
|
|
262
261
|
return;
|
|
263
262
|
}
|
|
264
263
|
|
|
265
264
|
/*SKIP CURRENT USER MESSAGES*/
|
|
266
265
|
if (message.sender.indexOf(CHANNEL_NAME) > -1) {
|
|
267
|
-
winston.
|
|
266
|
+
winston.debug("> SKIPPING ECHO message: " + JSON.stringify(message) );
|
|
268
267
|
return;
|
|
269
268
|
}
|
|
270
269
|
|
|
271
|
-
winston.
|
|
270
|
+
winston.debug("> SAVE message TO QUEUE: " + JSON.stringify(message) );
|
|
272
271
|
/*SAVE MESSAGE TO QUEUE WITH KET tiledesk:queue:+conversation_id*/
|
|
273
272
|
let conversation_id = message.recipient
|
|
274
273
|
let redis_data = [ message ]
|
|
@@ -59,7 +59,7 @@ class TiledeskSubscriptionClient {
|
|
|
59
59
|
if (callback) {
|
|
60
60
|
callback(null, resbody);
|
|
61
61
|
}
|
|
62
|
-
winston.
|
|
62
|
+
winston.debug("[TiledeskSubscriptionClient] Subscribed");
|
|
63
63
|
resolve(resbody);
|
|
64
64
|
}
|
|
65
65
|
}, true);
|
|
@@ -92,7 +92,7 @@ class TiledeskSubscriptionClient {
|
|
|
92
92
|
if (callback) {
|
|
93
93
|
callback(null, resbody);
|
|
94
94
|
}
|
|
95
|
-
winston.
|
|
95
|
+
winston.debug("[TiledeskSubscriptionClient] Unsubscribed");
|
|
96
96
|
resolve(resbody);
|
|
97
97
|
}
|
|
98
98
|
}, true);
|
|
@@ -69,7 +69,7 @@ class TiledeskTwilioTranslator {
|
|
|
69
69
|
|
|
70
70
|
//MANAGE CLOSE info message
|
|
71
71
|
const isInfoSupport = utils.messageType(TYPE_MESSAGE.INFO_SUPPORT, msg)
|
|
72
|
-
winston.
|
|
72
|
+
winston.debug("[TiledeskVXMLTranslator] isInfoSupport:"+ isInfoSupport);
|
|
73
73
|
if(isInfoSupport && utils.infoMessageType(msg) === INFO_MESSAGE_TYPE.CHAT_CLOSED){
|
|
74
74
|
const hangUp = this.hangupCall(xml)
|
|
75
75
|
return hangUp;
|
|
@@ -83,7 +83,7 @@ class TiledeskTwilioTranslator {
|
|
|
83
83
|
|
|
84
84
|
/** check for WAIT **/
|
|
85
85
|
const isWait = this.checkIfIsWait(msg);
|
|
86
|
-
winston.
|
|
86
|
+
winston.debug("[TiledeskVXMLTranslator] toVXML: isWait:"+ isWait);
|
|
87
87
|
if(isWait){
|
|
88
88
|
const delayForm = await this.delayVXMLConverter(xml, msg, vxmlAttributes);
|
|
89
89
|
return delayForm;
|
|
@@ -91,7 +91,7 @@ class TiledeskTwilioTranslator {
|
|
|
91
91
|
|
|
92
92
|
/** check for DTMF FORM **/
|
|
93
93
|
const isDtmfForm = this.checkIfIsDTMFForm(msg);
|
|
94
|
-
winston.
|
|
94
|
+
winston.debug("[TiledeskVXMLTranslator] toVXML: isDtmfForm: "+ isDtmfForm);
|
|
95
95
|
if(isDtmfForm){
|
|
96
96
|
const DTMFForm = await this.dtmfFormVXMLConverter(xml, msg, vxmlAttributes);
|
|
97
97
|
return DTMFForm;
|
|
@@ -99,7 +99,7 @@ class TiledeskTwilioTranslator {
|
|
|
99
99
|
|
|
100
100
|
/** check for BLIND TRANSFER **/
|
|
101
101
|
const isBlindFransfer = this.checkIfIsBlindFransfer(msg);
|
|
102
|
-
winston.
|
|
102
|
+
winston.debug("[TiledeskVXMLTranslator] toVXML: isBlindFransfer: "+ isBlindFransfer);
|
|
103
103
|
if(isBlindFransfer){
|
|
104
104
|
const blindTransfer = await this.blindTransferVXMLConverter(xml, msg, vxmlAttributes);
|
|
105
105
|
return blindTransfer;
|
|
@@ -107,7 +107,7 @@ class TiledeskTwilioTranslator {
|
|
|
107
107
|
|
|
108
108
|
/** check for DTMF MENU **/
|
|
109
109
|
const isMenu = this.checkIfIsDTMFMenuMessage(msg);
|
|
110
|
-
winston.
|
|
110
|
+
winston.debug("[TiledeskVXMLTranslator] toVXML: isMenu: "+ isMenu);
|
|
111
111
|
if(isMenu){
|
|
112
112
|
const menu = await this.menuVXMLConverter(xml, msg, vxmlAttributes);
|
|
113
113
|
return menu;
|
|
@@ -115,14 +115,14 @@ class TiledeskTwilioTranslator {
|
|
|
115
115
|
|
|
116
116
|
/** check for SPEECH FORM **/
|
|
117
117
|
const isSpeechForm = this.checkIfIsSpeechFormMessage(msg);
|
|
118
|
-
winston.
|
|
118
|
+
winston.debug("[TiledeskVXMLTranslator] toVXML: isSpeechForm: "+ isSpeechForm);
|
|
119
119
|
if(isSpeechForm){
|
|
120
120
|
const form = await this.speechFormVXMLConverter(xml, msg, vxmlAttributes);
|
|
121
121
|
return form;
|
|
122
122
|
}
|
|
123
123
|
|
|
124
124
|
/** check for FORM (PlayPrompt action) **/
|
|
125
|
-
winston.
|
|
125
|
+
winston.debug("[TiledeskVXMLTranslator] toVXML: isPrompt: true");
|
|
126
126
|
const prompt = await this.playPromptVXMLConverter(xml, msg, vxmlAttributes);
|
|
127
127
|
return prompt;
|
|
128
128
|
|
|
@@ -263,21 +263,24 @@ class TiledeskTwilioTranslator {
|
|
|
263
263
|
|
|
264
264
|
const gather = rootEle.ele("Gather", { input: "speech"})
|
|
265
265
|
|
|
266
|
-
if(xmlAttributes && xmlAttributes.noInputTimeout){
|
|
267
|
-
gather.att("timeout", xmlAttributes.noInputTimeout/1000 ).up();
|
|
268
|
-
}
|
|
269
|
-
|
|
270
266
|
const queryUrl = '?intentName='+ querystring.encode(xmlAttributes.intentName) + "&previousIntentTimestamp="+Date.now();
|
|
271
|
-
gather.att("action", this.BASE_URL + '/
|
|
267
|
+
gather.att("action", this.BASE_URL + '/speechresult/' + xmlAttributes.callSid + queryUrl)
|
|
272
268
|
.att("method", "POST")
|
|
273
269
|
.att("language", xmlAttributes.voiceLanguage)
|
|
270
|
+
.att('speechTimeout', "auto")
|
|
274
271
|
|
|
272
|
+
if(xmlAttributes && xmlAttributes.noInputTimeout){
|
|
273
|
+
gather.att("timeout", xmlAttributes.noInputTimeout/1000 ).up();
|
|
274
|
+
}
|
|
275
|
+
/*if(xmlAttributes && xmlAttributes.incompleteSpeechTimeout){
|
|
276
|
+
gather.att("speechTimeout", xmlAttributes.incompleteSpeechTimeout/1000 ).up();
|
|
277
|
+
}*/
|
|
275
278
|
|
|
276
279
|
const prompt = this.promptVXML(gather, message, xmlAttributes);
|
|
277
280
|
|
|
278
281
|
const handleNoInputNoMatchQuery = await this.handleNoInputNoMatch(rootEle, message, xmlAttributes);
|
|
279
282
|
if(handleNoInputNoMatchQuery && handleNoInputNoMatchQuery.queryNoInput){
|
|
280
|
-
rootEle.ele("Redirect", {}, this.BASE_URL + '/handle/' + xmlAttributes.callSid + '/no_input?'+ handleNoInputNoMatchQuery.queryNoInput)
|
|
283
|
+
rootEle.ele("Redirect", {method: "POST"}, this.BASE_URL + '/handle/' + xmlAttributes.callSid + '/no_input?'+ handleNoInputNoMatchQuery.queryNoInput)
|
|
281
284
|
}
|
|
282
285
|
|
|
283
286
|
|
|
@@ -355,7 +358,7 @@ class TiledeskTwilioTranslator {
|
|
|
355
358
|
|
|
356
359
|
const handleNoInputNoMatchQuery = await this.handleNoInputNoMatch(rootEle, message, xmlAttributes);
|
|
357
360
|
if(handleNoInputNoMatchQuery && handleNoInputNoMatchQuery.queryNoInput){
|
|
358
|
-
rootEle.ele("Redirect", {}, this.BASE_URL + '/handle/' + xmlAttributes.callSid + '/no_input?'+ handleNoInputNoMatchQuery.queryNoInput)
|
|
361
|
+
rootEle.ele("Redirect", {method: "POST"}, this.BASE_URL + '/handle/' + xmlAttributes.callSid + '/no_input?'+ handleNoInputNoMatchQuery.queryNoInput)
|
|
359
362
|
}
|
|
360
363
|
|
|
361
364
|
//.ele('disconnect')
|