Mesh Module

class py2p.mesh.mesh_connection(sock, server, outgoing=False)[source]

The class for mesh connection abstraction. This inherits from py2p.base.base_connection

send(msg_type, *args, **kargs)[source]

Sends a message through its connection.

Parameters:
  • msg_type – Message type, corresponds to the header in a py2p.base.pathfinding_message object
  • *args – A list of bytes-like objects, which correspond to the packets to send to you
  • **kargs – There are two available keywords:
  • id – The ID this message should appear to be sent from (default: your ID)
  • time – The time this message should appear to be sent from (default: now in UTC)
Returns:

the pathfinding_message object you just sent, or None if the sending was unsuccessful

found_terminator()[source]

This method is called when the expected amount of data is received

Returns:None
handle_waterfall(msg, packets)[source]

This method determines whether this message has been previously received or not.

If it has been previously received, this method returns True.

If it is older than a preset limit, this method returns True.

Otherwise this method returns None, and forwards the message appropriately.

Parameters:
  • msg – The message in question
  • packets – The message’s packets
Returns:

Either True or None

__init__(sock, server, outgoing=False)

Sets up a connection to another peer-to-peer socket

Parameters:
  • sock – The connected socket object
  • server – A reference to your peer-to-peer socket
  • outgoing – Whether this connection is outgoing (default: False)
collect_incoming_data(data)

Collects incoming data

Parameters:data – The most recently received byte
Returns:True if the data collection was successful, False if the connection was closed
fileno()

Mirror for the fileno() method of the connection’s underlying socket

find_terminator()

Returns whether the definied return sequences is found

handle_renegotiate(packets)

The handler for connection renegotiations

This is to deal with connection maintenence. For instance, it could be that a compression method fails to decode on the other end, and a node will need to renegotiate which methods it is using. Hence the name of the flag associated with it, “renegotiate”.

Parameters:packets – A list containing the packets received in this message
Returns:True if an action was taken, None if not
protocol

Returns server.protocol

class py2p.mesh.mesh_daemon(addr, port, server)[source]

The class for mesh daemon. This inherits from py2p.base.base_daemon

mainloop()[source]

Daemon thread which handles all incoming data and connections

handle_accept()[source]

Handle an incoming connection

process_data(handler)[source]

Collects incoming data from nodes

__init__(addr, port, server)

Sets up a daemon process for your peer-to-peer socket

Parameters:
  • addr – The address you wish to bind to
  • port – The port you wish to bind to
  • server – A reference to the peer-to-peer socket
Raises:
  • socket.error – The address you wanted is already in use
  • ValueError – If your peer-to-peer socket is set up with an unknown encryption method
kill_old_nodes(handler)

Cleans out connections which never finish a message

protocol

Returns server.protocol

class py2p.mesh.mesh_socket(addr, port, prot=<protocol object>, out_addr=None, debug_level=0)[source]

The class for mesh socket abstraction. This inherits from py2p.base.base_socket

__init__(addr, port, prot=<protocol object>, out_addr=None, debug_level=0)[source]

Initializes a mesh socket

Parameters:
  • addr – The address you wish to bind to (ie: “192.168.1.1”)
  • port – The port you wish to bind to (ie: 44565)
  • prot – The protocol you wish to operate over, defined by a py2p.base.protocol object
  • out_addr – Your outward facing address. Only needed if you’re connecting over the internet. If you use ‘0.0.0.0’ for the addr argument, this will automatically be set to your LAN address.
  • debug_level – The verbosity you want this socket to use when printing event data
Raises:

socket.error – The address you wanted could not be bound, or is otherwise used

outgoing

IDs of outgoing connections

incoming

IDs of incoming connections

handle_msg(msg, conn)[source]

Decides how to handle various message types, allowing some to be handled automatically

_send_handshake(handler)[source]

Shortcut method for sending a handshake to a given handler

Parameters:handler – A mesh_connection
_send_handshake_response(handler)[source]

Shortcut method to send a handshake response. This method is extracted from __handle_handshake() in order to allow cleaner inheritence from py2p.sync.sync_socket

send(*args, **kargs)[source]

This sends a message to all of your peers. If you use default values it will send it to everyone on the network

Parameters:
  • *args – A list of strings or bytes-like objects you want your peers to receive
  • **kargs – There are two keywords available:
  • flag – A string or bytes-like object which defines your flag. In other words, this defines packet 0.
  • type – A string or bytes-like object which defines your message type. Changing this from default can have adverse effects.

Warning

If you change the type attribute from default values, bad things could happen. It MUST be a value from py2p.base.flags , and more specifically, it MUST be either broadcast or whisper. The only other valid flags are waterfall and renegotiate, but these are RESERVED and must NOT be used.

waterfall(msg)[source]

This function handles message relays. Its return value is based on whether it took an action or not.

Parameters:msg – The message in question
Returns:True if the message was then forwarded. False if not.
connect(addr, port, id=None)[source]

This function connects you to a specific node in the overall network. Connecting to one node should connect you to the rest of the network, however if you connect to the wrong subnet, the handshake failure involved is silent. You can check this by looking at the truthiness of this objects routing table. Example:

>>> conn = mesh.mesh_socket('localhost', 4444)
>>> conn.connect('localhost', 5555)
>>> # do some other setup for your program
>>> if (!conn.routing_table):
...     conn.connect('localhost', 6666)  # any fallback address
Parameters:
  • addr – A string address
  • port – A positive, integral port
  • id – A string-like object which represents the expected ID of this node
disconnect(handler)[source]

Closes a given connection, and removes it from your routing tables

Parameters:handler – the connection you would like to close
request_peers()[source]

Requests your peers’ routing tables

recv(quantity=1)[source]

This function has two behaviors depending on whether quantity is truthy.

If truthy is truthy, it will return a list of message objects up to length len.

If truthy is not truthy, it will return either a single message object, or None

Parameters:quantity – The maximum number of message s you would like to pull
Returns:A list of message s, an empty list, a single message , or None
_mesh_socket__clean_waterfalls()

This function cleans the list of recently relayed messages based on the following heurisitics:

  • Delete all duplicates
  • Delete all older than 60 seconds
_mesh_socket__get_peer_list()

This function is used to generate a list-formatted group of your peers. It goes in format [ ((addr, port), ID), ...]

_mesh_socket__handle_handshake(msg, handler)

This callback is used to deal with handshake signals. Its three primary jobs are:

  • reject connections seeking a different network
  • set connection state
  • deal with connection conflicts
Parameters:
Returns:

Either True or None

_mesh_socket__handle_peers(msg, handler)

This callback is used to deal with peer signals. Its primary jobs is to connect to the given peers, if this does not exceed py2p.mesh.max_outgoing

Parameters:
Returns:

Either True or None

_mesh_socket__handle_request(msg, handler)

This callback is used to deal with request signals. Its three primary jobs are:

  • respond with a peers signal if packets[1] is '*'
  • if you know the ID requested, respond to it
  • if you don’t, make a request with your peers
Parameters:
Returns:

Either True or None

_mesh_socket__handle_response(msg, handler)

This callback is used to deal with response signals. Its two primary jobs are:

  • if it was your request, send the deferred message
  • if it was someone else’s request, relay the information
Parameters:
Returns:

Either True or None

_mesh_socket__resolve_connection_conflict(handler, h_id)

Sometimes in trying to recover a network a race condition is created. This function applies a heuristic to try and organize the fallout from that race condition. While it isn’t perfect, it seems to have increased connection recovery rate from ~20% to ~75%. This statistic is from memory on past tests. Much improvement can be made here, but this statistic can likely never be brought to 100%.

In the failure condition, the overall network is unaffacted for large networks. In small networks this failure condition causes a fork, usually where an individual node is kicked out.

Parameters:
  • handler – The handler with whom you have a connection conflict
  • h_id – The id of this handler
close()

If the socket is not closed, close the socket

Raises:RuntimeError – The socket was already closed
register_handler(method)

Register a handler for incoming method.

Parameters:method – A function with two given arguments. Its signature should be of the form handler(msg, handler), where msg is a py2p.base.message object, and handler is a py2p.base.base_connection object. It should return True if it performed an action, to reduce the number of handlers checked.
Raises:ValueError – If the method signature doesn’t parse correctly
status

The status of the socket.

Returns:"Nominal" if all is going well, or a list of unexpected (Excpetion, traceback) tuples if not