Example #1
0
    def submit_send_tx(self, tx : SimpleTransaction) -> bool:
        # TODO: Review this
        if tx and tx.validate_tx():
            block_chain_buffer = self.chain.block_chain_buffer
            block_number = block_chain_buffer.height() + 1
            tx_state = block_chain_buffer.get_stxn_state(block_number, tx.txfrom)

            if tx.state_validate_tx(tx_state=tx_state, transaction_pool=self.chain.transaction_pool):
                self.chain.add_tx_to_pool(tx)
                self.chain.wallet.save_wallet()
                self.p2pfactory.send_tx_to_peers(tx)
                return True

        return False
Example #2
0
 def create_send_tx(self, addr_from, addr_to, amount, fee, xmss_pk, xmss_ots_key):
     return SimpleTransaction.create(addr_from=addr_from,
                                     addr_to=addr_to,
                                     amount=amount,
                                     fee=fee,
                                     xmss_pk=xmss_pk,
                                     xmss_ots_key=xmss_ots_key)
Example #3
0
    def recv_tx(self, json_tx_obj):
        try:
            tx = SimpleTransaction().json_to_transaction(json_tx_obj)
        except Exception as e:
            logger.info(
                'tx rejected - unable to decode serialised data - closing connection'
            )
            logger.exception(e)
            self.transport.loseConnection()
            return

        if not self.factory.master_mr.isRequested(tx.get_message_hash(), self):
            return

        if tx.txhash in self.factory.chain.prev_txpool or tx.txhash in self.factory.chain.pending_tx_pool_hash:
            return

        del self.factory.chain.prev_txpool[0]
        self.factory.chain.prev_txpool.append(tx.txhash)

        for t in self.factory.chain.transaction_pool:  # duplicate tx already received, would mess up nonce..
            if tx.txhash == t.txhash:
                return

        self.factory.chain.update_pending_tx_pool(tx, self)

        self.factory.master_mr.register(tx.get_message_hash(), json_tx_obj,
                                        'TX')
        self.factory.broadcast(tx.get_message_hash(), 'TX')

        if not self.factory.txn_processor_running:
            txn_processor = TxnProcessor(
                block_chain_buffer=self.factory.chain.block_chain_buffer,
                pending_tx_pool=self.factory.chain.pending_tx_pool,
                transaction_pool=self.factory.chain.transaction_pool,
                txhash_timestamp=self.factory.chain.txhash_timestamp)

            task_defer = TxnProcessor.create_cooperate(
                txn_processor).whenDone()
            task_defer.addCallback(self.factory.reset_processor_flag) \
                .addErrback(self.factory.reset_processor_flag_with_err)
            self.factory.txn_processor_running = True
        return
Example #4
0
    def create_my_tx(self, txfrom, txto, amount, fee=0):
        if isinstance(txto, int):
            txto = self.wallet.address_bundle[txto].address

        xmss = self.wallet.address_bundle[txfrom].xmss
        tx_state = self.block_chain_buffer.get_stxn_state(
            self.block_chain_buffer.height() + 1, xmss.get_address())
        tx = SimpleTransaction().create(tx_state=tx_state,
                                        txto=txto,
                                        amount=amount,
                                        xmss=xmss,
                                        fee=fee)

        if tx and tx.state_validate_tx(tx_state=tx_state,
                                       transaction_pool=self.transaction_pool):
            self.add_tx_to_pool(tx)
            self.wallet.save_wallet()
            # need to keep state after tx ..use self.wallet.info to store index..
            # far faster than loading the 55mb self.wallet..
            return tx

        return False
Example #5
0
    def last_tx(self, data=None):
        logger.info('<<< API last_tx call')

        if not data:
            data = 1

        addr = {'transactions': []}

        error = {
            'status': 'error',
            'error': 'invalid argument',
            'method': 'last_tx',
            'parameter': data
        }

        try:
            n = int(data)
        except:
            return json_print_telnet(error)

        if n <= 0 or n > 20:
            return json_print_telnet(error)

        try:
            last_txn = self.factory.state.db.get('last_txn')
        except Exception:
            error['error'] = 'txnhash not found'
            return json_print_telnet(error)

        n = min(len(last_txn), n)
        while n > 0:
            n -= 1
            tx_meta = last_txn[n]
            tx = SimpleTransaction().json_to_transaction(tx_meta[0])
            tmp_txn = {
                'txhash': bin2hstr(tx.txhash),
                'block': tx_meta[1],
                'timestamp': tx_meta[2],
                'amount': self._format_qrlamount(tx.amount),
                'type': tx.subtype
            }

            addr['transactions'].append(tmp_txn)
            addr['status'] = 'ok'

        return json_print_telnet(addr)
Example #6
0
    def _search_address(self, address):

        addr = {'transactions': []}

        txnhash_added = set()

        # FIXME: breaking encapsulation and accessing DB/cache directly from API
        if not self.factory.state.state_address_used(address):
            addr['status'] = 'error'
            addr['error'] = 'Address not found'
            addr['parameter'] = address
            return json_print_telnet(addr)

        # FIXME: This is a duplicate of balance
        # FIXME: breaking encapsulation and accessing DB/cache directly from API
        nonce, balance, pubhash_list = self.factory.state.state_get_address(
            address)
        addr['state'] = {}
        addr['state']['address'] = address
        addr['state']['balance'] = self._format_qrlamount(balance)
        addr['state']['nonce'] = nonce

        for s in self.factory.state.stake_list_get():
            if address == s[0]:
                addr['stake'] = {}
                addr['stake']['selector'] = s[2]
                # pubhashes used could be put here..

        tmp_transactions = []
        for tx in self.factory.chain.transaction_pool:
            if tx.subtype not in (TX_SUBTYPE_TX, TX_SUBTYPE_COINBASE):
                continue
            if tx.txto == address or tx.txfrom == address:
                logger.info('%s found in transaction pool', address)

                tmp_txn = {
                    'subtype': tx.subtype,
                    'txhash': bin2hstr(tx.txhash),
                    'block': 'unconfirmed',
                    'amount': self._format_qrlamount(tx.amount),
                    'nonce': tx.nonce,
                    'ots_key': tx.ots_key,
                    'txto': tx.txto,
                    'txfrom': tx.txfrom,
                    'timestamp': 'unconfirmed'
                }

                if tx.subtype == TX_SUBTYPE_TX:
                    tmp_txn['fee'] = self._format_qrlamount(tx.fee)

                tmp_txn.subtype = Transaction.tx_id_to_name(tx.subtype)

                tmp_transactions.append(tmp_txn)
                txnhash_added.add(tx.txhash)

        addr['transactions'] = tmp_transactions

        my_txn = []
        try:
            my_txn = self.factory.state.db.get('txn_' + address)
        except:
            pass

        for txn_hash in my_txn:
            txn_metadata = self.factory.state.db.get(txn_hash)
            dict_txn_metadata = json.loads(txn_metadata[0])
            if dict_txn_metadata['subtype'] == TX_SUBTYPE_TX:
                tx = SimpleTransaction().json_to_transaction(txn_metadata[0])
            elif dict_txn_metadata['subtype'] == TX_SUBTYPE_COINBASE:
                tx = CoinBase().json_to_transaction(txn_metadata[0])

            if (tx.txto == address or tx.txfrom
                    == address) and tx.txhash not in txnhash_added:
                logger.info('%s found in block %s', address,
                            str(txn_metadata[1]))

                tmp_txn = {
                    'subtype': tx.subtype,
                    'txhash': bin2hstr(tx.txhash),
                    'block': txn_metadata[1],
                    'timestamp': txn_metadata[2],
                    'amount': self._format_qrlamount(tx.amount),
                    'nonce': tx.nonce,
                    'ots_key': tx.ots_key,
                    'txto': tx.txto,
                    'txfrom': tx.txfrom
                }

                if tx.subtype == TX_SUBTYPE_TX:
                    tmp_txn['fee'] = self._format_qrlamount(tx.fee)

                tmp_txn['subtype'] = Transaction.tx_id_to_name(
                    tmp_txn['subtype'])

                addr['transactions'].append(tmp_txn)
                txnhash_added.add(tx.txhash)

        if len(addr['transactions']) > 0:
            addr['state']['transactions'] = len(addr['transactions'])

        if addr == {'transactions': {}}:
            addr = {
                'status': 'error',
                'error': 'address not found',
                'method': 'address',
                'parameter': address
            }
        else:
            addr['status'] = 'ok'

        return json_print_telnet(addr)