mirror of
https://github.com/d0zingcat/gocryptotrader.git
synced 2026-06-07 15:11:03 +00:00
CI: Fix golangci-lint linter issues, add prealloc linter and bump version depends for Go 1.18 (#915)
* Bump CI versions * Specifically set go version as 1.17.x bumps it to 1.18 * Another * Adjust AppVeyor * Part 1 of linter issues * Part 2 * Fix various linters and improvements * Part 3 * Finishing touches * Tests and EqualFold * Fix nitterinos plus bonus requester jobs bump for exchanges with large number of tests * Fix nitterinos and bump golangci-lint timeout for AppVeyor * Address nits, ensure all books are returned on err due to syncer regression * Fix the wiggins * Fix duplication * Fix nitterinos
This commit is contained in:
@@ -119,16 +119,15 @@ func (b *Binance) GetExchangeInfo(ctx context.Context) (ExchangeInfo, error) {
|
||||
// OrderBookDataRequestParams contains the following members
|
||||
// symbol: string of currency pair
|
||||
// limit: returned limit amount
|
||||
func (b *Binance) GetOrderBook(ctx context.Context, obd OrderBookDataRequestParams) (OrderBook, error) {
|
||||
var orderbook OrderBook
|
||||
func (b *Binance) GetOrderBook(ctx context.Context, obd OrderBookDataRequestParams) (*OrderBook, error) {
|
||||
if err := b.CheckLimit(obd.Limit); err != nil {
|
||||
return orderbook, err
|
||||
return nil, err
|
||||
}
|
||||
|
||||
params := url.Values{}
|
||||
symbol, err := b.FormatSymbol(obd.Symbol, asset.Spot)
|
||||
if err != nil {
|
||||
return orderbook, err
|
||||
return nil, err
|
||||
}
|
||||
params.Set("symbol", symbol)
|
||||
params.Set("limit", fmt.Sprintf("%d", obd.Limit))
|
||||
@@ -138,52 +137,54 @@ func (b *Binance) GetOrderBook(ctx context.Context, obd OrderBookDataRequestPara
|
||||
exchange.RestSpotSupplementary,
|
||||
orderBookDepth+"?"+params.Encode(),
|
||||
orderbookLimit(obd.Limit), &resp); err != nil {
|
||||
return orderbook, err
|
||||
return nil, err
|
||||
}
|
||||
|
||||
orderbook := OrderBook{
|
||||
Bids: make([]OrderbookItem, len(resp.Bids)),
|
||||
Asks: make([]OrderbookItem, len(resp.Asks)),
|
||||
LastUpdateID: resp.LastUpdateID,
|
||||
}
|
||||
for x := range resp.Bids {
|
||||
price, err := strconv.ParseFloat(resp.Bids[x][0], 64)
|
||||
if err != nil {
|
||||
return orderbook, err
|
||||
return nil, err
|
||||
}
|
||||
|
||||
amount, err := strconv.ParseFloat(resp.Bids[x][1], 64)
|
||||
if err != nil {
|
||||
return orderbook, err
|
||||
return nil, err
|
||||
}
|
||||
|
||||
orderbook.Bids = append(orderbook.Bids, OrderbookItem{
|
||||
orderbook.Bids[x] = OrderbookItem{
|
||||
Price: price,
|
||||
Quantity: amount,
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
for x := range resp.Asks {
|
||||
price, err := strconv.ParseFloat(resp.Asks[x][0], 64)
|
||||
if err != nil {
|
||||
return orderbook, err
|
||||
return nil, err
|
||||
}
|
||||
|
||||
amount, err := strconv.ParseFloat(resp.Asks[x][1], 64)
|
||||
if err != nil {
|
||||
return orderbook, err
|
||||
return nil, err
|
||||
}
|
||||
|
||||
orderbook.Asks = append(orderbook.Asks, OrderbookItem{
|
||||
orderbook.Asks[x] = OrderbookItem{
|
||||
Price: price,
|
||||
Quantity: amount,
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
orderbook.LastUpdateID = resp.LastUpdateID
|
||||
return orderbook, nil
|
||||
return &orderbook, nil
|
||||
}
|
||||
|
||||
// GetMostRecentTrades returns recent trade activity
|
||||
// limit: Up to 500 results returned
|
||||
func (b *Binance) GetMostRecentTrades(ctx context.Context, rtr RecentTradeRequestParams) ([]RecentTrade, error) {
|
||||
var resp []RecentTrade
|
||||
|
||||
params := url.Values{}
|
||||
symbol, err := b.FormatSymbol(rtr.Symbol, asset.Spot)
|
||||
if err != nil {
|
||||
@@ -194,6 +195,7 @@ func (b *Binance) GetMostRecentTrades(ctx context.Context, rtr RecentTradeReques
|
||||
|
||||
path := recentTrades + "?" + params.Encode()
|
||||
|
||||
var resp []RecentTrade
|
||||
return resp, b.SendHTTPRequest(ctx,
|
||||
exchange.RestSpotSupplementary, path, spotDefaultRate, &resp)
|
||||
}
|
||||
@@ -356,14 +358,12 @@ func (b *Binance) batchAggregateTrades(ctx context.Context, arg *AggregatedTrade
|
||||
// startTime: startTime filter for kline data
|
||||
// endTime: endTime filter for the kline data
|
||||
func (b *Binance) GetSpotKline(ctx context.Context, arg *KlinesRequestParams) ([]CandleStick, error) {
|
||||
var resp interface{}
|
||||
var klineData []CandleStick
|
||||
|
||||
params := url.Values{}
|
||||
symbol, err := b.FormatSymbol(arg.Symbol, asset.Spot)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
params := url.Values{}
|
||||
params.Set("symbol", symbol)
|
||||
params.Set("interval", arg.Interval)
|
||||
if arg.Limit != 0 {
|
||||
@@ -377,6 +377,7 @@ func (b *Binance) GetSpotKline(ctx context.Context, arg *KlinesRequestParams) ([
|
||||
}
|
||||
|
||||
path := candleStick + "?" + params.Encode()
|
||||
var resp interface{}
|
||||
|
||||
err = b.SendHTTPRequest(ctx,
|
||||
exchange.RestSpotSupplementary,
|
||||
@@ -390,6 +391,8 @@ func (b *Binance) GetSpotKline(ctx context.Context, arg *KlinesRequestParams) ([
|
||||
if !ok {
|
||||
return nil, errors.New("unable to type assert responseData")
|
||||
}
|
||||
|
||||
klineData := make([]CandleStick, len(responseData))
|
||||
for x := range responseData {
|
||||
individualData, ok := responseData[x].([]interface{})
|
||||
if !ok {
|
||||
@@ -432,7 +435,7 @@ func (b *Binance) GetSpotKline(ctx context.Context, arg *KlinesRequestParams) ([
|
||||
if candle.TakerBuyQuoteAssetVolume, err = convert.FloatFromString(individualData[10]); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
klineData = append(klineData, candle)
|
||||
klineData[x] = candle
|
||||
}
|
||||
return klineData, nil
|
||||
}
|
||||
|
||||
@@ -82,10 +82,18 @@ func (b *Binance) FuturesExchangeInfo(ctx context.Context) (CExchangeInfo, error
|
||||
}
|
||||
|
||||
// GetFuturesOrderbook gets orderbook data for CoinMarginedFutures,
|
||||
func (b *Binance) GetFuturesOrderbook(ctx context.Context, symbol currency.Pair, limit int64) (OrderBook, error) {
|
||||
var resp OrderBook
|
||||
var data OrderbookData
|
||||
func (b *Binance) GetFuturesOrderbook(ctx context.Context, symbol currency.Pair, limit int64) (*OrderBook, error) {
|
||||
symbolValue, err := b.FormatSymbol(symbol, asset.CoinMarginedFutures)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
params := url.Values{}
|
||||
params.Set("symbol", symbolValue)
|
||||
if limit > 0 && limit <= 1000 {
|
||||
params.Set("limit", strconv.FormatInt(limit, 10))
|
||||
}
|
||||
|
||||
rateBudget := cFuturesDefaultRate
|
||||
switch {
|
||||
case limit == 5, limit == 10, limit == 20, limit == 50:
|
||||
@@ -97,48 +105,47 @@ func (b *Binance) GetFuturesOrderbook(ctx context.Context, symbol currency.Pair,
|
||||
case limit == 1000:
|
||||
rateBudget = cFuturesOrderbook1000Rate
|
||||
}
|
||||
symbolValue, err := b.FormatSymbol(symbol, asset.CoinMarginedFutures)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
}
|
||||
params.Set("symbol", symbolValue)
|
||||
if limit > 0 && limit <= 1000 {
|
||||
params.Set("limit", strconv.FormatInt(limit, 10))
|
||||
}
|
||||
|
||||
var data OrderbookData
|
||||
err = b.SendHTTPRequest(ctx, exchange.RestCoinMargined, cfuturesOrderbook+params.Encode(), rateBudget, &data)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
|
||||
var resp OrderBook
|
||||
var price, quantity float64
|
||||
resp.Asks = make([]OrderbookItem, len(data.Asks))
|
||||
for x := range data.Asks {
|
||||
price, err = strconv.ParseFloat(data.Asks[x][0], 64)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
quantity, err = strconv.ParseFloat(data.Asks[x][1], 64)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
resp.Asks = append(resp.Asks, OrderbookItem{
|
||||
resp.Asks[x] = OrderbookItem{
|
||||
Price: price,
|
||||
Quantity: quantity,
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
resp.Bids = make([]OrderbookItem, len(data.Bids))
|
||||
for y := range data.Bids {
|
||||
price, err = strconv.ParseFloat(data.Bids[y][0], 64)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
quantity, err = strconv.ParseFloat(data.Bids[y][1], 64)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
resp.Bids = append(resp.Bids, OrderbookItem{
|
||||
resp.Bids[y] = OrderbookItem{
|
||||
Price: price,
|
||||
Quantity: quantity,
|
||||
})
|
||||
}
|
||||
}
|
||||
return resp, nil
|
||||
return &resp, nil
|
||||
}
|
||||
|
||||
// GetFuturesPublicTrades gets recent public trades for CoinMarginedFutures,
|
||||
@@ -232,13 +239,11 @@ func (b *Binance) GetIndexAndMarkPrice(ctx context.Context, symbol, pair string)
|
||||
|
||||
// GetFuturesKlineData gets futures kline data for CoinMarginedFutures,
|
||||
func (b *Binance) GetFuturesKlineData(ctx context.Context, symbol currency.Pair, interval string, limit int64, startTime, endTime time.Time) ([]FuturesCandleStick, error) {
|
||||
var data [][10]interface{}
|
||||
var resp []FuturesCandleStick
|
||||
params := url.Values{}
|
||||
if !symbol.IsEmpty() {
|
||||
symbolValue, err := b.FormatSymbol(symbol, asset.CoinMarginedFutures)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
params.Set("symbol", symbolValue)
|
||||
}
|
||||
@@ -246,453 +251,462 @@ func (b *Binance) GetFuturesKlineData(ctx context.Context, symbol currency.Pair,
|
||||
params.Set("limit", strconv.FormatInt(limit, 10))
|
||||
}
|
||||
if !common.StringDataCompare(validFuturesIntervals, interval) {
|
||||
return resp, errors.New("invalid interval parsed")
|
||||
return nil, errors.New("invalid interval parsed")
|
||||
}
|
||||
params.Set("interval", interval)
|
||||
if !startTime.IsZero() && !endTime.IsZero() {
|
||||
if startTime.After(endTime) {
|
||||
return resp, errors.New("startTime cannot be after endTime")
|
||||
return nil, errors.New("startTime cannot be after endTime")
|
||||
}
|
||||
params.Set("start_time", strconv.FormatInt(startTime.Unix(), 10))
|
||||
params.Set("end_time", strconv.FormatInt(endTime.Unix(), 10))
|
||||
}
|
||||
|
||||
var data [][10]interface{}
|
||||
rateBudget := getKlineRateBudget(limit)
|
||||
err := b.SendHTTPRequest(ctx, exchange.RestCoinMargined, cfuturesKlineData+params.Encode(), rateBudget, &data)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
var floatData float64
|
||||
var strData string
|
||||
var ok bool
|
||||
var tempData FuturesCandleStick
|
||||
|
||||
resp := make([]FuturesCandleStick, len(data))
|
||||
for x := range data {
|
||||
var floatData float64
|
||||
var strData string
|
||||
var ok bool
|
||||
var tempData FuturesCandleStick
|
||||
floatData, ok = data[x][0].(float64)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for open time")
|
||||
return nil, errors.New("type assertion failed for open time")
|
||||
}
|
||||
tempData.OpenTime = time.Unix(int64(floatData), 0)
|
||||
strData, ok = data[x][1].(string)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for open")
|
||||
return nil, errors.New("type assertion failed for open")
|
||||
}
|
||||
floatData, err = strconv.ParseFloat(strData, 64)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
tempData.Open = floatData
|
||||
strData, ok = data[x][2].(string)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for high")
|
||||
return nil, errors.New("type assertion failed for high")
|
||||
}
|
||||
floatData, err = strconv.ParseFloat(strData, 64)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
tempData.High = floatData
|
||||
strData, ok = data[x][3].(string)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for low")
|
||||
return nil, errors.New("type assertion failed for low")
|
||||
}
|
||||
floatData, err = strconv.ParseFloat(strData, 64)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
tempData.Low = floatData
|
||||
strData, ok = data[x][4].(string)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for close")
|
||||
return nil, errors.New("type assertion failed for close")
|
||||
}
|
||||
floatData, err = strconv.ParseFloat(strData, 64)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
tempData.Close = floatData
|
||||
strData, ok = data[x][5].(string)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for volume")
|
||||
return nil, errors.New("type assertion failed for volume")
|
||||
}
|
||||
floatData, err = strconv.ParseFloat(strData, 64)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
tempData.Volume = floatData
|
||||
floatData, ok = data[x][6].(float64)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for close time")
|
||||
return nil, errors.New("type assertion failed for close time")
|
||||
}
|
||||
tempData.CloseTime = time.Unix(int64(floatData), 0)
|
||||
strData, ok = data[x][7].(string)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for base asset volume")
|
||||
return nil, errors.New("type assertion failed for base asset volume")
|
||||
}
|
||||
floatData, err = strconv.ParseFloat(strData, 64)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
tempData.BaseAssetVolume = floatData
|
||||
floatData, ok = data[x][8].(float64)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for taker buy volume")
|
||||
return nil, errors.New("type assertion failed for taker buy volume")
|
||||
}
|
||||
tempData.TakerBuyVolume = floatData
|
||||
strData, ok = data[x][9].(string)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for taker buy base asset volume")
|
||||
return nil, errors.New("type assertion failed for taker buy base asset volume")
|
||||
}
|
||||
floatData, err = strconv.ParseFloat(strData, 64)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
tempData.TakerBuyBaseAssetVolume = floatData
|
||||
resp = append(resp, tempData)
|
||||
resp[x] = tempData
|
||||
}
|
||||
return resp, nil
|
||||
}
|
||||
|
||||
// GetContinuousKlineData gets continuous kline data
|
||||
func (b *Binance) GetContinuousKlineData(ctx context.Context, pair, contractType, interval string, limit int64, startTime, endTime time.Time) ([]FuturesCandleStick, error) {
|
||||
var data [][10]interface{}
|
||||
var resp []FuturesCandleStick
|
||||
params := url.Values{}
|
||||
params.Set("pair", pair)
|
||||
if !common.StringDataCompare(validContractType, contractType) {
|
||||
return resp, errors.New("invalid contractType")
|
||||
return nil, errors.New("invalid contractType")
|
||||
}
|
||||
params.Set("contractType", contractType)
|
||||
if limit > 0 && limit <= 1500 {
|
||||
params.Set("limit", strconv.FormatInt(limit, 10))
|
||||
}
|
||||
if !common.StringDataCompare(validFuturesIntervals, interval) {
|
||||
return resp, errors.New("invalid interval parsed")
|
||||
return nil, errors.New("invalid interval parsed")
|
||||
}
|
||||
params.Set("interval", interval)
|
||||
if !startTime.IsZero() && !endTime.IsZero() {
|
||||
if startTime.After(endTime) {
|
||||
return resp, errors.New("startTime cannot be after endTime")
|
||||
return nil, errors.New("startTime cannot be after endTime")
|
||||
}
|
||||
params.Set("start_time", strconv.FormatInt(startTime.Unix(), 10))
|
||||
params.Set("end_time", strconv.FormatInt(endTime.Unix(), 10))
|
||||
}
|
||||
|
||||
rateBudget := getKlineRateBudget(limit)
|
||||
var data [][10]interface{}
|
||||
err := b.SendHTTPRequest(ctx, exchange.RestCoinMargined, cfuturesContinuousKline+params.Encode(), rateBudget, &data)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
var floatData float64
|
||||
var strData string
|
||||
var ok bool
|
||||
var tempData FuturesCandleStick
|
||||
|
||||
resp := make([]FuturesCandleStick, len(data))
|
||||
for x := range data {
|
||||
var floatData float64
|
||||
var strData string
|
||||
var ok bool
|
||||
var tempData FuturesCandleStick
|
||||
floatData, ok = data[x][0].(float64)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for open time")
|
||||
return nil, errors.New("type assertion failed for open time")
|
||||
}
|
||||
tempData.OpenTime = time.Unix(int64(floatData), 0)
|
||||
strData, ok = data[x][1].(string)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for open")
|
||||
return nil, errors.New("type assertion failed for open")
|
||||
}
|
||||
floatData, err = strconv.ParseFloat(strData, 64)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
tempData.Open = floatData
|
||||
strData, ok = data[x][2].(string)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for high")
|
||||
return nil, errors.New("type assertion failed for high")
|
||||
}
|
||||
floatData, err = strconv.ParseFloat(strData, 64)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
tempData.High = floatData
|
||||
strData, ok = data[x][3].(string)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for low")
|
||||
return nil, errors.New("type assertion failed for low")
|
||||
}
|
||||
floatData, err = strconv.ParseFloat(strData, 64)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
tempData.Low = floatData
|
||||
strData, ok = data[x][4].(string)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for close")
|
||||
return nil, errors.New("type assertion failed for close")
|
||||
}
|
||||
floatData, err = strconv.ParseFloat(strData, 64)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
tempData.Close = floatData
|
||||
strData, ok = data[x][5].(string)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for volume")
|
||||
return nil, errors.New("type assertion failed for volume")
|
||||
}
|
||||
floatData, err = strconv.ParseFloat(strData, 64)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
tempData.Volume = floatData
|
||||
floatData, ok = data[x][6].(float64)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for close time")
|
||||
return nil, errors.New("type assertion failed for close time")
|
||||
}
|
||||
tempData.CloseTime = time.Unix(int64(floatData), 0)
|
||||
strData, ok = data[x][7].(string)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for base asset volume")
|
||||
return nil, errors.New("type assertion failed for base asset volume")
|
||||
}
|
||||
floatData, err = strconv.ParseFloat(strData, 64)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
tempData.BaseAssetVolume = floatData
|
||||
floatData, ok = data[x][8].(float64)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for taker buy volume")
|
||||
return nil, errors.New("type assertion failed for taker buy volume")
|
||||
}
|
||||
tempData.TakerBuyVolume = floatData
|
||||
strData, ok = data[x][9].(string)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for taker buy base asset volume")
|
||||
return nil, errors.New("type assertion failed for taker buy base asset volume")
|
||||
}
|
||||
floatData, err = strconv.ParseFloat(strData, 64)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
tempData.TakerBuyBaseAssetVolume = floatData
|
||||
resp = append(resp, tempData)
|
||||
resp[x] = tempData
|
||||
}
|
||||
return resp, nil
|
||||
}
|
||||
|
||||
// GetIndexPriceKlines gets continuous kline data
|
||||
func (b *Binance) GetIndexPriceKlines(ctx context.Context, pair, interval string, limit int64, startTime, endTime time.Time) ([]FuturesCandleStick, error) {
|
||||
var data [][10]interface{}
|
||||
var resp []FuturesCandleStick
|
||||
params := url.Values{}
|
||||
params.Set("pair", pair)
|
||||
if limit > 0 && limit <= 1500 {
|
||||
params.Set("limit", strconv.FormatInt(limit, 10))
|
||||
}
|
||||
if !common.StringDataCompare(validFuturesIntervals, interval) {
|
||||
return resp, errors.New("invalid interval parsed")
|
||||
return nil, errors.New("invalid interval parsed")
|
||||
}
|
||||
params.Set("interval", interval)
|
||||
if !startTime.IsZero() && !endTime.IsZero() {
|
||||
if startTime.After(endTime) {
|
||||
return resp, errors.New("startTime cannot be after endTime")
|
||||
return nil, errors.New("startTime cannot be after endTime")
|
||||
}
|
||||
params.Set("start_time", strconv.FormatInt(startTime.Unix(), 10))
|
||||
params.Set("end_time", strconv.FormatInt(endTime.Unix(), 10))
|
||||
}
|
||||
|
||||
rateBudget := getKlineRateBudget(limit)
|
||||
var data [][10]interface{}
|
||||
err := b.SendHTTPRequest(ctx, exchange.RestCoinMargined, cfuturesIndexKline+params.Encode(), rateBudget, &data)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
var floatData float64
|
||||
var strData string
|
||||
var ok bool
|
||||
var tempData FuturesCandleStick
|
||||
|
||||
resp := make([]FuturesCandleStick, len(data))
|
||||
for x := range data {
|
||||
var floatData float64
|
||||
var strData string
|
||||
var ok bool
|
||||
var tempData FuturesCandleStick
|
||||
floatData, ok = data[x][0].(float64)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for open time")
|
||||
return nil, errors.New("type assertion failed for open time")
|
||||
}
|
||||
tempData.OpenTime = time.Unix(int64(floatData), 0)
|
||||
strData, ok = data[x][1].(string)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for open")
|
||||
return nil, errors.New("type assertion failed for open")
|
||||
}
|
||||
floatData, err = strconv.ParseFloat(strData, 64)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
tempData.Open = floatData
|
||||
strData, ok = data[x][2].(string)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for high")
|
||||
return nil, errors.New("type assertion failed for high")
|
||||
}
|
||||
floatData, err = strconv.ParseFloat(strData, 64)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
tempData.High = floatData
|
||||
strData, ok = data[x][3].(string)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for low")
|
||||
return nil, errors.New("type assertion failed for low")
|
||||
}
|
||||
floatData, err = strconv.ParseFloat(strData, 64)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
tempData.Low = floatData
|
||||
strData, ok = data[x][4].(string)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for close")
|
||||
return nil, errors.New("type assertion failed for close")
|
||||
}
|
||||
floatData, err = strconv.ParseFloat(strData, 64)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
tempData.Close = floatData
|
||||
strData, ok = data[x][5].(string)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for volume")
|
||||
return nil, errors.New("type assertion failed for volume")
|
||||
}
|
||||
floatData, err = strconv.ParseFloat(strData, 64)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
tempData.Volume = floatData
|
||||
floatData, ok = data[x][6].(float64)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for close time")
|
||||
return nil, errors.New("type assertion failed for close time")
|
||||
}
|
||||
tempData.CloseTime = time.Unix(int64(floatData), 0)
|
||||
strData, ok = data[x][7].(string)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for base asset volume")
|
||||
return nil, errors.New("type assertion failed for base asset volume")
|
||||
}
|
||||
floatData, err = strconv.ParseFloat(strData, 64)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
tempData.BaseAssetVolume = floatData
|
||||
floatData, ok = data[x][8].(float64)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for taker buy volume")
|
||||
return nil, errors.New("type assertion failed for taker buy volume")
|
||||
}
|
||||
tempData.TakerBuyVolume = floatData
|
||||
strData, ok = data[x][9].(string)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for taker buy base asset volume")
|
||||
return nil, errors.New("type assertion failed for taker buy base asset volume")
|
||||
}
|
||||
floatData, err = strconv.ParseFloat(strData, 64)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
tempData.TakerBuyBaseAssetVolume = floatData
|
||||
resp = append(resp, tempData)
|
||||
resp[x] = tempData
|
||||
}
|
||||
return resp, nil
|
||||
}
|
||||
|
||||
// GetMarkPriceKline gets mark price kline data
|
||||
func (b *Binance) GetMarkPriceKline(ctx context.Context, symbol currency.Pair, interval string, limit int64, startTime, endTime time.Time) ([]FuturesCandleStick, error) {
|
||||
var data [][10]interface{}
|
||||
var resp []FuturesCandleStick
|
||||
params := url.Values{}
|
||||
symbolValue, err := b.FormatSymbol(symbol, asset.CoinMarginedFutures)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
params := url.Values{}
|
||||
params.Set("symbol", symbolValue)
|
||||
if limit > 0 && limit <= 1500 {
|
||||
params.Set("limit", strconv.FormatInt(limit, 10))
|
||||
}
|
||||
if !common.StringDataCompare(validFuturesIntervals, interval) {
|
||||
return resp, errors.New("invalid interval parsed")
|
||||
return nil, errors.New("invalid interval parsed")
|
||||
}
|
||||
params.Set("interval", interval)
|
||||
if !startTime.IsZero() && !endTime.IsZero() {
|
||||
if startTime.After(endTime) {
|
||||
return resp, errors.New("startTime cannot be after endTime")
|
||||
return nil, errors.New("startTime cannot be after endTime")
|
||||
}
|
||||
params.Set("start_time", strconv.FormatInt(startTime.Unix(), 10))
|
||||
params.Set("end_time", strconv.FormatInt(endTime.Unix(), 10))
|
||||
}
|
||||
|
||||
var data [][10]interface{}
|
||||
rateBudget := getKlineRateBudget(limit)
|
||||
err = b.SendHTTPRequest(ctx, exchange.RestCoinMargined, cfuturesMarkPriceKline+params.Encode(), rateBudget, &data)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
var floatData float64
|
||||
var strData string
|
||||
var ok bool
|
||||
var tempData FuturesCandleStick
|
||||
|
||||
resp := make([]FuturesCandleStick, len(data))
|
||||
for x := range data {
|
||||
var floatData float64
|
||||
var strData string
|
||||
var ok bool
|
||||
var tempData FuturesCandleStick
|
||||
floatData, ok = data[x][0].(float64)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for open time")
|
||||
return nil, errors.New("type assertion failed for open time")
|
||||
}
|
||||
tempData.OpenTime = time.Unix(int64(floatData), 0)
|
||||
strData, ok = data[x][1].(string)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for open")
|
||||
return nil, errors.New("type assertion failed for open")
|
||||
}
|
||||
floatData, err = strconv.ParseFloat(strData, 64)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
tempData.Open = floatData
|
||||
strData, ok = data[x][2].(string)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for high")
|
||||
return nil, errors.New("type assertion failed for high")
|
||||
}
|
||||
floatData, err = strconv.ParseFloat(strData, 64)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
tempData.High = floatData
|
||||
strData, ok = data[x][3].(string)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for low")
|
||||
return nil, errors.New("type assertion failed for low")
|
||||
}
|
||||
floatData, err = strconv.ParseFloat(strData, 64)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
tempData.Low = floatData
|
||||
strData, ok = data[x][4].(string)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for close")
|
||||
return nil, errors.New("type assertion failed for close")
|
||||
}
|
||||
floatData, err = strconv.ParseFloat(strData, 64)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
tempData.Close = floatData
|
||||
strData, ok = data[x][5].(string)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for volume")
|
||||
return nil, errors.New("type assertion failed for volume")
|
||||
}
|
||||
floatData, err = strconv.ParseFloat(strData, 64)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
tempData.Volume = floatData
|
||||
floatData, ok = data[x][6].(float64)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for close time")
|
||||
return nil, errors.New("type assertion failed for close time")
|
||||
}
|
||||
tempData.CloseTime = time.Unix(int64(floatData), 0)
|
||||
strData, ok = data[x][7].(string)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for base asset volume")
|
||||
return nil, errors.New("type assertion failed for base asset volume")
|
||||
}
|
||||
floatData, err = strconv.ParseFloat(strData, 64)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
tempData.BaseAssetVolume = floatData
|
||||
floatData, ok = data[x][8].(float64)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for taker buy volume")
|
||||
return nil, errors.New("type assertion failed for taker buy volume")
|
||||
}
|
||||
tempData.TakerBuyVolume = floatData
|
||||
strData, ok = data[x][9].(string)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for taker buy base asset volume")
|
||||
return nil, errors.New("type assertion failed for taker buy base asset volume")
|
||||
}
|
||||
floatData, err = strconv.ParseFloat(strData, 64)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
tempData.TakerBuyBaseAssetVolume = floatData
|
||||
resp = append(resp, tempData)
|
||||
resp[x] = tempData
|
||||
}
|
||||
return resp, nil
|
||||
}
|
||||
@@ -1466,12 +1480,12 @@ func (b *Binance) FuturesPositionsADLEstimate(ctx context.Context, symbol curren
|
||||
|
||||
// FetchCoinMarginExchangeLimits fetches coin margined order execution limits
|
||||
func (b *Binance) FetchCoinMarginExchangeLimits(ctx context.Context) ([]order.MinMaxLevel, error) {
|
||||
var limits []order.MinMaxLevel
|
||||
coinFutures, err := b.FuturesExchangeInfo(ctx)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
limits := make([]order.MinMaxLevel, 0, len(coinFutures.Symbols))
|
||||
for x := range coinFutures.Symbols {
|
||||
symbol := strings.Split(coinFutures.Symbols[x].Symbol, currency.UnderscoreDelimiter)
|
||||
var cp currency.Pair
|
||||
|
||||
@@ -36,6 +36,7 @@ func TestMain(m *testing.M) {
|
||||
log.Fatal("Binance setup error", err)
|
||||
}
|
||||
b.setupOrderbookManager()
|
||||
request.MaxRequestJobs = 100
|
||||
b.Websocket.DataHandler = sharedtestvalues.GetWebsocketInterfaceChannelOverride()
|
||||
log.Printf(sharedtestvalues.LiveTesting, b.Name)
|
||||
os.Exit(m.Run())
|
||||
|
||||
@@ -12,6 +12,7 @@ import (
|
||||
|
||||
"github.com/thrasher-corp/gocryptotrader/config"
|
||||
"github.com/thrasher-corp/gocryptotrader/exchanges/mock"
|
||||
"github.com/thrasher-corp/gocryptotrader/exchanges/request"
|
||||
"github.com/thrasher-corp/gocryptotrader/exchanges/sharedtestvalues"
|
||||
)
|
||||
|
||||
@@ -57,6 +58,7 @@ func TestMain(m *testing.M) {
|
||||
log.Fatal(err)
|
||||
}
|
||||
}
|
||||
request.MaxRequestJobs = 100
|
||||
log.Printf(sharedtestvalues.MockTesting, b.Name)
|
||||
os.Exit(m.Run())
|
||||
}
|
||||
|
||||
@@ -84,22 +84,22 @@ func (b *Binance) UExchangeInfo(ctx context.Context) (UFuturesExchangeInfo, erro
|
||||
}
|
||||
|
||||
// UFuturesOrderbook gets orderbook data for usdt margined futures
|
||||
func (b *Binance) UFuturesOrderbook(ctx context.Context, symbol currency.Pair, limit int64) (OrderBook, error) {
|
||||
var resp OrderBook
|
||||
var data OrderbookData
|
||||
params := url.Values{}
|
||||
func (b *Binance) UFuturesOrderbook(ctx context.Context, symbol currency.Pair, limit int64) (*OrderBook, error) {
|
||||
symbolValue, err := b.FormatSymbol(symbol, asset.USDTMarginedFutures)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
|
||||
params := url.Values{}
|
||||
params.Set("symbol", symbolValue)
|
||||
strLimit := strconv.FormatInt(limit, 10)
|
||||
if strLimit != "" {
|
||||
if !common.StringDataCompare(uValidOBLimits, strLimit) {
|
||||
return resp, fmt.Errorf("invalid limit: %v", limit)
|
||||
return nil, fmt.Errorf("invalid limit: %v", limit)
|
||||
}
|
||||
params.Set("limit", strLimit)
|
||||
}
|
||||
|
||||
rateBudget := uFuturesDefaultRate
|
||||
switch {
|
||||
case limit == 5, limit == 10, limit == 20, limit == 50:
|
||||
@@ -111,42 +111,50 @@ func (b *Binance) UFuturesOrderbook(ctx context.Context, symbol currency.Pair, l
|
||||
case limit == 1000:
|
||||
rateBudget = uFuturesOrderbook1000Rate
|
||||
}
|
||||
|
||||
var data OrderbookData
|
||||
err = b.SendHTTPRequest(ctx, exchange.RestUSDTMargined, ufuturesOrderbook+params.Encode(), rateBudget, &data)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
resp.Symbol = symbolValue
|
||||
resp.LastUpdateID = data.LastUpdateID
|
||||
|
||||
resp := OrderBook{
|
||||
Symbol: symbolValue,
|
||||
LastUpdateID: data.LastUpdateID,
|
||||
Bids: make([]OrderbookItem, len(data.Bids)),
|
||||
Asks: make([]OrderbookItem, len(data.Asks)),
|
||||
}
|
||||
|
||||
var price, quantity float64
|
||||
for x := range data.Asks {
|
||||
price, err = strconv.ParseFloat(data.Asks[x][0], 64)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
quantity, err = strconv.ParseFloat(data.Asks[x][1], 64)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
resp.Asks = append(resp.Asks, OrderbookItem{
|
||||
resp.Asks[x] = OrderbookItem{
|
||||
Price: price,
|
||||
Quantity: quantity,
|
||||
})
|
||||
}
|
||||
}
|
||||
for y := range data.Bids {
|
||||
price, err = strconv.ParseFloat(data.Bids[y][0], 64)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
quantity, err = strconv.ParseFloat(data.Bids[y][1], 64)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
resp.Bids = append(resp.Bids, OrderbookItem{
|
||||
resp.Bids[y] = OrderbookItem{
|
||||
Price: price,
|
||||
Quantity: quantity,
|
||||
})
|
||||
}
|
||||
}
|
||||
return resp, nil
|
||||
return &resp, nil
|
||||
}
|
||||
|
||||
// URecentTrades gets recent trades for usdt margined futures
|
||||
@@ -212,16 +220,14 @@ func (b *Binance) UCompressedTrades(ctx context.Context, symbol currency.Pair, f
|
||||
|
||||
// UKlineData gets kline data for usdt margined futures
|
||||
func (b *Binance) UKlineData(ctx context.Context, symbol currency.Pair, interval string, limit int64, startTime, endTime time.Time) ([]FuturesCandleStick, error) {
|
||||
var data [][10]interface{}
|
||||
var resp []FuturesCandleStick
|
||||
params := url.Values{}
|
||||
symbolValue, err := b.FormatSymbol(symbol, asset.USDTMarginedFutures)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
params.Set("symbol", symbolValue)
|
||||
if !common.StringDataCompare(validFuturesIntervals, interval) {
|
||||
return resp, errors.New("invalid interval")
|
||||
return nil, errors.New("invalid interval")
|
||||
}
|
||||
params.Set("interval", interval)
|
||||
if limit > 0 && limit <= 1500 {
|
||||
@@ -229,7 +235,7 @@ func (b *Binance) UKlineData(ctx context.Context, symbol currency.Pair, interval
|
||||
}
|
||||
if !startTime.IsZero() && !endTime.IsZero() {
|
||||
if startTime.After(endTime) {
|
||||
return resp, errors.New("startTime cannot be after endTime")
|
||||
return nil, errors.New("startTime cannot be after endTime")
|
||||
}
|
||||
params.Set("startTime", timeString(startTime))
|
||||
params.Set("endTime", timeString(endTime))
|
||||
@@ -245,71 +251,76 @@ func (b *Binance) UKlineData(ctx context.Context, symbol currency.Pair, interval
|
||||
case limit > 1000:
|
||||
rateBudget = uFuturesKlineMaxRate
|
||||
}
|
||||
|
||||
var data [][10]interface{}
|
||||
err = b.SendHTTPRequest(ctx, exchange.RestUSDTMargined, ufuturesKlineData+params.Encode(), rateBudget, &data)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
var tempData FuturesCandleStick
|
||||
var floatData float64
|
||||
var strData string
|
||||
var ok bool
|
||||
|
||||
resp := make([]FuturesCandleStick, len(data))
|
||||
for x := range data {
|
||||
var tempData FuturesCandleStick
|
||||
var floatData float64
|
||||
var strData string
|
||||
var ok bool
|
||||
|
||||
floatData, ok = data[x][0].(float64)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for opentime")
|
||||
return nil, errors.New("type assertion failed for opentime")
|
||||
}
|
||||
tempData.OpenTime, err = convert.TimeFromUnixTimestampFloat(floatData)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
strData, ok = data[x][1].(string)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for open")
|
||||
return nil, errors.New("type assertion failed for open")
|
||||
}
|
||||
floatData, err = strconv.ParseFloat(strData, 64)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
tempData.Open = floatData
|
||||
strData, ok = data[x][2].(string)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for high")
|
||||
return nil, errors.New("type assertion failed for high")
|
||||
}
|
||||
floatData, err = strconv.ParseFloat(strData, 64)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
tempData.High = floatData
|
||||
strData, ok = data[x][3].(string)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for low")
|
||||
return nil, errors.New("type assertion failed for low")
|
||||
}
|
||||
floatData, err = strconv.ParseFloat(strData, 64)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
tempData.Low = floatData
|
||||
strData, ok = data[x][4].(string)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for close")
|
||||
return nil, errors.New("type assertion failed for close")
|
||||
}
|
||||
floatData, err = strconv.ParseFloat(strData, 64)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
tempData.Close = floatData
|
||||
strData, ok = data[x][5].(string)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for volume")
|
||||
return nil, errors.New("type assertion failed for volume")
|
||||
}
|
||||
floatData, err = strconv.ParseFloat(strData, 64)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
tempData.Volume = floatData
|
||||
floatData, ok = data[x][6].(float64)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for close time")
|
||||
return nil, errors.New("type assertion failed for close time")
|
||||
}
|
||||
tempData.CloseTime, err = convert.TimeFromUnixTimestampFloat(floatData)
|
||||
if err != nil {
|
||||
@@ -317,28 +328,28 @@ func (b *Binance) UKlineData(ctx context.Context, symbol currency.Pair, interval
|
||||
}
|
||||
strData, ok = data[x][7].(string)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed base asset volume")
|
||||
return nil, errors.New("type assertion failed base asset volume")
|
||||
}
|
||||
floatData, err = strconv.ParseFloat(strData, 64)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
tempData.BaseAssetVolume = floatData
|
||||
floatData, ok = data[x][8].(float64)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for taker buy volume")
|
||||
return nil, errors.New("type assertion failed for taker buy volume")
|
||||
}
|
||||
tempData.TakerBuyVolume = floatData
|
||||
strData, ok = data[x][9].(string)
|
||||
if !ok {
|
||||
return resp, errors.New("type assertion failed for taker buy base asset volume")
|
||||
return nil, errors.New("type assertion failed for taker buy base asset volume")
|
||||
}
|
||||
floatData, err = strconv.ParseFloat(strData, 64)
|
||||
if err != nil {
|
||||
return resp, err
|
||||
return nil, err
|
||||
}
|
||||
tempData.TakerBuyBaseAssetVolume = floatData
|
||||
resp = append(resp, tempData)
|
||||
resp[x] = tempData
|
||||
}
|
||||
return resp, nil
|
||||
}
|
||||
@@ -1139,12 +1150,12 @@ func (b *Binance) GetFundingRates(ctx context.Context, symbol currency.Pair, lim
|
||||
|
||||
// FetchUSDTMarginExchangeLimits fetches USDT margined order execution limits
|
||||
func (b *Binance) FetchUSDTMarginExchangeLimits(ctx context.Context) ([]order.MinMaxLevel, error) {
|
||||
var limits []order.MinMaxLevel
|
||||
usdtFutures, err := b.UExchangeInfo(ctx)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
limits := make([]order.MinMaxLevel, 0, len(usdtFutures.Symbols))
|
||||
for x := range usdtFutures.Symbols {
|
||||
var cp currency.Pair
|
||||
cp, err = currency.NewPairFromStrings(usdtFutures.Symbols[x].BaseAsset,
|
||||
|
||||
@@ -482,31 +482,32 @@ func (b *Binance) SeedLocalCache(ctx context.Context, p currency.Pair) error {
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
return b.SeedLocalCacheWithBook(p, &ob)
|
||||
return b.SeedLocalCacheWithBook(p, ob)
|
||||
}
|
||||
|
||||
// SeedLocalCacheWithBook seeds the local orderbook cache
|
||||
func (b *Binance) SeedLocalCacheWithBook(p currency.Pair, orderbookNew *OrderBook) error {
|
||||
var newOrderBook orderbook.Base
|
||||
newOrderBook := orderbook.Base{
|
||||
Pair: p,
|
||||
Asset: asset.Spot,
|
||||
Exchange: b.Name,
|
||||
LastUpdateID: orderbookNew.LastUpdateID,
|
||||
VerifyOrderbook: b.CanVerifyOrderbook,
|
||||
Bids: make(orderbook.Items, len(orderbookNew.Bids)),
|
||||
Asks: make(orderbook.Items, len(orderbookNew.Asks)),
|
||||
}
|
||||
for i := range orderbookNew.Bids {
|
||||
newOrderBook.Bids = append(newOrderBook.Bids, orderbook.Item{
|
||||
newOrderBook.Bids[i] = orderbook.Item{
|
||||
Amount: orderbookNew.Bids[i].Quantity,
|
||||
Price: orderbookNew.Bids[i].Price,
|
||||
})
|
||||
}
|
||||
}
|
||||
for i := range orderbookNew.Asks {
|
||||
newOrderBook.Asks = append(newOrderBook.Asks, orderbook.Item{
|
||||
newOrderBook.Asks[i] = orderbook.Item{
|
||||
Amount: orderbookNew.Asks[i].Quantity,
|
||||
Price: orderbookNew.Asks[i].Price,
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
newOrderBook.Pair = p
|
||||
newOrderBook.Asset = asset.Spot
|
||||
newOrderBook.Exchange = b.Name
|
||||
newOrderBook.LastUpdateID = orderbookNew.LastUpdateID
|
||||
newOrderBook.VerifyOrderbook = b.CanVerifyOrderbook
|
||||
|
||||
return b.Websocket.Orderbook.LoadSnapshot(&newOrderBook)
|
||||
}
|
||||
|
||||
@@ -626,7 +627,7 @@ func (b *Binance) Unsubscribe(channelsToUnsubscribe []stream.ChannelSubscription
|
||||
|
||||
// ProcessUpdate processes the websocket orderbook update
|
||||
func (b *Binance) ProcessUpdate(cp currency.Pair, a asset.Item, ws *WebsocketDepthStream) error {
|
||||
var updateBid []orderbook.Item
|
||||
updateBid := make([]orderbook.Item, len(ws.UpdateBids))
|
||||
for i := range ws.UpdateBids {
|
||||
price, ok := ws.UpdateBids[i][0].(string)
|
||||
if !ok {
|
||||
@@ -644,10 +645,10 @@ func (b *Binance) ProcessUpdate(cp currency.Pair, a asset.Item, ws *WebsocketDep
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
updateBid = append(updateBid, orderbook.Item{Price: p, Amount: a})
|
||||
updateBid[i] = orderbook.Item{Price: p, Amount: a}
|
||||
}
|
||||
|
||||
var updateAsk []orderbook.Item
|
||||
updateAsk := make([]orderbook.Item, len(ws.UpdateAsks))
|
||||
for i := range ws.UpdateAsks {
|
||||
price, ok := ws.UpdateAsks[i][0].(string)
|
||||
if !ok {
|
||||
@@ -665,7 +666,7 @@ func (b *Binance) ProcessUpdate(cp currency.Pair, a asset.Item, ws *WebsocketDep
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
updateAsk = append(updateAsk, orderbook.Item{Price: p, Amount: a})
|
||||
updateAsk[i] = orderbook.Item{Price: p, Amount: a}
|
||||
}
|
||||
|
||||
return b.Websocket.Orderbook.Update(&buffer.Update{
|
||||
|
||||
@@ -657,7 +657,7 @@ func (b *Binance) UpdateOrderbook(ctx context.Context, p currency.Pair, assetTyp
|
||||
Asset: assetType,
|
||||
VerifyOrderbook: b.CanVerifyOrderbook,
|
||||
}
|
||||
var orderbookNew OrderBook
|
||||
var orderbookNew *OrderBook
|
||||
var err error
|
||||
switch assetType {
|
||||
case asset.Spot, asset.Margin:
|
||||
@@ -673,17 +673,20 @@ func (b *Binance) UpdateOrderbook(ctx context.Context, p currency.Pair, assetTyp
|
||||
if err != nil {
|
||||
return book, err
|
||||
}
|
||||
|
||||
book.Bids = make(orderbook.Items, len(orderbookNew.Bids))
|
||||
for x := range orderbookNew.Bids {
|
||||
book.Bids = append(book.Bids, orderbook.Item{
|
||||
book.Bids[x] = orderbook.Item{
|
||||
Amount: orderbookNew.Bids[x].Quantity,
|
||||
Price: orderbookNew.Bids[x].Price,
|
||||
})
|
||||
}
|
||||
}
|
||||
book.Asks = make(orderbook.Items, len(orderbookNew.Asks))
|
||||
for x := range orderbookNew.Asks {
|
||||
book.Asks = append(book.Asks, orderbook.Item{
|
||||
book.Asks[x] = orderbook.Item{
|
||||
Amount: orderbookNew.Asks[x].Quantity,
|
||||
Price: orderbookNew.Asks[x].Price,
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
err = book.Process()
|
||||
@@ -834,15 +837,16 @@ func (b *Binance) GetWithdrawalsHistory(ctx context.Context, c currency.Code) (r
|
||||
|
||||
// GetRecentTrades returns the most recent trades for a currency and asset
|
||||
func (b *Binance) GetRecentTrades(ctx context.Context, p currency.Pair, assetType asset.Item) ([]trade.Data, error) {
|
||||
var resp []trade.Data
|
||||
limit := 1000
|
||||
const limit = 1000
|
||||
tradeData, err := b.GetMostRecentTrades(ctx,
|
||||
RecentTradeRequestParams{p, limit})
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
resp := make([]trade.Data, len(tradeData))
|
||||
for i := range tradeData {
|
||||
resp = append(resp, trade.Data{
|
||||
resp[i] = trade.Data{
|
||||
TID: strconv.FormatInt(tradeData[i].ID, 10),
|
||||
Exchange: b.Name,
|
||||
CurrencyPair: p,
|
||||
@@ -850,7 +854,7 @@ func (b *Binance) GetRecentTrades(ctx context.Context, p currency.Pair, assetTyp
|
||||
Price: tradeData[i].Price,
|
||||
Amount: tradeData[i].Quantity,
|
||||
Timestamp: tradeData[i].Time,
|
||||
})
|
||||
}
|
||||
}
|
||||
if b.IsSaveTradeDataEnabled() {
|
||||
err := trade.AddTradesToBuffer(b.Name, resp...)
|
||||
@@ -874,11 +878,11 @@ func (b *Binance) GetHistoricTrades(ctx context.Context, p currency.Pair, a asse
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
var result []trade.Data
|
||||
result := make([]trade.Data, len(trades))
|
||||
exName := b.GetName()
|
||||
for i := range trades {
|
||||
t := trades[i].toTradeData(p, exName, a)
|
||||
result = append(result, *t)
|
||||
result[i] = *t
|
||||
}
|
||||
return result, nil
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user