async def create_game(ws: WebSocketServerProtocol, pr: persister.Persister): ip = remote_addr(ws) request: NewGameRequest = await recv_d(ws, NewGameRequest, 'new-game') game_id = new_game_id() game = Game( game_id=game_id, game_name=request.game_name, round_length=request.round_length, hat_words_per_user=request.hat_words_per_user, state_saver=make_state_saver(game_id=game_id, pr=pr), ) rooms[game_id] = game.room log.info(f'Created game {game_id} named \"{request.game_name}\" for {ip}') await ws.send(rmsg('new-game-id', game_id))
async def _serve(pr: persister.Persister, ws: WebSocketServerProtocol, path: str): ip = remote_addr(ws) if RE_GAME_PATH.match(path): game_id = RE_GAME_PATH.matches.group(1) log.info(f'New connection from {ip} to game {game_id}') await serve_game(ws, game_id, False, pr) elif RE_ADMIN_PATH.match(path): game_id = RE_ADMIN_PATH.matches.group(1) log.info(f'New admin connection from {ip} to game {game_id}') await serve_game(ws, game_id, True, pr) elif RE_NEW_GAME_PATH.match(path): log.info(f'New game session connection from {ip}') await create_game(ws, pr) else: await ws.send(rerr('wrong-path', 'Wrong path')) await ws.close(1002, f'Wrong path {path}')
async def auth(websocket: WebSocketServerProtocol) -> Optional[User]: ip = remote_addr(websocket) try: tag, message = await recv(websocket, msg.AuthRequest) except ProtocolError as err: log.info(f'Remote socket {ip} failed to authenticate: {err}') return None user_name = message.user_name if user_name == 'admin': await websocket.send(rerr('auth-error', f'wrong name {user_name}')) return None user_id = adler32(user_name.encode()) user = User(user_id, user_name) await websocket.send(rmsg('auth-ok', user.to_msg())) log.info(f'Connection {ip} authenticated as {user}') return user
async def serve( pr: persister.Persister, ws: WebSocketServerProtocol, path: str, ): ip = remote_addr(ws) try: await _serve(pr=pr, ws=ws, path=path) except ConnectionClosed as err: log.info(f'Connection {ip} closed ({err.code})') except ProtocolError as err: log.info(f'Connection {ip}: protocol error: {err}') try: await ws.send(rerr('protocol-error', 'Protocol error')) await ws.close(1002, f'protocol error') except Exception as err: log.debug(f'Connection {ip}: Error closing failed socket: {err}') pass except Exception as err: log.exception(f'Exception in handle {ip} path {path}')
async def serve_game(ws: WebSocketServerProtocol, game_id: str, admin: bool, pr: persister.Persister): ip = remote_addr(ws) try: room = rooms[game_id] except KeyError: try: game = await load_game(game_id=game_id, pr=pr) rooms[game_id] = game.room room = rooms[game_id] log.info(f'Loaded game {game_id} from persister') except persister.GameDoesNotExist: log.info(f'{ip} is trying to join non-existent game {game_id}') await ws.send(rerr('wrong-game', 'Wrong game')) await ws.close() return if admin: await room.serve_admin(ws) else: await room.serve_user(ws) await ws.close()
def _wsfmt(ws: WebSocketServerProtocol): return remote_addr(ws)