mirror of
https://github.com/BEDOLAGA-DEV/remnawave-bedolaga-telegram-bot.git
synced 2026-02-23 21:01:17 +00:00
Merge pull request #439 from Fr1ngg/revert-438-bedolaga/add-payment-testing-options-in-admin-settings-5pai8v
Revert "Add payment testing actions to admin bot configuration"
This commit is contained in:
@@ -1,7 +1,6 @@
|
||||
import logging
|
||||
import math
|
||||
import time
|
||||
from typing import Iterable, List, Optional, Tuple
|
||||
from typing import Iterable, List, Tuple
|
||||
|
||||
from aiogram import Dispatcher, F, types
|
||||
from aiogram.filters import BaseFilter, StateFilter
|
||||
@@ -11,16 +10,9 @@ from sqlalchemy.ext.asyncio import AsyncSession
|
||||
from app.database.models import User
|
||||
from app.localization.texts import get_texts
|
||||
from app.services.remnawave_service import RemnaWaveService
|
||||
from app.services.payment_service import PaymentService
|
||||
from app.services.tribute_service import TributeService
|
||||
from app.services.system_settings_service import bot_configuration_service
|
||||
from app.states import BotConfigStates
|
||||
from app.utils.decorators import admin_required, error_handler
|
||||
from app.config import settings
|
||||
from app.utils.currency_converter import currency_converter
|
||||
|
||||
|
||||
logger = logging.getLogger(__name__)
|
||||
|
||||
|
||||
CATEGORY_PAGE_SIZE = 10
|
||||
@@ -344,72 +336,6 @@ def _build_settings_keyboard(
|
||||
)
|
||||
]
|
||||
)
|
||||
elif category_key == "YOOKASSA":
|
||||
rows.append(
|
||||
[
|
||||
types.InlineKeyboardButton(
|
||||
text="🧪 Тест YooKassa · 10 ₽",
|
||||
callback_data=(
|
||||
f"botcfg_test_payment:yookassa:{group_key}:{category_key}:{category_page}:{page}"
|
||||
),
|
||||
)
|
||||
]
|
||||
)
|
||||
elif category_key == "TRIBUTE":
|
||||
rows.append(
|
||||
[
|
||||
types.InlineKeyboardButton(
|
||||
text="🧪 Тест Tribute",
|
||||
callback_data=(
|
||||
f"botcfg_test_payment:tribute:{group_key}:{category_key}:{category_page}:{page}"
|
||||
),
|
||||
)
|
||||
]
|
||||
)
|
||||
elif category_key == "MULENPAY":
|
||||
rows.append(
|
||||
[
|
||||
types.InlineKeyboardButton(
|
||||
text="🧪 Тест MulenPay · 1 ₽",
|
||||
callback_data=(
|
||||
f"botcfg_test_payment:mulenpay:{group_key}:{category_key}:{category_page}:{page}"
|
||||
),
|
||||
)
|
||||
]
|
||||
)
|
||||
elif category_key == "PAL24":
|
||||
rows.append(
|
||||
[
|
||||
types.InlineKeyboardButton(
|
||||
text="🧪 Тест Pal24 · 10 ₽",
|
||||
callback_data=(
|
||||
f"botcfg_test_payment:pal24:{group_key}:{category_key}:{category_page}:{page}"
|
||||
),
|
||||
)
|
||||
]
|
||||
)
|
||||
elif category_key == "TELEGRAM":
|
||||
rows.append(
|
||||
[
|
||||
types.InlineKeyboardButton(
|
||||
text="🧪 Тест Stars · 1 ⭐",
|
||||
callback_data=(
|
||||
f"botcfg_test_payment:telegram_stars:{group_key}:{category_key}:{category_page}:{page}"
|
||||
),
|
||||
)
|
||||
]
|
||||
)
|
||||
elif category_key == "CRYPTOBOT":
|
||||
rows.append(
|
||||
[
|
||||
types.InlineKeyboardButton(
|
||||
text="🧪 Тест CryptoBot · 100 ₽",
|
||||
callback_data=(
|
||||
f"botcfg_test_payment:cryptobot:{group_key}:{category_key}:{category_page}:{page}"
|
||||
),
|
||||
)
|
||||
]
|
||||
)
|
||||
|
||||
for definition in sliced:
|
||||
value_preview = bot_configuration_service.format_value_for_list(definition.key)
|
||||
@@ -699,293 +625,6 @@ async def test_remnawave_connection(
|
||||
await callback.answer(message, show_alert=True)
|
||||
|
||||
|
||||
@admin_required
|
||||
@error_handler
|
||||
async def test_payment_system(
|
||||
callback: types.CallbackQuery,
|
||||
db_user: User,
|
||||
db: AsyncSession,
|
||||
):
|
||||
parts = callback.data.split(":", 6)
|
||||
provider = parts[1] if len(parts) > 1 else ""
|
||||
group_key = parts[2] if len(parts) > 2 else CATEGORY_FALLBACK_KEY
|
||||
category_key = parts[3] if len(parts) > 3 else ""
|
||||
|
||||
try:
|
||||
category_page = max(1, int(parts[4])) if len(parts) > 4 else 1
|
||||
except ValueError:
|
||||
category_page = 1
|
||||
|
||||
try:
|
||||
settings_page = max(1, int(parts[5])) if len(parts) > 5 else 1
|
||||
except ValueError:
|
||||
settings_page = 1
|
||||
|
||||
payment_service = PaymentService(callback.bot)
|
||||
|
||||
def _refresh_keyboard() -> None:
|
||||
definitions = bot_configuration_service.get_settings_for_category(category_key)
|
||||
if not definitions:
|
||||
return
|
||||
keyboard = _build_settings_keyboard(
|
||||
category_key,
|
||||
group_key,
|
||||
category_page,
|
||||
db_user.language,
|
||||
settings_page,
|
||||
)
|
||||
try:
|
||||
callback.message.edit_reply_markup(reply_markup=keyboard)
|
||||
except Exception:
|
||||
pass
|
||||
|
||||
def _url_button(text: str, url: str) -> types.InlineKeyboardMarkup:
|
||||
return types.InlineKeyboardMarkup(
|
||||
inline_keyboard=[[types.InlineKeyboardButton(text=text, url=url)]]
|
||||
)
|
||||
|
||||
response_text: Optional[str] = None
|
||||
response_markup: Optional[types.InlineKeyboardMarkup] = None
|
||||
alert_message: Optional[str] = None
|
||||
|
||||
if provider == "yookassa":
|
||||
if not settings.is_yookassa_enabled():
|
||||
alert_message = "YooKassa отключена в конфигурации"
|
||||
else:
|
||||
amount_kopeks = 1_000
|
||||
description = settings.get_balance_payment_description(amount_kopeks)
|
||||
metadata = {
|
||||
"test_payment": True,
|
||||
"initiator": "admin_bot_config",
|
||||
"provider": "yookassa",
|
||||
}
|
||||
result = await payment_service.create_yookassa_payment(
|
||||
db,
|
||||
db_user.id,
|
||||
amount_kopeks,
|
||||
description,
|
||||
metadata=metadata,
|
||||
)
|
||||
if result:
|
||||
confirmation_url = result.get("confirmation_url")
|
||||
status = result.get("status", "unknown")
|
||||
payment_id = result.get("yookassa_payment_id", "—")
|
||||
response_text = (
|
||||
"🧪 <b>Тестовый платеж YooKassa</b>\n\n"
|
||||
f"Сумма: {settings.format_price(amount_kopeks)}\n"
|
||||
f"Статус: {status}\n"
|
||||
f"ID: {payment_id}"
|
||||
)
|
||||
if confirmation_url:
|
||||
response_markup = _url_button("💳 Открыть платеж", confirmation_url)
|
||||
alert_message = "Ссылка на YooKassa платеж отправлена"
|
||||
else:
|
||||
alert_message = "Платеж создан без ссылки подтверждения"
|
||||
else:
|
||||
alert_message = "Не удалось создать тестовый платеж YooKassa"
|
||||
elif provider == "tribute":
|
||||
if not settings.TRIBUTE_ENABLED:
|
||||
alert_message = "Tribute отключен в конфигурации"
|
||||
else:
|
||||
tribute_service = TributeService(callback.bot)
|
||||
try:
|
||||
payment_url = await tribute_service.create_payment_link(
|
||||
user_id=db_user.telegram_id,
|
||||
amount_kopeks=0,
|
||||
description="Тестовое пополнение баланса через Tribute",
|
||||
)
|
||||
except Exception as error:
|
||||
logger.error("Ошибка создания тестового платежа Tribute: %s", error)
|
||||
payment_url = None
|
||||
|
||||
if payment_url:
|
||||
response_text = (
|
||||
"🧪 <b>Тестовое пополнение через Tribute</b>\n\n"
|
||||
"Кнопка работает так же, как в разделе пополнения.\n"
|
||||
"После оплаты проверьте вебхуки и уведомления."
|
||||
)
|
||||
response_markup = _url_button("💳 Перейти к оплате", payment_url)
|
||||
alert_message = "Ссылка для теста Tribute отправлена"
|
||||
else:
|
||||
alert_message = "Не удалось создать ссылку Tribute"
|
||||
elif provider == "mulenpay":
|
||||
if not settings.is_mulenpay_enabled():
|
||||
alert_message = "MulenPay отключен в конфигурации"
|
||||
else:
|
||||
requested_amount = 100
|
||||
description = settings.get_balance_payment_description(requested_amount)
|
||||
result = await payment_service.create_mulenpay_payment(
|
||||
db=db,
|
||||
user_id=db_user.id,
|
||||
amount_kopeks=requested_amount,
|
||||
description=description,
|
||||
language=db_user.language,
|
||||
)
|
||||
if not result and requested_amount < settings.MULENPAY_MIN_AMOUNT_KOPEKS:
|
||||
fallback_amount = settings.MULENPAY_MIN_AMOUNT_KOPEKS
|
||||
fallback_description = settings.get_balance_payment_description(
|
||||
fallback_amount
|
||||
)
|
||||
result = await payment_service.create_mulenpay_payment(
|
||||
db=db,
|
||||
user_id=db_user.id,
|
||||
amount_kopeks=fallback_amount,
|
||||
description=fallback_description,
|
||||
language=db_user.language,
|
||||
)
|
||||
if result:
|
||||
response_text = (
|
||||
"⚠️ <b>Минимальная сумма MulenPay</b>\n\n"
|
||||
f"Запрошено: {settings.format_price(requested_amount)}\n"
|
||||
f"Создан платеж на {settings.format_price(fallback_amount)}"
|
||||
)
|
||||
if result:
|
||||
payment_url = result.get("payment_url")
|
||||
actual_amount = result.get("amount_kopeks", requested_amount)
|
||||
if not response_text:
|
||||
response_text = (
|
||||
"🧪 <b>Тестовый платеж MulenPay</b>\n\n"
|
||||
f"Сумма: {settings.format_price(actual_amount)}"
|
||||
)
|
||||
if payment_url:
|
||||
response_markup = _url_button("💳 Открыть платеж", payment_url)
|
||||
alert_message = "Ссылка для теста MulenPay отправлена"
|
||||
elif not alert_message:
|
||||
alert_message = "Не удалось создать тестовый платеж MulenPay"
|
||||
elif provider == "pal24":
|
||||
if not settings.is_pal24_enabled():
|
||||
alert_message = "Pal24 отключен в конфигурации"
|
||||
else:
|
||||
requested_amount = 1_000
|
||||
description = settings.get_balance_payment_description(requested_amount)
|
||||
result = await payment_service.create_pal24_payment(
|
||||
db=db,
|
||||
user_id=db_user.id,
|
||||
amount_kopeks=requested_amount,
|
||||
description=description,
|
||||
language=db_user.language,
|
||||
)
|
||||
if not result and requested_amount < settings.PAL24_MIN_AMOUNT_KOPEKS:
|
||||
fallback_amount = settings.PAL24_MIN_AMOUNT_KOPEKS
|
||||
fallback_description = settings.get_balance_payment_description(
|
||||
fallback_amount
|
||||
)
|
||||
result = await payment_service.create_pal24_payment(
|
||||
db=db,
|
||||
user_id=db_user.id,
|
||||
amount_kopeks=fallback_amount,
|
||||
description=fallback_description,
|
||||
language=db_user.language,
|
||||
)
|
||||
if result:
|
||||
response_text = (
|
||||
"⚠️ <b>Минимальная сумма Pal24</b>\n\n"
|
||||
f"Запрошено: {settings.format_price(requested_amount)}\n"
|
||||
f"Создан платеж на {settings.format_price(fallback_amount)}"
|
||||
)
|
||||
if result:
|
||||
link_url = (
|
||||
result.get("link_url")
|
||||
or result.get("link_page_url")
|
||||
)
|
||||
actual_amount = result.get("amount_kopeks", requested_amount)
|
||||
if not response_text:
|
||||
response_text = (
|
||||
"🧪 <b>Тестовый платеж Pal24</b>\n\n"
|
||||
f"Сумма: {settings.format_price(actual_amount)}"
|
||||
)
|
||||
if link_url:
|
||||
response_markup = _url_button("💳 Открыть платеж", link_url)
|
||||
alert_message = "Ссылка для теста Pal24 отправлена"
|
||||
elif not alert_message:
|
||||
alert_message = "Не удалось создать тестовый платеж Pal24"
|
||||
elif provider == "telegram_stars":
|
||||
if not payment_service.stars_service:
|
||||
alert_message = "Сервис Telegram Stars недоступен"
|
||||
else:
|
||||
rubles_for_star = settings.stars_to_rubles(1)
|
||||
amount_kopeks = max(1, int(round(rubles_for_star * 100)))
|
||||
payload = f"admin_test_stars_{db_user.id}_{int(time.time())}"
|
||||
description = "Тестовое пополнение через Telegram Stars"
|
||||
try:
|
||||
invoice_link = await payment_service.create_stars_invoice(
|
||||
amount_kopeks=amount_kopeks,
|
||||
description=description,
|
||||
payload=payload,
|
||||
)
|
||||
except Exception as error:
|
||||
logger.error("Ошибка создания Stars invoice: %s", error)
|
||||
invoice_link = None
|
||||
|
||||
if invoice_link:
|
||||
stars_amount = settings.rubles_to_stars(amount_kopeks / 100)
|
||||
response_text = (
|
||||
"🧪 <b>Тестовый платеж Telegram Stars</b>\n\n"
|
||||
f"Сумма: ≈{stars_amount} ⭐ ({settings.format_price(amount_kopeks)})"
|
||||
)
|
||||
response_markup = _url_button("⭐ Открыть счет", invoice_link)
|
||||
alert_message = "Ссылка на Stars invoice отправлена"
|
||||
else:
|
||||
alert_message = "Не удалось создать Stars invoice"
|
||||
elif provider == "cryptobot":
|
||||
if not payment_service.cryptobot_service:
|
||||
alert_message = "CryptoBot недоступен"
|
||||
else:
|
||||
rub_amount = 100.0
|
||||
try:
|
||||
amount_usd = await currency_converter.rub_to_usd(rub_amount)
|
||||
except Exception as error:
|
||||
logger.error("Ошибка конвертации RUB в USD: %s", error)
|
||||
amount_usd = rub_amount / 100 # запасное значение ~1 USD
|
||||
amount_usd = round(amount_usd, 2)
|
||||
payload = f"admin_test_cryptobot_{db_user.id}_{int(time.time())}"
|
||||
description = "Тестовое пополнение через CryptoBot"
|
||||
result = await payment_service.create_cryptobot_payment(
|
||||
db=db,
|
||||
user_id=db_user.id,
|
||||
amount_usd=amount_usd,
|
||||
description=description,
|
||||
payload=payload,
|
||||
)
|
||||
if result:
|
||||
invoice_url = (
|
||||
result.get("web_app_invoice_url")
|
||||
or result.get("bot_invoice_url")
|
||||
or result.get("mini_app_invoice_url")
|
||||
)
|
||||
response_text = (
|
||||
"🧪 <b>Тестовый платеж CryptoBot</b>\n\n"
|
||||
f"Сумма: 100 ₽ (≈{amount_usd} USD)"
|
||||
)
|
||||
if invoice_url:
|
||||
response_markup = _url_button("💳 Открыть счет", invoice_url)
|
||||
alert_message = "Ссылка для теста CryptoBot отправлена"
|
||||
else:
|
||||
alert_message = "Не удалось создать счет CryptoBot"
|
||||
else:
|
||||
await callback.answer("Неизвестный провайдер", show_alert=True)
|
||||
return
|
||||
|
||||
if response_text:
|
||||
await callback.message.answer(
|
||||
response_text,
|
||||
reply_markup=response_markup,
|
||||
parse_mode="HTML",
|
||||
)
|
||||
elif response_markup:
|
||||
await callback.message.answer(
|
||||
"🧪 Тестовый платеж",
|
||||
reply_markup=response_markup,
|
||||
)
|
||||
|
||||
_refresh_keyboard()
|
||||
|
||||
if alert_message:
|
||||
await callback.answer(alert_message, show_alert=True)
|
||||
else:
|
||||
await callback.answer("Готово")
|
||||
|
||||
|
||||
@admin_required
|
||||
@error_handler
|
||||
async def show_bot_config_setting(
|
||||
@@ -1325,10 +964,6 @@ def register_handlers(dp: Dispatcher) -> None:
|
||||
test_remnawave_connection,
|
||||
F.data.startswith("botcfg_test_remnawave:"),
|
||||
)
|
||||
dp.callback_query.register(
|
||||
test_payment_system,
|
||||
F.data.startswith("botcfg_test_payment:"),
|
||||
)
|
||||
dp.callback_query.register(
|
||||
show_bot_config_setting,
|
||||
F.data.startswith("botcfg_setting:"),
|
||||
|
||||
Reference in New Issue
Block a user