package peergos.server.storage;
import peergos.shared.cbor.*;
import peergos.shared.crypto.asymmetric.*;
import peergos.shared.io.ipfs.multiaddr.MultiAddress;
import peergos.shared.io.ipfs.multihash.Multihash;
import peergos.shared.storage.ContentAddressedStorage;
import java.io.*;
import java.util.*;
import java.util.concurrent.*;
import java.util.stream.*;
public class IpfsDHT implements ContentAddressedStorage {
private final IPFS ipfs;
public IpfsDHT(IPFS ipfs) {
this.ipfs = ipfs;
try {
// test connectivity
ipfs.object._new(Optional.empty());
} catch (IOException e) {
throw new RuntimeException(e);
}
}
public IpfsDHT() {
this(new IPFS(new MultiAddress("/ip4/127.0.0.1/tcp/5001")));
}
@Override
public CompletableFuture<List<Multihash>> put(PublicSigningKey writer, List<byte[]> blocks) {
try {
return CompletableFuture.completedFuture(ipfs.block.put(blocks, Optional.of("cbor")))
.thenApply(nodes -> nodes.stream().map(n -> n.hash).collect(Collectors.toList()));
} catch (IOException e) {
throw new RuntimeException(e);
}
}
@Override
public CompletableFuture<Optional<CborObject>> get(Multihash hash) {
try {
byte[] raw = ipfs.block.get(hash);
return CompletableFuture.completedFuture(Optional.of(CborObject.fromByteArray(raw)));
} catch (IOException e) {
throw new RuntimeException(e);
}
}
@Override
public CompletableFuture<List<Multihash>> recursivePin(Multihash h) {
try {
List<Multihash> added = ipfs.pin.add(h);
return CompletableFuture.completedFuture(added);
} catch (IOException e) {
throw new RuntimeException(e);
}
}
@Override
public CompletableFuture<List<Multihash>> recursiveUnpin(Multihash h) {
try {
List<Multihash> removed = ipfs.pin.rm(h, true);
return CompletableFuture.completedFuture(removed);
} catch (IOException e) {
throw new RuntimeException(e);
}
}
@Override
public CompletableFuture<List<Multihash>> getLinks(Multihash root) {
CompletableFuture<List<Multihash>> res = new CompletableFuture<>();
try {
res.complete(ipfs.refs(root, false));
} catch (IOException e) {
res.completeExceptionally(e);
}
return res;
}
@Override
public CompletableFuture<Optional<Integer>> getSize(Multihash block) {
CompletableFuture<Optional<Integer>> res = new CompletableFuture<>();
try {
res.complete(Optional.of((Integer)ipfs.block.stat(block).get("Size")));
} catch (IOException e) {
res.completeExceptionally(e);
}
return res;
}
}