From 2001419f1ab8d3430e4aefb06ddab996302a9903 Mon Sep 17 00:00:00 2001 From: Zlatin Balevsky Date: Wed, 29 Apr 2020 06:07:22 +0100 Subject: [PATCH] Iterate through the swarms in order of last pinged, get hosts which have not been pinged recently, also in chronological order --- .../groovy/com/muwire/tracker/Swarm.groovy | 22 +++++++++++-- .../com/muwire/tracker/SwarmManager.groovy | 31 +++++++++++++++++++ 2 files changed, 51 insertions(+), 2 deletions(-) diff --git a/tracker/src/main/groovy/com/muwire/tracker/Swarm.groovy b/tracker/src/main/groovy/com/muwire/tracker/Swarm.groovy index d25bac7a..7cf95093 100644 --- a/tracker/src/main/groovy/com/muwire/tracker/Swarm.groovy +++ b/tracker/src/main/groovy/com/muwire/tracker/Swarm.groovy @@ -34,6 +34,11 @@ class Swarm { */ private long lastQueryTime + /** + * Last time a batch of hosts was pinged + */ + private long lastPingTime + Swarm(InfoHash infoHash) { this.infoHash = infoHash } @@ -119,13 +124,21 @@ class Swarm { negative.add(h.persona) } - synchronized List getBatchToPing(int max) { + /** + * @param max number of hosts to give back + * @param now what time is it now + * @param cutoff only consider hosts which have been pinged before this time + * @return hosts to be pinged + */ + synchronized List getBatchToPing(int max, long now, long cutOff) { List rv = new ArrayList<>() rv.addAll(unknown.values()) rv.addAll(seeds.values()) rv.addAll(leeches.values()) rv.removeAll(inFlight.values()) + rv.removeAll { it.lastPinged >= cutOff } + Collections.sort(rv, {l, r -> Long.compare(l.lastPinged, r.lastPinged) } as Comparator) @@ -133,15 +146,20 @@ class Swarm { if (rv.size() > max) rv = rv[0..(max-1)] - final long now = System.currentTimeMillis() rv.each { it.lastPinged = now inFlight.put(it.persona, it) } + if (!rv.isEmpty()) + lastPingTime = now rv } + synchronized long getLastPingTime() { + lastPingTime + } + public Info info() { List seeders = seeds.keySet().collect { it.getHumanReadableName() } List leechers = leeches.keySet().collect { it.getHumanReadableName() } diff --git a/tracker/src/main/groovy/com/muwire/tracker/SwarmManager.groovy b/tracker/src/main/groovy/com/muwire/tracker/SwarmManager.groovy index cb311038..56ae4a1a 100644 --- a/tracker/src/main/groovy/com/muwire/tracker/SwarmManager.groovy +++ b/tracker/src/main/groovy/com/muwire/tracker/SwarmManager.groovy @@ -73,6 +73,23 @@ class SwarmManager { if (it.shouldQuery(queryCutoff, now)) query(it) } + + List swarmList = new ArrayList<>(swarms.values()) + Collections.sort(swarmList,{Swarm x, Swarm y -> + Long.compare(x.getLastPingTime(), y.getLastPingTime()) + } as Comparator) + + List toPing = new ArrayList<>() + final int amount = trackerProperties.getSwarmParameters().getPingParallel() + final int pingCutoff = now - trackerProperties.getSwarmParameters().getPingInterval() * 60 * 1000L + + for(int i = 0; i < swarmList.size() && toPing.size() < amount; i++) { + Swarm s = swarmList.get(i) + List hostsFromSwarm = s.getBatchToPing(amount - toPing.size(), now, pingCutoff) + hostsFromSwarm.collect(toPing, { host -> new HostAndIH(host, s.getInfoHash())}) + } + + log.info("will ping $toPing") } private void query(Swarm swarm) { @@ -114,4 +131,18 @@ class SwarmManager { Swarm.Info info(InfoHash infoHash) { swarms.get(infoHash)?.info() } + + private static class HostAndIH { + private final Host host + private final InfoHash infoHash + HostAndIH(Host host, InfoHash infoHash) { + this.host = host + this.infoHash = infoHash + } + + @Override + public String toString() { + "$host:$infoHash" + } + } }