pkg/exchange: mv BalanceEvent to bybitapi and rename to WalletBalances

This commit is contained in:
Edwin 2023-08-09 12:39:19 +08:00
parent b711e1e439
commit 8c22863334
6 changed files with 94 additions and 84 deletions

View File

@ -0,0 +1,62 @@
package bybitapi
import (
"github.com/c9s/bbgo/pkg/fixedpoint"
)
type WalletBalances struct {
AccountType AccountType `json:"accountType"`
AccountIMRate fixedpoint.Value `json:"accountIMRate"`
AccountMMRate fixedpoint.Value `json:"accountMMRate"`
TotalEquity fixedpoint.Value `json:"totalEquity"`
TotalWalletBalance fixedpoint.Value `json:"totalWalletBalance"`
TotalMarginBalance fixedpoint.Value `json:"totalMarginBalance"`
TotalAvailableBalance fixedpoint.Value `json:"totalAvailableBalance"`
TotalPerpUPL fixedpoint.Value `json:"totalPerpUPL"`
TotalInitialMargin fixedpoint.Value `json:"totalInitialMargin"`
TotalMaintenanceMargin fixedpoint.Value `json:"totalMaintenanceMargin"`
// Account LTV: account total borrowed size / (account total equity + account total borrowed size).
// In non-unified mode & unified (inverse) & unified (isolated_margin), the field will be returned as an empty string.
AccountLTV fixedpoint.Value `json:"accountLTV"`
Coins []struct {
Coin string `json:"coin"`
// Equity of current coin
Equity fixedpoint.Value `json:"equity"`
// UsdValue of current coin. If this coin cannot be collateral, then it is 0
UsdValue fixedpoint.Value `json:"usdValue"`
// WalletBalance of current coin
WalletBalance fixedpoint.Value `json:"walletBalance"`
// Free available balance for Spot wallet. This is a unique field for Normal SPOT
Free fixedpoint.Value
// Locked balance for Spot wallet. This is a unique field for Normal SPOT
Locked fixedpoint.Value
// Available amount to withdraw of current coin
AvailableToWithdraw fixedpoint.Value `json:"availableToWithdraw"`
// Available amount to borrow of current coin
AvailableToBorrow fixedpoint.Value `json:"availableToBorrow"`
// Borrow amount of current coin
BorrowAmount fixedpoint.Value `json:"borrowAmount"`
// Accrued interest
AccruedInterest fixedpoint.Value `json:"accruedInterest"`
// Pre-occupied margin for order. For portfolio margin mode, it returns ""
TotalOrderIM fixedpoint.Value `json:"totalOrderIM"`
// Sum of initial margin of all positions + Pre-occupied liquidation fee. For portfolio margin mode, it returns ""
TotalPositionIM fixedpoint.Value `json:"totalPositionIM"`
// Sum of maintenance margin for all positions. For portfolio margin mode, it returns ""
TotalPositionMM fixedpoint.Value `json:"totalPositionMM"`
// Unrealised P&L
UnrealisedPnl fixedpoint.Value `json:"unrealisedPnl"`
// Cumulative Realised P&L
CumRealisedPnl fixedpoint.Value `json:"cumRealisedPnl"`
// Bonus. This is a unique field for UNIFIED account
Bonus fixedpoint.Value `json:"bonus"`
// Whether it can be used as a margin collateral currency (platform)
// - When marginCollateral=false, then collateralSwitch is meaningless
// - This is a unique field for UNIFIED account
CollateralSwitch bool `json:"collateralSwitch"`
// Whether the collateral is turned on by user (user)
// - When marginCollateral=true, then collateralSwitch is meaningful
// - This is a unique field for UNIFIED account
MarginCollateral bool `json:"marginCollateral"`
} `json:"coin"`
}

View File

@ -87,3 +87,7 @@ const (
TimeInForceIOC TimeInForce = "IOC" TimeInForceIOC TimeInForce = "IOC"
TimeInForceFOK TimeInForce = "FOK" TimeInForceFOK TimeInForce = "FOK"
) )
type AccountType string
const AccountTypeSpot AccountType = "SPOT"

View File

@ -265,3 +265,21 @@ func v3ToGlobalTrade(trade v3.Trade) (*types.Trade, error) {
IsIsolated: false, IsIsolated: false,
}, nil }, nil
} }
func toGlobalBalanceMap(events []bybitapi.WalletBalances) types.BalanceMap {
bm := types.BalanceMap{}
for _, event := range events {
if event.AccountType != bybitapi.AccountTypeSpot {
continue
}
for _, obj := range event.Coins {
bm[obj.Coin] = types.Balance{
Currency: obj.Coin,
Available: obj.Free,
Locked: obj.Locked,
}
}
}
return bm
}

View File

@ -33,7 +33,7 @@ type Stream struct {
types.StandardStream types.StandardStream
bookEventCallbacks []func(e BookEvent) bookEventCallbacks []func(e BookEvent)
walletEventCallbacks []func(e []WalletEvent) walletEventCallbacks []func(e []bybitapi.WalletBalances)
orderEventCallbacks []func(e []OrderEvent) orderEventCallbacks []func(e []OrderEvent)
} }
@ -77,7 +77,7 @@ func (s *Stream) dispatchEvent(event interface{}) {
case *BookEvent: case *BookEvent:
s.EmitBookEvent(*e) s.EmitBookEvent(*e)
case []WalletEvent: case []bybitapi.WalletBalances:
s.EmitWalletEvent(e) s.EmitWalletEvent(e)
case []OrderEvent: case []OrderEvent:
@ -110,7 +110,7 @@ func (s *Stream) parseWebSocketEvent(in []byte) (interface{}, error) {
return &book, nil return &book, nil
case TopicTypeWallet: case TopicTypeWallet:
var wallets []WalletEvent var wallets []bybitapi.WalletBalances
return wallets, json.Unmarshal(e.WebSocketTopicEvent.Data, &wallets) return wallets, json.Unmarshal(e.WebSocketTopicEvent.Data, &wallets)
case TopicTypeOrder: case TopicTypeOrder:
@ -239,23 +239,8 @@ func (s *Stream) handleBookEvent(e BookEvent) {
} }
} }
func (s *Stream) handleWalletEvent(events []WalletEvent) { func (s *Stream) handleWalletEvent(events []bybitapi.WalletBalances) {
bm := types.BalanceMap{} s.StandardStream.EmitBalanceSnapshot(toGlobalBalanceMap(events))
for _, event := range events {
if event.AccountType != AccountTypeSpot {
return
}
for _, obj := range event.Coins {
bm[obj.Coin] = types.Balance{
Currency: obj.Coin,
Available: obj.Free,
Locked: obj.Locked,
}
}
}
s.StandardStream.EmitBalanceSnapshot(bm)
} }
func (s *Stream) handleOrderEvent(events []OrderEvent) { func (s *Stream) handleOrderEvent(events []OrderEvent) {

View File

@ -2,7 +2,9 @@
package bybit package bybit
import () import (
"github.com/c9s/bbgo/pkg/exchange/bybit/bybitapi"
)
func (s *Stream) OnBookEvent(cb func(e BookEvent)) { func (s *Stream) OnBookEvent(cb func(e BookEvent)) {
s.bookEventCallbacks = append(s.bookEventCallbacks, cb) s.bookEventCallbacks = append(s.bookEventCallbacks, cb)
@ -14,11 +16,11 @@ func (s *Stream) EmitBookEvent(e BookEvent) {
} }
} }
func (s *Stream) OnWalletEvent(cb func(e []WalletEvent)) { func (s *Stream) OnWalletEvent(cb func(e []bybitapi.WalletBalances)) {
s.walletEventCallbacks = append(s.walletEventCallbacks, cb) s.walletEventCallbacks = append(s.walletEventCallbacks, cb)
} }
func (s *Stream) EmitWalletEvent(e []WalletEvent) { func (s *Stream) EmitWalletEvent(e []bybitapi.WalletBalances) {
for _, cb := range s.walletEventCallbacks { for _, cb := range s.walletEventCallbacks {
cb(e) cb(e)
} }

View File

@ -143,67 +143,6 @@ func getTopicType(topic string) TopicType {
return TopicType(slice[0]) return TopicType(slice[0])
} }
type AccountType string
const AccountTypeSpot AccountType = "SPOT"
type WalletEvent struct {
AccountType AccountType `json:"accountType"`
AccountIMRate fixedpoint.Value `json:"accountIMRate"`
AccountMMRate fixedpoint.Value `json:"accountMMRate"`
TotalEquity fixedpoint.Value `json:"totalEquity"`
TotalWalletBalance fixedpoint.Value `json:"totalWalletBalance"`
TotalMarginBalance fixedpoint.Value `json:"totalMarginBalance"`
TotalAvailableBalance fixedpoint.Value `json:"totalAvailableBalance"`
TotalPerpUPL fixedpoint.Value `json:"totalPerpUPL"`
TotalInitialMargin fixedpoint.Value `json:"totalInitialMargin"`
TotalMaintenanceMargin fixedpoint.Value `json:"totalMaintenanceMargin"`
// Account LTV: account total borrowed size / (account total equity + account total borrowed size).
// In non-unified mode & unified (inverse) & unified (isolated_margin), the field will be returned as an empty string.
AccountLTV fixedpoint.Value `json:"accountLTV"`
Coins []struct {
Coin string `json:"coin"`
// Equity of current coin
Equity fixedpoint.Value `json:"equity"`
// UsdValue of current coin. If this coin cannot be collateral, then it is 0
UsdValue fixedpoint.Value `json:"usdValue"`
// WalletBalance of current coin
WalletBalance fixedpoint.Value `json:"walletBalance"`
// Free available balance for Spot wallet. This is a unique field for Normal SPOT
Free fixedpoint.Value
// Locked balance for Spot wallet. This is a unique field for Normal SPOT
Locked fixedpoint.Value
// Available amount to withdraw of current coin
AvailableToWithdraw fixedpoint.Value `json:"availableToWithdraw"`
// Available amount to borrow of current coin
AvailableToBorrow fixedpoint.Value `json:"availableToBorrow"`
// Borrow amount of current coin
BorrowAmount fixedpoint.Value `json:"borrowAmount"`
// Accrued interest
AccruedInterest fixedpoint.Value `json:"accruedInterest"`
// Pre-occupied margin for order. For portfolio margin mode, it returns ""
TotalOrderIM fixedpoint.Value `json:"totalOrderIM"`
// Sum of initial margin of all positions + Pre-occupied liquidation fee. For portfolio margin mode, it returns ""
TotalPositionIM fixedpoint.Value `json:"totalPositionIM"`
// Sum of maintenance margin for all positions. For portfolio margin mode, it returns ""
TotalPositionMM fixedpoint.Value `json:"totalPositionMM"`
// Unrealised P&L
UnrealisedPnl fixedpoint.Value `json:"unrealisedPnl"`
// Cumulative Realised P&L
CumRealisedPnl fixedpoint.Value `json:"cumRealisedPnl"`
// Bonus. This is a unique field for UNIFIED account
Bonus fixedpoint.Value `json:"bonus"`
// Whether it can be used as a margin collateral currency (platform)
// - When marginCollateral=false, then collateralSwitch is meaningless
// - This is a unique field for UNIFIED account
CollateralSwitch bool `json:"collateralSwitch"`
// Whether the collateral is turned on by user (user)
// - When marginCollateral=true, then collateralSwitch is meaningful
// - This is a unique field for UNIFIED account
MarginCollateral bool `json:"marginCollateral"`
} `json:"coin"`
}
type OrderEvent struct { type OrderEvent struct {
bybitapi.Order bybitapi.Order