Find a file
2026-10-13 13:31:55 +03:00
assets Set the Telegram group's avatar automatically during setup 2026-08-14 11:48:55 +03:00
certs Аудит безопасности: HTTPS-панель, скоуп доверия CA, сериализация MAX-запросов 2026-08-14 21:13:26 +03:00
docs Релиз 1.3.7: выход из MAX без удаления (/logout, пульт; сессия завершается и в MAX, /kill тоже), «🔁 Перезапустить мост» в пульте, сторож Telegram (переподключение при зависшем приёме), HISTORY_LIMIT при первой синхронизации, подсказка админу в личке; новость на сайте 2026-10-13 13:31:55 +03:00
files-service 1.3.3-beta.9: лимит Let's Encrypt после настоящего отказа больше не прячет причину — бот называет её (порты, белый IP, домен) и добавляет «после исправления подождите час» 2026-10-11 19:49:05 +03:00
scripts Релиз 1.3.7: выход из MAX без удаления (/logout, пульт; сессия завершается и в MAX, /kill тоже), «🔁 Перезапустить мост» в пульте, сторож Telegram (переподключение при зависшем приёме), HISTORY_LIMIT при первой синхронизации, подсказка админу в личке; новость на сайте 2026-10-13 13:31:55 +03:00
src 1.3.7-beta.2: «🚪 Выйти из MAX» (пульт → Вход в MAX, /logout) — LOGOUT 0x14 из веб-клиента MAX завершает сессию и на стороне MAX (уходит из «Устройств»), здесь она забывается, темы/история/настройки остаются, номер запоминается для /login; /kill тоже завершает сессию в MAX и больше не просит закрыть её в приложении (если MAX не ответил — честно говорит) 2026-10-13 12:57:07 +03:00
telemetry-server Телеметрия: раз в 6 часов сверяет версию десктопного MAX из его apt-репозитория с той, которой представляется мост (src/max/client.ts на GitHub), и один раз на каждую новую версию MAX пишет в тему автоотчётов — заранее, до «Приложение устарело» 2026-10-12 18:52:57 +03:00
tests 1.3.7-beta.2: «🚪 Выйти из MAX» (пульт → Вход в MAX, /logout) — LOGOUT 0x14 из веб-клиента MAX завершает сессию и на стороне MAX (уходит из «Устройств»), здесь она забывается, темы/история/настройки остаются, номер запоминается для /login; /kill тоже завершает сессию в MAX и больше не просит закрыть её в приложении (если MAX не ответил — честно говорит) 2026-10-13 12:57:07 +03:00
.dockerignore Безопасность и надёжность (полный аудит): зеркало и телеметрия переведены на HTTPS, ключ подписи релизов закреплён в install.sh, контейнер работает без root, авто-реконнект при повреждённом кадре MAX, корректное завершение по SIGTERM, таймауты скачиваний и лимиты памяти 2026-08-25 22:19:52 +03:00
.env.example 1.3.7-beta.1: сторож Telegram — запрос новых сообщений висит дольше 2 минут (у Telegraf таймаут 500 с) → обрыв и переподключение, повторно за 10 минут → перезапуск контейнера, отчёт telegram-poll-stall; «🔁 Перезапустить мост» в пульте → Система (без пересборки, пульт возвращается сам); админу моста в личке — подсказка «команды в группе» с ссылкой вместо заглушки баг-бота; HISTORY_LIMIT — при первой синхронизации только последние N сообщений чата, с пометкой в теме, вопрос в установщике, строка в меню настроек 2026-10-13 12:49:31 +03:00
.gitattributes Безопасность и надёжность (полный аудит): зеркало и телеметрия переведены на HTTPS, ключ подписи релизов закреплён в install.sh, контейнер работает без root, авто-реконнект при повреждённом кадре MAX, корректное завершение по SIGTERM, таймауты скачиваний и лимиты памяти 2026-08-25 22:19:52 +03:00
.gitignore Убран случайно закоммиченный server.pid, *.pid добавлен в .gitignore 2026-08-14 21:29:47 +03:00
allowed_signers Подпись обновлений включена: релизы подписываются SSH-ключом, update.sh проверяет 2026-08-22 17:25:50 +03:00
CHANGELOG.md Релиз 1.3.7: выход из MAX без удаления (/logout, пульт; сессия завершается и в MAX, /kill тоже), «🔁 Перезапустить мост» в пульте, сторож Telegram (переподключение при зависшем приёме), HISTORY_LIMIT при первой синхронизации, подсказка админу в личке; новость на сайте 2026-10-13 13:31:55 +03:00
docker-compose.yml Headless-мост: веб-панель вырезана, опциональные стикеры (slim/full), подпись обновлений 2026-08-22 15:32:57 +03:00
Dockerfile Релиз 1.1.1: базовый образ закреплён по контрольной сумме, проверка места перед сборкой, причина неудачи в сообщении, чистка кэша сборок 2026-10-04 16:07:43 +03:00
entrypoint.sh Безопасность и надёжность (полный аудит): зеркало и телеметрия переведены на HTTPS, ключ подписи релизов закреплён в install.sh, контейнер работает без root, авто-реконнект при повреждённом кадре MAX, корректное завершение по SIGTERM, таймауты скачиваний и лимиты памяти 2026-08-25 22:19:52 +03:00
install.sh 1.3.0-beta.11: служба файлов поднимается за секунды — systemd .path следит за отметками мостов (ставит сам reconcile.sh); блокировка от двойного запуска; удаляется вместе с последним мостом 2026-10-10 00:45:09 +03:00
LICENSE Лицензия AGPL-3.0 (дуал-лицензия для закрытого использования, правообладатель Zergont) + Fail2ban по желанию при первой установке: защита SSH от подбора пароля, backend systemd, IP сессии в белом списке 2026-09-05 15:44:11 +03:00
package-lock.json Релиз 1.3.7: выход из MAX без удаления (/logout, пульт; сессия завершается и в MAX, /kill тоже), «🔁 Перезапустить мост» в пульте, сторож Telegram (переподключение при зависшем приёме), HISTORY_LIMIT при первой синхронизации, подсказка админу в личке; новость на сайте 2026-10-13 13:31:55 +03:00
package.json Релиз 1.3.7: выход из MAX без удаления (/logout, пульт; сессия завершается и в MAX, /kill тоже), «🔁 Перезапустить мост» в пульте, сторож Telegram (переподключение при зависшем приёме), HISTORY_LIMIT при первой синхронизации, подсказка админу в личке; новость на сайте 2026-10-13 13:31:55 +03:00
README.md 1.3.7-beta.2: «🚪 Выйти из MAX» (пульт → Вход в MAX, /logout) — LOGOUT 0x14 из веб-клиента MAX завершает сессию и на стороне MAX (уходит из «Устройств»), здесь она забывается, темы/история/настройки остаются, номер запоминается для /login; /kill тоже завершает сессию в MAX и больше не просит закрыть её в приложении (если MAX не ответил — честно говорит) 2026-10-13 12:57:07 +03:00
setup.sh 1.3.7-beta.1: сторож Telegram — запрос новых сообщений висит дольше 2 минут (у Telegraf таймаут 500 с) → обрыв и переподключение, повторно за 10 минут → перезапуск контейнера, отчёт telegram-poll-stall; «🔁 Перезапустить мост» в пульте → Система (без пересборки, пульт возвращается сам); админу моста в личке — подсказка «команды в группе» с ссылкой вместо заглушки баг-бота; HISTORY_LIMIT — при первой синхронизации только последние N сообщений чата, с пометкой в теме, вопрос в установщике, строка в меню настроек 2026-10-13 12:49:31 +03:00
tsconfig.json Бета: правки по ревью 1.0.1 (промежуточный коммит перед упрощением) 2026-09-27 10:01:57 +03:00
update-watcher.sh 1.3.0-beta.1: большие файлы по ссылкам (общая служба файлов на хост, порты 80/443 только при живых ссылках, IP-сертификат), пульт «Файлы», мини-приложения ботов ссылками 2026-10-09 21:25:25 +03:00
update.sh 1.2.0-beta.6: анонимные автоотчёты об ошибках; кнопки MESSAGE, запрос геолокации и контакта 2026-10-05 10:36:11 +03:00

Telemax — двусторонний мост MAX ↔ Telegram

🌐 Сайт проекта: telemax.svnest.ru

Двусторонний мост между мессенджером MAX и Telegram. Подключается к вашему личному MAX-аккаунту по номеру телефона — а не через бота, поэтому в Telegram зеркалятся все ваши чаты Макса автоматически (у бот-мостов так не выйдет — только там, куда добавили бота). Каждый номер MAX превращается в Telegram-группу с форум-темами (по одной на каждый MAX-чат), переписка идёт в обе стороны как в едином окне. На стороне Telegram — свой бот, всё крутится на вашем сервере: данные идут только через вашу инфраструктуру, без облачных прослоек.

⚠️ Неофициальный проект. Не связан с MAX и Telegram, работает поверх вашего собственного номера/аккаунта на свой страх и риск — см. «Отказ от ответственности».

Возможности

  • Текстовые сообщения, фото, файлы, голосовые, видео и видео-кружки (обе стороны)
  • Большие файлы — по ссылке: из Telegram в MAX больше 20 МБ (до 4 ГБ — лимит MAX), из MAX в Telegram больше 50 МБ; свой файлообменник в пульте (см. «Большие файлы»)
  • Кнопки ботов MAX — в Telegram: ссылки, копирование, нажатия; мини-приложения открываются ссылкой в MAX
  • Стикеры — статичные и анимированные (обе стороны)
  • Геолокация и контакты (обе стороны)
  • Опросы: создание и голосование в обе стороны, актуальный счёт по команде /poll
  • Удаление сообщений в обе стороны; удаление чата в MAX удаляет и его тему в Telegram
  • Ответы на сообщения (reply) — нативные в обе стороны, с переходом к оригиналу
  • Пересылка сообщений — обычным drag-forward в Telegram, с автоматической пометкой источника
  • 📡 Трансляция: новые сообщения чата MAX копируются в любые группы и каналы Telegram — для тех, у кого нет MAX (/broadcast, см. «Трансляция»)
  • 🎛 Пульт управления (/panel, закреплён в теме группы): поиск контакта MAX по номеру, нику или MAX ID и старт чата в один тап, пауза/возобновление MAX, бан/разбан чатов, вход в MAX, обновление — всё кнопками
  • Управление MAX-группами прямо из Telegram: создание, приглашение/удаление участников, переименование, описание, выход, удаление
  • Уведомления о звонках (входящий/завершённый/пропущенный) — только текстом, без передачи аудио
  • Авторизация MAX прямо в боте: /login в личке (номер + код из SMS, поддерживается пароль/2FA) — код и пароль в группу не попадают
  • /reboot — полный сброс и пересинхронизация Telegram-стороны без повторной авторизации в MAX
  • /logout (или пульт → «🔐 Вход в MAX» → «🚪 Выйти из MAX») — выйти из MAX без удаления: сессия завершается и в самом MAX, темы, история и настройки остаются; войти снова — /login
  • /kill — аварийный сброс: то же самое + выход из MAX (сессия завершается и в самом MAX) и стирание сохранённой сессии и всех данных
  • /version — проверка обновлений и обновление по кнопке прямо из Telegram (см. «Обновление»)
  • Прокси для Telegram (SOCKS5/HTTP) — если сервер выходит в Telegram только через прокси; MAX при этом идёт напрямую (см. «Прокси для Telegram»)
  • Уведомления о сбоях (потеря связи с MAX, ошибки доставки, внутренние ошибки) прямо в Telegram-группу, с защитой от спама
  • 🐞 Приём баг-репортов в личку бота с двусторонней перепиской (опционально, включается BUGREPORT_INBOX); по умолчанию посторонним, написавшим боту в личку, показывается ссылка на баг-репорт-бот проекта
  • Аватарка группы и цвет иконки каждой темы форума выставляются автоматически

Полный список команд бота — /help прямо в боте после запуска.

Пульт управления

Команда /panel (и закреплённое в теме группы сообщение) открывает пульт с кнопками — меню прямо в Telegram-группе:

  • 👤 Найти контакт — поиск MAX-контакта по номеру, нику или MAX ID; из карточки результата «Начать чат» в один тап создаёт диалог и его тему, а «➕ В контакты MAX» сохраняет человека в контакты вашего MAX (их видно и в приложении на телефоне). Или просто поделитесь в общей теме группы контактом из Telegram — бот найдёт его в MAX по номеру, а в контакты MAX сохранит под тем же именем, что у вас в Telegram (читать вашу книгу контактов Telegram бот не может: Bot API такого доступа не даёт). Человека, который закрыл поиск по номеру в настройках приватности MAX, не найти никак — попросите его написать вам первым, и чат сам появится темой.
  • 🚫 Управление чатами — заглушить (бан) или вернуть чат.
  • 🔐 Вход в MAX — кнопка ведёт в личку бота, где проходит авторизация (номер + SMS-код, при 2FA — пароль).
  • ⚙️ Система — «📊 Статус» (версия, аптайм, состояние MAX и Telegram, последние сообщения, диск/RAM/нагрузка, доступность обновления), пауза MAX на время (10 мин / 1 час / 1 сутки / до перезапуска моста), обновление, пересинхронизация, список команд и «🔁 Перезапустить мост» — без пересборки и без SSH, за 10–20 секунд.

Пульт виден всем участникам группы, но кнопки/команды срабатывают только у администраторов.

Требования

  • Сервер на Ubuntu 22.04+ или Debian 12+ (нужен git 2.34+ — им проверяется подпись релизов; на Ubuntu 20.04 / Debian 11 git старее)
  • Docker + Docker Compose
  • Telegram-бот (токен из @BotFather) и Telegram-группа с включёнными темами (forum topics), куда бот добавлен администратором с правом «Управление темами» (Manage Topics) — без него бот не сможет создавать темы под MAX-чаты
  • Номер MAX, на который будет авторизован мост

Быстрый старт

На чистом сервере Ubuntu 22.04+ / Debian 12+ (по SSH, от root) — одна команда:

curl -fsSL https://raw.githubusercontent.com/Trollobot/Telemax/main/install.sh | bash

Если GitHub с вашего сервера недоступен (заблокирован или лежит) — та же установка с резервного зеркала проекта:

curl -fsSL https://zergont-gate.duckdns.org/install.sh | bash

Скрипт в обоих случаях один и тот же: сначала пробует GitHub, при неудаче сам переключается на зеркало; обновления и проверка версий работают так же, с автоматическим фолбэком. Подлинность каждого релиза в любом случае проверяется по подписи тега — зеркало лишь транспорт.

Она сама обновит систему, поставит git, Docker и jq (если их ещё нет), предложит включить Fail2ban — защиту SSH от подбора пароля (по умолчанию — да), склонирует проект в /opt/telemax и запустит интерактивную настройку. Если на сервере уже есть установленный мост, та же команда вместо этого откроет меню: обновить или перенастроить существующий (в том числе переустановить начисто), поставить ещё один или удалить ненужный (см. «Несколько мостов на одном сервере»). Спросит токен Telegram-бота (создаётся через @BotFather) — id группы искать не придётся: добавьте бота в свою группу (с включёнными темами) администратором, отправьте туда любое сообщение, и скрипт сам определит нужный id. Секретные ключи сгенерирует сама, соберёт образ и запустит контейнер. Первая сборка дольше обычного (внутри образа headless-браузер для рендера анимированных стикеров) — это нормально, обычно несколько минут. Останется один шаг: авторизовать MAX командой /login в личке бота (подробнее — «Первая авторизация»). Повторный запуск setup.sh безопасен — на настроенной установке он открывает меню изменения настроек (см. «Изменение настроек после установки»).

Если Docker и git уже стоят (или разворачиваете не с нуля) — то же самое, но без системной части:

git clone https://github.com/Trollobot/Telemax.git
cd Telemax
./setup.sh

Совсем руками, без интерактивных скриптов:

cp .env.example .env
# впишите TELEGRAM_BOT_TOKEN и TARGET_TELEGRAM_GROUP, ключ шифрования сгенерируйте:
# openssl rand -hex 32   -> MAX_SESSION_KEY
docker compose up -d --build

Несколько мостов на одном сервере

На одном сервере может жить сколько угодно независимых мостов — например, два номера MAX, каждый со своей Telegram-группой. У каждого моста всё своё: каталог (/opt/telemax, /opt/telemax-2, …), свой Telegram-бот (токен нельзя переиспользовать — два моста на одном токене отбирают обновления друг у друга), своя группа и свой номер MAX, свои настройки (.env) и данные (data/). Общие на сервер — только Docker (одинаковые слои образов кэшируются, поэтому второй мост занимает на диске заметно меньше первого), единый таймер автообновления telemax-updater, который сам обслуживает все мосты, и Fail2ban.

Установщик сам находит уже установленные мосты: запустите ту же команду установки ещё раз, и вместо установки откроется меню —

  1. Обновить или перенастроить существующий мост (если их несколько — выбор какого). Внутри два уровня: обычное обновление с сохранением настроек (только до релиза с проверенной подписью, как и при автообновлении; если такого нет — мост остаётся на своей версии) или переустановка начисто — настройки и данные сбрасываются, но перед этим автоматически сохраняются в архив /root/telemax-backup-<имя>-<дата>.tar.gz (доступен только root). Если бэкап сохранить не удалось, ничего не удаляется.
  2. Установить ещё один мост — установщик предложит первый свободный каталог (/opt/telemax-2), путь можно поменять. Дальше — обычная настройка: токен нового бота, новая группа, /login с новым номером.
  3. Удалить мост — один по выбору или сразу все. Удаляются контейнер, образ и каталог; настройки и данные перед этим сохраняются в такой же бэкап-архив, а без бэкапа удаление не выполняется. Вместе с последним мостом убирается и общий таймер автообновления (Docker и Fail2ban остаются — они серверные).

Меню появляется только при интерактивном запуске; если каталог задан явно через INSTALL_DIR, установщик молча работает с ним — так что второй мост по-прежнему можно поставить и одной командой:

curl -fsSL https://raw.githubusercontent.com/Trollobot/Telemax/main/install.sh | INSTALL_DIR=/opt/telemax-2 bash

Практические мелочи: полный образ (с Chromium для анимированных стикеров) — это ~1,7 ГБ и заметный кусок RAM на каждый контейнер, на небольшом сервере для второго моста стоит выбрать режим slim; все команды обслуживания (docker compose logs -f, ./setup.sh, ./update.sh) выполняются из каталога конкретного моста.

Первая авторизация

⚠️ Не пропустите этот шаг. Без авторизации MAX мост поднят, но ни к какому аккаунту не подключён и ничего не пересылает.

После запуска контейнера откройте вашего бота в Telegram и напишите ему в личку команду /login (либо в группе: /panel → «🔐 Вход в MAX»). Бот спросит номер телефона MAX и код из SMS — всё в личной переписке, в группу они не попадают; если на аккаунте включён пароль (2FA), бот спросит и его и сразу удалит сообщение с паролем из чата. Вход доступен только администраторам группы.

После успешной авторизации сессия сохраняется зашифрованной в ./data — повторной авторизации при перезапуске контейнера не требуется. Повторный вход тем же путём (/login) нужен только после /kill, смены номера или если MAX отклонил сессию (бот сам напишет об этом в группу).

После входа мост переносит историю чатов в темы. Telegram разрешает боту писать в группу примерно 20 сообщений в минуту, поэтому большая история заливается долго: чат на 5 000 сообщений — около 4 часов (новые сообщения при этом приходят сразу). Установщик спрашивает, сколько последних сообщений каждого чата переносить; то же — HISTORY_LIMIT=300 в .env (затем docker compose up -d --force-recreate). Тема, куда попала не вся история, начинается с пометки об этом.

В личке бот работает только для входа в MAX (/login); все остальные команды — в группе моста. Если администратор напишет в личку что-то другое, бот подскажет, где пульт.

Большие файлы

У ботов Telegram жёсткие лимиты: скачать из Telegram бот может файл не больше 20 МБ, отправить в Telegram — не больше 50 МБ. MAX принимает файлы до 4 ГБ. Всё, что не пролезает, мост пересылает по ссылке:

  • Из Telegram в MAX, больше 20 МБ. Бот отвечает в теме кнопкой «📤 Загрузить файл»: по ссылке открывается страница на вашем сервере, файл загружается из браузера, и мост отправляет его в MAX обычным файлом — до 4 ГБ, это лимит MAX. Чтобы не ждать загрузку дважды (сначала в Telegram, потом по ссылке), напишите в теме чата /file — ссылка на загрузку придёт сразу. Большой файл MAX обрабатывает несколько минут — мост дожидается этого сам.
  • Из MAX в Telegram, больше 50 МБ. В теме сразу появляется «📥 Пришёл файл» с прогрессом сохранения, а когда файл ляжет на сервер — кнопка «⬇️ Скачать».
  • Пульт → «📁 Файлы». Список файлов на сервере: новая ссылка (продлевает хранение), удаление, повторная отправка в MAX, если она не удалась. Кнопка «📤 Загрузить файл» — свой файлообменник: положить на сервер файл любого размера (сколько вместит диск, лимит MAX тут ни при чём) и делиться ссылкой на скачивание где угодно. Файл живёт 3 дня от последней выданной ссылки, потом удаляется сам. Отправленные в MAX файлы на сервере не хранятся.

Как это устроено:

  • Ссылки обслуживает одна общая служба на сервер (files-service/: Caddy + маленькое приложение на Node) — для всех мостов сразу. Её запускает автообновление, и только пока есть действующие ссылки: тогда открыты порты 80 и 443. Ссылок нет — служба остановлена, порты закрыты. Запускается она за несколько секунд: за появлением ссылок следит systemd (telemax-files.path), его ставит само автообновление. Настройки адреса (FILES_DOMAIN, FILES_PUBLIC_URL, FILES_LISTEN) общие для всех мостов сервера и берутся из .env первого из них.

  • HTTPS — без домена: сертификат Let's Encrypt выпускается на IP-адрес сервера и продлевается сам. Если есть свой домен, укажите его: FILES_DOMAIN=files.example.ru в .env первого моста.

  • Порты 80 и 443 должны открываться из интернета — иначе Let's Encrypt не сможет выдать сертификат, и ссылки не заработают. Сервер дома за роутером — нужен белый IP у роутера и проброс на сервер портов 80 и 443 (с серым IP проброс не поможет: белый IP подключают у провайдера, или мост ставят на VPS); хостинг закрывает порты файрволом — откройте их в его панели. Если что-то мешает, бот прямо назовёт причину. Не нужны большие файлы — FILES=off.

  • Установщик проверяет это сам. Если у сервера нет своего белого IP (он дома за роутером) или порты 80/443 заняты другим веб-сервером, он объясняет, что нужно, и предлагает включить большие файлы, только если всё уже настроено — иначе ставит FILES=off. Включить позже — ./setup.sh → «Большие файлы».

  • Ссылка на загрузку, по которой ничего не загрузили, живёт 24 часа: сообщение с ней скажет, что она истекла. Загрузка, которая уже идёт, не обрывается, даже если срок вышел. Все ждущие ссылки видны в «📁 Файлы» — там их можно открыть или отменить.

  • Перед каждой передачей проверяется свободное место, и мост всегда оставляет запас 1,5 ГБ — столько нужно для обновления.

  • По ссылке открывается страница с кнопкой, а не сам файл: предпросмотр ссылок в мессенджерах её не «съедает». Ссылки случайные, без списков файлов, с ограниченным сроком.

  • Нужны свободные порты 80 и 443. Если на сервере уже есть свой веб-сервер (Caddy, nginx), службу файлов можно пустить через него: она будет слушать только локальный порт, а ваш сервер — передавать ей запросы по выбранному пути. Пример для Caddy — в блок вашего сайта:

    handle_path /tlmx-files/* {
    	reverse_proxy 127.0.0.1:3300
    }
    

    и в .env первого моста: FILES_PUBLIC_URL=https://ваш-домен/tlmx-files и FILES_LISTEN=127.0.0.1:3300. Без этого при занятых портах бот так и скажет, а файлы больше лимитов пересылаться не будут.

Настройки в .env (необязательные):

FILES=off              # выключить пересылку больших файлов совсем
FILES_TTL_HOURS=72     # сколько живёт файл после выдачи ссылки
FILES_UPLOAD_TTL_HOURS=24  # сколько живёт неиспользованная ссылка на загрузку
FILES_RESERVE_MB=1536  # сколько места всегда оставлять свободным
FILES_DOMAIN=          # свой домен вместо IP-адреса
FILES_PUBLIC_URL=      # адрес за вашим веб-сервером, например https://example.ru/tlmx-files
FILES_LISTEN=          # локальный порт службы для вашего веб-сервера, например 127.0.0.1:3300

Трансляция

Новые сообщения чата MAX можно копировать в обычные группы и каналы Telegram — для тех, у кого MAX нет. Например, чат садового товарищества — в канал, который читают соседи.

  • Включить. Напишите /broadcast в теме чата и нажмите «👥 В группу» или «📢 В канал»: Telegram покажет ваши группы или каналы и сам добавит туда бота — в канал администратором с правом публиковать. Если бот там уже есть — «🔎 Бот уже там»: выбор откроется в личке с ботом.
  • Мест — сколько угодно. Один чат можно транслировать в несколько групп и каналов, а в одну группу — несколько чатов. /broadcast в теме показывает, куда идёт трансляция, и останавливает любую кнопкой «⏹».
  • Что копируется. Новые сообщения с момента включения: текст, фото, файлы, голосовые, с подписью автора, как в теме. Вместо «🧑 Вы» стоит ваше имя из MAX, ваши сообщения, написанные в теме из Telegram, тоже идут туда. Правки и удаления в MAX повторяются, пока мост не перезапускался. Опросы — текстом: голоса из Telegram в MAX не попадут. История до включения не переносится, сообщения, пришедшие пока мост был выключен, — догоняются.
  • В одну сторону. Что пишут в группе трансляции, в MAX не уходит — бот там молчит. Чтобы участники только читали, выберите канал или закройте отправку сообщений в настройках группы.
  • Если бота удалят из группы или канала, трансляция туда остановится сама, а в теме чата появится сообщение.

Безопасность

Бот отвечает только внутри той Telegram-группы, что указана в TARGET_TELEGRAM_GROUP — любое сообщение или нажатие кнопки из другого чата (личка боту, добавление в чужую группу и т.п.) игнорируется. Исключение — группы и каналы трансляции: туда бот только пишет, а включить трансляцию может лишь администратор группы моста по одноразовой ссылке из /broadcast.

Внутри группы доступ разграничен: обычные участники могут читать и писать (в группу можно добавлять людей для общего обсуждения), но команды боту выполняются только для администраторов группы — снести сессию (/kill), пересобрать мост (/reboot), войти в MAX (/login), управлять MAX-группами может лишь админ, рядовой участник — нет.

Учтите: любой участник Telegram-группы видит в ней все зеркалированные MAX-чаты (по теме на чат), а не какой-то один. Доступ к самой группе — чувствительная вещь, раздавайте его осознанно.

Мост не открывает входящих портов: MAX — исходящее TCP-соединение, Telegram — long-polling. Единственное исключение — пересылка больших файлов (см. «Большие файлы»): пока на сервере есть хотя бы одна действующая ссылка на файл, открыты порты 80 и 443, а когда ссылок нет — служба останавливается и порты закрываются. Управление — только из Telegram-группы (админами) и по SSH через ./setup.sh. Единственная открытая дверь на сервере — SSH; install.sh предлагает поставить Fail2ban, который банит подбор пароля (5 промахов за 10 минут → бан на 10 минут; IP вашей сессии установки — в белом списке).

Сертификаты российского государственного УЦ (нужны только потому, что через них выпущен TLS-сертификат самого MAX) доверяются только соединениям с серверами MAX — запросы к Telegram, GitHub и всему остальному проверяются исключительно по стандартному набору корневых сертификатов Mozilla (подробнее — certs/README.md).

Обслуживание

docker compose logs -f      # логи
docker compose restart      # перезапуск
docker compose down         # остановка

Все состояние (сессия MAX, привязка чатов к темам) лежит в ./data на хосте — бэкап этой папки достаточен для переноса на другой сервер.

Изменение настроек после установки

Все настройки живут в одном месте — файле .env. Штатный способ их менять — зайти на сервер по SSH и запустить setup.sh ещё раз:

cd /opt/telemax && ./setup.sh

На настроенной установке он открывает меню:

  1. Показать текущие настройки (токен маской, группа, прокси без пароля, режим стикеров, статус контейнера)
  2. Изменить прокси Telegram — с живой проверкой соединения до записи
  3. Сменить токен бота / целевую группу (с повторным автоопределением группы)
  4. Переключить режим стикеров full/slim (с пересборкой образа)
  5. Проверить связь с MAX и Telegram
  6. Пересобрать и перезапустить контейнер
  7. Большие файлы: включить или выключить — с проверкой, есть ли у сервера свой белый IP и свободны ли порты 80/443

Изменения применяются пересозданием контейнера (меню предложит это само) — Docker читает .env только при создании контейнера, простого рестарта недостаточно.

Аварийный случай: бот молчит, потому что прокси умер, а починить через Telegram нельзя (канал управления идёт через тот самый прокси). По SSH это один заход: ./setup.sh → пункт 2 — или совсем вручную:

cd /opt/telemax && (umask 077; grep -v '^TELEGRAM_PROXY=' .env > .env.tmp && printf "TELEGRAM_PROXY='%s'\n" 'socks5://логин:пароль@хост:порт' >> .env.tmp) && mv .env.tmp .env && chmod 600 .env && docker compose up -d --force-recreate

Значение записывается в одинарных кавычках — так же, как это делает setup.sh. Без кавычек Docker Compose подставляет переменные в .env, и пароль с символом $ доходит до контейнера искажённым (pa$w0rd превращается в pa) — бот просто молча не подключается к Telegram. Адрес прокси в команде тоже взят в одинарные кавычки, поэтому $, & и # в пароле безопасны; если в пароле есть сам символ ', запишите его как %27 (например, pa%27ss) — так его принимает и setup.sh.

Прокси для Telegram

Если сервер выходит в Telegram только через прокси (например, домашний сервер, где прямой доступ к api.telegram.org закрыт) — укажите его. MAX при этом всегда идёт напрямую, через прокси гоняется только Telegram-трафик. Форматы: socks5://[логин:пароль@]хост:порт или http://[логин:пароль@]хост:порт.

Задать можно тремя способами:

  • При установке — setup.sh спрашивает про прокси ещё до проверки связи (иначе на proxy-only хосте проверка Telegram ложно упала бы), и тут же проверяет доступность через него.
  • После установки — повторный запуск ./setup.sh → пункт «Изменить прокси Telegram»: новая настройка сначала проверяется вживую и только потом записывается (см. «Изменение настроек после установки»).
  • В .env — переменная TELEGRAM_PROXY, затем docker compose up -d --force-recreate (Telegraf задаёт прокси при старте, на лету не подменяется).

Если что-то не работает

Сама установка проходит на любом Ubuntu 22.04+ / Debian 12+ (проверено вплоть до Debian 13 trixie) даже на VPS с менее чем 1 ГБ RAM — окружение почти никогда не причём. Быстрее всего локализовать проблему по одному признаку — проявляется ли бот в вашей Telegram-группе хоть как-то: приходит ли после старта его сообщение «✅ Telemax подключён к этой группе», заводятся ли темы под MAX-чаты.

  • Бота в группе не видно вообще (ни стартового сообщения, ни тем) — он не достучался до Telegram или до группы: пункты 1–3.
  • Бот активен, но сообщения из MAX не приходят — почти всегда не завершена авторизация MAX: пункт 4.

Все команды — из папки установки (cd /opt/telemax):

  1. Бот не достучался до Telegram (частый случай на хостингах в РФ). На dual-stack серверах IPv6-маршрут до api.telegram.org бывает заблокирован, а система по умолчанию пробует сначала именно IPv6 — бот виснет на подключении, в группе полная тишина. Свежие версии форсируют IPv4 сами, так что первым делом обновитесь: /version в группе → «Обновить» (или ./update.sh). Если по какой-то причине не помогло — как временный обходной путь можно прибить IPv4-адрес Telegram в /etc/hosts: 149.154.167.220 api.telegram.org.

  2. Контейнер не запущен.

    docker ps
    

    Если в списке пусто — посмотрите причину падения (docker compose logs --tail=50) и поднимите заново: docker compose up -d.

  3. Бот добавлен в группу без нужных прав. Он должен быть в группе администратором с правом «Управление темами» (Manage Topics) — без него бот не может создавать темы под MAX-чаты. И TARGET_TELEGRAM_GROUP в .env должен быть id именно этой группы. Если прав не хватает, бот сам напишет об этом в группу.

  4. Не завершена авторизация MAX — самая частая причина, когда бот в группе есть, а переписки нет. Проверьте логи:

    docker compose logs --tail=30
    

    Если нет строки Resumed session for +… — аккаунт не подключён. Авторизация делается прямо в боте: напишите ему в личку /login и введите номер MAX и код из SMS (см. «Первая авторизация»).

  5. Установка встала на проверке связи. setup.sh в начале проверяет доступность MAX и Telegram и падает с явной ошибкой, если один из серверов недоступен (файрвол хостинга или гео-блокировка). Если установка остановилась именно на этой проверке — дело в сети сервера. Перепроверить связь в любой момент: ./setup.sh → пункт «Проверить связь».

  6. При входе в MAX: «Приложение устарело, пожалуйста, обновитесь». MAX время от времени перестаёт пускать старые версии клиента, а мост представляется ему десктопным MAX. Сначала проверьте обновление моста: /version в группе → «Обновить» — исправление может быть уже выпущено. Если обновления нет — впишите актуальную версию сами, в .env:

    MAX_APP_VERSION=26.35.1
    MAX_BUILD_NUMBER=80662
    

    и пересоздайте контейнер: docker compose up -d --force-recreate. Текущие номера — в репозитории MAX для Linux: https://download.max.ru/linux/deb/dists/stable/main/binary-amd64/Packages. Первая строка Version: — это версия, а число перед .deb в строке Filename: (например, MAX-26.35.1.80662.deb) — номер сборки.

  7. Обновление не прошло на шаге «сборка образа». Почти всегда на сервере кончилось место: образ с Chromium весит около 1,7 ГБ, и при сборке новый должен поместиться рядом со старым. Мост при этом остаётся на прежней версии и работает. Сначала просто нажмите «Обновить» ещё раз — тяжёлая часть уже собрана и повторно не скачивается. Не помогло — освободите место и повторите:

    docker builder prune -af   # кэш прошлых сборок
    docker image prune -f      # образы, оставшиеся от неудачных попыток
    df -h /                    # сколько свободно; для обновления нужно от 1,5 ГБ, для первой сборки — от 3 ГБ
    

    На совсем маленьком диске помогает образ без Chromium: ./setup.sh → «Переключить режим стикеров» → slim (анимированные стикеры тогда приходят статичной картинкой).

Не нашли причину — заводите Issue с выводом docker compose logs --tail=50 (ключи/токены из .env не прикладывайте, а номер телефона MAX в логе — например в строке Resumed session for +… — замажьте).

Обновление

Раз в сутки (в случайное время) бот сам проверяет на GitHub, не вышел ли новый релиз (тег версии новее текущей), и если да — присылает в группу сообщение с кнопками «Обновить» / «Позже». То же самое можно спросить в любой момент командой /version. Проверка идёт по версии из package.json и тегам GitHub (semver), поэтому работает для любой сборки — в том числе собранной напрямую, без GIT_COMMIT.

Технически апдейт устроен так: сам контейнер с ботом ничего не обновляет и не перезапускает — у него нет и не будет доступа ни к докеру, ни к хосту (это осознанный выбор: код, который разбирает сообщения из MAX/Telegram, не должен иметь возможность управлять сервером). Вместо этого:

  • Кнопка «Обновить» просто оставляет файл-маркер в ./data.
  • На хосте (не в контейнере) параллельно работает systemd-таймер telemax-updater, который ставит setup.sh — раз в минуту проверяет этот маркер, и если он есть, запускает update.sh: он скачивает свежий код, но переходит только на тег релиза с проверенной подписью (нет такого, есть локальные правки или git старше 2.34 — обновление отклоняется), затем пересборка образа → docker compose up -d; при сбое возвращает прежнюю версию.
  • Таймер добавлен в автозапуск (systemctl enable), то есть переживает перезагрузку сервера.
  • update.sh пишет в группу на каждом шаге: сразу — что начал, при ошибке (проверка подписи/сборка/рестарт/контейнер не поднялся) — что именно сломалось и что мост остался на прежней версии. После успешного перезапуска бот сам напишет, до какой версии обновился.

Проверить/поуправлять им можно как обычным systemd-юнитом:

systemctl status telemax-updater.timer   # включён ли, когда сработает в следующий раз
systemctl disable --now telemax-updater.timer   # выключить совсем — обновляться придётся вручную: ./update.sh

Отказ от ответственности

Проект не аффилирован ни с MAX, ни с Telegram, ни с их правообладателями. Используя его, вы работаете со своим собственным аккаунтом MAX на свой страх и риск, в том числе в части соблюдения условий использования сервиса.

Переписка, которую бот пересылает, временно оседает на вашем собственном сервере: в логах контейнера, в персистентном хранилище (./data) и в истории самой Telegram-группы. Проект не несёт ответственности за сохранность, утечку или неправомерное использование этих данных — обеспечение их безопасности (доступ к серверу, шифрование диска, ротация логов и т.д.) целиком на вас.

Лицензия

Код распространяется по лицензии GNU AGPL-3.0 — полный текст в файле LICENSE. Это open source.

Коротко, что это значит:

  • Ставить, использовать и менять под себя — свободно, в том числе в бизнесе.
  • Открытость обязательна. Если вы распространяете изменённую версию или запускаете её как сервис для других (в этом отличие AGPL от обычной GPL), вы обязаны открыть исходный код своих изменений под той же лицензией.
  • Хотите закрыть код? Использовать Telemax без обязательств AGPL — в закрытом продукте или сервисе, не публикуя изменения — можно только по отдельной коммерческой лицензии. Пишите: zergont@gmail.com.
  • Имя «Telemax» лицензией на код не передаётся: выпускать свой продукт или сервис под этим названием без согласия правообладателя нельзя.
  • Программа поставляется как есть, без каких-либо гарантий — см. разделы 15–16 лицензии и «Отказ от ответственности» выше.

© 2026 Zergont · zergont@gmail.com

Обратная связь

Нашли баг или есть вопрос — напишите боту @TelemaxSvv_bot прямо в Telegram (ответим там же) или заведите Issue. Идеями и впечатлениями можно поделиться в Discussions.

Поддержать проект

Разработка

npm install
npm run dev       # мост в watch-режиме (tsx)
npm run lint      # проверка типов
npm test          # vitest

Телеметрия

Чтобы понимать, сколько инстансов моста реально работает, раз в сутки бот отправляет анонимный пинг: случайный идентификатор установки (UUID, генерируется один раз и хранится в ./data/install-id) и текущую версию. Никаких номеров телефонов, содержимого сообщений, IP или иных персональных данных не передаётся и не хранится — только «эта установка жива, версия такая-то».

Анонимные отчёты об ошибках

Если что-то ломается, мост сам отправляет разработчику короткий анонимный отчёт — чтобы ошибку можно было исправить, не прося вас искать логи на сервере. Отчёт уходит в пяти случаях:

  • internal — внутренняя ошибка моста (необработанное исключение или сбой обработчика Telegram);
  • session-rejected — MAX окончательно отклонил сохранённую сессию (то же событие, что и сообщение «❌ MAX-сессия отклонена»);
  • restart-loop — контейнер перезапустился три раза или больше за 10 минут;
  • fatal — мост не смог запуститься;
  • update — не удалось или было отклонено обновление (отправляет update.sh; в сообщении бота тогда есть строка «Анонимный отчёт отправлен разработчику»).

Что именно в отчёте — полный список полей:

Поле Содержимое
installId тот же случайный идентификатор установки, что и в пинге
version версия моста
kind один из пяти видов выше
step где произошла ошибка (шаг обновления или название обработчика)
error первая строка текста ошибки, не длиннее 300 символов; токены, пароли прокси, текст в кавычках и длинные числа (номера, идентификаторы) перед отправкой вырезаются
toVersion версия, на которую шло обновление (только update)
freeMb, memMb свободное место на диске и свободная память, МБ
os название и версия ОС
docker, git версии Docker и git (только update)
node версия Node.js (только отчёты моста)

В отчёте нет содержимого сообщений, названий чатов, идентификаторов чатов и собеседников, номера телефона и ничего из .env. Сервер принимает отчёты только от установок, которые уже известны ему по ежедневному пингу, и хранит их в сведённом виде: «такая-то ошибка встретилась столько-то раз на таких-то версиях». Мост отправляет не больше пяти отчётов в сутки и не повторяет один и тот же чаще раза в шесть часов.

Как отключить

Добавьте в .env:

TELEMETRY=off

и перезапустите контейнер (docker compose up -d). После этого не отправляется ничего: ни ежедневный пинг, ни отчёты об ошибках — в том числе при обновлении.