Files
malenia/texts.py
hexdev 606aa4b89f feat: add admin promotion broadcast system and psql health check
- Add `/push` command for admins to broadcast messages to all users
  with approve/decline confirmation flow (handlers/ads.py)
- Add common handler for undefined commands and delete callback
- Add `UserRepository.get_users()` to fetch all users
- Add `UserService.send_promotion_to_users()` with error logging
- Add promotion confirmation keyboard and FSM state
- Add PostgreSQL availability check in startup.sh before migrations
- Add new text constants for promotion flow
2026-04-15 20:19:07 +07:00

222 lines
8.3 KiB
Python
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
from db.models.tickets import TicketStatus
# ============================================================
# PREMIUM EMOJI
# ============================================================
class PremiumEmoji:
def __init__(self, emoji_id: int, emoji: str):
self.emoji_id = emoji_id
self.emoji = emoji
def __str__(self) -> str:
return f'<tg-emoji emoji-id="{self.emoji_id}">{self.emoji}</tg-emoji>'
# — Иконки бота
MALENIA_LOGO = PremiumEmoji(5265053829522562789, "☀️")
MALENIA_HEART = PremiumEmoji(5276516908257025723, "❤️")
MALENIA_LINK = PremiumEmoji(5276012730636082950, "🔗")
MALENIA_COINS = PremiumEmoji(5276298354551199712, "🪙")
MALENIA_LOCKED = PremiumEmoji(5276346642868508688, "🔒")
MALENIA_SUPPORT = PremiumEmoji(5275968088746006467, "🎧")
# ============================================================
# МАППИНГИ
# ============================================================
TICKET_STATUS_EMOJIS = {
TicketStatus.CLOSED.value: "🌑", # Более сдержанно
TicketStatus.OPEN.value: "📡", # В эфире
TicketStatus.PENDING.value: "",
}
# ============================================================
# СТАТУСЫ ПОДПИСКИ
# ============================================================
# — Иконки статусов
STATUS_ICON_ACTIVE = "🟢"
STATUS_ICON_DISABLED = ""
STATUS_ICON_EXPIRED = "🔴"
STATUS_ICON_LIMITED = "🟠"
STATUS_ICON_UNKNOWN = ""
# — Тексты статусов
STATUS_ACTIVE = "работает"
STATUS_DISABLED = "отключена"
STATUS_EXPIRED = "срок вышел"
STATUS_LIMITED = "трафик на нуле"
STATUS_UNKNOWN = "выясняем"
# ============================================================
# ФОРМАТИРОВАНИЕ ДАННЫХ
# ============================================================
# — Дни до истечения подписки
DAYS_LEFT_POSITIVE = "{days} дн."
DAYS_LEFT_EXPIRED = "истекла {days} дн. назад"
DAYS_LEFT_TODAY = "доживает последний день"
# — Username
NO_USERNAME = "скрыт"
USERNAME_DISPLAY = "@{username}"
# — Internal Squads
NO_SQUADS = "отсутствуют"
# — HWID лимит
UNLIMITED_HWID = "без лимитов"
# — Трафик
NO_TRAFFIC_LIMIT = "не ограничен"
TRAFFIC_WITH_LIMIT = "{used} / {limit}"
TRAFFIC_NO_LIMIT = "{used}"
# — Прочее
NOTHING_PLACEHOLDER = ""
# ============================================================
# ПОЛЬЗОВАТЕЛЬСКИЙ ИНТЕРФЕЙС
# ============================================================
MAIN_MENU = (
str(MALENIA_LOGO)
+ " <b>Malenia — <i>{quote}</i></b>\n\n"
+ f"<i>{MALENIA_COINS} Личный кабинет</i>\n"
+ f"<b>{MALENIA_LINK} Ключ доступа: <code>{{link}}</code></b>"
)
FAQ_TEXT = (
"<b>FAQ: Технический минимум</b>\n\n"
"Здесь нет магии и «инновационных прорывов». Только обфускация трафика и стабильные узлы. "
"Если что-то не грузится — скорее всего, фильтры опять пробуют новые сигнатуры. "
"Мы это уже чиним."
)
GENERAL_PROCESSING = "<i>⏳ Проверяем пакеты...</i>"
STANDARD_FALLBACK = "<b>❌ Ошибка в логике.</b> Прожмите /start. Если не поможет — значит, мы где-то не доглядели за кодом."
CALLBACK_FALLBACK = "❌ Пакет потерян, попробуйте снова"
CONTEXT_REINITIATED = "🌑 Сессия сброшена. Данные могли обновиться."
UNDEFINED_MESSAGE = "❌ Таких команд у нас нет. /start если потерялись."
# ============================================================
# РЕФЕРАЛЬНАЯ СИСТЕМА
# ============================================================
REFERALS_MENU = (
"<b>👥 Реферальная система</b>\n\n"
"Никакого сетевого маркетинга, просто делимся ресурсами.\n"
f"<b>{MALENIA_COINS} На вашем счету:</b> "
"<code>{balance}₽</code>\n"
f"<b>{MALENIA_LINK} Ссылка для своих:</b> "
"<code>{link}</code>"
)
# ============================================================
# ОФОРМЛЕНИЕ ПОДПИСКИ
# ============================================================
SUBSCRIPTION_DEVICE_SELECTOR = (
"Сколько девайсов нужно держать в сети одновременно?\n\nЦена вопроса: <b>{price}₽</b>"
)
SUBSCRIPTION_DURATION_SELECTOR = "На какой срок планируем инфраструктуру?\n\nИтого: <b>{price}₽</b>"
WHITELISTS_ALREADY_ON = "Списки доступа уже активны."
CHECKOUT_PAYMENT_CHOICE = (
"Автоплатежи — это не к нам. Стукните в поддержку, там объяснят, куда слать деньги."
)
# ============================================================
# ПОДДЕРЖКА
# ============================================================
SUPPORT_INIT = (
f"<b>{MALENIA_SUPPORT} Технический отдел</b>\n"
"— если интернет превратился в тыкву или есть идеи по конфигам.\n"
"Пишите по делу, скриншоты приветствуются.\n\n"
"<i>🌑 /cancel — вернуться к делам</i>"
)
SUPPORT_MSG_SENT = "⏳ Принято. Инженеры посмотрят, как освободятся. " "Вернуться в меню: /cancel"
SUPPORT_SIGNATURE = "<b>📡 Ответ от Malenia Team:</b>"
# ============================================================
# ШАБЛОНЫ — ОБЩИЕ БЛОКИ
# ============================================================
_SUPPORT_USER_DESCRIPTION = (
"👤 <b>Профиль:</b> {full_name}\n"
"🔗 <b>Alias:</b> {username_display}\n"
"🆔 <b>UID:</b> <code>{telegram_id}</code>\n\n"
"💰 <b>Баланс:</b> <code>{balance}</code>"
)
_DIVIDER = "────────────────────────────\n\n"
# ============================================================
# ШАБЛОНЫ — ЗАЯВКИ И ТИКЕТЫ
# ============================================================
SUPPORT_SUBSCRIPTION = (
"<b>🎫 ВХОДЯЩИЙ ЗАПРОС:</b>\n\n"
+ _SUPPORT_USER_DESCRIPTION
+ "\n"
+ _DIVIDER
+ "🗓️ Срок: <b>{duration} мес.</b>\n"
+ "📱 Устройства: <b>{devices}</b>\n"
+ "🏳️ Whitelists: <b>{whitelist_description}</b>\n\n"
+ "💰 К оплате: <b>{price}₽</b>"
)
ADMIN_TICKET_WITH_RW = (
"🎫 <b>ТИКЕТ T-{ticket_number:04d}</b>\n\n"
+ _SUPPORT_USER_DESCRIPTION
+ "\n"
+ _DIVIDER
+ "📊 <b>ТЕХ. ДАННЫЕ (Remnawave)</b>\n\n"
+ "{status_icon} <b>Статус:</b> {status}\n"
+ "📅 <b>Deadline:</b> {expire_date}\n"
+ "⏳ <b>Остаток:</b> {days_left}\n"
+ "📊 <b>Трафик:</b> {used_traffic}\n"
+ "📱 <b>HWID:</b> {hwid_limit}\n"
+ "🎯 <b>Squads:</b> {squads}\n\n"
+ _DIVIDER
+ "🔑 <b>UUID:</b> <code>{remnawave_uuid}</code>"
)
ADMIN_TICKET_WITHOUT_RW = (
"🎫 <b>ТИКЕТ T-{ticket_number:04d}</b>\n\n"
"👤 <b>Имя:</b> {full_name}\n"
"🔗 <b>Alias:</b> {username_display}\n"
"🆔 <b>UID:</b> <code>{telegram_id}</code>\n\n"
+ _DIVIDER
+ "⚠️ <b>Remnawave-профиль отсутствует</b>"
)
ADMIN_STANDARD_FALLBACK = "<b>❌ Ошибка выполнения.</b> Проверь логи, что-то пошло не по чертежу."
# ============================================================
# АДМИНСКАЯ ХУЙНЯ
# ============================================================
ADMIN_PROMOTION_INIT = "👥 Введите текст рассылки"
ADMIN_PROMOTION_CONFIRMATION = "❓ Отправить сообщение всем пользователям бота?"
SUCCESSFULLY_SENT_PROMOTION = "Успешно разосланно {user_count} пользователям."