Вернуться в список

Перенос сообщений между чатами: опыт автоматизации в меcсенджере МАКС

Перенос постов между чатами через Bot API: как это работает

Практический разбор автоматизации: от подготовки бота до боевого переноса сотен сообщений с медиафайлами, а также обзор других полезных возможностей ботов мессенджера.

Задача

В мессенджере существует групповой чат, в котором за долгое время накопилось несколько сотен сообщений: текстовые заметки, фотографии, видео, аудио, пересланные публикации. Появилась необходимость перенести эти сообщения в отдельный канал — чтобы контент был собран в ленту новостей, удобную для подписчиков. Переносить вручную невозможно: сообщений много, часть содержит тяжёлые медиафайлы. Решение — написать программу-переносчик на базе официального Bot API мессенджера.

Что понадобилось для старта

  • Бот с доступом к платформе. Чат-боты создаются через платформу для партнёров и работают от имени юридического лица или ИП. После создания и модерации выдаётся токен — ключ, который используется для всех запросов к API.
  • Права администратора в обоих чатах. Чтобы читать историю сообщений и публиковать в канал, бот должен быть администратором группы-источника и канала-цели.
  • Секретные данные строго изолированы. Токен хранится в отдельном конфигурационном файле, который не попадает в репозиторий и не выводится в логи.
Важный нюанс российской инфраструктуры: API доступен только по защищённому соединению, а часть корневых сертификатов удостоверяющего центра может отсутствовать в стандартном хранилище ОС. В этом случае подключается локальный бандл корневых сертификатов, и все запросы выполняются с его указанием — иначе TLS-соединение отклоняется.

Архитектура запросов к API

Все операции выполняются через HTTP-запросы к единому адресу платформы. Авторизация — заголовок:

Authorization: <токен бота>

Основные методы, задействованные в переносе:

МетодНазначение
GET /chatsПолучить список доступных боту чатов (групп, каналов) с их идентификаторами.
GET /chats/{id}Узнать права бота в конкретном чате, количество участников.
GET /messagesПрочитать историю сообщений с пагинацией и фильтрами по времени.
POST /uploadsЗагрузить медиафайл и получить токен для его повторного использования.
POST /messagesОпубликовать текстовое сообщение или сообщение с вложениями.
DELETE /messagesУдалить сообщение по его идентификатору.

Структура сообщения

Каждое сообщение в истории содержит время публикации, отправителя и тело. Тело — это объект с текстом и списком вложений. У вложений есть тип (изображение, видео, аудио, файл, стикер, пересланная ссылка) и «токен» — идентификатор уже загруженного медиа.

{
  "timestamp": 1760000000000,
  "sender": { "user_id": "...", "name": "..." },
  "body": {
    "text": "Текст сообщения",
    "attachments": [
      { "type": "image", "payload": { "token": "...", "url": "..." } }
    ]
  }
}

Подготовка бота и проверка прав

Перед запуском было реализовано несколько проверок, которые позволяют не тратить время впустую и сразу видеть готовность окружения:

  1. Проверка аутентификации токена.
  2. Проверка чтения из группы-источника: бот должен быть администратором, иначе история недоступна.
  3. Проверка чтения из канала-цели.
  4. Проверка наличия бота в списке администраторов канала.
  5. Тестовая публикация: единственная ошибка, которая на этом этапе допустима, — отсутствие права записи в канале.
Модуль проверки был оформлен отдельной командой флагов --check, чтобы окружение можно было проверять быстро и часто, не перечитывая весь код.

Чтение истории: пагинация и сортировка

API отдаёт историю порциями — по 100 сообщений за запрос. Новые сообщения возвращаются первыми, поэтому для обхода всей истории используется курсор: после каждой порции фиксируется время самого старого сообщения, и следующая порция запрашивается «до этого времени». Цикл продолжается, пока порция не окажется пустой.

while True:
    page = get_messages(chat, count=100, before=course)
    if not page: break
    all_messages.extend(page)
    course = min(ts for m in page) - 1

Для переноса важно сохранить хронологический порядок: сообщения должны встать в канале так же, как стояли в исходном чате. Для этого все сообщения собираются в память, сортируются по возрастанию времени и только затем публикуются. Без этой сортировки лента получилась бы «перевёрнутой» — первыми ушли бы самые свежие посты.

Извлечение контента: где лежит текст и вложения

Есть два типа сообщений, и их устройство различается:

  • Обычное сообщение — текст и вложения лежат в поле body.
  • Пересланное сообщение — в теле может быть только заглушка, а сам контент (текст и медиа) лежит во вложенном объекте link.message. Иногда цепочка пересылок вложена несколько уровней, и требуется рекурсивный поиск контента с ограничением глубины.

Именно второй случай — классическая ловушка для переносчика: если искать контент только в body, пересланные посты будут молча пропущены, а в логе появится расхождение между количеством сообщений в исходном чате и количеством опубликованных. По итогам отладки данные расхождения были обнаружены, логика извлечения исправлена, и пропущенные пересланные посты были доставлены отдельным повторным запуском.

Перенос медиафайлов

Вложения — самая требовательная часть. Механика выглядит так:

  1. У вложения берётся ссылка на файл или его существующий токен.
  2. Файл скачивается, затем перезагружается через POST /uploads под ботом.
  3. На ответе приходит свежий токен, который используется при публикации поста.

Оптимизация: если у вложения уже есть токен, повторная выгрузка не выполняется — токен переиспользуется. Это в разы ускоряет перенос серии постов с одинаковыми вложениями.

Ограничения платформы, которые учтены в коде:

  • не более 12 вложений на одно сообщение;
  • текст не длиннее нескольких тысяч символов;
  • примерно 2 сообщения в секунду на чат — между публикациями вставлена задержка;
  • стикеры репостятся как изображения (скачивание и перезагрузка в тип «картинка»);
  • пересланные ссылки (превью сайтов) не переносятся как отдельные вложения — их текст сохраняется, превью отбрасывается.

Алгоритм одного поста

def build_post(message):
    text, atts = resolve_content(message)
    attachments = [make_attachment(a) for a in atts]
    # разбивка на несколько постов, если attachment > 12
    return chunk(attachments)

def publish(post):
    if reuse_tokens: post.attachments = reuse_existing_tokens(post)
    else:            post.attachments = [upload_media(a) for a in post]
    r = POST /messages { chat_id, text, attachments }
    time.sleep(0.6)   # лимит ~2 сообщения/сек

Устойчивость и защита от дублей

Перенос выполняется не «одним махом», а с сохранением прогресса:

  • После каждого сообщения его идентификатор записывается в файл состояния.
  • При следующем запуске те сообщения, что уже в состоянии, пропускаются — продолжение идёт с места остановки.
  • Если что-то прервалось (сбой сети, лимиты, ошибка загрузки медиа), повторный запуск не создаст дубликатов.
  • Предусмотрен режим просмотра (сухой прогон): программа полностью «проигрывает» перенос, ничего не публикуя, и показывает, сколько постов будет создано и какие пропущены. Это позволяет до боевого запуска убедиться в корректности фильтров и порядка.

Фильтрация по отправителю

Возможность, оказавшаяся ключевой для практического использования. В конфигурации задаётся список идентификаторов авторов, и бот переносит только их сообщения:

  • сообщения сторонних участников пропускаются и помечаются в состоянии как обработанные — чтобы при повторных запусках к ним не возвращаться;
  • фильтр работает по внешнему отправителю: если участник переслал чужой пост, считается тот, кто переслал;
  • это позволило отобрать, например, только сообщения владельца группы — около двух третей всего объёма контента.

Боевой запуск и проверка результата

После успешного сухого прогона состояние сбрасывается и выполняется боевой перенос:

  1. Все посты выбранного автора публикуются в канал в хронологическом порядке.
  2. По завершении запускается контролёр: читается вся история канала, подсчитывается количество сообщений и проверяется, что нет дубликатов.
  3. Дополнительно проверяется монотонность времени публикаций — лента должна быть упорядочена от старого к новому.

В рассматриваемом сценарии было перенесено около 540 постов с медиафайлами без единого дубля и без потери порядка. Отдельно подтверждена одна из «фирменных» особенностей задачи: команда полной очистки канала через DELETE /messages позволила безопасно перезапустить перенос с нуля, когда изменились требования к отбору контента.

Что ещё умеют такие боты

Перенос постов — лишь малая часть того, на что способен бот в этом мессенджере. На той же базе (токен, API, право публикации) реализуются и более широкие сценарии.

Публикация и управление контентом

  • Регулярные рассылки и посты по расписанию: новости, анонсы, подборки — бот публикует в канал по таймеру совсем без участия человека.
  • Репосты и архивирование: перенос контента между группами и каналами, сбор «лучшего» из нескольких источников в одну ленту, бэкап истории.
  • Редактирование и удаление своих сообщений — исправление опечаток, замена медиа, снятие устаревших анонсов.

Взаимодействие с участниками

  • Приветствие и онбординг: автоматическое сообщение новому участнику группы с правилами и полезными ссылками.
  • Автоответы на ключевые слова: бот отвечает на типовые вопросы (цены, адреса, часы работы), снимая нагрузку с администраторов.
  • Кнопки и меню: интерактивные клавиатуры — меню с разделами, кнопки «записаться», «подписаться», «проголосовать».
  • Опросы и голосования при наличии соответствующего метода API.
  • Приём от участников: бот анализирует входящие сообщения, принимает заявки, собирает заказы, контактные данные и обратную связь.

Управление каналом и группой

  • Модерация: отслеживание новых сообщений, удаление нежелательных, ограничение спама.
  • Структура доступа: чтение состава участников, проверка прав администраторов у бота, управление подписками (с оговоркой об ограничениях API для некоторых типов чатов).

Бизнес и интеграции

  • Синхронизация с внешними системами: CRM, базы клиентов, рассылки из маркетинговых платформ — токен бота используется как «мост» для доставки уведомлений в мессенджер.
  • Онлайн-заказы и услуги: мини-приложения, подключаемые к боту, позволяют принимать заказы, оплату и брони без ухода из диалога.
  • Уведомления о событиях: статусы заказов, напоминания о записи, триггеры из внешних сервисов.
  • Рассылки подтверждённым контактам — доставка сообщений в личные диалоги подписчиков по заранее собранной базе (в рамках правил платформы).
  • Цифровой ID: для организаций доступна проверка возраста и льготных статусов — идентификация подписчиков прямо внутри сценариев бота.

Инженерные возможности

  • Устойчивость: повторные попытки при таймаутах, задержки по лимитам, логирование и контрольный аудит результатов.
  • Режимы безопасного запуска: «сухой прогон», тестирование на копии канала, проверка прав перед боевой операцией.
  • Масштабирование: тот же принцип переноса легко расширить на произвольное число источников и каналов — достаточно параметризовать конфигурацию.

Выводы

Перенос постов между чатами мессенджера на Bot API — задача, которая на первый взгляд кажется простой, но на практике требует внимания к деталям: разной структуре обычных и пересланных сообщений, лимитам на вложения и частоту запросов, сохранению хронологии и защите от дублей. Главные уроки проекта:

  • проверяйте права бота до начала боевых операций;
  • считайте ожидаемый результат и сверяйте его с фактическим после каждого запуска;
  • всегда отвечайте на вопрос «сколько должно было получиться и почему другой результат» — так были найдены скрытые пропуски пересланных постов;
  • сухой прогон и файл состояния — дешёвый способ избежать дорогих ошибок.

А дальше всё зависит от бизнес-задачи: тот же бот превращается из «переносчика» в полноценный инструмент коммуникации — от рассылок и автоответов до онбординга и интеграций с внешними системами.

Материал основан на практическом опыте автоматизации переноса контента в мессенджере: названия чатов, личные данные и идентификаторы участников намеренно не упоминаются.

Подписывайтесь на наш MAX-канал

Новости о 1С-Битрикс и Битрикс24, обзоры обновлений, полезные кейсы и спецпредложения по лицензиям.

Подписаться Бесплатно