From ea9d7ef42504789f159f75adf250ae47cc1be8be Mon Sep 17 00:00:00 2001
From: harlekin <5800926-mw102@users.noreply.gitlab.com>
Date: Sat, 4 Dec 2021 10:32:10 +0000
Subject: [PATCH] fixed hung socket added missing part to protocol.txt
---
protocol.txt | 8 +++
src/com/sheepit/client/Speedtest.java | 70 +++++++++++++++------------
2 files changed, 48 insertions(+), 30 deletions(-)
diff --git a/protocol.txt b/protocol.txt
index ec70b0e..e430ad7 100644
--- a/protocol.txt
+++ b/protocol.txt
@@ -56,6 +56,14 @@ The maximum duration between two heartbeats in seconds is given by the attribute
+The client then performs a speedtest on these mirror urls and POSTs back the 3 fastest ones using the "speedtest-answer" endpoint, together with the transfer time for the payload:
+
+
+
+
+
+
+
=== Session end ===
Url: use the request type "logout" from the configuration answer.
diff --git a/src/com/sheepit/client/Speedtest.java b/src/com/sheepit/client/Speedtest.java
index a009df4..dace61d 100644
--- a/src/com/sheepit/client/Speedtest.java
+++ b/src/com/sheepit/client/Speedtest.java
@@ -4,8 +4,11 @@ import com.sheepit.client.datamodel.SpeedTestTarget;
import java.io.IOException;
import java.io.InputStream;
+import java.net.InetAddress;
+import java.net.InetSocketAddress;
import java.net.MalformedURLException;
import java.net.Socket;
+import java.net.SocketAddress;
import java.net.URL;
import java.time.Duration;
import java.util.ArrayList;
@@ -24,23 +27,24 @@ public class Speedtest {
public Speedtest(Log log) {
this.log = log;
}
-
+
/**
- * @param urls the urls to the speedtest payloads
- * @param numberOfResults number of best mirrors to return
- *
- * @return An array of the mirrors with the best connection time. The size of the array is determined by numberOfResults or urls.size()
+ * @param urls the urls to the speedtest payloads
+ * @param numberOfResults number of best mirrors to return
+ *
+ * @return An array of the mirrors with the best connection time. The size of the array is determined by numberOfResults or urls.size()
* if numberOfResults > urls.size()
- */
+ */
public List doSpeedtests(List urls, int numberOfResults) {
-
+
List pingResult = (urls
- .stream()
- .map(this::measure)
- .sorted(ORDERED)
- .collect(Collectors.toList())
+ .stream()
+ .map(this::measure)
+ .filter(target -> target.getPing().getAverage() > 0)
+ .sorted(ORDERED)
+ .collect(Collectors.toList())
);
-
+
numberOfResults = Math.min(numberOfResults, urls.size());
List result = new ArrayList<>(numberOfResults);
@@ -66,22 +70,25 @@ public class Speedtest {
result.sort(Comparator.comparing(SpeedTestTarget::getSpeedtest).reversed());
return result;
}
-
+
private SpeedTestTarget measure(String mirror) {
long pingCount = 12;
- var pingStatistics = LongStream
- .range(0, pingCount)
- .map(i -> {
- try {
- return runTimed(() -> ping(mirror, PORT)).first;
- }
- catch (Exception e) {
- this.log.error("Speedtest::ping Exception " + e);
- return Long.MAX_VALUE;
- }
- })
- .summaryStatistics();
-
+
+ LongStream.Builder streamBuilder = LongStream.builder();
+
+ for (int i = 0; i < pingCount; i++) {
+ try {
+ streamBuilder.add(runTimed(() -> ping(mirror, PORT)).first);
+ }
+ catch (Exception e) {
+ this.log.error("Speedtest::ping Exception " + e);
+ pingCount /= 2;
+ streamBuilder.add(Long.MAX_VALUE);
+ }
+ }
+
+ var pingStatistics = streamBuilder.build().summaryStatistics();
+
return new SpeedTestTarget(mirror, -1, pingStatistics);
}
@@ -116,13 +123,16 @@ public class Speedtest {
throw new RuntimeException("Unable to execute speedtest to: " + url, e);
}
}
-
+
private static int ping(String url, int port) {
- try (Socket socket = new Socket(new URL(url).getHost(), port)) {
-
+ try (Socket socket = new Socket()) {
+ InetAddress mirrorIP = InetAddress.getByName(new URL(url).getHost());
+ SocketAddress socketAddress = new InetSocketAddress(mirrorIP, port);
+ int maxWaitingTime_ms = 3000;
+ socket.connect(socketAddress, maxWaitingTime_ms);
}
catch (IOException e) {
- throw new RuntimeException("Unable to open a socket to " + url + ":" + port, e);
+ throw new RuntimeException("Unable to connect to " + url + ":" + port, e);
}
return -1;
}