I'm trying to implement the Kademlia(binary tree) DHT in python. From what I understand the routing table needs to compare the individual bits from a root node's ID against a new entry. If the ID's bits do not match, you go left, if they match, you go right. This can be done recursively and your stopping condition is either that you have reached the end of the length of the ID's or that you have reached a leaf node. Then each leaf node contains its own kbucket (an array).
Currently what I have tried is the following:
#!/usr/bin/python
class Node:
def __init__(self, id, data):
self.id = id
self.data = data
self.left = None
self.right = None
def __str__(self):
return '{id:' + self.id + ',' + self.data + '}'
class Tree:
def __init__(self):
self.root = None
def find_placement(self, node, previous_node, id_index):
if (node == None):
return previous_node, id_index
elif (node.right == None and node.left == None):
return node, id_index
elif (node.id[id_index] == previous_node.id[id_index]):
return self.find_placement(node.right, node, id_index+1)
elif (node.id[id_index] != previous_node.id[id_index]):
return self.find_placement(node.left, node, id_index+1)
def add(self, id, data):
new_node = Node(id, data)
if (self.root == None):
self.root = new_node
return
previous_node = current_node = self.root
id_index = 0
current_node, id_index = self.find_placement(current_node, previous_node, id_index)
if (current_node.id[id_index] == new_node.id[id_index]):
current_node.right = new_node
elif (current_node.id[id_index] != new_node.id[id_index]):
current_node.left = new_node
new_node.parent = current_node
def printtree(self, node=None, level=0, lr = ''):
if (node == None):
node = self.root
print (lr, level, node)
if (node.left != None):
self.printtree(node.left, level+1, 'L')
if (node.right != None):
self.printtree(node.right, level+1, 'R')
if __name__ == "__main__":
t = Tree()
t.add('0000','test')
t.add('0100','test')
t.add('0010','test')
t.add('0001','test')
t.add('0101','test')
t.printtree()
Currently what I attempt to do is find a leaf node that the new node could be a child of.
Could anyone help me figure out what I'm doing wrong exactly? If I have left out anything that's needed I apologize in advance and welcome any suggestions on how I could make this post better!
I guess what my problem is this:
Currently my nodes are sorted according to the first bit that contradicts the bit at the same index of the root node. Instead what I need to do is have the nodes sorted such that the rightmost node is your own node after bootstrapping.
If this is the case, what would the root node be? Is there a way to do this where the root node is your own node while still maintaining the integrity of the network?
After adding a new node to the network, how would I restructure the tree to maintain the rule that the branches you traverse (each new fork) represents a single bit in a leaf node's id? To the point that the rightmost node is the closest node to your own and the leftmost would be the one furthest away.
The tree can be elaborated on more here: https://www.researchgate.net/publication/2492563_Kademlia_A_Peer-to-peer_Information_System_Based_on_the_XOR_Metric