Skip to content

Commit

Permalink
mm/libxc: Coinbase
Browse files Browse the repository at this point in the history
Co-authored-by: Brian Stafford <[email protected]>
  • Loading branch information
martonp and buck54321 committed Nov 29, 2024
1 parent 3a211e7 commit 92f7e28
Show file tree
Hide file tree
Showing 12 changed files with 2,372 additions and 73 deletions.
8 changes: 5 additions & 3 deletions client/mm/exchange_adaptor.go
Original file line number Diff line number Diff line change
Expand Up @@ -1877,8 +1877,9 @@ func (u *unifiedExchangeAdaptor) confirmWithdrawal(ctx context.Context, id strin
withdrawal.txMtx.RUnlock()

if txID == "" {
var amt uint64
var err error
_, txID, err = u.CEX.ConfirmWithdrawal(ctx, id, withdrawal.assetID)
amt, txID, err = u.CEX.ConfirmWithdrawal(ctx, id, withdrawal.assetID)
if errors.Is(err, libxc.ErrWithdrawalPending) {
return false
}
Expand All @@ -1888,6 +1889,7 @@ func (u *unifiedExchangeAdaptor) confirmWithdrawal(ctx context.Context, id strin
}

withdrawal.txMtx.Lock()
withdrawal.amtWithdrawn = amt
withdrawal.txID = txID
withdrawal.txMtx.Unlock()
}
Expand Down Expand Up @@ -1944,7 +1946,7 @@ func (u *unifiedExchangeAdaptor) withdraw(ctx context.Context, assetID uint32, a
}

u.balancesMtx.Lock()
withdrawalID, err := u.CEX.Withdraw(ctx, assetID, amount, addr)
withdrawalID, amtWithdrawn, err := u.CEX.Withdraw(ctx, assetID, amount, addr)
if err != nil {
u.balancesMtx.Unlock()
return err
Expand All @@ -1960,7 +1962,7 @@ func (u *unifiedExchangeAdaptor) withdraw(ctx context.Context, assetID uint32, a
eventLogID: u.eventLogID.Add(1),
timestamp: time.Now().Unix(),
assetID: assetID,
amtWithdrawn: amount,
amtWithdrawn: amtWithdrawn,
withdrawalID: withdrawalID,
}
u.pendingWithdrawals[withdrawalID] = withdrawal
Expand Down
88 changes: 67 additions & 21 deletions client/mm/libxc/binance.go
Original file line number Diff line number Diff line change
Expand Up @@ -908,18 +908,62 @@ func (bnc *binance) ConfirmWithdrawal(ctx context.Context, withdrawalID string,
return uint64(amt), status.TxID, nil
}

func floatToScaledUint(f float64) (uint64, int) {
str := strconv.FormatFloat(f, 'f', -1, 64)
parts := strings.Split(str, ".")
scaledStr := parts[0]
decimalPlaces := 0
if len(parts) == 2 {
scaledStr += parts[1]
decimalPlaces = len(parts[1])
}
scaledValue, _ := strconv.ParseUint(scaledStr, 10, 64)
return scaledValue, decimalPlaces
}

func scaledUintToString(u uint64, decimalPlaces int) string {
numStr := strconv.FormatUint(u, 10)
if decimalPlaces == 0 {
return numStr
}
length := len(numStr)
if decimalPlaces > length {
leadingZeros := decimalPlaces - length
return "0." + fmt.Sprintf("%0*d%s", leadingZeros, 0, numStr)
} else if decimalPlaces == length {
return "0." + numStr
} else {
return numStr[:length-decimalPlaces] + "." + numStr[length-decimalPlaces:]
}
}

func steppedAmount(amt float64, stepSize float64) float64 {
steppedAmountStr := steppedAmountStr(amt, stepSize)
steppedAmount, _ := strconv.ParseFloat(steppedAmountStr, 64)
return steppedAmount
}

func steppedAmountStr(amt float64, stepSize float64) string {
steps := uint64(math.Round(amt / stepSize))
if steps == 0 {
steps = 1
}
scaled, prec := floatToScaledUint(stepSize)
return scaledUintToString(steps*scaled, prec)
}

// Withdraw withdraws funds from the CEX to a certain address. onComplete
// is called with the actual amount withdrawn (amt - fees) and the
// transaction ID of the withdrawal.
func (bnc *binance) Withdraw(ctx context.Context, assetID uint32, qty uint64, address string) (string, error) {
func (bnc *binance) Withdraw(ctx context.Context, assetID uint32, qty uint64, address string) (string, uint64, error) {
assetCfg, err := bncAssetCfg(assetID)
if err != nil {
return "", fmt.Errorf("error getting symbol data for %d: %w", assetID, err)
return "", 0, fmt.Errorf("error getting symbol data for %d: %w", assetID, err)
}

precision, err := bnc.assetPrecision(assetCfg.coin)
if err != nil {
return "", fmt.Errorf("error getting precision for %s: %w", assetCfg.coin, err)
return "", 0, fmt.Errorf("error getting precision for %s: %w", assetCfg.coin, err)
}

amt := float64(qty) / float64(assetCfg.conversionFactor)
Expand All @@ -934,10 +978,10 @@ func (bnc *binance) Withdraw(ctx context.Context, assetID uint32, qty uint64, ad
}{}
err = bnc.postAPI(ctx, "/sapi/v1/capital/withdraw/apply", nil, v, true, true, &withdrawResp)
if err != nil {
return "", err
return "", 0, err
}

return withdrawResp.ID, nil
return withdrawResp.ID, qty, nil
}

// GetDepositAddress returns a deposit address for an asset.
Expand Down Expand Up @@ -1984,28 +2028,30 @@ func (bnc *binance) book(baseID, quoteID uint32) (*binanceOrderBook, error) {
return book, nil
}

func convertSide(side []*obEntry, sell bool, baseFactor, quoteFactor uint64) []*core.MiniOrder {
ords := make([]*core.MiniOrder, len(side))
for i, e := range side {
ords[i] = &core.MiniOrder{
Qty: float64(e.qty) / float64(baseFactor),
QtyAtomic: e.qty,
Rate: calc.ConventionalRateAlt(e.rate, baseFactor, quoteFactor),
MsgRate: e.rate,
Sell: sell,
}
}
return ords
}

func (bnc *binance) Book(baseID, quoteID uint32) (buys, sells []*core.MiniOrder, _ error) {
book, err := bnc.book(baseID, quoteID)
if err != nil {
return nil, nil, err
}
bids, asks := book.book.snap()
bFactor := float64(book.baseConversionFactor)
convertSide := func(side []*obEntry, sell bool) []*core.MiniOrder {
ords := make([]*core.MiniOrder, len(side))
for i, e := range side {
ords[i] = &core.MiniOrder{
Qty: float64(e.qty) / bFactor,
QtyAtomic: e.qty,
Rate: calc.ConventionalRateAlt(e.rate, book.baseConversionFactor, book.quoteConversionFactor),
MsgRate: e.rate,
Sell: sell,
}
}
return ords
}
buys = convertSide(bids, false)
sells = convertSide(asks, true)
bFactor := book.baseConversionFactor
qFactor := book.quoteConversionFactor
buys = convertSide(bids, false, bFactor, qFactor)
sells = convertSide(asks, true, bFactor, qFactor)
return
}

Expand Down
Loading

0 comments on commit 92f7e28

Please sign in to comment.