From f33b91dccdf5b7f6602dc471334f83955c750dd8 Mon Sep 17 00:00:00 2001 From: Louis Royer Date: Sat, 28 Mar 2020 16:31:24 +0100 Subject: [PATCH] Ratio implementation for client --- src/clientP2P/ClientDownload.java | 31 ++++++++++++++++++++++-- src/clientP2P/ClientDownloadPart.java | 26 ++++++++++++++++++-- src/clientP2P/ClientDownloadPartTCP.java | 5 ++-- src/clientP2P/ClientDownloadPartUDP.java | 5 ++-- src/clientP2P/ClientDownloadTCP.java | 7 +++--- src/clientP2P/ClientDownloadUDP.java | 7 +++--- src/clientP2P/ClientManagement.java | 2 ++ src/clientP2P/ClientManagementTCP.java | 2 +- src/clientP2P/ClientManagementUDP.java | 2 +- src/tracker/TrackerManagement.java | 1 + 10 files changed, 72 insertions(+), 16 deletions(-) diff --git a/src/clientP2P/ClientDownload.java b/src/clientP2P/ClientDownload.java index 99aabbd..0a3b18d 100644 --- a/src/clientP2P/ClientDownload.java +++ b/src/clientP2P/ClientDownload.java @@ -1,5 +1,7 @@ package clientP2P; +import java.util.Map; +import java.util.HashMap; import java.util.List; import java.util.ArrayList; import java.util.Arrays; @@ -24,6 +26,7 @@ import remoteException.ProtocolRemoteError; import remoteException.NotFound; import remoteException.InternalRemoteError; import remoteException.NotATracker; +import remoteException.UnknownHost; import protocolP2P.HashAlgorithm; import protocolP2P.HashResponse; import protocolP2P.HashRequest; @@ -32,6 +35,7 @@ import protocolP2P.FilePart; import protocolP2P.SizeRequest; import protocolP2P.SizeResponse; import protocolP2P.ProtocolP2PPacket; +import protocolP2P.UpdateRatio; import clientP2P.ClientDownloadPart; import tools.HostItem; import tools.Logger; @@ -49,6 +53,7 @@ public abstract class ClientDownload extends ServeErrors implements Runnable { protected String filename; protected byte[] hash512; protected List sockList = new ArrayList(); + protected Map ratioUpdater = new HashMap<>(); protected List offsetsToAsk = new ArrayList(); protected List offsetsPending = new ArrayList(); protected boolean stop; @@ -59,6 +64,7 @@ public abstract class ClientDownload extends ServeErrors implements Runnable { protected boolean success = false; protected Logger logger; protected HostItem client; + protected HostItem tracker; /** Constructor with parameters: filename, list of hosts, parts subdirectory and dirStorage * @param filename name of file to download @@ -67,14 +73,16 @@ public abstract class ClientDownload extends ServeErrors implements Runnable { * @param dirStorage directory to write assembled file * @param logger Logger * @param client HostItem of the application + * @param tracker HostItem of the tracker */ - public ClientDownload(String filename, List hostList, String partsSubdir, String dirStorage, Logger logger, HostItem client) { + public ClientDownload(String filename, List hostList, String partsSubdir, String dirStorage, Logger logger, HostItem client, HostItem tracker) { this.partsSubdir = partsSubdir; this.dirStorage = dirStorage; this.filename = filename; this.hostList = hostList; this.logger = logger; this.client = client; + this.tracker = tracker; this.stop = false; } @@ -165,6 +173,7 @@ public abstract class ClientDownload extends ServeErrors implements Runnable { } catch (InterruptedException e) { throw new InternalError(); } + ratioUpdater.put(c.getServer(), c.getReceivedBytesCount()); } writeLog("Task check status: " + offsetsToAsk.size() + " to asks, " + offsetsPending.size() + " pending", LogLevel.Info); if (offsetsToAsk.isEmpty() && offsetsPending.isEmpty()) { @@ -180,6 +189,25 @@ public abstract class ClientDownload extends ServeErrors implements Runnable { } } + /** Send Ratio update to the tracker + */ + public void sendRatioUpdate() { + for(HostItem server: ratioUpdater.keySet()) { + Long r = ratioUpdater.get(server); + if (r != null) { + long rl = r.longValue(); + if (rl != 0) { + try { + ProtocolP2PPacket d = createProtocolP2PPacket(new UpdateRatio(client, server, rl)); + d.sendRequest(getHostItemSocket(tracker)); + } catch (Exception e) { + writeLog(e, LogLevel.Error); + } + } + } + } + } + /** Get hashsum from server. * @param hostItem server to ask hash * @return hash512sum @@ -350,7 +378,6 @@ public abstract class ClientDownload extends ServeErrors implements Runnable { while(!stop) { assignTasks(); checkTasksStatus(); - } } writeLog("Reassembling file parts.", LogLevel.Info); diff --git a/src/clientP2P/ClientDownloadPart.java b/src/clientP2P/ClientDownloadPart.java index cccd3ba..c66fbfe 100644 --- a/src/clientP2P/ClientDownloadPart.java +++ b/src/clientP2P/ClientDownloadPart.java @@ -35,6 +35,7 @@ import tools.HostItem; * @version 1.0 */ public abstract class ClientDownloadPart extends ServeErrors implements Runnable { + protected long receivedBytesCount; protected List toDoTasks; protected List pendingTasks; protected List tasksDone; @@ -48,6 +49,7 @@ public abstract class ClientDownloadPart extends ServeErrors implements Runnable protected ClientDownload manager; protected Logger logger; protected HostItem client; + private HostItem server; /** Constructor with filename, socket, and part subdir * @param filename name of file to download @@ -55,13 +57,15 @@ public abstract class ClientDownloadPart extends ServeErrors implements Runnable * @param partsSubdir directory to store .part files * @param logger Logger * @param client HostItem of the application + * @param server HostItem of the server application */ - public ClientDownloadPart(ClientDownload manager, String filename, String partsSubdir, Logger logger, HostItem client) { + public ClientDownloadPart(ClientDownload manager, String filename, String partsSubdir, Logger logger, HostItem client, HostItem server) { this.manager = manager; this.partsSubdir = partsSubdir; this.filename = filename; this.logger = logger; this.client = client; + this.server = server; stop = false; failed = false; pendingTasks = new ArrayList<>(); @@ -69,6 +73,22 @@ public abstract class ClientDownloadPart extends ServeErrors implements Runnable tasksDone = new ArrayList<>(); noTask = true; tasksListsLock = false; + receivedBytesCount = 0; + } + + + /** receivedBytesCount getter + * @return receivedBytesCount + */ + public Long getReceivedBytesCount() { + return Long.valueOf(receivedBytesCount); + } + + /** Server getter + * @return server + */ + public HostItem getServer() { + return server; } /** True if thread has failed to get a file. @@ -271,8 +291,10 @@ public abstract class ClientDownloadPart extends ServeErrors implements Runnable } Long offset = Long.valueOf(fp.getOffset()); if (pendingTasks.contains(offset)) { + byte[] partialContent = fp.getPartialContent(); try { - Files.write(new File(partsSubdir + filename + "_" + offset + ".part").toPath(), fp.getPartialContent()); + Files.write(new File(partsSubdir + filename + "_" + offset + ".part").toPath(), partialContent); + receivedBytesCount += partialContent.length; } catch (IOException e) { writeLog("cannot write file (" + partsSubdir + filename + "_" + offset + ".part)", LogLevel.Error); } diff --git a/src/clientP2P/ClientDownloadPartTCP.java b/src/clientP2P/ClientDownloadPartTCP.java index d354ed4..f7dde9d 100644 --- a/src/clientP2P/ClientDownloadPartTCP.java +++ b/src/clientP2P/ClientDownloadPartTCP.java @@ -44,9 +44,10 @@ public class ClientDownloadPartTCP extends ClientDownloadPart { * @param partsSubdir directory to store .part files * @param logger Logger * @param client HostItem of the application + * @param server HostItem of the server application */ - public ClientDownloadPartTCP(ClientDownload manager, String filename, Socket socket, String partsSubdir, Logger logger, HostItem client) { - super(manager, filename, partsSubdir, logger, client); + public ClientDownloadPartTCP(ClientDownload manager, String filename, Socket socket, String partsSubdir, Logger logger, HostItem client, HostItem server) { + super(manager, filename, partsSubdir, logger, client, server); this.socket = socket; } diff --git a/src/clientP2P/ClientDownloadPartUDP.java b/src/clientP2P/ClientDownloadPartUDP.java index ae0a24c..3ab0a80 100644 --- a/src/clientP2P/ClientDownloadPartUDP.java +++ b/src/clientP2P/ClientDownloadPartUDP.java @@ -44,9 +44,10 @@ public class ClientDownloadPartUDP extends ClientDownloadPart { * @param partsSubdir directory to store .part files * @param logger Logger * @param client HostItem of the application + * @param server HostItem of the server application */ - public ClientDownloadPartUDP(ClientDownload manager, String filename, DatagramSocket socket, String partsSubdir, Logger logger, HostItem client) { - super(manager, filename, partsSubdir, logger, client); + public ClientDownloadPartUDP(ClientDownload manager, String filename, DatagramSocket socket, String partsSubdir, Logger logger, HostItem client, HostItem server) { + super(manager, filename, partsSubdir, logger, client, server); this.socket = socket; } diff --git a/src/clientP2P/ClientDownloadTCP.java b/src/clientP2P/ClientDownloadTCP.java index 0751845..9be9afe 100644 --- a/src/clientP2P/ClientDownloadTCP.java +++ b/src/clientP2P/ClientDownloadTCP.java @@ -51,16 +51,17 @@ public class ClientDownloadTCP extends ClientDownload { * @param dirStorage directory to write assembled file * @param logger Logger * @param client HostItem of the application + * @param tracker HostItem of the tracker */ - public ClientDownloadTCP(String filename, List hostList, String partsSubdir, String dirStorage, Logger logger, HostItem client) { - super(filename, hostList, partsSubdir, dirStorage, logger, client); + public ClientDownloadTCP(String filename, List hostList, String partsSubdir, String dirStorage, Logger logger, HostItem client, HostItem tracker) { + super(filename, hostList, partsSubdir, dirStorage, logger, client, tracker); } /** Create a clientDownloadPart * @param hostItem Hostitem of the server */ protected ClientDownloadPart createDownloadPart(HostItem hostItem) { - return (ClientDownloadPart)new ClientDownloadPartTCP((ClientDownload)this, filename, hostItem.getTCPSocket(), partsSubdir, logger, client); + return (ClientDownloadPart)new ClientDownloadPartTCP((ClientDownload)this, filename, hostItem.getTCPSocket(), partsSubdir, logger, client, hostItem); } /** Close HostItem socket diff --git a/src/clientP2P/ClientDownloadUDP.java b/src/clientP2P/ClientDownloadUDP.java index 5d5dd2a..ce37434 100644 --- a/src/clientP2P/ClientDownloadUDP.java +++ b/src/clientP2P/ClientDownloadUDP.java @@ -51,16 +51,17 @@ public class ClientDownloadUDP extends ClientDownload { * @param dirStorage directory to write assembled file * @param logger Logger * @param client HostItem of the application + * @param tracker HostItem of the tracker */ - public ClientDownloadUDP(String filename, List hostList, String partsSubdir, String dirStorage, Logger logger, HostItem client) { - super(filename, hostList, partsSubdir, dirStorage, logger, client); + public ClientDownloadUDP(String filename, List hostList, String partsSubdir, String dirStorage, Logger logger, HostItem client, HostItem tracker) { + super(filename, hostList, partsSubdir, dirStorage, logger, client, tracker); } /** Create a clientDownloadPart * @param hostItem Hostitem of the server */ protected ClientDownloadPart createDownloadPart(HostItem hostItem) { - return (ClientDownloadPart)new ClientDownloadPartUDP((ClientDownload)this, filename, hostItem.getUDPSocket(), partsSubdir, logger, client); + return (ClientDownloadPart)new ClientDownloadPartUDP((ClientDownload)this, filename, hostItem.getUDPSocket(), partsSubdir, logger, client, tracker); } /** Implementation of writeLog diff --git a/src/clientP2P/ClientManagement.java b/src/clientP2P/ClientManagement.java index a5a481e..2750c4f 100644 --- a/src/clientP2P/ClientManagement.java +++ b/src/clientP2P/ClientManagement.java @@ -210,6 +210,8 @@ public abstract class ClientManagement extends ServeErrors implements Runnable { line += "\n"; writeLog(line, LogLevel.Info); throw new InternalError(); + } else { + downLoader.sendRatioUpdate(); } } else { throw new InternalError(); diff --git a/src/clientP2P/ClientManagementTCP.java b/src/clientP2P/ClientManagementTCP.java index e922157..90f4c71 100644 --- a/src/clientP2P/ClientManagementTCP.java +++ b/src/clientP2P/ClientManagementTCP.java @@ -34,7 +34,7 @@ public class ClientManagementTCP extends ClientManagement { * @param filename Name of the file to download */ protected void initDownloader(String filename) { - downLoader = (ClientDownload) new ClientDownloadTCP(filename, hostList, partsSubdir, baseDirectory, logger, client); + downLoader = (ClientDownload) new ClientDownloadTCP(filename, hostList, partsSubdir, baseDirectory, logger, client, tracker); } diff --git a/src/clientP2P/ClientManagementUDP.java b/src/clientP2P/ClientManagementUDP.java index e34db9c..224a466 100644 --- a/src/clientP2P/ClientManagementUDP.java +++ b/src/clientP2P/ClientManagementUDP.java @@ -33,7 +33,7 @@ public class ClientManagementUDP extends ClientManagement { * @param filename Name of the file to download */ protected void initDownloader(String filename) { - downLoader = (ClientDownload) new ClientDownloadUDP(filename, hostList, partsSubdir, baseDirectory, logger, client); + downLoader = (ClientDownload) new ClientDownloadUDP(filename, hostList, partsSubdir, baseDirectory, logger, client, tracker); } /** Implementation of writeLog diff --git a/src/tracker/TrackerManagement.java b/src/tracker/TrackerManagement.java index 617f101..ab87305 100644 --- a/src/tracker/TrackerManagement.java +++ b/src/tracker/TrackerManagement.java @@ -170,6 +170,7 @@ public abstract class TrackerManagement extends ServeErrors implements Runnable HostItem updateRatioServer = updateRatio.getServer(); HostItem updateRatioClient = updateRatio.getClient(); long ratioSize = updateRatio.getDataSize(); + writeLog("Ratio += " + ratioSize + ", client: " + updateRatioClient + " / server: " + updateRatioServer, LogLevel.Debug); if (!ratioDown.containsKey(updateRatioClient) || ! ratioUp.containsKey(updateRatioServer)) { sendUnknownHost(pd); } else {