def test_verify_challenge_tx_sequence_not_zero(self):
        server_kp = Keypair.random()
        client_kp = Keypair.random()
        network_passphrase = Network.PUBLIC_NETWORK_PASSPHRASE
        anchor_name = "SDF"
        now = int(time.time())
        nonce = os.urandom(48)
        nonce_encoded = base64.b64encode(nonce)
        server_account = Account(server_kp.public_key, 10086)
        challenge_te = (TransactionBuilder(
            server_account, network_passphrase, 100).append_manage_data_op(
                data_name="{} auth".format(anchor_name),
                data_value=nonce_encoded,
                source=client_kp.public_key,
            ).add_time_bounds(now, now + 900).build())

        challenge_te.sign(server_kp)
        challenge_te.sign(client_kp)
        challenge_tx_signed = challenge_te.to_xdr()

        with pytest.raises(
                InvalidSep10ChallengeError,
                match="The transaction sequence number should be zero.",
        ):
            verify_challenge_transaction(challenge_tx_signed,
                                         server_kp.public_key,
                                         network_passphrase)
    def test_verify_challenge_tx_not_within_range_of_the_specified_timebounds(
            self):
        server_kp = Keypair.random()
        client_kp = Keypair.random()
        network_passphrase = Network.PUBLIC_NETWORK_PASSPHRASE
        anchor_name = "SDF"
        now = int(time.time())
        nonce = os.urandom(48)
        nonce_encoded = base64.b64encode(nonce)
        server_account = Account(server_kp.public_key, -1)
        challenge_te = (TransactionBuilder(
            server_account, network_passphrase, 100).append_manage_data_op(
                data_name="{} auth".format(anchor_name),
                data_value=nonce_encoded,
                source=client_kp.public_key,
            ).add_time_bounds(now - 100, now - 50).build())

        challenge_te.sign(server_kp)
        challenge_te.sign(client_kp)
        challenge_tx_signed = challenge_te.to_xdr()

        with pytest.raises(
                InvalidSep10ChallengeError,
                match=
                "Transaction is not within range of the specified timebounds.",
        ):
            verify_challenge_transaction(challenge_tx_signed,
                                         server_kp.public_key,
                                         network_passphrase)
    def test_verify_challenge_tx_transaction_is_not_signed_by_the_server(self):
        server_kp = Keypair.random()
        client_kp = Keypair.random()
        network_passphrase = Network.PUBLIC_NETWORK_PASSPHRASE
        anchor_name = "SDF"
        timeout = 900

        now = int(time.time())
        server_keypair = Keypair.from_secret(server_kp.secret)
        server_account = Account(account_id=server_keypair.public_key,
                                 sequence=-1)
        transaction_builder = TransactionBuilder(server_account,
                                                 network_passphrase, 100)
        transaction_builder.add_time_bounds(min_time=now,
                                            max_time=now + timeout)
        nonce = os.urandom(48)
        nonce_encoded = base64.b64encode(nonce)
        transaction_builder.append_manage_data_op(
            data_name="{} auth".format(anchor_name),
            data_value=nonce_encoded,
            source=client_kp.public_key,
        )
        challenge = transaction_builder.build().to_xdr()

        transaction = TransactionEnvelope.from_xdr(challenge,
                                                   network_passphrase)
        transaction.sign(client_kp)
        challenge_tx = transaction.to_xdr()
        with pytest.raises(
                InvalidSep10ChallengeError,
                match="Transaction not signed by server: {}".format(
                    server_kp.public_key),
        ):
            verify_challenge_transaction(challenge_tx, server_kp.public_key,
                                         network_passphrase)
    def test_verify_challenge_tx_source_is_different_to_server_account_id(
            self):
        server_kp = Keypair.random()
        client_kp = Keypair.random()
        network_passphrase = Network.TESTNET_NETWORK_PASSPHRASE
        anchor_name = "SDF"

        challenge = build_challenge_transaction(server_kp.secret,
                                                client_kp.public_key,
                                                anchor_name,
                                                network_passphrase)

        transaction = TransactionEnvelope.from_xdr(challenge,
                                                   network_passphrase)
        transaction.sign(client_kp)

        challenge_tx = transaction.to_xdr()
        with pytest.raises(
                InvalidSep10ChallengeError,
                match=
                "Transaction source account is not equal to server's account.",
        ):
            verify_challenge_transaction(challenge_tx,
                                         Keypair.random().public_key,
                                         network_passphrase)
    def test_verify_challenge_tx_donot_contain_managedata_operation(self):
        server_kp = Keypair.random()
        client_kp = Keypair.random()
        network_passphrase = Network.PUBLIC_NETWORK_PASSPHRASE
        now = int(time.time())
        server_account = Account(server_kp.public_key, -1)
        challenge_te = (TransactionBuilder(
            server_account, network_passphrase,
            100).append_set_options_op().add_time_bounds(now,
                                                         now + 900).build())

        challenge_te.sign(server_kp)
        challenge_te.sign(client_kp)
        challenge_tx_signed = challenge_te.to_xdr()

        with pytest.raises(InvalidSep10ChallengeError,
                           match="Operation type should be ManageData."):
            verify_challenge_transaction(challenge_tx_signed,
                                         server_kp.public_key,
                                         network_passphrase)
    def test_verify_challenge_transaction(self):
        server_kp = Keypair.random()
        client_kp = Keypair.random()
        timeout = 600
        network_passphrase = Network.PUBLIC_NETWORK_PASSPHRASE
        anchor_name = "SDF"

        challenge = build_challenge_transaction(
            server_secret=server_kp.secret,
            client_account_id=client_kp.public_key,
            anchor_name=anchor_name,
            network_passphrase=network_passphrase,
            timeout=timeout,
        )

        transaction = TransactionEnvelope.from_xdr(challenge,
                                                   network_passphrase)
        transaction.sign(client_kp)
        challenge_tx = transaction.to_xdr()
        verify_challenge_transaction(challenge_tx, server_kp.public_key,
                                     network_passphrase)
    def test_verify_challenge_tx_transaction_is_not_signed_by_the_client(self):
        server_kp = Keypair.random()
        client_account_id = "GBDIT5GUJ7R5BXO3GJHFXJ6AZ5UQK6MNOIDMPQUSMXLIHTUNR2Q5CFNF"
        timeout = 600
        network_passphrase = Network.TESTNET_NETWORK_PASSPHRASE
        anchor_name = "SDF"

        challenge = build_challenge_transaction(
            server_secret=server_kp.secret,
            client_account_id=client_account_id,
            anchor_name=anchor_name,
            network_passphrase=network_passphrase,
            timeout=timeout,
        )

        with pytest.raises(
                InvalidSep10ChallengeError,
                match="Transaction not signed by client: {}".format(
                    client_account_id),
        ):
            verify_challenge_transaction(challenge, server_kp.public_key,
                                         network_passphrase)
    def test_verify_challenge_tx_dont_contains_timebound(self):
        server_kp = Keypair.random()
        client_kp = Keypair.random()
        network_passphrase = Network.PUBLIC_NETWORK_PASSPHRASE
        anchor_name = "SDF"
        nonce = os.urandom(48)
        nonce_encoded = base64.b64encode(nonce)
        server_account = Account(server_kp.public_key, -1)
        challenge_te = (TransactionBuilder(
            server_account, network_passphrase, 100).append_manage_data_op(
                data_name="{} auth".format(anchor_name),
                data_value=nonce_encoded,
                source=client_kp.public_key,
            ).build())

        challenge_te.sign(server_kp)
        challenge_te.sign(client_kp)
        challenge_tx_signed = challenge_te.to_xdr()

        with pytest.raises(InvalidSep10ChallengeError,
                           match="Transaction requires timebounds."):
            verify_challenge_transaction(challenge_tx_signed,
                                         server_kp.public_key,
                                         network_passphrase)