github.com/frankrap/okex-api@v1.0.4/futures_api.go (about)

     1  package okex
     2  
     3  import (
     4  	"log"
     5  	"net/http"
     6  	"strings"
     7  )
     8  
     9  /*
    10   OKEX futures contract api
    11   @author Tony Tian
    12   @date 2018-03-17
    13   @version 1.0.0
    14  */
    15  
    16  /*
    17   =============================== Futures market api ===============================
    18  */
    19  /*
    20   The exchange rate of legal tender pairs
    21  */
    22  func (client *Client) GetFuturesExchangeRate() (ExchangeRate, error) {
    23  	var exchangeRate ExchangeRate
    24  	_, _, err := client.Request(GET, FUTURES_RATE, nil, &exchangeRate)
    25  	return exchangeRate, err
    26  }
    27  
    28  /*
    29    Get all of futures contract list
    30  */
    31  func (client *Client) GetFuturesInstruments() ([]FuturesInstrumentsResult, error) {
    32  	var Instruments []FuturesInstrumentsResult
    33  	_, _, err := client.Request(GET, FUTURES_INSTRUMENTS, nil, &Instruments)
    34  	return Instruments, err
    35  }
    36  
    37  /*
    38   Get the futures contract currencies
    39  */
    40  func (client *Client) GetFuturesInstrumentCurrencies() ([]FuturesInstrumentCurrenciesResult, error) {
    41  	var currencies []FuturesInstrumentCurrenciesResult
    42  	_, _, err := client.Request(GET, FUTURES_CURRENCIES, nil, &currencies)
    43  	return currencies, err
    44  }
    45  
    46  /*
    47  	获取深度数据
    48  	获取币对的深度列表。这个请求不支持分页,一个请求返回整个深度列表。
    49  
    50  	限速规则:20次/2s
    51  	HTTP请求
    52  	GET /api/futrurs/v3/instruments/<instrument_id>/book
    53  
    54  	签名请求示例
    55  	2018-09-12T07:57:09.130ZGET/api/futrurs/v3/instruments/BTC-USD-180309/book?size=10&depth=0.001
    56  
    57  */
    58  func (client *Client) GetFuturesInstrumentBook(InstrumentId string, optionalParams map[string]string) (FuturesInstrumentBookResult, error) {
    59  	var book FuturesInstrumentBookResult
    60  	params := NewParams()
    61  	if optionalParams != nil {
    62  		if v, ok := optionalParams["size"]; ok {
    63  			params["size"] = v
    64  		}
    65  		if v, ok := optionalParams["depth"]; ok {
    66  			params["depth"] = v
    67  		}
    68  	}
    69  	requestPath := BuildParams(GetInstrumentIdUri(FUTURES_INSTRUMENT_BOOK, InstrumentId), params)
    70  	_, _, err := client.Request(GET, requestPath, nil, &book)
    71  	return book, err
    72  }
    73  
    74  /*
    75   Get the futures contract Instrument all ticker
    76  */
    77  func (client *Client) GetFuturesInstrumentAllTicker() ([]FuturesInstrumentTickerResult, error) {
    78  	var tickers []FuturesInstrumentTickerResult
    79  	_, _, err := client.Request(GET, FUTURES_TICKERS, nil, &tickers)
    80  	return tickers, err
    81  }
    82  
    83  /*
    84   Get the futures contract Instrument ticker
    85  */
    86  func (client *Client) GetFuturesInstrumentTicker(InstrumentId string) (FuturesInstrumentTickerResult, error) {
    87  	var ticker FuturesInstrumentTickerResult
    88  	_, _, err := client.Request(GET, GetInstrumentIdUri(FUTURES_INSTRUMENT_TICKER, InstrumentId), nil, &ticker)
    89  	return ticker, err
    90  }
    91  
    92  /*
    93   Get the futures contract Instrument trades
    94  */
    95  func (client *Client) GetFuturesInstrumentTrades(InstrumentId string) ([]FuturesInstrumentTradesResult, error) {
    96  	var trades []FuturesInstrumentTradesResult
    97  	_, _, err := client.Request(GET, GetInstrumentIdUri(FUTURES_INSTRUMENT_TRADES, InstrumentId), nil, &trades)
    98  	return trades, err
    99  }
   100  
   101  /*
   102   Get the futures contract Instrument candles
   103   granularity: @see  file: futures_constants.go
   104  */
   105  func (client *Client) GetFuturesInstrumentCandles(InstrumentId string, optionalParams map[string]string) ([][]string, error) {
   106  	var candles [][]string
   107  	params := NewParams()
   108  
   109  	if optionalParams != nil && len(optionalParams) > 0 {
   110  		if v, ok := optionalParams["start"]; ok {
   111  			params["start"] = v
   112  		}
   113  		if v, ok := optionalParams["end"]; ok {
   114  			params["end"] = v
   115  		}
   116  		if v, ok := optionalParams["granularity"]; ok {
   117  			params["granularity"] = v
   118  		}
   119  	}
   120  	requestPath := BuildParams(GetInstrumentIdUri(FUTURES_INSTRUMENT_CANDLES, InstrumentId), params)
   121  	_, _, err := client.Request(GET, requestPath, nil, &candles)
   122  	return candles, err
   123  }
   124  
   125  /*
   126   Get the futures contract Instrument index
   127  */
   128  func (client *Client) GetFuturesInstrumentIndex(InstrumentId string) (FuturesInstrumentIndexResult, error) {
   129  	var index FuturesInstrumentIndexResult
   130  	_, _, err := client.Request(GET, GetInstrumentIdUri(FUTURES_INSTRUMENT_INDEX, InstrumentId), nil, &index)
   131  	return index, err
   132  }
   133  
   134  /*
   135   Get the futures contract Instrument estimated price
   136  */
   137  func (client *Client) GetFuturesInstrumentEstimatedPrice(InstrumentId string) (FuturesInstrumentEstimatedPriceResult, error) {
   138  	var estimatedPrice FuturesInstrumentEstimatedPriceResult
   139  	_, _, err := client.Request(GET, GetInstrumentIdUri(FUTURES_INSTRUMENT_ESTIMATED_PRICE, InstrumentId), nil, &estimatedPrice)
   140  	return estimatedPrice, err
   141  }
   142  
   143  /*
   144   Get the futures contract Instrument holds
   145  */
   146  func (client *Client) GetFuturesInstrumentOpenInterest(InstrumentId string) (FuturesInstrumentOpenInterestResult, error) {
   147  	var openInterest FuturesInstrumentOpenInterestResult
   148  	_, _, err := client.Request(GET, GetInstrumentIdUri(FUTURES_INSTRUMENT_OPEN_INTEREST, InstrumentId), nil, &openInterest)
   149  	return openInterest, err
   150  }
   151  
   152  /*
   153   Get the futures contract Instrument limit price
   154  */
   155  func (client *Client) GetFuturesInstrumentPriceLimit(InstrumentId string) (FuturesInstrumentPriceLimitResult, error) {
   156  	var priceLimit FuturesInstrumentPriceLimitResult
   157  	_, _, err := client.Request(GET, GetInstrumentIdUri(FUTURES_INSTRUMENT_PRICE_LIMIT, InstrumentId), nil, &priceLimit)
   158  	return priceLimit, err
   159  }
   160  
   161  /*
   162   Get the futures contract liquidation
   163  */
   164  func (client *Client) GetFuturesInstrumentLiquidation(InstrumentId string, status, from, to, limit int) (FuturesInstrumentLiquidationListResult, error) {
   165  	var liquidation []FuturesInstrumentLiquidationResult
   166  	params := NewParams()
   167  	params["status"] = Int2String(status)
   168  	params["from"] = Int2String(from)
   169  	params["to"] = Int2String(to)
   170  	params["limit"] = Int2String(limit)
   171  	requestPath := BuildParams(GetInstrumentIdUri(FUTURES_INSTRUMENT_LIQUIDATION, InstrumentId), params)
   172  	_, response, err := client.Request(GET, requestPath, nil, &liquidation)
   173  	var list FuturesInstrumentLiquidationListResult
   174  	page := parsePage(response)
   175  	list.Page = page
   176  	list.LiquidationList = liquidation
   177  	return list, err
   178  }
   179  
   180  /*
   181   =============================== Futures trade api ===============================
   182  */
   183  
   184  /*
   185   Get all of futures contract position list.
   186   return struct: FuturesPositions
   187  */
   188  func (client *Client) GetFuturesPositions() (FuturesPosition, error) {
   189  	_, response, err := client.Request(GET, FUTURES_POSITION, nil, nil)
   190  	return parsePositions(response, err)
   191  }
   192  
   193  /*
   194   Get all of futures contract position list.
   195   return struct: FuturesPositions
   196  */
   197  func (client *Client) GetFuturesInstrumentPosition(InstrumentId string) (FuturesPosition, error) {
   198  	_, response, err := client.Request(GET, GetInstrumentIdUri(FUTURES_INSTRUMENT_POSITION, InstrumentId), nil, nil)
   199  	return parsePositions(response, err)
   200  }
   201  
   202  /*
   203   Get all of futures contract account list
   204   return struct: FuturesAccounts
   205  */
   206  func (client *Client) GetFuturesAccounts() (GetFuturesAccountsResult, error) {
   207  	var r GetFuturesAccountsResult
   208  	_, _, err := client.Request(GET, FUTURES_ACCOUNTS, nil, &r)
   209  	//return parseAccounts(response, err)
   210  	return r, err
   211  }
   212  
   213  /*
   214   Get the futures contract currency account @see file : futures_constants.go
   215   return struct: FuturesCurrencyAccounts
   216  */
   217  func (client *Client) GetFuturesAccountsByCurrency(currency string) (result FuturesCurrencyAccount, err error) {
   218  	_, _, err = client.Request(GET, GetUnderlyingUri(FUTURES_ACCOUNT_CURRENCY_INFO, currency), nil, &result)
   219  	//return parseCurrencyAccounts(response, err)
   220  	return
   221  }
   222  
   223  /*
   224   Get the futures contract currency ledger
   225  */
   226  func (client *Client) GetFuturesAccountsLedgerByCurrency(currency string, from, to, limit int) ([]FuturesCurrencyLedger, error) {
   227  	var ledger []FuturesCurrencyLedger
   228  	params := NewParams()
   229  	params["from"] = Int2String(from)
   230  	params["to"] = Int2String(to)
   231  	params["limit"] = Int2String(limit)
   232  	requestPath := BuildParams(GetCurrencyUri(FUTURES_ACCOUNT_CURRENCY_LEDGER, currency), params)
   233  	_, _, err := client.Request(GET, requestPath, nil, &ledger)
   234  	return ledger, err
   235  }
   236  
   237  /*
   238   Get the futures contract Instrument holds
   239  */
   240  func (client *Client) GetFuturesAccountsHoldsByInstrumentId(InstrumentId string) (FuturesAccountsHolds, error) {
   241  	var holds FuturesAccountsHolds
   242  	_, _, err := client.Request(GET, GetInstrumentIdUri(FUTURES_ACCOUNT_INSTRUMENT_HOLDS, InstrumentId), nil, &holds)
   243  	return holds, err
   244  }
   245  
   246  /*
   247   Create a new order
   248  */
   249  func (client *Client) FuturesOrder(newOrderParams FuturesNewOrderParams) ([]byte, FuturesNewOrderResult, error) {
   250  	var newOrderResult FuturesNewOrderResult
   251  	var respBody []byte
   252  	respBody, _, err := client.Request(POST, FUTURES_ORDER, newOrderParams, &newOrderResult)
   253  	return respBody, newOrderResult, err
   254  }
   255  
   256  /*
   257   Batch create new order.(Max of 5 orders are allowed per request)
   258  */
   259  func (client *Client) FuturesOrders(batchNewOrder FuturesBatchNewOrderParams) ([]byte, FuturesBatchNewOrderResult, error) {
   260  	var batchNewOrderResult FuturesBatchNewOrderResult
   261  	var respBody []byte
   262  	respBody, _, err := client.Request(POST, FUTURES_ORDERS, batchNewOrder, &batchNewOrderResult)
   263  	return respBody, batchNewOrderResult, err
   264  }
   265  
   266  /*
   267   Get all of futures contract order list
   268  */
   269  func (client *Client) GetFuturesOrders(InstrumentId string, status int, after string, before string, limit int) (FuturesGetOrdersResult, error) {
   270  	var ordersResult FuturesGetOrdersResult
   271  	params := NewParams()
   272  	params["status"] = Int2String(status)
   273  	if after != "" {
   274  		params["after"] = after
   275  	}
   276  	if before != "" {
   277  		params["before"] = before
   278  	}
   279  	if limit > 0 {
   280  		params["limit"] = Int2String(limit)
   281  	}
   282  	requestPath := BuildParams(GetInstrumentIdUri(FUTURES_INSTRUMENT_ORDER_LIST, InstrumentId), params)
   283  	_, _, err := client.Request(GET, requestPath, nil, &ordersResult)
   284  	return ordersResult, err
   285  }
   286  
   287  /*
   288   Get all of futures contract a order by order id
   289  */
   290  func (client *Client) GetFuturesOrder(InstrumentId string, orderId string) (FuturesGetOrderResult, error) {
   291  	var getOrderResult FuturesGetOrderResult
   292  	_, _, err := client.Request(GET, GetInstrumentIdOrdersUri(FUTURES_INSTRUMENT_ORDER_INFO, InstrumentId, orderId), nil, &getOrderResult)
   293  	return getOrderResult, err
   294  }
   295  
   296  /*
   297   Batch Cancel the orders
   298  */
   299  func (client *Client) BatchCancelFuturesInstrumentOrders(InstrumentId, orderIds string) ([]byte, FuturesBatchCancelInstrumentOrdersResult, error) {
   300  	var cancelInstrumentOrdersResult FuturesBatchCancelInstrumentOrdersResult
   301  	params := NewParams()
   302  	params["order_ids"] = orderIds
   303  	var respBody []byte
   304  	respBody, _, err := client.Request(POST, GetInstrumentIdUri(FUTURES_INSTRUMENT_ORDER_BATCH_CANCEL, InstrumentId), params, &cancelInstrumentOrdersResult)
   305  	return respBody, cancelInstrumentOrdersResult, err
   306  }
   307  
   308  /*
   309   Cancel the order
   310  */
   311  func (client *Client) CancelFuturesInstrumentOrder(InstrumentId string, orderId string) ([]byte, FuturesCancelInstrumentOrderResult, error) {
   312  	var cancelInstrumentOrderResult FuturesCancelInstrumentOrderResult
   313  	var respBody []byte
   314  	respBody, _, err := client.Request(POST, GetInstrumentIdOrdersUri(FUTURES_INSTRUMENT_ORDER_CANCEL, InstrumentId, orderId), nil,
   315  		&cancelInstrumentOrderResult)
   316  	return respBody, cancelInstrumentOrderResult, err
   317  }
   318  
   319  /*
   320   Get all of futures contract transactions.
   321  */
   322  func (client *Client) GetFuturesFills(InstrumentId string, orderId int64, optionalParams map[string]int) ([]FuturesFillResult, error) {
   323  	var fillsResult []FuturesFillResult
   324  	params := NewParams()
   325  	params["order_id"] = Int64ToString(orderId)
   326  	params["instrument_id"] = InstrumentId
   327  
   328  	if optionalParams != nil && len(optionalParams) > 0 {
   329  		params["from"] = Int2String(optionalParams["from"])
   330  		params["to"] = Int2String(optionalParams["to"])
   331  		params["limit"] = Int2String(optionalParams["limit"])
   332  	}
   333  
   334  	requestPath := BuildParams(FUTURES_FILLS, params)
   335  	_, _, err := client.Request(GET, requestPath, nil, &fillsResult)
   336  	return fillsResult, err
   337  }
   338  
   339  /*
   340  获取标记价格
   341  获取合约标记价格。此接口为公共接口,不需要身份验证。
   342  
   343  请求示例
   344  GET/api/futures/v3/instruments/BTC-USD-180309/mark_price
   345  */
   346  func (client *Client) GetInstrumentMarkPrice(instrumentId string) (*FuturesMarkdown, error) {
   347  	uri := GetInstrumentIdUri(FUTURES_INSTRUMENT_MARK_PRICE, instrumentId)
   348  	r := FuturesMarkdown{}
   349  	_, _, err := client.Request(GET, uri, nil, &r)
   350  	return &r, err
   351  }
   352  
   353  func parsePositions(response *http.Response, err error) (FuturesPosition, error) {
   354  	var position FuturesPosition
   355  	if err != nil {
   356  		return position, err
   357  	}
   358  	var result Result
   359  	result.Result = false
   360  	jsonString := GetResponseDataJsonString(response)
   361  	if strings.Contains(jsonString, "\"margin_mode\":\"fixed\"") {
   362  		var fixedPosition FuturesFixedPosition
   363  		err = JsonString2Struct(jsonString, &fixedPosition)
   364  		if err != nil {
   365  			return position, err
   366  		} else {
   367  			position.Result = fixedPosition.Result
   368  			position.MarginMode = fixedPosition.MarginMode
   369  			position.FixedPosition = fixedPosition.FixedPosition
   370  		}
   371  	} else if strings.Contains(jsonString, "\"margin_mode\":\"crossed\"") {
   372  		var crossPosition FuturesCrossPosition
   373  		err = JsonString2Struct(jsonString, &crossPosition)
   374  		if err != nil {
   375  			return position, err
   376  		} else {
   377  			position.Result = crossPosition.Result
   378  			position.MarginMode = crossPosition.MarginMode
   379  			position.CrossPosition = crossPosition.CrossPosition
   380  		}
   381  	} else if strings.Contains(jsonString, "\"code\":") {
   382  		JsonString2Struct(jsonString, &position)
   383  		position.Result = result
   384  	} else {
   385  		position.Result = result
   386  	}
   387  
   388  	return position, nil
   389  }
   390  
   391  func parseAccounts(response *http.Response, err error) (FuturesAccount, error) {
   392  	var account FuturesAccount
   393  	if err != nil {
   394  		return account, err
   395  	}
   396  	var result Result
   397  	result.Result = false
   398  	jsonString := GetResponseDataJsonString(response)
   399  	log.Printf(jsonString)
   400  	if strings.Contains(jsonString, "\"contracts\"") {
   401  		var fixedAccount FuturesFixedAccountInfo
   402  		err = JsonString2Struct(jsonString, &fixedAccount)
   403  		if err != nil {
   404  			return account, err
   405  		} else {
   406  			account.Result = fixedAccount.Result
   407  			account.FixedAccount = fixedAccount.Info
   408  			account.MarginMode = "fixed"
   409  		}
   410  	} else if strings.Contains(jsonString, "\"realized_pnl\"") {
   411  		var crossAccount FuturesCrossAccountInfo
   412  		err = JsonString2Struct(jsonString, &crossAccount)
   413  		if err != nil {
   414  			return account, err
   415  		} else {
   416  			account.Result = crossAccount.Result
   417  			account.MarginMode = "crossed"
   418  			account.CrossAccount = crossAccount.Info
   419  		}
   420  	} else if strings.Contains(jsonString, "\"code\":") {
   421  		JsonString2Struct(jsonString, &account)
   422  		account.Result = result
   423  	} else {
   424  		account.Result = result
   425  	}
   426  	return account, nil
   427  }
   428  
   429  func parseCurrencyAccounts(response *http.Response, err error) (FuturesCurrencyAccount, error) {
   430  	var currencyAccount FuturesCurrencyAccount
   431  	if err != nil {
   432  		return currencyAccount, err
   433  	}
   434  	jsonString := GetResponseDataJsonString(response)
   435  	var result Result
   436  	result.Result = true
   437  	if strings.Contains(jsonString, "\"margin_mode\":\"fixed\"") {
   438  		var fixedAccount FuturesFixedAccount
   439  		err = JsonString2Struct(jsonString, &fixedAccount)
   440  		if err != nil {
   441  			return currencyAccount, err
   442  		} else {
   443  			//currencyAccount.Result = result
   444  			currencyAccount.MarginMode = fixedAccount.MarginMode
   445  			//currencyAccount.FixedAccount = fixedAccount
   446  		}
   447  	} else if strings.Contains(jsonString, "\"margin_mode\":\"crossed\"") {
   448  		var crossAccount FuturesCrossAccount
   449  		err = JsonString2Struct(jsonString, &crossAccount)
   450  		if err != nil {
   451  			return currencyAccount, err
   452  		} else {
   453  			//currencyAccount.Result = result
   454  			currencyAccount.MarginMode = crossAccount.MarginMode
   455  			//currencyAccount.CrossAccount = crossAccount
   456  		}
   457  	} else if strings.Contains(jsonString, "\"code\":") {
   458  		result.Result = true
   459  		JsonString2Struct(jsonString, &currencyAccount)
   460  		//currencyAccount.Result = result
   461  	} else {
   462  		result.Result = true
   463  		//currencyAccount.Result = result
   464  	}
   465  	return currencyAccount, nil
   466  }
   467  
   468  func parsePage(response *http.Response) PageResult {
   469  	var page PageResult
   470  	jsonString := GetResponsePageJsonString(response)
   471  	JsonString2Struct(jsonString, &page)
   472  	return page
   473  }
   474  
   475  /*
   476  设定合约币种杠杆倍数
   477  设定合约账户币种杠杆倍数,注意当前仓位有持仓或者挂单禁止切换杠杆。
   478  
   479  HTTP请求
   480  POST /api/futures/v3/accounts/<currency>/leverage
   481  
   482  请求示例
   483  POST/api/futures/v3/accounts/btc/leverage{"leverage":"10"}(全仓示例)
   484  POST/api/futures/v3/accounts/btc/leverage{"instrument_id":"BTC-USD-180213","direction":"long","leverage":"10"}(逐仓示例)
   485  
   486  */
   487  func (client *Client) PostFuturesAccountsLeverage(currency string, leverage int, optionalParams map[string]string) (map[string]interface{}, error) {
   488  	uri := GetUnderlyingUri(FUTURES_ACCOUNT_CURRENCY_LEVERAGE, currency)
   489  	params := NewParams()
   490  	params["leverage"] = Int2String(leverage)
   491  
   492  	if optionalParams != nil && len(optionalParams) > 0 {
   493  		params["instrument_id"] = optionalParams["instrument_id"]
   494  		params["direction"] = optionalParams["direction"]
   495  	}
   496  
   497  	r := new(map[string]interface{})
   498  	_, _, err := client.Request(POST, uri, params, r)
   499  
   500  	return *r, err
   501  }
   502  
   503  /*
   504  设置合约账户模式
   505  请求示例
   506  POST /api/futures/v3/accounts/margin_mode{"underlying":"btc-usd","margin_mode":"crossed"}
   507  */
   508  
   509  func (client *Client) PostFuturesAccountsMarginNode(underlying string, marginMode string) (map[string]interface{}, error) {
   510  	params := NewParams()
   511  	params["underlying"] = underlying
   512  	params["margin_mode"] = marginMode
   513  	r := new(map[string]interface{})
   514  	_, _, err := client.Request(POST, FUTURES_ACCOUNT_MARGIN_MODE, params, r)
   515  	return *r, err
   516  }
   517  
   518  /*
   519  获取合约账户币种杠杆倍数
   520  
   521  限速规则:5次/2s
   522  HTTP请求
   523  GET /api/futures/v3/accounts/<currency>/leverage
   524  
   525  请求示例
   526  GET/api/futures/v3/accounts/btc/leverage
   527  */
   528  func (client *Client) GetFuturesAccountsLeverage(currency string) (map[string]interface{}, error) {
   529  	uri := GetUnderlyingUri(FUTURES_ACCOUNT_CURRENCY_LEVERAGE, currency)
   530  	r := new(map[string]interface{})
   531  	_, _, err := client.Request(GET, uri, nil, r)
   532  	return *r, err
   533  }