Files
tg_bot_language/bot/handlers/reminder.py

174 lines
6.2 KiB
Python

from aiogram import Router, F
from aiogram.filters import Command
from aiogram.types import Message, InlineKeyboardMarkup, InlineKeyboardButton, CallbackQuery
from aiogram.fsm.context import FSMContext
from aiogram.fsm.state import State, StatesGroup
from database.db import async_session_maker
from services.user_service import UserService
from utils.i18n import t
router = Router()
class ReminderStates(StatesGroup):
"""Состояния для настройки напоминаний"""
waiting_for_time = State()
@router.message(Command("reminder"))
async def cmd_reminder(message: Message):
"""Обработчик команды /reminder"""
async with async_session_maker() as session:
user = await UserService.get_user_by_telegram_id(session, message.from_user.id)
if not user:
await message.answer(t('ru', 'common.start_first'))
return
lang = (user.language_interface if user else 'ru') or 'ru'
status = t(lang, 'reminder.status_on') if user.reminders_enabled else t(lang, 'reminder.status_off')
time_text = user.daily_task_time if user.daily_task_time else t(lang, 'reminder.time_not_set')
text = (
t(lang, 'reminder.title') + "\n\n" +
t(lang, 'reminder.status_line', status=status) + "\n" +
t(lang, 'reminder.time_line', time=time_text) + "\n\n" +
t(lang, 'reminder.desc1') + "\n" +
t(lang, 'reminder.desc2')
)
# Создаем кнопки
keyboard = []
if user.reminders_enabled:
keyboard.append([
InlineKeyboardButton(text=t(lang, 'reminder.btn_disable'), callback_data="reminder_disable")
])
else:
keyboard.append([
InlineKeyboardButton(text=t(lang, 'reminder.btn_enable'), callback_data="reminder_enable")
])
keyboard.append([
InlineKeyboardButton(text=t(lang, 'reminder.btn_change_time'), callback_data="reminder_set_time")
])
reply_markup = InlineKeyboardMarkup(inline_keyboard=keyboard)
await message.answer(text, reply_markup=reply_markup)
@router.callback_query(F.data == "reminder_enable")
async def enable_reminders(callback: CallbackQuery):
"""Включить напоминания"""
async with async_session_maker() as session:
user = await UserService.get_user_by_telegram_id(session, callback.from_user.id)
if not user.daily_task_time:
await callback.answer(
t(user.language_interface or 'ru', 'reminder.set_time_first'),
show_alert=True
)
return
user.reminders_enabled = True
await session.commit()
lang = (user.language_interface if user else 'ru') or 'ru'
await callback.answer(t(lang, 'reminder.enabled_toast'))
await callback.message.edit_text(
t(lang, 'reminder.enabled_title') + "\n\n" +
t(lang, 'reminder.time_line', time=user.daily_task_time) + "\n\n" +
t(lang, 'reminder.enabled_desc')
)
@router.callback_query(F.data == "reminder_disable")
async def disable_reminders(callback: CallbackQuery):
"""Выключить напоминания"""
async with async_session_maker() as session:
user = await UserService.get_user_by_telegram_id(session, callback.from_user.id)
user.reminders_enabled = False
await session.commit()
lang = (user.language_interface if user else 'ru') or 'ru'
await callback.answer(t(lang, 'reminder.disabled_toast'))
await callback.message.edit_text(
t(lang, 'reminder.disabled_title') + "\n\n" +
t(lang, 'reminder.disabled_desc')
)
@router.callback_query(F.data == "reminder_set_time")
async def set_reminder_time_prompt(callback: CallbackQuery, state: FSMContext):
"""Запросить время для напоминаний"""
await state.set_state(ReminderStates.waiting_for_time)
async with async_session_maker() as session:
user = await UserService.get_user_by_telegram_id(session, callback.from_user.id)
lang = (user.language_interface if user else 'ru') or 'ru'
await callback.message.edit_text(
t(lang, 'reminder.set_title') + "\n\n" +
t(lang, 'reminder.set_desc') + "\n\n" +
t(lang, 'reminder.set_examples') + "\n\n" +
t(lang, 'reminder.set_utc_hint') + "\n\n" +
t(lang, 'reminder.cancel_hint')
)
await callback.answer()
@router.message(Command("cancel"), ReminderStates.waiting_for_time)
async def cancel_set_time(message: Message, state: FSMContext):
"""Отменить установку времени"""
await state.clear()
await message.answer(t('ru', 'reminder.cancelled'))
@router.message(ReminderStates.waiting_for_time)
async def process_reminder_time(message: Message, state: FSMContext):
"""Обработать введённое время"""
time_str = message.text.strip()
# Валидация формата HH:MM
try:
parts = time_str.split(':')
if len(parts) != 2:
raise ValueError()
hour, minute = int(parts[0]), int(parts[1])
if not (0 <= hour <= 23 and 0 <= minute <= 59):
raise ValueError()
# Формат OK
formatted_time = f"{hour:02d}:{minute:02d}"
except:
await message.answer(t('ru', 'reminder.invalid_format'))
return
# Сохраняем время
async with async_session_maker() as session:
user = await UserService.get_user_by_telegram_id(session, message.from_user.id)
user.daily_task_time = formatted_time
# Автоматически включаем напоминания
user.reminders_enabled = True
await session.commit()
await state.clear()
async with async_session_maker() as session:
user = await UserService.get_user_by_telegram_id(session, message.from_user.id)
lang = (user.language_interface if user else 'ru') or 'ru'
await message.answer(
t(lang, 'reminder.time_set_title') + "\n\n" +
t(lang, 'reminder.time_line', time=formatted_time) + "\n" +
t(lang, 'reminder.status_on_line') + "\n\n" +
t(lang, 'reminder.enabled_desc') + "\n" +
t(lang, 'reminder.use_settings')
)