def sign_transaction(self, prepared_tx):
        with FinalizableSigner(self.secret_manager) as signer:
            signed_tx = signer.sign_transaction(prepared_tx)

        # log the actual byte count
        tx_byte_count = tx_utils.get_byte_count(signed_tx)
        logging.info('The actual transaction size is %d bytes', tx_byte_count)

        signed_hextx = signed_tx.as_hex()
        logging.info('Signed hextx=%s', signed_hextx)
        return signed_tx
    def sign_transaction(self, prepared_tx):
        with FinalizableSigner(self.secret_manager) as signer:
            signed_tx = signer.sign_transaction(prepared_tx)

        # log the actual byte count
        tx_byte_count = tx_utils.get_byte_count(signed_tx)
        logging.info('The actual transaction size is %d bytes', tx_byte_count)

        signed_hextx = signed_tx.as_hex()
        logging.info('Signed hextx=%s', signed_hextx)
        return signed_tx
示例#3
0
    def issue_on_blockchain(self):
        """
        Issue the certificates on the Bitcoin blockchain
        :param revocation_address:
        :return:
        """

        self.tree.make_tree()
        op_return_value_bytes = unhexlify(self.tree.get_merkle_root())
        op_return_value = hexlify(op_return_value_bytes)
        spendables = self.connector.get_unspent_outputs(self.issuing_address)
        if not spendables:
            error_message = 'No money to spend at address {}'.format(self.issuing_address)
            logging.error(error_message)
            raise InsufficientFundsError(error_message)

        last_input = spendables[-1]

        tx = self.transaction_handler.create_transaction(last_input, op_return_value_bytes)

        hex_tx = hexlify(tx.serialize())
        logging.info('Unsigned hextx=%s', hex_tx)

        prepared_tx = tx_utils.prepare_tx_for_signing(hex_tx, [last_input])
        with FinalizableSigner(self.secure_signer) as signer:
            signed_tx = signer.sign_transaction(prepared_tx)

        # log the actual byte count
        tx_byte_count = tx_utils.get_byte_count(signed_tx)
        logging.info('The actual transaction size is %d bytes', tx_byte_count)

        signed_hextx = signed_tx.as_hex()
        logging.info('Signed hextx=%s', signed_hextx)

        # verify transaction before broadcasting
        tx_utils.verify_transaction(signed_hextx, op_return_value)

        # send tx and persist txid
        tx_id = self.connector.broadcast_tx(signed_tx)
        if tx_id:
            logging.info('Broadcast transaction with txid %s', tx_id)
        else:
            logging.warning(
                'could not broadcast transaction but you can manually do it! signed hextx=%s', signed_hextx)

        return tx_id
示例#4
0
    def issue_on_blockchain(self, revocation_address):
        """
        Issue the certificates on the Bitcoin blockchain
        :param revocation_address:
        :return:
        """
        transactions_data = self.create_transactions(revocation_address)
        for transaction_data in transactions_data:
            unsigned_tx_file_name = transaction_data.batch_metadata.unsigned_tx_file_name
            signed_tx_file_name = transaction_data.batch_metadata.unsent_tx_file_name
            sent_tx_file_name = transaction_data.batch_metadata.sent_tx_file_name

            # persist the transaction in case broadcasting fails
            hex_tx = hexlify(transaction_data.tx.serialize())
            with open(unsigned_tx_file_name, 'w') as out_file:
                out_file.write(hex_tx)

            # sign transaction and persist result
            signed_tx = self.signer.sign_tx(hex_tx, transaction_data.tx_input, self.netcode)

            # log the actual byte count
            tx_byte_count = tx_utils.get_byte_count(signed_tx)
            logging.info('The actual transaction size is %d bytes', tx_byte_count)

            signed_hextx = signed_tx.as_hex()
            with open(signed_tx_file_name, 'w') as out_file:
                out_file.write(signed_hextx)

            # verify transaction before broadcasting
            tx_utils.verify_transaction(signed_hextx, transaction_data.op_return_value)

            # send tx and persist txid
            tx_id = self.connector.broadcast_tx(signed_tx)
            if tx_id:
                logging.info('Broadcast transaction with txid %s', tx_id)
            else:
                logging.warning(
                    'could not broadcast transaction but you can manually do it! signed hextx=%s', signed_hextx)

            self.persist_tx(sent_tx_file_name, tx_id)
示例#5
0
    def issue_on_blockchain(self):
        """
        Issue the certificates on the Bitcoin blockchain
        :param revocation_address:
        :return:
        """

        self.tree.make_tree()
        op_return_value_bytes = unhexlify(self.tree.get_merkle_root())
        op_return_value = hexlify(op_return_value_bytes)

        for attempt_number in range(0, self.max_retry):
            try:
                if self.prepared_inputs:
                    inputs = self.prepared_inputs
                else:
                    spendables = self.connector.get_unspent_outputs(
                        self.secure_signer.issuing_address)
                    if not spendables:
                        error_message = 'No money to spend at address {}'.format(
                            self.secure_signer.issuing_address)
                        logging.error(error_message)
                        raise InsufficientFundsError(error_message)

                    cost = self.transaction_handler.estimate_cost_for_certificate_batch(
                    )
                    current_total = 0
                    inputs = []
                    random.shuffle(spendables)
                    for s in spendables:
                        inputs.append(s)
                        current_total += s.coin_value
                        if current_total > cost:
                            break

                tx = self.transaction_handler.create_transaction(
                    inputs, op_return_value_bytes)
                hex_tx = hexlify(tx.serialize())
                logging.info('Unsigned hextx=%s', hex_tx)

                prepared_tx = tx_utils.prepare_tx_for_signing(hex_tx, inputs)
                with FinalizableSigner(self.secure_signer) as signer:
                    signed_tx = signer.sign_transaction(prepared_tx)

                # log the actual byte count
                tx_byte_count = tx_utils.get_byte_count(signed_tx)
                logging.info('The actual transaction size is %d bytes',
                             tx_byte_count)

                signed_hextx = signed_tx.as_hex()
                logging.info('Signed hextx=%s', signed_hextx)

                # verify transaction before broadcasting
                tx_utils.verify_transaction(signed_hextx, op_return_value)

                # send tx and persist txid
                tx_id = self.connector.broadcast_tx(signed_tx)
                logging.info('Broadcast transaction with txid %s', tx_id)
                return tx_id
            except BroadcastError:
                logging.warning(
                    'Failed broadcast reattempts. Trying to recreate transaction. This is attempt number %d',
                    attempt_number)
        logging.error(
            'All attempts to broadcast failed. Try rerunning issuer.')
        raise BroadcastError(
            'All attempts to broadcast failed. Try rerunning issuer.')