Add task interception UI

This commit is contained in:
Manfred Karrer 2015-03-13 12:39:22 +01:00
parent de6c293102
commit bb14db3b8d
21 changed files with 392 additions and 61 deletions

@ -21,6 +21,7 @@ import io.bitsquare.account.AccountSettings;
import io.bitsquare.gui.SystemTray;
import io.bitsquare.gui.components.Popups;
import io.bitsquare.gui.main.MainView;
import io.bitsquare.gui.main.debug.DebugView;
import io.bitsquare.gui.util.ImageUtil;
import io.bitsquare.persistence.Persistence;
import io.bitsquare.user.User;
@ -42,7 +43,9 @@ import javafx.application.Application;
import javafx.scene.*;
import javafx.scene.image.*;
import javafx.scene.input.*;
import javafx.stage.Modality;
import javafx.stage.Stage;
import javafx.stage.StageStyle;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
@ -58,6 +61,8 @@ public class BitsquareApp extends Application {
private BitsquareAppModule bitsquareAppModule;
private Injector injector;
private Stage primaryStage;
private Scene scene;
public static void setEnvironment(Environment env) {
BitsquareApp.env = env;
@ -65,6 +70,8 @@ public class BitsquareApp extends Application {
@Override
public void start(Stage primaryStage) throws IOException {
this.primaryStage = primaryStage;
log.trace("BitsquareApp.start");
bitsquareAppModule = new BitsquareAppModule(env, primaryStage);
injector = Guice.createInjector(bitsquareAppModule);
@ -92,10 +99,10 @@ public class BitsquareApp extends Application {
// load the main view and create the main scene
log.trace("viewLoader.load(MainView.class)");
ViewLoader viewLoader = injector.getInstance(CachingViewLoader.class);
CachingViewLoader viewLoader = injector.getInstance(CachingViewLoader.class);
View view = viewLoader.load(MainView.class);
Scene scene = new Scene((Parent) view.getRoot(), 1000, 600);
scene = new Scene((Parent) view.getRoot(), 1000, 600);
scene.getStylesheets().setAll(
"/io/bitsquare/gui/bitsquare.css",
"/io/bitsquare/gui/images.css");
@ -112,6 +119,8 @@ public class BitsquareApp extends Application {
if (new KeyCodeCombination(KeyCode.W, KeyCombination.SHORTCUT_DOWN).match(keyEvent) ||
new KeyCodeCombination(KeyCode.Q, KeyCombination.SHORTCUT_DOWN).match(keyEvent))
stop();
else if (new KeyCodeCombination(KeyCode.D, KeyCombination.SHORTCUT_DOWN).match(keyEvent))
showDebugWindow();
});
@ -139,6 +148,24 @@ public class BitsquareApp extends Application {
log.trace("primaryStage.show");
primaryStage.show();
//TODO just temp.
showDebugWindow();
}
private void showDebugWindow() {
ViewLoader viewLoader = injector.getInstance(ViewLoader.class);
View debugView = viewLoader.load(DebugView.class);
Parent parent = (Parent) debugView.getRoot();
Stage stage = new Stage();
stage.setScene(new Scene(parent));
stage.setTitle("Debug window");
stage.initModality(Modality.NONE);
stage.initStyle(StageStyle.UTILITY);
stage.initOwner(scene.getWindow());
stage.setX(primaryStage.getX() + primaryStage.getWidth() + 10);
stage.setY(primaryStage.getY());
stage.show();
}
@Override

@ -23,6 +23,8 @@ import org.bitcoinj.core.Transaction;
// Lets see if we get more restriction otherwise move it to other class
public class Restrictions {
public static final Coin MIN_TRADE_AMOUNT = Coin.parseCoin("0.0001");
public static final Coin MAX_TRADE_AMOUNT = Coin.parseCoin("10");
public static final Coin MIN_SECURITY_DEPOSIT = Coin.parseCoin("0.0001");
public static boolean isMinSpendableAmount(Coin amount) {

@ -99,8 +99,7 @@ public class MainView extends InitializableView<StackPane, MainViewModel> {
Pane portfolioButtonHolder = new Pane(portfolioButton);
Pane bankAccountComboBoxHolder = new Pane();
HBox leftNavPane = new HBox(
homeButton, buyButton, sellButton, portfolioButtonHolder, fundsButton, new Pane(msgButton)) {{
HBox leftNavPane = new HBox(homeButton, buyButton, sellButton, portfolioButtonHolder, fundsButton, new Pane(msgButton)) {{
setSpacing(10);
setLeftAnchor(this, 10d);
setTopAnchor(this, 0d);

@ -0,0 +1,82 @@
<?xml version="1.0" encoding="UTF-8"?>
<!--
~ This file is part of Bitsquare.
~
~ Bitsquare is free software: you can redistribute it and/or modify it
~ under the terms of the GNU Affero General Public License as published by
~ the Free Software Foundation, either version 3 of the License, or (at
~ your option) any later version.
~
~ Bitsquare is distributed in the hope that it will be useful, but WITHOUT
~ ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
~ FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public
~ License for more details.
~
~ You should have received a copy of the GNU Affero General Public License
~ along with Bitsquare. If not, see <http://www.gnu.org/licenses/>.
-->
<?import io.bitsquare.gui.components.TitledGroupBg?>
<?import javafx.geometry.Insets?>
<?import javafx.scene.control.*?>
<?import javafx.scene.layout.*?>
<GridPane fx:id="root" fx:controller="io.bitsquare.gui.main.debug.DebugView"
hgap="5.0" vgap="5.0"
AnchorPane.bottomAnchor="0.0" AnchorPane.leftAnchor="0.0"
AnchorPane.rightAnchor="0.0" AnchorPane.topAnchor="0.0"
xmlns:fx="http://javafx.com/fxml">
<padding>
<Insets bottom="10.0" left="25.0" top="30.0" right="25"/>
</padding>
<TitledGroupBg text="Intercept task" GridPane.rowSpan="8"/>
<Label text="Select Task:" GridPane.rowIndex="0">
<GridPane.margin>
<Insets top="10"/>
</GridPane.margin>
</Label>
<ComboBox fx:id="taskComboBox" onAction="#onSelectTask" promptText="Select task" GridPane.rowIndex="0" GridPane.columnIndex="1">
<GridPane.margin>
<Insets top="10"/>
</GridPane.margin>
</ComboBox>
<!-- <Label text="P2P network connection:" GridPane.rowIndex="1"/>
<TextField fx:id="connectionType" GridPane.rowIndex="1" GridPane.columnIndex="1"
mouseTransparent="true" focusTraversable="false"/>
<Label text="My external visible P2P network address:" GridPane.rowIndex="2"/>
<TextField fx:id="nodeAddress" GridPane.rowIndex="2" GridPane.columnIndex="1"
mouseTransparent="true" focusTraversable="false"/>
-->
<Label text="Intercept before run?:" GridPane.rowIndex="3">
<GridPane.margin>
<Insets bottom="-15"/>
</GridPane.margin>
</Label>
<CheckBox fx:id="interceptBeforeCheckBox" GridPane.rowIndex="3" GridPane.columnIndex="1">
<GridPane.margin>
<Insets bottom="-15"/>
</GridPane.margin>
</CheckBox>
<columnConstraints>
<ColumnConstraints hgrow="SOMETIMES" halignment="RIGHT" minWidth="200.0"/>
<ColumnConstraints hgrow="ALWAYS" minWidth="300.0"/>
</columnConstraints>
<rowConstraints>
<RowConstraints vgrow="NEVER"/>
<RowConstraints vgrow="NEVER"/>
<RowConstraints vgrow="NEVER"/>
</rowConstraints>
</GridPane>

@ -0,0 +1,188 @@
/*
* This file is part of Bitsquare.
*
* Bitsquare is free software: you can redistribute it and/or modify it
* under the terms of the GNU Affero General Public License as published by
* the Free Software Foundation, either version 3 of the License, or (at
* your option) any later version.
*
* Bitsquare is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public
* License for more details.
*
* You should have received a copy of the GNU Affero General Public License
* along with Bitsquare. If not, see <http://www.gnu.org/licenses/>.
*/
package io.bitsquare.gui.main.debug;
import io.bitsquare.trade.protocol.availability.CheckOfferAvailabilityProtocol;
import io.bitsquare.trade.protocol.availability.tasks.RequestIsOfferAvailable;
import io.bitsquare.trade.protocol.placeoffer.PlaceOfferProtocol;
import io.bitsquare.trade.protocol.placeoffer.tasks.AddOfferToRemoteOfferBook;
import io.bitsquare.trade.protocol.placeoffer.tasks.BroadcastCreateOfferFeeTx;
import io.bitsquare.trade.protocol.placeoffer.tasks.CreateOfferFeeTx;
import io.bitsquare.trade.protocol.placeoffer.tasks.ValidateOffer;
import io.bitsquare.trade.protocol.trade.offerer.BuyerAsOffererProtocol;
import io.bitsquare.trade.protocol.trade.offerer.tasks.CreateDepositTx;
import io.bitsquare.trade.protocol.trade.offerer.tasks.ProcessPayoutTxPublishedMessage;
import io.bitsquare.trade.protocol.trade.offerer.tasks.ProcessRequestOffererPublishDepositTxMessage;
import io.bitsquare.trade.protocol.trade.offerer.tasks.ProcessRequestTakeOfferMessage;
import io.bitsquare.trade.protocol.trade.offerer.tasks.ProcessTakeOfferFeePayedMessage;
import io.bitsquare.trade.protocol.trade.offerer.tasks.RespondToTakeOfferRequest;
import io.bitsquare.trade.protocol.trade.offerer.tasks.SendBankTransferInitedMessage;
import io.bitsquare.trade.protocol.trade.offerer.tasks.SendDepositTxIdToTaker;
import io.bitsquare.trade.protocol.trade.offerer.tasks.SendTakerDepositPaymentRequest;
import io.bitsquare.trade.protocol.trade.offerer.tasks.SetupListenerForBlockChainConfirmation;
import io.bitsquare.trade.protocol.trade.offerer.tasks.SignAndPublishDepositTx;
import io.bitsquare.trade.protocol.trade.offerer.tasks.SignPayoutTx;
import io.bitsquare.trade.protocol.trade.offerer.tasks.VerifyAndSignContract;
import io.bitsquare.trade.protocol.trade.offerer.tasks.VerifyTakeOfferFeePayment;
import io.bitsquare.trade.protocol.trade.offerer.tasks.VerifyTakerAccount;
import io.bitsquare.trade.protocol.trade.taker.SellerAsTakerProtocol;
import io.bitsquare.trade.protocol.trade.taker.tasks.CreateAndSignContract;
import io.bitsquare.trade.protocol.trade.taker.tasks.PayDeposit;
import io.bitsquare.trade.protocol.trade.taker.tasks.PayTakeOfferFee;
import io.bitsquare.trade.protocol.trade.taker.tasks.ProcessBankTransferInitedMessage;
import io.bitsquare.trade.protocol.trade.taker.tasks.ProcessDepositTxPublishedMessage;
import io.bitsquare.trade.protocol.trade.taker.tasks.ProcessRespondToTakeOfferRequestMessage;
import io.bitsquare.trade.protocol.trade.taker.tasks.ProcessTakerDepositPaymentRequestMessage;
import io.bitsquare.trade.protocol.trade.taker.tasks.RequestTakeOffer;
import io.bitsquare.trade.protocol.trade.taker.tasks.SendPayoutTxToOfferer;
import io.bitsquare.trade.protocol.trade.taker.tasks.SendSignedTakerDepositTxAsHex;
import io.bitsquare.trade.protocol.trade.taker.tasks.SendTakeOfferFeePayedMessage;
import io.bitsquare.trade.protocol.trade.taker.tasks.SignAndPublishPayoutTx;
import io.bitsquare.trade.protocol.trade.taker.tasks.TakerCommitDepositTx;
import io.bitsquare.trade.protocol.trade.taker.tasks.VerifyOfferFeePayment;
import io.bitsquare.trade.protocol.trade.taker.tasks.VerifyOffererAccount;
import io.bitsquare.util.tasks.TaskInterception;
import java.util.Arrays;
import javax.inject.Inject;
import viewfx.view.FxmlView;
import viewfx.view.support.InitializableView;
import javafx.collections.FXCollections;
import javafx.collections.ObservableList;
import javafx.fxml.FXML;
import javafx.scene.control.*;
import javafx.util.StringConverter;
@FxmlView
public class DebugView extends InitializableView {
@FXML ComboBox<Class> taskComboBox;
@FXML CheckBox interceptBeforeCheckBox;
@Inject
public DebugView() {
}
@Override
public void initialize() {
interceptBeforeCheckBox.setSelected(true);
final ObservableList<Class> items = FXCollections.observableArrayList(Arrays.asList(
/*---- Protocol ----*/
CheckOfferAvailabilityProtocol.class,
io.bitsquare.trade.protocol.availability.tasks.GetPeerAddress.class,
RequestIsOfferAvailable.class,
Boolean.class, /* used as seperator*/
/*---- Protocol ----*/
PlaceOfferProtocol.class,
ValidateOffer.class,
CreateOfferFeeTx.class,
BroadcastCreateOfferFeeTx.class,
AddOfferToRemoteOfferBook.class,
Boolean.class, /* used as seperator*/
/*---- Protocol ----*/
BuyerAsOffererProtocol.class,
ProcessRequestTakeOfferMessage.class,
RespondToTakeOfferRequest.class,
ProcessTakeOfferFeePayedMessage.class,
CreateDepositTx.class,
SendTakerDepositPaymentRequest.class,
ProcessRequestOffererPublishDepositTxMessage.class,
VerifyTakerAccount.class,
VerifyAndSignContract.class,
SignAndPublishDepositTx.class,
SetupListenerForBlockChainConfirmation.class,
SendDepositTxIdToTaker.class,
SignPayoutTx.class,
VerifyTakeOfferFeePayment.class,
SendBankTransferInitedMessage.class,
ProcessPayoutTxPublishedMessage.class,
Boolean.class, /* used as seperator*/
/*---- Protocol ----*/
SellerAsTakerProtocol.class,
io.bitsquare.trade.protocol.trade.taker.tasks.GetPeerAddress.class,
RequestTakeOffer.class,
ProcessRespondToTakeOfferRequestMessage.class,
PayTakeOfferFee.class,
SendTakeOfferFeePayedMessage.class,
ProcessTakerDepositPaymentRequestMessage.class,
VerifyOffererAccount.class,
CreateAndSignContract.class,
PayDeposit.class,
SendSignedTakerDepositTxAsHex.class,
ProcessDepositTxPublishedMessage.class,
TakerCommitDepositTx.class,
ProcessBankTransferInitedMessage.class,
SignAndPublishPayoutTx.class,
VerifyOfferFeePayment.class,
SendPayoutTxToOfferer.class
)
);
taskComboBox.setVisibleRowCount(items.size());
taskComboBox.setItems(items);
taskComboBox.setConverter(new StringConverter<Class>() {
@Override
public String toString(Class item) {
if (item.getSimpleName().contains("Protocol"))
return "--- " + item.getSimpleName() + " ---";
else if (item.getSimpleName().contains("Boolean"))
return "";
else
return item.getSimpleName();
}
@Override
public Class fromString(String s) {
return null;
}
});
}
@FXML
void onSelectTask() {
Class item = taskComboBox.getSelectionModel().getSelectedItem();
if (!item.getSimpleName().contains("Protocol")) {
if (interceptBeforeCheckBox.isSelected())
TaskInterception.taskToInterceptBeforeRun = item;
else
TaskInterception.taskToInterceptAfterRun = item;
}
}
}

@ -207,7 +207,7 @@ public class BootstrappedPeerBuilder {
futureRelayNAT.addListener(new BaseFutureListener<BaseFuture>() {
@Override
public void operationComplete(BaseFuture future) throws Exception {
public void operationComplete(BaseFuture futureRelayNAT) throws Exception {
if (futureDiscover.isSuccess()) {
if (useManualPortForwarding) {
setState(BootstrapState.DISCOVERY_MANUAL_PORT_FORWARDING_SUCCEEDED,
@ -228,7 +228,7 @@ public class BootstrappedPeerBuilder {
bootstrap();
}
else {
if (future.isSuccess()) {
if (futureRelayNAT.isSuccess()) {
// relay mode succeeded
setState(BootstrapState.RELAY_SUCCEEDED, "Bootstrap using relay was successful.");
bootstrap();

@ -19,6 +19,7 @@ package io.bitsquare.offer;
import io.bitsquare.arbitrator.Arbitrator;
import io.bitsquare.bank.BankAccountType;
import io.bitsquare.btc.Restrictions;
import io.bitsquare.locale.Country;
import org.bitcoinj.core.Coin;
@ -38,7 +39,6 @@ import javafx.beans.property.ObjectProperty;
import javafx.beans.property.SimpleObjectProperty;
import static com.google.common.base.Preconditions.*;
import static io.bitsquare.btc.Restrictions.MIN_TRADE_AMOUNT;
//TODO flatten down?
@ -226,9 +226,9 @@ public class Offer implements Serializable {
}
public State getState() {
if(state == null)
if (state == null)
setState(State.UNKNOWN);
return state;
}
@ -253,17 +253,15 @@ public class Offer implements Serializable {
checkNotNull(getMinAmount(), "MinAmount is null");
checkNotNull(getPrice(), "Price is null");
checkArgument(getMinAmount().compareTo(MIN_TRADE_AMOUNT) >= 0, "MinAmount is less then " + MIN_TRADE_AMOUNT);
checkArgument(getAmount().compareTo(MIN_TRADE_AMOUNT) >= 0, "Amount is less then " + MIN_TRADE_AMOUNT);
checkArgument(getMinAmount().compareTo(Restrictions.MIN_TRADE_AMOUNT) >= 0, "MinAmount is less then " + Restrictions.MIN_TRADE_AMOUNT.toFriendlyString());
checkArgument(getAmount().compareTo(Restrictions.MAX_TRADE_AMOUNT) <= 0, "Amount is larger then " + Restrictions.MAX_TRADE_AMOUNT.toFriendlyString());
checkArgument(getAmount().compareTo(getMinAmount()) >= 0, "MinAmount is larger then Amount");
checkArgument(getSecurityDeposit().isPositive(), "SecurityDeposit is not positive");
checkArgument(getPrice().isPositive(), "Price is 0 or negative");
// TODO check balance
// securityDeposit
// Coin totalsToFund
// getAddressInfoByTradeID(offerId)
// TODO when offer is flattened continue here...
checkArgument(getSecurityDeposit().compareTo(Restrictions.MIN_SECURITY_DEPOSIT) >= 0,
"SecurityDeposit is less then " + Restrictions.MIN_SECURITY_DEPOSIT.toFriendlyString());
checkArgument(getPrice().isPositive(), "Price is not a positive value");
// TODO check upper and lower bounds for fiat
}
@Override

@ -31,10 +31,10 @@ import io.bitsquare.offer.OpenOffer;
import io.bitsquare.persistence.Persistence;
import io.bitsquare.trade.handlers.TransactionResultHandler;
import io.bitsquare.trade.listeners.SendMessageListener;
import io.bitsquare.trade.protocol.offer.CheckOfferAvailabilityModel;
import io.bitsquare.trade.protocol.offer.CheckOfferAvailabilityProtocol;
import io.bitsquare.trade.protocol.offer.messages.ReportOfferAvailabilityMessage;
import io.bitsquare.trade.protocol.offer.messages.RequestIsOfferAvailableMessage;
import io.bitsquare.trade.protocol.availability.CheckOfferAvailabilityModel;
import io.bitsquare.trade.protocol.availability.CheckOfferAvailabilityProtocol;
import io.bitsquare.trade.protocol.availability.messages.ReportOfferAvailabilityMessage;
import io.bitsquare.trade.protocol.availability.messages.RequestIsOfferAvailableMessage;
import io.bitsquare.trade.protocol.placeoffer.PlaceOfferModel;
import io.bitsquare.trade.protocol.placeoffer.PlaceOfferProtocol;
import io.bitsquare.trade.protocol.trade.offerer.BuyerAsOffererModel;

@ -15,7 +15,7 @@
* along with Bitsquare. If not, see <http://www.gnu.org/licenses/>.
*/
package io.bitsquare.trade.protocol.offer;
package io.bitsquare.trade.protocol.availability;
import io.bitsquare.network.Peer;
import io.bitsquare.offer.Offer;

@ -15,14 +15,14 @@
* along with Bitsquare. If not, see <http://www.gnu.org/licenses/>.
*/
package io.bitsquare.trade.protocol.offer;
package io.bitsquare.trade.protocol.availability;
import io.bitsquare.network.Message;
import io.bitsquare.network.Peer;
import io.bitsquare.offer.Offer;
import io.bitsquare.trade.protocol.offer.messages.ReportOfferAvailabilityMessage;
import io.bitsquare.trade.protocol.offer.tasks.GetPeerAddress;
import io.bitsquare.trade.protocol.offer.tasks.RequestIsOfferAvailable;
import io.bitsquare.trade.protocol.availability.messages.ReportOfferAvailabilityMessage;
import io.bitsquare.trade.protocol.availability.tasks.GetPeerAddress;
import io.bitsquare.trade.protocol.availability.tasks.RequestIsOfferAvailable;
import io.bitsquare.util.tasks.TaskRunner;
import org.slf4j.Logger;

@ -15,7 +15,7 @@
* along with Bitsquare. If not, see <http://www.gnu.org/licenses/>.
*/
package io.bitsquare.trade.protocol.offer.messages;
package io.bitsquare.trade.protocol.availability.messages;
import io.bitsquare.trade.protocol.trade.OfferMessage;

@ -15,7 +15,7 @@
* along with Bitsquare. If not, see <http://www.gnu.org/licenses/>.
*/
package io.bitsquare.trade.protocol.offer.messages;
package io.bitsquare.trade.protocol.availability.messages;
import io.bitsquare.trade.protocol.trade.OfferMessage;

@ -15,11 +15,11 @@
* along with Bitsquare. If not, see <http://www.gnu.org/licenses/>.
*/
package io.bitsquare.trade.protocol.offer.tasks;
package io.bitsquare.trade.protocol.availability.tasks;
import io.bitsquare.network.Peer;
import io.bitsquare.trade.listeners.GetPeerAddressListener;
import io.bitsquare.trade.protocol.offer.CheckOfferAvailabilityModel;
import io.bitsquare.trade.protocol.availability.CheckOfferAvailabilityModel;
import io.bitsquare.util.tasks.Task;
import io.bitsquare.util.tasks.TaskRunner;

@ -15,11 +15,11 @@
* along with Bitsquare. If not, see <http://www.gnu.org/licenses/>.
*/
package io.bitsquare.trade.protocol.offer.tasks;
package io.bitsquare.trade.protocol.availability.tasks;
import io.bitsquare.trade.listeners.SendMessageListener;
import io.bitsquare.trade.protocol.offer.CheckOfferAvailabilityModel;
import io.bitsquare.trade.protocol.offer.messages.RequestIsOfferAvailableMessage;
import io.bitsquare.trade.protocol.availability.CheckOfferAvailabilityModel;
import io.bitsquare.trade.protocol.availability.messages.RequestIsOfferAvailableMessage;
import io.bitsquare.util.tasks.Task;
import io.bitsquare.util.tasks.TaskRunner;

@ -18,7 +18,7 @@
package io.bitsquare.trade.protocol.placeoffer;
import io.bitsquare.trade.handlers.TransactionResultHandler;
import io.bitsquare.trade.protocol.placeoffer.tasks.AddOffer;
import io.bitsquare.trade.protocol.placeoffer.tasks.AddOfferToRemoteOfferBook;
import io.bitsquare.trade.protocol.placeoffer.tasks.BroadcastCreateOfferFeeTx;
import io.bitsquare.trade.protocol.placeoffer.tasks.CreateOfferFeeTx;
import io.bitsquare.trade.protocol.placeoffer.tasks.ValidateOffer;
@ -67,8 +67,9 @@ public class PlaceOfferProtocol {
ValidateOffer.class,
CreateOfferFeeTx.class,
BroadcastCreateOfferFeeTx.class,
AddOffer.class
AddOfferToRemoteOfferBook.class
);
sequence.run();
}
}

@ -24,18 +24,15 @@ import io.bitsquare.util.tasks.TaskRunner;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
public class AddOffer extends Task<PlaceOfferModel> {
private static final Logger log = LoggerFactory.getLogger(AddOffer.class);
public class AddOfferToRemoteOfferBook extends Task<PlaceOfferModel> {
private static final Logger log = LoggerFactory.getLogger(AddOfferToRemoteOfferBook.class);
public AddOffer(TaskRunner taskHandler, PlaceOfferModel model) {
public AddOfferToRemoteOfferBook(TaskRunner taskHandler, PlaceOfferModel model) {
super(taskHandler, model);
}
@Override
protected void run() {
// need to write data before storage, otherwise hash is different when removing offer!
model.getOffer().setOfferFeePaymentTxID(model.getTransaction().getHashAsString());
model.getOfferBookService().addOffer(model.getOffer(),
() -> {
complete();

@ -42,10 +42,15 @@ public class BroadcastCreateOfferFeeTx extends Task<PlaceOfferModel> {
@Override
public void onSuccess(Transaction transaction) {
log.info("Broadcast of offer fee payment succeeded: transaction = " + transaction.toString());
if (transaction == null)
failed("Broadcast of offer fee payment failed because transaction = null.");
else
if (transaction != null) {
// need to write data before storage, otherwise hash is different when removing offer from DHT!
model.getOffer().setOfferFeePaymentTxID(model.getTransaction().getHashAsString());
complete();
}
else {
failed("Broadcast of offer fee payment failed because transaction = null.");
}
}
@Override

@ -37,6 +37,7 @@ public class CreateOfferFeeTx extends Task<PlaceOfferModel> {
protected void run() {
try {
Transaction transaction = model.getWalletService().createOfferFeeTx(model.getOffer().getId());
model.setTransaction(transaction);
complete();

@ -35,7 +35,7 @@ public class ValidateOffer extends Task<PlaceOfferModel> {
protected void run() {
try {
model.getOffer().validate();
complete();
} catch (Exception e) {
failed(e);

@ -0,0 +1,27 @@
/*
* This file is part of Bitsquare.
*
* Bitsquare is free software: you can redistribute it and/or modify it
* under the terms of the GNU Affero General Public License as published by
* the Free Software Foundation, either version 3 of the License, or (at
* your option) any later version.
*
* Bitsquare is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public
* License for more details.
*
* You should have received a copy of the GNU Affero General Public License
* along with Bitsquare. If not, see <http://www.gnu.org/licenses/>.
*/
package io.bitsquare.util.tasks;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
public class TaskInterception {
private static final Logger log = LoggerFactory.getLogger(TaskInterception.class);
public static Class<? extends Task> taskToInterceptBeforeRun;
public static Class<? extends Task> taskToInterceptAfterRun;
}

@ -38,10 +38,10 @@ public class TaskRunner<T extends SharedModel> {
private final FaultHandler faultHandler;
private boolean failed = false;
private Class<? extends Task> currentTask;
private Class<? extends Task> previousTask;
private boolean isCanceled;
private Class<? extends Task> currentTask;
public TaskRunner(T sharedModel, ResultHandler resultHandler, FaultHandler faultHandler) {
this.sharedModel = sharedModel;
@ -53,18 +53,16 @@ public class TaskRunner<T extends SharedModel> {
next();
}
public Class<? extends Task> getCurrentTask() {
return currentTask;
}
protected void next() {
if (!failed && !isCanceled) {
if (tasks.size() > 0) {
try {
setCurrentTask(tasks.poll());
currentTask = tasks.poll();
interceptBeforeRun(currentTask);
log.trace("Run task: " + currentTask.getSimpleName());
currentTask.getDeclaredConstructor(TaskRunner.class, sharedModel.getClass()).newInstance(this, sharedModel).run();
setPreviousTask(currentTask);
interceptAfterRun(currentTask);
} catch (Throwable t) {
t.printStackTrace();
faultHandler.handleFault(t.getMessage(), t);
@ -76,18 +74,21 @@ public class TaskRunner<T extends SharedModel> {
}
}
protected void interceptBeforeRun(Class<? extends Task> task) {
if (task == TaskInterception.taskToInterceptBeforeRun)
throw new RuntimeException("Task intercepted before run executed: task = " + task.getSimpleName());
}
protected void interceptAfterRun(Class<? extends Task> task) {
if (task == TaskInterception.taskToInterceptAfterRun)
throw new RuntimeException("Task intercepted after run executed: task = " + task.getSimpleName());
}
public void cancel() {
isCanceled = true;
}
protected void setPreviousTask(Class<? extends Task> task) {
previousTask = task;
}
protected void setCurrentTask(Class<? extends Task> task) {
currentTask = task;
}
public void addTask(Class<? extends Task> task) {
tasks.add(task);
}
@ -97,6 +98,7 @@ public class TaskRunner<T extends SharedModel> {
}
public void complete() {
log.trace("Task completed: " + currentTask.getSimpleName());
next();
}
@ -105,9 +107,11 @@ public class TaskRunner<T extends SharedModel> {
}
public void handleFault(String message, @NotNull Throwable throwable) {
log.error("Task failed: " + currentTask.getSimpleName());
log.debug(throwable.getMessage());
failed = true;
faultHandler.handleFault(message, throwable);
}
}