fixed controllers

This commit is contained in:
SlimusMinus
2026-07-31 01:08:53 +03:00
parent 74f7c88843
commit 2468c26b84
32 changed files with 536 additions and 432 deletions

View File

@@ -11,17 +11,22 @@ import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.Pageable;
import org.springframework.messaging.simp.SimpMessagingTemplate;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
@Slf4j
@Service
@RequiredArgsConstructor
public class ChatService {
private final ChatRepository chatRepository;
private final MessageRepository messageRepository;
private final SimpMessagingTemplate messagingTemplate;
private final UserRepository userRepository; // твой существующий репозиторий юзеров
private final UserRepository userRepository;
// Создать чат с пользователем (или вернуть существующий)
@Transactional
@@ -46,28 +51,28 @@ public class ChatService {
}
// Все чаты пользователя
@Transactional(readOnly = true)
public List<ChatDto> getUserChats(Long userId) {
return chatRepository.findAllByUserId(userId).stream()
.map(c -> toDto(c, userId))
.collect(Collectors.toList());
}
// История сообщений в чате
public List<MessageDto> getMessages(Long chatId) {
return messageRepository.findByChatIdOrderByCreatedAtAsc(chatId).stream()
.map(this::toMessageDto)
.collect(Collectors.toList());
// История сообщений в чате, с пагинацией и проверкой доступа
@Transactional(readOnly = true)
public Page<MessageDto> getMessages(Long chatId, Long userId, Pageable pageable) {
Chat chat = getChatOrThrow(chatId);
checkParticipant(chat, userId);
return messageRepository.findByChatIdOrderByCreatedAtDesc(chatId, pageable)
.map(this::toMessageDto);
}
// Отправка сообщения (вызывается из WebSocket контроллера)
@Transactional
public MessageDto sendMessage(Long senderId, Long chatId, String content) {
Chat chat = chatRepository.findById(chatId)
.orElseThrow(() -> new IllegalArgumentException("Чат не найден"));
if (!chat.getUserOneId().equals(senderId) && !chat.getUserTwoId().equals(senderId)) {
throw new SecurityException("Вы не участник этого чата");
}
Chat chat = getChatOrThrow(chatId);
checkParticipant(chat, senderId);
Message message = new Message();
message.setChatId(chatId);
@@ -95,6 +100,33 @@ public class ChatService {
return dto;
}
@Transactional
public void deleteChat(Long chatId, Long userId) {
Chat chat = getChatOrThrow(chatId);
checkParticipant(chat, userId);
chatRepository.deleteById(chatId);
}
@Transactional
public void markAsRead(Long chatId, Long userId) {
Chat chat = getChatOrThrow(chatId);
checkParticipant(chat, userId);
messageRepository.markAsReadByChatIdAndRecipient(chatId, userId);
}
// ---------- вспомогательные методы ----------
private Chat getChatOrThrow(Long chatId) {
return chatRepository.findById(chatId)
.orElseThrow(() -> new IllegalArgumentException("Чат не найден"));
}
private void checkParticipant(Chat chat, Long userId) {
if (!chat.getUserOneId().equals(userId) && !chat.getUserTwoId().equals(userId)) {
throw new SecurityException("Вы не участник этого чата");
}
}
private ChatDto toDto(Chat chat, Long currentUserId) {
Long otherUserId = chat.getUserOneId().equals(currentUserId)
? chat.getUserTwoId() : chat.getUserOneId();
@@ -104,18 +136,17 @@ public class ChatService {
dto.setOtherUserId(otherUserId);
dto.setPostId(chat.getPostId());
// Подтягиваем имя/аватар собеседника из твоего UserRepository
userRepository.findById(otherUserId).ifPresent(user -> {
dto.setOtherUserName(user.getName() + " " + user.getLastName());
dto.setOtherUserAvatar(user.getAvatarUrl());
});
List<Message> messages = messageRepository.findByChatIdOrderByCreatedAtAsc(chat.getId());
if (!messages.isEmpty()) {
Message last = messages.getLast();
dto.setLastMessage(last.getContent());
dto.setLastMessageAt(last.getCreatedAt());
}
// без N+1: берём только последнее сообщение, а не всю историю
messageRepository.findFirstByChatIdOrderByCreatedAtDesc(chat.getId())
.ifPresent(last -> {
dto.setLastMessage(last.getContent());
dto.setLastMessageAt(last.getCreatedAt());
});
dto.setUnreadCount(
messageRepository.countByChatIdAndIsReadFalseAndSenderIdNot(chat.getId(), currentUserId)
@@ -134,13 +165,4 @@ public class ChatService {
dto.setCreatedAt(m.getCreatedAt());
return dto;
}
public void deleteChat(Long chatId) {
chatRepository.deleteById(chatId);
}
@Transactional
public void markAsRead(Long chatId, Long userId) {
messageRepository.markAsReadByChatIdAndRecipient(chatId, userId);
}
}