def recv_peers_from(self, peer: blockchain_rpc.Peer): """ Sends get_peers request to a given peer recursively, accepting a list of peers currently known to that peer. Then send the same request to every peer in the list recursively. Discovers its's peer neighborhood. """ is_connected = peer.connect() if not is_connected: return False console.debug("> recv_peers from {:}".format(peer)) # Receve the initial list rcvd_peers = peer.get_peers() peer_queue = Queue() for rcvd_peer in rcvd_peers: if not self.is_known_peer(rcvd_peer): peer_queue.put(rcvd_peer) # Explore the initial list recursively while not peer_queue.empty(): rcvd_peer = peer_queue.get() self.maybe_add_peer(rcvd_peer) rcvd_peers = rcvd_peer.get_peers() for rcvd_peer in rcvd_peers: if not self.is_known_peer(rcvd_peer): peer_queue.put(rcvd_peer) return True
def remove(self, item): with self._lock: try: self._q.queue.remove(_PriorityQueueItem( item, self._f_priority)) console.debug("removing transaction") except ValueError: pass
def send_peers(self, peers, __): """ Server handler that accepts peers on `send_peers` request. """ console.debug("> req: send_peers") for peer in peers: peer = blockchain_rpc.Peer.from_proto(peer) console.debug("> rcvd peer: {:}".format(peer)) self.maybe_add_peer(peer) return service.messages.Empty()
def get_peers(self, _, __): """ Server handler that sends known peers in respond to `get_peers` request. """ with self._known_peers_lock: known_peers = list(self._known_peers) console.debug("> req: get_peers") for peer in known_peers: is_connected = peer.connect() if is_connected: console.debug("> sent peer: {:}".format(peer)) yield peer.to_proto()
def send_blocks(self, blocks): is_connected = self.connect() if not is_connected: return False console.debug("> send_blocks to {:}".format(self)) blocks = [block.to_proto() for block in blocks] try: self._stub.send_blocks(iter(blocks), timeout=GRPC_CALL_TIMEOUT) except: return False return True
def get_blocks(self): is_connected = self.connect() if not is_connected: return [] console.debug("> get_blocks from {:}".format(self)) try: blocks = list( self._stub.get_blocks(service.messages.Empty(), timeout=GRPC_CALL_TIMEOUT)) except: return [] return [blockchain.Block.from_proto(blocks) for blocks in blocks]
def send_transactions(self, transactions): is_connected = self.connect() if not is_connected: return False console.debug("> send_transactions to {:}".format(self)) transactions = [transaction.to_proto() for transaction in transactions] try: self._stub.send_transactions(iter(transactions), timeout=GRPC_CALL_TIMEOUT) except: return False return True
def get_transactions(self): is_connected = self.connect() if not is_connected: return [] console.debug("< get_transactions from {:}".format(self)) try: transactions = list( self._stub.get_transactions(service.messages.Empty(), timeout=GRPC_CALL_TIMEOUT)) except: return [] return [blockchain.Transaction.from_proto(tx) for tx in transactions]
def generate_transactions(self): """ Generates random transactions """ transaction_generator = blockchain.TransactionGeneratorFake( blocks=self._blockchain, peers=self._known_peers, ecdsa=self._ecdsa) while True: if len(self._transaction_queue.items) < 10: console.debug("generating transaction") transaction = transaction_generator.generate() self.maybe_add_transaction(transaction) else: time.sleep(3)
def send_peers(self, peers: Iterable['Peer']): """ Sends send_peers request """ is_connected = self.connect() if not is_connected: return False console.debug("> send_peers to {:}".format(self)) try: self._stub.send_peers(iter([peer.to_proto() for peer in peers]), timeout=GRPC_CALL_TIMEOUT) except: return False return True
def share_peers(self): """ Run peer sharing and then schedule it to run periodically. Peer sharing consist of sending all known peers to all known peers. """ if self._config.peer_sharing_interval >= 0: while True: console.debug("> sharing peers") with self._known_peers_lock: known_peers = set(self._known_peers) for peer in known_peers: is_connected = peer.connect() if is_connected: self.send_peers_to(peer) time.sleep(self._config.peer_sharing_interval)
def discover_peers(self): """ Run peer discovery and then schedule it to run periodically. Peer discovery consists of requesting known peers from all known peers. The initial peer discovery relies on a hardcoded list of initial peers, including, possibly, DNS-seeder nodes. """ if self._config.peer_discovery_interval >= 0: while True: console.debug("> discovering peers") with self._known_peers_lock: known_peers = set(self._known_peers) for peer in known_peers: self.recv_peers_from(peer) time.sleep(self._config.peer_discovery_interval)
def get_peers(self): """ Sends get_peers request """ is_connected = self.connect() if not is_connected: return [] console.debug("< get_peers from {:}".format(self)) try: peers = list( self._stub.get_peers(service.messages.Empty(), timeout=GRPC_CALL_TIMEOUT)) except: return [] return [Peer.from_proto(peer) for peer in peers]