From d0bbc1c4e9c1327097da170614f8f8ebf764a66d Mon Sep 17 00:00:00 2001 From: DongHoonYu96 Date: Thu, 21 Nov 2024 17:48:25 +0900 Subject: [PATCH] =?UTF-8?q?hotfix:=20[BE]=20=EB=B0=B0=ED=8F=AC=20=EB=B2=84?= =?UTF-8?q?=EA=B7=B8=EC=88=98=EC=A0=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 새롭게 입장한 플레이어는 어떤 게임모드인지 모르고, 디폴트가 SURVIVAL로 잡힘 --- .github/workflows/deploy.yml | 4 +-- BE/ecosystem.config.js | 18 ++++++++++++ BE/src/auth/auth.controller.spec.ts | 18 ------------ BE/src/auth/auth.service.spec.ts | 18 ------------ BE/src/game/dto/create-game.dto.ts | 2 +- BE/src/game/dto/update-room-option.dto.ts | 2 +- BE/src/game/game.gateway.ts | 3 +- .../game/redis/subscribers/room.subscriber.ts | 6 ++-- BE/src/game/service/game.room.service.ts | 19 ++++++++++--- BE/src/user/user.service.spec.ts | 18 ------------ BE/test/integration/game.integration.spec.ts | 28 +++++++++---------- 11 files changed, 55 insertions(+), 81 deletions(-) create mode 100644 BE/ecosystem.config.js delete mode 100644 BE/src/auth/auth.controller.spec.ts delete mode 100644 BE/src/auth/auth.service.spec.ts delete mode 100644 BE/src/user/user.service.spec.ts diff --git a/.github/workflows/deploy.yml b/.github/workflows/deploy.yml index db56b24..4eec350 100644 --- a/.github/workflows/deploy.yml +++ b/.github/workflows/deploy.yml @@ -116,9 +116,9 @@ jobs: cd cd /home/ubuntu/nest-server/current/FE npm i - npx pm2 stop backend-server || true + npx pm2 delete quiz-ground-was1 quiz-ground-was2 || true cd /home/ubuntu/nest-server/current/BE - npx pm2 start dist/src/main.js --name "backend-server" + npx pm2 start ecosystem.config.js # todo: # FrontEnd 배포 # # Frontend 배포 diff --git a/BE/ecosystem.config.js b/BE/ecosystem.config.js new file mode 100644 index 0000000..3dd69e4 --- /dev/null +++ b/BE/ecosystem.config.js @@ -0,0 +1,18 @@ +module.exports = { + apps: [ + { + name: 'quiz-ground-was1', + script: 'dist/src/main.js', + env: { + WAS_PORT: 3000 + } + }, + { + name: 'quiz-ground-was2', + script: 'dist/src/main.js', + env: { + WAS_PORT: 3001 + } + } + ] +}; diff --git a/BE/src/auth/auth.controller.spec.ts b/BE/src/auth/auth.controller.spec.ts deleted file mode 100644 index ccc9b38..0000000 --- a/BE/src/auth/auth.controller.spec.ts +++ /dev/null @@ -1,18 +0,0 @@ -import { Test, TestingModule } from '@nestjs/testing'; -import { AuthController } from './auth.controller'; - -describe('AuthController', () => { - let controller: AuthController; - - beforeEach(async () => { - const module: TestingModule = await Test.createTestingModule({ - controllers: [AuthController] - }).compile(); - - controller = module.get(AuthController); - }); - - it('should be defined', () => { - expect(controller).toBeDefined(); - }); -}); diff --git a/BE/src/auth/auth.service.spec.ts b/BE/src/auth/auth.service.spec.ts deleted file mode 100644 index 800ab66..0000000 --- a/BE/src/auth/auth.service.spec.ts +++ /dev/null @@ -1,18 +0,0 @@ -import { Test, TestingModule } from '@nestjs/testing'; -import { AuthService } from './auth.service'; - -describe('AuthService', () => { - let service: AuthService; - - beforeEach(async () => { - const module: TestingModule = await Test.createTestingModule({ - providers: [AuthService], - }).compile(); - - service = module.get(AuthService); - }); - - it('should be defined', () => { - expect(service).toBeDefined(); - }); -}); diff --git a/BE/src/game/dto/create-game.dto.ts b/BE/src/game/dto/create-game.dto.ts index 5b390c4..32edb41 100644 --- a/BE/src/game/dto/create-game.dto.ts +++ b/BE/src/game/dto/create-game.dto.ts @@ -36,5 +36,5 @@ export class CreateGameDto { message: '잘못된 boolean 값입니다' }); }) - isPublicGame: boolean; + isPublic: boolean; } diff --git a/BE/src/game/dto/update-room-option.dto.ts b/BE/src/game/dto/update-room-option.dto.ts index 0a3f8a9..4c144b1 100644 --- a/BE/src/game/dto/update-room-option.dto.ts +++ b/BE/src/game/dto/update-room-option.dto.ts @@ -40,5 +40,5 @@ export class UpdateRoomOptionDto { message: '잘못된 boolean 값입니다' }); }) - isPublicGame: boolean; + isPublic: boolean; } diff --git a/BE/src/game/game.gateway.ts b/BE/src/game/game.gateway.ts index bf92b45..5d7e1e1 100644 --- a/BE/src/game/game.gateway.ts +++ b/BE/src/game/game.gateway.ts @@ -62,8 +62,7 @@ export class GameGateway { if (client.data.user) { dto.playerName = client.data.user.nickname; } - const players = await this.gameRoomService.joinRoom(dto, client.id); - client.join(dto.gameId); + const players = await this.gameRoomService.joinRoom(client, dto, client.id); client.emit(SocketEvents.JOIN_ROOM, { players }); } diff --git a/BE/src/game/redis/subscribers/room.subscriber.ts b/BE/src/game/redis/subscribers/room.subscriber.ts index 4a5c794..8fc8e70 100644 --- a/BE/src/game/redis/subscribers/room.subscriber.ts +++ b/BE/src/game/redis/subscribers/room.subscriber.ts @@ -40,8 +40,8 @@ export class RoomSubscriber extends RedisSubscriber { server.to(gameId).emit(SocketEvents.UPDATE_ROOM_OPTION, { title: roomData.title, gameMode: roomData.gameMode, - maxPlayerCount: roomData.maxPlayerCount, - isPublic: roomData.isPublic + maxPlayerCount: parseInt(roomData.maxPlayerCount), + isPublic: roomData.isPublic === '1' }); this.logger.verbose(`Room option updated: ${gameId}`); break; @@ -49,7 +49,7 @@ export class RoomSubscriber extends RedisSubscriber { case 'Quizset': server.to(gameId).emit(SocketEvents.UPDATE_ROOM_QUIZSET, { quizSetId: roomData.quizSetId, - quizCount: roomData.quizCount + quizCount: parseInt(roomData.quizCount) }); this.logger.verbose(`Room quizset updated: ${gameId}`); break; diff --git a/BE/src/game/service/game.room.service.ts b/BE/src/game/service/game.room.service.ts index 20e9084..7a44c50 100644 --- a/BE/src/game/service/game.room.service.ts +++ b/BE/src/game/service/game.room.service.ts @@ -10,6 +10,7 @@ import SocketEvents from '../../common/constants/socket-events'; import { UpdateRoomOptionDto } from '../dto/update-room-option.dto'; import { UpdateRoomQuizsetDto } from '../dto/update-room-quizset.dto'; import { Cron, CronExpression } from '@nestjs/schedule'; +import { Socket } from 'socket.io'; @Injectable() export class GameRoomService { @@ -32,7 +33,7 @@ export class GameRoomService { title: gameConfig.title, gameMode: gameConfig.gameMode, maxPlayerCount: gameConfig.maxPlayerCount.toString(), - isPublicGame: gameConfig.isPublicGame ? '1' : '0', + isPublic: gameConfig.isPublic ? '1' : '0', isWaiting: '1', lastActivityAt: new Date().getTime().toString(), quizSetId: '-1', // 미설정시 기본퀴즈를 진행, -1은 기본 퀴즈셋 @@ -47,7 +48,7 @@ export class GameRoomService { return roomId; } - async joinRoom(dto: JoinRoomDto, clientId: string) { + async joinRoom(client: Socket, dto: JoinRoomDto, clientId: string) { const roomKey = REDIS_KEY.ROOM(dto.gameId); const room = await this.redis.hgetall(roomKey); this.gameValidator.validateRoomExists(SocketEvents.JOIN_ROOM, room); @@ -60,6 +61,8 @@ export class GameRoomService { ); this.gameValidator.validateRoomProgress(SocketEvents.JOIN_ROOM, room.status, room.isWaiting); + client.join(dto.gameId); //validation 후에 조인해야함 + const playerKey = REDIS_KEY.PLAYER(clientId); const positionX = Math.random(); const positionY = Math.random(); @@ -86,13 +89,21 @@ export class GameRoomService { }); } + const roomData = await this.redis.hgetall(REDIS_KEY.ROOM(dto.gameId)); + client.emit(SocketEvents.UPDATE_ROOM_OPTION, { + title: roomData.title, + gameMode: roomData.gameMode, + maxPlayerCount: parseInt(roomData.maxPlayerCount), + isPublic: roomData.isPublic === '1' + }); + this.logger.verbose(`게임 방 입장 완료: ${dto.gameId} - ${clientId} (${dto.playerName})`); return players; } async updateRoomOption(updateRoomOptionDto: UpdateRoomOptionDto, clientId: string) { - const { gameId, gameMode, title, maxPlayerCount, isPublicGame } = updateRoomOptionDto; + const { gameId, gameMode, title, maxPlayerCount, isPublic } = updateRoomOptionDto; const roomKey = `Room:${gameId}`; const room = await this.redis.hgetall(roomKey); @@ -105,7 +116,7 @@ export class GameRoomService { title: title, gameMode: gameMode, maxPlayerCount: maxPlayerCount.toString(), - isPublicGame: isPublicGame ? '1' : '0' + isPublic: isPublic ? '1' : '0' }); this.logger.verbose(`게임방 옵션 변경: ${gameId}`); } diff --git a/BE/src/user/user.service.spec.ts b/BE/src/user/user.service.spec.ts deleted file mode 100644 index 873de8a..0000000 --- a/BE/src/user/user.service.spec.ts +++ /dev/null @@ -1,18 +0,0 @@ -import { Test, TestingModule } from '@nestjs/testing'; -import { UserService } from './user.service'; - -describe('UserService', () => { - let service: UserService; - - beforeEach(async () => { - const module: TestingModule = await Test.createTestingModule({ - providers: [UserService], - }).compile(); - - service = module.get(UserService); - }); - - it('should be defined', () => { - expect(service).toBeDefined(); - }); -}); diff --git a/BE/test/integration/game.integration.spec.ts b/BE/test/integration/game.integration.spec.ts index 5b39779..70164ad 100644 --- a/BE/test/integration/game.integration.spec.ts +++ b/BE/test/integration/game.integration.spec.ts @@ -191,7 +191,7 @@ describe('GameGateway (e2e)', () => { title: 'hello world!', gameMode: 'RANKING', maxPlayerCount: 2, - isPublicGame: true + isPublic: true }; const response = await new Promise<{ gameId: string }>((resolve) => { @@ -213,19 +213,19 @@ describe('GameGateway (e2e)', () => { const invalidConfigs = [ { case: '빈 title', - config: { title: '', gameMode: 'RANKING', maxPlayerCount: 2, isPublicGame: true } + config: { title: '', gameMode: 'RANKING', maxPlayerCount: 2, isPublic: true } }, { case: '빈 gameMode', - config: { title: 'hello', gameMode: '', maxPlayerCount: 2, isPublicGame: true } + config: { title: 'hello', gameMode: '', maxPlayerCount: 2, isPublic: true } }, { case: '잘못된 gameMode', - config: { title: 'hello', gameMode: 'invalid', maxPlayerCount: 2, isPublicGame: true } + config: { title: 'hello', gameMode: 'invalid', maxPlayerCount: 2, isPublic: true } }, { case: '최소 인원 미달', - config: { title: 'hello', gameMode: 'RANKING', maxPlayerCount: 0, isPublicGame: true } + config: { title: 'hello', gameMode: 'RANKING', maxPlayerCount: 0, isPublic: true } } ]; @@ -251,7 +251,7 @@ describe('GameGateway (e2e)', () => { title: 'Test Room', gameMode: 'RANKING', maxPlayerCount: 5, - isPublicGame: true + isPublic: true }); }); @@ -304,7 +304,7 @@ describe('GameGateway (e2e)', () => { title: 'Test Room', gameMode: 'RANKING', maxPlayerCount: 5, - isPublicGame: true + isPublic: true }); // 순차적으로 이벤트 처리 @@ -342,7 +342,7 @@ describe('GameGateway (e2e)', () => { title: 'Chat Test Room', gameMode: 'RANKING', maxPlayerCount: 5, - isPublicGame: true + isPublic: true }); }); @@ -393,7 +393,7 @@ describe('GameGateway (e2e)', () => { title: 'Chat Test Room', gameMode: 'RANKING', maxPlayerCount: 5, - isPublicGame: true + isPublic: true }); }); @@ -442,7 +442,7 @@ describe('GameGateway (e2e)', () => { title: 'Chat Test Room', gameMode: 'RANKING', maxPlayerCount: 5, - isPublicGame: true + isPublic: true }); }); @@ -489,7 +489,7 @@ describe('GameGateway (e2e)', () => { title: 'Test Room', gameMode: 'RANKING', maxPlayerCount: 5, - isPublicGame: true + isPublic: true }); }); const gameId = createResponse.gameId; @@ -531,7 +531,7 @@ describe('GameGateway (e2e)', () => { title: 'Cache Test Room', gameMode: 'RANKING', maxPlayerCount: 5, - isPublicGame: true + isPublic: true }); }); const gameId = createResponse.gameId; @@ -613,7 +613,7 @@ describe('GameGateway (e2e)', () => { title: 'Cache Hit Test Room', gameMode: 'RANKING', maxPlayerCount: 5, - isPublicGame: true + isPublic: true }); }); const gameId = createResponse.gameId; @@ -693,7 +693,7 @@ describe('GameGateway (e2e)', () => { title: 'Expiry Test Room', gameMode: 'RANKING', maxPlayerCount: 5, - isPublicGame: true + isPublic: true }); }); const gameId = createResponse.gameId;