Первый коммит

This commit is contained in:
admin
2025-08-30 07:39:44 +07:00
commit d0baf76f8f
86 changed files with 7362 additions and 0 deletions

View File

@@ -0,0 +1,207 @@
import pytest
from typing import List, Dict
from sqlalchemy import select
from sqlalchemy.ext.asyncio import AsyncSession
from database import Role, RoleRegion, BotDatabase
@pytest.mark.asyncio
class TestRoleSystem:
"""Тесты для системы ролей с полной строгой типизацией"""
async def test_role_creation(self, test_db: BotDatabase, test_session: AsyncSession) -> None:
"""
Тест создания ролей.
Проверяет, что тестовые роли существуют в базе.
"""
stmt = select(Role)
result = await test_session.execute(stmt)
roles: List[Role] = result.scalars().all()
assert len(roles) >= 5
role_names: List[str] = [role.name for role in roles]
assert "Альбедо" in role_names
assert "Нахида" in role_names
assert "Кафка" in role_names
async def test_assign_role(
self, test_db: BotDatabase, test_session: AsyncSession, test_user: int
) -> None:
"""
Тест назначения роли пользователю.
Проверяет успешное назначение свободной роли и правильное сохранение в БД.
"""
user_id: int = test_user
# Освобождаем роль на всякий случай
await test_db.release_role("Альбедо")
# Назначаем роль
success: bool = await test_db.assign_role("Альбедо", user_id)
assert success, "Не удалось назначить роль"
# Проверяем, что роль действительно назначена
stmt = select(Role).where(Role.name == "Альбедо")
result = await test_session.execute(stmt)
role: Role = result.scalar_one()
assert role.occupied_by == user_id
async def test_assign_occupied_role(
self, test_db: BotDatabase, test_session: AsyncSession, test_user: int
) -> None:
"""
Тест назначения уже занятой роли.
Проверяет, что нельзя назначить роль, если она уже занята другим пользователем.
"""
user_id: int = test_user
other_user_id: int = 999000111
await test_db.release_role("Альбедо")
await test_db.add_user(other_user_id, "other_user", "Other User")
# Назначаем роль первому пользователю
success_first: bool = await test_db.assign_role("Альбедо", user_id)
assert success_first, "Не удалось назначить роль первому пользователю"
# Пытаемся назначить ту же роль другому пользователю
success_second: bool = await test_db.assign_role("Альбедо", other_user_id)
assert not success_second, "Нельзя назначить занятую роль"
async def test_release_role(
self, test_db: BotDatabase, test_session: AsyncSession, test_user: int
) -> None:
"""
Тест освобождения роли.
Проверяет, что роль успешно освобождается.
"""
user_id: int = test_user
await test_db.release_role("Нахида")
success_assign: bool = await test_db.assign_role("Нахида", user_id)
assert success_assign
success_release: bool = await test_db.release_role("Нахида")
assert success_release
stmt = select(Role).where(Role.name == "Нахида")
result = await test_session.execute(stmt)
role: Role = result.scalar_one()
assert role.occupied_by is None
async def test_release_unoccupied_role(self, test_db: BotDatabase) -> None:
"""
Тест освобождения свободной роли.
Проверяет, что нельзя освободить уже свободную роль.
"""
await test_db.release_role("Кафка")
success: bool = await test_db.release_role("Кафка")
assert not success, "Нельзя освободить свободную роль"
async def test_get_user_roles(
self, test_db: BotDatabase, test_session: AsyncSession, test_user: int
) -> None:
"""
Тест получения ролей пользователя.
Проверяет, что возвращается корректный список назначенных ролей.
"""
user_id: int = test_user
await test_db.release_role("Альбедо")
await test_db.release_role("Нахида")
success1: bool = await test_db.assign_role("Альбедо", user_id)
success2: bool = await test_db.assign_role("Нахида", user_id)
assert success1 and success2
roles: List[str] = await test_db.get_roles_by_user(user_id)
assert len(roles) == 2
assert "Альбедо" in roles
assert "Нахида" in roles
async def test_get_available_roles(
self, test_db: BotDatabase, test_session: AsyncSession, test_user: int
) -> None:
"""
Тест получения доступных ролей.
Проверяет, что назначенные роли не включены в список свободных.
"""
user_id: int = test_user
# Освобождаем все роли
for role_name in ["Альбедо", "Нахида", "Кафка", "Броння", "Чжун Ли"]:
await test_db.release_role(role_name)
# Назначаем одну роль
success: bool = await test_db.assign_role("Альбедо", user_id)
assert success
available_roles: List[Role] = await test_db.get_available_roles()
role_names: List[str] = [role.name for role in available_roles]
assert "Альбедо" not in role_names
assert len(available_roles) > 0
for role in available_roles:
assert role.occupied_by is None
async def test_get_occupied_roles(
self, test_db: BotDatabase, test_session: AsyncSession, test_user: int
) -> None:
"""
Тест получения занятых ролей.
Проверяет, что все назначенные роли возвращаются корректно.
"""
user_id: int = test_user
await test_db.release_role("Альбедо")
await test_db.release_role("Нахида")
success1: bool = await test_db.assign_role("Альбедо", user_id)
success2: bool = await test_db.assign_role("Нахида", user_id)
assert success1 and success2
occupied_roles: List[Role] = await test_db.get_occupied_roles()
role_names: List[str] = [role.name for role in occupied_roles]
assert "Альбедо" in role_names
assert "Нахида" in role_names
assert len(occupied_roles) >= 2
async def test_region_filter(
self, test_db: BotDatabase, test_session: AsyncSession
) -> None:
"""
Тест фильтрации ролей по регионам.
Проверяет, что метод возвращает роли только указанного региона.
"""
await test_db.release_role("Альбедо")
mondstadt_roles: List[Role] = await test_db.get_available_roles(RoleRegion.MONDSTADT)
assert len(mondstadt_roles) == 1
assert mondstadt_roles[0].name == "Альбедо"
assert mondstadt_roles[0].region == RoleRegion.MONDSTADT
async def test_region_stats(
self, test_db: BotDatabase, test_session: AsyncSession, test_user: int
) -> None:
"""
Тест статистики по регионам.
Проверяет, что метод возвращает корректное количество занятых ролей по регионам.
"""
user_id: int = test_user
await test_db.release_role("Альбедо")
await test_db.release_role("Нахида")
success1: bool = await test_db.assign_role("Альбедо", user_id)
success2: bool = await test_db.assign_role("Нахида", user_id)
assert success1 and success2
stats: Dict[RoleRegion, Dict[str, int]] = await test_db.get_region_stats()
assert RoleRegion.MONDSTADT in stats
assert RoleRegion.SUMERU in stats
assert stats[RoleRegion.MONDSTADT]["occupied"] == 1
assert stats[RoleRegion.MONDSTADT]["total"] == 1