new(whatsapp.gblib): New WhatsApp provider: Meta.

This commit is contained in:
Rodrigo Rodriguez 2024-04-28 00:28:47 -03:00
parent 3e9170d446
commit 37d9028f98
3 changed files with 88 additions and 43 deletions
package.json
packages
core.gbapp/services
whatsapp.gblib/services

View file

@ -214,6 +214,7 @@
"vm2-process": "2.1.1", "vm2-process": "2.1.1",
"walk-promise": "0.2.0", "walk-promise": "0.2.0",
"washyourmouthoutwithsoap": "1.0.2", "washyourmouthoutwithsoap": "1.0.2",
"whatsapp-cloud-api": "^0.3.1",
"whatsapp-web.js": "https://github.com/Julzk/whatsapp-web.js/tarball/jkr_hotfix_7", "whatsapp-web.js": "https://github.com/Julzk/whatsapp-web.js/tarball/jkr_hotfix_7",
"winston": "3.8.2", "winston": "3.8.2",
"ws": "8.14.2", "ws": "8.14.2",

View file

@ -442,9 +442,24 @@ export class GBMinService {
// Setups official handler for WhatsApp. // Setups official handler for WhatsApp.
GBServer.globals.server.post(`/${min.instance.botId}/whatsapp`, async (req, res) => { GBServer.globals.server.all(`/${min.instance.botId}/whatsapp`, async (req, res) => {
if (req.query['hub.mode'] === 'subscribe') {
const val = req.query['hub.challenge'];
res.send(val);
return;
}
let whatsAppDirectLine = min.whatsAppDirectLine;
// Not meta, multiples bots on root bot.
if (!req.body.object) {
const to = req.body.To.replace(/whatsapp\:\+/gi, ''); const to = req.body.To.replace(/whatsapp\:\+/gi, '');
const whatsAppDirectLine = WhatsappDirectLine.botsByNumber[to]; whatsAppDirectLine = WhatsappDirectLine.botsByNumber[to];
}
await whatsAppDirectLine.WhatsAppCallback(req, res, whatsAppDirectLine.botId); await whatsAppDirectLine.WhatsAppCallback(req, res, whatsAppDirectLine.botId);
}).bind(min); }).bind(min);
@ -455,6 +470,11 @@ export class GBMinService {
if (!res) { if (!res) {
return 'GeneralBots'; return 'GeneralBots';
} }
if (req.body.entry) {
return 'meta';
}
if (req.body?.AccountSid) { if (req.body?.AccountSid) {
return 'official'; return 'official';
} }
@ -1643,8 +1663,7 @@ export class GBMinService {
let ret = await GBVMService.callVM(script, min, null, pid, false, data); let ret = await GBVMService.callVM(script, min, null, pid, false, data);
if (script === 'start') if (script === 'start') {
{
ret = pid; ret = pid;
} }
return ret; return ret;

View file

@ -54,7 +54,7 @@ const { WAState, Client, MessageMedia } = pkg;
import twilio from 'twilio'; import twilio from 'twilio';
import { GBVMService } from '../../basic.gblib/services/GBVMService.js'; import { GBVMService } from '../../basic.gblib/services/GBVMService.js';
import { GBLogEx } from '../../core.gbapp/services/GBLogEx.js'; import { GBLogEx } from '../../core.gbapp/services/GBLogEx.js';
import { createBot } from 'whatsapp-cloud-api';
/** /**
* Support for Whatsapp. * Support for Whatsapp.
@ -103,9 +103,8 @@ export class WhatsappDirectLine extends GBService {
this.whatsappServiceKey = whatsappServiceKey; this.whatsappServiceKey = whatsappServiceKey;
this.whatsappServiceNumber = whatsappServiceNumber; this.whatsappServiceNumber = whatsappServiceNumber;
this.whatsappServiceUrl = whatsappServiceUrl; this.whatsappServiceUrl = whatsappServiceUrl;
this.provider = this.provider = whatsappServiceKey === 'internal'
whatsappServiceKey === 'internal' ? 'GeneralBots' : 'meta';
? 'GeneralBots' : 'official';
this.groupId = groupId; this.groupId = groupId;
} }
@ -253,12 +252,8 @@ export class WhatsappDirectLine extends GBService {
} }
} }
public static providerFromRequest(req: any) {
return req.body.ProfileName ? 'official' : 'GeneralBots';
}
public async received(req, res) { public async received(req, res) {
const provider = WhatsappDirectLine.providerFromRequest(req); const provider = GBMinService.getProviderName(req, res);
let message, to, from, fromName, text: string; let message, to, from, fromName, text: string;
let group = ''; let group = '';
@ -266,7 +261,13 @@ export class WhatsappDirectLine extends GBService {
let attachments = null; let attachments = null;
switch (provider) { switch (provider) {
case 'meta':
from = req.body.entry[0].changes[0].value.messages[0].from;
text = req.body.entry[0].changes[0].value.messages[0].text.body
to = this.min.core.getParam<string>(this.min.instance, 'Bot Number', null);
fromName = req.body.entry[0].changes[0].value.contacts[0].profile.name;
break;
case 'official': case 'official':
message = req.body; message = req.body;
from = req.body.From.replace(/whatsapp\:\+/gi, ''); from = req.body.From.replace(/whatsapp\:\+/gi, '');
@ -512,7 +513,7 @@ export class WhatsappDirectLine extends GBService {
} }
WhatsappDirectLine.mobiles[generatedConversationId] = from; WhatsappDirectLine.mobiles[generatedConversationId] = from;
WhatsappDirectLine.usernames[from] = fromName; WhatsappDirectLine.usernames[from] = fromName;
WhatsappDirectLine.chatIds[generatedConversationId] = message.chatId; WhatsappDirectLine.chatIds[generatedConversationId] = message?.chatId;
this.pollMessages(client, generatedConversationId, from, fromName); this.pollMessages(client, generatedConversationId, from, fromName);
this.inputMessage(client, generatedConversationId, text, from, fromName, group, attachments); this.inputMessage(client, generatedConversationId, text, from, fromName, group, attachments);
@ -594,7 +595,8 @@ export class WhatsappDirectLine extends GBService {
await this.printMessages(response.obj.activities, conversationId, from, fromName); await this.printMessages(response.obj.activities, conversationId, from, fromName);
} catch (err) { } catch (err) {
GBLog.error( GBLog.error(
`Error calling printMessages on Whatsapp channel ${err.data === undefined ? err : err.data} ${err.errObj ? err.errObj.message : '' `Error calling printMessages on Whatsapp channel ${err.data === undefined ?
err : err.data} ${err.errObj ? err.errObj.message : ''
}` }`
); );
} }
@ -718,17 +720,27 @@ export class WhatsappDirectLine extends GBService {
return await this.sendTextAsAudioToDevice(to, msg, chatId); return await this.sendTextAsAudioToDevice(to, msg, chatId);
} else { } else {
let options; let options, messages;
const botNumber = this.min.core.getParam(this.min.instance, 'Bot Number', null);
switch (this.provider) { switch (this.provider) {
case 'meta':
const bot = createBot(this.min.instance.whatsappServiceNumber,
this.min.instance.whatsappServiceKey);
messages = msg.match(/(.|[\r\n]){1,4096}/g)
await CollectionUtil.asyncForEach(messages, async msg => {
await GBUtil.sleep(3000);
await bot.sendText(to, msg);
});
break;
case 'official': case 'official':
const botNumber = this.min.core.getParam(this.min.instance, 'Bot Number', null);
if (to.charAt(0) !== '+') { if (to.charAt(0) !== '+') {
to = `+${to}` to = `+${to}`
} }
let messages = msg.match(/(.|[\r\n]){1,1000}/g) messages = msg.match(/(.|[\r\n]){1,1000}/g)
await CollectionUtil.asyncForEach(messages, async msg => { await CollectionUtil.asyncForEach(messages, async msg => {
await GBUtil.sleep(3000); await GBUtil.sleep(3000);
@ -793,6 +805,19 @@ export class WhatsappDirectLine extends GBService {
switch (provider) { switch (provider) {
case 'meta':
if (req.body.entry[0].changes[0].value.statuses){
GBLogEx.info(this.min, `WhatsApp: ${req.body.entry[0].changes[0].value.statuses[0].status}.`);
return;
}
id = req.body.entry[0].changes[0].value.messages[0].from;
text = req.body.entry[0].changes[0].value.messages[0].text.body
senderName = req.body.entry[0].changes[0].value.contacts[0].profile.name;
botId = this.botId;
break;
case 'official': case 'official':
const { body } = req; const { body } = req;