def do_list(args, config):
    url = config.get('DEFAULT', 'url')
    key_file = config.get('DEFAULT', 'key_file')

    client = BattleshipClient(base_url=url, keyfile=key_file)
    state = client.list_games()

    fmt = "%-15s %-15.15s %-15.15s %s"
    print(fmt % ('GAME', 'PLAYER 1', 'PLAYER 2', 'STATE'))
def do_join(args, config):
    name = args.name

    url = config.get('DEFAULT', 'url')
    key_file = config.get('DEFAULT', 'key_file')

    data = load_data(config)

    client_for_state = BattleshipClient(base_url=url, keyfile=key_file)
    state = client_for_state.list_games()
    if name not in state:
        raise BattleshipException(
            "No such game: {}".format(name)
        )
    game = state[name]
    ships = game['Ships']

    if name not in data['games']:
        new_layout = BoardLayout.generate(ships=ships)
        data['games'][name] = {}
        data['games'][name]['layout'] = new_layout.serialize()
        data['games'][name]['nonces'] = create_nonces(new_layout.size)

        home = os.path.expanduser("~")

        username = config.get('DEFAULT', 'username')

        data_file = os.path.join(home,
                                 ".sawtooth",
                                 "battleship-{}.data".format(username))
        with open(data_file + ".new", 'w') as fd:
            json.dump(data, fd, sort_keys=True, indent=4)
        if os.name == 'nt':
            if os.path.exists(data_file):
                os.remove(data_file)
        os.rename(data_file + ".new", data_file)
    else:
        print("Board and nonces already defined for game, reusing...")

    layout = BoardLayout.deserialize(data['games'][name]['layout'])
    nonces = data['games'][name]['nonces']

    hashed_board = layout.render_hashed(nonces)

    client = BattleshipClient(base_url=url, keyfile=key_file, wait=args.wait)
    client.join(name=name, board=hashed_board)
def do_join(args, config):
    name = args.name

    url = config.get('DEFAULT', 'url')
    key_file = config.get('DEFAULT', 'key_file')

    data = load_data(config)

    client_for_state = BattleshipClient(base_url=url, keyfile=key_file)
    state = client_for_state.list_games()
    if name not in state:
        raise BattleshipException(
            "No such game: {}".format(name)
        )
    game = state[name]
    ships = game['Ships']

    if name not in data['games']:
        new_layout = BoardLayout.generate(ships=ships)
        data['games'][name] = {}
        data['games'][name]['layout'] = new_layout.serialize()
        data['games'][name]['nonces'] = create_nonces(new_layout.size)

        home = os.path.expanduser("~")

        username = config.get('DEFAULT', 'username')

        data_file = os.path.join(home,
                                 ".sawtooth",
                                 "battleship-{}.data".format(username))
        with open(data_file + ".new", 'w') as fd:
            json.dump(data, fd, sort_keys=True, indent=4)
        if os.name == 'nt':
            if os.path.exists(data_file):
                os.remove(data_file)
        os.rename(data_file + ".new", data_file)
    else:
        print("Board and nonces already defined for game, reusing...")

    layout = BoardLayout.deserialize(data['games'][name]['layout'])
    nonces = data['games'][name]['nonces']

    hashed_board = layout.render_hashed(nonces)

    client = BattleshipClient(base_url=url, keyfile=key_file, wait=args.wait)
    client.join(name=name, board=hashed_board)
def do_fire(args, config):
    name = args.name
    column = args.column
    row = args.row

    url = config.get('DEFAULT', 'url')
    key_file = config.get('DEFAULT', 'key_file')

    data = load_data(config)

    if name not in data['games']:
        raise BattleshipException(
            "no such game in local database: {}".format(name))

    client = BattleshipClient(base_url=url, keyfile=key_file, wait=args.wait)
    state = client.list_games()

    if name not in state:
        raise BattleshipException(
            "no such game: {}".format(name))
    state_game = state[name]

    reveal_space = None
    reveal_nonce = None

    if 'LastFireColumn' in state_game:
        last_col = ord(state_game['LastFireColumn']) - ord('A')
        last_row = int(state_game['LastFireRow']) - 1

        layout = BoardLayout.deserialize(data['games'][name]['layout'])
        nonces = data['games'][name]['nonces']

        reveal_space = layout.render()[last_row][last_col]
        reveal_nonce = nonces[last_row][last_col]

    response = client.fire(
        name=name,
        column=column,
        row=row,
        reveal_space=reveal_space,
        reveal_nonce=reveal_nonce)

    print(response)
def do_fire(args, config):
    name = args.name
    column = args.column
    row = args.row

    url = config.get('DEFAULT', 'url')
    key_file = config.get('DEFAULT', 'key_file')

    data = load_data(config)

    if name not in data['games']:
        raise BattleshipException(
            "no such game in local database: {}".format(name))

    client = BattleshipClient(base_url=url, keyfile=key_file, wait=args.wait)
    state = client.list_games()

    if name not in state:
        raise BattleshipException(
            "no such game: {}".format(name))
    state_game = state[name]

    reveal_space = None
    reveal_nonce = None

    if 'LastFireColumn' in state_game:
        last_col = ord(state_game['LastFireColumn']) - ord('A')
        last_row = int(state_game['LastFireRow']) - 1

        layout = BoardLayout.deserialize(data['games'][name]['layout'])
        nonces = data['games'][name]['nonces']

        reveal_space = layout.render()[last_row][last_col]
        reveal_nonce = nonces[last_row][last_col]

    response = client.fire(
        name=name,
        column=column,
        row=row,
        reveal_space=reveal_space,
        reveal_nonce=reveal_nonce)

    print(response)
def do_list(args, config):
    url = config.get('DEFAULT', 'url')
    key_file = config.get('DEFAULT', 'key_file')

    client = BattleshipClient(base_url=url, keyfile=key_file)
    state = client.list_games()

    fmt = "%-15s %-15.15s %-15.15s %s"
    print(fmt % ('GAME', 'PLAYER 1', 'PLAYER 2', 'STATE'))

    keys = list(state.keys())
    keys.sort()
    for name in keys:
        if 'Player1' in state[name]:
            player1 = state[name]['Player1']
        else:
            player1 = ''
        if 'Player2' in state[name]:
            player2 = state[name]['Player2']
        else:
            player2 = ''
        game_state = state[name]['State']
        print(fmt % (name, player1, player2, game_state))
def do_list(args, config):
    url = config.get('DEFAULT', 'url')
    key_file = config.get('DEFAULT', 'key_file')

    client = BattleshipClient(base_url=url, keyfile=key_file)
    state = client.list_games()

    fmt = "%-15s %-15.15s %-15.15s %s"
    print(fmt % ('GAME', 'PLAYER 1', 'PLAYER 2', 'STATE'))

    keys = list(state.keys())
    keys.sort()
    for name in keys:
        if 'Player1' in state[name]:
            player1 = state[name]['Player1']
        else:
            player1 = ''
        if 'Player2' in state[name]:
            player2 = state[name]['Player2']
        else:
            player2 = ''
        game_state = state[name]['State']
        print(fmt % (name, player1, player2, game_state))
def do_show(args, config):
    name = args.name

    url = config.get('DEFAULT', 'url')
    key_file = config.get('DEFAULT', 'key_file')

    data = load_data(config)

    client = BattleshipClient(base_url=url, keyfile=key_file)
    state = client.list_games()

    if name not in state:
        raise BattleshipException('no such game: {}'.format(name))

    game = state[name]

    player1 = ''
    player2 = ''
    if 'Player1' in game:
        player1 = game['Player1']
    if 'Player2' in game:
        player2 = game['Player2']
    game_state = game['State']

    print("GAME:     : {}".format(name))
    print("PLAYER 1  : {}".format(player1))
    print("PLAYER 2  : {}".format(player2))
    print("STATE     : {}".format(game_state))

    # figure out the proper user's target board, given the public_key
    priv_filename = config.get('DEFAULT', 'key_file')
    if priv_filename.endswith(".priv"):
        public_key_filename = priv_filename[0:-len(".priv")] + ".pub"
    else:
        public_key_filename = priv_filename + ".pub"
    public_key_file = open(public_key_filename, mode='r')
    public_key = public_key_file.readline().rstrip('\n')

    if 'Player1' in game and public_key == game['Player1']:
        target_board_name = 'TargetBoard1'
    elif 'Player2' in game and public_key == game['Player2']:
        target_board_name = 'TargetBoard2'
    else:
        raise BattleshipException("Player hasn't joined game.")

    # figure out who fired last and who is calling do_show
    # to determine which board * is diplayed on to
    # show pending shot
    if 'LastFireRow' in game and 'LastFireColumn' in game:
        last_fire = (int(game['LastFireRow']) - 1,
                     int(ord(game['LastFireColumn'])) - ord('A'))
    else:
        last_fire = None

    if game_state == 'P1-NEXT' and target_board_name == 'TargetBoard1':
        # player 2 last shot and player 1 is looking
        will_be_on_target_board = False
    elif game_state == 'P1-NEXT' and target_board_name == 'TargetBoard2':
        # player 2 last shot and player 2 is looking
        will_be_on_target_board = True
    elif game_state == 'P2-NEXT' and target_board_name == 'TargetBoard1':
        # player 1 last shot and player 1 is looking
        will_be_on_target_board = True
    elif game_state == 'P2-NEXT' and target_board_name == 'TargetBoard2':
        # player 1 last shot and player 2 is looking
        will_be_on_target_board = False
    else:
        last_fire = None
        will_be_on_target_board = False

    if target_board_name in game:
        target_board = game[target_board_name]
        size = len(target_board)

        print()
        print("  Target Board")
        print_board(target_board,
                    size,
                    is_target_board=True,
                    pending_on_target_board=will_be_on_target_board,
                    last_fire=last_fire)

    if name in data['games']:
        layout = BoardLayout.deserialize(data['games'][name]['layout'])
        board = layout.render()
        size = len(board)

        print()
        print("  Secret Board")
        print_board(board,
                    size,
                    is_target_board=False,
                    pending_on_target_board=will_be_on_target_board,
                    last_fire=last_fire)
def do_show(args, config):
    name = args.name

    url = config.get('DEFAULT', 'url')
    key_file = config.get('DEFAULT', 'key_file')

    data = load_data(config)

    client = BattleshipClient(base_url=url, keyfile=key_file)
    state = client.list_games()

    if name not in state:
        raise BattleshipException('no such game: {}'.format(name))

    game = state[name]

    player1 = ''
    player2 = ''
    if 'Player1' in game:
        player1 = game['Player1']
    if 'Player2' in game:
        player2 = game['Player2']
    game_state = game['State']

    print("GAME:     : {}".format(name))
    print("PLAYER 1  : {}".format(player1))
    print("PLAYER 2  : {}".format(player2))
    print("STATE     : {}".format(game_state))

    # figure out the proper user's target board, given the public_key
    priv_filename = config.get('DEFAULT', 'key_file')
    if priv_filename.endswith(".priv"):
        public_key_filename = priv_filename[0:-len(".priv")] + ".pub"
    else:
        public_key_filename = priv_filename + ".pub"
    public_key_file = open(public_key_filename, mode='r')
    public_key = public_key_file.readline().rstrip('\n')

    if 'Player1' in game and public_key == game['Player1']:
        target_board_name = 'TargetBoard1'
    elif 'Player2' in game and public_key == game['Player2']:
        target_board_name = 'TargetBoard2'
    else:
        raise BattleshipException("Player hasn't joined game.")

    # figure out who fired last and who is calling do_show
    # to determine which board * is diplayed on to
    # show pending shot
    if 'LastFireRow' in game and 'LastFireColumn' in game:
        last_fire = (int(game['LastFireRow']) - 1,
                     int(ord(game['LastFireColumn'])) - ord('A'))
    else:
        last_fire = None

    if game_state == 'P1-NEXT' and target_board_name == 'TargetBoard1':
        # player 2 last shot and player 1 is looking
        will_be_on_target_board = False
    elif game_state == 'P1-NEXT' and target_board_name == 'TargetBoard2':
        # player 2 last shot and player 2 is looking
        will_be_on_target_board = True
    elif game_state == 'P2-NEXT' and target_board_name == 'TargetBoard1':
        # player 1 last shot and player 1 is looking
        will_be_on_target_board = True
    elif game_state == 'P2-NEXT' and target_board_name == 'TargetBoard2':
        # player 1 last shot and player 2 is looking
        will_be_on_target_board = False
    else:
        last_fire = None
        will_be_on_target_board = False

    if target_board_name in game:
        target_board = game[target_board_name]
        size = len(target_board)

        print()
        print("  Target Board")
        print_board(target_board, size, is_target_board=True,
                    pending_on_target_board=will_be_on_target_board,
                    last_fire=last_fire)

    if name in data['games']:
        layout = BoardLayout.deserialize(data['games'][name]['layout'])
        board = layout.render()
        size = len(board)

        print()
        print("  Secret Board")
        print_board(board, size, is_target_board=False,
                    pending_on_target_board=will_be_on_target_board,
                    last_fire=last_fire)