Skip to content

Commit

Permalink
feat: 실시간 접속자 현황 목록 조회 기능 구현 (#50)
Browse files Browse the repository at this point in the history
* feat: 인게임 입장 시 세션 ID 업데이트 로직 추가

* feat: 실시간 접속자 현황 파악 기능 구현

---------

Co-authored-by: marooo326 <[email protected]>
  • Loading branch information
park0jae and kimday0326 authored Feb 27, 2024
1 parent a18549b commit afc2ee5
Show file tree
Hide file tree
Showing 8 changed files with 140 additions and 6 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@

import com.pgms.api.domain.game.dto.response.GameQuestionGetResponse;
import com.pgms.api.domain.game.dto.response.GameRoomMemberGetResponse;
import com.pgms.api.global.exception.GameException;
import com.pgms.api.global.exception.SocketException;
import com.pgms.api.socket.dto.request.GameFinishRequest;
import com.pgms.api.socket.dto.request.GameInfoUpdateRequest;
Expand Down Expand Up @@ -55,12 +56,16 @@ public class GameService {
private final Producer producer;

// ============================== 입장 확인 및 첫 라운드 스타트 ==============================
public void startFirstRound(Long roomId) {
public void startFirstRound(Long roomId, Long accountId, String sessionId) {
final GameInfo gameInfo = getGameInfo(roomId);
final GameRoom gameRoom = getGameRoom(roomId);

// 카운트만 올려줌
final GameRoomMember gameRoomMember = gameRoomMemberRepository.findByMemberId(accountId)
.orElseThrow(() -> new GameException(GameRoomErrorCode.GAME_ROOM_MEMBER_NOT_FOUND));

// 카운트만 올려줌. TODO : 나중에 한명이 여러번 입장처리 못하게 수정
gameInfo.enter();
gameRoomMember.updateSessionId(sessionId);

// 모든 멤버가 입장했을 때
if (gameInfo.isAllEntered(gameRoom.getCurrentPlayer())) {
Expand Down
27 changes: 27 additions & 0 deletions api/src/main/java/com/pgms/api/domain/online/OnlineController.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
package com.pgms.api.domain.online;

import java.util.Set;

import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RestController;

import com.pgms.api.domain.online.dto.OnlineMemberGetResponse;
import com.pgms.coredomain.response.ApiResponse;
import com.pgms.coresecurity.resolver.Account;
import com.pgms.coresecurity.resolver.CurrentAccount;

import lombok.RequiredArgsConstructor;

@RestController
@RequiredArgsConstructor
public class OnlineController {

private final OnlineService onlineService;

@GetMapping("/api/v1/online")
public ResponseEntity<ApiResponse<Set<OnlineMemberGetResponse>>> getOnlineMembers(
@CurrentAccount Account account) {
return ResponseEntity.ok(ApiResponse.of(onlineService.getOnlineMembers(account)));
}
}
46 changes: 46 additions & 0 deletions api/src/main/java/com/pgms/api/domain/online/OnlineService.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,46 @@
package com.pgms.api.domain.online;

import java.util.HashSet;
import java.util.Set;

import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import com.pgms.api.domain.online.dto.OnlineMemberGetResponse;
import com.pgms.coredomain.repository.GameRoomMemberRepository;
import com.pgms.coreinfraredis.entity.OnlineMember;
import com.pgms.coreinfraredis.repository.OnlineMemberRepository;
import com.pgms.coresecurity.resolver.Account;

import lombok.RequiredArgsConstructor;

@Service
@Transactional
@RequiredArgsConstructor
public class OnlineService {

private final GameRoomMemberRepository gameRoomMemberRepository;
private final OnlineMemberRepository onlineMemberRepository;

public Set<OnlineMemberGetResponse> getOnlineMembers(Account account) {
HashSet<OnlineMemberGetResponse> onlineMembers = new HashSet<>();

OnlineMember currentMember = new OnlineMember(account.id(), account.nickname());
onlineMemberRepository.save(currentMember);

gameRoomMemberRepository.findAll()
.forEach(gameRoomMember -> onlineMembers.add(new OnlineMemberGetResponse(
gameRoomMember.getMemberId(),
gameRoomMember.getNickname())));

Iterable<OnlineMember> onlineMembersIterable = onlineMemberRepository.findAll();
onlineMembersIterable.forEach(onlineMember -> {
if (onlineMember != null) {
onlineMembers.add(new OnlineMemberGetResponse(
onlineMember.getId(),
onlineMember.getNickname()));
}
});
return onlineMembers;
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
package com.pgms.api.domain.online.dto;

import java.util.Objects;

public record OnlineMemberGetResponse(
Long memberId,
String nickname
) {
public static OnlineMemberGetResponse of(Long memberId, String nickname) {
return new OnlineMemberGetResponse(memberId, nickname);
}

@Override
public boolean equals(Object o) {
if (this == o)
return true;
if (o == null || getClass() != o.getClass())
return false;
OnlineMemberGetResponse that = (OnlineMemberGetResponse)o;
return Objects.equals(memberId, that.memberId) && Objects.equals(nickname, that.nickname);
}

@Override
public int hashCode() {
return Objects.hash(memberId, nickname);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@
import org.springframework.messaging.handler.annotation.Header;
import org.springframework.messaging.handler.annotation.MessageMapping;
import org.springframework.messaging.handler.annotation.Payload;
import org.springframework.messaging.simp.SimpMessageHeaderAccessor;
import org.springframework.web.bind.annotation.RestController;

import com.pgms.api.domain.game.service.GameService;
Expand All @@ -25,9 +26,12 @@ public class GameSocketController {
@MessageMapping("/game/{roomId}/connect")
public void roundStart(
@Header("AccountId") Long accountId,
@DestinationVariable Long roomId) {
log.info(">>>>>> Member Connected in game : roomId = {}, accountId = {}", roomId, accountId);
gameService.startFirstRound(roomId);
@DestinationVariable Long roomId,
SimpMessageHeaderAccessor headerAccessor) {
final String sessionId = headerAccessor.getSessionId();
log.info(">>>>>> Member Connected in game : roomId = {}, accountId = {}, sessionId = {}",
roomId, accountId, sessionId);
gameService.startFirstRound(roomId, accountId, sessionId);
}

// 게임 중 실시간 정보 업데이트 - 문장, 코드
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@

@Getter
@AllArgsConstructor
@RedisHash(value = "guest", timeToLive = 36000L)
@RedisHash(value = "guest", timeToLive = 1800L)
public class Guest implements Serializable {
@Id
private Long id;
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
package com.pgms.coreinfraredis.entity;

import org.springframework.data.redis.core.RedisHash;

import jakarta.persistence.Id;
import lombok.AllArgsConstructor;
import lombok.Getter;

@Getter
@AllArgsConstructor
@RedisHash(value = "onlineMember", timeToLive = 20L)
public class OnlineMember {
@Id
private Long id;

private String nickname;
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
package com.pgms.coreinfraredis.repository;

import org.springframework.data.repository.CrudRepository;

import com.pgms.coreinfraredis.entity.OnlineMember;

public interface OnlineMemberRepository extends CrudRepository<OnlineMember, Long> {
}

0 comments on commit afc2ee5

Please sign in to comment.