mirror of
https://github.com/anten-ka/gotelegram_pro.git
synced 2026-05-19 16:46:03 +00:00
v2.5.0: add local web admin dashboard
This commit is contained in:
@@ -20,6 +20,7 @@ Production-quality Telegram bot for managing MTProxy (telemt engine) on Linux se
|
||||
|
||||
- **Template Browsing** - Browse categories → templates → preview → install
|
||||
- **Per-user MTProxy Keys** - Manage telemt `[access.users]` from inline bot menus
|
||||
- **Local Web Admin** - Shows SSH tunnel instructions for the 127.0.0.1:1984 dashboard
|
||||
- **V1 Migration** - Detects old mtg Docker container and offers migration
|
||||
- **Access Control** - ALLOWED_IDS from .env
|
||||
- **Async/Await** - Full async support via python-telegram-bot v21+
|
||||
|
||||
@@ -117,6 +117,9 @@ PROMO_STAMP_FILE = "/opt/gotelegram/.promo_bot_last_shown"
|
||||
|
||||
BOT_TOKEN = os.getenv("BOT_TOKEN")
|
||||
ENV_FILE = "/opt/gotelegram-bot/.env"
|
||||
ADMIN_WEB_SERVICE = "gotelegram-admin"
|
||||
ADMIN_WEB_TOKEN_FILE = "/opt/gotelegram-admin/token"
|
||||
ADMIN_WEB_PORT = 1984
|
||||
|
||||
# ── Загрузка ALLOWED_IDS ────────────────────────────────────────────────────
|
||||
# Поддерживает запятую, пробел, или их комбинацию как разделитель
|
||||
@@ -521,14 +524,15 @@ def get_main_menu(user_id: Optional[int] = None) -> InlineKeyboardMarkup:
|
||||
InlineKeyboardButton(_t(user_id, "menu_users"), callback_data="menu_users"),
|
||||
],
|
||||
[
|
||||
InlineKeyboardButton(_t(user_id, "menu_remove"), callback_data="menu_remove"),
|
||||
InlineKeyboardButton(_t(user_id, "menu_admin_web"), callback_data="menu_admin_web"),
|
||||
InlineKeyboardButton(_t(user_id, "menu_admins"), callback_data="menu_admins"),
|
||||
],
|
||||
[
|
||||
InlineKeyboardButton(_t(user_id, "menu_remove"), callback_data="menu_remove"),
|
||||
InlineKeyboardButton(_t(user_id, "menu_credits"), callback_data="menu_credits"),
|
||||
InlineKeyboardButton(_t(user_id, "menu_language"), callback_data="menu_lang"),
|
||||
],
|
||||
[
|
||||
InlineKeyboardButton(_t(user_id, "menu_language"), callback_data="menu_lang"),
|
||||
InlineKeyboardButton(_t(user_id, "menu_close"), callback_data="close_menu"),
|
||||
],
|
||||
]
|
||||
@@ -2157,6 +2161,77 @@ async def cb_ssl_status(update: Update, context: ContextTypes.DEFAULT_TYPE) -> N
|
||||
await safe_edit_message(query,text, reply_markup=keyboard, parse_mode="HTML")
|
||||
|
||||
|
||||
def read_admin_web_token() -> str:
|
||||
try:
|
||||
token = Path(ADMIN_WEB_TOKEN_FILE).read_text(encoding="utf-8").strip()
|
||||
return token if len(token) >= 24 else ""
|
||||
except OSError:
|
||||
return ""
|
||||
|
||||
|
||||
async def admin_web_host_hint() -> str:
|
||||
config = load_json(GOTELEGRAM_CONFIG) or {}
|
||||
domain = str(config.get("domain") or "")
|
||||
if domain:
|
||||
return domain
|
||||
code, stdout, _ = await sh("curl", "-s", "-4", "--max-time", "5", "https://api.ipify.org", timeout=7)
|
||||
return stdout.strip() if code == 0 and stdout.strip() else "SERVER_IP"
|
||||
|
||||
|
||||
async def cb_menu_admin_web(update: Update, context: ContextTypes.DEFAULT_TYPE) -> None:
|
||||
query = update.callback_query
|
||||
await query.answer()
|
||||
user_id = _uid(update)
|
||||
running = await check_service_status(ADMIN_WEB_SERVICE)
|
||||
token = read_admin_web_token()
|
||||
host = await admin_web_host_hint()
|
||||
local_url = f"http://127.0.0.1:{ADMIN_WEB_PORT}/?token={token}" if token else f"http://127.0.0.1:{ADMIN_WEB_PORT}/"
|
||||
ssh_cmd = f"ssh -L {ADMIN_WEB_PORT}:127.0.0.1:{ADMIN_WEB_PORT} root@{host}"
|
||||
|
||||
if get_user_lang(user_id) == "ru":
|
||||
status = "запущена" if running else "не запущена"
|
||||
token_note = "Токен найден." if token else "Токен не найден: переустановите/обновите web-admin через CLI."
|
||||
text = (
|
||||
f"<b>🖥 Web Admin</b>\n\n"
|
||||
f"Статус: <code>{status}</code>\n"
|
||||
f"{html.escape(token_note)}\n\n"
|
||||
"<b>Termius</b>\n"
|
||||
"1. Откройте сервер → Port Forwarding.\n"
|
||||
f"2. Добавьте Local tunnel: <code>127.0.0.1:{ADMIN_WEB_PORT}</code> → "
|
||||
f"<code>127.0.0.1:{ADMIN_WEB_PORT}</code>.\n"
|
||||
"3. Запустите tunnel и откройте в браузере:\n"
|
||||
f"<code>{html.escape(local_url)}</code>\n\n"
|
||||
"<b>Обычный SSH</b>\n"
|
||||
f"<code>{html.escape(ssh_cmd)}</code>\n\n"
|
||||
"Админка слушает только localhost на сервере и не публикуется наружу."
|
||||
)
|
||||
else:
|
||||
status = "running" if running else "not running"
|
||||
token_note = "Token is ready." if token else "Token is missing: reinstall/update web-admin from CLI."
|
||||
text = (
|
||||
f"<b>🖥 Web Admin</b>\n\n"
|
||||
f"Status: <code>{status}</code>\n"
|
||||
f"{html.escape(token_note)}\n\n"
|
||||
"<b>Termius</b>\n"
|
||||
"1. Open the server → Port Forwarding.\n"
|
||||
f"2. Add a Local tunnel: <code>127.0.0.1:{ADMIN_WEB_PORT}</code> → "
|
||||
f"<code>127.0.0.1:{ADMIN_WEB_PORT}</code>.\n"
|
||||
"3. Start the tunnel and open:\n"
|
||||
f"<code>{html.escape(local_url)}</code>\n\n"
|
||||
"<b>Regular SSH</b>\n"
|
||||
f"<code>{html.escape(ssh_cmd)}</code>\n\n"
|
||||
"The admin listens only on server localhost and is not exposed publicly."
|
||||
)
|
||||
|
||||
await safe_edit_message(
|
||||
query,
|
||||
text,
|
||||
reply_markup=InlineKeyboardMarkup([[InlineKeyboardButton(_t(user_id, "btn_back"), callback_data="menu_main")]]),
|
||||
parse_mode="HTML",
|
||||
disable_web_page_preview=True,
|
||||
)
|
||||
|
||||
|
||||
# ============================================================================
|
||||
# ADMIN MANAGEMENT
|
||||
# ============================================================================
|
||||
@@ -2516,6 +2591,7 @@ async def handle_callback(update: Update, context: ContextTypes.DEFAULT_TYPE) ->
|
||||
"menu_website": cb_menu_website,
|
||||
"menu_promo": cb_menu_promo,
|
||||
"menu_credits": cb_menu_credits,
|
||||
"menu_admin_web": cb_menu_admin_web,
|
||||
"menu_admins": cb_menu_admins,
|
||||
"menu_users": cb_menu_users,
|
||||
"menu_remove": cb_menu_remove,
|
||||
|
||||
@@ -34,6 +34,7 @@
|
||||
"menu_promo": "🎁 Promo",
|
||||
"menu_stats": "📊 Traffic Stats",
|
||||
"menu_users": "🔑 Keys",
|
||||
"menu_admin_web": "🖥 Web Admin",
|
||||
"menu_remove": "🗑️ Remove",
|
||||
"menu_admins": "👤 Admins",
|
||||
"menu_credits": "ℹ️ Credits",
|
||||
|
||||
@@ -34,6 +34,7 @@
|
||||
"menu_promo": "🎁 Промо",
|
||||
"menu_stats": "📊 Трафик",
|
||||
"menu_users": "🔑 Ключи",
|
||||
"menu_admin_web": "🖥 Web Admin",
|
||||
"menu_remove": "🗑️ Удалить",
|
||||
"menu_admins": "👤 Админы",
|
||||
"menu_credits": "ℹ️ О проекте",
|
||||
|
||||
Reference in New Issue
Block a user