feat: мини-игры, premium подписка, улучшенные контексты

Мини-игры (/games):
- Speed Round: 10 раундов, 10 секунд на ответ, очки за скорость
- Match Pairs: 5 слов + 5 переводов, соединить пары

Premium-функции:
- Поля is_premium и premium_until для пользователей
- AI режим проверки ответов (учитывает синонимы)
- Batch проверка всех ответов одним запросом

Улучшения:
- Примеры использования для всех добавляемых слов
- Разбиение переводов по запятой на отдельные записи
- Полные предложения в контекстах (без ___)

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
This commit is contained in:
2025-12-10 19:42:10 +03:00
parent b74ea2170c
commit adc8a6bf8e
18 changed files with 1819 additions and 34 deletions

View File

@@ -170,7 +170,7 @@ async def add_single_word(callback: CallbackQuery, state: FSMContext):
# Добавляем слово
translation_lang = get_user_translation_lang(user)
await VocabularyService.add_word(
new_word = await VocabularyService.add_word(
session=session,
user_id=user_id,
word_original=word_data['word'],
@@ -182,6 +182,16 @@ async def add_single_word(callback: CallbackQuery, state: FSMContext):
source=WordSource.SUGGESTED
)
# Добавляем переводы в word_translations (разбиваем по запятой)
await VocabularyService.add_translation_split(
session=session,
vocabulary_id=new_word.id,
translation=word_data['translation'],
context=word_data.get('example'),
context_translation=word_data.get('example_translation'),
is_primary=True
)
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'
@@ -215,7 +225,7 @@ async def add_all_words(callback: CallbackQuery, state: FSMContext):
# Добавляем слово
translation_lang = get_user_translation_lang(user)
await VocabularyService.add_word(
new_word = await VocabularyService.add_word(
session=session,
user_id=user_id,
word_original=word_data['word'],
@@ -226,6 +236,16 @@ async def add_all_words(callback: CallbackQuery, state: FSMContext):
difficulty_level=data.get('level'),
source=WordSource.SUGGESTED
)
# Добавляем переводы в word_translations (разбиваем по запятой)
await VocabularyService.add_translation_split(
session=session,
vocabulary_id=new_word.id,
translation=word_data['translation'],
context=word_data.get('example'),
context_translation=word_data.get('example_translation'),
is_primary=True
)
added_count += 1
lang = (user.language_interface if user else 'ru') or 'ru'