Skip to content

Commit

Permalink
Merge pull request #69 from kookmin-sw/refactor/messagelist
Browse files Browse the repository at this point in the history
Refactor/messagelist
  • Loading branch information
imjanghyeok authored May 12, 2024
2 parents fdfcc29 + fb2f8ed commit f3ef70a
Show file tree
Hide file tree
Showing 4 changed files with 155 additions and 9 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@
import capstone.facefriend.chat.service.MessageService;
import capstone.facefriend.chat.service.dto.heart.HeartReplyRequest;
import capstone.facefriend.chat.service.dto.heart.SendHeartRequest;
import capstone.facefriend.chat.service.dto.message.MessageListRequest;
import capstone.facefriend.chat.service.dto.message.MessageListResponse;
import capstone.facefriend.chat.service.dto.message.MessageRequest;
import lombok.RequiredArgsConstructor;
Expand All @@ -25,13 +26,32 @@ public class MessageController {
private final MessageService messageService;
private final JwtProvider jwtProvider;

@MessageMapping("/stomp/connect")
public void enterApp(
StompHeaderAccessor headerAccessor
){
String authorizationHeader = headerAccessor.getFirstNativeHeader("Authorization");
String token = authorizationHeader.substring(BEARER_PREFIX.length());
Long memberId = jwtProvider.extractId(token);
messageService.enterApplication(memberId);
}

@PostMapping("/stomp/disconnect")
public String exitApp(
@AuthMember Long memberId
){
String msg = messageService.exitApplication(memberId);
return msg;
}

@GetMapping("/chat/{roomId}/messages")
public ResponseEntity<List<MessageListResponse>> getMessagesPage(
@PathVariable("roomId") Long roomId,
@AuthMember Long memberId,
@RequestParam(required = false, defaultValue = "1", value = "page") int pageNo
// @AuthMember Long memberId,
@RequestParam(required = false, defaultValue = "1", value = "page") int pageNo,
@RequestBody MessageListRequest messageListRequest
){
return ResponseEntity.ok(messageService.getMessagePage(roomId, memberId,pageNo));
return ResponseEntity.ok(messageService.getMessagePage(roomId, pageNo, messageListRequest));
}


Expand Down
79 changes: 74 additions & 5 deletions src/main/java/capstone/facefriend/chat/service/MessageService.java
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@
import capstone.facefriend.chat.service.dto.heart.HeartReplyRequest;
import capstone.facefriend.chat.service.dto.heart.HeartReplyResponse;
import capstone.facefriend.chat.service.dto.heart.SendHeartResponse;
import capstone.facefriend.chat.service.dto.message.MessageListRequest;
import capstone.facefriend.chat.service.dto.message.MessageListResponse;
import capstone.facefriend.chat.service.dto.message.MessageRequest;
import capstone.facefriend.chat.service.dto.message.MessageResponse;
Expand Down Expand Up @@ -227,20 +228,88 @@ public void heartReply(HeartReplyRequest heartReplyRequest, Long receiveId) {
simpMessagingTemplate.convertAndSend(destination, heartReplyResponse);
}

public List<MessageListResponse> getMessagePage(Long roomId, Long memberId, int pageNo) {
public List<MessageListResponse> getMessagePage(Long roomId, int pageNo, MessageListRequest messageListRequest) {
pageNo = pageNo - 1;
int pageSize = 40;
Sort sort = Sort.by(Sort.Direction.DESC, "sendTime");
Pageable pageable = PageRequest.of(pageNo, pageSize, sort);
String chatRoomInfoId = roomId + "/member/" + memberId;
ChatRoomInfo chatRoomInfo = findChatRoomInfo(chatRoomInfoId);
LocalDateTime time = chatRoomInfo.getEnterTime();
List<ChatMessage> chatMessagePage = chatMessageRepository.findChatMessagesByChatRoom_IdAndSendTimeBefore(roomId, time, pageable);
LocalDateTime time2 = messageListRequest.sendTime();
List<ChatMessage> chatMessagePage = chatMessageRepository.findChatMessagesByChatRoom_IdAndSendTimeBefore(roomId, time2, pageable);
List<MessageListResponse> messageListResponses = new ArrayList<>();
for (ChatMessage chatMessage : chatMessagePage){
MessageListResponse messageListResponse = MessageListResponse.of(chatMessage);
messageListResponses.add(messageListResponse);
}
return messageListResponses;
}

@Transactional
public void enterApplication(Long memberId) {
String exceptionDestination = "/sub/chat/" + memberId;
SocketInfo socketInfo = new SocketInfo();
socketInfo.setMemberId(memberId);
socketInfo.setConnectTime(LocalDateTime.now());
socketInfoRedisRepository.save(socketInfo);
if (isExistUnReadMessage(memberId)) {
sendSentMessage(memberId);
}

if(isExistUnSendHeart(memberId)) {
sendSentHeart(memberId);
}

simpMessagingTemplate.convertAndSend(exceptionDestination, "저장 성공");
}

@Transactional
public String exitApplication(Long memberId) {
SocketInfo socketInfo = findSocketInfo(memberId);
socketInfoRedisRepository.delete(socketInfo);
return "성공";
}

private Boolean isExistUnReadMessage(Long memberId) {
Boolean isUnRead = redisTemplate.hasKey("/sub/chat/" + memberId + "message");
log.info(isUnRead.toString());
return !isUnRead;
}

private Boolean isExistUnSendHeart(Long memberId) {
Boolean isUnRead = redisTemplate.hasKey("/sub/chat/" + memberId + "SendHeart");
log.info(isUnRead.toString());
return !isUnRead;
}

private void sendSentMessage(Long receiveId) {
String topic = channelTopic.getTopic();
String destination = "/sub/chat" + receiveId + "message";
Long messagesListSize = redisTemplate.opsForList().size(destination);
log.info(messagesListSize.toString());
log.info("messageList: {}", redisTemplate.opsForList().range(destination, 0, -1));

if (messagesListSize > 0) {
for (Long i = messagesListSize; i > 0; i--) {
// 맵으로 받음
LinkedHashMap<String, Object> map = (LinkedHashMap<String, Object>) redisTemplate.opsForList().rightPop(destination);
MessageResponse messageResponse = (MessageResponse) map.get(destination);
log.info("messageResponse: {}", messageResponse.toString());
redisTemplate.convertAndSend(topic, messageResponse);
}
}
}

private void sendSentHeart(Long receiveId) {
String topic = channelTopic.getTopic();
String destination = "/sub/chat" + receiveId + "heart";
Long messagesListSize = redisTemplate.opsForList().size(destination);
log.info("SendHeartListSize: {}", messagesListSize.toString());
if (messagesListSize > 0) {
for (Long i = messagesListSize; i > 0; i--) {
LinkedHashMap<String, Object> map = (LinkedHashMap<String, Object>) redisTemplate.opsForList().rightPop(destination);
SendHeartResponse sendHeartResponse = (SendHeartResponse) map.get(destination);
log.info("messageResponse: {}", sendHeartResponse.toString());
redisTemplate.convertAndSend(topic, sendHeartResponse);
}
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -33,18 +33,64 @@ public void onMessage(Message message, byte[] pattern) {
try {
// redis에서 발행된 데이터를 받아 역직렬화
String publishMessage = (String) redisTemplate.getStringSerializer().deserialize(message.getBody());

if (publishMessage.contains("message")) {
log.info(publishMessage);
MessageResponse messageResponse = objectMapper.readValue(publishMessage, MessageResponse.class);
log.info(messageResponse.toString());
GetMessageResponse chatMessageResponse = new GetMessageResponse(messageResponse);
log.info(chatMessageResponse.toString());
if (isExistSubscriber(messageResponse.getReceiveId())) {
messagingTemplate.convertAndSend("/sub/chat/" + messageResponse.getReceiveId(), chatMessageResponse);
} else {
saveUnReadMessage("/sub/chat" + messageResponse.getReceiveId() + "message", messageResponse);
}


messagingTemplate.convertAndSend("/sub/chat/" + messageResponse.getReceiveId(), chatMessageResponse);
} else if (publishMessage.contains("Heart")) {
SendHeartResponse sendHeartResponse = objectMapper.readValue(publishMessage, SendHeartResponse.class);

GetSendHeartResponse chatSendHeartResponse = new GetSendHeartResponse(sendHeartResponse);
if (isExistSubscriber(chatSendHeartResponse.getReceiveId())) {
messagingTemplate.convertAndSend("/sub/chat/" + sendHeartResponse.getReceiveId(), chatSendHeartResponse);
} else {
saveUnReadHeart("/sub/chat" + sendHeartResponse.getReceiveId() + "heart", sendHeartResponse);
}

messagingTemplate.convertAndSend("/sub/chat/" + sendHeartResponse.getReceiveId(), chatSendHeartResponse);
}
} catch (IOException e) {
throw new RuntimeException("Failed to process message", e);
}
}

private Boolean isExistSubscriber(Long memberId) {
log.info("isExistSubscriber 호출");
Boolean isMember = redisTemplate.opsForSet().isMember("SocketInfo", memberId);
log.info("Socket: " + memberId);
log.info("SocketInfo: " + isMember);

return isMember;
}



private void saveUnReadMessage(String destination, MessageResponse messageResponse) {
Boolean isUnRead = redisTemplate.hasKey(destination);
log.info(isUnRead.toString());
if (isUnRead) {
redisTemplate.opsForList().rightPush(destination, messageResponse);
} else {
redisTemplate.opsForList().rightPush(destination, messageResponse);
}
}

private void saveUnReadHeart(String destination, SendHeartResponse sendHeartResponse) {
Boolean isUnRead = redisTemplate.hasKey(destination);
if (isUnRead) {
redisTemplate.opsForList().rightPush(destination, sendHeartResponse);
} else {
redisTemplate.opsForList().rightPush(destination, sendHeartResponse);
}
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
package capstone.facefriend.chat.service.dto.message;

import org.springframework.format.annotation.DateTimeFormat;

import java.time.LocalDateTime;

public record MessageListRequest(
@DateTimeFormat(pattern = "yyyy-MM-dd HH:mm")
LocalDateTime sendTime
) {
}

0 comments on commit f3ef70a

Please sign in to comment.