@@ -19,7 +19,6 @@ import (
19
19
"fmt"
20
20
"github.com/emirpasic/gods/maps/treemap"
21
21
"github.com/gitbitex/gitbitex-spot/models"
22
- "github.com/gitbitex/gitbitex-spot/utils"
23
22
"github.com/shopspring/decimal"
24
23
"github.com/siddontang/go-log/log"
25
24
"math"
@@ -30,68 +29,51 @@ const (
30
29
)
31
30
32
31
type orderBook struct {
33
- // 每一个product都会对应一个order book
32
+ // one product corresponds to one order book
34
33
product * models.Product
35
34
36
- // 深度, asks & bids
35
+ // depths: asks & bids
37
36
depths map [models.Side ]* depth
38
37
39
- // 严格连续递增的交易id,用于在trade的主键id
38
+ // strictly continuously increasing transaction ID, used for the primary key ID of trade
40
39
tradeSeq int64
41
40
42
- // 严格连续递增的日志seq,用于写入撮合日志
41
+ // strictly continuously increasing log SEQ, used to write matching log
43
42
logSeq int64
44
43
45
- // 防止order被重复提交到orderBook中,采用滑动窗口去重策略
44
+ // to prevent the order from being submitted to the order book repeatedly,
45
+ // a sliding window de duplication strategy is adopted.
46
46
orderIdWindow Window
47
47
}
48
48
49
- // orderBook快照,定时保存快照用于快速启动恢复
50
49
type orderBookSnapshot struct {
51
- // 对应的product id
50
+ // order book product id
52
51
ProductId string
53
52
54
- // orderBook中的全量订单
53
+ // all orders
55
54
Orders []BookOrder
56
55
57
- // 当前tradeSeq
56
+ // trade seq at snapshot time
58
57
TradeSeq int64
59
58
60
- // 当前logSeq
59
+ // log seq at snapshot time
61
60
LogSeq int64
62
61
63
- // 去重窗口
62
+ // state of de duplication window
64
63
OrderIdWindow Window
65
64
}
66
65
67
- type PriceLevel struct {
68
- Price decimal.Decimal
69
- Size decimal.Decimal
70
- OrderCount int64
71
- }
72
-
73
66
type priceOrderIdKey struct {
74
67
price decimal.Decimal
75
68
orderId int64
76
69
}
77
70
78
- type BookOrder struct {
79
- OrderId int64
80
- Size decimal.Decimal
81
- Funds decimal.Decimal
82
- Price decimal.Decimal
83
- Side models.Side
84
- Type models.OrderType
85
- }
86
-
87
71
func NewOrderBook (product * models.Product ) * orderBook {
88
72
asks := & depth {
89
- levels : treemap .NewWith (utils .DecimalAscComparator ),
90
73
queue : treemap .NewWith (priceOrderIdKeyAscComparator ),
91
74
orders : map [int64 ]* BookOrder {},
92
75
}
93
76
bids := & depth {
94
- levels : treemap .NewWith (utils .DecimalDescComparator ),
95
77
queue : treemap .NewWith (priceOrderIdKeyDescComparator ),
96
78
orders : map [int64 ]* BookOrder {},
97
79
}
@@ -112,14 +94,7 @@ func (o *orderBook) ApplyOrder(order *models.Order) (logs []Log) {
112
94
return logs
113
95
}
114
96
115
- takerOrder := & BookOrder {
116
- OrderId : order .Id ,
117
- Size : order .Size ,
118
- Funds : order .Funds ,
119
- Price : order .Price ,
120
- Side : order .Side ,
121
- Type : order .Type ,
122
- }
97
+ takerOrder := newBookOrder (order )
123
98
124
99
// If it's a Market-Buy order, set price to infinite high, and if it's market-sell,
125
100
// set price to zero, which ensures that prices will cross.
@@ -286,35 +261,17 @@ func (o *orderBook) nextTradeSeq() int64 {
286
261
}
287
262
288
263
type depth struct {
289
- // 保存所有正在book上的order
264
+ // all orders
290
265
orders map [int64 ]* BookOrder
291
266
292
- // 价格优先的priceLevel队列,用于获取level2
293
- // Price -> *PriceLevel
294
- levels * treemap.Map
295
-
296
- // 价格优先,时间优先的订单队列,用于订单match
267
+ // price first, time first order queue for order match
297
268
// priceOrderIdKey -> orderId
298
269
queue * treemap.Map
299
270
}
300
271
301
272
func (d * depth ) add (order BookOrder ) {
302
273
d .orders [order .OrderId ] = & order
303
-
304
274
d .queue .Put (& priceOrderIdKey {order .Price , order .OrderId }, order .OrderId )
305
-
306
- val , found := d .levels .Get (order .Price )
307
- if ! found {
308
- d .levels .Put (order .Price , & PriceLevel {
309
- Price : order .Price ,
310
- Size : order .Size ,
311
- OrderCount : 1 ,
312
- })
313
- } else {
314
- level := val .(* PriceLevel )
315
- level .Size = level .Size .Add (order .Size )
316
- level .OrderCount ++
317
- }
318
275
}
319
276
320
277
func (d * depth ) decrSize (orderId int64 , size decimal.Decimal ) error {
@@ -327,29 +284,35 @@ func (d *depth) decrSize(orderId int64, size decimal.Decimal) error {
327
284
return errors .New (fmt .Sprintf ("order %v Size %v less than %v" , orderId , order .Size , size ))
328
285
}
329
286
330
- var removed bool
331
287
order .Size = order .Size .Sub (size )
332
288
if order .Size .IsZero () {
333
289
delete (d .orders , orderId )
334
- removed = true
335
- }
336
-
337
- // 订单被移除出orderBook,清理priceTime队列
338
- if removed {
339
290
d .queue .Remove (& priceOrderIdKey {order .Price , order .OrderId })
340
291
}
341
292
342
- val , _ := d .levels .Get (order .Price )
343
- level := val .(* PriceLevel )
344
- level .Size = level .Size .Sub (size )
345
- if level .Size .IsZero () {
346
- d .levels .Remove (order .Price )
347
- } else if removed {
348
- level .OrderCount --
349
- }
350
293
return nil
351
294
}
352
295
296
+ type BookOrder struct {
297
+ OrderId int64
298
+ Size decimal.Decimal
299
+ Funds decimal.Decimal
300
+ Price decimal.Decimal
301
+ Side models.Side
302
+ Type models.OrderType
303
+ }
304
+
305
+ func newBookOrder (order * models.Order ) * BookOrder {
306
+ return & BookOrder {
307
+ OrderId : order .Id ,
308
+ Size : order .Size ,
309
+ Funds : order .Funds ,
310
+ Price : order .Price ,
311
+ Side : order .Side ,
312
+ Type : order .Type ,
313
+ }
314
+ }
315
+
353
316
func priceOrderIdKeyAscComparator (a , b interface {}) int {
354
317
aAsserted := a .(* priceOrderIdKey )
355
318
bAsserted := b .(* priceOrderIdKey )
0 commit comments