code.vegaprotocol.io/vega@v0.79.0/datanode/service/market_depth_test.go (about) 1 // Copyright (C) 2023 Gobalsky Labs Limited 2 // 3 // This program is free software: you can redistribute it and/or modify 4 // it under the terms of the GNU Affero General Public License as 5 // published by the Free Software Foundation, either version 3 of the 6 // License, or (at your option) any later version. 7 // 8 // This program is distributed in the hope that it will be useful, 9 // but WITHOUT ANY WARRANTY; without even the implied warranty of 10 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 11 // GNU Affero General Public License for more details. 12 // 13 // You should have received a copy of the GNU Affero General Public License 14 // along with this program. If not, see <http://www.gnu.org/licenses/>. 15 16 package service_test 17 18 import ( 19 "context" 20 "testing" 21 "time" 22 23 "code.vegaprotocol.io/vega/core/types" 24 "code.vegaprotocol.io/vega/datanode/entities" 25 "code.vegaprotocol.io/vega/datanode/service" 26 "code.vegaprotocol.io/vega/datanode/service/mocks" 27 "code.vegaprotocol.io/vega/libs/num" 28 "code.vegaprotocol.io/vega/logging" 29 30 "github.com/golang/mock/gomock" 31 "github.com/shopspring/decimal" 32 "github.com/stretchr/testify/assert" 33 "github.com/stretchr/testify/require" 34 ) 35 36 type MDS struct { 37 service *service.MarketDepth 38 ctrl *gomock.Controller 39 pos *mocks.MockPositionStore 40 amm *mocks.MockAMMStore 41 orders *mocks.MockOrderStore 42 marketData *mocks.MockMarketDataStore 43 markets *mocks.MockMarketStore 44 assets *mocks.MockAssetStore 45 } 46 47 func getTestMDS(t *testing.T) *MDS { 48 t.Helper() 49 ctrl := gomock.NewController(t) 50 pos := mocks.NewMockPositionStore(ctrl) 51 orders := mocks.NewMockOrderStore(ctrl) 52 marketData := mocks.NewMockMarketDataStore(ctrl) 53 amm := mocks.NewMockAMMStore(ctrl) 54 markets := mocks.NewMockMarketStore(ctrl) 55 56 amm.EXPECT().ListActive(gomock.Any()).Return(nil, nil).AnyTimes() 57 58 return &MDS{ 59 service: service.NewMarketDepth(service.NewDefaultConfig().MarketDepth, orders, amm, marketData, pos, nil, markets, logging.NewTestLogger()), 60 ctrl: ctrl, 61 pos: pos, 62 amm: amm, 63 orders: orders, 64 marketData: marketData, 65 markets: markets, 66 } 67 } 68 69 func buildOrder(id string, side types.Side, orderType types.OrderType, price uint64, size uint64, remaining uint64) *types.Order { 70 order := &types.Order{ 71 ID: id, 72 Side: side, 73 Type: orderType, 74 Price: num.NewUint(price), 75 OriginalPrice: num.NewUint(price), 76 Size: size, 77 Remaining: remaining, 78 TimeInForce: types.OrderTimeInForceGTC, 79 Status: types.OrderStatusActive, 80 MarketID: "M", 81 } 82 return order 83 } 84 85 func TestBuyPriceLevels(t *testing.T) { 86 mds := getTestMDS(t) 87 vegaTime := time.Now() 88 89 order1 := buildOrder("Order1", types.SideBuy, types.OrderTypeLimit, 100, 9, 9) 90 mds.service.AddOrder(order1, vegaTime, 1) 91 92 order2 := buildOrder("Order2", types.SideBuy, types.OrderTypeLimit, 102, 7, 7) 93 mds.service.AddOrder(order2, vegaTime, 2) 94 95 order3 := buildOrder("Order3", types.SideBuy, types.OrderTypeLimit, 101, 8, 8) 96 mds.service.AddOrder(order3, vegaTime, 3) 97 98 order4 := buildOrder("Order4", types.SideBuy, types.OrderTypeLimit, 99, 10, 10) 99 mds.service.AddOrder(order4, vegaTime, 4) 100 101 assert.Equal(t, 4, mds.service.GetBuyPriceLevels("M")) 102 assert.Equal(t, 0, mds.service.GetSellPriceLevels("M")) 103 assert.Equal(t, int64(4), mds.service.GetOrderCount("M")) 104 105 assert.Equal(t, uint64(7), mds.service.GetVolumeAtPrice("M", types.SideBuy, 102)) 106 assert.Equal(t, uint64(1), mds.service.GetOrderCountAtPrice("M", types.SideBuy, 102)) 107 108 assert.Equal(t, uint64(8), mds.service.GetVolumeAtPrice("M", types.SideBuy, 101)) 109 assert.Equal(t, uint64(1), mds.service.GetOrderCountAtPrice("M", types.SideBuy, 101)) 110 111 assert.Equal(t, uint64(9), mds.service.GetVolumeAtPrice("M", types.SideBuy, 100)) 112 assert.Equal(t, uint64(1), mds.service.GetOrderCountAtPrice("M", types.SideBuy, 100)) 113 114 assert.Equal(t, uint64(10), mds.service.GetVolumeAtPrice("M", types.SideBuy, 99)) 115 assert.Equal(t, uint64(1), mds.service.GetOrderCountAtPrice("M", types.SideBuy, 99)) 116 } 117 118 func TestSellPriceLevels(t *testing.T) { 119 mds := getTestMDS(t) 120 vegaTime := time.Now() 121 122 order1 := buildOrder("Order1", types.SideSell, types.OrderTypeLimit, 100, 9, 9) 123 mds.service.AddOrder(order1, vegaTime, 1) 124 125 order2 := buildOrder("Order2", types.SideSell, types.OrderTypeLimit, 102, 7, 7) 126 mds.service.AddOrder(order2, vegaTime, 2) 127 128 order3 := buildOrder("Order3", types.SideSell, types.OrderTypeLimit, 101, 8, 8) 129 mds.service.AddOrder(order3, vegaTime, 3) 130 131 order4 := buildOrder("Order4", types.SideSell, types.OrderTypeLimit, 99, 10, 10) 132 mds.service.AddOrder(order4, vegaTime, 4) 133 134 assert.Equal(t, 0, mds.service.GetBuyPriceLevels("M")) 135 assert.Equal(t, 4, mds.service.GetSellPriceLevels("M")) 136 assert.Equal(t, int64(4), mds.service.GetOrderCount("M")) 137 138 assert.Equal(t, uint64(7), mds.service.GetVolumeAtPrice("M", types.SideSell, 102)) 139 assert.Equal(t, uint64(1), mds.service.GetOrderCountAtPrice("M", types.SideSell, 102)) 140 141 assert.Equal(t, uint64(8), mds.service.GetVolumeAtPrice("M", types.SideSell, 101)) 142 assert.Equal(t, uint64(1), mds.service.GetOrderCountAtPrice("M", types.SideSell, 101)) 143 144 assert.Equal(t, uint64(9), mds.service.GetVolumeAtPrice("M", types.SideSell, 100)) 145 assert.Equal(t, uint64(1), mds.service.GetOrderCountAtPrice("M", types.SideSell, 100)) 146 147 assert.Equal(t, uint64(10), mds.service.GetVolumeAtPrice("M", types.SideSell, 99)) 148 assert.Equal(t, uint64(1), mds.service.GetOrderCountAtPrice("M", types.SideSell, 99)) 149 } 150 151 func TestAddOrderToEmptyBook(t *testing.T) { 152 mds := getTestMDS(t) 153 vegaTime := time.Now() 154 155 order := buildOrder("Order1", types.SideBuy, types.OrderTypeLimit, 100, 10, 10) 156 mds.service.AddOrder(order, vegaTime, 1) 157 158 assert.Equal(t, 1, mds.service.GetBuyPriceLevels("M")) 159 assert.Equal(t, 0, mds.service.GetSellPriceLevels("M")) 160 assert.Equal(t, int64(1), mds.service.GetOrderCount("M")) 161 162 assert.Equal(t, uint64(10), mds.service.GetVolumeAtPrice("M", types.SideBuy, 100)) 163 assert.Equal(t, uint64(1), mds.service.GetOrderCountAtPrice("M", types.SideBuy, 100)) 164 } 165 166 func TestCancelOrder(t *testing.T) { 167 mds := getTestMDS(t) 168 vegaTime := time.Now() 169 170 order := buildOrder("Order1", types.SideBuy, types.OrderTypeLimit, 100, 10, 10) 171 mds.service.AddOrder(order, vegaTime, 1) 172 173 cancelorder := *order 174 cancelorder.Status = types.OrderStatusCancelled 175 mds.service.AddOrder(&cancelorder, vegaTime, 2) 176 177 assert.Equal(t, 0, mds.service.GetBuyPriceLevels("M")) 178 assert.Equal(t, 0, mds.service.GetSellPriceLevels("M")) 179 assert.Equal(t, int64(0), mds.service.GetOrderCount("M")) 180 181 assert.Equal(t, uint64(0), mds.service.GetVolumeAtPrice("M", types.SideBuy, 100)) 182 assert.Equal(t, uint64(0), mds.service.GetOrderCountAtPrice("M", types.SideBuy, 100)) 183 } 184 185 func TestStoppedOrder(t *testing.T) { 186 mds := getTestMDS(t) 187 vegaTime := time.Now() 188 189 order := buildOrder("Order1", types.SideBuy, types.OrderTypeLimit, 100, 10, 10) 190 mds.service.AddOrder(order, vegaTime, 1) 191 192 cancelorder := *order 193 cancelorder.Status = types.OrderStatusStopped 194 mds.service.AddOrder(&cancelorder, vegaTime, 2) 195 196 assert.Equal(t, 0, mds.service.GetBuyPriceLevels("M")) 197 assert.Equal(t, 0, mds.service.GetSellPriceLevels("M")) 198 assert.Equal(t, int64(0), mds.service.GetOrderCount("M")) 199 200 assert.Equal(t, uint64(0), mds.service.GetVolumeAtPrice("M", types.SideBuy, 100)) 201 assert.Equal(t, uint64(0), mds.service.GetOrderCountAtPrice("M", types.SideBuy, 100)) 202 } 203 204 func TestExpiredOrder(t *testing.T) { 205 mds := getTestMDS(t) 206 vegaTime := time.Now() 207 208 order := buildOrder("Order1", types.SideBuy, types.OrderTypeLimit, 100, 10, 10) 209 mds.service.AddOrder(order, vegaTime, 1) 210 211 cancelorder := *order 212 cancelorder.Status = types.OrderStatusExpired 213 mds.service.AddOrder(&cancelorder, vegaTime, 2) 214 215 assert.Equal(t, 0, mds.service.GetBuyPriceLevels("M")) 216 assert.Equal(t, 0, mds.service.GetSellPriceLevels("M")) 217 assert.Equal(t, int64(0), mds.service.GetOrderCount("M")) 218 219 assert.Equal(t, uint64(0), mds.service.GetVolumeAtPrice("M", types.SideBuy, 100)) 220 assert.Equal(t, uint64(0), mds.service.GetOrderCountAtPrice("M", types.SideBuy, 100)) 221 } 222 223 func TestAmendOrderPrice(t *testing.T) { 224 mds := getTestMDS(t) 225 vegaTime := time.Now() 226 227 order := buildOrder("Order1", types.SideBuy, types.OrderTypeLimit, 100, 10, 10) 228 order2 := buildOrder("Order2", types.SideBuy, types.OrderTypeLimit, 100, 10, 10) 229 230 mds.service.AddOrder(order, vegaTime, 1) 231 mds.service.AddOrder(order2, vegaTime, 2) 232 233 // Amend the price to force a change in price level 234 amendorder := *order 235 amendorder.Price = num.NewUint(90) 236 amendorder.OriginalPrice = num.NewUint(90) 237 mds.service.AddOrder(&amendorder, vegaTime, 3) 238 239 assert.Equal(t, 2, mds.service.GetBuyPriceLevels("M")) 240 assert.Equal(t, 0, mds.service.GetSellPriceLevels("M")) 241 assert.Equal(t, int64(2), mds.service.GetOrderCount("M")) 242 243 assert.Equal(t, uint64(10), mds.service.GetVolumeAtPrice("M", types.SideBuy, 100)) 244 assert.Equal(t, uint64(10), mds.service.GetVolumeAtPrice("M", types.SideBuy, 90)) 245 assert.Equal(t, uint64(1), mds.service.GetOrderCountAtPrice("M", types.SideBuy, 100)) 246 assert.Equal(t, uint64(1), mds.service.GetOrderCountAtPrice("M", types.SideBuy, 90)) 247 } 248 249 func TestAmendOrderVolumeUp(t *testing.T) { 250 mds := getTestMDS(t) 251 vegaTime := time.Now() 252 253 order := buildOrder("Order1", types.SideBuy, types.OrderTypeLimit, 100, 10, 10) 254 mds.service.AddOrder(order, vegaTime, 1) 255 256 amendorder := *order 257 amendorder.Size = 20 258 amendorder.Remaining = 20 259 mds.service.AddOrder(&amendorder, vegaTime, 2) 260 261 assert.Equal(t, 1, mds.service.GetBuyPriceLevels("M")) 262 assert.Equal(t, 0, mds.service.GetSellPriceLevels("M")) 263 assert.Equal(t, int64(1), mds.service.GetOrderCount("M")) 264 265 assert.Equal(t, uint64(20), mds.service.GetVolumeAtPrice("M", types.SideBuy, 100)) 266 assert.Equal(t, uint64(1), mds.service.GetOrderCountAtPrice("M", types.SideBuy, 100)) 267 } 268 269 func TestAmendOrderVolumeDown(t *testing.T) { 270 mds := getTestMDS(t) 271 vegaTime := time.Now() 272 273 order := buildOrder("Order1", types.SideBuy, types.OrderTypeLimit, 100, 10, 10) 274 mds.service.AddOrder(order, vegaTime, 1) 275 276 amendorder := *order 277 amendorder.Size = 5 278 amendorder.Remaining = 5 279 mds.service.AddOrder(&amendorder, vegaTime, 2) 280 281 assert.Equal(t, 1, mds.service.GetBuyPriceLevels("M")) 282 assert.Equal(t, 0, mds.service.GetSellPriceLevels("M")) 283 assert.Equal(t, int64(1), mds.service.GetOrderCount("M")) 284 285 assert.Equal(t, uint64(5), mds.service.GetVolumeAtPrice("M", types.SideBuy, 100)) 286 assert.Equal(t, uint64(1), mds.service.GetOrderCountAtPrice("M", types.SideBuy, 100)) 287 } 288 289 func TestAmendOrderVolumeDownToZero(t *testing.T) { 290 mds := getTestMDS(t) 291 vegaTime := time.Now() 292 293 order := buildOrder("Order1", types.SideBuy, types.OrderTypeLimit, 100, 10, 10) 294 mds.service.AddOrder(order, vegaTime, 1) 295 296 amendorder := *order 297 amendorder.Size = 0 298 amendorder.Remaining = 0 299 mds.service.AddOrder(&amendorder, vegaTime, 2) 300 301 assert.Equal(t, 0, mds.service.GetBuyPriceLevels("M")) 302 assert.Equal(t, 0, mds.service.GetSellPriceLevels("M")) 303 assert.Equal(t, int64(0), mds.service.GetOrderCount("M")) 304 305 assert.Equal(t, uint64(0), mds.service.GetVolumeAtPrice("M", types.SideBuy, 100)) 306 assert.Equal(t, uint64(0), mds.service.GetOrderCountAtPrice("M", types.SideBuy, 100)) 307 } 308 309 func TestPartialFill(t *testing.T) { 310 mds := getTestMDS(t) 311 vegaTime := time.Now() 312 313 order := buildOrder("Order1", types.SideBuy, types.OrderTypeLimit, 100, 10, 10) 314 mds.service.AddOrder(order, vegaTime, 1) 315 316 pforder := *order 317 pforder.Remaining = 5 318 mds.service.AddOrder(&pforder, vegaTime, 2) 319 320 assert.Equal(t, 1, mds.service.GetBuyPriceLevels("M")) 321 assert.Equal(t, 0, mds.service.GetSellPriceLevels("M")) 322 assert.Equal(t, int64(1), mds.service.GetOrderCount("M")) 323 324 assert.Equal(t, uint64(5), mds.service.GetVolumeAtPrice("M", types.SideBuy, 100)) 325 assert.Equal(t, uint64(1), mds.service.GetOrderCountAtPrice("M", types.SideBuy, 100)) 326 } 327 328 func TestIOCPartialFill(t *testing.T) { 329 mds := getTestMDS(t) 330 vegaTime := time.Now() 331 332 order := buildOrder("Order1", types.SideBuy, types.OrderTypeLimit, 100, 10, 5) 333 order.Status = types.OrderStatusPartiallyFilled 334 order.TimeInForce = types.OrderTimeInForceIOC 335 mds.service.AddOrder(order, vegaTime, 1) 336 337 assert.Equal(t, 0, mds.service.GetBuyPriceLevels("M")) 338 assert.Equal(t, 0, mds.service.GetSellPriceLevels("M")) 339 assert.Equal(t, int64(0), mds.service.GetOrderCount("M")) 340 341 assert.Equal(t, uint64(0), mds.service.GetVolumeAtPrice("M", types.SideBuy, 100)) 342 assert.Equal(t, uint64(0), mds.service.GetOrderCountAtPrice("M", types.SideBuy, 100)) 343 } 344 345 func TestFullyFill(t *testing.T) { 346 mds := getTestMDS(t) 347 vegaTime := time.Now() 348 349 order := buildOrder("Order1", types.SideBuy, types.OrderTypeLimit, 100, 10, 10) 350 mds.service.AddOrder(order, vegaTime, 1) 351 352 fforder := *order 353 fforder.Remaining = 0 354 fforder.Status = types.OrderStatusFilled 355 mds.service.AddOrder(&fforder, vegaTime, 2) 356 357 assert.Equal(t, 0, mds.service.GetBuyPriceLevels("M")) 358 assert.Equal(t, 0, mds.service.GetSellPriceLevels("M")) 359 assert.Equal(t, int64(0), mds.service.GetOrderCount("M")) 360 361 assert.Equal(t, uint64(0), mds.service.GetVolumeAtPrice("M", types.SideBuy, 100)) 362 assert.Equal(t, uint64(0), mds.service.GetOrderCountAtPrice("M", types.SideBuy, 100)) 363 } 364 365 func TestMarketOrder(t *testing.T) { 366 mds := getTestMDS(t) 367 vegaTime := time.Now() 368 369 // market orders should not stay on the book 370 marketorder := buildOrder("Order1", types.SideBuy, types.OrderTypeMarket, 100, 10, 10) 371 mds.service.AddOrder(marketorder, vegaTime, 1) 372 373 assert.Equal(t, 0, mds.service.GetBuyPriceLevels("M")) 374 assert.Equal(t, 0, mds.service.GetSellPriceLevels("M")) 375 assert.Equal(t, int64(0), mds.service.GetOrderCount("M")) 376 377 assert.Equal(t, uint64(0), mds.service.GetVolumeAtPrice("M", types.SideBuy, 100)) 378 assert.Equal(t, uint64(0), mds.service.GetOrderCountAtPrice("M", types.SideBuy, 100)) 379 } 380 381 func TestFOKOrder(t *testing.T) { 382 mds := getTestMDS(t) 383 vegaTime := time.Now() 384 385 // FOK orders do not stay on the book 386 fokorder := buildOrder("Order1", types.SideBuy, types.OrderTypeLimit, 100, 10, 10) 387 fokorder.TimeInForce = types.OrderTimeInForceFOK 388 mds.service.AddOrder(fokorder, vegaTime, 1) 389 390 assert.Equal(t, 0, mds.service.GetBuyPriceLevels("M")) 391 assert.Equal(t, 0, mds.service.GetSellPriceLevels("M")) 392 assert.Equal(t, int64(0), mds.service.GetOrderCount("M")) 393 394 assert.Equal(t, uint64(0), mds.service.GetVolumeAtPrice("M", types.SideBuy, 100)) 395 assert.Equal(t, uint64(0), mds.service.GetOrderCountAtPrice("M", types.SideBuy, 100)) 396 } 397 398 func TestIOCOrder(t *testing.T) { 399 mds := getTestMDS(t) 400 vegaTime := time.Now() 401 402 // IOC orders do not stay on the book 403 iocorder := buildOrder("Order1", types.SideBuy, types.OrderTypeLimit, 100, 10, 10) 404 iocorder.TimeInForce = types.OrderTimeInForceIOC 405 mds.service.AddOrder(iocorder, vegaTime, 1) 406 407 assert.Equal(t, 0, mds.service.GetBuyPriceLevels("M")) 408 assert.Equal(t, 0, mds.service.GetSellPriceLevels("M")) 409 assert.Equal(t, int64(0), mds.service.GetOrderCount("M")) 410 411 assert.Equal(t, uint64(0), mds.service.GetVolumeAtPrice("M", types.SideBuy, 100)) 412 assert.Equal(t, uint64(0), mds.service.GetOrderCountAtPrice("M", types.SideBuy, 100)) 413 } 414 415 func TestRejectedOrder(t *testing.T) { 416 mds := getTestMDS(t) 417 vegaTime := time.Now() 418 419 // Rejected orders should be ignored 420 order := buildOrder("Order1", types.SideBuy, types.OrderTypeLimit, 100, 10, 10) 421 order.Status = types.OrderStatusRejected 422 mds.service.AddOrder(order, vegaTime, 1) 423 424 assert.Equal(t, 0, mds.service.GetBuyPriceLevels("M")) 425 assert.Equal(t, 0, mds.service.GetSellPriceLevels("M")) 426 assert.Equal(t, int64(0), mds.service.GetOrderCount("M")) 427 428 assert.Equal(t, uint64(0), mds.service.GetVolumeAtPrice("M", types.SideBuy, 100)) 429 assert.Equal(t, uint64(0), mds.service.GetOrderCountAtPrice("M", types.SideBuy, 100)) 430 } 431 432 func TestInvalidOrder(t *testing.T) { 433 mds := getTestMDS(t) 434 vegaTime := time.Now() 435 436 // Invalid orders should be ignored 437 order := buildOrder("Order1", types.SideBuy, types.OrderTypeLimit, 100, 10, 10) 438 order.Status = types.OrderStatusUnspecified 439 mds.service.AddOrder(order, vegaTime, 1) 440 441 assert.Equal(t, 0, mds.service.GetBuyPriceLevels("M")) 442 assert.Equal(t, 0, mds.service.GetSellPriceLevels("M")) 443 assert.Equal(t, int64(0), mds.service.GetOrderCount("M")) 444 445 assert.Equal(t, uint64(0), mds.service.GetVolumeAtPrice("M", types.SideBuy, 100)) 446 assert.Equal(t, uint64(0), mds.service.GetOrderCountAtPrice("M", types.SideBuy, 100)) 447 } 448 449 func TestPartialMatchOrders(t *testing.T) { 450 mds := getTestMDS(t) 451 vegaTime := time.Now() 452 453 order1 := buildOrder("Order1", types.SideBuy, types.OrderTypeLimit, 100, 10, 10) 454 order2 := buildOrder("Order1", types.SideBuy, types.OrderTypeLimit, 100, 10, 8) 455 order3 := buildOrder("Order1", types.SideBuy, types.OrderTypeLimit, 100, 10, 5) 456 order4 := buildOrder("Order1", types.SideBuy, types.OrderTypeLimit, 100, 10, 1) 457 458 mds.service.AddOrder(order1, vegaTime, 1) 459 mds.service.AddOrder(order2, vegaTime, 2) 460 mds.service.AddOrder(order3, vegaTime, 3) 461 mds.service.AddOrder(order4, vegaTime, 4) 462 463 assert.Equal(t, 1, mds.service.GetBuyPriceLevels("M")) 464 assert.Equal(t, 0, mds.service.GetSellPriceLevels("M")) 465 assert.Equal(t, int64(1), mds.service.GetOrderCount("M")) 466 467 assert.Equal(t, uint64(1), mds.service.GetVolumeAtPrice("M", types.SideBuy, 100)) 468 assert.Equal(t, uint64(1), mds.service.GetOrderCountAtPrice("M", types.SideBuy, 100)) 469 } 470 471 func TestFullyMatchOrders(t *testing.T) { 472 mds := getTestMDS(t) 473 vegaTime := time.Now() 474 475 order1 := buildOrder("Order1", types.SideBuy, types.OrderTypeLimit, 100, 10, 10) 476 order2 := buildOrder("Order1", types.SideBuy, types.OrderTypeLimit, 100, 10, 8) 477 order3 := buildOrder("Order1", types.SideBuy, types.OrderTypeLimit, 100, 10, 5) 478 order4 := buildOrder("Order1", types.SideBuy, types.OrderTypeLimit, 100, 10, 0) 479 order4.Status = types.OrderStatusFilled 480 481 mds.service.AddOrder(order1, vegaTime, 1) 482 mds.service.AddOrder(order2, vegaTime, 2) 483 mds.service.AddOrder(order3, vegaTime, 3) 484 mds.service.AddOrder(order4, vegaTime, 4) 485 486 assert.Equal(t, 0, mds.service.GetBuyPriceLevels("M")) 487 assert.Equal(t, 0, mds.service.GetSellPriceLevels("M")) 488 assert.Equal(t, int64(0), mds.service.GetOrderCount("M")) 489 490 assert.Equal(t, uint64(0), mds.service.GetVolumeAtPrice("M", types.SideBuy, 100)) 491 assert.Equal(t, uint64(0), mds.service.GetOrderCountAtPrice("M", types.SideBuy, 100)) 492 } 493 494 func TestRemovingPriceLevels(t *testing.T) { 495 mds := getTestMDS(t) 496 vegaTime := time.Now() 497 498 order1 := buildOrder("Order1", types.SideBuy, types.OrderTypeLimit, 101, 10, 10) 499 order2 := buildOrder("Order2", types.SideBuy, types.OrderTypeLimit, 100, 10, 10) 500 order3 := buildOrder("Order3", types.SideBuy, types.OrderTypeLimit, 102, 10, 10) 501 order4 := buildOrder("Order1", types.SideBuy, types.OrderTypeLimit, 101, 10, 0) 502 order4.Status = types.OrderStatusFilled 503 504 mds.service.AddOrder(order1, vegaTime, 1) 505 mds.service.AddOrder(order2, vegaTime, 2) 506 mds.service.AddOrder(order3, vegaTime, 3) 507 mds.service.AddOrder(order4, vegaTime, 4) 508 509 assert.Equal(t, 2, mds.service.GetBuyPriceLevels("M")) 510 assert.Equal(t, 0, mds.service.GetSellPriceLevels("M")) 511 assert.Equal(t, int64(2), mds.service.GetOrderCount("M")) 512 513 assert.Equal(t, uint64(0), mds.service.GetVolumeAtPrice("M", types.SideBuy, 101)) 514 assert.Equal(t, uint64(0), mds.service.GetOrderCountAtPrice("M", types.SideBuy, 101)) 515 } 516 517 func TestMarketDepthFields(t *testing.T) { 518 mds := getTestMDS(t) 519 vegaTime := time.Now() 520 521 order1 := buildOrder("Order1", types.SideBuy, types.OrderTypeLimit, 101, 10, 10) 522 mds.service.AddOrder(order1, vegaTime, 1) 523 524 md := mds.service.GetMarketDepth("M", 0) 525 assert.NotNil(t, md) 526 527 assert.Equal(t, "M", md.MarketId) 528 assert.Equal(t, 1, len(md.GetBuy())) 529 530 priceLevels := md.GetBuy() 531 pl := priceLevels[0] 532 assert.NotNil(t, pl) 533 assert.Equal(t, uint64(1), pl.NumberOfOrders) 534 assert.Equal(t, "101", pl.Price) 535 assert.Equal(t, uint64(10), pl.Volume) 536 } 537 538 func TestParkingOrder(t *testing.T) { 539 mds := getTestMDS(t) 540 vegaTime := time.Now() 541 542 // Create a valid and live pegged order 543 order1 := buildOrder("Order1", types.SideBuy, types.OrderTypeLimit, 101, 10, 10) 544 order1.PeggedOrder = &types.PeggedOrder{Reference: types.PeggedReferenceBestBid, Offset: num.NewUint(1)} 545 mds.service.AddOrder(order1, vegaTime, 1) 546 547 // Park it 548 order2 := buildOrder("Order1", types.SideBuy, types.OrderTypeLimit, 0, 10, 10) 549 order2.PeggedOrder = &types.PeggedOrder{Reference: types.PeggedReferenceBestBid, Offset: num.NewUint(1)} 550 order2.Status = types.OrderStatusParked 551 mds.service.AddOrder(order2, vegaTime, 2) 552 553 md := mds.service.GetMarketDepth("M", 0) 554 assert.NotNil(t, md) 555 556 assert.Equal(t, "M", md.MarketId) 557 assert.Equal(t, 0, len(md.GetBuy())) 558 assert.Equal(t, 0, len(md.GetSell())) 559 560 // Unpark it 561 order3 := buildOrder("Order1", types.SideBuy, types.OrderTypeLimit, 101, 10, 10) 562 order3.PeggedOrder = &types.PeggedOrder{Reference: types.PeggedReferenceBestBid, Offset: num.NewUint(1)} 563 order3.Status = types.OrderStatusActive 564 mds.service.AddOrder(order3, vegaTime, 3) 565 566 md2 := mds.service.GetMarketDepth("M", 0) 567 assert.NotNil(t, md2) 568 569 assert.Equal(t, "M", md2.MarketId) 570 assert.Equal(t, 1, len(md2.GetBuy())) 571 assert.Equal(t, 0, len(md2.GetSell())) 572 } 573 574 func TestParkedOrder(t *testing.T) { 575 mds := getTestMDS(t) 576 vegaTime := time.Now() 577 578 // Create a parked pegged order which should not go on the depth book 579 order1 := buildOrder("Order1", types.SideBuy, types.OrderTypeLimit, 101, 10, 10) 580 order1.PeggedOrder = &types.PeggedOrder{Reference: types.PeggedReferenceBestBid, Offset: num.NewUint(1)} 581 order1.Status = types.OrderStatusParked 582 mds.service.AddOrder(order1, vegaTime, 1) 583 584 md := mds.service.GetMarketDepth("M", 0) 585 assert.NotNil(t, md) 586 587 assert.Equal(t, "M", md.MarketId) 588 assert.Equal(t, 0, len(md.GetBuy())) 589 assert.Equal(t, 0, len(md.GetSell())) 590 } 591 592 func TestParkedOrder2(t *testing.T) { 593 mds := getTestMDS(t) 594 vegaTime := time.Now() 595 596 // Create parked pegged order 597 order1 := buildOrder("Pegged1", types.SideBuy, types.OrderTypeLimit, 0, 10, 10) 598 order1.PeggedOrder = &types.PeggedOrder{Reference: types.PeggedReferenceBestBid, Offset: num.NewUint(1)} 599 order1.Status = types.OrderStatusParked 600 mds.service.AddOrder(order1, vegaTime, 1) 601 602 // Create normal order 603 order2 := buildOrder("Normal1", types.SideBuy, types.OrderTypeLimit, 100, 1, 1) 604 mds.service.AddOrder(order2, vegaTime, 2) 605 606 // Unpark pegged order 607 order3 := buildOrder("Pegged1", types.SideBuy, types.OrderTypeLimit, 99, 10, 10) 608 order3.PeggedOrder = &types.PeggedOrder{Reference: types.PeggedReferenceBestBid, Offset: num.NewUint(1)} 609 order3.Status = types.OrderStatusActive 610 mds.service.AddOrder(order3, vegaTime, 3) 611 612 // Cancel normal order 613 order4 := buildOrder("Normal1", types.SideBuy, types.OrderTypeLimit, 100, 1, 1) 614 order4.Status = types.OrderStatusCancelled 615 mds.service.AddOrder(order4, vegaTime, 4) 616 617 // Park pegged order 618 order5 := buildOrder("Pegged1", types.SideBuy, types.OrderTypeLimit, 99, 10, 10) 619 order5.PeggedOrder = &types.PeggedOrder{Reference: types.PeggedReferenceBestBid, Offset: num.NewUint(1)} 620 order5.Status = types.OrderStatusParked 621 mds.service.AddOrder(order5, vegaTime, 5) 622 623 // Create normal order 624 order6 := buildOrder("Normal2", types.SideBuy, types.OrderTypeLimit, 100, 1, 1) 625 mds.service.AddOrder(order6, vegaTime, 6) 626 627 // Unpark pegged order 628 order7 := buildOrder("Pegged1", types.SideBuy, types.OrderTypeLimit, 99, 10, 10) 629 order7.PeggedOrder = &types.PeggedOrder{Reference: types.PeggedReferenceBestBid, Offset: num.NewUint(1)} 630 order7.Status = types.OrderStatusActive 631 mds.service.AddOrder(order7, vegaTime, 7) 632 633 // Fill normal order 634 order8 := buildOrder("Normal2", types.SideBuy, types.OrderTypeLimit, 100, 1, 0) 635 order8.Status = types.OrderStatusFilled 636 mds.service.AddOrder(order8, vegaTime, 8) 637 638 // Create new matching order 639 order9 := buildOrder("Normal3", types.SideSell, types.OrderTypeLimit, 100, 1, 0) 640 order9.Status = types.OrderStatusFilled 641 mds.service.AddOrder(order9, vegaTime, 9) 642 643 // Park pegged order 644 order10 := buildOrder("Pegged1", types.SideBuy, types.OrderTypeLimit, 99, 10, 10) 645 order10.PeggedOrder = &types.PeggedOrder{Reference: types.PeggedReferenceBestBid, Offset: num.NewUint(1)} 646 order10.Status = types.OrderStatusParked 647 mds.service.AddOrder(order10, vegaTime, 10) 648 649 md := mds.service.GetMarketDepth("M", 0) 650 assert.NotNil(t, md) 651 652 assert.Equal(t, "M", md.MarketId) 653 assert.Equal(t, 0, len(md.GetBuy())) 654 assert.Equal(t, 0, len(md.GetSell())) 655 } 656 657 func TestInitFromSqlStore(t *testing.T) { 658 ctrl := gomock.NewController(t) 659 660 ctx := context.Background() 661 662 t.Run("Init from SQL Store when SQL Store is in use", func(t *testing.T) { 663 store := mocks.NewMockOrderStore(ctrl) 664 amm := mocks.NewMockAMMStore(ctrl) 665 amm.EXPECT().ListActive(gomock.Any()).Return(nil, nil).AnyTimes() 666 store.EXPECT().GetLiveOrders(gomock.Any()).Return([]entities.Order{ 667 { 668 ID: "22EEA97BF1D9067D7533D0E671FC97C22146CE6785B4B142EBDF53FF0ED73E25", 669 MarketID: "2EBD1AF4C84D5E004FD2797FF268258BFA21A37A6D0BCE289FB21151ACEF0F36", 670 PartyID: "FB0C9F50787E5E090591E6600DBBEB5A4771D5A0C9B1AE09BC673AB9F471D210", 671 Side: 2, 672 Price: decimal.NewFromInt(1200), 673 Size: 5, 674 Remaining: 5, 675 TimeInForce: 1, 676 Type: 1, 677 Status: 1, 678 Reference: "", 679 Reason: 0, 680 Version: 1, 681 PeggedOffset: decimal.NewFromInt(0), 682 BatchID: 0, 683 PeggedReference: 0, 684 LpID: nil, 685 CreatedAt: time.Time{}, 686 UpdatedAt: time.Time{}, 687 ExpiresAt: time.Time{}, 688 VegaTime: time.Date(2022, 3, 8, 14, 14, 45, 762739000, time.UTC), 689 SeqNum: 32, 690 }, 691 { 692 ID: "0E6BFB468B1D57B6463B3A2D133DEA107A56B34CC641235469E834145DE55803", 693 MarketID: "52D3FCF2EFC15518EDFA25154E909348A2D7F45903C72CD88CB32EFD747CA001", 694 PartyID: "29FE22227631DE06D9FBBCF2450DEA492E685E5953AEF60A76A95D0DA156806D", 695 Side: 1, 696 Price: decimal.NewFromInt(22), 697 Size: 26, 698 Remaining: 26, 699 TimeInForce: 1, 700 Type: 1, 701 Status: 1, 702 Reference: "", 703 Reason: 0, 704 Version: 2, 705 PeggedOffset: decimal.NewFromInt(0), 706 BatchID: 1, 707 PeggedReference: 0, 708 LpID: nil, 709 CreatedAt: time.Time{}, 710 UpdatedAt: time.Time{}, 711 ExpiresAt: time.Time{}, 712 VegaTime: time.Date(2022, 3, 8, 14, 11, 39, 901022000, time.UTC), 713 SeqNum: 32, 714 }, 715 { 716 ID: "D8DA96D3B61F1E745061F85D46CE4440E188F846BBD76F7475C7D8AF0E9AB971", 717 MarketID: "2EBD1AF4C84D5E004FD2797FF268258BFA21A37A6D0BCE289FB21151ACEF0F36", 718 PartyID: "5F9A129B40E17BA0A17272697E3D521356AFC20BB56BF68C9242097AAFF879BF", 719 Side: 1, 720 Price: decimal.NewFromInt(900), 721 Size: 5, 722 Remaining: 5, 723 TimeInForce: 1, 724 Type: 1, 725 Status: 1, 726 Reference: "", 727 Reason: 0, 728 Version: 1, 729 PeggedOffset: decimal.NewFromInt(0), 730 BatchID: 0, 731 PeggedReference: 0, 732 LpID: nil, 733 CreatedAt: time.Time{}, 734 UpdatedAt: time.Time{}, 735 ExpiresAt: time.Time{}, 736 VegaTime: time.Date(2022, 3, 8, 14, 14, 45, 762739000, time.UTC), 737 SeqNum: 39, 738 }, 739 { 740 ID: "9CABDED74F357688E96AAD50353122F23C441CF6134BA1B31E4B75D5D5EB7B36", 741 MarketID: "2EBD1AF4C84D5E004FD2797FF268258BFA21A37A6D0BCE289FB21151ACEF0F36", 742 PartyID: "5F9A129B40E17BA0A17272697E3D521356AFC20BB56BF68C9242097AAFF879BF", 743 Side: 1, 744 Price: decimal.NewFromInt(100), 745 Size: 1, 746 Remaining: 1, 747 TimeInForce: 1, 748 Type: 1, 749 Status: 1, 750 Reference: "", 751 Reason: 0, 752 Version: 1, 753 PeggedOffset: decimal.NewFromInt(0), 754 BatchID: 0, 755 PeggedReference: 0, 756 LpID: nil, 757 CreatedAt: time.Time{}, 758 UpdatedAt: time.Time{}, 759 ExpiresAt: time.Time{}, 760 VegaTime: time.Date(2022, 3, 8, 14, 14, 45, 762739000, time.UTC), 761 SeqNum: 43, 762 }, 763 { 764 ID: "4300A037014C7ACFFC1C371697BD7A0ECAE4A54FCC4BFCB8A43E6EF4140A4F64", 765 MarketID: "2EBD1AF4C84D5E004FD2797FF268258BFA21A37A6D0BCE289FB21151ACEF0F36", 766 PartyID: "FB0C9F50787E5E090591E6600DBBEB5A4771D5A0C9B1AE09BC673AB9F471D210", 767 Side: 2, 768 Price: decimal.NewFromInt(100000), 769 Size: 1, 770 Remaining: 1, 771 TimeInForce: 1, 772 Type: 1, 773 Status: 1, 774 Reference: "", 775 Reason: 0, 776 Version: 2, 777 PeggedOffset: decimal.NewFromInt(0), 778 BatchID: 0, 779 PeggedReference: 0, 780 LpID: nil, 781 CreatedAt: time.Time{}, 782 UpdatedAt: time.Time{}, 783 ExpiresAt: time.Time{}, 784 VegaTime: time.Date(2022, 3, 8, 14, 14, 45, 762739000, time.UTC), 785 SeqNum: 53, 786 }, 787 { 788 ID: "F8062CA2F4EE26C6208881CFC9844F12BEE6AA0A087D155BE695AFF6FF00AB00", 789 MarketID: "2EBD1AF4C84D5E004FD2797FF268258BFA21A37A6D0BCE289FB21151ACEF0F36", 790 PartyID: "076E3373D4F4197731A3161D2F50CE286B93278BF2B650705691514DD49EFDA1", 791 Side: 2, 792 Price: decimal.NewFromInt(1201), 793 Size: 1301, 794 Remaining: 1301, 795 TimeInForce: 1, 796 Type: 1, 797 Status: 1, 798 Reference: "", 799 Reason: 0, 800 Version: 1, 801 PeggedOffset: decimal.NewFromInt(0), 802 BatchID: 1, 803 PeggedReference: 0, 804 LpID: nil, 805 CreatedAt: time.Time{}, 806 UpdatedAt: time.Time{}, 807 ExpiresAt: time.Time{}, 808 VegaTime: time.Date(2022, 3, 8, 14, 14, 58, 985875000, time.UTC), 809 SeqNum: 61, 810 }, 811 { 812 ID: "15E8D38DD216C5EE969EC7B7A2EB031E56474A9552CC10E00036A7DC1C0546B5", 813 MarketID: "2EBD1AF4C84D5E004FD2797FF268258BFA21A37A6D0BCE289FB21151ACEF0F36", 814 PartyID: "076E3373D4F4197731A3161D2F50CE286B93278BF2B650705691514DD49EFDA1", 815 Side: 1, 816 Price: decimal.NewFromInt(899), 817 Size: 1738, 818 Remaining: 1738, 819 TimeInForce: 1, 820 Type: 1, 821 Status: 1, 822 Reference: "", 823 Reason: 0, 824 Version: 1, 825 PeggedOffset: decimal.NewFromInt(0), 826 BatchID: 1, 827 PeggedReference: 0, 828 LpID: nil, 829 CreatedAt: time.Time{}, 830 UpdatedAt: time.Time{}, 831 ExpiresAt: time.Time{}, 832 VegaTime: time.Date(2022, 3, 8, 14, 14, 58, 985875000, time.UTC), 833 SeqNum: 66, 834 }, 835 }, nil).Times(1) 836 svc := service.NewMarketDepth(service.NewDefaultConfig().MarketDepth, store, amm, nil, nil, nil, nil, logging.NewTestLogger()) 837 require.NoError(t, svc.Initialise(ctx)) 838 }) 839 }