2025-12-04 11:09:54 +03:00
|
|
|
|
from aiogram import Router, F
|
|
|
|
|
|
from aiogram.filters import CommandStart, Command
|
2025-12-04 17:15:49 +03:00
|
|
|
|
from aiogram.types import (
|
|
|
|
|
|
Message,
|
|
|
|
|
|
InlineKeyboardMarkup,
|
|
|
|
|
|
InlineKeyboardButton,
|
|
|
|
|
|
CallbackQuery,
|
|
|
|
|
|
ReplyKeyboardMarkup,
|
|
|
|
|
|
KeyboardButton,
|
|
|
|
|
|
)
|
2025-12-04 11:09:54 +03:00
|
|
|
|
from aiogram.fsm.context import FSMContext
|
|
|
|
|
|
|
|
|
|
|
|
from database.db import async_session_maker
|
|
|
|
|
|
from services.user_service import UserService
|
|
|
|
|
|
|
|
|
|
|
|
router = Router()
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
@router.message(CommandStart())
|
|
|
|
|
|
async def cmd_start(message: Message, state: FSMContext):
|
|
|
|
|
|
"""Обработчик команды /start"""
|
|
|
|
|
|
async with async_session_maker() as session:
|
2025-12-04 16:00:38 +03:00
|
|
|
|
# Проверяем, существует ли пользователь
|
|
|
|
|
|
existing_user = await UserService.get_user_by_telegram_id(session, message.from_user.id)
|
|
|
|
|
|
is_new_user = existing_user is None
|
|
|
|
|
|
|
|
|
|
|
|
# Создаём или получаем пользователя
|
2025-12-04 11:09:54 +03:00
|
|
|
|
user = await UserService.get_or_create_user(
|
|
|
|
|
|
session,
|
|
|
|
|
|
telegram_id=message.from_user.id,
|
|
|
|
|
|
username=message.from_user.username
|
|
|
|
|
|
)
|
|
|
|
|
|
|
2025-12-04 16:00:38 +03:00
|
|
|
|
if is_new_user:
|
|
|
|
|
|
# Новый пользователь
|
2025-12-04 11:09:54 +03:00
|
|
|
|
await message.answer(
|
|
|
|
|
|
f"👋 Привет, {message.from_user.first_name}!\n\n"
|
|
|
|
|
|
f"Я бот для изучения английского языка. Помогу тебе:\n"
|
Добавлены основные функции MVP: тематические подборки, импорт слов, диалоговая практика, напоминания и тест уровня
Новые команды:
- /words [тема] - AI-генерация тематических подборок слов (10 слов по теме с учётом уровня)
- /import - извлечение до 15 ключевых слов из текста (книги, статьи, песни)
- /practice - диалоговая практика с AI в 6 сценариях (ресторан, магазин, путешествие, работа, врач, общение)
- /reminder - настройка ежедневных напоминаний по расписанию
- /level_test - тест из 7 вопросов для определения уровня английского (A1-C2)
Основные изменения:
- AI сервис: добавлены методы generate_thematic_words, extract_words_from_text, start_conversation, continue_conversation, generate_level_test
- Диалоговая практика: исправление ошибок в реальном времени, подсказки, перевод реплик
- Напоминания: APScheduler для ежедневной отправки напоминаний в выбранное время
- Тест уровня: автоматическое определение уровня при регистрации, можно пропустить
- База данных: добавлены поля reminders_enabled, last_reminder_sent
- Vocabulary service: метод get_word_by_original для проверки дубликатов
- Зависимости: apscheduler==3.10.4
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
2025-12-04 15:46:02 +03:00
|
|
|
|
f"📚 Пополнять словарный запас (ручное/тематическое/из текста)\n"
|
|
|
|
|
|
f"✍️ Выполнять интерактивные задания\n"
|
|
|
|
|
|
f"💬 Практиковать язык в диалоге с AI\n"
|
|
|
|
|
|
f"📊 Отслеживать свой прогресс\n\n"
|
2025-12-04 16:00:38 +03:00
|
|
|
|
f"<b>Команды:</b>\n"
|
|
|
|
|
|
f"• /add [слово] - добавить слово\n"
|
|
|
|
|
|
f"• /words [тема] - тематическая подборка\n"
|
|
|
|
|
|
f"• /import - импорт из текста\n"
|
|
|
|
|
|
f"• /vocabulary - мой словарь\n"
|
|
|
|
|
|
f"• /task - задания\n"
|
|
|
|
|
|
f"• /practice - диалог с AI\n"
|
|
|
|
|
|
f"• /stats - статистика\n"
|
|
|
|
|
|
f"• /settings - настройки\n"
|
|
|
|
|
|
f"• /reminder - напоминания\n"
|
2025-12-04 17:15:49 +03:00
|
|
|
|
f"• /help - полная справка",
|
|
|
|
|
|
reply_markup=main_menu_keyboard(),
|
Добавлены основные функции MVP: тематические подборки, импорт слов, диалоговая практика, напоминания и тест уровня
Новые команды:
- /words [тема] - AI-генерация тематических подборок слов (10 слов по теме с учётом уровня)
- /import - извлечение до 15 ключевых слов из текста (книги, статьи, песни)
- /practice - диалоговая практика с AI в 6 сценариях (ресторан, магазин, путешествие, работа, врач, общение)
- /reminder - настройка ежедневных напоминаний по расписанию
- /level_test - тест из 7 вопросов для определения уровня английского (A1-C2)
Основные изменения:
- AI сервис: добавлены методы generate_thematic_words, extract_words_from_text, start_conversation, continue_conversation, generate_level_test
- Диалоговая практика: исправление ошибок в реальном времени, подсказки, перевод реплик
- Напоминания: APScheduler для ежедневной отправки напоминаний в выбранное время
- Тест уровня: автоматическое определение уровня при регистрации, можно пропустить
- База данных: добавлены поля reminders_enabled, last_reminder_sent
- Vocabulary service: метод get_word_by_original для проверки дубликатов
- Зависимости: apscheduler==3.10.4
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
2025-12-04 15:46:02 +03:00
|
|
|
|
)
|
|
|
|
|
|
|
|
|
|
|
|
# Предлагаем пройти тест уровня
|
|
|
|
|
|
keyboard = InlineKeyboardMarkup(inline_keyboard=[
|
|
|
|
|
|
[InlineKeyboardButton(text="📊 Пройти тест уровня", callback_data="offer_level_test")],
|
|
|
|
|
|
[InlineKeyboardButton(text="➡️ Пропустить", callback_data="skip_level_test")]
|
|
|
|
|
|
])
|
|
|
|
|
|
|
|
|
|
|
|
await message.answer(
|
|
|
|
|
|
"🎯 <b>Определим твой уровень?</b>\n\n"
|
|
|
|
|
|
"Короткий тест (7 вопросов) поможет подобрать задания под твой уровень.\n"
|
|
|
|
|
|
"Это займёт 2-3 минуты.\n\n"
|
|
|
|
|
|
"Или можешь пропустить и установить уровень вручную позже в /settings",
|
|
|
|
|
|
reply_markup=keyboard
|
2025-12-04 11:09:54 +03:00
|
|
|
|
)
|
|
|
|
|
|
else:
|
|
|
|
|
|
# Существующий пользователь
|
|
|
|
|
|
await message.answer(
|
|
|
|
|
|
f"С возвращением, {message.from_user.first_name}! 👋\n\n"
|
2025-12-04 16:00:38 +03:00
|
|
|
|
f"Готов продолжить обучение?\n\n"
|
|
|
|
|
|
f"<b>Быстрый доступ:</b>\n"
|
|
|
|
|
|
f"• /vocabulary - посмотреть словарь\n"
|
|
|
|
|
|
f"• /task - получить задание\n"
|
|
|
|
|
|
f"• /practice - практика диалога\n"
|
|
|
|
|
|
f"• /words [тема] - тематическая подборка\n"
|
|
|
|
|
|
f"• /stats - статистика\n"
|
2025-12-04 17:15:49 +03:00
|
|
|
|
f"• /help - все команды",
|
|
|
|
|
|
reply_markup=main_menu_keyboard(),
|
2025-12-04 11:09:54 +03:00
|
|
|
|
)
|
|
|
|
|
|
|
|
|
|
|
|
|
2025-12-04 17:15:49 +03:00
|
|
|
|
@router.message(Command("menu"))
|
|
|
|
|
|
async def cmd_menu(message: Message):
|
|
|
|
|
|
"""Показать клавиатуру с основными командами."""
|
|
|
|
|
|
await message.answer("Главное меню доступно ниже ⤵️", reply_markup=main_menu_keyboard())
|
|
|
|
|
|
|
|
|
|
|
|
|
2025-12-04 11:09:54 +03:00
|
|
|
|
@router.message(Command("help"))
|
|
|
|
|
|
async def cmd_help(message: Message):
|
|
|
|
|
|
"""Обработчик команды /help"""
|
|
|
|
|
|
await message.answer(
|
|
|
|
|
|
"<b>📖 Справка по командам:</b>\n\n"
|
|
|
|
|
|
"<b>Управление словарём:</b>\n"
|
2025-12-04 16:00:38 +03:00
|
|
|
|
"• /add [слово] - добавить слово в словарь\n"
|
|
|
|
|
|
"• /vocabulary - просмотр словаря\n"
|
|
|
|
|
|
"• /words [тема] - тематическая подборка слов\n"
|
|
|
|
|
|
"• /import - импортировать слова из текста\n\n"
|
2025-12-04 11:09:54 +03:00
|
|
|
|
"<b>Обучение:</b>\n"
|
2025-12-04 16:00:38 +03:00
|
|
|
|
"• /task - задание (перевод, заполнение пропусков)\n"
|
|
|
|
|
|
"• /practice - диалог с ИИ (6 сценариев)\n"
|
|
|
|
|
|
"• /level_test - тест определения уровня\n\n"
|
2025-12-04 11:09:54 +03:00
|
|
|
|
"<b>Статистика:</b>\n"
|
2025-12-04 16:00:38 +03:00
|
|
|
|
"• /stats - твой прогресс\n\n"
|
2025-12-04 11:09:54 +03:00
|
|
|
|
"<b>Настройки:</b>\n"
|
2025-12-04 16:00:38 +03:00
|
|
|
|
"• /settings - уровень и язык\n"
|
|
|
|
|
|
"• /reminder - ежедневные напоминания\n\n"
|
|
|
|
|
|
"💡 Ты также можешь просто отправить мне слово, и я предложу добавить его в словарь!"
|
2025-12-04 11:09:54 +03:00
|
|
|
|
)
|
Добавлены основные функции MVP: тематические подборки, импорт слов, диалоговая практика, напоминания и тест уровня
Новые команды:
- /words [тема] - AI-генерация тематических подборок слов (10 слов по теме с учётом уровня)
- /import - извлечение до 15 ключевых слов из текста (книги, статьи, песни)
- /practice - диалоговая практика с AI в 6 сценариях (ресторан, магазин, путешествие, работа, врач, общение)
- /reminder - настройка ежедневных напоминаний по расписанию
- /level_test - тест из 7 вопросов для определения уровня английского (A1-C2)
Основные изменения:
- AI сервис: добавлены методы generate_thematic_words, extract_words_from_text, start_conversation, continue_conversation, generate_level_test
- Диалоговая практика: исправление ошибок в реальном времени, подсказки, перевод реплик
- Напоминания: APScheduler для ежедневной отправки напоминаний в выбранное время
- Тест уровня: автоматическое определение уровня при регистрации, можно пропустить
- База данных: добавлены поля reminders_enabled, last_reminder_sent
- Vocabulary service: метод get_word_by_original для проверки дубликатов
- Зависимости: apscheduler==3.10.4
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
2025-12-04 15:46:02 +03:00
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
@router.callback_query(F.data == "offer_level_test")
|
|
|
|
|
|
async def offer_level_test_callback(callback: CallbackQuery, state: FSMContext):
|
|
|
|
|
|
"""Начать тест уровня из приветствия"""
|
|
|
|
|
|
from bot.handlers.level_test import start_level_test
|
|
|
|
|
|
await callback.message.delete()
|
|
|
|
|
|
await start_level_test(callback.message, state)
|
|
|
|
|
|
await callback.answer()
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
@router.callback_query(F.data == "skip_level_test")
|
|
|
|
|
|
async def skip_level_test_callback(callback: CallbackQuery):
|
|
|
|
|
|
"""Пропустить тест уровня"""
|
|
|
|
|
|
await callback.message.edit_text(
|
|
|
|
|
|
"✅ Хорошо!\n\n"
|
2025-12-04 17:15:49 +03:00
|
|
|
|
def main_menu_keyboard() -> ReplyKeyboardMarkup:
|
|
|
|
|
|
"""Клавиатура с основными командами (кнопки отправляют команды)."""
|
|
|
|
|
|
return ReplyKeyboardMarkup(
|
|
|
|
|
|
resize_keyboard=True,
|
|
|
|
|
|
keyboard=[
|
|
|
|
|
|
[
|
|
|
|
|
|
KeyboardButton(text="/add"),
|
|
|
|
|
|
KeyboardButton(text="/vocabulary"),
|
|
|
|
|
|
],
|
|
|
|
|
|
[
|
|
|
|
|
|
KeyboardButton(text="/task"),
|
|
|
|
|
|
KeyboardButton(text="/practice"),
|
|
|
|
|
|
],
|
|
|
|
|
|
[
|
|
|
|
|
|
KeyboardButton(text="/words travel"),
|
|
|
|
|
|
KeyboardButton(text="/import"),
|
|
|
|
|
|
],
|
|
|
|
|
|
[
|
|
|
|
|
|
KeyboardButton(text="/stats"),
|
|
|
|
|
|
KeyboardButton(text="/settings"),
|
|
|
|
|
|
],
|
|
|
|
|
|
],
|
|
|
|
|
|
)
|
|
|
|
|
|
|
Добавлены основные функции MVP: тематические подборки, импорт слов, диалоговая практика, напоминания и тест уровня
Новые команды:
- /words [тема] - AI-генерация тематических подборок слов (10 слов по теме с учётом уровня)
- /import - извлечение до 15 ключевых слов из текста (книги, статьи, песни)
- /practice - диалоговая практика с AI в 6 сценариях (ресторан, магазин, путешествие, работа, врач, общение)
- /reminder - настройка ежедневных напоминаний по расписанию
- /level_test - тест из 7 вопросов для определения уровня английского (A1-C2)
Основные изменения:
- AI сервис: добавлены методы generate_thematic_words, extract_words_from_text, start_conversation, continue_conversation, generate_level_test
- Диалоговая практика: исправление ошибок в реальном времени, подсказки, перевод реплик
- Напоминания: APScheduler для ежедневной отправки напоминаний в выбранное время
- Тест уровня: автоматическое определение уровня при регистрации, можно пропустить
- База данных: добавлены поля reminders_enabled, last_reminder_sent
- Vocabulary service: метод get_word_by_original для проверки дубликатов
- Зависимости: apscheduler==3.10.4
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
2025-12-04 15:46:02 +03:00
|
|
|
|
"Ты можешь пройти тест позже командой /level_test\n"
|
|
|
|
|
|
"или установить уровень вручную в /settings\n\n"
|
|
|
|
|
|
"Давай начнём! Попробуй:\n"
|
|
|
|
|
|
"• /words travel - тематическая подборка\n"
|
|
|
|
|
|
"• /practice - диалог с AI\n"
|
|
|
|
|
|
"• /add hello - добавить слово"
|
|
|
|
|
|
)
|
|
|
|
|
|
await callback.answer()
|