- README: расширен раздел Tg-notify.bot — три подсистемы, поток привязка/подписка/CheckAll, полная таблица конфига (+kp_api_key, +tmdb_lang), быстрый старт, команды, HTTP API, фактическое состояние инстанса (bot_token пуст, /lite/mirage=disable, /lite/collaps=503) - AGENT.md: правило 11 — эксплуатация бота, диагностика, данные database/tgnotify
Lampac NextGen — локальный Docker-развёртывание
Локальное развёртывание Lampac NextGen — самохостируемого бекенда для Lampa — в Docker. Официальная документация: docs.lampac.dev.
Быстрый старт
docker compose up -d # первый запуск
docker compose logs -f # логи (строки compilation / configure module / loaded module)
docker compose restart # после правки config/init.conf или манифестов в mods/
- Веб-клиент Lampa: http://localhost:9118
- Админ-панель: http://localhost:9118/adminpanel (root-пароль из
config/passwd) - TorrServer-прокси:
http://localhost:9118/ts/*(порт TorrServer — 9085)
По умолчанию сервер слушает порт 9118; если порт занят — меняй listen.port в config/init.conf до первого запуска.
Структура проекта
| Путь | Назначение |
|---|---|
docker-compose.yaml |
Основной сервис (образ закреплён на ghcr.io/lampac-nextgen/lampac:1.68.0) |
config/init.conf |
Конфигурация сервера (JSON, монтируется в /lampac/init.conf) |
config/passwd |
Пароль root для /adminpanel и /weblog (не в git) |
cache/ |
Кеш (/lampac/cache) |
database/ |
SQLite-базы Sync, TimeCode, Music, tg-notify (/lampac/database) |
dlna/ |
Локальные медиа для DLNA (/lampac/data/dlna) |
plugins/extensions.json |
Каталог плагинов для веб-клиента (раздел «Плагины»), отдаётся через /extensions |
mods/<Имя>/ |
Пользовательские копии встроенных модулей с enable: true |
docker-compose.override.yml(в .gitignore) — серверное override для Proxmox (том DLNA ->/mnt/torrents), живёт только на сервере.
Включённые модули из mods/
Встроенные модули с "enable": false в manifest.json внутри образа нельзя включать правкой файла в контейнере — файлы пропадут при обновлении. Механика по официальной документации (модули Lampac, пользовательские модули):
- Скопировать модуль из образа в
mods/<Имя>/на хосте:docker cp lampac:/lampac/module/<Имя> "mods/<Имя>" - В
mods/<Имя>/manifest.jsonпоставить"enable": true. - Добавить том в
docker-compose.yaml:- ./mods/<Имя>:/lampac/mods/<Имя> - При необходимости добавить секцию модуля в
config/init.conf(runtime-флаг). docker compose up -d(при добавлении тома) илиrestart(при правке манифеста сdynamic: true).
Сейчас подключены
| Модуль | Что даёт | Секция в init.conf |
|---|---|---|
Tracks |
/tracks.js, /ffprobe — субтитры и дорожки |
"Tracks": { "enable": true } |
AdminPanel |
/adminpanel — редактор init.conf, current.conf, users.json |
"AdminPanel": { "enable": true } |
Music |
/music.js, /music/* — музыкальный каталог, плейлисты, стримы |
секция "Music" (базовые дефолты) |
Tg-notify.bot |
/tg-notify.js, /api/tg/* — уведомления о новых сериях в Telegram |
секция "TelegramBot" |
Клиентские плагины music.js и tg-notify.js зарегистрированы в LampaWeb.customPlugins; {localhost} в URL автоматически подставляется сервером.
Ещё можно включить тем же способом
В образе выключены также: DatabaseEditor, ExternalBind, LogUserRequest-Lite, Transcoding, WatchTogether, TelegramAuth, TelegramAuthBot.
Конфигурация
config/init.conf— JSON. После правки:docker compose restart. Следи за валидностью JSON (лишняя запятая ломает парсинг).BaseModule.SkipModules/BaseModule.LoadModules— фильтры загрузки модулей (имя, группа, regex).SkipModulesимеет приоритет надLoadModules.LampaWeb.initPlugins— флаги встроенных плагинов веб-клиента;LampaWeb.customPlugins— дополнительные плагины (status: 1).LampaWeb.autoupdate: true— Lampa Web-клиент автообновляется изyumata/lampa(раз в 90 минут).
Установка плагинов по ссылке через веб (AdminPanel)
Список плагинов, который сервер раздаёт всем клиентам через /lampainit.js и /on.js, собирается по LampaWeb.initPlugins + LampaWeb.customPlugins. Watcher перечитывает init.conf без перезапуска (интервал ~1 с, runtime-параметры применяются на лету).
- Открой http://localhost:9118/adminpanel, введи root-пароль (содержимое
config/passwd) — пароль сохраняется в cookieaccspasswd(штатный механизм root-авторизации). - В редакторе
init.confоткрой секциюLampaWeb→customPluginsи добавь запись:Поддерживается плейсхолдер{ "url": "https://example.com/plugin.js", "status": 1, "name": "ИмяПлагина" }{localhost}— сервер подставит свой адрес. - Сохрани — перезапуск не нужен. Проверка:
curl -s http://localhost:9118/lampainit.js | grep <имя>.
Нюансы:
status: 1— активная запись.- Family-dedup:
name.jsиname/js/{token}считаются одним плагином; если в registry клиента уже есть один вариант, второй из серверного списка не добавляется. - Внешние URL должны быть доступны из браузеров клиентов и отдавать CORS-заголовки.
- Альтернатива без сервера: вставить ссылку напрямую в веб-клиенте Lampa (настройки → «Плагины») — тогда плагин живёт только в localStorage этого браузера и грузится браузером напрямую.
API (для скриптов): GET/POST /adminpanel/api/init, POST /adminpanel/api/init/section/{key} с cookie accspasswd=<root-пароль>.
Каталог плагинов (раздел «Плагины» в веб-клиенте)
В веб-клиенте Lampa раздел «Плагины» грузит каталог (store) с маршрута /extensions (включается при LampaWeb.initPlugins.pirate_store: true). Содержимое берётся из файла LampaWeb/plugins/extensions.json модуля — у нас он переопределён файловым mount из ./plugins/extensions.json (см. docker-compose.yaml). Плейсхолдер {localhost} в ссылках сервер заменяет своим адресом.
Все плагины каталога размещены локально (mirror): .js-файлы лежат в ./plugins/, каталог целиком смонтирован в /lampac/wwwroot/plugins/ (одна строка в compose) и ссылки в каталоге ведут на {localhost}/plugins/<имя>.js. (Целиком в корень wwwroot монтировать нельзя — перекроется веб-клиент lampa-main.) Сами файлы плагинов всегда локальные; исключение — плагин-лоадеры, подгружающие основной код с внешнего хоста: «Клубничка 18+» (rc.bwa.ad) и Showy (showy.online/online.js — файл локально патчен под абсолютный URL, иначе он бы подгружал /online.js с нашего сервера). Остальные скачаны целиком (для pubtorr / torrentmanager / td скачано тело, а не лоадер).
plugins/sources.json— карта «локальный файл → исходный URL». Для обновления плагина: скачать файл по исходному URL, перезаписать локальный, перезапуск не нужен.plugins/modss.js— локальная patched-копия MODS's (заменён вызовLampa.Utils.isPWA()), раздаётся как/plugins/modss.js, но из каталога исключена (upstream мёртв: загрузчик отвечает stub-ошибкой «Используйте: lampa.mx»). Вернуть карточку можно, добавив запись сlink: "{localhost}/plugins/modss.js".
Удалены из каталога (мёртвы upstream, проверено по факту выдачи):
- «MODS's» (
lampa.stream/modss) — загрузчик отвечает stub-ошибкой; - «Отзывы и рецензии» (
lampaplugins.github.io/store/o.js) — файл заменён автором на пустой stub; - «Вторая кнопка Торренты», «Поиск локального TorrServer», «Горячие кнопки», «Золотая Тема», «Тип управления», «Старый стиль», «Мультфильмы» — публичных копий нет;
- «Телевидение by Skaz» / «ТВ by skaz» / «ТВ by skaz 2.0» — файлы заменены placeholder-заглушками;
- «Импорт/Экспорт закладок, истории» (
skaz.tv/export.js) — 404.
Важный нюанс — диск-кеш ответа: маршруты LampaWeb кешируют ответы в cache/static/<bucket>/<id>.json (том ./cache), кеш переживает рестарт контейнера. После правки extensions.json для мгновенного применения удалить закешированную запись:
rm -rf cache/static/59 # bucket /extensions; либо rm -rf cache/static
Перезапуск контейнера при этом не требуется (маршрут читает файл при каждом запросе, если нет кеш-записи).
Tg-notify.bot: Telegram-бот уведомлений о новых сериях
Фоновый Telegram-бот (long polling): пользователь подписывается на сериал прямо из карточки Lampa, бот отслеживает выход новых эпизодов и появление выбранной озвучки и шлёт в Telegram уведомление с обложкой, номером серии и описанием из TMDB.
Модуль объединяет три подсистемы:
- Трекер новых серий — Trakt API (если задан
trakt_client_id), иначе TMDB. - Трекер озвучек — параллельный опрос встроенных балансиров Mirage, Collaps и VideoHub через
lampac_host(/lite/mirage,/lite/collaps,/lite/cdnvideohub); берётся максимальный эпизод из всех источников. - Клиентский плагин
tg-notify.js— вкладка «TG Подписки», перехват кнопки 🔔 в карточке, меню выбора озвучки.
Как это работает (поток)
-
Привязка аккаунта — во вкладке «TG Подписки» в Lampa выдаётся deep-link
/start link_{uid}(для UID вида email —/start link64_{base64url(uid)}). После/startбот сохраняет связкуchat_id ↔ lampac_uidвdatabase/tgnotify/users.json; подписки становятся общими для всех устройств этого аккаунта. -
Подписка — в карточке сериала кнопка 🔔 перехватывается плагином, показывается меню озвучек (
GET /api/tg/voices), выбор уходит наPOST /api/tg/subscribeи сохраняется вsubscriptions.json. -
Фоновый цикл
CheckAll— раз вcheck_interval_minutes(первый прогон — через 2 минуты после старта, вручную —/check): новые серии через Trakt→TMDB; если выбрана конкретная озвучка — параллельно Mirage + Collaps + VideoHub. -
Уведомление — сообщение вида:
🎬 Название 🎙 Озвучка 📺 S05E08 — Название эпизода Описание (до 300 символов)с обложкой кадра из TMDB (
still_path), если есть.
Конфигурация (секция TelegramBot в config/init.conf)
| Поле | Назначение |
|---|---|
bot_token |
Токен от @BotFather. Обязателен — без него long polling не стартует (в логе предупреждение, сервер работает) |
tmdb_api_key |
Ключ TMDB v3: обложки, описания эпизодов, определение актуального сезона |
trakt_client_id |
Client ID Trakt; основной источник новых серий (если пуст — только TMDB) |
lampac_host |
Базовый URL Lampac для запросов к балансерам; в Docker — http://127.0.0.1:9118 |
lampac_token |
Токен accsdb; обязателен, если включена защита (иначе балансеры вернут ошибку входа) |
kp_api_key |
Ключ kinopoiskapiunofficial.tech — резолвинг tmdb_id → kinopoisk_id по названию для VideoHub (опционально; без него покрытие ~40% через мост /externalids) |
check_interval_minutes |
Период фоновой проверки (дефолт 60) |
tmdb_lang |
Язык метаданных TMDB (дефолт ru-RU, фоллбэк en-US) |
data_dir |
Каталог users.json/subscriptions.json (дефолт database/tgnotify — у нас это том ./database/, переживает рестарты) |
Быстрый старт
- @BotFather →
/newbot→ получить токен. config/init.conf→TelegramBot.bot_token= токен.docker compose restart lampac(по желанию — заполнитьtmdb_api_keyиtrakt_client_id).- В Lampa (http://localhost:9118) вкладка «TG Подписки» → deep-link →
/startу бота. - В карточке сериала — 🔔, выбрать озвучку (или «без озвучки» — уведомление о самом факте выхода серии).
Команды бота
| Команда | Действие |
|---|---|
/start |
Приветствие; /start link_{uid} — привязка аккаунта |
/list |
Список активных подписок |
/check |
Принудительная проверка в фоне |
/help |
Справка |
/unlink |
Отвязать аккаунт |
HTTP API
| Метод | Маршрут | Назначение |
|---|---|---|
GET |
/tg-notify.js |
Раздача клиентского плагина (AllowAnonymous) |
POST |
/api/tg/subscribe |
Подписка на сериал/озвучку |
POST |
/api/tg/unsubscribe |
Отписка |
GET |
/api/tg/status?tmdb_id= |
Статус подписки текущего пользователя |
GET |
/api/tg/voices?title=&year=&season=&tmdb_id= |
Доступные озвучки (Mirage + Collaps + VideoHub) |
GET |
/api/tg/link |
Deep-link для привязки бота |
GET |
/api/tg/subscriptions |
Все подписки пользователя с метаданными |
Все маршруты, кроме /tg-notify.js и /api/tg/voices, требуют requestInfo.user_uid (вход в аккаунт).
Состояние на нашем инстансе
- Модуль загружен,
/tg-notify.js→ 200, плагин уже вLampaWeb.customPlugins, вкладка «TG Подписки» видна. bot_tokenпуст → long polling не работает (лог:[TelegramBot] Установите bot_token…); уведомления придут только после заполнения токена.- Трекинг озвучек зависит от балансиров: на текущий момент
GET /lite/mirage→ телоdisable,GET /lite/collaps→503— до тех пор, пока они не будут доступны (или не включитсяlampac_tokenпри защите), бот будет уведомлять только о выходе серий (TMDB/Trakt).
Обновление Lampac
docker compose pull
docker compose up -d
Перед обновлением проверить, что в docker-compose.yaml раскомментированы нужные тома. Данные сохраняются в примонтированных томах: config/, cache/, database/, dlna/, mods/. Изображение закреплено на конкретном теге — при обновлении поменяй тег в docker-compose.yaml.
Безопасность
По предупреждению официальной документации:
- Не публикуй в интернет без аутентификации, WAF и ограничения сети:
/adminpanel,/weblog,/database-editor,Tracks,Transcoding,Catalog,DLNA, proxy-модули. - Нигде не раскрывай
config/passwd, cookieaccspasswd, заголовокlcrqpasswd. - Для публикации за reverse proxy: deployment/reverse-proxy (HTTPS в ответах, реальный IP клиента, WebSocket, SSE, streaming).
shm_size: 4096mb— рекомендованный минимум для Playwright/Chromium.