Une exception on the command.run to notify the player instead on direct send

This commit is contained in:
2025-03-14 21:02:37 +01:00
parent 5a5e7ab7cf
commit 7d06babdeb
8 changed files with 35 additions and 28 deletions

View File

@@ -0,0 +1,5 @@
package eventDemo.app.command
class CommandException(
override val message: String,
) : Exception(message)

View File

@@ -14,7 +14,7 @@ fun errorNotifier(
): ErrorNotifier =
{
val logger = KotlinLogging.logger { }
ErrorNotification(message = it)
ErrorNotification(message = it, command = command)
.let { notification ->
logger.atWarn {
message = "Notification ERROR sent: ${notification.message}"

View File

@@ -19,13 +19,16 @@ class GameCommandRunner(
outgoingErrorChannelNotification: SendChannel<Notification>,
) {
val gameState = gameStateRepository.getLast(command.payload.aggregateId)
val errorNotifier = errorNotifier(command, outgoingErrorChannelNotification)
try {
when (command) {
is IWantToPlayCardCommand -> command.run(gameState, errorNotifier, this.eventHandler)
is IamReadyToPlayCommand -> command.run(gameState, errorNotifier, this.eventHandler)
is IWantToJoinTheGameCommand -> command.run(gameState, errorNotifier, this.eventHandler)
is ICantPlayCommand -> command.run(gameState, errorNotifier, this.eventHandler)
is IWantToPlayCardCommand -> command.run(gameState, this.eventHandler)
is IamReadyToPlayCommand -> command.run(gameState, this.eventHandler)
is IWantToJoinTheGameCommand -> command.run(gameState, this.eventHandler)
is ICantPlayCommand -> command.run(gameState, this.eventHandler)
}
} catch (e: CommandException) {
errorNotifier(command, outgoingErrorChannelNotification)(e.message)
}
}
}

View File

@@ -1,6 +1,6 @@
package eventDemo.app.command.command
import eventDemo.app.command.ErrorNotifier
import eventDemo.app.command.CommandException
import eventDemo.app.entity.GameId
import eventDemo.app.entity.Player
import eventDemo.app.event.GameEventHandler
@@ -26,12 +26,10 @@ data class ICantPlayCommand(
suspend fun run(
state: GameState,
playerErrorNotifier: ErrorNotifier,
eventHandler: GameEventHandler,
) {
if (state.currentPlayerTurn != payload.player) {
playerErrorNotifier("Its not your turn!")
return
throw CommandException("Its not your turn!")
}
val playableCards = state.playableCards(payload.player)
if (playableCards.isEmpty()) {
@@ -46,7 +44,7 @@ data class ICantPlayCommand(
)
}
} else {
playerErrorNotifier("You can and must play one card, like ${playableCards.first()::class.simpleName}")
throw CommandException("You can and must play one card, like ${playableCards.first()::class.simpleName}")
}
}
}

View File

@@ -1,6 +1,6 @@
package eventDemo.app.command.command
import eventDemo.app.command.ErrorNotifier
import eventDemo.app.command.CommandException
import eventDemo.app.entity.GameId
import eventDemo.app.entity.Player
import eventDemo.app.event.GameEventHandler
@@ -26,7 +26,6 @@ data class IWantToJoinTheGameCommand(
suspend fun run(
state: GameState,
playerErrorNotifier: ErrorNotifier,
eventHandler: GameEventHandler,
) {
if (!state.isStarted) {
@@ -38,7 +37,7 @@ data class IWantToJoinTheGameCommand(
)
}
} else {
playerErrorNotifier("The game is already started")
throw CommandException("The game is already started")
}
}
}

View File

@@ -1,6 +1,6 @@
package eventDemo.app.command.command
import eventDemo.app.command.ErrorNotifier
import eventDemo.app.command.CommandException
import eventDemo.app.entity.Card
import eventDemo.app.entity.GameId
import eventDemo.app.entity.Player
@@ -28,16 +28,13 @@ data class IWantToPlayCardCommand(
suspend fun run(
state: GameState,
playerErrorNotifier: ErrorNotifier,
eventHandler: GameEventHandler,
) {
if (!state.isStarted) {
playerErrorNotifier("The game is Not started")
return
throw CommandException("The game is Not started")
}
if (state.currentPlayerTurn != payload.player) {
playerErrorNotifier("Its not your turn!")
return
throw CommandException("Its not your turn!")
}
if (state.canBePlayThisCard(payload.player, payload.card)) {
@@ -50,7 +47,7 @@ data class IWantToPlayCardCommand(
)
}
} else {
playerErrorNotifier("You cannot play this card")
throw CommandException("You cannot play this card")
}
}
}

View File

@@ -1,6 +1,6 @@
package eventDemo.app.command.command
import eventDemo.app.command.ErrorNotifier
import eventDemo.app.command.CommandException
import eventDemo.app.entity.GameId
import eventDemo.app.entity.Player
import eventDemo.app.event.GameEventHandler
@@ -24,20 +24,20 @@ data class IamReadyToPlayCommand(
override val player: Player,
) : GameCommand.Payload
@Throws(CommandException::class)
suspend fun run(
state: GameState,
playerErrorNotifier: ErrorNotifier,
eventHandler: GameEventHandler,
) {
val playerExist: Boolean = state.players.contains(payload.player)
val playerIsAlreadyReady: Boolean = state.readyPlayers.contains(payload.player)
if (state.isStarted) {
playerErrorNotifier("The game is already started")
throw CommandException("The game is already started")
} else if (!playerExist) {
playerErrorNotifier("You are not in the game")
throw CommandException("You are not in the game")
} else if (playerIsAlreadyReady) {
playerErrorNotifier("You are already ready")
throw CommandException("You are already ready")
} else {
eventHandler.handle(payload.aggregateId) {
PlayerReadyEvent(

View File

@@ -1,12 +1,17 @@
package eventDemo.app.notification
import eventDemo.configuration.UUIDSerializer
import eventDemo.libs.command.Command
import kotlinx.serialization.Serializable
import java.util.UUID
sealed interface CommandStateNotification : Notification
@Serializable
data class ErrorNotification(
@Serializable(with = UUIDSerializer::class)
override val id: UUID = UUID.randomUUID(),
val message: String,
) : Notification
val command: Command,
) : Notification,
CommandStateNotification