parse open/close initiator

This commit is contained in:
Carsten Otto
2021-11-17 22:48:16 +01:00
parent 6d80886a84
commit f33138c645
41 changed files with 989 additions and 371 deletions

View File

@@ -3,6 +3,7 @@ package de.cotto.lndmanagej.service;
import com.google.common.cache.LoadingCache;
import de.cotto.lndmanagej.caching.CacheBuilder;
import de.cotto.lndmanagej.grpc.GrpcChannels;
import de.cotto.lndmanagej.grpc.GrpcClosedChannels;
import de.cotto.lndmanagej.model.ClosedChannel;
import de.cotto.lndmanagej.model.ForceClosingChannel;
import de.cotto.lndmanagej.model.LocalChannel;
@@ -25,13 +26,13 @@ public class ChannelService {
private final LoadingCache<Object, Set<ForceClosingChannel>> forceClosingChannelsCache;
private final LoadingCache<Object, Set<WaitingCloseChannel>> waitingCloseChannelsCache;
public ChannelService(GrpcChannels grpcChannels) {
public ChannelService(GrpcChannels grpcChannels, GrpcClosedChannels grpcClosedChannels) {
channelsCache = new CacheBuilder()
.withExpiryMinutes(CACHE_EXPIRY_MINUTES)
.build(grpcChannels::getChannels);
closedChannelsCache = new CacheBuilder()
.withExpiryMinutes(CACHE_EXPIRY_MINUTES)
.build(grpcChannels::getClosedChannels);
.build(grpcClosedChannels::getClosedChannels);
forceClosingChannelsCache = new CacheBuilder()
.withExpiryMinutes(CACHE_EXPIRY_MINUTES)
.build(grpcChannels::getForceClosingChannels);

View File

@@ -1,6 +1,7 @@
package de.cotto.lndmanagej.service;
import de.cotto.lndmanagej.grpc.GrpcChannels;
import de.cotto.lndmanagej.grpc.GrpcClosedChannels;
import org.junit.jupiter.api.Test;
import org.junit.jupiter.api.extension.ExtendWith;
import org.mockito.InjectMocks;
@@ -35,6 +36,9 @@ class ChannelServiceTest {
@Mock
private GrpcChannels grpcChannels;
@Mock
private GrpcClosedChannels grpcClosedChannels;
@Test
void getOpenChannelsWith_by_pubkey() {
when(grpcChannels.getChannels()).thenReturn(Set.of(LOCAL_OPEN_CHANNEL, LOCAL_OPEN_CHANNEL_3));
@@ -60,7 +64,7 @@ class ChannelServiceTest {
@Test
void getClosedChannels() {
when(grpcChannels.getClosedChannels())
when(grpcClosedChannels.getClosedChannels())
.thenReturn(Set.of(CLOSED_CHANNEL, CLOSED_CHANNEL_2));
assertThat(channelService.getClosedChannels())
.containsExactlyInAnyOrder(CLOSED_CHANNEL, CLOSED_CHANNEL_2);
@@ -89,7 +93,7 @@ class ChannelServiceTest {
when(grpcChannels.getChannels()).thenReturn(Set.of(LOCAL_OPEN_CHANNEL, LOCAL_OPEN_CHANNEL_TO_NODE_3));
when(grpcChannels.getForceClosingChannels())
.thenReturn(Set.of(FORCE_CLOSING_CHANNEL, FORCE_CLOSING_CHANNEL_TO_NODE_3));
when(grpcChannels.getClosedChannels())
when(grpcClosedChannels.getClosedChannels())
.thenReturn(Set.of(CLOSED_CHANNEL_3, CLOSED_CHANNEL_TO_NODE_3));
assertThat(channelService.getAllChannelsWith(PUBKEY_2)).containsExactlyInAnyOrder(

View File

@@ -23,6 +23,7 @@ import static de.cotto.lndmanagej.model.CoopClosedChannelFixtures.CLOSED_CHANNEL
import static de.cotto.lndmanagej.model.ForceClosingChannelFixtures.FORCE_CLOSING_CHANNEL;
import static de.cotto.lndmanagej.model.LocalOpenChannelFixtures.LOCAL_OPEN_CHANNEL;
import static de.cotto.lndmanagej.model.LocalOpenChannelFixtures.LOCAL_OPEN_CHANNEL_2;
import static de.cotto.lndmanagej.model.OpenInitiator.LOCAL;
import static de.cotto.lndmanagej.model.PubkeyFixtures.PUBKEY;
import static de.cotto.lndmanagej.model.PubkeyFixtures.PUBKEY_2;
import static de.cotto.lndmanagej.model.WaitingCloseChannelFixtures.WAITING_CLOSE_CHANNEL;
@@ -135,12 +136,33 @@ class TransactionBackgroundLoaderTest {
@Test
void update_one_unknown() {
LocalOpenChannel channel1 =
new LocalOpenChannel(CHANNEL_ID, CHANNEL_POINT, CAPACITY, PUBKEY, PUBKEY_2, BALANCE_INFORMATION);
LocalOpenChannel channel2 =
new LocalOpenChannel(CHANNEL_ID_2, CHANNEL_POINT_2, CAPACITY, PUBKEY, PUBKEY_2, BALANCE_INFORMATION);
LocalOpenChannel channel3 =
new LocalOpenChannel(CHANNEL_ID_3, CHANNEL_POINT_3, CAPACITY, PUBKEY, PUBKEY_2, BALANCE_INFORMATION);
LocalOpenChannel channel1 = new LocalOpenChannel(
CHANNEL_ID,
CHANNEL_POINT,
CAPACITY,
PUBKEY,
PUBKEY_2,
BALANCE_INFORMATION,
LOCAL
);
LocalOpenChannel channel2 = new LocalOpenChannel(
CHANNEL_ID_2,
CHANNEL_POINT_2,
CAPACITY,
PUBKEY,
PUBKEY_2,
BALANCE_INFORMATION,
LOCAL
);
LocalOpenChannel channel3 = new LocalOpenChannel(
CHANNEL_ID_3,
CHANNEL_POINT_3,
CAPACITY,
PUBKEY,
PUBKEY_2,
BALANCE_INFORMATION,
LOCAL
);
when(channelService.getOpenChannels()).thenReturn(Set.of(channel1, channel2, channel3));
String unknownHash = CHANNEL_POINT_3.getTransactionHash();
when(transactionService.isUnknown(any())).thenReturn(false);

View File

@@ -14,17 +14,14 @@ jacocoTestCoverageVerification {
violationRules {
rules.forEach {rule ->
rule.limits.forEach {limit ->
if (limit.counter == 'CLASS') {
limit.minimum = 0.6
}
if (limit.counter == 'INSTRUCTION') {
limit.minimum = 0.61
limit.minimum = 0.83
}
if (limit.counter == 'METHOD') {
limit.minimum = 0.78
limit.minimum = 0.8
}
if (limit.counter == 'BRANCH') {
limit.minimum = 0.94
limit.minimum = 0.92
}
}
}

View File

@@ -15,7 +15,7 @@ public class GrpcBase {
protected final StubCreator stubCreator;
@SuppressWarnings("PMD.ConstructorCallsOverridableMethod")
public GrpcBase(LndConfiguration lndConfiguration) throws IOException {
protected GrpcBase(LndConfiguration lndConfiguration) throws IOException {
stubCreator = getStubCreator(lndConfiguration);
}

View File

@@ -4,17 +4,13 @@ import de.cotto.lndmanagej.model.BalanceInformation;
import de.cotto.lndmanagej.model.ChannelId;
import de.cotto.lndmanagej.model.ChannelIdResolver;
import de.cotto.lndmanagej.model.ChannelPoint;
import de.cotto.lndmanagej.model.CloseType;
import de.cotto.lndmanagej.model.ClosedChannel;
import de.cotto.lndmanagej.model.Coins;
import de.cotto.lndmanagej.model.CoopClosedChannel;
import de.cotto.lndmanagej.model.ForceClosedChannel;
import de.cotto.lndmanagej.model.ForceClosingChannel;
import de.cotto.lndmanagej.model.LocalOpenChannel;
import de.cotto.lndmanagej.model.OpenInitiator;
import de.cotto.lndmanagej.model.Pubkey;
import de.cotto.lndmanagej.model.WaitingCloseChannel;
import lnrpc.ChannelCloseSummary;
import lnrpc.ChannelCloseSummary.ClosureType;
import lnrpc.Channel;
import lnrpc.PendingChannelsResponse;
import lnrpc.PendingChannelsResponse.PendingChannel;
import lnrpc.PendingHTLC;
@@ -26,19 +22,18 @@ import java.util.Set;
import static java.util.stream.Collectors.toSet;
@Component
public class GrpcChannels {
public class GrpcChannels extends GrpcChannelsBase {
private final GrpcService grpcService;
private final GrpcGetInfo grpcGetInfo;
private final ChannelIdResolver channelIdResolver;
public GrpcChannels(
GrpcService grpcService,
GrpcGetInfo grpcGetInfo,
ChannelIdResolver channelIdResolver
) {
super(channelIdResolver);
this.grpcService = grpcService;
this.grpcGetInfo = grpcGetInfo;
this.channelIdResolver = channelIdResolver;
}
public Set<LocalOpenChannel> getChannels() {
@@ -48,15 +43,6 @@ public class GrpcChannels {
.collect(toSet());
}
public Set<ClosedChannel> getClosedChannels() {
Pubkey ownPubkey = grpcGetInfo.getPubkey();
return grpcService.getClosedChannels().stream()
.filter(this::hasSupportedCloseType)
.map(channelCloseSummary -> toClosedChannel(channelCloseSummary, ownPubkey))
.flatMap(Optional::stream)
.collect(toSet());
}
public Set<ForceClosingChannel> getForceClosingChannels() {
Pubkey ownPubkey = grpcGetInfo.getPubkey();
return grpcService.getForceClosingChannels().stream()
@@ -73,47 +59,6 @@ public class GrpcChannels {
.collect(toSet());
}
private Optional<WaitingCloseChannel> toWaitingCloseChannel(
PendingChannelsResponse.WaitingCloseChannel waitingCloseChannel,
Pubkey ownPubkey
) {
PendingChannel pendingChannel = waitingCloseChannel.getChannel();
ChannelPoint channelPoint = ChannelPoint.create(pendingChannel.getChannelPoint());
return channelIdResolver.resolveFromChannelPoint(channelPoint)
.map(id -> new WaitingCloseChannel(
id,
channelPoint,
Coins.ofSatoshis(pendingChannel.getCapacity()),
ownPubkey,
Pubkey.create(pendingChannel.getRemoteNodePub())
));
}
private Optional<ForceClosingChannel> toForceClosingChannel(
PendingChannelsResponse.ForceClosedChannel forceClosedChannel,
Pubkey ownPubkey
) {
PendingChannel pendingChannel = forceClosedChannel.getChannel();
ChannelPoint channelPoint = ChannelPoint.create(pendingChannel.getChannelPoint());
return channelIdResolver.resolveFromChannelPoint(channelPoint)
.map(id -> new ForceClosingChannel(
id,
channelPoint,
Coins.ofSatoshis(pendingChannel.getCapacity()),
ownPubkey,
Pubkey.create(pendingChannel.getRemoteNodePub()),
forceClosedChannel.getClosingTxid(),
getHtlcOutpoints(forceClosedChannel)
));
}
private Set<ChannelPoint> getHtlcOutpoints(PendingChannelsResponse.ForceClosedChannel forceClosedChannel) {
return forceClosedChannel.getPendingHtlcsList().stream()
.map(PendingHTLC::getOutpoint)
.map(ChannelPoint::create)
.collect(toSet());
}
public Optional<LocalOpenChannel> getChannel(ChannelId channelId) {
Pubkey ownPubkey = grpcGetInfo.getPubkey();
long expectedChannelId = channelId.getShortChannelId();
@@ -123,77 +68,69 @@ public class GrpcChannels {
.findFirst();
}
private LocalOpenChannel toLocalOpenChannel(lnrpc.Channel lndChannel, Pubkey ownPubkey) {
ChannelId channelId = ChannelId.fromShortChannelId(lndChannel.getChanId());
ChannelPoint channelPoint = ChannelPoint.create(lndChannel.getChannelPoint());
Pubkey remotePubkey = Pubkey.create(lndChannel.getRemotePubkey());
Coins capacity = Coins.ofSatoshis(lndChannel.getCapacity());
private Optional<WaitingCloseChannel> toWaitingCloseChannel(
PendingChannelsResponse.WaitingCloseChannel waitingCloseChannel,
Pubkey ownPubkey
) {
PendingChannel pendingChannel = waitingCloseChannel.getChannel();
ChannelPoint channelPoint = ChannelPoint.create(pendingChannel.getChannelPoint());
return resolveChannelId(channelPoint).map(id -> new WaitingCloseChannel(
id,
channelPoint,
Coins.ofSatoshis(pendingChannel.getCapacity()),
ownPubkey,
Pubkey.create(pendingChannel.getRemoteNodePub()),
getOpenInitiator(pendingChannel.getInitiator())
));
}
private Optional<ForceClosingChannel> toForceClosingChannel(
PendingChannelsResponse.ForceClosedChannel forceClosedChannel,
Pubkey ownPubkey
) {
PendingChannel pendingChannel = forceClosedChannel.getChannel();
ChannelPoint channelPoint = ChannelPoint.create(pendingChannel.getChannelPoint());
return resolveChannelId(channelPoint).map(id -> new ForceClosingChannel(
id,
channelPoint,
Coins.ofSatoshis(pendingChannel.getCapacity()),
ownPubkey,
Pubkey.create(pendingChannel.getRemoteNodePub()),
forceClosedChannel.getClosingTxid(),
getHtlcOutpoints(forceClosedChannel),
getOpenInitiator(pendingChannel.getInitiator())
));
}
private Set<ChannelPoint> getHtlcOutpoints(PendingChannelsResponse.ForceClosedChannel forceClosedChannel) {
return forceClosedChannel.getPendingHtlcsList().stream()
.map(PendingHTLC::getOutpoint)
.map(ChannelPoint::create)
.collect(toSet());
}
private LocalOpenChannel toLocalOpenChannel(Channel lndChannel, Pubkey ownPubkey) {
BalanceInformation balanceInformation = new BalanceInformation(
Coins.ofSatoshis(lndChannel.getLocalBalance()),
Coins.ofSatoshis(lndChannel.getLocalConstraints().getChanReserveSat()),
Coins.ofSatoshis(lndChannel.getRemoteBalance()),
Coins.ofSatoshis(lndChannel.getRemoteConstraints().getChanReserveSat())
);
return new LocalOpenChannel(channelId, channelPoint, capacity, ownPubkey, remotePubkey, balanceInformation);
return new LocalOpenChannel(
ChannelId.fromShortChannelId(lndChannel.getChanId()),
ChannelPoint.create(lndChannel.getChannelPoint()),
Coins.ofSatoshis(lndChannel.getCapacity()),
ownPubkey,
Pubkey.create(lndChannel.getRemotePubkey()),
balanceInformation,
getOpenInitiator(lndChannel)
);
}
private Optional<ClosedChannel> toClosedChannel(
ChannelCloseSummary channelCloseSummary,
Pubkey ownPubkey
) {
ChannelPoint channelPoint = ChannelPoint.create(channelCloseSummary.getChannelPoint());
Pubkey remotePubkey = Pubkey.create(channelCloseSummary.getRemotePubkey());
Coins capacity = Coins.ofSatoshis(channelCloseSummary.getCapacity());
Optional<ChannelId> optionalChannelId = getChannelId(channelCloseSummary)
.or(() -> channelIdResolver.resolveFromChannelPoint(channelPoint));
ClosureType closureType = channelCloseSummary.getCloseType();
if (closureType.equals(ClosureType.COOPERATIVE_CLOSE)) {
return optionalChannelId
.map(id -> new CoopClosedChannel(
id,
channelPoint,
capacity,
ownPubkey,
remotePubkey,
channelCloseSummary.getClosingTxHash()
));
private OpenInitiator getOpenInitiator(Channel lndChannel) {
if (lndChannel.getInitiator()) {
return OpenInitiator.LOCAL;
}
return optionalChannelId
.map(id -> new ForceClosedChannel(
id,
channelPoint,
capacity,
ownPubkey,
remotePubkey,
channelCloseSummary.getClosingTxHash(),
getCloseType(closureType)
));
}
private CloseType getCloseType(ClosureType closureType) {
CloseType closeType;
if (closureType.equals(ClosureType.REMOTE_FORCE_CLOSE)) {
closeType = CloseType.REMOTE;
} else if (closureType.equals(ClosureType.LOCAL_FORCE_CLOSE)) {
closeType = CloseType.LOCAL;
} else if (closureType.equals(ClosureType.BREACH_CLOSE)) {
closeType = CloseType.BREACH;
} else {
throw new IllegalStateException("unexpected close type: " + closureType);
}
return closeType;
}
private Optional<ChannelId> getChannelId(ChannelCloseSummary channelCloseSummary) {
long chanId = channelCloseSummary.getChanId();
if (chanId == 0) {
return Optional.empty();
}
return Optional.of(ChannelId.fromShortChannelId(chanId));
}
private boolean hasSupportedCloseType(ChannelCloseSummary channelCloseSummary) {
ClosureType closeType = channelCloseSummary.getCloseType();
return closeType != ClosureType.ABANDONED && closeType != ClosureType.FUNDING_CANCELED;
return OpenInitiator.REMOTE;
}
}

View File

@@ -0,0 +1,44 @@
package de.cotto.lndmanagej.grpc;
import de.cotto.lndmanagej.model.ChannelId;
import de.cotto.lndmanagej.model.ChannelIdResolver;
import de.cotto.lndmanagej.model.ChannelPoint;
import de.cotto.lndmanagej.model.OpenInitiator;
import lnrpc.Initiator;
import java.util.Optional;
import static lnrpc.Initiator.INITIATOR_LOCAL;
import static lnrpc.Initiator.INITIATOR_REMOTE;
import static lnrpc.Initiator.INITIATOR_UNKNOWN;
public class GrpcChannelsBase {
private final ChannelIdResolver channelIdResolver;
protected GrpcChannelsBase(ChannelIdResolver channelIdResolver) {
this.channelIdResolver = channelIdResolver;
}
OpenInitiator getOpenInitiator(Initiator openInitiator) {
if (openInitiator.equals(INITIATOR_LOCAL)) {
return OpenInitiator.LOCAL;
} else if (openInitiator.equals(INITIATOR_REMOTE)) {
return OpenInitiator.REMOTE;
} else if (openInitiator.equals(INITIATOR_UNKNOWN)) {
return OpenInitiator.UNKNOWN;
}
throw new IllegalStateException("unexpected open initiator: " + openInitiator);
}
Optional<ChannelId> getChannelId(long chanId, ChannelPoint channelPoint) {
if (chanId == 0) {
return resolveChannelId(channelPoint);
}
return Optional.of(ChannelId.fromShortChannelId(chanId));
}
Optional<ChannelId> resolveChannelId(ChannelPoint channelPoint) {
return channelIdResolver.resolveFromChannelPoint(channelPoint);
}
}

View File

@@ -0,0 +1,97 @@
package de.cotto.lndmanagej.grpc;
import de.cotto.lndmanagej.model.BreachForceClosedChannelBuilder;
import de.cotto.lndmanagej.model.ChannelIdResolver;
import de.cotto.lndmanagej.model.ChannelPoint;
import de.cotto.lndmanagej.model.CloseInitiator;
import de.cotto.lndmanagej.model.ClosedChannel;
import de.cotto.lndmanagej.model.ClosedChannelBuilder;
import de.cotto.lndmanagej.model.Coins;
import de.cotto.lndmanagej.model.CoopClosedChannelBuilder;
import de.cotto.lndmanagej.model.ForceClosedChannelBuilder;
import de.cotto.lndmanagej.model.Pubkey;
import lnrpc.ChannelCloseSummary;
import lnrpc.ChannelCloseSummary.ClosureType;
import lnrpc.Initiator;
import org.springframework.stereotype.Component;
import java.util.Optional;
import java.util.Set;
import static java.util.stream.Collectors.toSet;
import static lnrpc.ChannelCloseSummary.ClosureType.LOCAL_FORCE_CLOSE;
import static lnrpc.ChannelCloseSummary.ClosureType.REMOTE_FORCE_CLOSE;
import static lnrpc.Initiator.INITIATOR_LOCAL;
import static lnrpc.Initiator.INITIATOR_REMOTE;
import static lnrpc.Initiator.INITIATOR_UNKNOWN;
@Component
public class GrpcClosedChannels extends GrpcChannelsBase {
private final GrpcService grpcService;
private final GrpcGetInfo grpcGetInfo;
public GrpcClosedChannels(
GrpcService grpcService,
GrpcGetInfo grpcGetInfo,
ChannelIdResolver channelIdResolver
) {
super(channelIdResolver);
this.grpcService = grpcService;
this.grpcGetInfo = grpcGetInfo;
}
public Set<ClosedChannel> getClosedChannels() {
Pubkey ownPubkey = grpcGetInfo.getPubkey();
return grpcService.getClosedChannels().stream()
.filter(this::hasSupportedCloseType)
.map(channelCloseSummary -> toClosedChannel(channelCloseSummary, ownPubkey))
.flatMap(Optional::stream)
.collect(toSet());
}
private boolean hasSupportedCloseType(ChannelCloseSummary channelCloseSummary) {
ClosureType closeType = channelCloseSummary.getCloseType();
return closeType != ClosureType.ABANDONED && closeType != ClosureType.FUNDING_CANCELED;
}
private Optional<ClosedChannel> toClosedChannel(
ChannelCloseSummary channelCloseSummary,
Pubkey ownPubkey
) {
ClosureType closureType = channelCloseSummary.getCloseType();
CloseInitiator closeInitiator = getCloseInitiator(channelCloseSummary);
ClosedChannelBuilder<? extends ClosedChannel> builder;
if (closureType.equals(ClosureType.COOPERATIVE_CLOSE)) {
builder = new CoopClosedChannelBuilder().withCloseInitiator(closeInitiator);
} else if (closureType.equals(ClosureType.BREACH_CLOSE)) {
builder = new BreachForceClosedChannelBuilder();
} else {
builder = new ForceClosedChannelBuilder().withCloseInitiator(closeInitiator);
}
ChannelPoint channelPoint = ChannelPoint.create(channelCloseSummary.getChannelPoint());
return getChannelId(channelCloseSummary.getChanId(), channelPoint)
.map(channelId -> builder
.withChannelId(channelId)
.withChannelPoint(channelPoint)
.withCapacity(Coins.ofSatoshis(channelCloseSummary.getCapacity()))
.withOwnPubkey(ownPubkey)
.withRemotePubkey(Pubkey.create(channelCloseSummary.getRemotePubkey()))
.withCloseTransactionHash(channelCloseSummary.getClosingTxHash())
.withOpenInitiator(getOpenInitiator(channelCloseSummary.getOpenInitiator()))
.build()
);
}
CloseInitiator getCloseInitiator(ChannelCloseSummary channelCloseSummary) {
Initiator closeInitiator = channelCloseSummary.getCloseInitiator();
ChannelCloseSummary.ClosureType closureType = channelCloseSummary.getCloseType();
if (closeInitiator.equals(INITIATOR_LOCAL) || closureType.equals(LOCAL_FORCE_CLOSE)) {
return CloseInitiator.LOCAL;
} else if (closeInitiator.equals(INITIATOR_REMOTE) || closureType.equals(REMOTE_FORCE_CLOSE)) {
return CloseInitiator.REMOTE;
} else if (closeInitiator.equals(INITIATOR_UNKNOWN)) {
return CloseInitiator.UNKNOWN;
}
throw new IllegalStateException("unexpected close initiator: " + closeInitiator);
}
}

View File

@@ -0,0 +1,73 @@
package de.cotto.lndmanagej.grpc;
import de.cotto.lndmanagej.model.ChannelIdResolver;
import de.cotto.lndmanagej.model.OpenInitiator;
import lnrpc.Initiator;
import org.junit.jupiter.api.Test;
import org.junit.jupiter.api.extension.ExtendWith;
import org.mockito.InjectMocks;
import org.mockito.Mock;
import org.mockito.junit.jupiter.MockitoExtension;
import java.util.Optional;
import static de.cotto.lndmanagej.model.ChannelIdFixtures.CHANNEL_ID;
import static de.cotto.lndmanagej.model.ChannelIdFixtures.CHANNEL_ID_2;
import static de.cotto.lndmanagej.model.ChannelPointFixtures.CHANNEL_POINT;
import static org.assertj.core.api.Assertions.assertThat;
import static org.mockito.ArgumentMatchers.any;
import static org.mockito.Mockito.never;
import static org.mockito.Mockito.verify;
import static org.mockito.Mockito.when;
@ExtendWith(MockitoExtension.class)
class GrpcChannelsBaseTest {
@InjectMocks
private GrpcChannelsBase grpcChannelsBase;
@Mock
private ChannelIdResolver channelIdResolver;
@Test
void getOpenInitiator_unknown() {
assertThat(grpcChannelsBase.getOpenInitiator(Initiator.INITIATOR_UNKNOWN)).isEqualTo(OpenInitiator.UNKNOWN);
}
@Test
void getOpenInitiator_local() {
assertThat(grpcChannelsBase.getOpenInitiator(Initiator.INITIATOR_LOCAL)).isEqualTo(OpenInitiator.LOCAL);
}
@Test
void getOpenInitiator_remote() {
assertThat(grpcChannelsBase.getOpenInitiator(Initiator.INITIATOR_REMOTE)).isEqualTo(OpenInitiator.REMOTE);
}
@Test
void getChannelId_already_resolved() {
assertThat(grpcChannelsBase.getChannelId(CHANNEL_ID.getShortChannelId(), CHANNEL_POINT)).contains(CHANNEL_ID);
verify(channelIdResolver, never()).resolveFromChannelPoint(any());
}
@Test
void getChannelId_resolved() {
when(channelIdResolver.resolveFromChannelPoint(CHANNEL_POINT)).thenReturn(Optional.of(CHANNEL_ID_2));
assertThat(grpcChannelsBase.getChannelId(0, CHANNEL_POINT)).contains(CHANNEL_ID_2);
}
@Test
void getChannelId_not_resolved() {
assertThat(grpcChannelsBase.getChannelId(0, CHANNEL_POINT)).isEmpty();
}
@Test
void resolveChannelId_resolved() {
when(channelIdResolver.resolveFromChannelPoint(CHANNEL_POINT)).thenReturn(Optional.of(CHANNEL_ID_2));
assertThat(grpcChannelsBase.resolveChannelId(CHANNEL_POINT)).contains(CHANNEL_ID_2);
}
@Test
void resolveChannelId_not_resolved() {
assertThat(grpcChannelsBase.resolveChannelId(CHANNEL_POINT)).isEmpty();
}
}

View File

@@ -4,8 +4,8 @@ import de.cotto.lndmanagej.model.ChannelId;
import de.cotto.lndmanagej.model.ChannelIdResolver;
import de.cotto.lndmanagej.model.ChannelPoint;
import lnrpc.Channel;
import lnrpc.ChannelCloseSummary;
import lnrpc.ChannelConstraints;
import lnrpc.Initiator;
import lnrpc.PendingChannelsResponse;
import lnrpc.PendingChannelsResponse.ForceClosedChannel;
import lnrpc.PendingHTLC;
@@ -23,18 +23,10 @@ import static de.cotto.lndmanagej.model.BalanceInformationFixtures.BALANCE_INFOR
import static de.cotto.lndmanagej.model.ChannelFixtures.CAPACITY;
import static de.cotto.lndmanagej.model.ChannelIdFixtures.CHANNEL_ID;
import static de.cotto.lndmanagej.model.ChannelIdFixtures.CHANNEL_ID_2;
import static de.cotto.lndmanagej.model.ChannelIdFixtures.CHANNEL_ID_3;
import static de.cotto.lndmanagej.model.ChannelPointFixtures.CHANNEL_POINT;
import static de.cotto.lndmanagej.model.ChannelPointFixtures.CHANNEL_POINT_2;
import static de.cotto.lndmanagej.model.ChannelPointFixtures.CHANNEL_POINT_3;
import static de.cotto.lndmanagej.model.ChannelPointFixtures.TRANSACTION_HASH_2;
import static de.cotto.lndmanagej.model.ChannelPointFixtures.TRANSACTION_HASH_3;
import static de.cotto.lndmanagej.model.CoopClosedChannelFixtures.CLOSED_CHANNEL;
import static de.cotto.lndmanagej.model.CoopClosedChannelFixtures.CLOSED_CHANNEL_2;
import static de.cotto.lndmanagej.model.CoopClosedChannelFixtures.CLOSED_CHANNEL_3;
import static de.cotto.lndmanagej.model.ForceClosedChannelFixtures.FORCE_CLOSED_CHANNEL_BREACH;
import static de.cotto.lndmanagej.model.ForceClosedChannelFixtures.FORCE_CLOSED_CHANNEL_LOCAL;
import static de.cotto.lndmanagej.model.ForceClosedChannelFixtures.FORCE_CLOSED_CHANNEL_REMOTE;
import static de.cotto.lndmanagej.model.ForceClosingChannelFixtures.FORCE_CLOSING_CHANNEL;
import static de.cotto.lndmanagej.model.ForceClosingChannelFixtures.FORCE_CLOSING_CHANNEL_2;
import static de.cotto.lndmanagej.model.ForceClosingChannelFixtures.HTLC_OUTPOINT;
@@ -44,16 +36,7 @@ import static de.cotto.lndmanagej.model.PubkeyFixtures.PUBKEY;
import static de.cotto.lndmanagej.model.PubkeyFixtures.PUBKEY_2;
import static de.cotto.lndmanagej.model.WaitingCloseChannelFixtures.WAITING_CLOSE_CHANNEL;
import static de.cotto.lndmanagej.model.WaitingCloseChannelFixtures.WAITING_CLOSE_CHANNEL_2;
import static lnrpc.ChannelCloseSummary.ClosureType.ABANDONED;
import static lnrpc.ChannelCloseSummary.ClosureType.BREACH_CLOSE;
import static lnrpc.ChannelCloseSummary.ClosureType.COOPERATIVE_CLOSE;
import static lnrpc.ChannelCloseSummary.ClosureType.FUNDING_CANCELED;
import static lnrpc.ChannelCloseSummary.ClosureType.LOCAL_FORCE_CLOSE;
import static lnrpc.ChannelCloseSummary.ClosureType.REMOTE_FORCE_CLOSE;
import static org.assertj.core.api.Assertions.assertThat;
import static org.mockito.ArgumentMatchers.any;
import static org.mockito.Mockito.never;
import static org.mockito.Mockito.verify;
import static org.mockito.Mockito.when;
@ExtendWith(MockitoExtension.class)
@@ -82,52 +65,13 @@ class GrpcChannelsTest {
@Test
void getChannels() {
when(grpcService.getChannels()).thenReturn(List.of(channel(CHANNEL_ID), channel(CHANNEL_ID_2)));
when(grpcService.getChannels()).thenReturn(List.of(
channel(CHANNEL_ID, true),
channel(CHANNEL_ID_2, false)
));
assertThat(grpcChannels.getChannels()).containsExactlyInAnyOrder(LOCAL_OPEN_CHANNEL, LOCAL_OPEN_CHANNEL_2);
}
@Test
void getClosedChannels_empty() {
assertThat(grpcChannels.getClosedChannels()).isEmpty();
}
@Test
void getClosedChannels() {
when(grpcService.getClosedChannels()).thenReturn(
List.of(
closedChannel(CHANNEL_ID.getShortChannelId(), COOPERATIVE_CLOSE),
closedChannel(CHANNEL_ID_2.getShortChannelId(), COOPERATIVE_CLOSE)
)
);
assertThat(grpcChannels.getClosedChannels())
.containsExactlyInAnyOrder(CLOSED_CHANNEL, CLOSED_CHANNEL_2);
verify(channelIdResolver, never()).resolveFromChannelPoint(any());
}
@Test
void getClosedChannels_force_closed_local() {
when(grpcService.getClosedChannels())
.thenReturn(List.of(closedChannel(CHANNEL_ID.getShortChannelId(), LOCAL_FORCE_CLOSE)));
assertThat(grpcChannels.getClosedChannels())
.containsExactlyInAnyOrder(FORCE_CLOSED_CHANNEL_LOCAL);
}
@Test
void getClosedChannels_force_closed_remote() {
when(grpcService.getClosedChannels())
.thenReturn(List.of(closedChannel(CHANNEL_ID.getShortChannelId(), REMOTE_FORCE_CLOSE)));
assertThat(grpcChannels.getClosedChannels())
.containsExactlyInAnyOrder(FORCE_CLOSED_CHANNEL_REMOTE);
}
@Test
void getClosedChannels_force_closed_breach_detected() {
when(grpcService.getClosedChannels())
.thenReturn(List.of(closedChannel(CHANNEL_ID.getShortChannelId(), BREACH_CLOSE)));
assertThat(grpcChannels.getClosedChannels())
.containsExactlyInAnyOrder(FORCE_CLOSED_CHANNEL_BREACH);
}
@Test
void getForceClosingChannels_both_resolved() {
when(channelIdResolver.resolveFromChannelPoint(CHANNEL_POINT)).thenReturn(Optional.of(CHANNEL_ID));
@@ -168,49 +112,12 @@ class GrpcChannelsTest {
assertThat(grpcChannels.getWaitingCloseChannels()).containsExactlyInAnyOrder(WAITING_CLOSE_CHANNEL);
}
@Test
void getClosedChannels_with_zero_channel_id_not_resolved() {
when(grpcService.getClosedChannels()).thenReturn(List.of(
closedChannel(CHANNEL_ID.getShortChannelId(), COOPERATIVE_CLOSE),
closedChannel(0, COOPERATIVE_CLOSE)
));
assertThat(grpcChannels.getClosedChannels()).containsExactlyInAnyOrder(CLOSED_CHANNEL);
verify(channelIdResolver).resolveFromChannelPoint(CHANNEL_POINT);
}
@Test
void getClosedChannels_with_zero_channel_id_resolved() {
when(channelIdResolver.resolveFromChannelPoint(CHANNEL_POINT)).thenReturn(Optional.of(CHANNEL_ID_3));
when(grpcService.getClosedChannels()).thenReturn(List.of(
closedChannel(CHANNEL_ID.getShortChannelId(), COOPERATIVE_CLOSE),
closedChannel(0, COOPERATIVE_CLOSE)
));
assertThat(grpcChannels.getClosedChannels()).containsExactlyInAnyOrder(CLOSED_CHANNEL, CLOSED_CHANNEL_3);
}
@Test
void getClosedChannels_ignores_abandoned() {
when(grpcService.getClosedChannels()).thenReturn(List.of(
closedChannel(CHANNEL_ID.getShortChannelId(),
COOPERATIVE_CLOSE), closedChannelWithType(ABANDONED)
));
assertThat(grpcChannels.getClosedChannels()).containsExactlyInAnyOrder(CLOSED_CHANNEL);
verify(channelIdResolver, never()).resolveFromChannelPoint(any());
}
@Test
void getClosedChannels_ignores_funding_canceled() {
when(grpcService.getClosedChannels()).thenReturn(List.of(
closedChannel(CHANNEL_ID.getShortChannelId(), COOPERATIVE_CLOSE),
closedChannelWithType(FUNDING_CANCELED)
));
assertThat(grpcChannels.getClosedChannels()).containsExactlyInAnyOrder(CLOSED_CHANNEL);
verify(channelIdResolver, never()).resolveFromChannelPoint(any());
}
@Test
void getChannel() {
when(grpcService.getChannels()).thenReturn(List.of(channel(CHANNEL_ID_2), channel(CHANNEL_ID)));
when(grpcService.getChannels()).thenReturn(List.of(
channel(CHANNEL_ID_2, false),
channel(CHANNEL_ID, true)
));
assertThat(grpcChannels.getChannel(CHANNEL_ID)).contains(LOCAL_OPEN_CHANNEL);
}
@@ -219,7 +126,7 @@ class GrpcChannelsTest {
assertThat(grpcChannels.getChannel(CHANNEL_ID)).isEmpty();
}
private Channel channel(ChannelId channelId) {
private Channel channel(ChannelId channelId, boolean isInitiator) {
ChannelConstraints localConstraints = ChannelConstraints.newBuilder()
.setChanReserveSat(BALANCE_INFORMATION.localReserve().satoshis())
.build();
@@ -235,17 +142,7 @@ class GrpcChannelsTest {
.setRemoteBalance(BALANCE_INFORMATION.remoteBalance().satoshis())
.setLocalConstraints(localConstraints)
.setRemoteConstraints(remoteConstraints)
.build();
}
private ChannelCloseSummary closedChannel(long channelId, ChannelCloseSummary.ClosureType closeType) {
return ChannelCloseSummary.newBuilder()
.setChanId(channelId)
.setRemotePubkey(PUBKEY_2.toString())
.setCapacity(CAPACITY.satoshis())
.setChannelPoint(CHANNEL_POINT.toString())
.setClosingTxHash(TRANSACTION_HASH_2)
.setCloseType(closeType)
.setInitiator(isInitiator)
.build();
}
@@ -268,16 +165,7 @@ class GrpcChannelsTest {
.setRemoteNodePub(PUBKEY_2.toString())
.setCapacity(CAPACITY.satoshis())
.setChannelPoint(channelPoint.toString())
.build();
}
private ChannelCloseSummary closedChannelWithType(ChannelCloseSummary.ClosureType abandoned) {
return ChannelCloseSummary.newBuilder()
.setChanId(0)
.setRemotePubkey(PUBKEY_2.toString())
.setCapacity(CAPACITY.satoshis())
.setChannelPoint(CHANNEL_POINT.toString())
.setCloseType(abandoned)
.setInitiator(Initiator.INITIATOR_LOCAL)
.build();
}
}

View File

@@ -0,0 +1,170 @@
package de.cotto.lndmanagej.grpc;
import de.cotto.lndmanagej.model.ChannelIdResolver;
import lnrpc.ChannelCloseSummary;
import lnrpc.Initiator;
import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.Test;
import org.junit.jupiter.api.extension.ExtendWith;
import org.mockito.InjectMocks;
import org.mockito.Mock;
import org.mockito.junit.jupiter.MockitoExtension;
import java.util.List;
import java.util.Optional;
import static de.cotto.lndmanagej.model.ChannelFixtures.CAPACITY;
import static de.cotto.lndmanagej.model.ChannelIdFixtures.CHANNEL_ID_2_SHORT;
import static de.cotto.lndmanagej.model.ChannelIdFixtures.CHANNEL_ID_3;
import static de.cotto.lndmanagej.model.ChannelIdFixtures.CHANNEL_ID_SHORT;
import static de.cotto.lndmanagej.model.ChannelPointFixtures.CHANNEL_POINT;
import static de.cotto.lndmanagej.model.ChannelPointFixtures.TRANSACTION_HASH_2;
import static de.cotto.lndmanagej.model.CoopClosedChannelFixtures.CLOSED_CHANNEL;
import static de.cotto.lndmanagej.model.CoopClosedChannelFixtures.CLOSED_CHANNEL_2;
import static de.cotto.lndmanagej.model.CoopClosedChannelFixtures.CLOSED_CHANNEL_3;
import static de.cotto.lndmanagej.model.ForceClosedChannelFixtures.FORCE_CLOSED_CHANNEL_BREACH;
import static de.cotto.lndmanagej.model.ForceClosedChannelFixtures.FORCE_CLOSED_CHANNEL_LOCAL;
import static de.cotto.lndmanagej.model.ForceClosedChannelFixtures.FORCE_CLOSED_CHANNEL_REMOTE;
import static de.cotto.lndmanagej.model.PubkeyFixtures.PUBKEY;
import static de.cotto.lndmanagej.model.PubkeyFixtures.PUBKEY_2;
import static lnrpc.ChannelCloseSummary.ClosureType.ABANDONED;
import static lnrpc.ChannelCloseSummary.ClosureType.BREACH_CLOSE;
import static lnrpc.ChannelCloseSummary.ClosureType.COOPERATIVE_CLOSE;
import static lnrpc.ChannelCloseSummary.ClosureType.FUNDING_CANCELED;
import static lnrpc.ChannelCloseSummary.ClosureType.LOCAL_FORCE_CLOSE;
import static lnrpc.ChannelCloseSummary.ClosureType.REMOTE_FORCE_CLOSE;
import static lnrpc.Initiator.INITIATOR_LOCAL;
import static lnrpc.Initiator.INITIATOR_REMOTE;
import static lnrpc.Initiator.INITIATOR_UNKNOWN;
import static org.assertj.core.api.Assertions.assertThat;
import static org.mockito.ArgumentMatchers.any;
import static org.mockito.Mockito.never;
import static org.mockito.Mockito.verify;
import static org.mockito.Mockito.when;
@ExtendWith(MockitoExtension.class)
class GrpcClosedChannelsTest {
@InjectMocks
private GrpcClosedChannels grpcClosedChannels;
@Mock
private GrpcService grpcService;
@Mock
private GrpcGetInfo grpcGetInfo;
@Mock
private ChannelIdResolver channelIdResolver;
@BeforeEach
void setUp() {
when(grpcGetInfo.getPubkey()).thenReturn(PUBKEY);
}
@Test
void getClosedChannels() {
when(grpcService.getClosedChannels()).thenReturn(
List.of(
closedChannel(CHANNEL_ID_SHORT, COOPERATIVE_CLOSE, INITIATOR_LOCAL, INITIATOR_REMOTE),
closedChannel(CHANNEL_ID_2_SHORT, COOPERATIVE_CLOSE, INITIATOR_UNKNOWN, INITIATOR_LOCAL)
)
);
assertThat(grpcClosedChannels.getClosedChannels())
.containsExactlyInAnyOrder(CLOSED_CHANNEL, CLOSED_CHANNEL_2);
verify(channelIdResolver, never()).resolveFromChannelPoint(any());
}
@Test
void getClosedChannels_force_closed_local() {
when(grpcService.getClosedChannels()).thenReturn(List.of(
closedChannel(CHANNEL_ID_SHORT, LOCAL_FORCE_CLOSE, INITIATOR_LOCAL, INITIATOR_UNKNOWN)
));
assertThat(grpcClosedChannels.getClosedChannels())
.containsExactlyInAnyOrder(FORCE_CLOSED_CHANNEL_LOCAL);
}
@Test
void getClosedChannels_force_closed_remote() {
when(grpcService.getClosedChannels()).thenReturn(List.of(
closedChannel(CHANNEL_ID_SHORT, REMOTE_FORCE_CLOSE, INITIATOR_LOCAL, INITIATOR_REMOTE)
));
assertThat(grpcClosedChannels.getClosedChannels())
.containsExactlyInAnyOrder(FORCE_CLOSED_CHANNEL_REMOTE);
}
@Test
void getClosedChannels_force_closed_breach_detected() {
when(grpcService.getClosedChannels()).thenReturn(List.of(
closedChannel(CHANNEL_ID_SHORT, BREACH_CLOSE, INITIATOR_LOCAL, INITIATOR_REMOTE)
));
assertThat(grpcClosedChannels.getClosedChannels())
.containsExactlyInAnyOrder(FORCE_CLOSED_CHANNEL_BREACH);
}
@Test
void getClosedChannels_with_zero_channel_id_not_resolved() {
when(grpcService.getClosedChannels()).thenReturn(List.of(
closedChannel(CHANNEL_ID_SHORT, COOPERATIVE_CLOSE, INITIATOR_LOCAL, INITIATOR_REMOTE),
closedChannel(0, COOPERATIVE_CLOSE, INITIATOR_LOCAL, INITIATOR_REMOTE)
));
assertThat(grpcClosedChannels.getClosedChannels()).containsExactlyInAnyOrder(CLOSED_CHANNEL);
verify(channelIdResolver).resolveFromChannelPoint(CHANNEL_POINT);
}
@Test
void getClosedChannels_with_zero_channel_id_resolved() {
when(channelIdResolver.resolveFromChannelPoint(CHANNEL_POINT)).thenReturn(Optional.of(CHANNEL_ID_3));
when(grpcService.getClosedChannels()).thenReturn(List.of(
closedChannel(0, COOPERATIVE_CLOSE, INITIATOR_LOCAL, INITIATOR_UNKNOWN)
));
assertThat(grpcClosedChannels.getClosedChannels()).containsExactlyInAnyOrder(CLOSED_CHANNEL_3);
}
@Test
void getClosedChannels_ignores_abandoned() {
when(grpcService.getClosedChannels()).thenReturn(List.of(
closedChannel(CHANNEL_ID_SHORT, COOPERATIVE_CLOSE, INITIATOR_LOCAL, INITIATOR_REMOTE),
closedChannelWithType(ABANDONED)
));
assertThat(grpcClosedChannels.getClosedChannels()).containsExactlyInAnyOrder(CLOSED_CHANNEL);
verify(channelIdResolver, never()).resolveFromChannelPoint(any());
}
@Test
void getClosedChannels_ignores_funding_canceled() {
when(grpcService.getClosedChannels()).thenReturn(List.of(
closedChannel(CHANNEL_ID_SHORT, COOPERATIVE_CLOSE, INITIATOR_LOCAL, INITIATOR_REMOTE),
closedChannelWithType(FUNDING_CANCELED)
));
assertThat(grpcClosedChannels.getClosedChannels()).containsExactlyInAnyOrder(CLOSED_CHANNEL);
verify(channelIdResolver, never()).resolveFromChannelPoint(any());
}
private ChannelCloseSummary closedChannel(
long channelId,
ChannelCloseSummary.ClosureType closeType,
Initiator openInitiator,
Initiator closeInitiator
) {
return ChannelCloseSummary.newBuilder()
.setChanId(channelId)
.setRemotePubkey(PUBKEY_2.toString())
.setCapacity(CAPACITY.satoshis())
.setChannelPoint(CHANNEL_POINT.toString())
.setClosingTxHash(TRANSACTION_HASH_2)
.setCloseType(closeType)
.setOpenInitiator(openInitiator)
.setCloseInitiator(closeInitiator)
.build();
}
private ChannelCloseSummary closedChannelWithType(ChannelCloseSummary.ClosureType abandoned) {
return ChannelCloseSummary.newBuilder()
.setChanId(0)
.setRemotePubkey(PUBKEY_2.toString())
.setCapacity(CAPACITY.satoshis())
.setChannelPoint(CHANNEL_POINT.toString())
.setCloseType(abandoned)
.build();
}
}

View File

@@ -0,0 +1,24 @@
package de.cotto.lndmanagej.model;
public class BreachForceClosedChannel extends ForceClosedChannel {
public BreachForceClosedChannel(
ChannelId channelId,
ChannelPoint channelPoint,
Coins capacity,
Pubkey ownPubkey,
Pubkey remotePubkey,
String closeTransactionHash,
OpenInitiator openInitiator
) {
super(
channelId,
channelPoint,
capacity,
ownPubkey,
remotePubkey,
closeTransactionHash,
openInitiator,
CloseInitiator.REMOTE
);
}
}

View File

@@ -0,0 +1,22 @@
package de.cotto.lndmanagej.model;
import static java.util.Objects.requireNonNull;
public class BreachForceClosedChannelBuilder extends ClosedChannelBuilder<BreachForceClosedChannel> {
public BreachForceClosedChannelBuilder() {
super();
}
@Override
public BreachForceClosedChannel build() {
return new BreachForceClosedChannel(
requireNonNull(channelId),
requireNonNull(channelPoint),
requireNonNull(capacity),
requireNonNull(ownPubkey),
requireNonNull(remotePubkey),
requireNonNull(closeTransactionHash),
requireNonNull(openInitiator)
);
}
}

View File

@@ -0,0 +1,5 @@
package de.cotto.lndmanagej.model;
public enum CloseInitiator {
LOCAL, REMOTE, UNKNOWN
}

View File

@@ -1,5 +0,0 @@
package de.cotto.lndmanagej.model;
public enum CloseType {
REMOTE, LOCAL, BREACH
}

View File

@@ -1,14 +1,54 @@
package de.cotto.lndmanagej.model;
import java.util.Objects;
public abstract class ClosedChannel extends ClosedOrClosingChannel {
private final CloseInitiator closeInitiator;
public ClosedChannel(
ChannelId channelId,
ChannelPoint channelPoint,
Coins capacity,
Pubkey ownPubkey,
Pubkey remotePubkey,
String closeTransactionHash
String closeTransactionHash,
OpenInitiator openInitiator,
CloseInitiator closeInitiator
) {
super(channelId, channelPoint, capacity, ownPubkey, remotePubkey, closeTransactionHash);
super(
channelId,
channelPoint,
capacity,
ownPubkey,
remotePubkey,
closeTransactionHash,
openInitiator
);
this.closeInitiator = closeInitiator;
}
public CloseInitiator getCloseInitiator() {
return closeInitiator;
}
@Override
@SuppressWarnings("CPD-START")
public boolean equals(Object other) {
if (this == other) {
return true;
}
if (other == null || getClass() != other.getClass()) {
return false;
}
if (!super.equals(other)) {
return false;
}
ClosedChannel that = (ClosedChannel) other;
return closeInitiator == that.closeInitiator;
}
@Override
public int hashCode() {
return Objects.hash(super.hashCode(), closeInitiator);
}
}

View File

@@ -0,0 +1,75 @@
package de.cotto.lndmanagej.model;
import javax.annotation.Nullable;
public abstract class ClosedChannelBuilder<T extends ClosedChannel> {
@Nullable
ChannelId channelId;
@Nullable
ChannelPoint channelPoint;
@Nullable
Coins capacity;
@Nullable
Pubkey ownPubkey;
@Nullable
Pubkey remotePubkey;
@Nullable
String closeTransactionHash;
@Nullable
OpenInitiator openInitiator;
@Nullable
CloseInitiator closeInitiator;
public ClosedChannelBuilder() {
// default constructor
}
public ClosedChannelBuilder<T> withChannelId(ChannelId channelId) {
this.channelId = channelId;
return this;
}
public ClosedChannelBuilder<T> withChannelPoint(ChannelPoint channelPoint) {
this.channelPoint = channelPoint;
return this;
}
public ClosedChannelBuilder<T> withCapacity(Coins capacity) {
this.capacity = capacity;
return this;
}
public ClosedChannelBuilder<T> withOwnPubkey(Pubkey ownPubkey) {
this.ownPubkey = ownPubkey;
return this;
}
public ClosedChannelBuilder<T> withRemotePubkey(Pubkey remotePubkey) {
this.remotePubkey = remotePubkey;
return this;
}
public ClosedChannelBuilder<T> withCloseTransactionHash(String closeTransactionHash) {
this.closeTransactionHash = closeTransactionHash;
return this;
}
public ClosedChannelBuilder<T> withOpenInitiator(OpenInitiator openInitiator) {
this.openInitiator = openInitiator;
return this;
}
public ClosedChannelBuilder<T> withCloseInitiator(CloseInitiator closeInitiator) {
this.closeInitiator = closeInitiator;
return this;
}
public abstract T build();
}

View File

@@ -11,9 +11,10 @@ public class ClosedOrClosingChannel extends LocalChannel {
Coins capacity,
Pubkey ownPubkey,
Pubkey remotePubkey,
String closeTransactionHash
String closeTransactionHash,
OpenInitiator openInitiator
) {
super(channelId, channelPoint, capacity, ownPubkey, remotePubkey);
super(channelId, channelPoint, capacity, ownPubkey, remotePubkey, openInitiator);
this.closeTransactionHash = closeTransactionHash;
}

View File

@@ -7,8 +7,19 @@ public class CoopClosedChannel extends ClosedChannel {
Coins capacity,
Pubkey ownPubkey,
Pubkey remotePubkey,
String closeTransactionHash
String closeTransactionHash,
OpenInitiator openInitiator,
CloseInitiator closeInitiator
) {
super(channelId, channelPoint, capacity, ownPubkey, remotePubkey, closeTransactionHash);
super(
channelId,
channelPoint,
capacity,
ownPubkey,
remotePubkey,
closeTransactionHash,
openInitiator,
closeInitiator
);
}
}

View File

@@ -0,0 +1,23 @@
package de.cotto.lndmanagej.model;
import static java.util.Objects.requireNonNull;
public class CoopClosedChannelBuilder extends ClosedChannelBuilder<CoopClosedChannel> {
public CoopClosedChannelBuilder() {
super();
}
@Override
public CoopClosedChannel build() {
return new CoopClosedChannel(
requireNonNull(channelId),
requireNonNull(channelPoint),
requireNonNull(capacity),
requireNonNull(ownPubkey),
requireNonNull(remotePubkey),
requireNonNull(closeTransactionHash),
requireNonNull(openInitiator),
requireNonNull(closeInitiator)
);
}
}

View File

@@ -1,10 +1,6 @@
package de.cotto.lndmanagej.model;
import java.util.Objects;
public class ForceClosedChannel extends ClosedChannel {
private final CloseType closeType;
public ForceClosedChannel(
ChannelId channelId,
ChannelPoint channelPoint,
@@ -12,30 +8,18 @@ public class ForceClosedChannel extends ClosedChannel {
Pubkey ownPubkey,
Pubkey remotePubkey,
String closeTransactionHash,
CloseType closeType
OpenInitiator openInitiator,
CloseInitiator closeInitiator
) {
super(channelId, channelPoint, capacity, ownPubkey, remotePubkey, closeTransactionHash);
this.closeType = closeType;
}
@Override
@SuppressWarnings("CPD-START")
public boolean equals(Object other) {
if (this == other) {
return true;
}
if (other == null || getClass() != other.getClass()) {
return false;
}
if (!super.equals(other)) {
return false;
}
ForceClosedChannel that = (ForceClosedChannel) other;
return closeType == that.closeType;
}
@Override
public int hashCode() {
return Objects.hash(super.hashCode(), closeType);
super(
channelId,
channelPoint,
capacity,
ownPubkey,
remotePubkey,
closeTransactionHash,
openInitiator,
closeInitiator
);
}
}

View File

@@ -0,0 +1,23 @@
package de.cotto.lndmanagej.model;
import static java.util.Objects.requireNonNull;
public class ForceClosedChannelBuilder extends ClosedChannelBuilder<ForceClosedChannel> {
public ForceClosedChannelBuilder() {
super();
}
@Override
public ForceClosedChannel build() {
return new ForceClosedChannel(
requireNonNull(channelId),
requireNonNull(channelPoint),
requireNonNull(capacity),
requireNonNull(ownPubkey),
requireNonNull(remotePubkey),
requireNonNull(closeTransactionHash),
requireNonNull(openInitiator),
requireNonNull(closeInitiator)
);
}
}

View File

@@ -13,9 +13,10 @@ public final class ForceClosingChannel extends ClosedOrClosingChannel {
Pubkey ownPubkey,
Pubkey remotePubkey,
String closeTransactionHash,
Set<ChannelPoint> htlcOutpoints
Set<ChannelPoint> htlcOutpoints,
OpenInitiator openInitiator
) {
super(channelId, channelPoint, capacity, ownPubkey, remotePubkey, closeTransactionHash);
super(channelId, channelPoint, capacity, ownPubkey, remotePubkey, closeTransactionHash, openInitiator);
this.htlcOutpoints = htlcOutpoints;
}

View File

@@ -4,16 +4,19 @@ import java.util.Objects;
public class LocalChannel extends Channel {
private final Pubkey remotePubkey;
private final OpenInitiator openInitiator;
protected LocalChannel(
ChannelId channelId,
ChannelPoint channelPoint,
Coins capacity,
Pubkey ownPubkey,
Pubkey remotePubkey
Pubkey remotePubkey,
OpenInitiator openInitiator
) {
super(channelId, channelPoint, capacity, ownPubkey, remotePubkey);
this.remotePubkey = remotePubkey;
this.openInitiator = openInitiator;
}
public Pubkey getRemotePubkey() {
@@ -33,11 +36,15 @@ public class LocalChannel extends Channel {
return false;
}
LocalChannel that = (LocalChannel) other;
return Objects.equals(remotePubkey, that.remotePubkey);
return Objects.equals(remotePubkey, that.remotePubkey) && openInitiator == that.openInitiator;
}
@Override
public int hashCode() {
return Objects.hash(super.hashCode(), remotePubkey);
return Objects.hash(super.hashCode(), remotePubkey, openInitiator);
}
public OpenInitiator getOpenInitiator() {
return openInitiator;
}
}

View File

@@ -11,9 +11,10 @@ public class LocalOpenChannel extends LocalChannel {
Coins capacity,
Pubkey ownPubkey,
Pubkey remotePubkey,
BalanceInformation balanceInformation
BalanceInformation balanceInformation,
OpenInitiator openInitiator
) {
super(channelId, channelPoint, capacity, ownPubkey, remotePubkey);
super(channelId, channelPoint, capacity, ownPubkey, remotePubkey, openInitiator);
this.balanceInformation = balanceInformation;
}
@@ -22,6 +23,7 @@ public class LocalOpenChannel extends LocalChannel {
}
@Override
@SuppressWarnings("CPD-START")
public boolean equals(Object other) {
if (this == other) {
return true;

View File

@@ -0,0 +1,5 @@
package de.cotto.lndmanagej.model;
public enum OpenInitiator {
LOCAL, REMOTE, UNKNOWN
}

View File

@@ -6,8 +6,9 @@ public class WaitingCloseChannel extends LocalChannel {
ChannelPoint channelPoint,
Coins capacity,
Pubkey ownPubkey,
Pubkey remotePubkey
Pubkey remotePubkey,
OpenInitiator openInitiator
) {
super(channelId, channelPoint, capacity, ownPubkey, remotePubkey);
super(channelId, channelPoint, capacity, ownPubkey, remotePubkey, openInitiator);
}
}

View File

@@ -0,0 +1,74 @@
package de.cotto.lndmanagej.model;
import nl.jqno.equalsverifier.EqualsVerifier;
import org.junit.jupiter.api.Test;
import static de.cotto.lndmanagej.model.ChannelFixtures.CAPACITY;
import static de.cotto.lndmanagej.model.ChannelIdFixtures.CHANNEL_ID;
import static de.cotto.lndmanagej.model.ChannelPointFixtures.CHANNEL_POINT;
import static de.cotto.lndmanagej.model.ChannelPointFixtures.TRANSACTION_HASH_2;
import static de.cotto.lndmanagej.model.ForceClosedChannelFixtures.FORCE_CLOSED_CHANNEL_BREACH;
import static de.cotto.lndmanagej.model.PubkeyFixtures.PUBKEY;
import static de.cotto.lndmanagej.model.PubkeyFixtures.PUBKEY_2;
import static org.assertj.core.api.Assertions.assertThat;
class BreachForceClosedChannelTest {
@Test
void create() {
assertThat(new BreachForceClosedChannelBuilder()
.withChannelId(CHANNEL_ID)
.withChannelPoint(CHANNEL_POINT)
.withCapacity(CAPACITY)
.withOwnPubkey(PUBKEY)
.withRemotePubkey(PUBKEY_2)
.withCloseTransactionHash(TRANSACTION_HASH_2)
.withOpenInitiator(OpenInitiator.LOCAL)
.build()
).isEqualTo(FORCE_CLOSED_CHANNEL_BREACH);
}
@Test
void getId() {
assertThat(FORCE_CLOSED_CHANNEL_BREACH.getId()).isEqualTo(CHANNEL_ID);
}
@Test
void getRemotePubkey() {
assertThat(FORCE_CLOSED_CHANNEL_BREACH.getRemotePubkey()).isEqualTo(PUBKEY_2);
}
@Test
void getCapacity() {
assertThat(FORCE_CLOSED_CHANNEL_BREACH.getCapacity()).isEqualTo(CAPACITY);
}
@Test
void getChannelPoint() {
assertThat(FORCE_CLOSED_CHANNEL_BREACH.getChannelPoint()).isEqualTo(CHANNEL_POINT);
}
@Test
void getPubkeys() {
assertThat(FORCE_CLOSED_CHANNEL_BREACH.getPubkeys()).containsExactlyInAnyOrder(PUBKEY, PUBKEY_2);
}
@Test
void getCloseTransactionHash() {
assertThat(FORCE_CLOSED_CHANNEL_BREACH.getCloseTransactionHash()).isEqualTo(TRANSACTION_HASH_2);
}
@Test
void getOpenInitiator() {
assertThat(FORCE_CLOSED_CHANNEL_BREACH.getOpenInitiator()).isEqualTo(OpenInitiator.LOCAL);
}
@Test
void getCloseInitiator() {
assertThat(FORCE_CLOSED_CHANNEL_BREACH.getCloseInitiator()).isEqualTo(CloseInitiator.REMOTE);
}
@Test
void testEquals() {
EqualsVerifier.forClass(BreachForceClosedChannel.class).usingGetClass().verify();
}
}

View File

@@ -0,0 +1,11 @@
package de.cotto.lndmanagej.model;
import nl.jqno.equalsverifier.EqualsVerifier;
import org.junit.jupiter.api.Test;
class ClosedOrClosingChannelTest {
@Test
void testEquals() {
EqualsVerifier.forClass(ClosedOrClosingChannel.class).usingGetClass().verify();
}
}

View File

@@ -15,8 +15,19 @@ import static org.assertj.core.api.Assertions.assertThat;
class CoopClosedChannelTest {
@Test
void create() {
assertThat(new CoopClosedChannel(CHANNEL_ID, CHANNEL_POINT, CAPACITY, PUBKEY, PUBKEY_2, TRANSACTION_HASH_2))
.isEqualTo(CLOSED_CHANNEL);
// CPD-OFF
assertThat(new CoopClosedChannelBuilder()
.withChannelId(CHANNEL_ID)
.withChannelPoint(CHANNEL_POINT)
.withCapacity(CAPACITY)
.withOwnPubkey(PUBKEY)
.withRemotePubkey(PUBKEY_2)
.withCloseTransactionHash(TRANSACTION_HASH_2)
.withOpenInitiator(OpenInitiator.LOCAL)
.withCloseInitiator(CloseInitiator.REMOTE)
.build()
).isEqualTo(CLOSED_CHANNEL);
// CPD-ON
}
@Test
@@ -49,8 +60,18 @@ class CoopClosedChannelTest {
assertThat(CLOSED_CHANNEL.getCloseTransactionHash()).isEqualTo(TRANSACTION_HASH_2);
}
@Test
void getOpenInitiator() {
assertThat(CLOSED_CHANNEL.getOpenInitiator()).isEqualTo(OpenInitiator.LOCAL);
}
@Test
void getCloseInitiator() {
assertThat(CLOSED_CHANNEL.getCloseInitiator()).isEqualTo(CloseInitiator.REMOTE);
}
@Test
void testEquals() {
EqualsVerifier.forClass(ClosedChannel.class).usingGetClass().verify();
EqualsVerifier.forClass(CoopClosedChannel.class).usingGetClass().verify();
}
}

View File

@@ -7,7 +7,6 @@ import static de.cotto.lndmanagej.model.ChannelFixtures.CAPACITY;
import static de.cotto.lndmanagej.model.ChannelIdFixtures.CHANNEL_ID;
import static de.cotto.lndmanagej.model.ChannelPointFixtures.CHANNEL_POINT;
import static de.cotto.lndmanagej.model.ChannelPointFixtures.TRANSACTION_HASH_2;
import static de.cotto.lndmanagej.model.CloseType.REMOTE;
import static de.cotto.lndmanagej.model.ForceClosedChannelFixtures.FORCE_CLOSED_CHANNEL_REMOTE;
import static de.cotto.lndmanagej.model.PubkeyFixtures.PUBKEY;
import static de.cotto.lndmanagej.model.PubkeyFixtures.PUBKEY_2;
@@ -16,15 +15,17 @@ import static org.assertj.core.api.Assertions.assertThat;
class ForceClosedChannelTest {
@Test
void create() {
assertThat(new ForceClosedChannel(
CHANNEL_ID,
CHANNEL_POINT,
CAPACITY,
PUBKEY,
PUBKEY_2,
TRANSACTION_HASH_2,
REMOTE
)).isEqualTo(FORCE_CLOSED_CHANNEL_REMOTE);
assertThat(new ForceClosedChannelBuilder()
.withChannelId(CHANNEL_ID)
.withChannelPoint(CHANNEL_POINT)
.withCapacity(CAPACITY)
.withOwnPubkey(PUBKEY)
.withRemotePubkey(PUBKEY_2)
.withCloseTransactionHash(TRANSACTION_HASH_2)
.withOpenInitiator(OpenInitiator.LOCAL)
.withCloseInitiator(CloseInitiator.REMOTE)
.build()
).isEqualTo(FORCE_CLOSED_CHANNEL_REMOTE);
}
@Test
@@ -57,6 +58,16 @@ class ForceClosedChannelTest {
assertThat(FORCE_CLOSED_CHANNEL_REMOTE.getCloseTransactionHash()).isEqualTo(TRANSACTION_HASH_2);
}
@Test
void getOpenInitiator() {
assertThat(FORCE_CLOSED_CHANNEL_REMOTE.getOpenInitiator()).isEqualTo(OpenInitiator.LOCAL);
}
@Test
void getCloseInitiator() {
assertThat(FORCE_CLOSED_CHANNEL_REMOTE.getCloseInitiator()).isEqualTo(CloseInitiator.REMOTE);
}
@Test
void testEquals() {
EqualsVerifier.forClass(ForceClosedChannel.class).usingGetClass().verify();

View File

@@ -9,6 +9,7 @@ import static de.cotto.lndmanagej.model.ChannelPointFixtures.CHANNEL_POINT;
import static de.cotto.lndmanagej.model.ChannelPointFixtures.TRANSACTION_HASH_3;
import static de.cotto.lndmanagej.model.ForceClosingChannelFixtures.FORCE_CLOSING_CHANNEL;
import static de.cotto.lndmanagej.model.ForceClosingChannelFixtures.HTLC_OUTPOINTS;
import static de.cotto.lndmanagej.model.OpenInitiator.LOCAL;
import static de.cotto.lndmanagej.model.PubkeyFixtures.PUBKEY;
import static de.cotto.lndmanagej.model.PubkeyFixtures.PUBKEY_2;
import static org.assertj.core.api.Assertions.assertThat;
@@ -17,8 +18,15 @@ class ForceClosingChannelTest {
@Test
void create() {
assertThat(new ForceClosingChannel(
CHANNEL_ID, CHANNEL_POINT, CAPACITY, PUBKEY, PUBKEY_2, TRANSACTION_HASH_3, HTLC_OUTPOINTS
)).isEqualTo(FORCE_CLOSING_CHANNEL);
CHANNEL_ID,
CHANNEL_POINT,
CAPACITY,
PUBKEY,
PUBKEY_2,
TRANSACTION_HASH_3,
HTLC_OUTPOINTS,
LOCAL)
).isEqualTo(FORCE_CLOSING_CHANNEL);
}
@Test

View File

@@ -12,6 +12,7 @@ import static de.cotto.lndmanagej.model.ChannelFixtures.CAPACITY;
import static de.cotto.lndmanagej.model.ChannelIdFixtures.CHANNEL_ID;
import static de.cotto.lndmanagej.model.ChannelPointFixtures.CHANNEL_POINT;
import static de.cotto.lndmanagej.model.LocalOpenChannelFixtures.LOCAL_OPEN_CHANNEL;
import static de.cotto.lndmanagej.model.OpenInitiator.LOCAL;
import static de.cotto.lndmanagej.model.PubkeyFixtures.PUBKEY;
import static de.cotto.lndmanagej.model.PubkeyFixtures.PUBKEY_2;
import static org.assertj.core.api.Assertions.assertThat;
@@ -25,7 +26,7 @@ class LocalOpenChannelTest {
@Test
void getRemotePubkey_swapped() {
LocalOpenChannel localOpenChannel =
new LocalOpenChannel(CHANNEL_ID, CHANNEL_POINT, CAPACITY, PUBKEY_2, PUBKEY, BALANCE_INFORMATION);
new LocalOpenChannel(CHANNEL_ID, CHANNEL_POINT, CAPACITY, PUBKEY_2, PUBKEY, BALANCE_INFORMATION, LOCAL);
assertThat(localOpenChannel.getRemotePubkey()).isEqualTo(PUBKEY);
}
@@ -49,6 +50,11 @@ class LocalOpenChannelTest {
assertThat(LOCAL_OPEN_CHANNEL.getBalanceInformation().remoteReserve()).isEqualTo(REMOTE_RESERVE);
}
@Test
void getOpenInitiator() {
assertThat(LOCAL_OPEN_CHANNEL.getOpenInitiator()).isEqualTo(LOCAL);
}
@Test
void testEquals() {
EqualsVerifier.forClass(LocalOpenChannel.class).usingGetClass().verify();

View File

@@ -14,7 +14,7 @@ import static org.assertj.core.api.Assertions.assertThat;
class WaitingCloseChannelTest {
@Test
void create() {
assertThat(new WaitingCloseChannel(CHANNEL_ID, CHANNEL_POINT, CAPACITY, PUBKEY, PUBKEY_2))
assertThat(new WaitingCloseChannel(CHANNEL_ID, CHANNEL_POINT, CAPACITY, PUBKEY, PUBKEY_2, OpenInitiator.LOCAL))
.isEqualTo(WAITING_CLOSE_CHANNEL);
}
@@ -47,4 +47,9 @@ class WaitingCloseChannelTest {
void testEquals() {
EqualsVerifier.forClass(WaitingCloseChannel.class).usingGetClass().verify();
}
@Test
void getOpenInitiator() {
assertThat(WAITING_CLOSE_CHANNEL.getOpenInitiator()).isEqualTo(OpenInitiator.LOCAL);
}
}

View File

@@ -9,4 +9,8 @@ public class ChannelIdFixtures {
public static final ChannelId CHANNEL_ID_2 = ChannelId.fromCompactForm(CHANNEL_ID_COMPACT_2);
public static final ChannelId CHANNEL_ID_3 = ChannelId.fromCompactForm(CHANNEL_ID_COMPACT_3);
public static final ChannelId CHANNEL_ID_4 = ChannelId.fromCompactForm(CHANNEL_ID_COMPACT_4);
public static final long CHANNEL_ID_SHORT = CHANNEL_ID.getShortChannelId();
public static final long CHANNEL_ID_2_SHORT = CHANNEL_ID_2.getShortChannelId();
public static final long CHANNEL_ID_3_SHORT = CHANNEL_ID_3.getShortChannelId();
public static final long CHANNEL_ID_4_SHORT = CHANNEL_ID_4.getShortChannelId();
}

View File

@@ -0,0 +1,25 @@
package de.cotto.lndmanagej.model;
import static de.cotto.lndmanagej.model.ChannelFixtures.CAPACITY;
import static de.cotto.lndmanagej.model.ChannelIdFixtures.CHANNEL_ID;
import static de.cotto.lndmanagej.model.ChannelPointFixtures.CHANNEL_POINT;
import static de.cotto.lndmanagej.model.ChannelPointFixtures.TRANSACTION_HASH_2;
import static de.cotto.lndmanagej.model.PubkeyFixtures.PUBKEY;
import static de.cotto.lndmanagej.model.PubkeyFixtures.PUBKEY_2;
public final class ClosedChannelFixtures {
private ClosedChannelFixtures() {
// do not instantiate
}
public static <T extends ClosedChannel> ClosedChannelBuilder<T> getWithDefaults(ClosedChannelBuilder<T> builder) {
return builder.withChannelId(CHANNEL_ID)
.withChannelPoint(CHANNEL_POINT)
.withCapacity(CAPACITY)
.withOwnPubkey(PUBKEY)
.withRemotePubkey(PUBKEY_2)
.withCloseTransactionHash(TRANSACTION_HASH_2)
.withOpenInitiator(OpenInitiator.LOCAL)
.withCloseInitiator(CloseInitiator.REMOTE);
}
}

View File

@@ -1,22 +1,31 @@
package de.cotto.lndmanagej.model;
import static de.cotto.lndmanagej.model.ChannelFixtures.CAPACITY;
import static de.cotto.lndmanagej.model.ChannelIdFixtures.CHANNEL_ID;
import static de.cotto.lndmanagej.model.ChannelIdFixtures.CHANNEL_ID_2;
import static de.cotto.lndmanagej.model.ChannelIdFixtures.CHANNEL_ID_3;
import static de.cotto.lndmanagej.model.ChannelPointFixtures.CHANNEL_POINT;
import static de.cotto.lndmanagej.model.ChannelPointFixtures.TRANSACTION_HASH_2;
import static de.cotto.lndmanagej.model.PubkeyFixtures.PUBKEY;
import static de.cotto.lndmanagej.model.PubkeyFixtures.PUBKEY_2;
import static de.cotto.lndmanagej.model.PubkeyFixtures.PUBKEY_3;
public class CoopClosedChannelFixtures {
public class CoopClosedChannelFixtures {
public static final CoopClosedChannel CLOSED_CHANNEL =
new CoopClosedChannel(CHANNEL_ID, CHANNEL_POINT, CAPACITY, PUBKEY, PUBKEY_2, TRANSACTION_HASH_2);
public static final CoopClosedChannel CLOSED_CHANNEL_2
= new CoopClosedChannel(CHANNEL_ID_2, CHANNEL_POINT, CAPACITY, PUBKEY, PUBKEY_2, TRANSACTION_HASH_2);
ClosedChannelFixtures.getWithDefaults(new CoopClosedChannelBuilder())
.build();
public static final CoopClosedChannel CLOSED_CHANNEL_2 =
ClosedChannelFixtures.getWithDefaults(new CoopClosedChannelBuilder())
.withChannelId(CHANNEL_ID_2)
.withOpenInitiator(OpenInitiator.UNKNOWN)
.withCloseInitiator(CloseInitiator.LOCAL)
.build();
public static final CoopClosedChannel CLOSED_CHANNEL_3 =
new CoopClosedChannel(CHANNEL_ID_3, CHANNEL_POINT, CAPACITY, PUBKEY, PUBKEY_2, TRANSACTION_HASH_2);
ClosedChannelFixtures.getWithDefaults(new CoopClosedChannelBuilder())
.withChannelId(CHANNEL_ID_3)
.withCloseInitiator(CloseInitiator.UNKNOWN)
.build();
public static final CoopClosedChannel CLOSED_CHANNEL_TO_NODE_3 =
new CoopClosedChannel(CHANNEL_ID_3, CHANNEL_POINT, CAPACITY, PUBKEY, PUBKEY_3, TRANSACTION_HASH_2);
ClosedChannelFixtures.getWithDefaults(new CoopClosedChannelBuilder())
.withChannelId(CHANNEL_ID_3)
.withRemotePubkey(PUBKEY_3)
.build();
}

View File

@@ -1,20 +1,14 @@
package de.cotto.lndmanagej.model;
import static de.cotto.lndmanagej.model.ChannelFixtures.CAPACITY;
import static de.cotto.lndmanagej.model.ChannelIdFixtures.CHANNEL_ID;
import static de.cotto.lndmanagej.model.ChannelPointFixtures.CHANNEL_POINT;
import static de.cotto.lndmanagej.model.ChannelPointFixtures.TRANSACTION_HASH_2;
import static de.cotto.lndmanagej.model.CloseType.BREACH;
import static de.cotto.lndmanagej.model.CloseType.LOCAL;
import static de.cotto.lndmanagej.model.CloseType.REMOTE;
import static de.cotto.lndmanagej.model.PubkeyFixtures.PUBKEY;
import static de.cotto.lndmanagej.model.PubkeyFixtures.PUBKEY_2;
public class ForceClosedChannelFixtures {
public static final ForceClosedChannel FORCE_CLOSED_CHANNEL_REMOTE =
new ForceClosedChannel(CHANNEL_ID, CHANNEL_POINT, CAPACITY, PUBKEY, PUBKEY_2, TRANSACTION_HASH_2, REMOTE);
ClosedChannelFixtures.getWithDefaults(new ForceClosedChannelBuilder()).build();
public static final ForceClosedChannel FORCE_CLOSED_CHANNEL_LOCAL =
new ForceClosedChannel(CHANNEL_ID, CHANNEL_POINT, CAPACITY, PUBKEY, PUBKEY_2, TRANSACTION_HASH_2, LOCAL);
public static final ForceClosedChannel FORCE_CLOSED_CHANNEL_BREACH =
new ForceClosedChannel(CHANNEL_ID, CHANNEL_POINT, CAPACITY, PUBKEY, PUBKEY_2, TRANSACTION_HASH_2, BREACH);
ClosedChannelFixtures.getWithDefaults(new ForceClosedChannelBuilder())
.withCloseInitiator(CloseInitiator.LOCAL)
.build();
public static final BreachForceClosedChannel FORCE_CLOSED_CHANNEL_BREACH =
ClosedChannelFixtures.getWithDefaults(new BreachForceClosedChannelBuilder()).build();
}

View File

@@ -10,6 +10,7 @@ import static de.cotto.lndmanagej.model.ChannelPointFixtures.CHANNEL_POINT;
import static de.cotto.lndmanagej.model.ChannelPointFixtures.CHANNEL_POINT_2;
import static de.cotto.lndmanagej.model.ChannelPointFixtures.CHANNEL_POINT_3;
import static de.cotto.lndmanagej.model.ChannelPointFixtures.TRANSACTION_HASH_3;
import static de.cotto.lndmanagej.model.OpenInitiator.LOCAL;
import static de.cotto.lndmanagej.model.PubkeyFixtures.PUBKEY;
import static de.cotto.lndmanagej.model.PubkeyFixtures.PUBKEY_2;
import static de.cotto.lndmanagej.model.PubkeyFixtures.PUBKEY_3;
@@ -18,15 +19,11 @@ public class ForceClosingChannelFixtures {
public static final ChannelPoint HTLC_OUTPOINT = CHANNEL_POINT_3;
public static final Set<ChannelPoint> HTLC_OUTPOINTS = Set.of(HTLC_OUTPOINT);
public static final ForceClosingChannel FORCE_CLOSING_CHANNEL = new ForceClosingChannel(
CHANNEL_ID, CHANNEL_POINT, CAPACITY, PUBKEY, PUBKEY_2, TRANSACTION_HASH_3, HTLC_OUTPOINTS
);
CHANNEL_ID, CHANNEL_POINT, CAPACITY, PUBKEY, PUBKEY_2, TRANSACTION_HASH_3, HTLC_OUTPOINTS, LOCAL);
public static final ForceClosingChannel FORCE_CLOSING_CHANNEL_2 = new ForceClosingChannel(
CHANNEL_ID_2, CHANNEL_POINT_2, CAPACITY, PUBKEY, PUBKEY_2, TRANSACTION_HASH_3, HTLC_OUTPOINTS
);
CHANNEL_ID_2, CHANNEL_POINT_2, CAPACITY, PUBKEY, PUBKEY_2, TRANSACTION_HASH_3, HTLC_OUTPOINTS, LOCAL);
public static final ForceClosingChannel FORCE_CLOSING_CHANNEL_3 = new ForceClosingChannel(
CHANNEL_ID_3, CHANNEL_POINT, CAPACITY, PUBKEY, PUBKEY_2, TRANSACTION_HASH_3, HTLC_OUTPOINTS
);
CHANNEL_ID_3, CHANNEL_POINT, CAPACITY, PUBKEY, PUBKEY_2, TRANSACTION_HASH_3, HTLC_OUTPOINTS, LOCAL);
public static final ForceClosingChannel FORCE_CLOSING_CHANNEL_TO_NODE_3 = new ForceClosingChannel(
CHANNEL_ID_3, CHANNEL_POINT, CAPACITY, PUBKEY, PUBKEY_3, TRANSACTION_HASH_3, HTLC_OUTPOINTS
);
CHANNEL_ID_3, CHANNEL_POINT, CAPACITY, PUBKEY, PUBKEY_3, TRANSACTION_HASH_3, HTLC_OUTPOINTS, LOCAL);
}

View File

@@ -8,17 +8,19 @@ import static de.cotto.lndmanagej.model.ChannelIdFixtures.CHANNEL_ID_2;
import static de.cotto.lndmanagej.model.ChannelIdFixtures.CHANNEL_ID_3;
import static de.cotto.lndmanagej.model.ChannelIdFixtures.CHANNEL_ID_4;
import static de.cotto.lndmanagej.model.ChannelPointFixtures.CHANNEL_POINT;
import static de.cotto.lndmanagej.model.OpenInitiator.LOCAL;
import static de.cotto.lndmanagej.model.OpenInitiator.REMOTE;
import static de.cotto.lndmanagej.model.PubkeyFixtures.PUBKEY;
import static de.cotto.lndmanagej.model.PubkeyFixtures.PUBKEY_2;
import static de.cotto.lndmanagej.model.PubkeyFixtures.PUBKEY_3;
public class LocalOpenChannelFixtures {
public static final LocalOpenChannel LOCAL_OPEN_CHANNEL =
new LocalOpenChannel(CHANNEL_ID, CHANNEL_POINT, CAPACITY, PUBKEY, PUBKEY_2, BALANCE_INFORMATION);
new LocalOpenChannel(CHANNEL_ID, CHANNEL_POINT, CAPACITY, PUBKEY, PUBKEY_2, BALANCE_INFORMATION, LOCAL);
public static final LocalOpenChannel LOCAL_OPEN_CHANNEL_2 =
new LocalOpenChannel(CHANNEL_ID_2, CHANNEL_POINT, CAPACITY, PUBKEY, PUBKEY_2, BALANCE_INFORMATION);
new LocalOpenChannel(CHANNEL_ID_2, CHANNEL_POINT, CAPACITY, PUBKEY, PUBKEY_2, BALANCE_INFORMATION, REMOTE);
public static final LocalOpenChannel LOCAL_OPEN_CHANNEL_3 =
new LocalOpenChannel(CHANNEL_ID_3, CHANNEL_POINT, CAPACITY, PUBKEY, PUBKEY_2, BALANCE_INFORMATION);
new LocalOpenChannel(CHANNEL_ID_3, CHANNEL_POINT, CAPACITY, PUBKEY, PUBKEY_2, BALANCE_INFORMATION, LOCAL);
public static final LocalOpenChannel LOCAL_OPEN_CHANNEL_TO_NODE_3 =
new LocalOpenChannel(CHANNEL_ID_4, CHANNEL_POINT, CAPACITY_2, PUBKEY, PUBKEY_3, BALANCE_INFORMATION);
new LocalOpenChannel(CHANNEL_ID_4, CHANNEL_POINT, CAPACITY_2, PUBKEY, PUBKEY_3, BALANCE_INFORMATION, LOCAL);
}

View File

@@ -6,17 +6,16 @@ import static de.cotto.lndmanagej.model.ChannelIdFixtures.CHANNEL_ID_2;
import static de.cotto.lndmanagej.model.ChannelIdFixtures.CHANNEL_ID_3;
import static de.cotto.lndmanagej.model.ChannelPointFixtures.CHANNEL_POINT;
import static de.cotto.lndmanagej.model.ChannelPointFixtures.CHANNEL_POINT_2;
import static de.cotto.lndmanagej.model.OpenInitiator.LOCAL;
import static de.cotto.lndmanagej.model.PubkeyFixtures.PUBKEY;
import static de.cotto.lndmanagej.model.PubkeyFixtures.PUBKEY_2;
import static de.cotto.lndmanagej.model.PubkeyFixtures.PUBKEY_3;
public class WaitingCloseChannelFixtures {
public static final WaitingCloseChannel WAITING_CLOSE_CHANNEL =
new WaitingCloseChannel(CHANNEL_ID, CHANNEL_POINT, CAPACITY, PUBKEY, PUBKEY_2);
new WaitingCloseChannel(CHANNEL_ID, CHANNEL_POINT, CAPACITY, PUBKEY, PUBKEY_2, LOCAL);
public static final WaitingCloseChannel WAITING_CLOSE_CHANNEL_2
= new WaitingCloseChannel(CHANNEL_ID_2, CHANNEL_POINT_2, CAPACITY, PUBKEY, PUBKEY_2);
public static final WaitingCloseChannel WAITING_CLOSE_CHANNEL_3 =
new WaitingCloseChannel(CHANNEL_ID_3, CHANNEL_POINT, CAPACITY, PUBKEY, PUBKEY_2);
= new WaitingCloseChannel(CHANNEL_ID_2, CHANNEL_POINT_2, CAPACITY, PUBKEY, PUBKEY_2, LOCAL);
public static final WaitingCloseChannel WAITING_CLOSE_CHANNEL_TO_NODE_3 =
new WaitingCloseChannel(CHANNEL_ID_3, CHANNEL_POINT, CAPACITY, PUBKEY, PUBKEY_3);
new WaitingCloseChannel(CHANNEL_ID_3, CHANNEL_POINT, CAPACITY, PUBKEY, PUBKEY_3, LOCAL);
}