diff --git a/.idea/runConfigurations.xml b/.idea/runConfigurations.xml
deleted file mode 100644
index 797acea..0000000
--- a/.idea/runConfigurations.xml
+++ /dev/null
@@ -1,10 +0,0 @@
-
-
-
-
-
-
\ No newline at end of file
diff --git a/Data-Integration.iml b/Data-Integration.iml
index 6f3b297..0133fd5 100644
--- a/Data-Integration.iml
+++ b/Data-Integration.iml
@@ -6,7 +6,7 @@
-
+
@@ -20,24 +20,24 @@
-
-
+
+
-
+
-
-
-
-
-
-
-
-
+
+
+
+
+
+
+
+
diff --git a/src/OrderBook/OrderBook.java b/src/OrderBook/OrderBook.java
index 0e15e35..3522d2b 100644
--- a/src/OrderBook/OrderBook.java
+++ b/src/OrderBook/OrderBook.java
@@ -29,7 +29,7 @@ private void sortedPlace(Order order){
return;
}
else if (sideOfBook.get(i).price < order.price && !isAsk ||
- sideOfBook.get(i).price > order.price && isAsk){
+ sideOfBook.get(i).price > order.price && isAsk) {
if (order.side == Side.ASK)
asks.add(i,order);
else
@@ -84,8 +84,14 @@ public void placeOrder(Order order){
sittingVolume += order.size;
adjustBBO();
placedOrders.put(order.orderID, order.orderID);
+
+ if (bestBidPrice > bestAskPrice && bestBidPrice != -1 && bestAskPrice != -1) {
+ // NEW ASSERTION, check for crossed orderbook condition where best bid over best ask
+ throw new RuntimeException("Crossed orderbook condition!");
+ }
}
+
/**
* Registers fill event on the order book
* WARNING: Will throw if fill event doesn't fill any sitting order
@@ -100,4 +106,4 @@ public void fillEvent(Fill fill){
adjustBBO();
recordedFills.put(fill.orderID, fill.orderID);
}
-}
+}
\ No newline at end of file
diff --git a/src/test/testOrderBook.java b/src/test/testOrderBook.java
index 063dff6..bd5c24d 100644
--- a/src/test/testOrderBook.java
+++ b/src/test/testOrderBook.java
@@ -1,6 +1,12 @@
import OrderBook.Order;
+import OrderBook.Fill;
import OrderBook.OrderBook;
import OrderBook.Side;
+
+import static OrderBook.OrderType.MARKET_ORDER;
+import static OrderBook.OrderType.LIMIT_ORDER;
+import static OrderBook.OrderType.STOP_LIMIT_ORDER;
+
import org.junit.jupiter.api.Test;
import static org.junit.jupiter.api.Assertions.*;
@@ -168,4 +174,146 @@ void placeTwoAsk() {
assertEquals(-1f, testSubject.bestBidPrice);
assertEquals(1.8f, testSubject.sittingVolume);
}
-}
+
+ @Test
+ void placeOneBidSTOPLIMIT() {
+ // Init and checking start conditions
+ OrderBook testSubject = new OrderBook();
+ assertEquals(0, testSubject.asks.size());
+ assertEquals(0, testSubject.bids.size());
+ assertEquals(-1f, testSubject.bestAskPrice);
+ assertEquals(-1f, testSubject.bestBidPrice);
+ assertEquals(0f, testSubject.sittingVolume);
+ // Operation
+ Order newSTOPLIMIT = new Order("helloUUID!", "helloproductID!", 2.2f, 99.99f,
+ STOP_LIMIT_ORDER, false, Side.BID, 1677598183L);
+ testSubject.placeOrder(newSTOPLIMIT);
+ // Checking Operation
+ assertEquals(0, testSubject.asks.size());
+ assertEquals(1, testSubject.bids.size());
+ assertEquals(99.99f, testSubject.bids.getFirst().price);
+ assertEquals(2.2f, testSubject.bids.getFirst().size);
+ assertEquals(1677598183L, testSubject.bids.getFirst().createdTs);
+ assertEquals(-1f, testSubject.bestAskPrice);
+ assertEquals(99.99f, testSubject.bestBidPrice);
+ assertEquals(2.2f, testSubject.sittingVolume);
+ }
+
+ @Test
+ void placeOneAskLIMITORDER() {
+ // Init and checking start conditions
+ OrderBook testSubject = new OrderBook();
+ assertEquals(0, testSubject.asks.size());
+ assertEquals(0, testSubject.bids.size());
+ assertEquals(-1f, testSubject.bestAskPrice);
+ assertEquals(-1f, testSubject.bestBidPrice);
+ assertEquals(0f, testSubject.sittingVolume);
+ // Operation
+ Order newLIMIT = new Order("helloUUID!", "helloproductID!", 6.9f, 69.69f,
+ LIMIT_ORDER, false, Side.ASK, 69L);
+ testSubject.placeOrder(newLIMIT);
+ // Checking Operation
+ assertEquals(1, testSubject.asks.size());
+ assertEquals(0, testSubject.bids.size());
+ assertEquals(69.69f, testSubject.asks.getFirst().price);
+ assertEquals(6.9f, testSubject.asks.getFirst().size);
+ assertEquals(69L, testSubject.asks.getFirst().createdTs);
+ assertEquals(69.69f, testSubject.bestAskPrice);
+ assertEquals(-1f, testSubject.bestBidPrice);
+ assertEquals(6.9f, testSubject.sittingVolume);
+ }
+
+ @Test
+ void placeTwoAskMARKETORDERandOneBidLIMITORDERthrowCROSSED_ORDERBOOK() {
+ // Init and checking start conditions
+ OrderBook testSubject = new OrderBook();
+ assertEquals(0, testSubject.asks.size());
+ assertEquals(0, testSubject.bids.size());
+ assertEquals(-1f, testSubject.bestAskPrice);
+ assertEquals(-1f, testSubject.bestBidPrice);
+ assertEquals(0f, testSubject.sittingVolume);
+ // Operation
+ Order newMARKETORDER = new Order("helloUUID!", "helloproductID_1!", 106.0f,
+ 99.99f, MARKET_ORDER, false, Side.ASK, 1677598097L);
+ testSubject.placeOrder(newMARKETORDER);
+ // Checking Operation
+ assertEquals(1, testSubject.asks.size());
+ assertEquals(0, testSubject.bids.size());
+ assertEquals(99.99f, testSubject.asks.getFirst().price); // No orders have been filled yet
+ assertEquals(106.0f, testSubject.asks.getFirst().size); // No orders have been filled yet
+ assertEquals(1677598097L, testSubject.asks.getFirst().createdTs);
+ assertEquals(99.99f, testSubject.bestAskPrice);
+ assertEquals(-1f, testSubject.bestBidPrice);
+ assertEquals(106.0f, testSubject.sittingVolume);
+ // Operation
+ newMARKETORDER = new Order("helloUUID!", "helloproductID_2!", 3.7f,
+ 0.01f, MARKET_ORDER, false, Side.ASK, 1677598150L);
+ testSubject.placeOrder(newMARKETORDER);
+ // Checking Operation
+ assertEquals(2, testSubject.asks.size());
+ assertEquals(0, testSubject.bids.size());
+ assertEquals(0.01f, testSubject.asks.getFirst().price);
+ assertEquals(3.7f, testSubject.asks.getFirst().size);
+ assertEquals(1677598150L, testSubject.asks.getFirst().createdTs);
+ assertEquals(0.01f, testSubject.bestAskPrice);
+ assertEquals(-1f, testSubject.bestBidPrice);
+ assertEquals(109.7f, testSubject.sittingVolume);
+ /* // Operation
+ Order newLIMITORDER = new Order("helloUUID!", "helloproductID_3!", 100.0f,
+ 49.97f, LIMIT_ORDER, false, Side.BID, 1677598167L);
+ testSubject.placeOrder(newLIMITORDER);
+ // Checking Operation, note CROSSED ORDERBOOK */
+ }
+
+ @Test
+ void placeOneBidandOneAskLIMITORDERfillEvent() {
+ // Init and checking start conditions
+ OrderBook testSubject = new OrderBook();
+ assertEquals(0, testSubject.asks.size());
+ assertEquals(0, testSubject.bids.size());
+ assertEquals(-1f, testSubject.bestAskPrice);
+ assertEquals(-1f, testSubject.bestBidPrice);
+ assertEquals(0f, testSubject.sittingVolume);
+ // Operation
+ Order newLIMITORDER = new Order("helloUUID!", "helloproductID_1!", 100.0f,
+ 27.37f, LIMIT_ORDER, false, Side.BID, 100L);
+ testSubject.placeOrder(newLIMITORDER);
+ assertEquals(0, testSubject.asks.size());
+ assertEquals(1, testSubject.bids.size());
+ assertEquals(27.37f, testSubject.bids.getFirst().price);
+ assertEquals(100.0f, testSubject.bids.getFirst().size);
+ assertEquals(100L, testSubject.bids.getFirst().createdTs);
+ assertEquals(-1f, testSubject.bestAskPrice);
+ assertEquals(27.37f, testSubject.bestBidPrice);
+ assertEquals(100.0f, testSubject.sittingVolume);
+ // Operation
+ newLIMITORDER = new Order("helloUUID!", "helloproductID_2!", 50.0f,
+ 34.31f, LIMIT_ORDER, false, Side.ASK, 200L);
+ testSubject.placeOrder(newLIMITORDER);
+ assertEquals(1, testSubject.asks.size());
+ assertEquals(1, testSubject.bids.size());
+ assertEquals(34.31f, testSubject.asks.getFirst().price);
+ assertEquals(50.0f, testSubject.asks.getFirst().size);
+ assertEquals(27.37f, testSubject.bids.getFirst().price);
+ assertEquals(100.0f, testSubject.bids.getFirst().size);
+ assertEquals(200L, testSubject.asks.getFirst().createdTs);
+ assertEquals(100L, testSubject.bids.getFirst().createdTs);
+ assertEquals(34.31f, testSubject.bestAskPrice);
+ assertEquals(27.37f, testSubject.bestBidPrice);
+ assertEquals(150.0f, testSubject.sittingVolume);
+ // Operation
+ Fill newFill = new Fill("helloproductID_2!", "helloclientID!", 35.5f,
+ 34.31f, 1.5f, LIMIT_ORDER, Side.ASK, 330L);
+ testSubject.fillEvent(newFill);
+ assertEquals(1, testSubject.asks.size());
+ assertEquals(1, testSubject.bids.size());
+ assertEquals(34.31f, testSubject.asks.getFirst().price);
+ assertEquals(14.5f, testSubject.asks.getFirst().size);
+ assertEquals(27.37f, testSubject.bids.getFirst().price);
+ assertEquals(100.0f, testSubject.bids.getFirst().size);
+ assertEquals(100L, testSubject.bids.getFirst().createdTs);
+ assertEquals(34.31f, testSubject.bestAskPrice);
+ assertEquals(27.37f, testSubject.bestBidPrice);
+ assertEquals(114.5f, testSubject.sittingVolume);
+ }
+}
\ No newline at end of file