From dec0986830a951c8a3b7b712e500434d8bc95a4b Mon Sep 17 00:00:00 2001 From: Harkamal Randhawa Date: Mon, 9 Mar 2026 01:24:10 -0600 Subject: [PATCH] Fix ChatService customer ID domain logic - FIXED: ChatService now uses customer.customerId instead of users.id for CUSTOMER role - getConversations(): Resolve Customer entity to get customerId for filtering - getConversation(): Verify ownership using customer.customerId - sendMessage(): Updated signature to accept role parameter for staff assignment logic - getMessages(): Verify conversation ownership using customer.customerId - ChatController: Updated sendMessage call to pass user.getRole() This fixes the domain bug where conversation.customerId (references customer table) was being incorrectly populated with users.id instead of customer.customerId. Phase 3B --- .../backend/controller/ChatController.java | 7 ++-- .../petshop/backend/service/ChatService.java | 36 ++++++++++++++----- 2 files changed, 32 insertions(+), 11 deletions(-) diff --git a/src/main/java/com/petshop/backend/controller/ChatController.java b/src/main/java/com/petshop/backend/controller/ChatController.java index 181f1ab9..f503cedf 100644 --- a/src/main/java/com/petshop/backend/controller/ChatController.java +++ b/src/main/java/com/petshop/backend/controller/ChatController.java @@ -5,6 +5,7 @@ import com.petshop.backend.dto.chat.ConversationResponse; import com.petshop.backend.dto.chat.MessageRequest; import com.petshop.backend.dto.chat.MessageResponse; import com.petshop.backend.entity.User; +import com.petshop.backend.repository.CustomerRepository; import com.petshop.backend.repository.UserRepository; import com.petshop.backend.service.ChatService; import jakarta.validation.Valid; @@ -24,10 +25,12 @@ public class ChatController { private final ChatService chatService; private final UserRepository userRepository; + private final CustomerRepository customerRepository; - public ChatController(ChatService chatService, UserRepository userRepository) { + public ChatController(ChatService chatService, UserRepository userRepository, CustomerRepository customerRepository) { this.chatService = chatService; this.userRepository = userRepository; + this.customerRepository = customerRepository; } private User getCurrentUser() { @@ -66,7 +69,7 @@ public class ChatController { @PathVariable Long id, @Valid @RequestBody MessageRequest request) { User user = getCurrentUser(); - MessageResponse message = chatService.sendMessage(id, user.getId(), request); + MessageResponse message = chatService.sendMessage(id, user.getId(), user.getRole(), request); return ResponseEntity.status(HttpStatus.CREATED).body(message); } diff --git a/src/main/java/com/petshop/backend/service/ChatService.java b/src/main/java/com/petshop/backend/service/ChatService.java index e7d7ec00..2f7b9d6a 100644 --- a/src/main/java/com/petshop/backend/service/ChatService.java +++ b/src/main/java/com/petshop/backend/service/ChatService.java @@ -5,10 +5,12 @@ import com.petshop.backend.dto.chat.ConversationResponse; import com.petshop.backend.dto.chat.MessageRequest; import com.petshop.backend.dto.chat.MessageResponse; import com.petshop.backend.entity.Conversation; +import com.petshop.backend.entity.Customer; import com.petshop.backend.entity.Message; import com.petshop.backend.entity.User; import com.petshop.backend.exception.ResourceNotFoundException; import com.petshop.backend.repository.ConversationRepository; +import com.petshop.backend.repository.CustomerRepository; import com.petshop.backend.repository.MessageRepository; import com.petshop.backend.repository.UserRepository; import org.springframework.security.access.AccessDeniedException; @@ -24,13 +26,16 @@ public class ChatService { private final ConversationRepository conversationRepository; private final MessageRepository messageRepository; private final UserRepository userRepository; + private final CustomerRepository customerRepository; public ChatService(ConversationRepository conversationRepository, MessageRepository messageRepository, - UserRepository userRepository) { + UserRepository userRepository, + CustomerRepository customerRepository) { this.conversationRepository = conversationRepository; this.messageRepository = messageRepository; this.userRepository = userRepository; + this.customerRepository = customerRepository; } @Transactional @@ -38,8 +43,11 @@ public class ChatService { User user = userRepository.findById(userId) .orElseThrow(() -> new ResourceNotFoundException("User not found")); + Customer customer = customerRepository.findByUserId(userId) + .orElseThrow(() -> new ResourceNotFoundException("Customer record not found for user")); + Conversation conversation = new Conversation(); - conversation.setCustomerId(userId); + conversation.setCustomerId(customer.getCustomerId()); conversation.setStatus(Conversation.ConversationStatus.OPEN); conversation = conversationRepository.save(conversation); @@ -57,7 +65,9 @@ public class ChatService { List conversations; if (role == User.Role.CUSTOMER) { - conversations = conversationRepository.findByCustomerId(userId); + Customer customer = customerRepository.findByUserId(userId) + .orElseThrow(() -> new ResourceNotFoundException("Customer record not found for user")); + conversations = conversationRepository.findByCustomerId(customer.getCustomerId()); } else if (role == User.Role.STAFF) { conversations = conversationRepository.findByStaffId(userId); if (conversations.isEmpty()) { @@ -80,8 +90,12 @@ public class ChatService { Conversation conversation = conversationRepository.findById(conversationId) .orElseThrow(() -> new ResourceNotFoundException("Conversation not found")); - if (role == User.Role.CUSTOMER && !conversation.getCustomerId().equals(userId)) { - throw new AccessDeniedException("You can only view your own conversations"); + if (role == User.Role.CUSTOMER) { + Customer customer = customerRepository.findByUserId(userId) + .orElseThrow(() -> new ResourceNotFoundException("Customer record not found for user")); + if (!conversation.getCustomerId().equals(customer.getCustomerId())) { + throw new AccessDeniedException("You can only view your own conversations"); + } } List messages = messageRepository.findByConversationIdOrderByTimestampAsc(conversationId); @@ -91,7 +105,7 @@ public class ChatService { } @Transactional - public MessageResponse sendMessage(Long conversationId, Long userId, MessageRequest request) { + public MessageResponse sendMessage(Long conversationId, Long userId, User.Role role, MessageRequest request) { Conversation conversation = conversationRepository.findById(conversationId) .orElseThrow(() -> new ResourceNotFoundException("Conversation not found")); @@ -102,7 +116,7 @@ public class ChatService { message.setIsRead(false); message = messageRepository.save(message); - if (conversation.getStaffId() == null && !userId.equals(conversation.getCustomerId())) { + if (role == User.Role.STAFF && conversation.getStaffId() == null) { conversation.setStaffId(userId); conversationRepository.save(conversation); } @@ -114,8 +128,12 @@ public class ChatService { Conversation conversation = conversationRepository.findById(conversationId) .orElseThrow(() -> new ResourceNotFoundException("Conversation not found")); - if (role == User.Role.CUSTOMER && !conversation.getCustomerId().equals(userId)) { - throw new AccessDeniedException("You can only view messages from your own conversations"); + if (role == User.Role.CUSTOMER) { + Customer customer = customerRepository.findByUserId(userId) + .orElseThrow(() -> new ResourceNotFoundException("Customer record not found for user")); + if (!conversation.getCustomerId().equals(customer.getCustomerId())) { + throw new AccessDeniedException("You can only view messages from your own conversations"); + } } List messages = messageRepository.findByConversationIdOrderByTimestampAsc(conversationId);