Переписал почти все тесты
feat: улучшено логирование и обработка скорингов в PostService и RagApiClient - Добавлены отладочные сообщения для передачи скорингов в функции обработки постов. - Обновлено логирование успешного получения скорингов из RAG API с дополнительной информацией. - Оптимизирована обработка скорингов в функции get_text_message для улучшения отладки. - Обновлены тесты для проверки новых функциональных возможностей и обработки ошибок.
This commit is contained in:
176
tests/test_admin_dependencies.py
Normal file
176
tests/test_admin_dependencies.py
Normal file
@@ -0,0 +1,176 @@
|
||||
"""
|
||||
Тесты для helper_bot.handlers.admin.dependencies: AdminAccessMiddleware, get_bot_db, get_settings.
|
||||
"""
|
||||
|
||||
from unittest.mock import AsyncMock, MagicMock, patch
|
||||
|
||||
import pytest
|
||||
|
||||
from helper_bot.handlers.admin.dependencies import (
|
||||
AdminAccessMiddleware,
|
||||
get_bot_db,
|
||||
get_settings,
|
||||
)
|
||||
|
||||
|
||||
@pytest.mark.unit
|
||||
@pytest.mark.asyncio
|
||||
class TestAdminAccessMiddleware:
|
||||
"""Тесты для AdminAccessMiddleware."""
|
||||
|
||||
@pytest.fixture
|
||||
def middleware(self):
|
||||
"""Экземпляр middleware."""
|
||||
return AdminAccessMiddleware()
|
||||
|
||||
@pytest.fixture
|
||||
def mock_handler(self):
|
||||
"""Мок handler."""
|
||||
return AsyncMock(return_value="handler_result")
|
||||
|
||||
@patch("helper_bot.handlers.admin.dependencies.check_access", new_callable=AsyncMock)
|
||||
async def test_access_granted_calls_handler(self, mock_check_access, middleware, mock_handler):
|
||||
"""При доступе разрешён вызывается handler с event и data."""
|
||||
mock_check_access.return_value = True
|
||||
event = MagicMock()
|
||||
event.from_user = MagicMock()
|
||||
event.from_user.id = 123
|
||||
event.from_user.username = "admin"
|
||||
data = {"bot_db": MagicMock()}
|
||||
|
||||
result = await middleware(mock_handler, event, data)
|
||||
|
||||
mock_check_access.assert_awaited_once_with(123, data["bot_db"])
|
||||
mock_handler.assert_awaited_once_with(event, data)
|
||||
assert result == "handler_result"
|
||||
|
||||
@patch("helper_bot.handlers.admin.dependencies.check_access", new_callable=AsyncMock)
|
||||
async def test_access_denied_answers_and_does_not_call_handler(
|
||||
self, mock_check_access, middleware, mock_handler
|
||||
):
|
||||
"""При доступе запрещён отправляется ответ и handler не вызывается."""
|
||||
mock_check_access.return_value = False
|
||||
event = MagicMock()
|
||||
event.from_user = MagicMock()
|
||||
event.from_user.id = 456
|
||||
event.from_user.username = "user"
|
||||
event.answer = AsyncMock()
|
||||
data = {"bot_db": MagicMock()}
|
||||
|
||||
result = await middleware(mock_handler, event, data)
|
||||
|
||||
mock_check_access.assert_awaited_once()
|
||||
event.answer.assert_awaited_once_with("Доступ запрещен!")
|
||||
mock_handler.assert_not_awaited()
|
||||
assert result is None
|
||||
|
||||
@patch("helper_bot.handlers.admin.dependencies.check_access", new_callable=AsyncMock)
|
||||
@patch("helper_bot.handlers.admin.dependencies.get_global_instance")
|
||||
async def test_fallback_get_db_from_global_when_bot_db_missing(
|
||||
self, mock_get_global, mock_check_access, middleware, mock_handler
|
||||
):
|
||||
"""Если bot_db нет в data, берётся из get_global_instance().get_db()."""
|
||||
mock_check_access.return_value = True
|
||||
mock_bdf = MagicMock()
|
||||
mock_bdf.get_db.return_value = MagicMock()
|
||||
mock_get_global.return_value = mock_bdf
|
||||
event = MagicMock()
|
||||
event.from_user = MagicMock()
|
||||
event.from_user.id = 1
|
||||
event.from_user.username = "u"
|
||||
data = {}
|
||||
|
||||
await middleware(mock_handler, event, data)
|
||||
|
||||
mock_get_global.assert_called_once()
|
||||
mock_bdf.get_db.assert_called_once()
|
||||
mock_check_access.assert_awaited_once_with(1, mock_bdf.get_db.return_value)
|
||||
|
||||
@patch("helper_bot.handlers.admin.dependencies.check_access", new_callable=AsyncMock)
|
||||
async def test_event_without_from_user_calls_handler(self, mock_check_access, middleware, mock_handler):
|
||||
"""Если у event нет from_user, handler вызывается (проверка доступа не выполняется)."""
|
||||
class EventWithoutUser:
|
||||
pass
|
||||
event = EventWithoutUser()
|
||||
data = {}
|
||||
|
||||
result = await middleware(mock_handler, event, data)
|
||||
|
||||
mock_check_access.assert_not_awaited()
|
||||
mock_handler.assert_awaited_once_with(event, data)
|
||||
assert result == "handler_result"
|
||||
|
||||
@patch("helper_bot.handlers.admin.dependencies.check_access", new_callable=AsyncMock)
|
||||
async def test_handler_typeerror_missing_data_calls_handler_without_data(
|
||||
self, mock_check_access, middleware
|
||||
):
|
||||
"""При TypeError из-за отсутствия data вызывается handler(event) без data."""
|
||||
mock_check_access.return_value = True
|
||||
call_count = 0
|
||||
|
||||
async def handler(event, data=None):
|
||||
nonlocal call_count
|
||||
call_count += 1
|
||||
if call_count == 1 and data is not None:
|
||||
raise TypeError("missing 1 required positional argument: 'data'")
|
||||
return "ok"
|
||||
|
||||
handler.__name__ = "test_handler"
|
||||
event = MagicMock()
|
||||
event.from_user = MagicMock()
|
||||
event.from_user.id = 1
|
||||
event.from_user.username = "u"
|
||||
data = {"bot_db": MagicMock()}
|
||||
|
||||
result = await middleware(handler, event, data)
|
||||
|
||||
assert call_count == 2
|
||||
assert result == "ok"
|
||||
|
||||
@patch("helper_bot.handlers.admin.dependencies.check_access", new_callable=AsyncMock)
|
||||
async def test_handler_other_exception_reraises(self, mock_check_access, middleware):
|
||||
"""При другом исключении в handler оно пробрасывается."""
|
||||
mock_check_access.return_value = True
|
||||
|
||||
async def handler(event, data):
|
||||
raise ValueError("other error")
|
||||
|
||||
event = MagicMock()
|
||||
event.from_user = MagicMock()
|
||||
event.from_user.id = 1
|
||||
event.from_user.username = "u"
|
||||
data = {"bot_db": MagicMock()}
|
||||
|
||||
with pytest.raises(ValueError, match="other error"):
|
||||
await middleware(handler, event, data)
|
||||
|
||||
|
||||
@pytest.mark.unit
|
||||
class TestDependencyProviders:
|
||||
"""Тесты для get_bot_db и get_settings."""
|
||||
|
||||
@patch("helper_bot.handlers.admin.dependencies.get_global_instance")
|
||||
def test_get_bot_db_returns_bdf_get_db(self, mock_get_global):
|
||||
"""get_bot_db возвращает bdf.get_db()."""
|
||||
mock_bdf = MagicMock()
|
||||
mock_db = MagicMock()
|
||||
mock_bdf.get_db.return_value = mock_db
|
||||
mock_get_global.return_value = mock_bdf
|
||||
|
||||
result = get_bot_db()
|
||||
|
||||
mock_get_global.assert_called_once()
|
||||
mock_bdf.get_db.assert_called_once()
|
||||
assert result is mock_db
|
||||
|
||||
@patch("helper_bot.handlers.admin.dependencies.get_global_instance")
|
||||
def test_get_settings_returns_bdf_settings(self, mock_get_global):
|
||||
"""get_settings возвращает bdf.settings."""
|
||||
mock_bdf = MagicMock()
|
||||
mock_bdf.settings = {"Telegram": {"bot_token": "x"}}
|
||||
mock_get_global.return_value = mock_bdf
|
||||
|
||||
result = get_settings()
|
||||
|
||||
mock_get_global.assert_called_once()
|
||||
assert result == {"Telegram": {"bot_token": "x"}}
|
||||
Reference in New Issue
Block a user