void Handle (DHT& dht, const Host& host, const Packet& pckt)
	{
		Key k = pckt.GetArg<Key>(DHT_GET_KEY);
		pf_log[W_DHT] << "Get received with key " << k;

		if(dht.GetStorage()->hasKey(k))
		{
			pf_log[W_DHT] << "Answer with data " << dht.GetStorage()->getInfo(k)->GetStr();
			Packet get_ack(DHTGetAckType, dht.GetMe(), host.GetKey());
			get_ack.SetArg(DHT_GET_ACK_KEY, k);
			get_ack.SetArg(DHT_GET_ACK_DATA, dht.GetStorage()->getInfo(k));
			if(!dht.GetChimera()->Send(host, get_ack))
				pf_log[W_DHT] << "Send get ACK message failed!";
			return;
		}

		pf_log[W_DHT] << "Data not in cache, try to relay to a closest host.";
		if(!dht.GetChimera()->Route(pckt))
		{
			pf_log[W_DHT] << "I'm the owner and the key is unknow, answer with GET_NACK.";
			Packet get_nack(DHTGetNAckType, dht.GetMe(), host.GetKey());
			get_nack.SetArg(DHT_GET_NACK_KEY, k);
			if(!dht.GetChimera()->Send(host, get_nack))
				pf_log[W_DHT] << "Send get NACK message failed!";
			return;
		}
		pf_log[W_DHT] << "GET relayed.";
	}
	void Handle (DHT& dht, const Host&, const Packet& pckt)
	{
		Key k = pckt.GetArg<Key>(DHT_UNPUBLISH_KEY);
		pf_log[W_DHT] << "Got Unpublish message for key " << k;

		Data *data = pckt.GetArg<Data*>(DHT_UNPUBLISH_DATA);
		pf_log[W_DHT] << "Data: " << data->GetStr();

		try {
			dht.GetStorage()->removeInfo(k, data);
		}
		catch(Storage::WrongDataType e) {
			pf_log[W_DHT] << "Asked to remove wrong data type, abord.";
			return;
		}

		/* Repeat unpublish on redondancy hosts */
		Packet replicate(DHTRepeatUType, dht.GetMe());
		replicate.SetArg(DHT_REPEAT_U_KEY, k);
		replicate.SetArg(DHT_REPEAT_U_DATA, data);
		dht.GetChimera()->SendToNeighbours(dht.REDONDANCY, replicate);
	}
Exemple #3
0
int main(int argc, char** argv)
{
	if(argc < 2)
	{
		std::cout << "Usage: " << argv[0] << " listen_port [boostrap_host:port]" << std::endl;
		return EXIT_FAILURE;
	}

	srand(time(NULL));

	DHT* dht = new DHT(NULL, StrToTyp<uint16_t>(argv[1]));

	pf_log.SetLoggedFlags("DESYNCH WARNING ERR INFO DHT", false);
	Scheduler::StartSchedulers(5);

	if(argc > 2)
	{
		Host host = hosts_list.DecodeHost(argv[2]);
		pf_log[W_INFO] << "Connecting to " << host;
		dht->GetChimera()->Join(host);
	}

	std::string s;
	while(std::getline(std::cin, s))
	{
		std::string command_str = stringtok(s, " ");
		Key k;

		if(command_str.length() == 0)
			continue;

		switch(command_str[0])
		{
			case 's':
			case 'S':
				pf_log[W_DHT] << dht->GetStorage()->GetStr();
				break;
			case 'l':
			case 'L':
				pf_log[W_DHT] << dht->GetChimera()->GetRouting()->GetLeafset()->GetStr();
				break;
			case 'r':
			case 'R':
				pf_log[W_DHT] << dht->GetChimera()->GetRouting()->GetRoutingTable()->GetStr();
				break;
			case 'p':
			case 'P':
				k.MakeHash(s);
				pf_log[W_DHT] << "Publish " << s << " with key " << k;
				dht->Publish(k, s);
				break;
			case 'u':
			case 'U':
				k = stringtok(s, " ");
				pf_log[W_DHT] << "Unublish " << s << " with key " << k;
				dht->Unpublish(k, s);
				break;
			case 'g':
			case 'G':
				k = s;
				pf_log[W_DHT] << "Request data with key " << k;
				if(!dht->RequestData(k))
					if(dht->GetStorage()->hasKey(k))
						pf_log[W_DHT] << dht->GetStorage()->getInfo(k)->GetStr();
				break;
			case 'q':
			case 'Q':
				return EXIT_SUCCESS;
			default:
				pf_log[W_ERR] << "Command not recognized.";
		}
	}

	return EXIT_SUCCESS;
}