@tiledesk/tiledesk-server 2.2.39 → 2.3.1-8.2

Sign up to get free protection for your applications and to get access to all the features.
Files changed (93) hide show
  1. package/CHANGELOG.md +121 -0
  2. package/LICENSE +14 -657
  3. package/README.md +17 -3
  4. package/app.js +21 -60
  5. package/channels/chat21/chat21Handler.js +18 -3
  6. package/channels/chat21/chat21WebHook.js +31 -15
  7. package/channels/chat21/package-lock.json +663 -706
  8. package/channels/chat21/package.json +2 -2
  9. package/deploy.sh +2 -0
  10. package/event/botEvent.js +1 -1
  11. package/event/subscriptionEvent.js +11 -0
  12. package/fonts/Roboto-Italic.ttf +0 -0
  13. package/fonts/Roboto-Medium.ttf +0 -0
  14. package/fonts/Roboto-MediumItalic.ttf +0 -0
  15. package/fonts/Roboto-Regular.ttf +0 -0
  16. package/middleware/ipFilter.js +220 -0
  17. package/middleware/passport.js +11 -2
  18. package/models/lead.js +2 -0
  19. package/models/project.js +10 -0
  20. package/models/project_user.js +4 -0
  21. package/models/request.js +50 -12
  22. package/models/subscriptionLog.js +34 -0
  23. package/models/tagLibrary.js +42 -0
  24. package/package.json +6 -12
  25. package/pubmodules/activities/activityArchiver.js +314 -0
  26. package/pubmodules/activities/index.js +3 -0
  27. package/pubmodules/activities/models/activity.js +88 -0
  28. package/pubmodules/activities/routes/activity.js +710 -0
  29. package/pubmodules/activities/test/activityRoute.js +85 -0
  30. package/pubmodules/analytics/analytics.js +1719 -0
  31. package/pubmodules/analytics/index.js +3 -0
  32. package/pubmodules/canned/cannedResponse.js +55 -0
  33. package/pubmodules/canned/cannedResponseRoute.js +163 -0
  34. package/pubmodules/canned/index.js +3 -0
  35. package/pubmodules/emailNotification/requestNotification.js +215 -28
  36. package/pubmodules/events/eventRoute.js +37 -7
  37. package/pubmodules/messageActions/messageActionsInterceptor.js +4 -2
  38. package/pubmodules/pubModulesManager.js +129 -5
  39. package/pubmodules/rasa/listener.js +5 -5
  40. package/pubmodules/rules/conciergeBot.js +4 -4
  41. package/pubmodules/scheduler/tasks/closeAgentUnresponsiveRequestTask.js +3 -1
  42. package/pubmodules/scheduler/tasks/closeBotUnresponsiveRequestTask.js +3 -1
  43. package/pubmodules/tilebot/index.js +11 -0
  44. package/pubmodules/tilebot/listener.js +69 -0
  45. package/pubmodules/trigger/default.js +271 -0
  46. package/pubmodules/trigger/event/actionEventEmitter.js +10 -0
  47. package/pubmodules/trigger/event/flowEventEmitter.js +10 -0
  48. package/pubmodules/trigger/event/triggerEventEmitter.js +10 -0
  49. package/pubmodules/trigger/index.js +3 -0
  50. package/pubmodules/trigger/models/trigger.js +149 -0
  51. package/pubmodules/trigger/rulesTrigger.js +1181 -0
  52. package/pubmodules/trigger/start.js +118 -0
  53. package/pubmodules/trigger/triggerRoute.js +150 -0
  54. package/routes/auth.js +7 -2
  55. package/routes/department.js +51 -0
  56. package/routes/faq.js +7 -0
  57. package/routes/faq_kb.js +1 -1
  58. package/routes/group.js +140 -0
  59. package/routes/lead.js +24 -1
  60. package/routes/message.js +6 -3
  61. package/routes/project.js +118 -0
  62. package/routes/project_user.js +9 -0
  63. package/routes/public-request.js +280 -2
  64. package/routes/request.js +122 -16
  65. package/routes/subscription.js +140 -0
  66. package/routes/tag.js +138 -0
  67. package/routes/user-request.js +3 -2
  68. package/routes/users.js +1 -1
  69. package/routes/widget.js +80 -3
  70. package/routes/widgetLoader.js +31 -0
  71. package/services/banUserNotifier.js +86 -0
  72. package/services/emailService.js +189 -11
  73. package/services/faqService.js +2 -2
  74. package/services/geoService.js +30 -4
  75. package/services/leadService.js +2 -0
  76. package/services/modulesManager.js +7 -188
  77. package/services/requestService.js +364 -6
  78. package/services/subscriptionNotifier.js +485 -0
  79. package/template/email/assignedEmailMessage.html +1 -1
  80. package/template/email/assignedRequest.html +1 -1
  81. package/template/email/newMessage.html +1 -1
  82. package/template/email/newMessageFollower.html +236 -0
  83. package/template/email/passwordChanged.html +1 -1
  84. package/template/email/pooledEmailMessage.html +1 -1
  85. package/template/email/pooledRequest.html +1 -1
  86. package/template/email/resetPassword.html +2 -2
  87. package/template/email/ticket.html +1 -1
  88. package/test/cannedRoute.js +166 -0
  89. package/test/messageRoute.js +69 -0
  90. package/test/requestService.js +3 -1
  91. package/utils/orgUtil.js +3 -3
  92. package/views/messages.jade +2 -2
  93. package/websocket/webSocketServer.js +23 -5
@@ -0,0 +1,485 @@
1
+ var Subscription = require('../models/subscription');
2
+ var SubscriptionLog = require('../models/subscriptionLog');
3
+ const requestEvent = require('../event/requestEvent');
4
+ const messageEvent = require('../event/messageEvent');
5
+ const message2Event = require('../event/message2Event');
6
+ const leadEvent = require('../event/leadEvent');
7
+ const botEvent = require('../event/botEvent');
8
+ const authEvent = require('../event/authEvent');
9
+ const departmentEvent = require('../event/departmentEvent');
10
+ const groupEvent = require('../event/groupEvent');
11
+ const faqBotEvent = require('../event/faqBotEvent');
12
+ const eventEvent = require('../pubmodules/events/eventEvent');
13
+ const event2Event = require('../pubmodules/events/event2Event');
14
+ const projectEvent = require('../event/projectEvent');
15
+
16
+ // var Request = require("../models/request");
17
+ var Message = require("../models/message");
18
+ // var Faq_kb = require("../models/faq_kb");
19
+ var winston = require('../config/winston');
20
+ var jwt = require('jsonwebtoken');
21
+ var config = require('../config/database'); // get db config file
22
+ var cacheUtil = require("../utils/cacheUtil");
23
+
24
+
25
+ var webhook_origin = process.env.WEBHOOK_ORIGIN || "http://localhost:3000";
26
+ winston.debug("webhook_origin: "+webhook_origin);
27
+
28
+
29
+ var request = require('retry-request', {
30
+ request: require('request')
31
+ });
32
+
33
+ class SubscriptionNotifier {
34
+ // var SubscriptionNotifier = {
35
+
36
+
37
+ findSubscriber(event, id_project) {
38
+ return new Promise(function (resolve, reject) {
39
+ Subscription.find({event:event, $or:[{id_project: id_project}, {global: true}]})
40
+ .cache(cacheUtil.longTTL, id_project+":subscriptions:event:"+event)
41
+ .select("+secret +global")
42
+ .exec(function (err, subscriptions) {
43
+ // if (subscriptions && subscriptions.length>0) {
44
+ // winston.debug("Subscription.notify", event, item , "length", subscriptions.length);
45
+ // }
46
+ resolve(subscriptions);
47
+ });
48
+ });
49
+ }
50
+
51
+ notify(subscriptions, payload, callback) {
52
+ // winston.debug("Subscription.notify", event, item);
53
+
54
+ // Subscription.find({event:event, id_project: item.id_project}).exec(function (err, subscriptions) {
55
+ // if (subscriptions && subscriptions.length>0) {
56
+ // winston.debug("Subscription.notify", event, item , "length", subscriptions.length);
57
+ // }
58
+
59
+
60
+ //var json = {event: event, timestamp: Date.now(), payload: item};
61
+ winston.debug("subscriptions",subscriptions);
62
+ var json = {timestamp: Date.now(), payload: payload};
63
+ subscriptions.forEach(function(s) {
64
+
65
+ // winston.debug("s",s);
66
+ var secret = s.secret;
67
+
68
+ let sJson = s.toObject();
69
+ delete sJson.secret;
70
+ delete sJson.global;
71
+
72
+ json["hook"] = sJson;
73
+
74
+
75
+
76
+ var signOptions = {
77
+ issuer: 'https://tiledesk.com',
78
+ subject: 'subscription',
79
+ audience: 'https://tiledesk.com/subscriptions/'+s._id,
80
+ };
81
+
82
+ if (s.global==true){
83
+ signOptions.audience = 'https://tiledesk.com';
84
+ secret = config.secret;
85
+ }
86
+
87
+ var token = jwt.sign(sJson, secret, signOptions);
88
+ json["token"] = token;
89
+
90
+
91
+ // for sync use no retry
92
+
93
+ request({
94
+ url: s.target,
95
+ headers: {
96
+ 'Content-Type' : 'application/json',
97
+ 'x-hook-secret': secret,
98
+ 'User-Agent': 'tiledesk-webhooks',
99
+ 'Origin': webhook_origin
100
+ },
101
+ json: json,
102
+ method: 'POST'
103
+
104
+ }, function(err, response, json){
105
+ winston.debug("SENT " + s.event + " TO " + s.target, "with error " , err);
106
+ winston.debug("SubscriptionLog response", response);
107
+ winston.debug("SubscriptionLog json", json);
108
+
109
+ var subscriptionLog = new SubscriptionLog({event: s.event, target: s.target,
110
+ response: JSON.stringify(response),
111
+ body: JSON.stringify(json),
112
+ err: err, id_project:s.id_project});
113
+
114
+ subscriptionLog.save(function (errSL, sl) {
115
+ if (errSL) {
116
+ winston.error("Error saving subscriptionLog", errSL);
117
+ return 0;
118
+ }
119
+ winston.debug("SubscriptionLog saved", sl);
120
+ });
121
+
122
+ if (err) {
123
+ winston.error("Error sending webhook for event " + s.event + " TO " + s.target, "with error " , err);
124
+ if (callback) {
125
+ callback(err, json);
126
+ }
127
+
128
+ }
129
+ //return
130
+ // console.log("callback qui1", callback);
131
+ if (callback) {
132
+ // console.log("callback qui", json);
133
+ callback(null, json);
134
+ }
135
+
136
+ });
137
+ });
138
+ // });
139
+ }
140
+ // https://mongoosejs.com/docs/middleware.html#post-async
141
+ decorate(model, modelName) {
142
+ var isNew = false;
143
+
144
+ model.pre('save', function(next) {
145
+ isNew = this.isNew;
146
+ winston.debug("Subscription.notify.pre (isNew)", isNew);
147
+
148
+ return next();
149
+ });
150
+
151
+ //winston.debug("decorate");
152
+ // .afterCreate = function(item, next) {
153
+ model.post('save', function(doc, next) {
154
+
155
+ // If we have isNew flag then it's an update
156
+ var event = (isNew) ? 'create' : 'update';
157
+ winston.debug("Subscription.notify."+event);
158
+ next(null, doc);
159
+ SubscriptionNotifier.notify(modelName+'.'+event, doc);
160
+ });
161
+
162
+ // model.afterUpdate = function(item, next) {
163
+ // next(null, item);
164
+ // SubscriptionNotifier.notify(modelName+'.update', item);
165
+ // }
166
+
167
+ // model.afterDestroy = function(next) {
168
+ // next();
169
+ // SubscriptionNotifier.notify(modelName+'.delete', {});
170
+ // }
171
+ }
172
+
173
+ start() {
174
+ winston.debug('SubscriptionNotifier start');
175
+
176
+ var enabled = process.env.RESTHOOK_ENABLED || "false";
177
+ winston.debug('SubscriptionNotifier enabled:'+enabled);
178
+
179
+ if (enabled==="true") {
180
+ winston.debug('SubscriptionNotifier enabled');
181
+ }else {
182
+ winston.info('Resthook disabled');
183
+ return 0;
184
+ }
185
+
186
+
187
+ messageEvent.on('message.create', function(message) {
188
+ setImmediate(() => {
189
+ subscriptionNotifier.subscribe('message.create', message);
190
+ });
191
+ });
192
+
193
+ message2Event.on('message.create.**.channel.*', function(message) {
194
+ // message2Event.on('message.create.request.channel.*', function(message) {
195
+ winston.debug("message2Event: "+this.event, message);
196
+ subscriptionNotifier.subscribe(this.event, message);
197
+ }, {async: true});
198
+
199
+
200
+
201
+ // messageEvent.on('message.received.for.bot', function(message) {
202
+ // setImmediate(() => {
203
+ // subscriptionNotifier.subscribe('message.received.for.bot', message);
204
+ // });
205
+ // });
206
+
207
+ // messageEvent.on('message.received', function(message) {
208
+ // setImmediate(() => {
209
+ // subscriptionNotifier.subscribe('message.received', message);
210
+ // });
211
+ // });
212
+ // messageEvent.on('message.sending', function(message) {
213
+ // setImmediate(() => {
214
+ // subscriptionNotifier.subscribe('message.sending', message);
215
+ // });
216
+ // });
217
+
218
+
219
+ requestEvent.on('request.create', function(request) {
220
+ setImmediate(() => {
221
+ subscriptionNotifier.subscribe('request.create', request);
222
+ });
223
+ });
224
+
225
+ requestEvent.on('request.update', function(request) {
226
+ setImmediate(() => {
227
+ subscriptionNotifier.subscribe('request.update', request);
228
+ });
229
+ });
230
+
231
+ requestEvent.on('request.close', function(request) {
232
+ setImmediate(() => {
233
+ Message.find({recipient: request.request_id, id_project: request.id_project}).sort({updatedAt: 'asc'}).exec(function(err, messages) {
234
+ var requestJson = request.toJSON();
235
+ requestJson.messages = messages;
236
+ subscriptionNotifier.subscribe('request.close', requestJson);
237
+ });
238
+ });
239
+ });
240
+
241
+
242
+ leadEvent.on('lead.create', function(lead) {
243
+ setImmediate(() => {
244
+ subscriptionNotifier.subscribe('lead.create', lead);
245
+ });
246
+ });
247
+
248
+
249
+ botEvent.on('faqbot.create', function(faqBot) {
250
+ setImmediate(() => {
251
+ subscriptionNotifier.subscribe('faqbot.create', faqBot);
252
+ });
253
+ });
254
+
255
+ botEvent.on('faqbot.update', function(faqBot) {
256
+ setImmediate(() => {
257
+ subscriptionNotifier.subscribe('faqbot.update', faqBot);
258
+ });
259
+ });
260
+
261
+ botEvent.on('faqbot.delete', function(faqBot) {
262
+ setImmediate(() => {
263
+ subscriptionNotifier.subscribe('faqbot.delete', faqBot);
264
+ });
265
+ });
266
+
267
+ faqBotEvent.on('faq.create', function(faq) {
268
+ setImmediate(() => {
269
+ subscriptionNotifier.subscribe('faq.create', faq);
270
+ });
271
+ });
272
+
273
+ faqBotEvent.on('faq.update', function(faq) {
274
+ setImmediate(() => {
275
+ subscriptionNotifier.subscribe('faq.update', faq);
276
+ });
277
+ });
278
+ faqBotEvent.on('faq.delete', function(faq) {
279
+ setImmediate(() => {
280
+ subscriptionNotifier.subscribe('faq.delete', faq);
281
+ });
282
+ });
283
+
284
+ authEvent.on('user.signup', function(event) {
285
+ setImmediate(() => {
286
+ var user = event.savedUser;
287
+ delete user.password;
288
+
289
+ subscriptionNotifier.subscribe('user.signup', user);
290
+ });
291
+ });
292
+
293
+
294
+ // authEvent.emit('project_user.invite', {req:req, savedProject_userPopulated: savedProject_userPopulated});
295
+
296
+ authEvent.on('project_user.invite', function(event) {
297
+ setImmediate(() => {
298
+ subscriptionNotifier.subscribe('project_user.invite', event.savedProject_userPopulated);
299
+ });
300
+ });
301
+
302
+ // authEvent.emit('project_user.update', {updatedProject_userPopulated:updatedProject_userPopulated, req: req});
303
+
304
+ authEvent.on('project_user.update', function(event) {
305
+ setImmediate(() => {
306
+ subscriptionNotifier.subscribe('project_user.update', event.updatedProject_userPopulated);
307
+ });
308
+ });
309
+
310
+ // authEvent.emit('project_user.delete', {req: req, project_userPopulated: project_userPopulated});
311
+
312
+ authEvent.on('project_user.delete', function(event) {
313
+ setImmediate(() => {
314
+ subscriptionNotifier.subscribe('project_user.delete', event.project_userPopulated);
315
+ });
316
+ });
317
+
318
+
319
+ //TODO lanciare user.signin in questo modo uno esternamente con webhook può creare proactive greetings
320
+
321
+ departmentEvent.on('operator.select', function(result) {
322
+ winston.debug("departmentEvent.on(operator.select");
323
+
324
+ var operatorSelectedEvent = result.result;
325
+ var resolve = result.resolve;
326
+ var reject = result.reject;
327
+
328
+ // aggiungere context. lascio lo passso già a result.result
329
+ // operatorSelectedEvent["context"] = result.context;
330
+
331
+ var disableWebHookCall = result.disableWebHookCall;
332
+ winston.debug("subscriptionNotifier disableWebHookCall: "+ disableWebHookCall);
333
+
334
+ if (disableWebHookCall === true) {
335
+ winston.debug("subscriptionNotifier disableWebHookCall enabled: "+ disableWebHookCall);
336
+ return resolve(operatorSelectedEvent);
337
+ }
338
+ subscriptionNotifier.subscribe('operator.select', operatorSelectedEvent, function(err, json) {
339
+ winston.debug("qui callback",json, err);
340
+ if (err) {
341
+ if (err.code == 404) {
342
+ winston.debug("call resolve default resolve because not found", err);
343
+ }else {
344
+ winston.warn("call resolve default resolve because err", err);
345
+ }
346
+ return resolve(operatorSelectedEvent);
347
+ }
348
+ if (json && json.operators) {
349
+ winston.verbose("call resolve valid json", json);
350
+ return resolve(json);
351
+ }else {
352
+ winston.verbose("call resolve default resolve");
353
+ return resolve(operatorSelectedEvent);
354
+ }
355
+
356
+ });
357
+ });
358
+
359
+
360
+ departmentEvent.on('department.create', function(department) {
361
+ setImmediate(() => {
362
+ subscriptionNotifier.subscribe('department.create', department);
363
+ });
364
+ });
365
+
366
+
367
+ departmentEvent.on('department.update', function(department) {
368
+ setImmediate(() => {
369
+ subscriptionNotifier.subscribe('department.update', department);
370
+ });
371
+ });
372
+
373
+ departmentEvent.on('department.delete', function(department) {
374
+ setImmediate(() => {
375
+ subscriptionNotifier.subscribe('department.delete', department);
376
+ });
377
+ });
378
+
379
+
380
+ groupEvent.on('group.create', function(group) {
381
+ setImmediate(() => {
382
+ subscriptionNotifier.subscribe('group.create', group);
383
+ });
384
+ });
385
+
386
+
387
+ groupEvent.on('group.update', function(group) {
388
+ setImmediate(() => {
389
+ subscriptionNotifier.subscribe('group.update', group);
390
+ });
391
+ });
392
+
393
+ groupEvent.on('group.delete', function(group) {
394
+ setImmediate(() => {
395
+ subscriptionNotifier.subscribe('group.delete', group);
396
+ });
397
+ });
398
+
399
+ eventEvent.on('event.emit', function(event) {
400
+ setImmediate(() => {
401
+ subscriptionNotifier.subscribe('event.emit', event);
402
+ });
403
+ });
404
+
405
+ // event2Event.on(name, savedEventPopulated);
406
+ event2Event.on('**', function(savedEventPopulated) {
407
+ setImmediate(() => {
408
+ winston.debug("eventname",this.event);
409
+ subscriptionNotifier.subscribe('event.emit.'+this.event, savedEventPopulated);
410
+ });
411
+ });
412
+
413
+
414
+ projectEvent.on('project.create', function(project) {
415
+ setImmediate(() => {
416
+ var projectJson = project.toJSON();
417
+ projectJson.id_project = projectJson._id;
418
+ subscriptionNotifier.subscribe('project.create', projectJson);
419
+ });
420
+ });
421
+
422
+ projectEvent.on('project.update', function(project) {
423
+ setImmediate(() => {
424
+ var projectJson = project.toJSON();
425
+ projectJson.id_project = projectJson._id;
426
+ subscriptionNotifier.subscribe('project.update', projectJson);
427
+ });
428
+ });
429
+
430
+ projectEvent.on('project.downgrade', function(project) {
431
+ setImmediate(() => {
432
+ var projectJson = project.toJSON();
433
+ projectJson.id_project = projectJson._id;
434
+ subscriptionNotifier.subscribe('project.downgrade', projectJson);
435
+ });
436
+ });
437
+
438
+ projectEvent.on('project.delete', function(project) {
439
+ setImmediate(() => {
440
+ var projectJson = project.toJSON();
441
+ projectJson.id_project = projectJson._id;
442
+ subscriptionNotifier.subscribe('project.delete', projectJson);
443
+ });
444
+ });
445
+
446
+
447
+
448
+
449
+ // tagEvent.webhook for pypestream
450
+
451
+
452
+ // TODO add user events
453
+
454
+ winston.info('SubscriptionNotifier started');
455
+ }
456
+
457
+
458
+ subscribe(eventName, payload, callback ) {
459
+ winston.debug("Subscription.notify");
460
+ // findSubscriber(event, id_project)
461
+ subscriptionNotifier.findSubscriber(eventName, payload.id_project).then(function(subscriptions) {
462
+ //winston.debug("Subscription.notify subscriptionNotifier", subscriptions.length);
463
+ if (subscriptions && subscriptions.length>0) {
464
+ winston.debug("Subscription.notify", eventName, payload , "length", subscriptions.length);
465
+ subscriptionNotifier.notify(subscriptions, payload, callback);
466
+ } else {
467
+ if (callback) {
468
+ var err = {msg:"No subscriptions found", code:404};
469
+ callback(err, undefined);
470
+ }
471
+ }
472
+ });
473
+
474
+ }
475
+
476
+
477
+
478
+ };
479
+
480
+ var subscriptionNotifier = new SubscriptionNotifier();
481
+
482
+ // winston.debug('messageEvent', messageEvent);
483
+
484
+
485
+ module.exports = subscriptionNotifier;
@@ -82,7 +82,7 @@
82
82
 
83
83
  <div style="text-align:center">
84
84
  <a href="http://www.tiledesk.com" style="color:#2daae1;font-weight:bold;text-decoration:none;word-break:break-word" target="_blank">
85
- <img src="https://tiledesk.com/tiledesk-logo-x1.png" style="width:10%;outline:none;text-decoration:none;border:none;min-height:36px" class="CToWUd">
85
+ <img src="https://tiledesk.com/wp-content/uploads/2022/07/tiledesk_v2.png" style="width:10%;outline:none;text-decoration:none;border:none;min-height:36px" class="CToWUd">
86
86
  </a>
87
87
  </div>
88
88
  </tr>
@@ -82,7 +82,7 @@
82
82
 
83
83
  <div style="text-align:center">
84
84
  <a href="http://www.tiledesk.com" style="color:#2daae1;font-weight:bold;text-decoration:none;word-break:break-word" target="_blank">
85
- <img src="https://tiledesk.com/tiledesk-logo-x1.png" style="width:10%;outline:none;text-decoration:none;border:none;min-height:36px" class="CToWUd">
85
+ <img src="https://tiledesk.com/wp-content/uploads/2022/07/tiledesk_v2.png" style="width:10%;outline:none;text-decoration:none;border:none;min-height:36px" class="CToWUd">
86
86
  </a>
87
87
  </div>
88
88
  </tr>
@@ -80,7 +80,7 @@
80
80
 
81
81
  <div style="text-align:center">
82
82
  <a href="http://www.tiledesk.com" style="color:#2daae1;font-weight:bold;text-decoration:none;word-break:break-word" target="_blank">
83
- <img src="https://tiledesk.com/tiledesk-logo-x1.png" style="width:10%;outline:none;text-decoration:none;border:none;min-height:36px" class="CToWUd">
83
+ <img src="https://tiledesk.com/wp-content/uploads/2022/07/tiledesk_v2.png" style="width:10%;outline:none;text-decoration:none;border:none;min-height:36px" class="CToWUd">
84
84
  </a>
85
85
  </div>
86
86
  </tr>