diff --git a/apps/server/src/network/handlers/eventDefinitionRegistrar.ts b/apps/server/src/network/handlers/eventDefinitionRegistrar.ts index 09cf32e..196816b 100644 --- a/apps/server/src/network/handlers/eventDefinitionRegistrar.ts +++ b/apps/server/src/network/handlers/eventDefinitionRegistrar.ts @@ -35,39 +35,35 @@ }; /** 検証付きイベント定義を登録する */ -export const registerGuardedEvents = ( +export const registerGuardedEvent = ( subscribe: (event: TEvent, callback: (payload: unknown) => void) => void, - createGuard: ( + createGuard: ( event: TEvent, validator: (value: unknown) => value is TPayload, ) => (payload: unknown) => payload is TPayload, - definitions: GuardedEventDefinition[], + definition: GuardedEventDefinition, ): void => { - definitions.forEach((definition) => { - const guard = createGuard(definition.event, definition.validator); - subscribe(definition.event, (payload) => { - if (!guard(payload)) { - return; - } + const guard = createGuard(definition.event, definition.validator); + subscribe(definition.event, (payload) => { + if (!guard(payload)) { + return; + } - void definition.orchestrate(payload); - }); + void definition.orchestrate(payload); }); }; /** 自前検証イベント定義を登録する */ -export const registerSelfValidatedEvents = ( +export const registerSelfValidatedEvent = ( subscribe: (event: TEvent, callback: (payload: unknown) => void) => void, - definitions: SelfValidatedEventDefinition[], + definition: SelfValidatedEventDefinition, ): void => { - definitions.forEach((definition) => { - subscribe(definition.event, (payload) => { - if (!definition.validator(payload)) { - return; - } + subscribe(definition.event, (payload) => { + if (!definition.validator(payload)) { + return; + } - void definition.orchestrate(payload); - }); + void definition.orchestrate(payload); }); }; diff --git a/apps/server/src/network/handlers/game/gameEventOrchestrators.ts b/apps/server/src/network/handlers/game/gameEventOrchestrators.ts index 36dbb86..a522685 100644 --- a/apps/server/src/network/handlers/game/gameEventOrchestrators.ts +++ b/apps/server/src/network/handlers/game/gameEventOrchestrators.ts @@ -24,6 +24,18 @@ targetPlayerCount?: number; }; +/** PINGイベントの入力ペイロード型 */ +export type PingEventPayload = Parameters[1]; + +/** MOVEイベントの入力ペイロード型 */ +export type MoveEventPayload = Parameters[1]; + +/** PLACE_BOMBイベントの入力ペイロード型 */ +export type PlaceBombEventPayload = Parameters[1]; + +/** BOMB_HIT_REPORTイベントの入力ペイロード型 */ +export type BombHitReportEventPayload = Parameters[1]; + /** ゲームイベント調停で利用する依存集合 */ export type GameEventOrchestratorDeps = { socketId: string; diff --git a/apps/server/src/network/handlers/game/registerGameHandlers.ts b/apps/server/src/network/handlers/game/registerGameHandlers.ts index 17cbcab..39107ec 100644 --- a/apps/server/src/network/handlers/game/registerGameHandlers.ts +++ b/apps/server/src/network/handlers/game/registerGameHandlers.ts @@ -19,46 +19,40 @@ import { createPayloadGuard } from "@server/network/handlers/payloadGuard"; import type { GameOutputAdapter } from "./createGameOutputAdapter"; import { + type BombHitReportEventPayload, + type MoveEventPayload, + type PingEventPayload, + type PlaceBombEventPayload, handleBombHitReportEvent, type GameEventOrchestratorDeps, handleMoveEvent, handlePingEvent, handlePlaceBombEvent, handleReadyForGameEvent, + type StartGamePayload, handleStartGameEvent, } from "./gameEventOrchestrators"; import { - registerGuardedEvents, - registerSelfValidatedEvents, + registerGuardedEvent, + registerSelfValidatedEvent, registerUnguardedEvents, type GuardedEventDefinition, type SelfValidatedEventDefinition, type UnguardedEventDefinition, } from "@server/network/handlers/eventDefinitionRegistrar"; -type PingEventDefinition = GuardedEventDefinition< - typeof protocol.SocketEvents.PING, - Parameters[1] ->; +type PingEventDefinition = GuardedEventDefinition; -type MoveEventDefinition = GuardedEventDefinition< - typeof protocol.SocketEvents.MOVE, - Parameters[1] ->; +type MoveEventDefinition = GuardedEventDefinition; -type PlaceBombEventDefinition = GuardedEventDefinition< - typeof protocol.SocketEvents.PLACE_BOMB, - Parameters[1] ->; +type PlaceBombEventDefinition = GuardedEventDefinition; -type BombHitReportEventDefinition = GuardedEventDefinition< - typeof protocol.SocketEvents.BOMB_HIT_REPORT, - Parameters[1] ->; +type BombHitReportEventDefinition = GuardedEventDefinition; -type StartGameEventDefinition = SelfValidatedEventDefinition< - typeof protocol.SocketEvents.START_GAME, - Parameters[1] +type StartGameEventDefinition = SelfValidatedEventDefinition; + +type ReadyForGameEventDefinition = UnguardedEventDefinition< + typeof protocol.SocketEvents.READY_FOR_GAME >; /** ゲーム受信イベントごとの入力検証関数を保持するテーブル */ @@ -84,6 +78,83 @@ }; }; +/** PINGイベント定義を生成する */ +const createPingEventDefinition = ( + deps: GameEventOrchestratorDeps, +): PingEventDefinition => { + return { + event: protocol.SocketEvents.PING, + validator: gamePayloadValidators[protocol.SocketEvents.PING], + orchestrate: (payload) => { + handlePingEvent(deps, payload); + }, + }; +}; + +/** MOVEイベント定義を生成する */ +const createMoveEventDefinition = ( + deps: GameEventOrchestratorDeps, +): MoveEventDefinition => { + return { + event: protocol.SocketEvents.MOVE, + validator: gamePayloadValidators[protocol.SocketEvents.MOVE], + orchestrate: (payload) => { + handleMoveEvent(deps, payload); + }, + }; +}; + +/** PLACE_BOMBイベント定義を生成する */ +const createPlaceBombEventDefinition = ( + deps: GameEventOrchestratorDeps, +): PlaceBombEventDefinition => { + return { + event: protocol.SocketEvents.PLACE_BOMB, + validator: gamePayloadValidators[protocol.SocketEvents.PLACE_BOMB], + orchestrate: (payload) => { + handlePlaceBombEvent(deps, payload); + }, + }; +}; + +/** BOMB_HIT_REPORTイベント定義を生成する */ +const createBombHitReportEventDefinition = ( + deps: GameEventOrchestratorDeps, +): BombHitReportEventDefinition => { + return { + event: protocol.SocketEvents.BOMB_HIT_REPORT, + validator: gamePayloadValidators[protocol.SocketEvents.BOMB_HIT_REPORT], + orchestrate: (payload) => { + handleBombHitReportEvent(deps, payload); + }, + }; +}; + +/** START_GAMEイベント定義を生成する */ +const createStartGameEventDefinition = ( + deps: GameEventOrchestratorDeps, +): StartGameEventDefinition => { + return { + event: protocol.SocketEvents.START_GAME, + validator: isStartGamePayload, + orchestrate: (payload) => { + handleStartGameEvent(deps, payload); + }, + }; +}; + +/** READY_FOR_GAMEイベント定義を生成する */ +const createReadyForGameEventDefinition = ( + deps: GameEventOrchestratorDeps, +): ReadyForGameEventDefinition => { + return { + event: protocol.SocketEvents.READY_FOR_GAME, + orchestrate: () => { + handleReadyForGameEvent(deps); + }, + }; +}; + /** ゲームイベントの購読とユースケース呼び出しを設定する */ export const registerGameHandlers = ( socket: Socket, @@ -101,65 +172,24 @@ const { guardOnEvent } = createPayloadGuard(socket.id); // 検証が必要なイベントを宣言的に登録する - const guardedGameEventDefinitions: Array< - | PingEventDefinition - | MoveEventDefinition - | PlaceBombEventDefinition - | BombHitReportEventDefinition - > = [ - { - event: protocol.SocketEvents.PING, - validator: gamePayloadValidators[protocol.SocketEvents.PING], - orchestrate: (payload) => { - handlePingEvent(orchestratorDeps, payload); - }, - }, - { - event: protocol.SocketEvents.MOVE, - validator: gamePayloadValidators[protocol.SocketEvents.MOVE], - orchestrate: (payload) => { - handleMoveEvent(orchestratorDeps, payload); - }, - }, - { - event: protocol.SocketEvents.PLACE_BOMB, - validator: gamePayloadValidators[protocol.SocketEvents.PLACE_BOMB], - orchestrate: (payload) => { - handlePlaceBombEvent(orchestratorDeps, payload); - }, - }, - { - event: protocol.SocketEvents.BOMB_HIT_REPORT, - validator: gamePayloadValidators[protocol.SocketEvents.BOMB_HIT_REPORT], - orchestrate: (payload) => { - handleBombHitReportEvent(orchestratorDeps, payload); - }, - }, - ]; + const pingEventDefinition = createPingEventDefinition(orchestratorDeps); + const moveEventDefinition = createMoveEventDefinition(orchestratorDeps); + const placeBombEventDefinition = createPlaceBombEventDefinition(orchestratorDeps); + const bombHitReportEventDefinition = createBombHitReportEventDefinition(orchestratorDeps); - registerGuardedEvents(onEvent, guardOnEvent, guardedGameEventDefinitions); + registerGuardedEvent(onEvent, guardOnEvent, pingEventDefinition); + registerGuardedEvent(onEvent, guardOnEvent, moveEventDefinition); + registerGuardedEvent(onEvent, guardOnEvent, placeBombEventDefinition); + registerGuardedEvent(onEvent, guardOnEvent, bombHitReportEventDefinition); // payloadGuard対象外だが検証が必要なイベントを宣言的に登録する - const selfValidatedGameEventDefinitions: StartGameEventDefinition[] = [ - { - event: protocol.SocketEvents.START_GAME, - validator: isStartGamePayload, - orchestrate: (payload) => { - handleStartGameEvent(orchestratorDeps, payload); - }, - }, - ]; + const startGameEventDefinition = createStartGameEventDefinition(orchestratorDeps); - registerSelfValidatedEvents(onEvent, selfValidatedGameEventDefinitions); + registerSelfValidatedEvent(onEvent, startGameEventDefinition); // 検証不要イベントを宣言的に登録する - const unguardedGameEventDefinitions: UnguardedEventDefinition[] = [ - { - event: protocol.SocketEvents.READY_FOR_GAME, - orchestrate: () => { - handleReadyForGameEvent(orchestratorDeps); - }, - }, + const unguardedGameEventDefinitions: ReadyForGameEventDefinition[] = [ + createReadyForGameEventDefinition(orchestratorDeps), ]; registerUnguardedEvents(onEvent, unguardedGameEventDefinitions); diff --git a/apps/server/src/network/handlers/room/registerRoomHandlers.ts b/apps/server/src/network/handlers/room/registerRoomHandlers.ts index 246ab11..5264d12 100644 --- a/apps/server/src/network/handlers/room/registerRoomHandlers.ts +++ b/apps/server/src/network/handlers/room/registerRoomHandlers.ts @@ -17,7 +17,7 @@ type JoinRoomOrchestratorDeps, } from "./roomEventOrchestrators"; import { - registerGuardedEvents, + registerGuardedEvent, type GuardedEventDefinition, } from "@server/network/handlers/eventDefinitionRegistrar"; @@ -49,6 +49,19 @@ }; }; +/** JOIN_ROOMイベント定義を生成する */ +const createJoinRoomEventDefinition = ( + deps: JoinRoomOrchestratorDeps, +): JoinRoomEventDefinition => { + return { + event: protocol.SocketEvents.JOIN_ROOM, + validator: roomPayloadValidators[protocol.SocketEvents.JOIN_ROOM], + orchestrate: async (payload) => { + await handleJoinRoomEvent(deps, payload); + }, + }; +}; + /** ルーム参加イベントを検証して参加ユースケースへ連携する */ export const registerRoomHandlers = ( socket: Socket, @@ -66,15 +79,9 @@ const { guardOnEvent } = createPayloadGuard(socket.id); // 検証が必要なイベントを宣言的に登録する - const guardedRoomEventDefinitions: JoinRoomEventDefinition[] = [ - { - event: protocol.SocketEvents.JOIN_ROOM, - validator: roomPayloadValidators[protocol.SocketEvents.JOIN_ROOM], - orchestrate: async (payload) => { - await handleJoinRoomEvent(orchestratorDeps, payload); - }, - }, - ]; + const joinRoomEventDefinition = createJoinRoomEventDefinition( + orchestratorDeps, + ); - registerGuardedEvents(onEvent, guardOnEvent, guardedRoomEventDefinitions); + registerGuardedEvent(onEvent, guardOnEvent, joinRoomEventDefinition); };