mirror of
https://github.com/EvolutionAPI/evolution-api.git
synced 2025-07-16 04:02:54 -06:00
feat: Integrate Wavoip for voice call functionality
- Added Wavoip integration to support voice calls within the application. - Introduced `wavoipToken` in various DTOs and models to manage authentication. - Updated `ChannelStartupService` to handle Wavoip settings and events. - Enhanced `BaileysStartupService` to utilize Wavoip for call signaling. - Updated CHANGELOG.md to version 1.8.7.
This commit is contained in:
parent
8e65526ce9
commit
5043ce8405
@ -1,4 +1,10 @@
|
|||||||
# 1.8.6 (develop)
|
# 1.8.7
|
||||||
|
|
||||||
|
### Features
|
||||||
|
|
||||||
|
* Wavoip integration
|
||||||
|
|
||||||
|
# 1.8.6
|
||||||
|
|
||||||
### Features
|
### Features
|
||||||
|
|
||||||
|
@ -84,6 +84,7 @@
|
|||||||
"redis": "^4.6.5",
|
"redis": "^4.6.5",
|
||||||
"sharp": "^0.32.2",
|
"sharp": "^0.32.2",
|
||||||
"socket.io": "^4.7.1",
|
"socket.io": "^4.7.1",
|
||||||
|
"socket.io-client": "^4.8.1",
|
||||||
"socks-proxy-agent": "^8.0.1",
|
"socks-proxy-agent": "^8.0.1",
|
||||||
"swagger-ui-express": "^5.0.0",
|
"swagger-ui-express": "^5.0.0",
|
||||||
"uuid": "^9.0.0",
|
"uuid": "^9.0.0",
|
||||||
|
@ -78,6 +78,7 @@ export class InstanceController {
|
|||||||
read_messages,
|
read_messages,
|
||||||
read_status,
|
read_status,
|
||||||
sync_full_history,
|
sync_full_history,
|
||||||
|
wavoipToken,
|
||||||
websocket_enabled,
|
websocket_enabled,
|
||||||
websocket_events,
|
websocket_events,
|
||||||
rabbitmq_enabled,
|
rabbitmq_enabled,
|
||||||
@ -401,6 +402,7 @@ export class InstanceController {
|
|||||||
read_messages: read_messages || false,
|
read_messages: read_messages || false,
|
||||||
read_status: read_status || false,
|
read_status: read_status || false,
|
||||||
sync_full_history: sync_full_history ?? false,
|
sync_full_history: sync_full_history ?? false,
|
||||||
|
wavoipToken: wavoipToken ?? '',
|
||||||
};
|
};
|
||||||
|
|
||||||
this.logger.verbose('settings: ' + JSON.stringify(settings));
|
this.logger.verbose('settings: ' + JSON.stringify(settings));
|
||||||
|
@ -21,6 +21,7 @@ export class InstanceDto {
|
|||||||
read_messages?: boolean;
|
read_messages?: boolean;
|
||||||
read_status?: boolean;
|
read_status?: boolean;
|
||||||
sync_full_history?: boolean;
|
sync_full_history?: boolean;
|
||||||
|
wavoipToken?: string;
|
||||||
chatwoot_account_id?: string;
|
chatwoot_account_id?: string;
|
||||||
chatwoot_token?: string;
|
chatwoot_token?: string;
|
||||||
chatwoot_url?: string;
|
chatwoot_url?: string;
|
||||||
|
@ -6,4 +6,5 @@ export class SettingsDto {
|
|||||||
read_messages?: boolean;
|
read_messages?: boolean;
|
||||||
read_status?: boolean;
|
read_status?: boolean;
|
||||||
sync_full_history?: boolean;
|
sync_full_history?: boolean;
|
||||||
|
wavoipToken?: string;
|
||||||
}
|
}
|
||||||
|
@ -11,6 +11,7 @@ export class SettingsRaw {
|
|||||||
read_messages?: boolean;
|
read_messages?: boolean;
|
||||||
read_status?: boolean;
|
read_status?: boolean;
|
||||||
sync_full_history?: boolean;
|
sync_full_history?: boolean;
|
||||||
|
wavoipToken?: string;
|
||||||
}
|
}
|
||||||
|
|
||||||
const settingsSchema = new Schema<SettingsRaw>({
|
const settingsSchema = new Schema<SettingsRaw>({
|
||||||
@ -22,6 +23,7 @@ const settingsSchema = new Schema<SettingsRaw>({
|
|||||||
read_messages: { type: Boolean, required: true },
|
read_messages: { type: Boolean, required: true },
|
||||||
read_status: { type: Boolean, required: true },
|
read_status: { type: Boolean, required: true },
|
||||||
sync_full_history: { type: Boolean, required: true },
|
sync_full_history: { type: Boolean, required: true },
|
||||||
|
wavoipToken: { type: String, required: true },
|
||||||
});
|
});
|
||||||
|
|
||||||
export const SettingsModel = dbserver?.model(SettingsRaw.name, settingsSchema, 'settings');
|
export const SettingsModel = dbserver?.model(SettingsRaw.name, settingsSchema, 'settings');
|
||||||
|
@ -181,6 +181,9 @@ export class ChannelStartupService {
|
|||||||
this.localSettings.sync_full_history = data?.sync_full_history;
|
this.localSettings.sync_full_history = data?.sync_full_history;
|
||||||
this.logger.verbose(`Settings sync_full_history: ${this.localSettings.sync_full_history}`);
|
this.logger.verbose(`Settings sync_full_history: ${this.localSettings.sync_full_history}`);
|
||||||
|
|
||||||
|
this.localSettings.wavoipToken = data?.wavoipToken;
|
||||||
|
this.logger.verbose(`Settings wavoipToken: ${this.localSettings.wavoipToken}`);
|
||||||
|
|
||||||
this.logger.verbose('Settings loaded');
|
this.logger.verbose('Settings loaded');
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -194,6 +197,7 @@ export class ChannelStartupService {
|
|||||||
this.logger.verbose(`Settings read_messages: ${data.read_messages}`);
|
this.logger.verbose(`Settings read_messages: ${data.read_messages}`);
|
||||||
this.logger.verbose(`Settings read_status: ${data.read_status}`);
|
this.logger.verbose(`Settings read_status: ${data.read_status}`);
|
||||||
this.logger.verbose(`Settings sync_full_history: ${data.sync_full_history}`);
|
this.logger.verbose(`Settings sync_full_history: ${data.sync_full_history}`);
|
||||||
|
this.logger.verbose(`Settings wavoipToken: ${data.wavoipToken}`);
|
||||||
Object.assign(this.localSettings, data);
|
Object.assign(this.localSettings, data);
|
||||||
this.logger.verbose('Settings set');
|
this.logger.verbose('Settings set');
|
||||||
}
|
}
|
||||||
@ -214,6 +218,7 @@ export class ChannelStartupService {
|
|||||||
this.logger.verbose(`Settings read_messages: ${data.read_messages}`);
|
this.logger.verbose(`Settings read_messages: ${data.read_messages}`);
|
||||||
this.logger.verbose(`Settings read_status: ${data.read_status}`);
|
this.logger.verbose(`Settings read_status: ${data.read_status}`);
|
||||||
this.logger.verbose(`Settings sync_full_history: ${data.sync_full_history}`);
|
this.logger.verbose(`Settings sync_full_history: ${data.sync_full_history}`);
|
||||||
|
this.logger.verbose(`Settings wavoipToken: ${data.wavoipToken}`);
|
||||||
return {
|
return {
|
||||||
reject_call: data.reject_call,
|
reject_call: data.reject_call,
|
||||||
msg_call: data.msg_call,
|
msg_call: data.msg_call,
|
||||||
@ -222,6 +227,7 @@ export class ChannelStartupService {
|
|||||||
read_messages: data.read_messages,
|
read_messages: data.read_messages,
|
||||||
read_status: data.read_status,
|
read_status: data.read_status,
|
||||||
sync_full_history: data.sync_full_history,
|
sync_full_history: data.sync_full_history,
|
||||||
|
wavoipToken: data.wavoipToken,
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -719,7 +725,12 @@ export class ChannelStartupService {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public async sendDataWebhook<T = any>(event: Events, data: T, local = true) {
|
public async sendDataWebhook<T = any>(
|
||||||
|
event: Events,
|
||||||
|
data: T,
|
||||||
|
local = true,
|
||||||
|
integration = ['websocket', 'rabbitmq', 'sqs', 'webhook'],
|
||||||
|
) {
|
||||||
const webhookGlobal = this.configService.get<Webhook>('WEBHOOK');
|
const webhookGlobal = this.configService.get<Webhook>('WEBHOOK');
|
||||||
const webhookLocal = this.localWebhook.events;
|
const webhookLocal = this.localWebhook.events;
|
||||||
const websocketLocal = this.localWebsocket.events;
|
const websocketLocal = this.localWebsocket.events;
|
||||||
@ -739,7 +750,7 @@ export class ChannelStartupService {
|
|||||||
const tokenStore = await this.repository.auth.find(this.instanceName);
|
const tokenStore = await this.repository.auth.find(this.instanceName);
|
||||||
const instanceApikey = tokenStore?.apikey || 'Apikey not found';
|
const instanceApikey = tokenStore?.apikey || 'Apikey not found';
|
||||||
|
|
||||||
if (rabbitmqEnabled) {
|
if (rabbitmqEnabled && integration.includes('rabbitmq')) {
|
||||||
const amqp = getAMQP();
|
const amqp = getAMQP();
|
||||||
if (this.localRabbitmq.enabled && amqp) {
|
if (this.localRabbitmq.enabled && amqp) {
|
||||||
if (Array.isArray(rabbitmqLocal) && rabbitmqLocal.includes(we)) {
|
if (Array.isArray(rabbitmqLocal) && rabbitmqLocal.includes(we)) {
|
||||||
@ -884,7 +895,7 @@ export class ChannelStartupService {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (this.localSqs.enabled) {
|
if (this.localSqs.enabled && integration.includes('sqs')) {
|
||||||
const sqs = getSQS();
|
const sqs = getSQS();
|
||||||
|
|
||||||
if (sqs) {
|
if (sqs) {
|
||||||
@ -954,7 +965,7 @@ export class ChannelStartupService {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (this.configService.get<Websocket>('WEBSOCKET')?.ENABLED) {
|
if (this.configService.get<Websocket>('WEBSOCKET')?.ENABLED && integration.includes('websocket')) {
|
||||||
this.logger.verbose('Sending data to websocket on channel: ' + this.instance.name);
|
this.logger.verbose('Sending data to websocket on channel: ' + this.instance.name);
|
||||||
const io = getIO();
|
const io = getIO();
|
||||||
|
|
||||||
@ -1028,7 +1039,7 @@ export class ChannelStartupService {
|
|||||||
const globalApiKey = this.configService.get<Auth>('AUTHENTICATION').API_KEY.KEY;
|
const globalApiKey = this.configService.get<Auth>('AUTHENTICATION').API_KEY.KEY;
|
||||||
|
|
||||||
if (local) {
|
if (local) {
|
||||||
if (Array.isArray(webhookLocal) && webhookLocal.includes(we)) {
|
if (Array.isArray(webhookLocal) && webhookLocal.includes(we) && integration.includes('webhook')) {
|
||||||
this.logger.verbose('Sending data to webhook local');
|
this.logger.verbose('Sending data to webhook local');
|
||||||
let baseURL: string;
|
let baseURL: string;
|
||||||
|
|
||||||
@ -1096,7 +1107,7 @@ export class ChannelStartupService {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (webhookGlobal.GLOBAL?.ENABLED) {
|
if (webhookGlobal.GLOBAL?.ENABLED && integration.includes('webhook')) {
|
||||||
if (webhookGlobal.EVENTS[we]) {
|
if (webhookGlobal.EVENTS[we]) {
|
||||||
this.logger.verbose('Sending data to webhook global');
|
this.logger.verbose('Sending data to webhook global');
|
||||||
const globalWebhook = this.configService.get<Webhook>('WEBHOOK').GLOBAL;
|
const globalWebhook = this.configService.get<Webhook>('WEBHOOK').GLOBAL;
|
||||||
|
78
src/api/services/channels/voiceCalls/transport.type.ts
Normal file
78
src/api/services/channels/voiceCalls/transport.type.ts
Normal file
@ -0,0 +1,78 @@
|
|||||||
|
import { BinaryNode, Contact, JidWithDevice, proto, WAConnectionState } from 'baileys';
|
||||||
|
|
||||||
|
export interface ServerToClientEvents {
|
||||||
|
withAck: (d: string, callback: (e: number) => void) => void;
|
||||||
|
onWhatsApp: onWhatsAppType;
|
||||||
|
profilePictureUrl: ProfilePictureUrlType;
|
||||||
|
assertSessions: AssertSessionsType;
|
||||||
|
createParticipantNodes: CreateParticipantNodesType;
|
||||||
|
getUSyncDevices: GetUSyncDevicesType;
|
||||||
|
generateMessageTag: GenerateMessageTagType;
|
||||||
|
sendNode: SendNodeType;
|
||||||
|
'signalRepository:decryptMessage': SignalRepositoryDecryptMessageType;
|
||||||
|
}
|
||||||
|
|
||||||
|
export interface ClientToServerEvents {
|
||||||
|
init: (
|
||||||
|
me: Contact | undefined,
|
||||||
|
account: proto.IADVSignedDeviceIdentity | undefined,
|
||||||
|
status: WAConnectionState,
|
||||||
|
) => void;
|
||||||
|
'CB:call': (packet: any) => void;
|
||||||
|
'CB:ack,class:call': (packet: any) => void;
|
||||||
|
'connection.update:status': (
|
||||||
|
me: Contact | undefined,
|
||||||
|
account: proto.IADVSignedDeviceIdentity | undefined,
|
||||||
|
status: WAConnectionState,
|
||||||
|
) => void;
|
||||||
|
'connection.update:qr': (qr: string) => void;
|
||||||
|
}
|
||||||
|
|
||||||
|
export type onWhatsAppType = (jid: string, callback: onWhatsAppCallback) => void;
|
||||||
|
export type onWhatsAppCallback = (
|
||||||
|
response: {
|
||||||
|
exists: boolean;
|
||||||
|
jid: string;
|
||||||
|
}[],
|
||||||
|
) => void;
|
||||||
|
|
||||||
|
export type ProfilePictureUrlType = (
|
||||||
|
jid: string,
|
||||||
|
type: 'image' | 'preview',
|
||||||
|
timeoutMs: number | undefined,
|
||||||
|
callback: ProfilePictureUrlCallback,
|
||||||
|
) => void;
|
||||||
|
export type ProfilePictureUrlCallback = (response: string | undefined) => void;
|
||||||
|
|
||||||
|
export type AssertSessionsType = (jids: string[], force: boolean, callback: AssertSessionsCallback) => void;
|
||||||
|
export type AssertSessionsCallback = (response: boolean) => void;
|
||||||
|
|
||||||
|
export type CreateParticipantNodesType = (
|
||||||
|
jids: string[],
|
||||||
|
message: any,
|
||||||
|
extraAttrs: any,
|
||||||
|
callback: CreateParticipantNodesCallback,
|
||||||
|
) => void;
|
||||||
|
export type CreateParticipantNodesCallback = (nodes: any, shouldIncludeDeviceIdentity: boolean) => void;
|
||||||
|
|
||||||
|
export type GetUSyncDevicesType = (
|
||||||
|
jids: string[],
|
||||||
|
useCache: boolean,
|
||||||
|
ignoreZeroDevices: boolean,
|
||||||
|
callback: GetUSyncDevicesTypeCallback,
|
||||||
|
) => void;
|
||||||
|
export type GetUSyncDevicesTypeCallback = (jids: JidWithDevice[]) => void;
|
||||||
|
|
||||||
|
export type GenerateMessageTagType = (callback: GenerateMessageTagTypeCallback) => void;
|
||||||
|
export type GenerateMessageTagTypeCallback = (response: string) => void;
|
||||||
|
|
||||||
|
export type SendNodeType = (stanza: BinaryNode, callback: SendNodeTypeCallback) => void;
|
||||||
|
export type SendNodeTypeCallback = (response: boolean) => void;
|
||||||
|
|
||||||
|
export type SignalRepositoryDecryptMessageType = (
|
||||||
|
jid: string,
|
||||||
|
type: 'pkmsg' | 'msg',
|
||||||
|
ciphertext: Buffer,
|
||||||
|
callback: SignalRepositoryDecryptMessageCallback,
|
||||||
|
) => void;
|
||||||
|
export type SignalRepositoryDecryptMessageCallback = (response: any) => void;
|
181
src/api/services/channels/voiceCalls/useVoiceCallsBaileys.ts
Normal file
181
src/api/services/channels/voiceCalls/useVoiceCallsBaileys.ts
Normal file
@ -0,0 +1,181 @@
|
|||||||
|
import { ConnectionState, WAConnectionState, WASocket } from 'baileys';
|
||||||
|
import { io, Socket } from 'socket.io-client';
|
||||||
|
|
||||||
|
import { ClientToServerEvents, ServerToClientEvents } from './transport.type';
|
||||||
|
|
||||||
|
let baileys_connection_state: WAConnectionState = 'close';
|
||||||
|
|
||||||
|
export const useVoiceCallsBaileys = async (
|
||||||
|
wavoip_token: string,
|
||||||
|
baileys_sock: WASocket,
|
||||||
|
status?: WAConnectionState,
|
||||||
|
logger?: boolean,
|
||||||
|
) => {
|
||||||
|
baileys_connection_state = status ?? 'close';
|
||||||
|
|
||||||
|
const socket: Socket<ServerToClientEvents, ClientToServerEvents> = io('https://devices.wavoip.com/baileys', {
|
||||||
|
transports: ['websocket'],
|
||||||
|
path: `/${wavoip_token}/websocket`,
|
||||||
|
});
|
||||||
|
|
||||||
|
socket.on('connect', () => {
|
||||||
|
if (logger) console.log('[*] - Wavoip connected', socket.id);
|
||||||
|
|
||||||
|
socket.emit(
|
||||||
|
'init',
|
||||||
|
baileys_sock.authState.creds.me,
|
||||||
|
baileys_sock.authState.creds.account,
|
||||||
|
baileys_connection_state,
|
||||||
|
);
|
||||||
|
});
|
||||||
|
|
||||||
|
socket.on('disconnect', () => {
|
||||||
|
if (logger) console.log('[*] - Wavoip disconnect');
|
||||||
|
});
|
||||||
|
|
||||||
|
socket.on('connect_error', (error) => {
|
||||||
|
if (socket.active) {
|
||||||
|
if (logger)
|
||||||
|
console.log(
|
||||||
|
'[*] - Wavoip connection error temporary failure, the socket will automatically try to reconnect',
|
||||||
|
error,
|
||||||
|
);
|
||||||
|
} else {
|
||||||
|
if (logger) console.log('[*] - Wavoip connection error', error.message);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
socket.on('onWhatsApp', async (jid, callback) => {
|
||||||
|
try {
|
||||||
|
const response: any = await baileys_sock.onWhatsApp(jid);
|
||||||
|
|
||||||
|
callback(response);
|
||||||
|
|
||||||
|
if (logger) console.log('[*] Success on call onWhatsApp function', response, jid);
|
||||||
|
} catch (error) {
|
||||||
|
if (logger) console.error('[*] Error on call onWhatsApp function', error);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
socket.on('profilePictureUrl', async (jid, type, timeoutMs, callback) => {
|
||||||
|
try {
|
||||||
|
const response = await baileys_sock.profilePictureUrl(jid, type, timeoutMs);
|
||||||
|
|
||||||
|
callback(response);
|
||||||
|
|
||||||
|
if (logger) console.log('[*] Success on call profilePictureUrl function', response);
|
||||||
|
} catch (error) {
|
||||||
|
if (logger) console.error('[*] Error on call profilePictureUrl function', error);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
socket.on('assertSessions', async (jids, force, callback) => {
|
||||||
|
try {
|
||||||
|
const response = await baileys_sock.assertSessions(jids, force);
|
||||||
|
|
||||||
|
callback(response);
|
||||||
|
|
||||||
|
if (logger) console.log('[*] Success on call assertSessions function', response);
|
||||||
|
} catch (error) {
|
||||||
|
if (logger) console.error('[*] Error on call assertSessions function', error);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
socket.on('createParticipantNodes', async (jids, message, extraAttrs, callback) => {
|
||||||
|
try {
|
||||||
|
const response = await baileys_sock.createParticipantNodes(jids, message, extraAttrs);
|
||||||
|
|
||||||
|
callback(response, true);
|
||||||
|
|
||||||
|
if (logger) console.log('[*] Success on call createParticipantNodes function', response);
|
||||||
|
} catch (error) {
|
||||||
|
if (logger) console.error('[*] Error on call createParticipantNodes function', error);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
socket.on('getUSyncDevices', async (jids, useCache, ignoreZeroDevices, callback) => {
|
||||||
|
try {
|
||||||
|
const response = await baileys_sock.getUSyncDevices(jids, useCache, ignoreZeroDevices);
|
||||||
|
|
||||||
|
callback(response);
|
||||||
|
|
||||||
|
if (logger) console.log('[*] Success on call getUSyncDevices function', response);
|
||||||
|
} catch (error) {
|
||||||
|
if (logger) console.error('[*] Error on call getUSyncDevices function', error);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
socket.on('generateMessageTag', async (callback) => {
|
||||||
|
try {
|
||||||
|
const response = await baileys_sock.generateMessageTag();
|
||||||
|
|
||||||
|
callback(response);
|
||||||
|
|
||||||
|
if (logger) console.log('[*] Success on call generateMessageTag function', response);
|
||||||
|
} catch (error) {
|
||||||
|
if (logger) console.error('[*] Error on call generateMessageTag function', error);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
socket.on('sendNode', async (stanza, callback) => {
|
||||||
|
try {
|
||||||
|
console.log('sendNode', JSON.stringify(stanza));
|
||||||
|
const response = await baileys_sock.sendNode(stanza);
|
||||||
|
|
||||||
|
callback(true);
|
||||||
|
|
||||||
|
if (logger) console.log('[*] Success on call sendNode function', response);
|
||||||
|
} catch (error) {
|
||||||
|
if (logger) console.error('[*] Error on call sendNode function', error);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
socket.on('signalRepository:decryptMessage', async (jid, type, ciphertext, callback) => {
|
||||||
|
try {
|
||||||
|
const response = await baileys_sock.signalRepository.decryptMessage({
|
||||||
|
jid: jid,
|
||||||
|
type: type,
|
||||||
|
ciphertext: ciphertext,
|
||||||
|
});
|
||||||
|
|
||||||
|
callback(response);
|
||||||
|
|
||||||
|
if (logger) console.log('[*] Success on call signalRepository:decryptMessage function', response);
|
||||||
|
} catch (error) {
|
||||||
|
if (logger) console.error('[*] Error on call signalRepository:decryptMessage function', error);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
// we only use this connection data to inform the webphone that the device is connected and creeds account to generate e2e whatsapp key for make call packets
|
||||||
|
baileys_sock.ev.on('connection.update', (update: Partial<ConnectionState>) => {
|
||||||
|
const { connection } = update;
|
||||||
|
|
||||||
|
if (connection) {
|
||||||
|
baileys_connection_state = connection;
|
||||||
|
socket
|
||||||
|
.timeout(1000)
|
||||||
|
.emit(
|
||||||
|
'connection.update:status',
|
||||||
|
baileys_sock.authState.creds.me,
|
||||||
|
baileys_sock.authState.creds.account,
|
||||||
|
connection,
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (update.qr) {
|
||||||
|
socket.timeout(1000).emit('connection.update:qr', update.qr);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
baileys_sock.ws.on('CB:call', (packet) => {
|
||||||
|
if (logger) console.log('[*] Signling received');
|
||||||
|
socket.volatile.timeout(1000).emit('CB:call', packet);
|
||||||
|
});
|
||||||
|
|
||||||
|
baileys_sock.ws.on('CB:ack,class:call', (packet) => {
|
||||||
|
if (logger) console.log('[*] Signling ack received');
|
||||||
|
socket.volatile.timeout(1000).emit('CB:ack,class:call', packet);
|
||||||
|
});
|
||||||
|
|
||||||
|
return socket;
|
||||||
|
};
|
@ -131,6 +131,7 @@ import { waMonitor } from '../../server.module';
|
|||||||
import { Events, MessageSubtype, TypeMediaMessage, wa } from '../../types/wa.types';
|
import { Events, MessageSubtype, TypeMediaMessage, wa } from '../../types/wa.types';
|
||||||
import { CacheService } from './../cache.service';
|
import { CacheService } from './../cache.service';
|
||||||
import { ChannelStartupService } from './../channel.service';
|
import { ChannelStartupService } from './../channel.service';
|
||||||
|
import { useVoiceCallsBaileys } from './voiceCalls/useVoiceCallsBaileys';
|
||||||
|
|
||||||
const groupMetadataCache = new CacheService(new CacheEngine(configService, 'groups').getEngine());
|
const groupMetadataCache = new CacheService(new CacheEngine(configService, 'groups').getEngine());
|
||||||
|
|
||||||
@ -669,10 +670,32 @@ export class BaileysStartupService extends ChannelStartupService {
|
|||||||
|
|
||||||
this.logger.verbose('Socket created');
|
this.logger.verbose('Socket created');
|
||||||
|
|
||||||
|
if (this.localSettings.wavoipToken && this.localSettings.wavoipToken.length > 0) {
|
||||||
|
useVoiceCallsBaileys(this.localSettings.wavoipToken, this.client, this.connectionStatus.state as any, true);
|
||||||
|
}
|
||||||
|
|
||||||
this.eventHandler();
|
this.eventHandler();
|
||||||
|
|
||||||
this.logger.verbose('Socket event handler initialized');
|
this.logger.verbose('Socket event handler initialized');
|
||||||
|
|
||||||
|
this.client.ws.on('CB:call', (packet) => {
|
||||||
|
console.log('CB:call', packet);
|
||||||
|
const payload = {
|
||||||
|
event: 'CB:call',
|
||||||
|
packet: packet,
|
||||||
|
};
|
||||||
|
this.sendDataWebhook(Events.CALL, payload, true, ['websocket']);
|
||||||
|
});
|
||||||
|
|
||||||
|
this.client.ws.on('CB:ack,class:call', (packet) => {
|
||||||
|
console.log('CB:ack,class:call', packet);
|
||||||
|
const payload = {
|
||||||
|
event: 'CB:ack,class:call',
|
||||||
|
packet: packet,
|
||||||
|
};
|
||||||
|
this.sendDataWebhook(Events.CALL, payload, true, ['websocket']);
|
||||||
|
});
|
||||||
|
|
||||||
this.phoneNumber = number;
|
this.phoneNumber = number;
|
||||||
|
|
||||||
return this.client;
|
return this.client;
|
||||||
@ -1030,7 +1053,7 @@ export class BaileysStartupService extends ChannelStartupService {
|
|||||||
|
|
||||||
await this.contactHandle['contacts.upsert'](
|
await this.contactHandle['contacts.upsert'](
|
||||||
contacts
|
contacts
|
||||||
.filter((c) => !!c.notify ?? !!c.name)
|
.filter((c) => !!c.notify || !!c.name)
|
||||||
.map((c) => ({
|
.map((c) => ({
|
||||||
id: c.id,
|
id: c.id,
|
||||||
name: c.name ?? c.notify,
|
name: c.name ?? c.notify,
|
||||||
@ -1117,13 +1140,9 @@ export class BaileysStartupService extends ChannelStartupService {
|
|||||||
const contentMsg = received?.message[getContentType(received.message)] as any;
|
const contentMsg = received?.message[getContentType(received.message)] as any;
|
||||||
|
|
||||||
if (
|
if (
|
||||||
(
|
(this.localWebhook.webhook_base64 === true ||
|
||||||
this.localWebhook.webhook_base64 === true ||
|
(this.configService.get<Websocket>('WEBSOCKET').GLOBAL_EVENTS === true &&
|
||||||
(
|
this.configService.get<Websocket>('WEBSOCKET').ENABLED === true)) &&
|
||||||
this.configService.get<Websocket>('WEBSOCKET').GLOBAL_EVENTS === true &&
|
|
||||||
this.configService.get<Websocket>('WEBSOCKET').ENABLED === true
|
|
||||||
)
|
|
||||||
) &&
|
|
||||||
isMedia
|
isMedia
|
||||||
) {
|
) {
|
||||||
const buffer = await downloadMediaMessage(
|
const buffer = await downloadMediaMessage(
|
||||||
@ -1975,13 +1994,9 @@ export class BaileysStartupService extends ChannelStartupService {
|
|||||||
console.log('isMedia', isMedia);
|
console.log('isMedia', isMedia);
|
||||||
|
|
||||||
if (
|
if (
|
||||||
(
|
(this.localWebhook.webhook_base64 === true ||
|
||||||
this.localWebhook.webhook_base64 === true ||
|
(this.configService.get<Websocket>('WEBSOCKET').GLOBAL_EVENTS === true &&
|
||||||
(
|
this.configService.get<Websocket>('WEBSOCKET').ENABLED === true)) &&
|
||||||
this.configService.get<Websocket>('WEBSOCKET').GLOBAL_EVENTS === true &&
|
|
||||||
this.configService.get<Websocket>('WEBSOCKET').ENABLED === true
|
|
||||||
)
|
|
||||||
) &&
|
|
||||||
isMedia
|
isMedia
|
||||||
) {
|
) {
|
||||||
const buffer = await downloadMediaMessage(
|
const buffer = await downloadMediaMessage(
|
||||||
|
@ -83,6 +83,7 @@ export declare namespace wa {
|
|||||||
read_messages?: boolean;
|
read_messages?: boolean;
|
||||||
read_status?: boolean;
|
read_status?: boolean;
|
||||||
sync_full_history?: boolean;
|
sync_full_history?: boolean;
|
||||||
|
wavoipToken?: string;
|
||||||
};
|
};
|
||||||
|
|
||||||
export type LocalWebsocket = {
|
export type LocalWebsocket = {
|
||||||
|
@ -1002,9 +1002,26 @@ export const settingsSchema: JSONSchema7 = {
|
|||||||
read_messages: { type: 'boolean', enum: [true, false] },
|
read_messages: { type: 'boolean', enum: [true, false] },
|
||||||
read_status: { type: 'boolean', enum: [true, false] },
|
read_status: { type: 'boolean', enum: [true, false] },
|
||||||
sync_full_history: { type: 'boolean', enum: [true, false] },
|
sync_full_history: { type: 'boolean', enum: [true, false] },
|
||||||
|
wavoipToken: { type: 'string' },
|
||||||
},
|
},
|
||||||
required: ['reject_call', 'groups_ignore', 'always_online', 'read_messages', 'read_status', 'sync_full_history'],
|
required: [
|
||||||
...isNotEmpty('reject_call', 'groups_ignore', 'always_online', 'read_messages', 'read_status', 'sync_full_history'),
|
'reject_call',
|
||||||
|
'groups_ignore',
|
||||||
|
'always_online',
|
||||||
|
'read_messages',
|
||||||
|
'read_status',
|
||||||
|
'sync_full_history',
|
||||||
|
'wavoipToken',
|
||||||
|
],
|
||||||
|
...isNotEmpty(
|
||||||
|
'reject_call',
|
||||||
|
'groups_ignore',
|
||||||
|
'always_online',
|
||||||
|
'read_messages',
|
||||||
|
'read_status',
|
||||||
|
'sync_full_history',
|
||||||
|
'wavoipToken',
|
||||||
|
),
|
||||||
};
|
};
|
||||||
|
|
||||||
export const websocketSchema: JSONSchema7 = {
|
export const websocketSchema: JSONSchema7 = {
|
||||||
|
Loading…
Reference in New Issue
Block a user