feat: добавлено управление сообщениями пользователей в админ-панель
All checks were successful
continuous-integration/drone/push Build is passing

- Добавлена кнопка 'Сообщения пользователей' в админ меню
- Реализован просмотр последних сообщений с фильтрацией
- Возможность просмотра медиа (фото, видео) прямо в боте
- Функция удаления сообщений администратором
- Удаление происходит как в БД, так и у пользователей в Telegram
- Просмотр всех сообщений конкретного пользователя
- Добавлены методы в ChatMessageService и UserService
- Метод get_user_messages_all для получения всех сообщений
- Метод mark_as_deleted для пометки сообщений как удаленных
- Метод count_messages для подсчета количества сообщений
- Метод get_user_by_id в UserService
This commit is contained in:
2025-11-22 19:46:38 +09:00
parent 49f220c2a2
commit 8e692d2f61
4 changed files with 343 additions and 2 deletions

View File

@@ -284,6 +284,58 @@ class ChatMessageService:
result = await session.execute(query)
return result.scalars().all()
@staticmethod
async def get_user_messages_all(
session: AsyncSession,
limit: int = 50,
offset: int = 0,
include_deleted: bool = False
) -> List[ChatMessage]:
"""Получить последние сообщения всех пользователей"""
query = select(ChatMessage).options(selectinload(ChatMessage.sender))
if not include_deleted:
query = query.where(ChatMessage.is_deleted == False)
query = query.order_by(ChatMessage.created_at.desc()).limit(limit).offset(offset)
result = await session.execute(query)
return result.scalars().all()
@staticmethod
async def count_messages(
session: AsyncSession,
include_deleted: bool = False
) -> int:
"""Подсчитать количество сообщений"""
from sqlalchemy import func
query = select(func.count(ChatMessage.id))
if not include_deleted:
query = query.where(ChatMessage.is_deleted == False)
result = await session.execute(query)
return result.scalar() or 0
@staticmethod
async def mark_as_deleted(
session: AsyncSession,
message_id: int,
deleted_by: int
) -> bool:
"""Пометить сообщение как удаленное"""
result = await session.execute(
update(ChatMessage)
.where(ChatMessage.id == message_id)
.values(
is_deleted=True,
deleted_by=deleted_by,
deleted_at=datetime.now(timezone.utc)
)
)
await session.commit()
return result.rowcount > 0
class ChatPermissionService:

View File

@@ -49,6 +49,12 @@ class UserService:
)
return result.scalar_one_or_none()
@staticmethod
async def get_user_by_id(session: AsyncSession, user_id: int) -> Optional[User]:
"""Получить пользователя по ID"""
result = await session.execute(select(User).where(User.id == user_id))
return result.scalar_one_or_none()
@staticmethod
async def get_user_by_username(session: AsyncSession, username: str) -> Optional[User]:
"""Получить пользователя по username"""