Перейти к содержимому

Работа с Форумами и Топиками

Telegram позволяет преобразовывать супергруппы и личные сообщения в Форумы. В этом режиме сообщения разделяются на отдельные ветки — Топики (Topics).

ZenithGram предоставляет удобный API для управления топиками и отправки сообщений в конкретные ветки.

Управление топиками

Для работы с темами в классе ZG предусмотрен набор методов. Если бот получает обновление из конкретного топика, thread_id подставляется автоматически.

Создание и редактирование

php
$bot->onCommand('new_topic', '/create')->func(function(ZG $tg) {
    // 1. Создаем новый топик
    // Возвращает массив с информацией о созданном топике
    $response = $tg->createTopic(
        name: 'Обсуждение проекта', 
        icon_custom_emoji_id: '53101321...' // Опционально: кастомный эмодзи
    );
    
    $topicId = $tg->getMsgThreadId();
    
    // 2. Отправляем сообщение в этот топик
    $tg->msg("Топик создан! Добро пожаловать.")
       ->send(message_thread_id: $topicId);
       
    // 3. Редактируем название (например, через время)
    $tg->editTopic(
        name: 'Архив проекта', 
        thread_id: $topicId // Явно указываем ID
    );
});

Управление состоянием (Закрыть/Открыть/Удалить)

php
// Закрываем текущий топик (откуда пришла команда)
$bot->onCommand('close', '/close')->func(function(ZG $tg) {
    $tg->closeTopic(); 
    $tg->msg("Тема закрыта администратором.")->send();
});

// Удаляем топик по ID
$tg->deleteTopic(thread_id: 12345);

Работа с темой "General" (Основная)

Основная тема имеет особый статус, поэтому для неё существуют отдельные методы:

php
$tg->editGeneralTopic('Главный чат');
$tg->hideGeneralTopic(); // Скрыть из списка
$tg->unpinGeneralTopicMessages(); // Открепить все сообщения

Отправка сообщений в топики

Класс Message (через метод $tg->msg()) умеет отправлять сообщения в конкретные ветки.

  1. Автоматически: Если вы отвечаете на сообщение (reply) или просто пишете в контексте обработчика, библиотека сама определит message_thread_id.
  2. Вручную: Если нужно написать в другой топик.
php
// Отправка в конкретный топик ID 55
$tg->msg('Привет в ветку 55!')->send(message_thread_id: 55);

// Отправка в "General" (обычно null, но зависит от настроек чата)
$tg->msg('Привет всем!')->send(message_thread_id: null);

MessageDraft в Топиках

MessageDraft — это инструмент для создания "живых" сообщений (стриминга), которые обновляются в реальном времени. Это идеально подходит для отображения прогресса операций, логов или загрузки данных.

При работе в форумах важно передавать message_thread_id в метод send(), чтобы драфт появился в нужной ветке.

Особые условия

Такой тип сообщений возможно использовать только в лс и при условии, что в вашем боте включен режим ThreadedMode

Пример: Система Тикетов (Ticket System)

В этом примере мы создадим топик для обращения пользователя и будем отображать статус обработки "в прямом эфире" с помощью MessageDraft.

php
<?php
require_once __DIR__ . '/vendor/autoload.php';
use ZenithGram\ZenithGram\ZG;
use ZenithGram\ZenithGram\Bot;
use ZenithGram\ZenithGram\Enums\MessageParseMode;
$tg = ZG::create(BOT_TOKEN);
$bot = new Bot($tg);

$bot->onCommand('help', '/help')
    ->func(function(ZG $tg) {
        // 1. Создаем топик для пользователя
        $user = $tg->getUser();
        $topicName = "Тикет #{$user->id}: {$user->firstName}";
        
        $response = $tg->createTopic($topicName);
        $threadId = $response['result']['message_thread_id'];

        // 2. Создаем Draft в ЭТОМ топике
        // Важно: передаем message_thread_id в send()
        $draft = $tg->msgDraft("⏳ <b>Инициализация системы поддержки...</b>")
            ->parseMode(MessageParseMode::HTML)
            ->send(message_thread_id: $threadId);

        // Эмуляция работы (в реальности тут запросы к БД/API)
        sleep(1);
        
        // 3. Обновляем сообщение (ID чата и треда драфт помнит сам)
        $draft->setText("🔍 <b>Поиск свободного оператора...</b>")->send();
        
        sleep(2);
        
        // 4. Финальное обновление драфта
        $draft->setText("✅ <b>Оператор найден!</b>\nОпишите вашу проблему ниже.")->send();

        // 5. Отправляем уведомление пользователю в ЛС или общий чат
        $tg->msg("Для вас создан тикет. Перейдите в тему: $topicName")->send();
    });

$bot->run();

Как это работает внутри

  1. msgDraft() создает объект сообщения.
  2. Первый вызов send(message_thread_id: $id) отправляет сообщение в API и запоминает message_id, chat_id и message_thread_id внутри объекта $draft.
  3. Последующие вызовы setText()->send() используют запомненные данные для вызова метода editMessageText, автоматически попадая в нужный топик.

Опубликовано под лицензией MIT.