text: """ This script defines an example automated tron client that will avoid walls if it's about to crash into one.
  
  This is meant to be an example of how to implement a basic matchmaking agent.
  
  """
  
  import argparse
  
  from random import choice, randint
  
  from colosseumrl.envs.tron.rllib import SimpleAvoidAgent
  from colosseumrl.matchmaking import request_game, GameResponse
  from colosseumrl.RLApp import create_rl_agent
  from colosseumrl.envs.tron import TronGridClientEnvironment
  from colosseumrl.envs.tron import TronGridEnvironment
  from colosseumrl.rl_logging import get_logger
  
  logger = get_logger()
  
  
  def tron_client(env: TronGridClientEnvironment, username: str):
      """ Our client function for the random tron client.
  
      Parameters
      ----------
      env : TronGridClientEnvironment
          The client environment that we will interact with for this agent.
      username : str
          Our desired username.
      """
  
      # Connect to the game server and wait for the game to begin.
      # We run env.connect once we have initialized ourselves and we are ready to join the game.
      player_num = env.connect(username)
      logger.debug("Player number: {}".format(player_num))
  
      # Next we run env.wait_for_turn() to wait for our first real observation
      env.wait_for_turn()
      logger.info("Game started...")
  
      # Keep executing moves until the game is over
      terminal = False
      agent = SimpleAvoidAgent()
  
      while not terminal:
          # See if there is a wall in front of us, if there is, then we will turn in a random direction.
          action = agent(env.server_environment, env.observation)
  
          # We use env.step in order to execute an action and wait until it is our turn again.
          # This function will block while the action is executed and will return the next observation that belongs to us
          new_obs, reward, terminal, winners = env.step(action)
          print("Took step with action {}, got: {}".format(action, (new_obs, reward, terminal, winners)))
  
      # Once the game is over, we print out the results and close the agent.
      logger.info("Game is over. Players {} won".format(winners))
      logger.info("Final observation: {}".format(new_obs))
  
  
  if __name__ == '__main__':
      parser = argparse.ArgumentParser(formatter_class=argparse.ArgumentDefaultsHelpFormatter)
      parser.add_argument("--host", "-s", type=str, default="localhost",
                          help="Hostname of the matchmaking server.")
      parser.add_argument("--port", "-p", type=int, default=50051,
                          help="Port the matchmaking server is running on.")
      parser.add_argument("--username", "-u", type=str, default="",
                          help="Desired username to use for your connection. By default it will generate a random one.")
  
      logger.debug("Connecting to matchmaking server. Waiting for a game to be created.")
  
      args = parser.parse_args()
  
      if args.username == "":
          username = "Tester_{}".format(randint(0, 1000))
      else:
          username = args.username
  
      # We use request game to connect to the matchmaking server and await a game assigment.
      game: GameResponse = request_game(args.host, args.port, username)
      logger.debug("Game has been created. Playing as {}".format(username))
      logger.debug("Current Ranking: {}".format(game.ranking))
  
      # Once we have been assigned a game server, we launch an RLApp agent and begin our computation
      agent = create_rl_agent(agent_fn=tron_client,
                              host=game.host,
                              port=game.port,
                              auth_key=game.token,
                              client_environment=TronGridClientEnvironment,
                              server_environment=TronGridEnvironment)
      agent(username)
  