Files
arestools/src/business/events.js
T

71 lines
2.9 KiB
JavaScript
Raw Normal View History

import { isOwner } from '../config.js';
import { detectMediaFromBusiness } from '../core/media.js';
import { logger } from '../core/logger.js';
import { runHook } from '../core/registry.js';
/**
* Подписывает бота на бизнес-апдейты Telegram и раздаёт их модулям через хуки.
* Работает через официальное бизнес-подключение (Настройки → Telegram для
* бизнеса → Чат-боты) — никакой сессии, только апдейты от подключённого аккаунта.
*
* Событие удаления (deleted_business_messages) несёт только id сообщений и чат —
* без содержимого. Поэтому модуль cache складывает каждое входящее заранее,
* а antidelete достаёт его из кэша по (chatId, msgId).
*/
export function wireBusiness(bot, registry, ctx) {
bot.on('business_message', (gctx) =>
runHook(registry, 'onMessage', normalizeBusinessMessage(gctx), ctx),
);
bot.on('edited_business_message', (gctx) =>
runHook(registry, 'onEdited', normalizeBusinessMessage(gctx), ctx),
);
bot.on('deleted_business_messages', (gctx) => {
const d = gctx.deletedBusinessMessages;
return runHook(
registry,
'onDeleted',
{ chatId: d.chat?.id, msgIds: d.message_ids ?? [] },
ctx,
);
});
bot.on('business_connection', (gctx) => {
const c = gctx.businessConnection;
if (c?.is_enabled) {
logger.info(`Бизнес-подключение активно (id ${c.id})`);
} else {
logger.warn(`Бизнес-подключение отключено владельцем (id ${c?.id}). Перехват приостановлен.`);
}
});
logger.debug('бизнес-апдейты подписаны: message / edited / deleted / connection');
}
/**
* Приводит grammY-контекст бизнес-сообщения к плоскому виду, понятному модулям.
* isPrivateIncoming — входящее в личном 1-на-1 чате, не от самого владельца.
*/
export function normalizeBusinessMessage(gctx) {
const msg = gctx.businessMessage ?? gctx.editedBusinessMessage ?? gctx.msg;
const from = msg?.from;
const chat = msg?.chat;
return {
chatId: chat?.id,
msgId: msg?.message_id,
senderId: from?.id,
sender: senderLabel(from),
text: msg?.text ?? msg?.caption ?? '',
media: detectMediaFromBusiness(msg),
// Свои исходящие отсекаем через isOwner (как раньше через message.out).
isPrivateIncoming: chat?.type === 'private' && !isOwner(from?.id),
};
}
function senderLabel(from) {
if (!from) return '';
const name = [from.first_name, from.last_name].filter(Boolean).join(' ');
return from.username ? `${name} (@${from.username})`.trim() : name;
}