async def check_transaction_receipts(self):
        """
        Look for failed transactions, and emit transaction fail event if any are found.
        """
        ev_loop: asyncio.BaseEventLoop = asyncio.get_event_loop()
        tasks = [
            ev_loop.run_in_executor(hummingbot.get_executor(),
                                    self._w3.eth.getTransactionReceipt,
                                    tx_hash)
            for tx_hash in self._pending_tx_dict.keys()
        ]
        transaction_receipts: List[AttributeDict] = [
            tr for tr in await asyncio.gather(*tasks)
            if (tr is not None and tr.get("blockHash") is not None)
        ]
        block_hash_set: Set[HexBytes] = set(tr.blockHash
                                            for tr in transaction_receipts)
        fetch_block_tasks = [
            ev_loop.run_in_executor(hummingbot.get_executor(),
                                    self._w3.eth.getBlock, block_hash)
            for block_hash in block_hash_set
        ]
        blocks: Dict[HexBytes, AttributeDict] = dict(
            (block.hash, block)
            for block in await asyncio.gather(*fetch_block_tasks)
            if block is not None)

        for receipt in transaction_receipts:
            # Emit gas used event.
            tx_hash: str = receipt.transactionHash.hex()
            gas_price_wei: int = self._pending_tx_dict[tx_hash]
            gas_used: int = receipt.gasUsed
            gas_eth_amount_raw: int = gas_price_wei * gas_used

            if receipt.blockHash in blocks:
                block: AttributeDict = blocks[receipt.blockHash]

                if receipt.status == 0:
                    self.logger().warning(
                        f"The transaction {tx_hash} has failed.")
                    self.trigger_event(WalletEvent.TransactionFailure, tx_hash)

                self.trigger_event(
                    WalletEvent.GasUsed,
                    EthereumGasUsedEvent(float(block.timestamp), tx_hash,
                                         float(gas_price_wei * 1e-9),
                                         gas_price_wei, gas_used,
                                         float(gas_eth_amount_raw * 1e-18),
                                         gas_eth_amount_raw))

                # Stop tracking the transaction.
                self._stop_tx_tracking(tx_hash)
Example #2
0
    async def check_transaction_receipts(self):
        """
        Look for failed transactions, and emit transaction fail event if any are found.
        """
        async_scheduler: AsyncCallScheduler = AsyncCallScheduler.shared_instance(
        )
        tasks = [
            self._check_transaction_receipt(
                tx_hash, self._pending_tx_dict[tx_hash]['timestamp'])
            for tx_hash in self._pending_tx_dict.keys()
        ]
        transaction_receipts: List[AttributeDict] = [
            tr for tr in await safe_gather(*tasks)
            if (tr is not None and tr.get("blockHash") is not None)
        ]
        block_hash_set: Set[HexBytes] = set(tr.blockHash
                                            for tr in transaction_receipts)
        fetch_block_tasks = [
            async_scheduler.call_async(self._w3.eth.getBlock, block_hash)
            for block_hash in block_hash_set
        ]
        blocks: Dict[HexBytes, AttributeDict] = dict(
            (block.hash, block)
            for block in await safe_gather(*fetch_block_tasks)
            if block is not None)

        for receipt in transaction_receipts:
            # Emit gas used event.
            tx_hash: str = receipt.transactionHash.hex()
            gas_price_wei: int = self._pending_tx_dict[tx_hash]['gas_price']
            gas_used: int = receipt.gasUsed
            gas_eth_amount_raw: int = gas_price_wei * gas_used

            if receipt.blockHash in blocks:
                block: AttributeDict = blocks[receipt.blockHash]

                if receipt.status == 0:
                    self.logger().warning(
                        f"The transaction {tx_hash} has failed.")
                    self.trigger_event(WalletEvent.TransactionFailure, tx_hash)

                self.trigger_event(
                    WalletEvent.GasUsed,
                    EthereumGasUsedEvent(float(block.timestamp), tx_hash,
                                         float(gas_price_wei * 1e-9),
                                         gas_price_wei, gas_used,
                                         float(gas_eth_amount_raw * 1e-18),
                                         gas_eth_amount_raw))

                # Stop tracking the transaction.
                self._stop_tx_tracking(tx_hash)