コード例 #1
0
 def update_finger(self, successor, index):
     if self._finger[index] is not None:
         if inrange(successor.node_id(),
                    self.node_id() - 1, self._finger[index].node.node_id()):
             self._finger[index].node = successor
             # TODO: replace `update_finger` with a RPC call
             self._predecessor.update_finger(successor, index)
コード例 #2
0
    def _closest_preceding_node(self, id):
        # from m down to 1
        for x in reversed(range(len(self._finger))):
            entry = self._finger[x]
            # TODO: replace id method with RPC call, maybe a new method to replace _closest_preceding_node
            if entry != None and entry.node != None and inrange(
                    entry.node.node_id(), self.node_id(), id):
                return entry.node

        return self
コード例 #3
0
 def find_predecessor(self, id):
     lg = "find_predecessor of: {}".format(id)
     self.log(lg)
     node = self
     # when the ring only has one node, node.id is the same as node.successor.id,
     # if we are alone in the ring, we are the pred(id)
     if node.node_id() == node.successor().node_id():
         return node
     while not inrange(id, node.node_id(), node.successor().node_id() + 1):
         node = node._closest_preceding_node(id)
     return node
コード例 #4
0
    def find_successor(self, id):
        print('---------find_successor--------------')
        self.log("find_successor of {}".format(id))
        # if self._predecessor exists, and _predecessor.id < id < self.id, the successor is current node
        pre_id = self._predecessor.node_id()
        self_id = self.node_id()
        if self._predecessor and inrange(id, pre_id, self_id):
            return self

        # TODO: replace `find_predecessor` and `successor` with RPC call
        return self.find_predecessor(id).successor()
コード例 #5
0
    def init_finger(self, remote_address=None):
        if remote_address:
            # get the arbitrary node in which the target node want to join
            # TODO: _remote.getRemoteNode _remote with RPC client
            # remote_node = self._remote.getRemoteNode(remote_address)
            remote_node = self.get_remote_node(remote_address)

            # first find its successor, i.e. the first entry in its finger table
            successor = self.successor()
            if successor is None:
                # TODO: replace with RPC call find_succ
                successor = remote_node.find_successor(self.node_id())
                self._successor = successor

            # initialize the rest of its finger table
            for x in range(1, M_BIT):
                start_id = (self.node_id() + 2**x) % NUM_SLOTS
                self._finger[x] = FingerEntry(start_id, None)

            # find the corresponding nodes that are supposed to be in the finger table
            for x in range(0, M_BIT - 1):
                start_id = self._finger[x + 1].start

                if inrange(start_id, self.node_id(),
                           self._finger[x].node.node_id()):
                    # if inrange, no RPC call needed, assign locally
                    self._finger[x + 1].node = self._finger[x].node
                else:
                    """
                    need to call find successor leveraging finger table
                    for `self.find_successor`, if its the first node
                    """
                    successor = self.find_successor(start_id)
                    self._finger[x + 1] = FingerEntry(start_id, successor)

        else:
            # n is the only node in the network
            for x in range(0, M_BIT):
                start_id = math.floor((self.node_id() + 2**x) % NUM_SLOTS)
                self._finger[x] = FingerEntry(start_id, self)

        self.print_finger('init_finger')
コード例 #6
0
    def stabilize(self):
        if self._leave:
            return
        # prevent successor failure
        successor = self.successor()

        # pre = successor._predecessor
        pre = successor.predecessor()
        print('-----------stabilize--------------')
        pre_id = pre.node_id()
        self_id = self.node_id()
        succ_id = successor.node_id()

        if pre is not None and inrange(pre_id, self_id, succ_id):
            self.log('stabilize calls update_successor')
            self.update_successor(pre)

        print('stabilize successor: ', successor.notify)
        successor.notify(self)
        self.print_finger('stabilize')

        threading.Timer(2, self.stabilize).start()
コード例 #7
0
 def exposed_notify(self, pre):
     # check if pre is the new predecessor
     if (self._predecessor is None
             or inrange(pre.node_id(), self._predecessor.node_id(),
                        self.node_id())):
         self._predecessor = pre