Files
stcs/app/telegram/handlers/handlers_main.py

320 lines
10 KiB
Python

import logging.config
from aiogram import F, Router
from aiogram.filters import Command
from aiogram.fsm.context import FSMContext
from aiogram.types import CallbackQuery, Message
import app.telegram.keyboards.inline as kbi
import app.telegram.keyboards.reply as kbr
import database.request as rq
from app.bybit.profile_bybit import user_profile_bybit
from app.telegram.functions.profile_tg import user_profile_tg
from logger_helper.logger_helper import LOGGING_CONFIG
logging.config.dictConfig(LOGGING_CONFIG)
logger = logging.getLogger("handlers_main")
router_handlers_main = Router(name="handlers_main")
@router_handlers_main.message(Command("start", "hello"))
@router_handlers_main.message(F.text.lower() == "привет")
async def cmd_start(message: Message, state: FSMContext) -> None:
"""
Handle the /start or /hello commands and the text message "привет".
Checks if the user exists in the database and sends a user profile or creates a new user
with default settings and greeting message.
Args:
message (Message): Incoming Telegram message object.
state (FSMContext): FSMContext for managing user state.
Raises:
None: Exceptions are caught and logged internally.
"""
tg_id = message.from_user.id
username = message.from_user.username
full_name = message.from_user.full_name
user = await rq.get_user(tg_id)
try:
if user:
await user_profile_tg(tg_id=message.from_user.id, message=message)
logger.debug(
"Command start processed successfully for user: %s",
message.from_user.id,
)
else:
await rq.create_user(tg_id=tg_id, username=username)
await rq.set_user_symbol(tg_id=tg_id, symbol="BTCUSDT")
await rq.create_user_additional_settings(tg_id=tg_id)
await rq.create_user_risk_management(tg_id=tg_id)
await rq.create_user_conditional_settings(tg_id=tg_id)
await message.answer(
text=f"Добро пожаловать, {full_name}!\n\n"
"PHANTOM TRADING - ваш надежный помощник для автоматизации трейдинга😉",
reply_markup=kbi.connect_the_platform,
)
logger.debug(
"Command start processed successfully for user: %s",
message.from_user.id,
)
except Exception as e:
logger.error(
"Error processing command start for user %s: %s", message.from_user.id, e
)
await message.answer(text="Произошла ошибка. Пожалуйста, попробуйте позже.")
finally:
await state.clear()
@router_handlers_main.message(Command("profile"))
@router_handlers_main.message(F.text == "Профиль")
async def cmd_to_main(message: Message, state: FSMContext) -> None:
"""
Handle the /profile command or text "Профиль".
Clears the current FSM state and sends the Telegram user profile.
Args:
message (Message): Incoming Telegram message object.
state (FSMContext): FSM state context.
Raises:
None: Exceptions are caught and logged internally.
"""
try:
await user_profile_tg(tg_id=message.from_user.id, message=message)
logger.debug(
"Command to_profile_tg processed successfully for user: %s",
message.from_user.id,
)
except Exception as e:
logger.error(
"Error processing command to_profile_tg for user %s: %s",
message.from_user.id,
e,
)
finally:
await state.clear()
@router_handlers_main.message(Command("bybit"))
@router_handlers_main.message(F.text == "Панель Bybit")
async def profile_bybit(message: Message, state: FSMContext) -> None:
"""
Handle the /bybit command or text "Панель Bybit".
Clears FSM state and sends Bybit trading panel profile.
Args:
message (Message): Incoming Telegram message object.
state (FSMContext): FSM state context.
Raises:
None: Exceptions are caught and logged internally.
"""
try:
await state.clear()
await user_profile_bybit(
tg_id=message.from_user.id, message=message, state=state
)
logger.debug(
"Command to_profile_bybit processed successfully for user: %s",
message.from_user.id,
)
except Exception as e:
logger.error(
"Error processing command to_profile_bybit for user %s: %s",
message.from_user.id,
e,
)
@router_handlers_main.callback_query(F.data == "profile_bybit")
async def profile_bybit_callback(
callback_query: CallbackQuery, state: FSMContext
) -> None:
"""
Handle callback query with data "profile_bybit".
Clears FSM state and sends the Bybit profile in response.
Args:
callback_query (CallbackQuery): Callback query object from Telegram.
state (FSMContext): FSM state context.
Raises:
None: Exceptions are caught and logged internally.
"""
try:
await state.clear()
await user_profile_bybit(
tg_id=callback_query.from_user.id,
message=callback_query.message,
state=state,
)
logger.debug(
"Callback profile_bybit processed successfully for user: %s",
callback_query.from_user.id,
)
await callback_query.answer()
except Exception as e:
logger.error(
"Error processing callback profile_bybit for user %s: %s",
callback_query.from_user.id,
e,
)
@router_handlers_main.callback_query(F.data == "main_settings")
async def settings(callback_query: CallbackQuery, state: FSMContext) -> None:
"""
Handle callback query with data "main_settings".
Clears FSM state and edits the message to show main settings options.
Args:
callback_query (CallbackQuery): Callback query object.
state (FSMContext): FSM state context.
Raises:
None: Exceptions are caught and logged internally.
"""
try:
await state.clear()
msg = await callback_query.message.edit_text(
text="Выберите, что вы хотите настроить:", reply_markup=kbi.main_settings
)
await state.update_data(prompt_message_id=msg.message_id)
logger.debug(
"Command settings processed successfully for user: %s",
callback_query.from_user.id,
)
except Exception as e:
logger.error(
"Error processing command settings for user %s: %s",
callback_query.from_user.id,
e,
)
@router_handlers_main.message(Command("help"))
async def cmd_help(message: Message, state: FSMContext) -> None:
"""
Handle the /help command.
Clears FSM state and sends a help message with available commands and reply keyboard.
Args:
message (Message): Incoming Telegram message object.
state (FSMContext): FSM state context.
Raises:
None: Exceptions are caught and logged internally.
"""
try:
await state.clear()
await message.answer(
text="Используйте одну из следующих команд:\n"
"/start - Запустить бота\n"
"/profile - Профиль\n"
"/bybit - Панель Bybit\n",
reply_markup=kbr.profile,
)
logger.debug(
"Command help processed successfully for user: %s",
message.from_user.id,
)
except Exception as e:
logger.error(
"Error processing command help for user %s: %s", message.from_user.id, e
)
await message.answer(
text="Произошла ошибка. Пожалуйста, попробуйте позже.",
reply_markup=kbr.profile,
)
@router_handlers_main.message(Command("cancel"))
@router_handlers_main.message(
lambda message: message.text.casefold() in ["cancel", "отмена"]
)
async def cmd_cancel_handler(message: Message, state: FSMContext) -> None:
"""
Handle /cancel command or text 'cancel'/'отмена'.
If there is an active FSM state, clears it and informs the user.
Otherwise, informs that no operation was in progress.
Args:
message (Message): Incoming Telegram message object.
state (FSMContext): FSM state context.
Raises:
None: Exceptions are caught and logged internally.
"""
current_state = await state.get_state()
if current_state is None:
await message.reply(
text="Хорошо, но ничего не происходило.", reply_markup=kbr.profile
)
logger.debug(
"Cancel command received but no active state for user %s.",
message.from_user.id,
)
return
try:
await state.clear()
await message.reply(text="Команда отменена.", reply_markup=kbr.profile)
logger.debug(
"Command cancel executed successfully. State cleared for user %s.",
message.from_user.id,
)
except Exception as e:
logger.error(
"Error while cancelling command for user %s: %s", message.from_user.id, e
)
await message.answer(
text="Произошла ошибка при отмене. Пожалуйста, попробуйте позже.",
reply_markup=kbr.profile,
)
@router_handlers_main.callback_query(F.data == "cancel")
async def cmd_cancel(callback_query: CallbackQuery, state: FSMContext) -> None:
"""
Handle callback query with data "cancel".
Clears the FSM state and sends a cancellation message.
Args:
callback_query (CallbackQuery): Callback query object.
state (FSMContext): FSM state context.
Raises:
None: Exceptions are caught and logged internally.
"""
try:
await callback_query.message.delete()
await user_profile_bybit(
tg_id=callback_query.from_user.id,
message=callback_query.message,
state=state,
)
logger.debug(
"Command cancel processed successfully for user: %s",
callback_query.from_user.id,
)
except Exception as e:
logger.error(
"Error processing command cancel for user %s: %s",
callback_query.from_user.id,
e,
)
finally:
await state.clear()