mirror of
https://github.com/Qortal/altcoinj.git
synced 2025-07-31 20:11:23 +00:00
Add a feature to PeerGroup that lets you find/wait for peers that match a certain mask, similar to those methods that exist for peer versions.
This commit is contained in:
@@ -1501,7 +1501,7 @@ public class PeerGroup implements TransactionBroadcaster {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns a mutable array list of peers that implement the given protocol version or better.
|
* Returns an array list of peers that implement the given protocol version or better.
|
||||||
*/
|
*/
|
||||||
public List<Peer> findPeersOfAtLeastVersion(long protocolVersion) {
|
public List<Peer> findPeersOfAtLeastVersion(long protocolVersion) {
|
||||||
lock.lock();
|
lock.lock();
|
||||||
@@ -1516,6 +1516,48 @@ public class PeerGroup implements TransactionBroadcaster {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns a future that is triggered when there are at least the requested number of connected peers that support
|
||||||
|
* the given protocol version or higher. To block immediately, just call get() on the result.
|
||||||
|
*
|
||||||
|
* @param numPeers How many peers to wait for.
|
||||||
|
* @param mask An integer representing a bit mask that will be ANDed with the peers advertised service masks.
|
||||||
|
* @return a future that will be triggered when the number of connected peers implementing protocolVersion or higher >= numPeers
|
||||||
|
*/
|
||||||
|
public ListenableFuture<List<Peer>> waitForPeersWithServiceMask(final int numPeers, final int mask) {
|
||||||
|
List<Peer> foundPeers = findPeersWithServiceMask(mask);
|
||||||
|
if (foundPeers.size() >= numPeers)
|
||||||
|
return Futures.immediateFuture(foundPeers);
|
||||||
|
final SettableFuture<List<Peer>> future = SettableFuture.create();
|
||||||
|
addEventListener(new AbstractPeerEventListener() {
|
||||||
|
@Override
|
||||||
|
public void onPeerConnected(Peer peer, int peerCount) {
|
||||||
|
final List<Peer> peers = findPeersWithServiceMask(mask);
|
||||||
|
if (peers.size() >= numPeers) {
|
||||||
|
future.set(peers);
|
||||||
|
removeEventListener(this);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
return future;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns an array list of peers that match the requested service bit mask.
|
||||||
|
*/
|
||||||
|
public List<Peer> findPeersWithServiceMask(int mask) {
|
||||||
|
lock.lock();
|
||||||
|
try {
|
||||||
|
ArrayList<Peer> results = new ArrayList<Peer>(peers.size());
|
||||||
|
for (Peer peer : peers)
|
||||||
|
if ((peer.getPeerVersionMessage().localServices & mask) == mask)
|
||||||
|
results.add(peer);
|
||||||
|
return results;
|
||||||
|
} finally {
|
||||||
|
lock.unlock();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns the number of connections that are required before transactions will be broadcast. If there aren't
|
* Returns the number of connections that are required before transactions will be broadcast. If there aren't
|
||||||
* enough, {@link PeerGroup#broadcastTransaction(Transaction)} will wait until the minimum number is reached so
|
* enough, {@link PeerGroup#broadcastTransaction(Transaction)} will wait until the minimum number is reached so
|
||||||
|
@@ -698,6 +698,31 @@ public class PeerGroupTest extends TestWithPeerGroup {
|
|||||||
assertTrue(future.isDone());
|
assertTrue(future.isDone());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void waitForPeersWithServiceFlags() throws Exception {
|
||||||
|
ListenableFuture<List<Peer>> future = peerGroup.waitForPeersWithServiceMask(2, 3);
|
||||||
|
|
||||||
|
VersionMessage ver1 = new VersionMessage(params, 10);
|
||||||
|
ver1.clientVersion = 70000;
|
||||||
|
ver1.localServices = VersionMessage.NODE_NETWORK;
|
||||||
|
VersionMessage ver2 = new VersionMessage(params, 10);
|
||||||
|
ver2.clientVersion = 70000;
|
||||||
|
ver2.localServices = VersionMessage.NODE_NETWORK | 2;
|
||||||
|
peerGroup.start();
|
||||||
|
assertFalse(future.isDone());
|
||||||
|
connectPeer(1, ver1);
|
||||||
|
assertTrue(peerGroup.findPeersWithServiceMask(3).isEmpty());
|
||||||
|
assertFalse(future.isDone());
|
||||||
|
connectPeer(2, ver2);
|
||||||
|
assertFalse(future.isDone());
|
||||||
|
assertEquals(1, peerGroup.findPeersWithServiceMask(3).size());
|
||||||
|
assertTrue(peerGroup.waitForPeersWithServiceMask(1, 0x3).isDone()); // Immediate completion.
|
||||||
|
connectPeer(3, ver2);
|
||||||
|
future.get();
|
||||||
|
assertTrue(future.isDone());
|
||||||
|
peerGroup.stop();
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void preferLocalPeer() throws IOException {
|
public void preferLocalPeer() throws IOException {
|
||||||
// Because we are using the same port (8333 or 18333) that is used by Satoshi client
|
// Because we are using the same port (8333 or 18333) that is used by Satoshi client
|
||||||
|
Reference in New Issue
Block a user