mirror of
https://github.com/NoFxAiOS/nofx.git
synced 2026-06-06 05:51:19 +08:00
feat: implement coinank openapi liquidation interface (#1247)
- implement LiquidationExchangeStatistics,LiquidationCoinAggHistory in provider/coinank/liquidation.go - implement LiquidationHistory,LiquidationOrders in provider/coinank/liquidation.go
This commit is contained in:
172
provider/coinank/liquidation.go
Normal file
172
provider/coinank/liquidation.go
Normal file
@@ -0,0 +1,172 @@
|
||||
package coinank
|
||||
|
||||
import (
|
||||
"context"
|
||||
"encoding/json"
|
||||
"nofx/provider/coinank/coinank_enum"
|
||||
"strconv"
|
||||
)
|
||||
|
||||
// LiquidationExchangeStatistics Current Exchange Liquidation Statistics
|
||||
func (c *CoinankClient) LiquidationExchangeStatistics(ctx context.Context, baseCoin string) (*LiquidationExchangeStatisticsResponse, error) {
|
||||
paramsMap := make(map[string]string, 3)
|
||||
paramsMap["baseCoin"] = baseCoin
|
||||
resp, err := c.Get(ctx, "/api/liquidation/allExchange/intervals", paramsMap)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
var result CoinankResponse[LiquidationExchangeStatisticsResponse]
|
||||
err = json.Unmarshal([]byte(resp), &result)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
if !result.Success {
|
||||
return nil, HttpError
|
||||
}
|
||||
return &result.Data, nil
|
||||
}
|
||||
|
||||
// LiquidationCoinAggHistory coin liquidation aggregated history
|
||||
func (c *CoinankClient) LiquidationCoinAggHistory(ctx context.Context, baseCoin string, interval coinank_enum.Interval,
|
||||
endTime int64, size int) ([]LiquidationStatistic, error) {
|
||||
paramsMap := make(map[string]string, 4)
|
||||
paramsMap["baseCoin"] = baseCoin
|
||||
paramsMap["interval"] = string(interval)
|
||||
paramsMap["endTime"] = strconv.FormatInt(endTime, 10)
|
||||
paramsMap["size"] = strconv.Itoa(size)
|
||||
resp, err := c.Get(ctx, "/api/liquidation/aggregated-history", paramsMap)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
var result CoinankResponse[[]LiquidationStatistic]
|
||||
err = json.Unmarshal([]byte(resp), &result)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
if !result.Success {
|
||||
return nil, HttpError
|
||||
}
|
||||
return result.Data, nil
|
||||
}
|
||||
|
||||
// LiquidationHistory Trading Pair Liquidation Statistics
|
||||
func (c *CoinankClient) LiquidationHistory(ctx context.Context, exchange coinank_enum.Exchange, symbol string,
|
||||
interval coinank_enum.Interval, endTime int64, size int) ([]LiquidationSymbol, error) {
|
||||
paramsMap := make(map[string]string, 5)
|
||||
paramsMap["exchange"] = string(exchange)
|
||||
paramsMap["symbol"] = symbol
|
||||
paramsMap["interval"] = string(interval)
|
||||
paramsMap["endTime"] = strconv.FormatInt(endTime, 10)
|
||||
paramsMap["size"] = strconv.Itoa(size)
|
||||
resp, err := c.Get(ctx, "/api/liquidation/history", paramsMap)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
var result CoinankResponse[[]LiquidationSymbol]
|
||||
err = json.Unmarshal([]byte(resp), &result)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
if !result.Success {
|
||||
return nil, HttpError
|
||||
}
|
||||
return result.Data, nil
|
||||
}
|
||||
|
||||
// LiquidationOrders Liquidation order, side:`long` or `short`,amount: order amount greater than amount
|
||||
func (c *CoinankClient) LiquidationOrders(ctx context.Context, baseCoin string, exchange coinank_enum.Exchange,
|
||||
side string, amount int, endTime int64) ([]LiquidationOrdersResponse, error) {
|
||||
paramsMap := make(map[string]string, 5)
|
||||
if baseCoin != "" {
|
||||
paramsMap["baseCoin"] = baseCoin
|
||||
}
|
||||
if exchange != "" {
|
||||
paramsMap["exchange"] = string(exchange)
|
||||
}
|
||||
if side != "" {
|
||||
paramsMap["side"] = string(side)
|
||||
}
|
||||
if amount != 0 {
|
||||
paramsMap["amount"] = strconv.Itoa(amount)
|
||||
}
|
||||
if endTime != 0 {
|
||||
paramsMap["endTime"] = strconv.FormatInt(endTime, 10)
|
||||
}
|
||||
resp, err := c.Get(ctx, "/api/liquidation/orders", paramsMap)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
var result CoinankResponse[[]LiquidationOrdersResponse]
|
||||
err = json.Unmarshal([]byte(resp), &result)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
if !result.Success {
|
||||
return nil, HttpError
|
||||
}
|
||||
return result.Data, nil
|
||||
}
|
||||
|
||||
type LiquidationOrdersResponse struct {
|
||||
ExchangeName string `json:"exchangeName"`
|
||||
BaseCoin string `json:"baseCoin"`
|
||||
ContractCode string `json:"contractCode"` //contract code
|
||||
PosSide string `json:"posSide"` // `long`: long ,`short`:short
|
||||
Amount float64 `json:"amount"` //liquidation amount
|
||||
Price float64 `json:"price"` //liquidation price
|
||||
AvgPrice float64 `json:"avgPrice"`
|
||||
TradeTurnover float64 `json:"tradeTurnover"` // liquidation turnover
|
||||
Ts int64 `json:"ts"`
|
||||
}
|
||||
|
||||
type LiquidationSymbol struct {
|
||||
Symbol string `json:"symbol"`
|
||||
ExchangeName string `json:"exchangeName"`
|
||||
Ts int64 `json:"ts"` // timestamp
|
||||
LongTurnover float64 `json:"longTurnover"` //long turnover
|
||||
ShortTurnover float64 `json:"shortTurnover"` //short turnover
|
||||
ShortAmount float64 `json:"shortAmount"` //short amount
|
||||
LongAmount float64 `json:"longAmount"` // long amount
|
||||
}
|
||||
|
||||
type LiquidationStatistic struct {
|
||||
All struct {
|
||||
LongTurnover float64 `json:"longTurnover"`
|
||||
ShortTurnover float64 `json:"shortTurnover"`
|
||||
ShortAmount float64 `json:"shortAmount"`
|
||||
LongAmount float64 `json:"longAmount"`
|
||||
} `json:"all"` //coin liquidation aggregated with all exchanges
|
||||
Ts int64 `json:"ts"` // timestamp
|
||||
}
|
||||
|
||||
type LiquidationExchangeStatisticsResponse struct {
|
||||
TopOrder struct {
|
||||
Symbol string `json:"symbol"`
|
||||
PosSide string `json:"posSide"` //side
|
||||
ExchangeName string `json:"exchangeName"` //exchangeName
|
||||
TradeTurnover float64 `json:"tradeTurnover"` //turnover
|
||||
BaseCoin string `json:"baseCoin"`
|
||||
Ts int64 `json:"ts"`
|
||||
} `json:"topOrder"` // 24 hour liquidation top order
|
||||
Total int `json:"total"` // 24 hour total liquidation number
|
||||
Two4H struct { // 24 hour liquidation data
|
||||
BaseCoin string `json:"baseCoin"`
|
||||
TotalTurnover float64 `json:"totalTurnover"`
|
||||
LongTurnover float64 `json:"longTurnover"`
|
||||
ShortTurnover float64 `json:"shortTurnover"`
|
||||
Percentage float64 `json:"percentage"`
|
||||
LongRatio float64 `json:"longRatio"`
|
||||
ShortRatio float64 `json:"shortRatio"`
|
||||
Interval string `json:"interval"`
|
||||
} `json:"24h"`
|
||||
OneH struct { // 1 hour liquidation data
|
||||
BaseCoin string `json:"baseCoin"`
|
||||
TotalTurnover float64 `json:"totalTurnover"`
|
||||
LongTurnover float64 `json:"longTurnover"`
|
||||
ShortTurnover float64 `json:"shortTurnover"`
|
||||
Percentage float64 `json:"percentage"`
|
||||
LongRatio float64 `json:"longRatio"`
|
||||
ShortRatio float64 `json:"shortRatio"`
|
||||
Interval string `json:"interval"`
|
||||
} `json:"1h"`
|
||||
}
|
||||
89
provider/coinank/liquidation_test.go
Normal file
89
provider/coinank/liquidation_test.go
Normal file
@@ -0,0 +1,89 @@
|
||||
package coinank
|
||||
|
||||
import (
|
||||
"context"
|
||||
"encoding/json"
|
||||
"nofx/provider/coinank/coinank_enum"
|
||||
"testing"
|
||||
"time"
|
||||
)
|
||||
|
||||
func TestLiquidationExchangeStatistics(t *testing.T) {
|
||||
client := NewCoinankClient(coinank_enum.MainUrl, TestApikey)
|
||||
resp, err := client.LiquidationExchangeStatistics(context.TODO(), "BTC")
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if resp.Total <= 0 {
|
||||
t.Errorf("total amount is negative")
|
||||
}
|
||||
res, err := json.Marshal(resp)
|
||||
if err != nil {
|
||||
t.Error(err)
|
||||
}
|
||||
t.Logf("%s", res)
|
||||
}
|
||||
|
||||
func TestLiquidationCoinAggHistory(t *testing.T) {
|
||||
client := NewCoinankClient(coinank_enum.MainUrl, TestApikey)
|
||||
resp, err := client.LiquidationCoinAggHistory(context.TODO(), "BTC", coinank_enum.Hour1, time.Now().UnixMilli(), 10)
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if resp[0].All.LongTurnover <= 0 {
|
||||
t.Errorf("longTurnover is negative")
|
||||
}
|
||||
res, err := json.Marshal(resp)
|
||||
if err != nil {
|
||||
t.Error(err)
|
||||
}
|
||||
t.Logf("%s", res)
|
||||
}
|
||||
|
||||
func TestLiquidationHistory(t *testing.T) {
|
||||
client := NewCoinankClient(coinank_enum.MainUrl, TestApikey)
|
||||
resp, err := client.LiquidationHistory(context.TODO(), coinank_enum.Binance, "BTCUSDT", coinank_enum.Hour1, time.Now().UnixMilli(), 10)
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if resp[0].LongTurnover <= 0 {
|
||||
t.Errorf("longTurnover is negative")
|
||||
}
|
||||
res, err := json.Marshal(resp)
|
||||
if err != nil {
|
||||
t.Error(err)
|
||||
}
|
||||
t.Logf("%s", res)
|
||||
}
|
||||
|
||||
func TestLiquidationOrders(t *testing.T) {
|
||||
client := NewCoinankClient(coinank_enum.MainUrl, TestApikey)
|
||||
resp, err := client.LiquidationOrders(context.TODO(), "BTC", coinank_enum.Binance, "long", 1000, time.Now().UnixMilli())
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
res, err := json.Marshal(resp)
|
||||
if resp[0].Price <= 0 {
|
||||
t.Errorf("price is negative")
|
||||
}
|
||||
if err != nil {
|
||||
t.Error(err)
|
||||
}
|
||||
t.Logf("%s", res)
|
||||
}
|
||||
|
||||
func TestLiquidationOrdersNoArgs(t *testing.T) {
|
||||
client := NewCoinankClient(coinank_enum.MainUrl, TestApikey)
|
||||
resp, err := client.LiquidationOrders(context.TODO(), "", "", "", 0, 0)
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
res, err := json.Marshal(resp)
|
||||
if resp[0].Price <= 0 {
|
||||
t.Errorf("price is negative")
|
||||
}
|
||||
if err != nil {
|
||||
t.Error(err)
|
||||
}
|
||||
t.Logf("%s", res)
|
||||
}
|
||||
Reference in New Issue
Block a user