diff --git a/pom.xml b/pom.xml
index 052e69d..ea57383 100644
--- a/pom.xml
+++ b/pom.xml
@@ -74,24 +74,24 @@
jlibnotify
1.1.0
-
- com.github.hypfvieh
- dbus-java-core
- 5.1.0-SNAPSHOT
-
-
-
- com.github.hypfvieh
- dbus-java-transport-native-unixsocket
- 5.1.0-SNAPSHOT
-
+
+
+
+
+
+
+
+
+
+
+
-
-
- com.github.hypfvieh
- dbus-java-transport-tcp
- 5.1.0-SNAPSHOT
-
+
+
+
+
+
+
diff --git a/src/main/java/moe/nekojimi/friendcloud/ConnectionManager.java b/src/main/java/moe/nekojimi/friendcloud/ConnectionManager.java
index ff4f0b7..ab7e645 100644
--- a/src/main/java/moe/nekojimi/friendcloud/ConnectionManager.java
+++ b/src/main/java/moe/nekojimi/friendcloud/ConnectionManager.java
@@ -48,12 +48,13 @@ public class ConnectionManager extends Thread
{
consumer.accept(nodeTCPConnection);
}
- } catch (IOException e)
+ } catch (Exception e)
{
- System.err.println("ConnectionManager TCP experienced exception:" + e.getMessage());
+ System.err.println("ConnectionManager experienced exception:" + e.getMessage());
e.printStackTrace(System.err);
}
}
+ System.err.println("ConnectionManager: thread dying!");
}
public PeerConnection getNodeConnection(URI uri) throws IOException
@@ -81,13 +82,14 @@ public class ConnectionManager extends Thread
return nodeConnection;
}
- public PeerConnection getNodeConnection(Peer peer) throws IOException
+ public PeerConnection getNodeConnection(Peer peer)
{
// try to find if we already have an active connection to this peer
purgeDeadConnections();
+ System.out.println("ConnectionManager: trying to get connection to " + peer + " (have " + activeConnections.size() + " connections open)");
for (PeerConnection peerConnection: activeConnections)
{
- if (peerConnection.getNode() == peer)
+ if (peerConnection.getNode().equals(peer))
return peerConnection;
}
@@ -95,14 +97,14 @@ public class ConnectionManager extends Thread
{
try
{
- return getNodeConnection(address);
+ return getNodeConnection(address, peer);
}
catch (IOException ex)
{
- System.err.println("Couldn't create PeerConnection to " + address + " : " + ex.getMessage());
+ System.err.println("ConnectionManager: Couldn't create PeerConnection to " + address + " : " + ex.getMessage());
}
}
- System.err.println("Failed to create PeerConnection to " + peer + "!");
+ System.err.println("ConnectionManager: Failed to create PeerConnection to " + peer + "!");
return null;
}
@@ -121,7 +123,10 @@ public class ConnectionManager extends Thread
for (PeerConnection peerConnection: activeConnections)
{
if (!peerConnection.isAlive())
+ {
+ System.out.println("ConnectionManager: purged dead connection to " + peerConnection.getUri());
deadConnections.add(peerConnection);
+ }
}
activeConnections.removeAll(deadConnections);
}
diff --git a/src/main/java/moe/nekojimi/friendcloud/FilePieceAccess.java b/src/main/java/moe/nekojimi/friendcloud/FilePieceAccess.java
index 6c6caa9..80cecb1 100644
--- a/src/main/java/moe/nekojimi/friendcloud/FilePieceAccess.java
+++ b/src/main/java/moe/nekojimi/friendcloud/FilePieceAccess.java
@@ -21,9 +21,9 @@ public class FilePieceAccess implements Closeable
randomAccessFile.setLength(file.length());
}
- public int getPieceOffset(int index)
+ public long getPieceOffset(int index)
{
- return Math.toIntExact(index * networkFile.getPieceSize());
+ return (index * networkFile.getPieceSize());
}
public int getPieceSize(int index)
@@ -47,7 +47,7 @@ public class FilePieceAccess implements Closeable
int pieceSize = getPieceSize(index);
byte[] buffer = new byte[pieceSize];
- int pieceOffset = getPieceOffset(index);
+ long pieceOffset = getPieceOffset(index);
System.out.println("Reading piece " + index + " from file " + file.getName() + " (offset=" + pieceOffset + ", size=" + pieceSize + ")");
randomAccessFile.seek(pieceOffset);
randomAccessFile.read(buffer);
diff --git a/src/main/java/moe/nekojimi/friendcloud/FileRemoteAccess.java b/src/main/java/moe/nekojimi/friendcloud/FileRemoteAccess.java
index 5b53987..c0c493a 100644
--- a/src/main/java/moe/nekojimi/friendcloud/FileRemoteAccess.java
+++ b/src/main/java/moe/nekojimi/friendcloud/FileRemoteAccess.java
@@ -74,7 +74,7 @@ public class FileRemoteAccess
if (!neededPieces.isEmpty())
{
- boolean ok = waitForPieceRange(neededPieces, 10000);
+ boolean ok = waitForPieceRange(neededPieces, 1000);
if (!ok)
{
System.err.println("FRA: timed out while waiting for pieces " + neededPieces);
diff --git a/src/main/java/moe/nekojimi/friendcloud/Main.java b/src/main/java/moe/nekojimi/friendcloud/Main.java
index 0bcbce1..6f19f50 100644
--- a/src/main/java/moe/nekojimi/friendcloud/Main.java
+++ b/src/main/java/moe/nekojimi/friendcloud/Main.java
@@ -24,12 +24,15 @@ import moe.nekojimi.friendcloud.network.requests.ObjectListRequest;
import moe.nekojimi.friendcloud.objects.NetworkFile;
import moe.nekojimi.friendcloud.objects.NetworkObject;
import moe.nekojimi.friendcloud.objects.Peer;
+import moe.nekojimi.friendcloud.objects.PeerFileState;
import moe.nekojimi.friendcloud.protos.ObjectStatements;
+import moe.nekojimi.friendcloud.storage.DataStore;
import moe.nekojimi.friendcloud.storage.Model;
import moe.nekojimi.friendcloud.storage.StupidJSONFileStore;
import moe.nekojimi.friendcloud.tasks.JoinNetworkTask;
import org.slf4j.simple.SimpleLogger;
+import java.awt.*;
import java.io.File;
import java.io.IOException;
import java.net.*;
@@ -60,12 +63,16 @@ public class Main
@Parameter(names="-create-network")
private boolean createNetwork = false;
+ @Parameter(names = "-storage")
+ private String storageLocation = ".";
+
// @Parameter(names="-file")
private ConnectionManager connectionManager;
private final ScheduledExecutorService executor = new ScheduledThreadPoolExecutor(16);
private final FUSEAccess fuseAccess = new FUSEAccess();
- private final Model model = new Model(new StupidJSONFileStore(new File("storage")));
+ private Model model;
+ private final NotificationManager notificationManager = new NotificationManager();
public static void main(String[] args)
{
@@ -77,8 +84,9 @@ public class Main
try
{
instance.run();
- } catch (IOException | InterruptedException | JLibnotifyLoadException | JLibnotifyInitException e)
+ } catch (Exception e)
{
+ System.err.println("main() received exception, dying horribly!!");
e.printStackTrace(System.err);
try
{
@@ -94,6 +102,10 @@ public class Main
private void run() throws IOException, InterruptedException, JLibnotifyLoadException, JLibnotifyInitException
{
+ DataStore dataStore = new StupidJSONFileStore(new File(storageLocation));
+ model = new Model(dataStore);
+
+ model.init();
connectionManager = new ConnectionManager(tcpPort);
Path mountPoint;
@@ -106,7 +118,6 @@ public class Main
mountPoint = Path.of(System.getProperty("user.dir") + "/fuse-mount-" + tcpPort);
boolean created = mountPoint.toFile().mkdirs();
System.out.println("Created FUSE mount point " + mountPoint);
-
}
fuseAccess.mount(mountPoint);
System.out.println("Mounted virtual filesystem at " + mountPoint);
@@ -122,10 +133,11 @@ public class Main
}
}));
- DefaultJLibnotify libnotify = (DefaultJLibnotify) DefaultJLibnotifyLoader.init().load();
- libnotify.init("FriendCloud");
- JLibnotifyNotification notification = libnotify.createNotification("Holy balls a notification!", "Woah!!!", "dialog-information");
- notification.show();
+// if (Desktop.isDesktopSupported())
+// {
+// Desktop desktop = Desktop.getDesktop();
+// desktop.browse(mountPoint.toFile().toURI());
+// }
connectionManager.addNewConnectionConsumer(this::requestCompleteState);
@@ -184,8 +196,8 @@ public class Main
}
}
- JoinNetworkTask joinNetworkTask = new JoinNetworkTask();
- executor.submit(joinNetworkTask);
+// JoinNetworkTask joinNetworkTask = new JoinNetworkTask();
+// executor.submit(joinNetworkTask);
for (String knownPeerAddress : knownPeers)
{
@@ -309,4 +321,9 @@ public class Main
{
return model;
}
+
+ public NotificationManager getNotificationManager()
+ {
+ return notificationManager;
+ }
}
\ No newline at end of file
diff --git a/src/main/java/moe/nekojimi/friendcloud/NotificationManager.java b/src/main/java/moe/nekojimi/friendcloud/NotificationManager.java
new file mode 100644
index 0000000..48caaa1
--- /dev/null
+++ b/src/main/java/moe/nekojimi/friendcloud/NotificationManager.java
@@ -0,0 +1,105 @@
+package moe.nekojimi.friendcloud;
+
+import es.blackleg.jlibnotify.JLibnotify;
+import es.blackleg.jlibnotify.JLibnotifyNotification;
+import es.blackleg.jlibnotify.core.DefaultJLibnotifyLoader;
+import es.blackleg.jlibnotify.exception.JLibnotifyInitException;
+import es.blackleg.jlibnotify.exception.JLibnotifyLoadException;
+
+public class NotificationManager
+{
+ private final JLibnotify libnotify;
+
+ public NotificationManager()
+ {
+ JLibnotify n;
+ try
+ {
+ n = DefaultJLibnotifyLoader.init().load();
+ n.init("FriendCloud");
+ System.out.println("Libnotify capabilities detected: " + n.getServerCapabilities());
+ JLibnotifyNotification notification = n.createNotification("FriendCloud started", "It works! Cool!", "dialog-information");
+ notification.show();
+ } catch (JLibnotifyLoadException | JLibnotifyInitException e)
+ {
+ n = null;
+ System.err.println("Failed to initialise notification manager.");
+ e.printStackTrace(System.err);
+ }
+ libnotify = n;
+ }
+
+ public enum NotificationType
+ {
+ HELLO,
+ TRANSFER_IN_PROGRESS,
+ TRANSFER_DONE,
+ }
+
+ protected String getNotificationIcon(NotificationType type)
+ {
+ return switch (type)
+ {
+ default -> "dialog-information";
+ };
+ }
+
+ public Notification createNotification(String heading, String body, NotificationType type)
+ {
+ try
+ {
+ return new Notification(heading, body, type);
+ } catch (Exception e)
+ {
+ e.printStackTrace(System.err);
+ return null;
+ }
+ }
+
+ public class Notification
+ {
+ private String heading;
+ private String body;
+ private NotificationType type;
+
+ private JLibnotifyNotification notification;
+
+ public Notification(String heading, String body, NotificationType type)
+ {
+ this.heading = heading;
+ this.body = body;
+ this.type = type;
+
+ if (libnotify != null)
+ {
+ notification = libnotify.createNotification(heading, body, getNotificationIcon(type));
+// notification.setTimeOut(10);
+ notification.show();
+ }
+ }
+
+ public void setHeading(String heading)
+ {
+ this.heading = heading;
+ update();
+ }
+
+ public void setBody(String body)
+ {
+ this.body = body;
+ update();
+ }
+
+ public void setType(NotificationType type)
+ {
+ this.type = type;
+ update();
+ }
+
+ public void update()
+ {
+ notification.update(heading, body, getNotificationIcon(type));
+// notification.setTimeOut(10);
+ }
+ }
+}
diff --git a/src/main/java/moe/nekojimi/friendcloud/ObjectChangeRecord.java b/src/main/java/moe/nekojimi/friendcloud/ObjectChangeRecord.java
index 973e010..aee582f 100644
--- a/src/main/java/moe/nekojimi/friendcloud/ObjectChangeRecord.java
+++ b/src/main/java/moe/nekojimi/friendcloud/ObjectChangeRecord.java
@@ -1,6 +1,6 @@
package moe.nekojimi.friendcloud;
-import moe.nekojimi.friendcloud.objects.NetworkObject;
+import moe.nekojimi.friendcloud.objects.ObjectID;
import moe.nekojimi.friendcloud.protos.ObjectStatements;
import moe.nekojimi.friendcloud.storage.Storable;
@@ -13,18 +13,13 @@ public class ObjectChangeRecord implements Storable
{
// private final long changeID;
- private NetworkObject.ObjectID creatorPeer;
+ private ObjectID creatorPeer;
private Set changeHeads = new HashSet<>();
private Set changes = new HashSet<>();
- public ObjectChangeRecord(NetworkObject.ObjectID creatorPeer)
- {
- this.creatorPeer = creatorPeer;
- }
-
public static ObjectChangeRecord createFromChangeMessage(ObjectStatements.ObjectChangeMessage objectChangeMessage)
{
- ObjectChangeRecord record = new ObjectChangeRecord(new NetworkObject.ObjectID(0)); // TODO: decode creator
+ ObjectChangeRecord record = new ObjectChangeRecord(); // TODO: decode creator
record.changeHeads.addAll(objectChangeMessage.getChangeHeadsList());
for (ObjectStatements.ObjectChange objectChange : objectChangeMessage.getChangesList())
{
@@ -39,9 +34,10 @@ public class ObjectChangeRecord implements Storable
return record;
}
- public static ObjectChangeRecord createFromChanges(NetworkObject.ObjectID creator, Set changes)
+ public static ObjectChangeRecord createFromChanges(ObjectID creator, Set changes)
{
- ObjectChangeRecord record = new ObjectChangeRecord(creator);
+ ObjectChangeRecord record = new ObjectChangeRecord();
+ record.creatorPeer = creator;
record.changes.addAll(changes);
return record;
}
@@ -83,7 +79,7 @@ public class ObjectChangeRecord implements Storable
{
changeHeads = new HashSet<>((Collection) map.get("changeHeads"));
changes = new HashSet<>((Collection) map.get("changes"));
- creatorPeer = new NetworkObject.ObjectID((Long) map.get("creator"));
+ creatorPeer = new ObjectID((Long) map.get("creator"));
}
public String toString()
@@ -115,7 +111,7 @@ public class ObjectChangeRecord implements Storable
return Util.xorBytesToLong(bytes);
}
- public NetworkObject.ObjectID getCreatorPeer()
+ public ObjectID getCreatorPeer()
{
return creatorPeer;
}
@@ -131,12 +127,12 @@ public class ObjectChangeRecord implements Storable
return changeHeads;
}
- public record Change(NetworkObject.ObjectID objectID, Map beforeValues, Map afterValues)
+ public record Change(ObjectID objectID, Map beforeValues, Map afterValues)
{
public static Change createFromObjectChange(ObjectStatements.ObjectChange change)
{
- return new Change(new NetworkObject.ObjectID(change.getObjectId()), change.getBeforeMap(), change.getAfterMap());
+ return new Change(new ObjectID(change.getObjectId()), change.getBeforeMap(), change.getAfterMap());
}
public static Change createFromObjectStates(ObjectStatements.ObjectState before, ObjectStatements.ObjectState after)
@@ -155,7 +151,7 @@ public class ObjectChangeRecord implements Storable
}
if (!afterValues.isEmpty())
{
- return new Change(new NetworkObject.ObjectID(before.getObjectId()), beforeValues, afterValues);
+ return new Change(new ObjectID(before.getObjectId()), beforeValues, afterValues);
}
return null;
}
diff --git a/src/main/java/moe/nekojimi/friendcloud/ObjectChangeTransaction.java b/src/main/java/moe/nekojimi/friendcloud/ObjectChangeTransaction.java
index 5788394..0ebefb9 100644
--- a/src/main/java/moe/nekojimi/friendcloud/ObjectChangeTransaction.java
+++ b/src/main/java/moe/nekojimi/friendcloud/ObjectChangeTransaction.java
@@ -1,6 +1,7 @@
package moe.nekojimi.friendcloud;
import moe.nekojimi.friendcloud.objects.NetworkObject;
+import moe.nekojimi.friendcloud.objects.ObjectID;
import moe.nekojimi.friendcloud.protos.ObjectStatements;
import moe.nekojimi.friendcloud.tasks.PropagateMessageTask;
@@ -13,29 +14,29 @@ import java.util.Set;
public class ObjectChangeTransaction implements Closeable
{
- private final NetworkObject.ObjectID creator;
+ private final ObjectID creator;
private final ConnectionManager connectionManager;
- private final Map beforeStates = new HashMap<>();
+ private final Map beforeStates = new HashMap<>();
private boolean ended = false;
- ObjectChangeTransaction(ConnectionManager connectionManager, NetworkObject.ObjectID creator)
+ ObjectChangeTransaction(ConnectionManager connectionManager, ObjectID creator)
{
this.creator = creator;
this.connectionManager = connectionManager;
}
- public static ObjectChangeTransaction startTransaction(ConnectionManager connectionManager, NetworkObject.ObjectID creatorPeer, NetworkObject.ObjectID... objects)
+ public static ObjectChangeTransaction startTransaction(ConnectionManager connectionManager, ObjectID creatorPeer, ObjectID... objects)
{
ObjectChangeTransaction builder = new ObjectChangeTransaction(connectionManager, creatorPeer);
- for (NetworkObject.ObjectID id : objects)
+ for (ObjectID id : objects)
{
builder.addObjectBeforeChange(id);
}
return builder;
}
- public ObjectChangeTransaction addObjectBeforeChange(NetworkObject.ObjectID id)
+ public ObjectChangeTransaction addObjectBeforeChange(ObjectID id)
{
NetworkObject object = Main.getInstance().getModel().getObject(id);
if (object != null)
@@ -50,7 +51,7 @@ public class ObjectChangeTransaction implements Closeable
ended = true;
Set changes = new HashSet<>();
- for (Map.Entry entry : beforeStates.entrySet())
+ for (Map.Entry entry : beforeStates.entrySet())
{
ObjectStatements.ObjectState afterState = Main.getInstance().getModel().getObject(entry.getKey()).buildObjectState().build();
ObjectChangeRecord.Change change = ObjectChangeRecord.Change.createFromObjectStates(entry.getValue(), afterState);
diff --git a/src/main/java/moe/nekojimi/friendcloud/Util.java b/src/main/java/moe/nekojimi/friendcloud/Util.java
index 4534dbe..f000a5f 100644
--- a/src/main/java/moe/nekojimi/friendcloud/Util.java
+++ b/src/main/java/moe/nekojimi/friendcloud/Util.java
@@ -17,4 +17,16 @@ public class Util
return ret;
}
+ public static long unconditionalNumberToLong(Object number)
+ {
+ assert (number instanceof Number);
+ return ((Number)number).longValue();
+ }
+
+ public static double unconditionalNumberToDouble(Object number)
+ {
+ assert (number instanceof Number);
+ return ((Number)number).doubleValue();
+ }
+
}
diff --git a/src/main/java/moe/nekojimi/friendcloud/network/PeerConnection.java b/src/main/java/moe/nekojimi/friendcloud/network/PeerConnection.java
index 574eff1..ed99ba7 100644
--- a/src/main/java/moe/nekojimi/friendcloud/network/PeerConnection.java
+++ b/src/main/java/moe/nekojimi/friendcloud/network/PeerConnection.java
@@ -9,6 +9,7 @@ import moe.nekojimi.friendcloud.FilePieceAccess;
import moe.nekojimi.friendcloud.Main;
import moe.nekojimi.friendcloud.objects.NetworkFile;
import moe.nekojimi.friendcloud.objects.NetworkObject;
+import moe.nekojimi.friendcloud.objects.ObjectID;
import moe.nekojimi.friendcloud.objects.Peer;
import moe.nekojimi.friendcloud.protos.CommonMessages;
import moe.nekojimi.friendcloud.protos.ObjectStatements;
@@ -129,9 +130,9 @@ public abstract class PeerConnection extends Thread
}
}
- NetworkObject.ObjectID senderID = new NetworkObject.ObjectID(header.getSenderId());
+ ObjectID senderID = new ObjectID(header.getSenderId());
if (peer == null)
- peer = (Peer) Main.getInstance().getModel().getOrCreateObject(senderID);
+ peer = Main.getInstance().getModel().getOrCreateObject(senderID);
else
{
if (!senderID.equals(peer.getObjectID()))
@@ -194,7 +195,7 @@ public abstract class PeerConnection extends Thread
{
objectList.addStates(object.buildObjectState());
}
- System.out.println("Replying to ObjectListRequest with ObjectList, objects=" + objectList.getStatesList());
+// System.out.println("Replying to ObjectListRequest with ObjectList, objects=" + objectList.getStatesList());
sendMessage(wrapMessage(objectList.build(), header));
}
else if (body.is(PieceMessages.FilePiecesRequestMessage.class))
@@ -205,7 +206,7 @@ public abstract class PeerConnection extends Thread
replyWithError(CommonMessages.Error.ERROR_INVALID_ARGUMENT, header);
}
- NetworkFile networkFile = (NetworkFile) Main.getInstance().getModel().getObject(new NetworkObject.ObjectID(filePiecesRequestMessage.getFileId()));
+ NetworkFile networkFile = (NetworkFile) Main.getInstance().getModel().getObject(new ObjectID(filePiecesRequestMessage.getFileId()));
if (networkFile == null)
{
replyWithError(CommonMessages.Error.ERROR_OBJECT_NOT_FOUND, header);
diff --git a/src/main/java/moe/nekojimi/friendcloud/network/PeerTCPConnection.java b/src/main/java/moe/nekojimi/friendcloud/network/PeerTCPConnection.java
index d63e071..8abe51a 100644
--- a/src/main/java/moe/nekojimi/friendcloud/network/PeerTCPConnection.java
+++ b/src/main/java/moe/nekojimi/friendcloud/network/PeerTCPConnection.java
@@ -47,10 +47,13 @@ public class PeerTCPConnection extends PeerConnection
messageReceived(message);
}
}
- } catch (IOException ex)
+ } catch (Exception ex)
{
// fuck
+ ex.printStackTrace(System.err);
}
+
+ System.out.println("TCP Connection: connection closed");
}
@Override
diff --git a/src/main/java/moe/nekojimi/friendcloud/network/requests/ObjectListRequest.java b/src/main/java/moe/nekojimi/friendcloud/network/requests/ObjectListRequest.java
index db8fbb3..d1bfe53 100644
--- a/src/main/java/moe/nekojimi/friendcloud/network/requests/ObjectListRequest.java
+++ b/src/main/java/moe/nekojimi/friendcloud/network/requests/ObjectListRequest.java
@@ -4,6 +4,7 @@ import com.google.protobuf.Any;
import com.google.protobuf.InvalidProtocolBufferException;
import moe.nekojimi.friendcloud.Main;
import moe.nekojimi.friendcloud.objects.NetworkObject;
+import moe.nekojimi.friendcloud.objects.ObjectID;
import moe.nekojimi.friendcloud.protos.ObjectStatements;
import java.io.IOException;
@@ -37,15 +38,16 @@ public class ObjectListRequest extends Request fileStates = new HashMap<>();
+ private final SortedSet peersWithCopy = new TreeSet<>();
+// private final Map fileStates = new HashMap<>();
private BitSet pieces = new BitSet();
// private List pieces = new ArrayList<>();
@@ -97,6 +99,11 @@ public class NetworkFile extends NetworkFSNode
System.out.println("Total hash: " + HexFormat.of().formatHex(hash));
System.out.println("Have " + pieces.cardinality() + " of " + getPieceCount() + " pieces.");
+ if (pieces.cardinality() >= getPieceCount())
+ {
+ peersWithCopy.add(Main.getInstance().getModel().getSelfPeer().getObjectID());
+ }
+
} catch (NoSuchAlgorithmException e)
{
throw new RuntimeException(e);
@@ -115,6 +122,15 @@ public class NetworkFile extends NetworkFSNode
hash = HexFormat.of().parseHex(state.getValuesOrThrow("hash"));
if (state.containsValues("pieceSize"))
pieceSize = Long.parseLong(state.getValuesOrThrow("pieceSize"));
+ if (state.containsValues("peersWithCopy"))
+ {
+ peersWithCopy.clear();
+ String[] peers = state.getValuesOrThrow("peersWithCopy").split(",");
+ for (String peer: peers)
+ {
+ peersWithCopy.add(new ObjectID(Long.parseUnsignedLong(peer,16)));
+ }
+ }
}
@Override
@@ -124,7 +140,8 @@ public class NetworkFile extends NetworkFSNode
// .putValues("path", path)
.putValues("size", Long.toString(size))
.putValues("hash", HexFormat.of().formatHex(hash))
- .putValues("pieceSize", Long.toString(pieceSize));
+ .putValues("pieceSize", Long.toString(pieceSize))
+ .putValues("peersWithCopy", peersWithCopy.stream().map(ObjectID::toLong).map(Long::toHexString).collect(Collectors.joining(",")));
}
@Override
@@ -136,6 +153,7 @@ public class NetworkFile extends NetworkFSNode
ret.put("pieceSize", pieceSize);
ret.put("pieces", Arrays.stream(pieces.toLongArray()).boxed().toList());
ret.put("localFile", localFile != null ? localFile.getAbsolutePath() : "");
+ ret.put("peersWithCopy", peersWithCopy.stream().map(ObjectID::toLong).toList());
return ret;
}
@@ -146,13 +164,14 @@ public class NetworkFile extends NetworkFSNode
size = ((Number) map.get("size")).longValue();
hash = HexFormat.of().parseHex((CharSequence) map.get("hash"));
pieceSize = ((Number) map.get("pieceSize")).longValue();
- ArrayList pieces1 = (ArrayList) map.get("pieces");
- pieces = BitSet.valueOf(pieces1.stream().mapToLong(Number::longValue).toArray());
+ pieces = BitSet.valueOf(((ArrayList) map.get("pieces")).stream().mapToLong(Number::longValue).toArray());
String localFilePath = (String) map.get("localFile");
if (localFilePath.isEmpty())
localFile = null;
else
localFile = new File(localFilePath);
+ peersWithCopy.clear();
+ peersWithCopy.addAll(((List