verify arbitrator signature when dispute closed

This commit is contained in:
woodser 2023-01-15 11:23:46 -05:00
parent 435fc164b2
commit 9260cf53ee
15 changed files with 76 additions and 88 deletions

View File

@ -174,10 +174,12 @@ public abstract class DisputeManager<T extends DisputeList<Dispute>> extends Sup
@Override
public List<ChatMessage> getAllChatMessages() {
synchronized (getDisputeList()) {
return getDisputeList().stream()
.flatMap(dispute -> dispute.getChatMessages().stream())
.collect(Collectors.toList());
}
}
@Override
public boolean channelOpen(ChatMessage message) {
@ -294,6 +296,7 @@ public abstract class DisputeManager<T extends DisputeList<Dispute>> extends Sup
}
public Optional<Dispute> findOwnDispute(String tradeId) {
synchronized (getDisputeList()) {
T disputeList = getDisputeList();
if (disputeList == null) {
log.warn("disputes is null");
@ -301,6 +304,7 @@ public abstract class DisputeManager<T extends DisputeList<Dispute>> extends Sup
}
return disputeList.stream().filter(e -> e.getTradeId().equals(tradeId)).findAny();
}
}
///////////////////////////////////////////////////////////////////////////////////////////
// Dispute handling

View File

@ -25,6 +25,8 @@ import bisq.common.util.Utilities;
import org.bitcoinj.core.Coin;
import com.google.protobuf.ByteString;
import javafx.beans.property.BooleanProperty;
import javafx.beans.property.SimpleBooleanProperty;
import javafx.beans.property.SimpleStringProperty;
@ -159,6 +161,8 @@ public final class DisputeResult implements NetworkPayload {
.setSellerPayoutAmount(sellerPayoutAmount)
.setCloseDate(closeDate);
Optional.ofNullable(arbitratorSignature).ifPresent(arbitratorSignature -> builder.setArbitratorSignature(ByteString.copyFrom(arbitratorSignature)));
Optional.ofNullable(arbitratorPubKey).ifPresent(arbitratorPubKey -> builder.setArbitratorPubKey(ByteString.copyFrom(arbitratorPubKey)));
Optional.ofNullable(winner).ifPresent(result -> builder.setWinner(protobuf.DisputeResult.Winner.valueOf(winner.name())));
Optional.ofNullable(chatMessage).ifPresent(chatMessage ->
builder.setChatMessage(chatMessage.toProtoNetworkEnvelope().getChatMessage()));

View File

@ -19,8 +19,7 @@ package bisq.core.support.dispute;
import bisq.core.locale.Res;
import bisq.core.support.dispute.agent.DisputeAgent;
import bisq.core.support.dispute.mediation.mediator.MediatorManager;
import bisq.core.support.dispute.refund.refundagent.RefundAgentManager;
import bisq.core.support.dispute.arbitration.arbitrator.ArbitratorManager;
import bisq.network.p2p.NodeAddress;
@ -64,18 +63,14 @@ public class DisputeSummaryVerification {
SEPARATOR2);
}
public static String verifySignature(String input,
MediatorManager mediatorManager,
RefundAgentManager refundAgentManager) {
public static void verifySignature(String input,
ArbitratorManager arbitratorMediator) {
try {
String[] parts = input.split(SEPARATOR1);
String textToSign = parts[0];
String fullAddress = textToSign.split("\n")[1].split(": ")[1];
NodeAddress nodeAddress = new NodeAddress(fullAddress);
DisputeAgent disputeAgent = mediatorManager.getDisputeAgentByNodeAddress(nodeAddress).orElse(null);
if (disputeAgent == null) {
disputeAgent = refundAgentManager.getDisputeAgentByNodeAddress(nodeAddress).orElse(null);
}
DisputeAgent disputeAgent = arbitratorMediator.getDisputeAgentByNodeAddress(nodeAddress).orElse(null);
checkNotNull(disputeAgent);
PublicKey pubKey = disputeAgent.getPubKeyRing().getSignaturePubKey();
@ -85,15 +80,15 @@ public class DisputeSummaryVerification {
try {
boolean result = Sig.verify(pubKey, hash, sig);
if (result) {
return Res.get("support.sigCheck.popup.success");
return;
} else {
return Res.get("support.sigCheck.popup.failed");
throw new IllegalArgumentException(Res.get("support.sigCheck.popup.failed"));
}
} catch (CryptoException e) {
return Res.get("support.sigCheck.popup.failed");
throw new IllegalArgumentException(Res.get("support.sigCheck.popup.failed"));
}
} catch (Throwable e) {
return Res.get("support.sigCheck.popup.invalidFormat");
throw new IllegalArgumentException(Res.get("support.sigCheck.popup.invalidFormat"));
}
}
}

View File

@ -28,7 +28,9 @@ import bisq.core.support.SupportType;
import bisq.core.support.dispute.Dispute;
import bisq.core.support.dispute.DisputeManager;
import bisq.core.support.dispute.DisputeResult;
import bisq.core.support.dispute.DisputeSummaryVerification;
import bisq.core.support.dispute.DisputeResult.Winner;
import bisq.core.support.dispute.arbitration.arbitrator.ArbitratorManager;
import bisq.core.support.dispute.messages.DisputeClosedMessage;
import bisq.core.support.dispute.messages.DisputeOpenedMessage;
import bisq.core.support.messages.ChatMessage;
@ -73,6 +75,8 @@ import monero.wallet.model.MoneroTxWallet;
@Singleton
public final class ArbitrationManager extends DisputeManager<ArbitrationDisputeList> {
private final ArbitratorManager arbitratorManager;
///////////////////////////////////////////////////////////////////////////////////////////
// Constructor
///////////////////////////////////////////////////////////////////////////////////////////
@ -83,6 +87,7 @@ public final class ArbitrationManager extends DisputeManager<ArbitrationDisputeL
XmrWalletService walletService,
CoreMoneroConnectionsService connectionService,
CoreNotificationService notificationService,
ArbitratorManager arbitratorManager,
TradeManager tradeManager,
ClosedTradableManager closedTradableManager,
OpenOfferManager openOfferManager,
@ -92,7 +97,8 @@ public final class ArbitrationManager extends DisputeManager<ArbitrationDisputeL
PriceFeedService priceFeedService) {
super(p2PService, tradeWalletService, walletService, connectionService, notificationService, tradeManager, closedTradableManager,
openOfferManager, keyRing, arbitrationDisputeListService, config, priceFeedService);
HavenoUtils.arbitrationManager = this; // store static reference
this.arbitratorManager = arbitratorManager;
HavenoUtils.arbitrationManager = this; // TODO: storing static reference, better way?
}
@ -181,6 +187,10 @@ public final class ArbitrationManager extends DisputeManager<ArbitrationDisputeL
log.info("Processing {} for {} {}", disputeClosedMessage.getClass().getSimpleName(), trade.getClass().getSimpleName(), disputeResult.getTradeId());
// verify arbitrator signature
String summaryText = chatMessage.getMessage();
DisputeSummaryVerification.verifySignature(summaryText, arbitratorManager);
// get dispute
Optional<Dispute> disputeOptional = findDispute(disputeResult);
String uid = disputeClosedMessage.getUid();

View File

@ -289,7 +289,7 @@ public class HavenoUtils {
message.setBuyerSignature(signature);
// verify signature
String errMessage = "The buyer signature is invalid for the " + message.getClass().getSimpleName() + " for trade " + trade.getId();
String errMessage = "The buyer signature is invalid for the " + message.getClass().getSimpleName() + " for " + trade.getClass().getSimpleName() + " " + trade.getId();
try {
if (!Sig.verify(trade.getBuyer().getPubKeyRing().getSignaturePubKey(), unsignedMessageAsJson.getBytes(Charsets.UTF_8), signature)) throw new RuntimeException(errMessage);
} catch (Exception e) {
@ -320,7 +320,7 @@ public class HavenoUtils {
message.setSellerSignature(signature);
// verify signature
String errMessage = "The seller signature is invalid for the " + message.getClass().getSimpleName() + " for trade " + trade.getId();
String errMessage = "The seller signature is invalid for the " + message.getClass().getSimpleName() + " for " + trade.getClass().getSimpleName() + " " + trade.getId();
try {
if (!Sig.verify(trade.getSeller().getPubKeyRing().getSignaturePubKey(), unsignedMessageAsJson.getBytes(Charsets.UTF_8), signature)) throw new RuntimeException(errMessage);
} catch (Exception e) {

View File

@ -21,8 +21,7 @@ import bisq.desktop.main.overlays.Overlay;
import bisq.core.locale.Res;
import bisq.core.support.dispute.DisputeSummaryVerification;
import bisq.core.support.dispute.mediation.mediator.MediatorManager;
import bisq.core.support.dispute.refund.refundagent.RefundAgentManager;
import bisq.core.support.dispute.arbitration.arbitrator.ArbitratorManager;
import javafx.scene.control.TextArea;
import javafx.scene.control.TextField;
@ -43,12 +42,10 @@ import static bisq.desktop.util.FormBuilder.addTopLabelTextField;
public class VerifyDisputeResultSignatureWindow extends Overlay<VerifyDisputeResultSignatureWindow> {
private TextArea textArea;
private TextField resultTextField;
private final MediatorManager mediatorManager;
private final RefundAgentManager refundAgentManager;
private final ArbitratorManager arbitratorManager;
public VerifyDisputeResultSignatureWindow(MediatorManager mediatorManager, RefundAgentManager refundAgentManager) {
this.mediatorManager = mediatorManager;
this.refundAgentManager = refundAgentManager;
public VerifyDisputeResultSignatureWindow(ArbitratorManager arbitratorManager) {
this.arbitratorManager = arbitratorManager;
type = Type.Attention;
}
@ -68,9 +65,12 @@ public class VerifyDisputeResultSignatureWindow extends Overlay<VerifyDisputeRes
display();
textArea.textProperty().addListener((observable, oldValue, newValue) -> {
resultTextField.setText(DisputeSummaryVerification.verifySignature(newValue,
mediatorManager,
refundAgentManager));
try {
DisputeSummaryVerification.verifySignature(newValue, arbitratorManager);
resultTextField.setText(Res.get("support.sigCheck.popup.success"));
} catch (Exception e) {
resultTextField.setText(e.getMessage());
}
});
}

View File

@ -44,9 +44,8 @@ import bisq.core.support.dispute.DisputeManager;
import bisq.core.support.dispute.DisputeResult;
import bisq.core.support.dispute.DisputeSession;
import bisq.core.support.dispute.agent.DisputeAgentLookupMap;
import bisq.core.support.dispute.arbitration.arbitrator.ArbitratorManager;
import bisq.core.support.dispute.mediation.MediationManager;
import bisq.core.support.dispute.mediation.mediator.MediatorManager;
import bisq.core.support.dispute.refund.refundagent.RefundAgentManager;
import bisq.core.support.messages.ChatMessage;
import bisq.core.trade.Contract;
import bisq.core.trade.Trade;
@ -157,8 +156,7 @@ public abstract class DisputeView extends ActivatableView<VBox, Void> {
private final TradeDetailsWindow tradeDetailsWindow;
private final AccountAgeWitnessService accountAgeWitnessService;
private final MediatorManager mediatorManager;
private final RefundAgentManager refundAgentManager;
private final ArbitratorManager arbitratorManager;
private final boolean useDevPrivilegeKeys;
protected TableView<Dispute> tableView;
@ -198,8 +196,7 @@ public abstract class DisputeView extends ActivatableView<VBox, Void> {
ContractWindow contractWindow,
TradeDetailsWindow tradeDetailsWindow,
AccountAgeWitnessService accountAgeWitnessService,
MediatorManager mediatorManager,
RefundAgentManager refundAgentManager,
ArbitratorManager arbitratorManager,
boolean useDevPrivilegeKeys) {
this.disputeManager = disputeManager;
this.keyRing = keyRing;
@ -211,8 +208,7 @@ public abstract class DisputeView extends ActivatableView<VBox, Void> {
this.contractWindow = contractWindow;
this.tradeDetailsWindow = tradeDetailsWindow;
this.accountAgeWitnessService = accountAgeWitnessService;
this.mediatorManager = mediatorManager;
this.refundAgentManager = refundAgentManager;
this.arbitratorManager = arbitratorManager;
this.useDevPrivilegeKeys = useDevPrivilegeKeys;
DisputeChatPopup.ChatCallback chatCallback = this::handleOnProcessDispute;
chatPopup = new DisputeChatPopup(disputeManager, formatter, preferences, chatCallback);
@ -286,7 +282,7 @@ public abstract class DisputeView extends ActivatableView<VBox, Void> {
sigCheckButton = new AutoTooltipButton(Res.get("support.sigCheck.button"));
HBox.setHgrow(sigCheckButton, Priority.NEVER);
sigCheckButton.setOnAction(e -> {
new VerifyDisputeResultSignatureWindow(mediatorManager, refundAgentManager).show();
new VerifyDisputeResultSignatureWindow(arbitratorManager).show();
});
Pane spacer = new Pane();

View File

@ -31,8 +31,7 @@ import bisq.core.support.dispute.Dispute;
import bisq.core.support.dispute.DisputeList;
import bisq.core.support.dispute.DisputeManager;
import bisq.core.support.dispute.agent.MultipleHolderNameDetection;
import bisq.core.support.dispute.mediation.mediator.MediatorManager;
import bisq.core.support.dispute.refund.refundagent.RefundAgentManager;
import bisq.core.support.dispute.arbitration.arbitrator.ArbitratorManager;
import bisq.core.trade.TradeDataValidation;
import bisq.core.trade.TradeManager;
import bisq.core.user.DontShowAgainLookup;
@ -79,8 +78,7 @@ public abstract class DisputeAgentView extends DisputeView implements MultipleHo
ContractWindow contractWindow,
TradeDetailsWindow tradeDetailsWindow,
AccountAgeWitnessService accountAgeWitnessService,
MediatorManager mediatorManager,
RefundAgentManager refundAgentManager,
ArbitratorManager arbitratorManager,
boolean useDevPrivilegeKeys) {
super(disputeManager,
keyRing,
@ -92,8 +90,7 @@ public abstract class DisputeAgentView extends DisputeView implements MultipleHo
contractWindow,
tradeDetailsWindow,
accountAgeWitnessService,
mediatorManager,
refundAgentManager,
arbitratorManager,
useDevPrivilegeKeys);
multipleHolderNameDetection = new MultipleHolderNameDetection(disputeManager);

View File

@ -30,8 +30,7 @@ import bisq.core.support.dispute.Dispute;
import bisq.core.support.dispute.DisputeSession;
import bisq.core.support.dispute.arbitration.ArbitrationManager;
import bisq.core.support.dispute.arbitration.ArbitrationSession;
import bisq.core.support.dispute.mediation.mediator.MediatorManager;
import bisq.core.support.dispute.refund.refundagent.RefundAgentManager;
import bisq.core.support.dispute.arbitration.arbitrator.ArbitratorManager;
import bisq.core.trade.TradeManager;
import bisq.core.user.Preferences;
import bisq.core.util.FormattingUtils;
@ -57,8 +56,7 @@ public class ArbitratorView extends DisputeAgentView {
ContractWindow contractWindow,
TradeDetailsWindow tradeDetailsWindow,
AccountAgeWitnessService accountAgeWitnessService,
MediatorManager mediatorManager,
RefundAgentManager refundAgentManager,
ArbitratorManager arbitratorManager,
@Named(Config.USE_DEV_PRIVILEGE_KEYS) boolean useDevPrivilegeKeys) {
super(arbitrationManager,
keyRing,
@ -70,8 +68,7 @@ public class ArbitratorView extends DisputeAgentView {
contractWindow,
tradeDetailsWindow,
accountAgeWitnessService,
mediatorManager,
refundAgentManager,
arbitratorManager,
useDevPrivilegeKeys);
}

View File

@ -28,10 +28,9 @@ import bisq.core.alert.PrivateNotificationManager;
import bisq.core.support.SupportType;
import bisq.core.support.dispute.Dispute;
import bisq.core.support.dispute.DisputeSession;
import bisq.core.support.dispute.arbitration.arbitrator.ArbitratorManager;
import bisq.core.support.dispute.mediation.MediationManager;
import bisq.core.support.dispute.mediation.MediationSession;
import bisq.core.support.dispute.mediation.mediator.MediatorManager;
import bisq.core.support.dispute.refund.refundagent.RefundAgentManager;
import bisq.core.trade.TradeManager;
import bisq.core.user.Preferences;
import bisq.core.util.FormattingUtils;
@ -57,8 +56,7 @@ public class MediatorView extends DisputeAgentView {
ContractWindow contractWindow,
TradeDetailsWindow tradeDetailsWindow,
AccountAgeWitnessService accountAgeWitnessService,
MediatorManager mediatorManager,
RefundAgentManager refundAgentManager,
ArbitratorManager arbitratorManager,
@Named(Config.USE_DEV_PRIVILEGE_KEYS) boolean useDevPrivilegeKeys) {
super(mediationManager,
keyRing,
@ -70,8 +68,7 @@ public class MediatorView extends DisputeAgentView {
contractWindow,
tradeDetailsWindow,
accountAgeWitnessService,
mediatorManager,
refundAgentManager,
arbitratorManager,
useDevPrivilegeKeys);
}

View File

@ -30,10 +30,9 @@ import bisq.core.locale.Res;
import bisq.core.support.SupportType;
import bisq.core.support.dispute.Dispute;
import bisq.core.support.dispute.DisputeSession;
import bisq.core.support.dispute.mediation.mediator.MediatorManager;
import bisq.core.support.dispute.arbitration.arbitrator.ArbitratorManager;
import bisq.core.support.dispute.refund.RefundManager;
import bisq.core.support.dispute.refund.RefundSession;
import bisq.core.support.dispute.refund.refundagent.RefundAgentManager;
import bisq.core.trade.TradeManager;
import bisq.core.user.Preferences;
import bisq.core.util.FormattingUtils;
@ -59,8 +58,7 @@ public class RefundAgentView extends DisputeAgentView {
ContractWindow contractWindow,
TradeDetailsWindow tradeDetailsWindow,
AccountAgeWitnessService accountAgeWitnessService,
MediatorManager mediatorManager,
RefundAgentManager refundAgentManager,
ArbitratorManager arbitratorService,
@Named(Config.USE_DEV_PRIVILEGE_KEYS) boolean useDevPrivilegeKeys) {
super(refundManager,
keyRing,
@ -72,8 +70,7 @@ public class RefundAgentView extends DisputeAgentView {
contractWindow,
tradeDetailsWindow,
accountAgeWitnessService,
mediatorManager,
refundAgentManager,
arbitratorService,
useDevPrivilegeKeys);
}

View File

@ -27,8 +27,7 @@ import bisq.core.alert.PrivateNotificationManager;
import bisq.core.support.dispute.Dispute;
import bisq.core.support.dispute.DisputeList;
import bisq.core.support.dispute.DisputeManager;
import bisq.core.support.dispute.mediation.mediator.MediatorManager;
import bisq.core.support.dispute.refund.refundagent.RefundAgentManager;
import bisq.core.support.dispute.arbitration.arbitrator.ArbitratorManager;
import bisq.core.trade.TradeManager;
import bisq.core.user.Preferences;
import bisq.core.util.coin.CoinFormatter;
@ -46,12 +45,10 @@ public abstract class DisputeClientView extends DisputeView {
ContractWindow contractWindow,
TradeDetailsWindow tradeDetailsWindow,
AccountAgeWitnessService accountAgeWitnessService,
MediatorManager mediatorManager,
RefundAgentManager refundAgentManager,
ArbitratorManager arbitratorManager,
boolean useDevPrivilegeKeys) {
super(DisputeManager, keyRing, tradeManager, formatter, preferences, disputeSummaryWindow, privateNotificationManager,
contractWindow, tradeDetailsWindow, accountAgeWitnessService,
mediatorManager, refundAgentManager, useDevPrivilegeKeys);
contractWindow, tradeDetailsWindow, accountAgeWitnessService, arbitratorManager, useDevPrivilegeKeys);
}
@Override

View File

@ -30,8 +30,7 @@ import bisq.core.support.dispute.Dispute;
import bisq.core.support.dispute.DisputeSession;
import bisq.core.support.dispute.arbitration.ArbitrationManager;
import bisq.core.support.dispute.arbitration.ArbitrationSession;
import bisq.core.support.dispute.mediation.mediator.MediatorManager;
import bisq.core.support.dispute.refund.refundagent.RefundAgentManager;
import bisq.core.support.dispute.arbitration.arbitrator.ArbitratorManager;
import bisq.core.trade.TradeManager;
import bisq.core.user.Preferences;
import bisq.core.util.FormattingUtils;
@ -56,12 +55,11 @@ public class ArbitrationClientView extends DisputeClientView {
ContractWindow contractWindow,
TradeDetailsWindow tradeDetailsWindow,
AccountAgeWitnessService accountAgeWitnessService,
MediatorManager mediatorManager,
RefundAgentManager refundAgentManager,
ArbitratorManager arbitratorManager,
@Named(Config.USE_DEV_PRIVILEGE_KEYS) boolean useDevPrivilegeKeys) {
super(arbitrationManager, keyRing, tradeManager, formatter, preferences, disputeSummaryWindow,
privateNotificationManager, contractWindow, tradeDetailsWindow, accountAgeWitnessService,
mediatorManager, refundAgentManager, useDevPrivilegeKeys);
arbitratorManager, useDevPrivilegeKeys);
}
@Override

View File

@ -30,10 +30,9 @@ import bisq.core.locale.Res;
import bisq.core.support.SupportType;
import bisq.core.support.dispute.Dispute;
import bisq.core.support.dispute.DisputeSession;
import bisq.core.support.dispute.arbitration.arbitrator.ArbitratorManager;
import bisq.core.support.dispute.mediation.MediationManager;
import bisq.core.support.dispute.mediation.MediationSession;
import bisq.core.support.dispute.mediation.mediator.MediatorManager;
import bisq.core.support.dispute.refund.refundagent.RefundAgentManager;
import bisq.core.trade.Contract;
import bisq.core.trade.TradeManager;
import bisq.core.user.Preferences;
@ -61,12 +60,11 @@ public class MediationClientView extends DisputeClientView {
ContractWindow contractWindow,
TradeDetailsWindow tradeDetailsWindow,
AccountAgeWitnessService accountAgeWitnessService,
MediatorManager mediatorManager,
RefundAgentManager refundAgentManager,
ArbitratorManager arbitratorManager,
@Named(Config.USE_DEV_PRIVILEGE_KEYS) boolean useDevPrivilegeKeys) {
super(mediationManager, keyRing, tradeManager, formatter, preferences, disputeSummaryWindow,
privateNotificationManager, contractWindow, tradeDetailsWindow, accountAgeWitnessService,
mediatorManager, refundAgentManager, useDevPrivilegeKeys);
arbitratorManager, useDevPrivilegeKeys);
}
@Override

View File

@ -28,10 +28,9 @@ import bisq.core.alert.PrivateNotificationManager;
import bisq.core.support.SupportType;
import bisq.core.support.dispute.Dispute;
import bisq.core.support.dispute.DisputeSession;
import bisq.core.support.dispute.mediation.mediator.MediatorManager;
import bisq.core.support.dispute.arbitration.arbitrator.ArbitratorManager;
import bisq.core.support.dispute.refund.RefundManager;
import bisq.core.support.dispute.refund.RefundSession;
import bisq.core.support.dispute.refund.refundagent.RefundAgentManager;
import bisq.core.trade.Contract;
import bisq.core.trade.TradeManager;
import bisq.core.user.Preferences;
@ -59,12 +58,11 @@ public class RefundClientView extends DisputeClientView {
ContractWindow contractWindow,
TradeDetailsWindow tradeDetailsWindow,
AccountAgeWitnessService accountAgeWitnessService,
MediatorManager mediatorManager,
RefundAgentManager refundAgentManager,
ArbitratorManager arbitratorManager,
@Named(Config.USE_DEV_PRIVILEGE_KEYS) boolean useDevPrivilegeKeys) {
super(refundManager, keyRing, tradeManager, formatter, preferences, disputeSummaryWindow,
privateNotificationManager, contractWindow, tradeDetailsWindow, accountAgeWitnessService,
mediatorManager, refundAgentManager, useDevPrivilegeKeys);
arbitratorManager, useDevPrivilegeKeys);
}
@Override