def handle_find_node(self, node_id):
        # if the finding node is this node
        finded_node = None
        if self.id == node_id:
            return True
        else:
            flag = False
            visited = {self.id}
            k_nodes = deque(self.find_nearest_k(node_id, self.k))
            while k_nodes:
                node = k_nodes.popleft()

                if not node.id in visited:
                    self.update_k_bucket(node)
                    if node.id == node_id:
                        flag = True
                        break
                    with grpc.insecure_channel(node.address + ":" +
                                               str(node.port)) as channel:
                        stub = csci4220_hw3_pb2_grpc.KadImplStub(channel)
                        cur_node = csci4220_hw3_pb2.Node(id=self.id,
                                                         port=int(self.port),
                                                         address=self.address)
                        IDKey = csci4220_hw3_pb2.IDKey(node=cur_node,
                                                       idkey=node_id)
                        res = stub.FindNode(IDKey)
                        visited.add(node.id)
                        for n in res.nodes:
                            if not n.id in visited:
                                k_nodes.append(n)
            while k_nodes:
                node = k_nodes.popleft()
                self.update_k_bucket(node)

            return flag
예제 #2
0
def find_value(args):
    print("Before FIND_VALUE command, k-buckets are:\n{}".format(
        print_buckets()))

    key = int(args.split()[1])  # Getting value from the input
    if hash_table.contains_key(
            key):  # the hash table is where we keep the key value pairs
        print("Found data \"{}\" for key {}".format(hash_table.get(key), key))
        print("After FIND_VALUE command, k-buckets are:\n" + print_buckets())
        return
    else:
        unvisited = find_k_closest(
            key)  #  if we dont have the value in out hash ...
        visited = list()
        visited.append(
            csci4220_hw3_pb2.
            Node(  # we need to loop over the k closest nodes, similar to findnode
                id=local_id,
                port=int(my_port),
                address=my_address))

        value_found = False
        value = None
        while len(
                unvisited
        ) > 0 and not value_found:  # Now, we loop over all of the unvisited nodes
            for node in unvisited:
                channel = grpc.insecure_channel("{}:{}".format(
                    node.address, node.port))
                kad = csci4220_hw3_pb2_grpc.KadImplStub(channel)
                response = kad.FindValue(  # Create a connection to that node
                    csci4220_hw3_pb2.IDKey(node=csci4220_hw3_pb2.Node(
                        id=local_id, port=int(my_port), address=my_address),
                                           idkey=key))
                save_node(
                    node)  # Save it, as it needs to be updated based on LRU
                visited.append(
                    node)  # And we add it to the visited nodes array

                if response.mode_kv:
                    value = response.kv.value
                    value_found = True
                    break

                for resp_node in response.nodes:  # If we havent found the value in our direct k_buckets....
                    if not node_is_stored(
                            resp_node
                    ) and resp_node.id != local_id:  # We look in each node's k_buckets
                        save_node(resp_node)
            # Look for any unvisited nodes and add them for next iteration
            unvisited = []
            for node in find_k_closest(key):
                if node not in visited:
                    unvisited.append(node)

        if value_found:  # Handling the output statements for the found value, if it is found/not
            print("Found value \"{}\" for key {}".format(value, key))
        else:
            print("Could not find key {}".format(key))
        print("After FIND_VALUE command, k-buckets are:\n" + print_buckets())
예제 #3
0
	def Store(self, request, context):

		global bucket
		global local_key
		global local_value

		# store nodes directly at server node
		local_key = request.key
		local_value = request.value

		print('Storing key {} value "{}"'.format(request.key,request.value))
		sys.stdout.flush()

		if request.node.id==1000:
			request.node.id = 0
		index = locateBucket(local_node,request.node.id)
		if index!=-1:
			if index not in bucket:
				tmp = []
				tmp.append(nodeObj(request.node.id,request.node.port,request.node.address))
				bucket[index] = tmp
			else:
				n = len(bucket[index])
				if n==bucket_max:
					tmp = bucket[index]
					tmp.pop()
					tmp.insert(0,nodeObj(request.node.id,request.node.port,request.node.address))
					bucket[index] = tmp


		tmp = csci4220_hw3_pb2.Node(id=local_node,port=local_port,address=local_address)
		return csci4220_hw3_pb2.IDKey(node=tmp,idkey=request.key)
    def handle_find_value(self, key):
        #reserve the visited node id
        if key in self.library:
            print("Found data \"%s\" for key %d" % (self.library[key], key))
            return

        visited = set()
        visited.add(self.id)
        k_nodes = deque(self.find_nearest_k(key, self.k))

        # change to while with pop
        while k_nodes:
            node = k_nodes.popleft()
            if not node.id in visited:
                with grpc.insecure_channel(node.address + ":" +
                                           str(node.port)) as channel:
                    stub = csci4220_hw3_pb2_grpc.KadImplStub(channel)
                    cur_node = csci4220_hw3_pb2.Node(id=self.id,
                                                     port=int(self.port),
                                                     address=self.address)
                    IDKey = csci4220_hw3_pb2.IDKey(node=cur_node, idkey=key)
                    res = stub.FindValue(IDKey)
                    visited.add(node.id)
                    # contain key value or nodes
                    if res.mode_kv:
                        print("Found value \"%s\" for key %d" %
                              (res.kv.value, key))
                        if res.responding_node != self.id:
                            self.update_k_bucket(node)
                        return
                    else:
                        for n in res.nodes:
                            if not n.id in visited:
                                k_nodes.append(n)
        print("Could not find key %d" % (key))
 def Store(self, request, context):
     print("Storing key %d value \"%s\"" % (request.key, request.value))
     self.library[request.key] = request.value
     cur_node = csci4220_hw3_pb2.Node(id=self.id,
                                      port=int(self.port),
                                      address=self.address)
     IDKey = csci4220_hw3_pb2.IDKey(node=cur_node, idkey=request.key)
     return IDKey
예제 #6
0
    def FindNode(self, request, context):
        node = request.node
        id_key = request.idkey

        print("Serving FindNode({}) request for {}".format(id_key, node.id))

        closest_nodes = find_k_closest(id_key)
        save_node(node)

        return csci4220_hw3_pb2.NodeList(responding_node=csci4220_hw3_pb2.Node(
            id=local_id, port=int(my_port), address=my_address),
                                         nodes=closest_nodes)
 def find_nearest_k(self, key, k, filter=[]):
     res = {}
     lst = []
     cur_node = csci4220_hw3_pb2.Node(id=self.id,
                                      port=int(self.port),
                                      address=self.address)
     lst.append((cur_node, self.compute_dist(self.id, key)))
     for i in range(4):
         for k_i in self.k_bucket[i]:
             v = self.k_bucket[i][k_i]
             lst.append((v, self.compute_dist(v.id, key)))
     sorted_lst = sorted(lst, key=lambda x: (x[1], x[0].id ^ key))
     nodes = [i[0] for i in sorted_lst if not i[0].id in filter]
     return nodes[:k]
 def Quit(self, request, context):
     quit_id = request.idkey
     i = self.compute_dist(self.id, quit_id) - 1
     flag = True
     if quit_id in self.k_bucket[i]:
         del self.k_bucket[i][quit_id]
         print("Evicting quitting node %d from bucket %i" % (quit_id, i))
     else:
         print("No record of quitting node %d in k-buckets." % quit_id)
     cur_node = csci4220_hw3_pb2.Node(id=self.id,
                                      port=int(self.port),
                                      address=self.address)
     IDKey = csci4220_hw3_pb2.IDKey(node=cur_node, idkey=quit_id)
     return IDKey
 def FindValue(self, request, context):
     print("Serving FindKey(%d) request for %d" %
           (request.idkey, request.node.id))
     key = request.idkey
     if self.id != request.node.id:
         self.update_k_bucket(request.node)
     if key in self.library:
         cur_node = csci4220_hw3_pb2.Node(id=self.id,
                                          port=int(self.port),
                                          address=self.address)
         key_value = csci4220_hw3_pb2.KeyValue(node=cur_node,
                                               key=key,
                                               value=self.library[key])
         kv_wrapper = csci4220_hw3_pb2.KV_Node_Wrapper(
             responding_node=cur_node, mode_kv=1, kv=key_value, nodes=[])
         return kv_wrapper
     else:
         cur_node = csci4220_hw3_pb2.Node(id=self.id,
                                          port=int(self.port),
                                          address=self.address)
         k_nodes = self.find_nearest_k(request.idkey, self.k)
         kv_wrapper = csci4220_hw3_pb2.KV_Node_Wrapper(
             responding_node=cur_node, mode_kv=0, kv=None, nodes=k_nodes)
         return kv_wrapper
    def FindNode(self, request, context):
        print("Serving FindNode(%d) request for %d" %
              (request.idkey, request.node.id))
        #update key buckets:
        if self.id != request.node.id:
            i = self.compute_dist(self.id, request.node.id) - 1
            self.k_bucket[i][request.node.id] = request.node
        k_nodes = self.find_nearest_k(request.idkey, self.k,
                                      [request.node.id, self.id])
        cur_node = csci4220_hw3_pb2.Node(id=self.id,
                                         port=int(self.port),
                                         address=self.address)

        nl = csci4220_hw3_pb2.NodeList(responding_node=cur_node, nodes=k_nodes)
        return nl
예제 #11
0
파일: hw3.py 프로젝트: gct38/NetProg
def run():
    global local_node
    global k
    if len(sys.argv) != 4:
        print("Error, correct usage is {} [my id] [my port] [k]".format(
            sys.argv[0]))
        sys.exit(-1)
    local_id = int(sys.argv[1])
    my_port = str(int(sys.argv[2]))  # add_insecure_port() will want a string
    k = int(sys.argv[3])
    my_hostname = socket.gethostname()  # Gets my host name
    my_address = socket.gethostbyname(
        my_hostname)  # Gets my IP address from my hostname

    local_node = csci4220_hw3_pb2.Node(id=local_id,
                                       port=int(my_port),
                                       address=my_address)

    server = grpc.server(futures.ThreadPoolExecutor(max_workers=10))
    csci4220_hw3_pb2_grpc.add_KadImplServicer_to_server(
        KadImplServicer(), server)
    server.add_insecure_port('[::]:' + my_port)
    server.start()

    while (1):
        inp = input().split()
        if inp[0] == "QUIT":
            Quit()
            print("Shut down node %d" % local_id)
            sys.exit(0)
        elif inp[0] == "BOOTSTRAP" and (len(inp) == 3):
            Bootstrap(inp[1], inp[2])
        elif inp[0] == "FIND_NODE" and (len(inp) == 2):
            print("Before FIND_NODE command, k-buckets are:")
            print_k_buckets()
            Find_Node(int(inp[1]))
            print("After FIND_NODE command, k-buckets are:")
            print_k_buckets()
        elif inp[0] == "FIND_VALUE" and (len(inp) == 2):
            print("Before FIND_VALUE command, k-buckets are:")
            print_k_buckets()
            Find_Value(int(inp[1]))
            print("After FIND_VALUE command, k-buckets are:")
            print_k_buckets()
        elif inp[0] == "STORE" and (len(inp) == 3):
            Store(int(inp[1]), inp[2])
        else:
            print("Invalid arguement!")
예제 #12
0
    def __init__(self, id, port, addr, k):
        self.id = id
        self.port = port
        self.addr = addr
        self.k = k
        self.node = csci4220_hw3_pb2.Node(id=self.id,
                                          port=self.port,
                                          address=self.addr)
        '''
        Least Recently Used (LRU) List

                index 0 <--        list        --> index -1
            least recently used             most recently used
        '''
        # k_buckets have a fixed size of four
        self.k_buckets = [[], [], [], []]  # Store Node(id, port, address)
        self.key_value = []  # Store tuple(key, value)
 def handle_store(self, key, value):
     near_point = self.find_nearest_k(key, 1)[0]
     if near_point.id == self.id:
         self.library[key] = value
         print("Storing key %d at node %d" % (key, self.id))
     else:
         with grpc.insecure_channel(near_point.address + ":" +
                                    str(near_point.port)) as channel:
             stub = csci4220_hw3_pb2_grpc.KadImplStub(channel)
             cur_node = csci4220_hw3_pb2.Node(id=self.id,
                                              port=int(self.port),
                                              address=self.address)
             kv = csci4220_hw3_pb2.KeyValue(node=cur_node,
                                            key=key,
                                            value=value)
             print("Storing key %d at node %d" % (key, near_point.id))
             res = stub.Store(kv)
 def broadcast(self, remote_hostname, remote_port):
     with grpc.insecure_channel(remote_hostname + ":" +
                                str(remote_port)) as channel:
         stub = csci4220_hw3_pb2_grpc.KadImplStub(channel)
         cur_node = csci4220_hw3_pb2.Node(id=self.id,
                                          port=int(self.port),
                                          address=self.address)
         IDKey = csci4220_hw3_pb2.IDKey(node=cur_node, idkey=self.id)
         # run the remote FindNode
         res = stub.FindNode(IDKey)
         #update the k_bucket
         self.update_k_bucket(res.responding_node)
         for new_node in res.nodes:
             self.update_k_bucket(new_node)
         #print k_bucket
         print("After BOOTSTRAP(%d), k_buckets now look like:" %
               res.responding_node.id)
         self.print_k_bucket()
    def handle_quit(self):
        for i in range(4):
            for k in self.k_bucket[i]:
                v = self.k_bucket[i][k]
                print("Letting %d know I'm quitting." % (v.id))
                try:
                    with grpc.insecure_channel(v.address + ":" +
                                               str(v.port)) as channel:
                        stub = csci4220_hw3_pb2_grpc.KadImplStub(channel)
                        cur_node = csci4220_hw3_pb2.Node(id=self.id,
                                                         port=int(self.port),
                                                         address=self.address)
                        IDKey = csci4220_hw3_pb2.IDKey(node=cur_node,
                                                       idkey=self.id)
                        stub.Quit(IDKey)
                except Exception as e:
                    pass

        print("Shut down node %d" % self.id)
예제 #16
0
def store(args):
    key = int(args.split()[1])
    value = args.split()[2]

    k_closest = find_k_closest(key)
    closest_node = None if len(k_closest) < 1 else k_closest[0]

    if closest_node is None or key ^ local_id < key ^ closest_node.id:
        print("Storing key {} at node {}".format(key, local_id))
        hash_table.put(key, value)
    else:
        print("Storing key {} at node {}".format(key, closest_node.id))
        channel = grpc.insecure_channel("{}:{}".format(closest_node.address,
                                                       closest_node.port))
        kad = csci4220_hw3_pb2_grpc.KadImplStub(channel)

        kad.Store(
            csci4220_hw3_pb2.KeyValue(node=csci4220_hw3_pb2.Node(
                id=local_id, port=int(my_port), address=my_address),
                                      key=key,
                                      value=value))
예제 #17
0
    def FindValue(self, request, context):
        print("Serving FindKey({}) request for {}".format(
            request.idkey, request.node.id))
        has_key = hash_table.contains_key(request.idkey)
        value = ""
        nodes = []
        if has_key:
            value = hash_table.get(request.idkey)
        else:
            nodes = find_k_closest(request.idkey)

        save_node(request.node)

        return csci4220_hw3_pb2.KV_Node_Wrapper(
            responding_node=csci4220_hw3_pb2.Node(id=local_id,
                                                  port=int(my_port),
                                                  address=my_address),
            mode_kv=has_key,
            kv=csci4220_hw3_pb2.KeyValue(node=request.node,
                                         key=request.idkey,
                                         value=value),
            nodes=nodes)
예제 #18
0
	def Quit(self, request, context):

		global bucket
		Found = False

		if request.node.id==1000:
			request.node.id = 0

		# loop over to find client node and delete it from bucket
		for k,v in list(bucket.items()):
			mark = -1
			for i in range(0,len(v)):
				if v[i].id==request.idkey:
					mark = i
					if len(v)>1:
						Found = True
						print("Evicting quitting node {} from bucket {}".format(request.idkey,k))
						sys.stdout.flush()	
			if mark!=-1 and Found==True:
				v.remove(mark)

											
		for k,v in list(bucket.items()):
			for i in range(0,len(v)):
				if v[i].id==request.idkey:
					if len(v)==1:
						Found = True
						del bucket[k]
						print("Evicting quitting node {} from bucket {}".format(request.idkey,k))
						sys.stdout.flush()	
					
		if Found==False:
			print("No record of quitting node {} in k-buckets.".format(request.node.id))
			sys.stdout.flush()

		r_node = csci4220_hw3_pb2.Node(id=local_node,port=local_port,address=local_address)
		return csci4220_hw3_pb2.IDKey(node=r_node,idkey=local_node)
예제 #19
0
def bootstrap(args):
    hostname = args.split()[1]  # Gettting the hostname from input
    port = args.split()[2]  # Getting the port from input
    address = socket.gethostbyname(hostname)  # Getting the hostname

    channel = grpc.insecure_channel("{}:{}".format(address, port))
    kad = csci4220_hw3_pb2_grpc.KadImplStub(channel)

    # Get NodeList from remote node to update k_buckets
    response = kad.FindNode(
        csci4220_hw3_pb2.IDKey(node=csci4220_hw3_pb2.Node(id=local_id,
                                                          port=int(my_port),
                                                          address=my_address),
                               idkey=local_id))

    # Save bootstrap node
    save_node(response.responding_node)

    # Save nodes learned from bootstrap node
    for node in response.nodes:
        save_node(node)

    print("After BOOTSTRAP({}), k_buckets now look like:\n{}".format(
        response.responding_node.id, print_buckets()))
예제 #20
0
def findingNode(find_node_id):

	visited = []
	Found = False

	print("Before FIND_NODE command, k-buckets are:")
	sys.stdout.flush()
	for i in range(0,N):
		tmp = str(i)+":"
		for k,v in bucket.items():
			if k==i and len(v)!=0:
				for m in v:
					tmp += " "
					tmp += str(m.id)
					tmp += ":"
					tmp += str(m.port)
		print(tmp)
		sys.stdout.flush()


	all_nodes = []
	for k,v in bucket.items():
		for j in range(len(v)):
			if v[j].id==find_node_id:
				Found = True
				index = locateBucket(find_node_id,local_node)
				tmp = bucket[index]
				x = v[j]
				tmp.remove(x)
				tmp.insert(0, x)
				print("Found destination id " + str(find_node_id))
				sys.stdout.flush()
				print("After FIND_NODE command, k-buckets are:")
				sys.stdout.flush()
				for i in range(0,N):
					tmp = str(i)+":"
					for k,v in bucket.items():
						if k==i and len(v)!=0:
							for m in v:
								tmp += " "
								tmp += str(m.id)
								tmp += ":"
								tmp += str(m.port)
					print(tmp)
					sys.stdout.flush()
				return
			else:
				all_nodes.append(v[j])

	ordered_nodes = sorted(all_nodes, key=lambda x : XOR(x.id,find_node_id))

	S = []
	S_prime = []
	if len(ordered_nodes)<bucket_max:
		S = ordered_nodes
	else:
		for i in range(0,bucket_max):
			S.append(ordered_nodes[i])


	for x in S:
		add = True
		for v_node in visited:
			if x==v_node:
				add = False
		if add==True:
			S_prime.append(x)


	for search_node in S_prime:

		if search_node.id==find_node_id:
			Found = True
			print("Found destination id " + str(find_node_id))
			break

		visited.append(search_node.id)
		remote_host = search_node.id
		remote_port = int(search_node.port)
		remote_addr = search_node.address
		with grpc.insecure_channel(remote_addr + ':' + str(remote_port)) as channel:
			stub = csci4220_hw3_pb2_grpc.KadImplStub(channel)
			node_tmp = csci4220_hw3_pb2.Node(id=find_node_id,port=0,address="")
			idKey = csci4220_hw3_pb2.IDKey(node=node_tmp,idkey=local_node)
			nodeList = stub.FindNode(idKey)

			R = []
			for node in nodeList.nodes:
				R.append(node)

		mr_used = search_node
		mr_index = locateBucket(local_node,mr_used.id)

		for x in R:
			if x.id==1000:
				x.id = 0	
			if x.id==find_node_id:
				Found = True
				print("Found destination id " + str(find_node_id))						
			index = locateBucket(local_node,x.id)
			update = True
			for k,v in bucket.items():
				if k==index:
					for i in range(0,len(v)):
						if v[i].id==mr_used.id or v[i].id==local_node:
							update==False
						for j in range(0,len(v)):
							if v[i].id==v[j].id:
								update==False

			if update==True:
				mr_used = x
				if index not in bucket:
					tmp = []
					tmp.append(x)
					bucket[index] = tmp
				else:
					tmp = bucket[index]
					tmp.append(x)
					n = len(tmp)
					if n>bucket_max:
						tmp.pop(0)
						bucket[index] = tmp				

		if mr_index in bucket.values():
			bucket[mr_index].remove(mr_used)
			bucket[mr_index].insert(0,mr_used)

		channel.close()

	print("After FIND_NODE command, k-buckets are:")
	sys.stdout.flush()
	for i in range(0,N):
		tmp = str(i)+":"
		for k,v in bucket.items():
			if k==i and len(v)!=0:
				for m in v:
					tmp += " "
					tmp += str(m.id)
					tmp += ":"
					tmp += str(m.port)
		print(tmp)
		sys.stdout.flush()

	if Found==False:
		print("Could not find destination id " + str(find_node_id))
		sys.stdout.flush()
예제 #21
0
def bootStrap(stub,remote_host,remote_port):

	global bucket_max

	# locate other side send connection
	node_tmp = csci4220_hw3_pb2.Node(id=local_node,port=local_port,address=local_address)
	idKey = csci4220_hw3_pb2.IDKey(node=node_tmp,idkey=local_node)
	nodeList = stub.FindNode(idKey)


	to_bucket = []
	to_bucket.append(nodeList.responding_node)
	for node in nodeList.nodes:
		to_bucket.append(node)


	# update bucket
	for x in to_bucket:
		if x.id==1000:
			x.id = 0
		add = True
		for item in bucket.items():
			for node in item[1]:
				if x.id==node.id:
					add = False
		if add==True:

			index = locateBucket(local_node,x.id)

			if index!=-1:
				if index not in bucket:
					tmp = []
					obj = nodeObj(x.id,x.port,x.address)
					tmp.append(obj)
					bucket[index] = tmp
				else:
					n = len(bucket[index])
					tmp = bucket[index]
					if n==bucket_max:
						l = tmp[-1]
						tmp[-1] = tmp[0]
						tmp[0] = l
						tmp.pop()
					obj = nodeObj(x.id,x.port,x.address)
					tmp.append(obj)					
					bucket[index] = tmp

	# outprint
	print("After BOOTSTRAP(" + str(remote_host) + "), k_buckets now look like:")
	sys.stdout.flush()
	for i in range(0,N):
		tmp = str(i)+":"
		for k,v in bucket.items():
			if k==i and len(v)!=0:
				for m in v:
					tmp += " "
					tmp += str(m.id)
					tmp += ":"
					tmp += str(m.port)
		print(tmp)
		sys.stdout.flush()
예제 #22
0
	def FindValue(self, request, context):

		global bucket

		# delete same nodes
		for k,v in list(bucket.items()):
			for i in range(0,len(v)):
				if v[i].id==local_node:
					if len(v)==1:
						del bucket[k]
					else:
						v.remove(i)


		print("Serving FindKey(" + str(request.idkey) + ") request for " + str(request.node.id))
		sys.stdout.flush()

		# if found the key in server node, return the key directly
		if request.idkey==local_key:
			r_node = csci4220_hw3_pb2.Node(id=local_node,port=local_port,address=local_address)
			mode = True
			key_value = csci4220_hw3_pb2.KeyValue(node=r_node,key=local_key,value=local_value)
			return csci4220_hw3_pb2.KV_Node_Wrapper(responding_node=r_node,mode_kv=mode,kv=key_value,nodes=[])


		# if not found, return a k-near list of nodes
		else:
			mode = False

			index = locateBucket(local_node,request.node.id)
			if index!=-1:
				if index not in bucket:
					tmp = []
					tmp.append(nodeObj(request.node.id,request.node.port,request.node.address))
					bucket[index] = tmp
				else:
					adding = True
					n = len(bucket[index])
					for i in range(0,n):
						if bucket[index][i].id==request.node.id:
							adding = False
							break
					if adding==True:
						if n==bucket_max:
							tmp = bucket[index]
							tmp.pop()
							tmp.insert(0,nodeObj(request.node.id,request.node.port,request.node.address))
							bucket[index] = tmp


			all_nodes = []
			for k,v in bucket.items():
				for j in range(len(v)):
					all_nodes.append(v[j])

			ordered_nodes = sorted(all_nodes, key=lambda x : XOR(x.id,request.node.id))

			node_tmp = csci4220_hw3_pb2.Node(id=local_node,port=local_port,address=local_address)
			ret = []

			for node in ordered_nodes:
				if node.id==0:
					tmp = csci4220_hw3_pb2.Node(id=1000,port=node.port,address=node.address)
				else:
					tmp = csci4220_hw3_pb2.Node(id=node.id,port=node.port,address=node.address)
				ret.append(tmp)

			r_node = csci4220_hw3_pb2.Node(id=local_node,port=local_port,address=local_address)
			key_value = csci4220_hw3_pb2.KeyValue(node=r_node,key=local_key,value=local_value)
			return csci4220_hw3_pb2.KV_Node_Wrapper(responding_node=r_node,mode_kv=mode,kv=key_value,nodes=ret)
예제 #23
0
					if XOR(v[i].id,key)<=min_distrance:
						min_distrance = XOR(v[i].id,key)
						target = v[i]

			tmp_id = target.id

			if target.id==local_id:
				local_key = key
				local_value = value
				print("Storing key " + str(key) + " at node " + str(local_id))
				sys.stdout.flush()
			else:
				if target.id==0:
					tmp_id = 1000

				node = csci4220_hw3_pb2.Node(id=tmp_id,port=target.port,address=target.address)
				ky = csci4220_hw3_pb2.KeyValue(node=node,key=key,value=value)
				with grpc.insecure_channel(target.address + ':' + str(target.port)) as channel:
					stub = csci4220_hw3_pb2_grpc.KadImplStub(channel)
					stub.Store(ky)
				print("Storing key " + str(key) + " at node " + str(target.id))
				sys.stdout.flush()
				channel.close()


		elif msg.split(" ")[0]=='QUIT':

			if already_quit==False:
				for k,v in list(bucket.items()):
					for i in range(0,len(v)):
						if v[i].id!=local_node:
예제 #24
0
def run():
	if len(sys.argv) != 4:
		print("Error, correct usage is {} [my id] [my port] [k]".format(sys.argv[0]))
		sys.exit(-1)

	local_id = int(sys.argv[1])
	my_port = str(int(sys.argv[2])) # add_insecure_port() will want a string
	k = int(sys.argv[3])
	my_hostname = socket.gethostname() # Gets my host name
	my_address = socket.gethostbyname(my_hostname) # Gets my IP address from my hostname

	''' Use the following code to convert a hostname to an IP and start a channel
	Note that every stub needs a channel attached to it
	When you are done with a channel you should call .close() on the channel.
	Submitty may kill your program if you have too many file descriptors open
	at the same time. '''
	
	#remote_addr = socket.gethostbyname(remote_addr_string)
	#remote_port = int(remote_port_string)
	#channel = grpc.insecure_channel(remote_addr + ':' + str(remote_port))

	ourNode = csci4220_hw3_pb2.Node(id = local_id, port = int(my_port), address = my_address)
	ourServicer = KadImplServicer(k, ourNode)

  # Code to start the servicer for our node
	server = grpc.server(futures.ThreadPoolExecutor(max_workers=10))
	csci4220_hw3_pb2_grpc.add_KadImplServicer_to_server(ourServicer, server)
	server.add_insecure_port(f'[::]:{my_port}')
	server.start() # Let servicer start listening w/t blocking

	while True:
		userInput = input() # Perhaps change this to select, but that's a discussion for later :P
		userInput = userInput.strip().split()
		if ((userInput[0]).lower().strip() == "bootstrap"):
			remoteHost = (userInput[1]).strip()
			remotePort = (userInput[2]).strip()
			remote_addr = socket.gethostbyname(remoteHost)
			remote_port = int(remotePort)
			with grpc.insecure_channel(remote_addr + ':' + str(remote_port)) as channel:
				stub = csci4220_hw3_pb2_grpc.KadImplStub(channel)
				result = stub.FindNode(csci4220_hw3_pb2.IDKey(node = ourNode, idkey = ourNode.id))
				remoteID = result.responding_node.id]
				ourServicer.DHT.updateNodeLoc(result.responding_node)
				for node_ in result.nodes:
					ourServicer.DHT.updateNodeLoc(node_)

				print(f'After BOOTSTRAP({remoteID}), k_buckets now look like:')
				ourServicer.DHT.print()

		elif ((userInput[0]).lower().strip() == "find_node" or (userInput[0]).lower().strip() == "find_value"):
			nodeID = int((userInput[1]).strip())
			findNode = (userInput[0]).lower().strip() == "find_node"
			print(f"Before FIND_{'NODE' if findNode else 'VALUE'} command, k-buckets are:")
			ourServicer.DHT.print()

			found = nodeID == local_id if findNode else ourServicer.values.get(nodeID) is not None
			value = (found, ourServicer.values.get(nodeID))

			if (not found):
				# Do the search
				Visited = set() # Stores id of visited nodes
				nodeOfInterest = csci4220_hw3_pb2.IDKey(node = ourNode, idkey = nodeID)
				
				# Condition for us to use FindNode or FindValue
				# S = ourServicer.DHT.kClosest(nodeOfInterest.idkey) # get k closest to idkey

				S = ourServicer.DHT.kClosest(nodeOfInterest.idkey) # get k closest nodes to idkey
				# print(f"Closest nodes to {nodeOfInterest.idkey} are {[n.id for n in S]}")
				notVisited = [n for n in S if n.id not in Visited]
				while not found and len(notVisited) > 0:
					for node in notVisited:
						with grpc.insecure_channel(node.address + ':' + str(node.port)) as channel:
							stub = csci4220_hw3_pb2_grpc.KadImplStub(channel)
							
							# Condition for us to use FindNode or FindValue
							R = stub.FindNode(nodeOfInterest) if findNode else stub.FindValue(nodeOfInterest)

							# Update our k-buckets with node
							ourServicer.DHT.updateNodeLoc(R.responding_node)
							
							if not findNode and R.mode_kv: # If we're for FindValue
								found = True
								value = (R.responding_node.id == ourNode.id, R.kv.value)
							
							# If a node in R was already in a k-bucket, its position does not change.
							# If it was not in the bucket yet, then it is added as the most recently used in that bucket.
							# This _may_ kick out the node from above.
							for n in R.nodes:
								if findNode and (n.id ^ nodeOfInterest.idkey) == 0:
									found = True
								ourServicer.DHT.updateNodeLoc(n)
							
							Visited.add(node.id)
							if found:
								break
					S = ourServicer.DHT.kClosest(nodeOfInterest.idkey) # get k closest nodes to idkey
					notVisited = [n for n in S if n.id not in Visited]
					
			# Do the printing
			if (found):
				if findNode:
					print(f'Found destination id {nodeID}', flush=True)
				else:
					if value[0]:
						print(f'Found data "{value[1]}" for key {nodeID}')
					else:
						print(f'Found value "{value[1]}" for key {nodeID}')
			else:
				if findNode:
					print(f'Could not find destination id {nodeID}', flush=True)
				else:
					print(f'Could not find key {nodeID}')
			print(f"After FIND_{'NODE' if findNode else 'VALUE'} command, k-buckets are:")
			ourServicer.DHT.print()

		elif ((userInput[0]).lower().strip() == "store"):
			key = int(userInput[1].strip())
			val = userInput[2].strip()
			# Find the node it knows that's closest to the key
			closestNodes = ourServicer.DHT.kClosest(key)

			if len(closestNodes) == 0 or (ourNode.id ^ key <= closestNodes[0].id ^ key):
				print(f'Storing key {key} at node {ourNode.id}', flush=True)
				ourServicer.values[key] = val
			else:
				print(f'Storing key {key} at node {closestNodes[0].id}', flush=True)
				with grpc.insecure_channel(closestNodes[0].address + ':' + str(closestNodes[0].port)) as channel:
					stub = csci4220_hw3_pb2_grpc.KadImplStub(channel)
					stub.Store(csci4220_hw3_pb2.KeyValue(node = ourNode,
					                                     key = key,
																							 value = val))

		elif ((userInput[0]).lower().strip() == "quit"):
			for node in ourServicer.DHT.getAllNodes():
				with grpc.insecure_channel(node.address + ':' + str(node.port)) as channel:
					stub = csci4220_hw3_pb2_grpc.KadImplStub(channel)
					print(f'Letting {node.id} know I\'m quitting.', flush=True)
					try:
						stub.Quit(csci4220_hw3_pb2.IDKey(node = ourNode, idkey = ourNode.id))
					except:
						pass # The stub already closed

			print(f'Shut down node {ourNode.id}', flush=True)
			server.stop(None)
			break
		else:
			print("Invalid Command", flush=True)
예제 #25
0
def findingValue(find_key):
	visited = []
	Found = False

	print("Before FIND_VALUE command, k-buckets are:")
	sys.stdout.flush()
	for i in range(0,N):
		tmp = str(i)+":"
		for k,v in bucket.items():
			if k==i and len(v)!=0:
				for m in v:
					tmp += " "
					tmp += str(m.id)
					tmp += ":"
					tmp += str(m.port)
		print(tmp)
		sys.stdout.flush()


	all_nodes = []
	for k,v in bucket.items():
		for j in range(len(v)):
			if v[j].id!=local_node:
				all_nodes.append(v[j])

	ordered_nodes = sorted(all_nodes, key=lambda x : XOR(x.id,local_node))

	S = []
	S_prime = []
	if len(ordered_nodes)<bucket_max:
		S = ordered_nodes
	else:
		for i in range(0,bucket_max):
			S.append(ordered_nodes[i])

	for x in S:
		add = True
		for v_node in visited:
			if x==v_node:
				add = False
		if add==True:
			S_prime.append(x)

	for search_node in S_prime:

		visited.append(search_node.id)
		remote_host = search_node.id
		remote_port = int(search_node.port)
		remote_addr = search_node.address
		with grpc.insecure_channel(remote_addr + ':' + str(remote_port)) as channel:
			stub = csci4220_hw3_pb2_grpc.KadImplStub(channel)
			node_tmp = csci4220_hw3_pb2.Node(id=local_node,port=local_port,address=local_address)
			idKey = csci4220_hw3_pb2.IDKey(node=node_tmp,idkey=find_key)
			ret = stub.FindValue(idKey)

			if ret.mode_kv==True:
				Found = True

				tmp_p = '"'+ret.kv.value+'"'
				print("Found value ""{}"" for key {}".format(tmp_p,find_key))


				mr_used = ret.responding_node
				mr_index = locateBucket(local_node,mr_used.id)

				if mr_index not in bucket:
					tmp = []
					tmp.append(mr_used)
					bucket[mr_index] = tmp
				else:
					adding = True
					for y in bucket[mr_index]:
						if y.id==mr_used.id and len(bucket[mr_index])==1:
							adding = False
						elif y.id==mr_used.id and len(bucket[mr_index])==bucket_max and bucket[mr_index][-1].id==mr_used.id:
							adding = False
					if adding==True:
						tmp = bucket[mr_index]
						tmp.pop(0)
						tmp.append(mr_used)
						bucket[mr_index] = tmp				

				break


			elif ret.mode_kv==False:

				R = []
				for node in ret.nodes:
					R.append(node)

				mr_used = search_node
				mr_index = locateBucket(local_node,mr_used.id)

				for x in R:
					if x.id==1000:
						x.id = 0	
					if x.id==find_key:
						Found = True
						remote_host = x.id
						remote_port = int(x.port)
						remote_addr = x.address
						with grpc.insecure_channel(remote_addr + ':' + str(remote_port)) as channel:
							stub = csci4220_hw3_pb2_grpc.KadImplStub(channel)
							node_tmp = csci4220_hw3_pb2.Node(id=local_node,port=local_port,address=local_address)
							idKey = csci4220_hw3_pb2.IDKey(node=node_tmp,idkey=find_key)
							result = stub.FindValue(idKey)						

						tmp_p = '"'+result.kv.value+'"'
						print("Found value ""{}"" for key {}".format(tmp_p,find_key))						
					index = locateBucket(local_node,x.id)
					update = True
					for k,v in bucket.items():
						if k==index:
							for i in range(0,len(v)):
								if v[i].id==mr_used.id or v[i].id==local_node:
									update==False

					if update==True:
						if index not in bucket:
							tmp = []
							tmp.append(x)
							bucket[index] = tmp
						else:
							adding = True
							for y in bucket[index]:
								if y.id==mr_used.id:
									adding = False
							if adding==True:
								tmp = bucket[index]
								n = len(tmp)
								if n<bucket_max:
									tmp.insert(0,x)
								else:
									tmp.insert(0,x)
									tmp.pop()
							#	print(tmp)
								bucket[index] = tmp				

				if mr_index in bucket.values():
					bucket[mr_index].remove(mr_used)
					bucket[mr_index].insert(0,mr_used)

		channel.close()

	if Found==False:
		print("Could not find key " + str(find_key))
		sys.stdout.flush()


	print("After FIND_VALUE command, k-buckets are:")
	sys.stdout.flush()
	for i in range(0,N):
		tmp = str(i)+":"
		for k,v in bucket.items():
			if k==i and len(v)!=0:
				for m in v:
					tmp += " "
					tmp += str(m.id)
					tmp += ":"
					tmp += str(m.port)
		print(tmp)
		sys.stdout.flush()
예제 #26
0
	def FindNode(self, request, context):
		
		global bucket
		
		# Findnode function for bootstrap
		if request.idkey==request.node.id:
			index = locateBucket(local_node,request.node.id)
			if index!=-1:
				if index not in bucket:
					tmp = []
					tmp.append(nodeObj(request.node.id,request.node.port,request.node.address))
					bucket[index] = tmp
				else:
					adding = True
					for k,v in bucket.items():
						for i in range(0,len(v)):
							if v[i].id==request.node.id:
								adding = False
					if adding==True:
						n = len(bucket[index])
						tmp = bucket[index]
						if n==bucket_max:
							tmp.pop()
						tmp.insert(0,nodeObj(request.node.id,request.node.port,request.node.address))
						bucket[index] = tmp
					
			# add all nodes to a list and sort
			all_nodes = []
			for k,v in bucket.items():
				for j in range(len(v)):
					if v[j].id!=request.node.id:
						all_nodes.append(v[j])

			ordered_nodes = sorted(all_nodes, key=lambda x : XOR(x.id,request.node.id))
			node_tmp = csci4220_hw3_pb2.Node(id=local_node,port=local_port,address=local_address)
			ret = []			
			
			# update bucket
			i = 0
			for node in ordered_nodes:
				i += 1
				if i>bucket_max:
					break
				else:
					if node.id==0:
						tmp = csci4220_hw3_pb2.Node(id=1000,port=node.port,address=node.address)
						ret.append(tmp)
					else:
						tmp = csci4220_hw3_pb2.Node(id=node.id,port=node.port,address=node.address)
						ret.append(tmp)

			print("Serving FindNode(" + str(request.node.id) + ") request for " + str(request.idkey))
			sys.stdout.flush()
			return csci4220_hw3_pb2.NodeList(responding_node=node_tmp,nodes=ret)


		# Findnode function for find node 
		else:
			index = locateBucket(local_node,request.node.id)
			if index!=-1:
				if index not in bucket:
					tmp = []
					tmp.append(nodeObj(request.node.id,request.node.port,request.node.address))
					bucket[index] = tmp
				else:
					adding = True
					for k,v in bucket.items():
						for i in range(0,len(v)):
							if v[i].id==request.node.id:
								adding = False
					if adding==True:					
						n = len(bucket[index])
						tmp = bucket[index]
						if n==bucket_max:
							tmp.pop()
						tmp.insert(0,nodeObj(request.node.id,request.node.port,request.node.address))
						bucket[index] = tmp


			all_nodes = []
			for k,v in bucket.items():
				for j in range(len(v)):
					all_nodes.append(v[j])

			ordered_nodes = sorted(all_nodes, key=lambda x : XOR(x.id,request.node.id))

			node_tmp = csci4220_hw3_pb2.Node(id=local_node,port=local_port,address=local_address)
			ret = []

			# update bucket
			for node in ordered_nodes:
				if node.id!=request.idkey:
					if node.id==0:
						tmp = csci4220_hw3_pb2.Node(id=1000,port=node.port,address=node.address)
						ret.append(tmp)
					else:
						tmp = csci4220_hw3_pb2.Node(id=node.id,port=node.port,address=node.address)
						ret.append(tmp)

			print("Serving FindNode(" + str(request.node.id) + ") request for " + str(request.idkey))
			sys.stdout.flush()
			return csci4220_hw3_pb2.NodeList(responding_node=node_tmp,nodes=ret)
예제 #27
0
def run():
    '''
    Check the # of command-line arguments, which should have
        hw3.py <nodeID> <port> <k>
    '''
    if len(sys.argv) != 4:
        print("Error, correct usage is {} [my id] [my port] [k]".format(
            sys.argv[0]))
        sys.exit(-1)

    local_id = int(sys.argv[1])
    my_port = str(int(sys.argv[2]))  # add_insecure_port() will want a string
    k = int(sys.argv[3])

    my_hostname = socket.gethostname()  # Gets my host name
    my_address = socket.gethostbyname(
        my_hostname)  # Gets my IP address from my hostname
    # print("[myself] Running as {0} @ {1}".format(my_hostname,my_address))
    # Setting up the server
    server = grpc.server(futures.ThreadPoolExecutor(max_workers=10))
    servicer = KadImplServicer(local_id, int(my_port), my_address, k)
    csci4220_hw3_pb2_grpc.add_KadImplServicer_to_server(servicer, server)
    server.add_insecure_port("[::]:" + my_port)
    server.start()
    # Run the client
    while True:
        inputs = input()
        arguments = inputs.split()

        if arguments[0] == "BOOTSTRAP":
            remote_hostname = arguments[1]
            my_port = int(arguments[2])

            remote_addr = socket.gethostbyname(remote_hostname)

            # Connect to other peer
            channel = grpc.insecure_channel(
                str(remote_addr) + ':' + str(my_port))
            stub = csci4220_hw3_pb2_grpc.KadImplStub(channel)
            # Find peer node using servicer node
            nodee = stub.FindNode(
                csci4220_hw3_pb2.IDKey(node=servicer.node, idkey=local_id))

            # Add node that was responding
            res_node = nodee.responding_node
            bit_len = ((res_node.id) ^ local_id).bit_length()
            bit_len -= 1
            if len(servicer.k_buckets[bit_len]) == k:
                servicer.k_buckets[bit_len].popleft()
            servicer.k_buckets[bit_len].append(res_node)

            # Print bucket contents
            print('After BOOTSTRAP({}), k_buckets now look like:'.format(
                str(res_node.id)))
            servicer.print_k_buckets()
            channel.close()

        elif arguments[0] == "FIND_NODE":
            # Load the inputs argument
            node_id = int(arguments[1])

            print("Before FIND_NODE command, k-buckets are:")
            servicer.print_k_buckets()

            S = servicer.find_k_closest_nodes(node_id)
            S_no = S  # Nodes in S that have not been contacted yet
            S_yes = []  # Nodes that have been contacted

            found = False
            while S_no and (not found):
                for no in S_no:
                    # Start a channel
                    channel = grpc.insecure_channel(no.address + ':' +
                                                    str(no.port))
                    stub = csci4220_hw3_pb2_grpc.KadImplStub(channel)

                    # Send a FindNode RPC
                    R = stub.FindNode(
                        csci4220_hw3_pb2.IDKey(node=servicer.node,
                                               idkey=node_id))

                    # Update the k-buckets
                    servicer.update_k_buckets(no, True)
                    for node in R.nodes:
                        servicer.update_k_buckets(node, False)
                    # Update S_yes
                    S_yes.append(no)

                    # Close the channel
                    channel.close()

                # Check if the node has been found
                for bucket in servicer.k_buckets:
                    if any(node.id == node_id for node in bucket):
                        found = True
                        print("Found destination id {}".format(node_id))
                        break

                if not found:
                    # Update S and S_no
                    S = servicer.find_k_closest_nodes(node_id)
                    S_no.clear()
                    for node in S:
                        if not any(yes.id == node.id for yes in S_yes):
                            S_no.append(node)

            if not found:
                print("Could not find destination id {}".format(node_id))

            print("After FIND_NODE command, k-buckets are:")
            servicer.print_k_buckets()

        elif arguments[0] == "FIND_VALUE":
            # Load the inputs argument
            key = int(arguments[1])

            print("Before FIND_VALUE command, k-buckets are:")
            servicer.print_k_buckets()

            found = False
            # See if the key/value pair has already been stored
            for pair in servicer.key_value:
                if pair[0] == key:
                    found = True
                    print("Found data \"{}\" for key {}".format(pair[1], key))
                    break

            if not found:
                S = servicer.find_k_closest_nodes(key)
                S_no = S  # Nodes in S that have not been contacted yet
                S_yes = []  # Nodes that have been contacted

                while S_no and (not found):
                    for no in S_no:
                        # Start a channel
                        channel = grpc.insecure_channel(no.address + ':' +
                                                        str(no.port))
                        stub = csci4220_hw3_pb2_grpc.KadImplStub(channel)

                        # Send a FindNode RPC
                        R = stub.FindValue(
                            csci4220_hw3_pb2.IDKey(node=servicer.node,
                                                   idkey=key))

                        # Update the k-buckets
                        servicer.update_k_buckets(no, True)
                        # Update S_yes
                        S_yes.append(no)

                        # Close the channel
                        channel.close()

                        # Check if the value is found
                        if R.mode_kv:
                            found = True
                            print("Found value \"{}\" for key {}".format(
                                R.kv.value, key))
                            break
                        else:
                            # Update the k-buckets
                            for node in R.nodes:
                                servicer.update_k_buckets(node, False)

                    if not found:
                        # Update S and S_no
                        S = servicer.find_k_closest_nodes(key)
                        S_no.clear()
                        for node in S:
                            if not any(yes.id == node.id for yes in S_yes):
                                S_no.append(node)

                if not found:
                    print("Could not find key {}".format(key))

            print("After FIND_VALUE command, k-buckets are:")
            servicer.print_k_buckets()

        elif arguments[0] == "STORE":

            this_key = int(arguments[1])
            this_value = arguments[2]

            closest_node = csci4220_hw3_pb2.Node(id=local_id,
                                                 port=int(my_port),
                                                 address=str(my_address))
            distance = abs(local_id - this_key)
            for bucket in servicer.k_buckets:
                for entry in bucket:
                    if abs(int(entry.id) - this_key) < distance:
                        closest_node = entry
                        distance = abs(int(entry.id) - this_key)

            closest_port = int(closest_node.port)

            #Connect to server & stub
            this_addr = closest_node.address + ':' + str(closest_port)
            channel = grpc.insecure_channel(this_addr)
            stub = csci4220_hw3_pb2_grpc.KadImplStub(channel)

            some_idkey = stub.Store(
                csci4220_hw3_pb2.KeyValue(node=servicer.node,
                                          key=this_key,
                                          value=this_value))
            print("Storing key {} at node {}".format(this_key,
                                                     some_idkey.idkey))
            channel.close()

        elif arguments[0] == "QUIT":
            # Tell everyone we are quitting, goodbye :(
            for bucket in servicer.k_buckets:
                for entry in bucket:
                    remote_host = str(entry.id)
                    remote_port = int(entry.port)

                    my_addr = entry.address + ':' + str(remote_port)

                    # Create channel and tell other peer we are quitting
                    channel = grpc.insecure_channel(my_addr)
                    stub = csci4220_hw3_pb2_grpc.KadImplStub(channel)

                    print("Letting " + remote_host + " know I'm quitting.")
                    some_idkey = stub.Quit(
                        csci4220_hw3_pb2.IDKey(node=servicer.node,
                                               idkey=local_id))
                    channel.close()
            print("Shut down node " + str(local_id))
            break

        else:
            # Unknown command
            print("Unknown command. Use BOOTSTRAP , FIND_VALUE , STORE , QUIT")