import TelegramBot from 'node-telegram-bot-api';
import { EventEmitter } from 'node:events';
import { createReadStream } from 'node:fs';

export class Bot extends EventEmitter {
  constructor(token, authorizedUsers) {
    super();
    this._authorized = new Set(authorizedUsers.map(String));
    this._tg = new TelegramBot(token, { polling: true });

    this._tg.on('message', (msg) => this._onMessage(msg));
    this._tg.on('polling_error', (err) => {
      console.error('[bot] Polling error:', err.message || err);
    });

    process.on('SIGTERM', () => {
      console.log('[bot] SIGTERM received, stopping...');
      this.stop();
      process.exit(0);
    });
  }

  async _onMessage(msg) {
    if (!this._authorized.has(String(msg.from?.id))) return;

    const userId = msg.from.id;
    const chatId = msg.chat.id;

    if (msg.photo) {
      try {
        const largest = msg.photo[msg.photo.length - 1];
        const link = await this._tg.getFileLink(largest.file_id);
        const res = await fetch(link);
        const base64 = Buffer.from(await res.arrayBuffer()).toString('base64');
        this.emit('photo', { userId, chatId, caption: msg.caption || '', base64 });
      } catch (err) {
        console.error('[bot] Failed to download photo:', err.message);
      }
    } else if (msg.text) {
      this.emit('message', { userId, chatId, text: msg.text });
    }
  }

  sendText(chatId, text, options = {}) {
    return this._tg.sendMessage(chatId, text, options);
  }

  sendImage(chatId, source) {
    if (
      typeof source === 'string' &&
      (source.startsWith('http://') || source.startsWith('https://'))
    ) {
      return this._tg.sendPhoto(chatId, source);
    }
    return this._tg.sendPhoto(chatId, createReadStream(source));
  }

  stop() {
    this._tg.stopPolling();
  }
}
