from __future__ import annotations import json from typing import Optional, TypeVar from pydantic import Field from pydantic.generics import GenericModel from hopper.api.dto import BaseModel, BoardDto, DestinationDto, PlayerDto, PositionDto from hopper.enums import ObjectType class LayerObjectDto(BaseModel): type: ObjectType = Field(..., alias="type_") position: PositionDto class LayerDto(BaseModel): name: str objects: list[LayerObjectDto] class GameDumpDto(BaseModel): board: BoardDto destination: DestinationDto players: list[PlayerDto] layers: list[LayerDto] class PlayerReachedDestinationDto(BaseModel): player: PlayerDto TMessageData = TypeVar("TMessageData", bound=BaseModel) class WSMessage(GenericModel): message: str data: Optional[TMessageData] = None def __str__(self) -> str: return self.to_str() def to_str(self) -> str: return json.dumps(self.dict()) @classmethod @property def message_type(cls) -> str: return cls.__fields__["message"].default class WSGameDumpMessage(WSMessage): message: str = "game_dump" data: GameDumpDto class WSProductSelectionDoneMessage(WSMessage): message: str = "product_selection_done" class WSProductSelectionTimeoutMessage(WSMessage): message: str = "product_selection_timeout" class WSPlayerReachedDestinationMessage(WSMessage): message: str = "player_reached_destination" data: PlayerReachedDestinationDto