4607 lines
204 KiB
Go
4607 lines
204 KiB
Go
package ccxt
|
|
|
|
// PLEASE DO NOT EDIT THIS FILE, IT IS GENERATED AND WILL BE OVERWRITTEN:
|
|
// https://github.com/ccxt/ccxt/blob/master/CONTRIBUTING.md#how-to-contribute-code
|
|
|
|
type bitfinex struct {
|
|
Exchange
|
|
|
|
}
|
|
|
|
func NewBitfinexCore() bitfinex {
|
|
p := bitfinex{}
|
|
setDefaults(&p)
|
|
return p
|
|
}
|
|
|
|
func (this *bitfinex) Describe() interface{} {
|
|
return this.DeepExtend(this.Exchange.Describe(), map[string]interface{} {
|
|
"id": "bitfinex",
|
|
"name": "Bitfinex",
|
|
"countries": []interface{}{"VG"},
|
|
"version": "v2",
|
|
"certified": false,
|
|
"pro": true,
|
|
"has": map[string]interface{} {
|
|
"CORS": nil,
|
|
"spot": true,
|
|
"margin": true,
|
|
"swap": true,
|
|
"future": false,
|
|
"option": false,
|
|
"addMargin": false,
|
|
"borrowCrossMargin": false,
|
|
"borrowIsolatedMargin": false,
|
|
"cancelAllOrders": true,
|
|
"cancelOrder": true,
|
|
"cancelOrders": true,
|
|
"createDepositAddress": true,
|
|
"createLimitOrder": true,
|
|
"createMarketOrder": true,
|
|
"createOrder": true,
|
|
"createPostOnlyOrder": true,
|
|
"createReduceOnlyOrder": true,
|
|
"createStopLimitOrder": true,
|
|
"createStopMarketOrder": true,
|
|
"createStopOrder": true,
|
|
"createTrailingAmountOrder": true,
|
|
"createTrailingPercentOrder": false,
|
|
"createTriggerOrder": true,
|
|
"editOrder": true,
|
|
"fetchBalance": true,
|
|
"fetchBorrowInterest": false,
|
|
"fetchBorrowRate": false,
|
|
"fetchBorrowRateHistories": false,
|
|
"fetchBorrowRateHistory": false,
|
|
"fetchBorrowRates": false,
|
|
"fetchBorrowRatesPerSymbol": false,
|
|
"fetchClosedOrder": true,
|
|
"fetchClosedOrders": true,
|
|
"fetchCrossBorrowRate": false,
|
|
"fetchCrossBorrowRates": false,
|
|
"fetchCurrencies": true,
|
|
"fetchDepositAddress": true,
|
|
"fetchDepositAddresses": false,
|
|
"fetchDepositAddressesByNetwork": false,
|
|
"fetchDepositsWithdrawals": true,
|
|
"fetchFundingHistory": false,
|
|
"fetchFundingRate": "emulated",
|
|
"fetchFundingRateHistory": true,
|
|
"fetchFundingRates": true,
|
|
"fetchIndexOHLCV": false,
|
|
"fetchIsolatedBorrowRate": false,
|
|
"fetchIsolatedBorrowRates": false,
|
|
"fetchLedger": true,
|
|
"fetchLeverage": false,
|
|
"fetchLeverageTiers": false,
|
|
"fetchLiquidations": true,
|
|
"fetchMarginMode": false,
|
|
"fetchMarketLeverageTiers": false,
|
|
"fetchMarkOHLCV": false,
|
|
"fetchMyTrades": true,
|
|
"fetchOHLCV": true,
|
|
"fetchOpenInterest": true,
|
|
"fetchOpenInterestHistory": true,
|
|
"fetchOpenInterests": true,
|
|
"fetchOpenOrder": true,
|
|
"fetchOpenOrders": true,
|
|
"fetchOrder": true,
|
|
"fetchOrderBook": true,
|
|
"fetchOrderBooks": false,
|
|
"fetchOrderTrades": true,
|
|
"fetchPosition": false,
|
|
"fetchPositionMode": false,
|
|
"fetchPositions": true,
|
|
"fetchPremiumIndexOHLCV": false,
|
|
"fetchStatus": true,
|
|
"fetchTickers": true,
|
|
"fetchTime": false,
|
|
"fetchTradingFee": false,
|
|
"fetchTradingFees": true,
|
|
"fetchTransactionFees": nil,
|
|
"fetchTransactions": "emulated",
|
|
"reduceMargin": false,
|
|
"repayCrossMargin": false,
|
|
"repayIsolatedMargin": false,
|
|
"setLeverage": false,
|
|
"setMargin": true,
|
|
"setMarginMode": false,
|
|
"setPositionMode": false,
|
|
"signIn": false,
|
|
"transfer": true,
|
|
"withdraw": true,
|
|
},
|
|
"timeframes": map[string]interface{} {
|
|
"1m": "1m",
|
|
"5m": "5m",
|
|
"15m": "15m",
|
|
"30m": "30m",
|
|
"1h": "1h",
|
|
"3h": "3h",
|
|
"4h": "4h",
|
|
"6h": "6h",
|
|
"12h": "12h",
|
|
"1d": "1D",
|
|
"1w": "7D",
|
|
"2w": "14D",
|
|
"1M": "1M",
|
|
},
|
|
"rateLimit": 250,
|
|
"urls": map[string]interface{} {
|
|
"logo": "https://github.com/user-attachments/assets/4a8e947f-ab46-481a-a8ae-8b20e9b03178",
|
|
"api": map[string]interface{} {
|
|
"v1": "https://api.bitfinex.com",
|
|
"public": "https://api-pub.bitfinex.com",
|
|
"private": "https://api.bitfinex.com",
|
|
},
|
|
"www": "https://www.bitfinex.com",
|
|
"doc": []interface{}{"https://docs.bitfinex.com/v2/docs/", "https://github.com/bitfinexcom/bitfinex-api-node"},
|
|
"fees": "https://www.bitfinex.com/fees",
|
|
},
|
|
"api": map[string]interface{} {
|
|
"public": map[string]interface{} {
|
|
"get": map[string]interface{} {
|
|
"conf/{config}": 2.7,
|
|
"conf/pub:{action}:{object}": 2.7,
|
|
"conf/pub:{action}:{object}:{detail}": 2.7,
|
|
"conf/pub:map:{object}": 2.7,
|
|
"conf/pub:map:{object}:{detail}": 2.7,
|
|
"conf/pub:map:currency:{detail}": 2.7,
|
|
"conf/pub:map:currency:sym": 2.7,
|
|
"conf/pub:map:currency:label": 2.7,
|
|
"conf/pub:map:currency:unit": 2.7,
|
|
"conf/pub:map:currency:undl": 2.7,
|
|
"conf/pub:map:currency:pool": 2.7,
|
|
"conf/pub:map:currency:explorer": 2.7,
|
|
"conf/pub:map:currency:tx:fee": 2.7,
|
|
"conf/pub:map:tx:method": 2.7,
|
|
"conf/pub:list:{object}": 2.7,
|
|
"conf/pub:list:{object}:{detail}": 2.7,
|
|
"conf/pub:list:currency": 2.7,
|
|
"conf/pub:list:pair:exchange": 2.7,
|
|
"conf/pub:list:pair:margin": 2.7,
|
|
"conf/pub:list:pair:futures": 2.7,
|
|
"conf/pub:list:competitions": 2.7,
|
|
"conf/pub:info:{object}": 2.7,
|
|
"conf/pub:info:{object}:{detail}": 2.7,
|
|
"conf/pub:info:pair": 2.7,
|
|
"conf/pub:info:pair:futures": 2.7,
|
|
"conf/pub:info:tx:status": 2.7,
|
|
"conf/pub:fees": 2.7,
|
|
"platform/status": 8,
|
|
"tickers": 2.7,
|
|
"ticker/{symbol}": 2.7,
|
|
"tickers/hist": 2.7,
|
|
"trades/{symbol}/hist": 2.7,
|
|
"book/{symbol}/{precision}": 1,
|
|
"book/{symbol}/P0": 1,
|
|
"book/{symbol}/P1": 1,
|
|
"book/{symbol}/P2": 1,
|
|
"book/{symbol}/P3": 1,
|
|
"book/{symbol}/R0": 1,
|
|
"stats1/{key}:{size}:{symbol}:{side}/{section}": 2.7,
|
|
"stats1/{key}:{size}:{symbol}:{side}/last": 2.7,
|
|
"stats1/{key}:{size}:{symbol}:{side}/hist": 2.7,
|
|
"stats1/{key}:{size}:{symbol}/{section}": 2.7,
|
|
"stats1/{key}:{size}:{symbol}/last": 2.7,
|
|
"stats1/{key}:{size}:{symbol}/hist": 2.7,
|
|
"stats1/{key}:{size}:{symbol}:long/last": 2.7,
|
|
"stats1/{key}:{size}:{symbol}:long/hist": 2.7,
|
|
"stats1/{key}:{size}:{symbol}:short/last": 2.7,
|
|
"stats1/{key}:{size}:{symbol}:short/hist": 2.7,
|
|
"candles/trade:{timeframe}:{symbol}:{period}/{section}": 2.7,
|
|
"candles/trade:{timeframe}:{symbol}/{section}": 2.7,
|
|
"candles/trade:{timeframe}:{symbol}/last": 2.7,
|
|
"candles/trade:{timeframe}:{symbol}/hist": 2.7,
|
|
"status/{type}": 2.7,
|
|
"status/deriv": 2.7,
|
|
"status/deriv/{symbol}/hist": 2.7,
|
|
"liquidations/hist": 80,
|
|
"rankings/{key}:{timeframe}:{symbol}/{section}": 2.7,
|
|
"rankings/{key}:{timeframe}:{symbol}/hist": 2.7,
|
|
"pulse/hist": 2.7,
|
|
"pulse/profile/{nickname}": 2.7,
|
|
"funding/stats/{symbol}/hist": 10,
|
|
"ext/vasps": 1,
|
|
},
|
|
"post": map[string]interface{} {
|
|
"calc/trade/avg": 2.7,
|
|
"calc/fx": 2.7,
|
|
},
|
|
},
|
|
"private": map[string]interface{} {
|
|
"post": map[string]interface{} {
|
|
"auth/r/wallets": 2.7,
|
|
"auth/r/wallets/hist": 2.7,
|
|
"auth/r/orders": 2.7,
|
|
"auth/r/orders/{symbol}": 2.7,
|
|
"auth/w/order/submit": 2.7,
|
|
"auth/w/order/update": 2.7,
|
|
"auth/w/order/cancel": 2.7,
|
|
"auth/w/order/multi": 2.7,
|
|
"auth/w/order/cancel/multi": 2.7,
|
|
"auth/r/orders/{symbol}/hist": 2.7,
|
|
"auth/r/orders/hist": 2.7,
|
|
"auth/r/order/{symbol}:{id}/trades": 2.7,
|
|
"auth/r/trades/{symbol}/hist": 2.7,
|
|
"auth/r/trades/hist": 2.7,
|
|
"auth/r/ledgers/{currency}/hist": 2.7,
|
|
"auth/r/ledgers/hist": 2.7,
|
|
"auth/r/info/margin/{key}": 2.7,
|
|
"auth/r/info/margin/base": 2.7,
|
|
"auth/r/info/margin/sym_all": 2.7,
|
|
"auth/r/positions": 2.7,
|
|
"auth/w/position/claim": 2.7,
|
|
"auth/w/position/increase:": 2.7,
|
|
"auth/r/position/increase/info": 2.7,
|
|
"auth/r/positions/hist": 2.7,
|
|
"auth/r/positions/audit": 2.7,
|
|
"auth/r/positions/snap": 2.7,
|
|
"auth/w/deriv/collateral/set": 2.7,
|
|
"auth/w/deriv/collateral/limits": 2.7,
|
|
"auth/r/funding/offers": 2.7,
|
|
"auth/r/funding/offers/{symbol}": 2.7,
|
|
"auth/w/funding/offer/submit": 2.7,
|
|
"auth/w/funding/offer/cancel": 2.7,
|
|
"auth/w/funding/offer/cancel/all": 2.7,
|
|
"auth/w/funding/close": 2.7,
|
|
"auth/w/funding/auto": 2.7,
|
|
"auth/w/funding/keep": 2.7,
|
|
"auth/r/funding/offers/{symbol}/hist": 2.7,
|
|
"auth/r/funding/offers/hist": 2.7,
|
|
"auth/r/funding/loans": 2.7,
|
|
"auth/r/funding/loans/hist": 2.7,
|
|
"auth/r/funding/loans/{symbol}": 2.7,
|
|
"auth/r/funding/loans/{symbol}/hist": 2.7,
|
|
"auth/r/funding/credits": 2.7,
|
|
"auth/r/funding/credits/hist": 2.7,
|
|
"auth/r/funding/credits/{symbol}": 2.7,
|
|
"auth/r/funding/credits/{symbol}/hist": 2.7,
|
|
"auth/r/funding/trades/{symbol}/hist": 2.7,
|
|
"auth/r/funding/trades/hist": 2.7,
|
|
"auth/r/info/funding/{key}": 2.7,
|
|
"auth/r/info/user": 2.7,
|
|
"auth/r/summary": 2.7,
|
|
"auth/r/logins/hist": 2.7,
|
|
"auth/r/permissions": 2.7,
|
|
"auth/w/token": 2.7,
|
|
"auth/r/audit/hist": 2.7,
|
|
"auth/w/transfer": 2.7,
|
|
"auth/w/deposit/address": 24,
|
|
"auth/w/deposit/invoice": 24,
|
|
"auth/w/withdraw": 24,
|
|
"auth/r/movements/{currency}/hist": 2.7,
|
|
"auth/r/movements/hist": 2.7,
|
|
"auth/r/alerts": 5.34,
|
|
"auth/w/alert/set": 2.7,
|
|
"auth/w/alert/price:{symbol}:{price}/del": 2.7,
|
|
"auth/w/alert/{type}:{symbol}:{price}/del": 2.7,
|
|
"auth/calc/order/avail": 2.7,
|
|
"auth/w/settings/set": 2.7,
|
|
"auth/r/settings": 2.7,
|
|
"auth/w/settings/del": 2.7,
|
|
"auth/r/pulse/hist": 2.7,
|
|
"auth/w/pulse/add": 16,
|
|
"auth/w/pulse/del": 2.7,
|
|
},
|
|
},
|
|
},
|
|
"fees": map[string]interface{} {
|
|
"trading": map[string]interface{} {
|
|
"feeSide": "get",
|
|
"percentage": true,
|
|
"tierBased": true,
|
|
"maker": this.ParseNumber("0.001"),
|
|
"taker": this.ParseNumber("0.002"),
|
|
"tiers": map[string]interface{} {
|
|
"taker": []interface{}{[]interface{}{this.ParseNumber("0"), this.ParseNumber("0.002")}, []interface{}{this.ParseNumber("500000"), this.ParseNumber("0.002")}, []interface{}{this.ParseNumber("1000000"), this.ParseNumber("0.002")}, []interface{}{this.ParseNumber("2500000"), this.ParseNumber("0.002")}, []interface{}{this.ParseNumber("5000000"), this.ParseNumber("0.002")}, []interface{}{this.ParseNumber("7500000"), this.ParseNumber("0.002")}, []interface{}{this.ParseNumber("10000000"), this.ParseNumber("0.0018")}, []interface{}{this.ParseNumber("15000000"), this.ParseNumber("0.0016")}, []interface{}{this.ParseNumber("20000000"), this.ParseNumber("0.0014")}, []interface{}{this.ParseNumber("25000000"), this.ParseNumber("0.0012")}, []interface{}{this.ParseNumber("30000000"), this.ParseNumber("0.001")}},
|
|
"maker": []interface{}{[]interface{}{this.ParseNumber("0"), this.ParseNumber("0.001")}, []interface{}{this.ParseNumber("500000"), this.ParseNumber("0.0008")}, []interface{}{this.ParseNumber("1000000"), this.ParseNumber("0.0006")}, []interface{}{this.ParseNumber("2500000"), this.ParseNumber("0.0004")}, []interface{}{this.ParseNumber("5000000"), this.ParseNumber("0.0002")}, []interface{}{this.ParseNumber("7500000"), this.ParseNumber("0")}, []interface{}{this.ParseNumber("10000000"), this.ParseNumber("0")}, []interface{}{this.ParseNumber("15000000"), this.ParseNumber("0")}, []interface{}{this.ParseNumber("20000000"), this.ParseNumber("0")}, []interface{}{this.ParseNumber("25000000"), this.ParseNumber("0")}, []interface{}{this.ParseNumber("30000000"), this.ParseNumber("0")}},
|
|
},
|
|
},
|
|
"funding": map[string]interface{} {
|
|
"withdraw": map[string]interface{} {},
|
|
},
|
|
},
|
|
"precisionMode": SIGNIFICANT_DIGITS,
|
|
"options": map[string]interface{} {
|
|
"precision": "R0",
|
|
"exchangeTypes": map[string]interface{} {
|
|
"MARKET": "market",
|
|
"EXCHANGE MARKET": "market",
|
|
"LIMIT": "limit",
|
|
"EXCHANGE LIMIT": "limit",
|
|
"EXCHANGE STOP": "market",
|
|
"EXCHANGE FOK": "limit",
|
|
"EXCHANGE STOP LIMIT": "limit",
|
|
"EXCHANGE IOC": "limit",
|
|
},
|
|
"orderTypes": map[string]interface{} {
|
|
"market": "EXCHANGE MARKET",
|
|
"limit": "EXCHANGE LIMIT",
|
|
},
|
|
"fiat": map[string]interface{} {
|
|
"USD": "USD",
|
|
"EUR": "EUR",
|
|
"JPY": "JPY",
|
|
"GBP": "GBP",
|
|
"CHN": "CHN",
|
|
},
|
|
"v2AccountsByType": map[string]interface{} {
|
|
"spot": "exchange",
|
|
"exchange": "exchange",
|
|
"funding": "funding",
|
|
"margin": "margin",
|
|
"derivatives": "margin",
|
|
"future": "margin",
|
|
"swap": "margin",
|
|
},
|
|
"withdraw": map[string]interface{} {
|
|
"includeFee": false,
|
|
},
|
|
"networks": map[string]interface{} {
|
|
"BTC": "BITCOIN",
|
|
"LTC": "LITECOIN",
|
|
"ERC20": "ETHEREUM",
|
|
"OMNI": "TETHERUSO",
|
|
"LIQUID": "TETHERUSL",
|
|
"TRC20": "TETHERUSX",
|
|
"EOS": "TETHERUSS",
|
|
"AVAX": "TETHERUSDTAVAX",
|
|
"SOL": "TETHERUSDTSOL",
|
|
"ALGO": "TETHERUSDTALG",
|
|
"BCH": "TETHERUSDTBCH",
|
|
"KSM": "TETHERUSDTKSM",
|
|
"DVF": "TETHERUSDTDVF",
|
|
"OMG": "TETHERUSDTOMG",
|
|
},
|
|
"networksById": map[string]interface{} {
|
|
"TETHERUSE": "ERC20",
|
|
},
|
|
},
|
|
"features": map[string]interface{} {
|
|
"default": map[string]interface{} {
|
|
"sandbox": false,
|
|
"createOrder": map[string]interface{} {
|
|
"marginMode": true,
|
|
"triggerPrice": true,
|
|
"triggerPriceType": nil,
|
|
"triggerDirection": false,
|
|
"stopLossPrice": true,
|
|
"takeProfitPrice": true,
|
|
"attachedStopLossTakeProfit": nil,
|
|
"timeInForce": map[string]interface{} {
|
|
"IOC": true,
|
|
"FOK": true,
|
|
"PO": true,
|
|
"GTD": false,
|
|
},
|
|
"hedged": false,
|
|
"trailing": true,
|
|
"leverage": true,
|
|
"marketBuyRequiresPrice": false,
|
|
"marketBuyByCost": true,
|
|
"selfTradePrevention": false,
|
|
"iceberg": false,
|
|
},
|
|
"createOrders": map[string]interface{} {
|
|
"max": 75,
|
|
},
|
|
"fetchMyTrades": map[string]interface{} {
|
|
"marginMode": false,
|
|
"limit": 2500,
|
|
"daysBack": nil,
|
|
"untilDays": 100000,
|
|
"symbolRequired": false,
|
|
},
|
|
"fetchOrder": map[string]interface{} {
|
|
"marginMode": false,
|
|
"trigger": false,
|
|
"trailing": false,
|
|
"symbolRequired": false,
|
|
},
|
|
"fetchOpenOrders": map[string]interface{} {
|
|
"marginMode": false,
|
|
"limit": nil,
|
|
"trigger": false,
|
|
"trailing": false,
|
|
"symbolRequired": false,
|
|
},
|
|
"fetchOrders": nil,
|
|
"fetchClosedOrders": map[string]interface{} {
|
|
"marginMode": false,
|
|
"limit": nil,
|
|
"daysBack": nil,
|
|
"daysBackCanceled": nil,
|
|
"untilDays": 100000,
|
|
"trigger": false,
|
|
"trailing": false,
|
|
"symbolRequired": false,
|
|
},
|
|
"fetchOHLCV": map[string]interface{} {
|
|
"limit": 10000,
|
|
},
|
|
},
|
|
"spot": map[string]interface{} {
|
|
"extends": "default",
|
|
},
|
|
"swap": map[string]interface{} {
|
|
"linear": map[string]interface{} {
|
|
"extends": "default",
|
|
},
|
|
"inverse": nil,
|
|
},
|
|
"future": map[string]interface{} {
|
|
"linear": nil,
|
|
"inverse": nil,
|
|
},
|
|
},
|
|
"exceptions": map[string]interface{} {
|
|
"exact": map[string]interface{} {
|
|
"11010": RateLimitExceeded,
|
|
"10001": PermissionDenied,
|
|
"10020": BadRequest,
|
|
"10100": AuthenticationError,
|
|
"10114": InvalidNonce,
|
|
"20060": OnMaintenance,
|
|
"temporarily_unavailable": ExchangeNotAvailable,
|
|
},
|
|
"broad": map[string]interface{} {
|
|
"available balance is only": InsufficientFunds,
|
|
"not enough exchange balance": InsufficientFunds,
|
|
"Order not found": OrderNotFound,
|
|
"symbol: invalid": BadSymbol,
|
|
},
|
|
},
|
|
"commonCurrencies": map[string]interface{} {
|
|
"UST": "USDT",
|
|
"EUTF0": "EURT",
|
|
"USTF0": "USDT",
|
|
"ALG": "ALGO",
|
|
"AMP": "AMPL",
|
|
"ATO": "ATOM",
|
|
"BCHABC": "XEC",
|
|
"BCHN": "BCH",
|
|
"DAT": "DATA",
|
|
"DOG": "MDOGE",
|
|
"DSH": "DASH",
|
|
"EDO": "PNT",
|
|
"EUS": "EURS",
|
|
"EUT": "EURT",
|
|
"HTX": "HT",
|
|
"IDX": "ID",
|
|
"IOT": "IOTA",
|
|
"IQX": "IQ",
|
|
"LUNA": "LUNC",
|
|
"LUNA2": "LUNA",
|
|
"MNA": "MANA",
|
|
"ORS": "ORS Group",
|
|
"PAS": "PASS",
|
|
"QSH": "QASH",
|
|
"QTM": "QTUM",
|
|
"RBT": "RBTC",
|
|
"SNG": "SNGLS",
|
|
"STJ": "STORJ",
|
|
"TERRAUST": "USTC",
|
|
"TSD": "TUSD",
|
|
"YGG": "YEED",
|
|
"YYW": "YOYOW",
|
|
"UDC": "USDC",
|
|
"VSY": "VSYS",
|
|
"WAX": "WAXP",
|
|
"XCH": "XCHF",
|
|
"ZBT": "ZB",
|
|
},
|
|
})
|
|
}
|
|
func (this *bitfinex) IsFiat(code interface{}) interface{} {
|
|
return (InOp(GetValue(this.Options, "fiat"), code))
|
|
}
|
|
func (this *bitfinex) GetCurrencyId(code interface{}) interface{} {
|
|
return Add("f", code)
|
|
}
|
|
func (this *bitfinex) GetCurrencyName(code interface{}) interface{} {
|
|
// temporary fix for transpiler recognition, even though this is in parent class
|
|
if IsTrue(InOp(GetValue(this.Options, "currencyNames"), code)) {
|
|
return GetValue(GetValue(this.Options, "currencyNames"), code)
|
|
}
|
|
panic(NotSupported(Add(Add(Add(this.Id, " "), code), " not supported for withdrawal")))
|
|
}
|
|
func (this *bitfinex) AmountToPrecision(symbol interface{}, amount interface{}) interface{} {
|
|
// https://docs.bitfinex.com/docs/introduction#amount-precision
|
|
// The amount field allows up to 8 decimals.
|
|
// Anything exceeding this will be rounded to the 8th decimal.
|
|
symbol = this.SafeSymbol(symbol)
|
|
return this.DecimalToPrecision(amount, TRUNCATE, GetValue(GetValue(GetValue(this.Markets, symbol), "precision"), "amount"), DECIMAL_PLACES)
|
|
}
|
|
func (this *bitfinex) PriceToPrecision(symbol interface{}, price interface{}) interface{} {
|
|
symbol = this.SafeSymbol(symbol)
|
|
price = this.DecimalToPrecision(price, ROUND, GetValue(GetValue(GetValue(this.Markets, symbol), "precision"), "price"), this.PrecisionMode)
|
|
// https://docs.bitfinex.com/docs/introduction#price-precision
|
|
// The precision level of all trading prices is based on significant figures.
|
|
// All pairs on Bitfinex use up to 5 significant digits and up to 8 decimals (e.g. 1.2345, 123.45, 1234.5, 0.00012345).
|
|
// Prices submit with a precision larger than 5 will be cut by the API.
|
|
return this.DecimalToPrecision(price, TRUNCATE, 8, DECIMAL_PLACES)
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitfinex#fetchStatus
|
|
* @description the latest known information on the availability of the exchange API
|
|
* @see https://docs.bitfinex.com/reference/rest-public-platform-status
|
|
* @param {object} [params] extra parameters specific to the exchange API endpoint
|
|
* @returns {object} a [status structure]{@link https://docs.ccxt.com/#/?id=exchange-status-structure}
|
|
*/
|
|
func (this *bitfinex) FetchStatus(optionalArgs ...interface{}) <- chan interface{} {
|
|
ch := make(chan interface{})
|
|
go func() interface{} {
|
|
defer close(ch)
|
|
defer ReturnPanicError(ch)
|
|
//
|
|
// [1] // operative
|
|
// [0] // maintenance
|
|
//
|
|
params := GetArg(optionalArgs, 0, map[string]interface{} {})
|
|
_ = params
|
|
|
|
response:= (<-this.PublicGetPlatformStatus(params))
|
|
PanicOnError(response)
|
|
var statusRaw interface{} = this.SafeString(response, 0)
|
|
|
|
ch <- map[string]interface{} {
|
|
"status": this.SafeString(map[string]interface{} {
|
|
"0": "maintenance",
|
|
"1": "ok",
|
|
}, statusRaw, statusRaw),
|
|
"updated": nil,
|
|
"eta": nil,
|
|
"url": nil,
|
|
"info": response,
|
|
}
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitfinex#fetchMarkets
|
|
* @description retrieves data on all markets for bitfinex
|
|
* @see https://docs.bitfinex.com/reference/rest-public-conf
|
|
* @param {object} [params] extra parameters specific to the exchange API endpoint
|
|
* @returns {object[]} an array of objects representing market data
|
|
*/
|
|
func (this *bitfinex) FetchMarkets(optionalArgs ...interface{}) <- chan interface{} {
|
|
ch := make(chan interface{})
|
|
go func() interface{} {
|
|
defer close(ch)
|
|
defer ReturnPanicError(ch)
|
|
params := GetArg(optionalArgs, 0, map[string]interface{} {})
|
|
_ = params
|
|
var spotMarketsInfoPromise interface{} = this.PublicGetConfPubInfoPair(params)
|
|
var futuresMarketsInfoPromise interface{} = this.PublicGetConfPubInfoPairFutures(params)
|
|
var marginIdsPromise interface{} = this.PublicGetConfPubListPairMargin(params)
|
|
spotMarketsInfofuturesMarketsInfomarginIdsVariable := (<-promiseAll([]interface{}{spotMarketsInfoPromise, futuresMarketsInfoPromise, marginIdsPromise}));
|
|
spotMarketsInfo := GetValue(spotMarketsInfofuturesMarketsInfomarginIdsVariable,0);
|
|
futuresMarketsInfo := GetValue(spotMarketsInfofuturesMarketsInfomarginIdsVariable,1);
|
|
marginIds := GetValue(spotMarketsInfofuturesMarketsInfomarginIdsVariable,2)
|
|
spotMarketsInfo = this.SafeList(spotMarketsInfo, 0, []interface{}{})
|
|
futuresMarketsInfo = this.SafeList(futuresMarketsInfo, 0, []interface{}{})
|
|
var markets interface{} = this.ArrayConcat(spotMarketsInfo, futuresMarketsInfo)
|
|
marginIds = this.SafeValue(marginIds, 0, []interface{}{})
|
|
//
|
|
// [
|
|
// "1INCH:USD",
|
|
// [
|
|
// null,
|
|
// null,
|
|
// null,
|
|
// "2.0",
|
|
// "100000.0",
|
|
// null,
|
|
// null,
|
|
// null,
|
|
// null,
|
|
// null,
|
|
// null,
|
|
// null
|
|
// ]
|
|
// ]
|
|
//
|
|
var result interface{} = []interface{}{}
|
|
for i := 0; IsLessThan(i, GetArrayLength(markets)); i++ {
|
|
var pair interface{} = GetValue(markets, i)
|
|
var id interface{} = this.SafeStringUpper(pair, 0)
|
|
var market interface{} = this.SafeValue(pair, 1, map[string]interface{} {})
|
|
var spot interface{} = true
|
|
if IsTrue(IsGreaterThanOrEqual(GetIndexOf(id, "F0"), 0)) {
|
|
spot = false
|
|
}
|
|
var swap interface{} = !IsTrue(spot)
|
|
var baseId interface{} = nil
|
|
var quoteId interface{} = nil
|
|
if IsTrue(IsGreaterThanOrEqual(GetIndexOf(id, ":"), 0)) {
|
|
var parts interface{} = Split(id, ":")
|
|
baseId = GetValue(parts, 0)
|
|
quoteId = GetValue(parts, 1)
|
|
} else {
|
|
baseId = Slice(id, 0, 3)
|
|
quoteId = Slice(id, 3, 6)
|
|
}
|
|
var base interface{} = this.SafeCurrencyCode(baseId)
|
|
var quote interface{} = this.SafeCurrencyCode(quoteId)
|
|
var splitBase interface{} = Split(base, "F0")
|
|
var splitQuote interface{} = Split(quote, "F0")
|
|
base = this.SafeString(splitBase, 0)
|
|
quote = this.SafeString(splitQuote, 0)
|
|
var symbol interface{} = Add(Add(base, "/"), quote)
|
|
baseId = this.GetCurrencyId(baseId)
|
|
quoteId = this.GetCurrencyId(quoteId)
|
|
var settle interface{} = nil
|
|
var settleId interface{} = nil
|
|
if IsTrue(swap) {
|
|
settle = quote
|
|
settleId = quote
|
|
symbol = Add(Add(symbol, ":"), settle)
|
|
}
|
|
var minOrderSizeString interface{} = this.SafeString(market, 3)
|
|
var maxOrderSizeString interface{} = this.SafeString(market, 4)
|
|
var margin interface{} = false
|
|
if IsTrue(IsTrue(spot) && IsTrue(this.InArray(id, marginIds))) {
|
|
margin = true
|
|
}
|
|
AppendToArray(&result,map[string]interface{} {
|
|
"id": Add("t", id),
|
|
"symbol": symbol,
|
|
"base": base,
|
|
"quote": quote,
|
|
"settle": settle,
|
|
"baseId": baseId,
|
|
"quoteId": quoteId,
|
|
"settleId": settleId,
|
|
"type": Ternary(IsTrue(spot), "spot", "swap"),
|
|
"spot": spot,
|
|
"margin": margin,
|
|
"swap": swap,
|
|
"future": false,
|
|
"option": false,
|
|
"active": true,
|
|
"contract": swap,
|
|
"linear": Ternary(IsTrue(swap), true, nil),
|
|
"inverse": Ternary(IsTrue(swap), false, nil),
|
|
"contractSize": Ternary(IsTrue(swap), this.ParseNumber("1"), nil),
|
|
"expiry": nil,
|
|
"expiryDatetime": nil,
|
|
"strike": nil,
|
|
"optionType": nil,
|
|
"precision": map[string]interface{} {
|
|
"amount": ParseInt("8"),
|
|
"price": ParseInt("5"),
|
|
},
|
|
"limits": map[string]interface{} {
|
|
"leverage": map[string]interface{} {
|
|
"min": nil,
|
|
"max": nil,
|
|
},
|
|
"amount": map[string]interface{} {
|
|
"min": this.ParseNumber(minOrderSizeString),
|
|
"max": this.ParseNumber(maxOrderSizeString),
|
|
},
|
|
"price": map[string]interface{} {
|
|
"min": this.ParseNumber("1e-8"),
|
|
"max": nil,
|
|
},
|
|
"cost": map[string]interface{} {
|
|
"min": nil,
|
|
"max": nil,
|
|
},
|
|
},
|
|
"created": nil,
|
|
"info": market,
|
|
})
|
|
}
|
|
|
|
ch <- result
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitfinex#fetchCurrencies
|
|
* @description fetches all available currencies on an exchange
|
|
* @see https://docs.bitfinex.com/reference/rest-public-conf
|
|
* @param {object} [params] extra parameters specific to the exchange API endpoint
|
|
* @returns {object} an associative dictionary of currencies
|
|
*/
|
|
func (this *bitfinex) FetchCurrencies(optionalArgs ...interface{}) <- chan interface{} {
|
|
ch := make(chan interface{})
|
|
go func() interface{} {
|
|
defer close(ch)
|
|
defer ReturnPanicError(ch)
|
|
params := GetArg(optionalArgs, 0, map[string]interface{} {})
|
|
_ = params
|
|
var labels interface{} = []interface{}{"pub:list:currency", "pub:map:currency:sym", "pub:map:currency:label", "pub:map:currency:unit", "pub:map:currency:undl", "pub:map:currency:pool", "pub:map:currency:explorer", "pub:map:currency:tx:fee", "pub:map:tx:method"}
|
|
var config interface{} = Join(labels, ",")
|
|
var request interface{} = map[string]interface{} {
|
|
"config": config,
|
|
}
|
|
|
|
response:= (<-this.PublicGetConfConfig(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
//
|
|
// [
|
|
//
|
|
// a list of symbols
|
|
// ["AAA","ABS","ADA"],
|
|
//
|
|
// // sym
|
|
// // maps symbols to their API symbols, BAB > BCH
|
|
// [
|
|
// [ "BAB", "BCH" ],
|
|
// [ "CNHT", "CNHt" ],
|
|
// [ "DSH", "DASH" ],
|
|
// [ "IOT", "IOTA" ],
|
|
// [ "LES", "LEO-EOS" ],
|
|
// [ "LET", "LEO-ERC20" ],
|
|
// [ "STJ", "STORJ" ],
|
|
// [ "TSD", "TUSD" ],
|
|
// [ "UDC", "USDC" ],
|
|
// [ "USK", "USDK" ],
|
|
// [ "UST", "USDt" ],
|
|
// [ "USTF0", "USDt0" ],
|
|
// [ "XCH", "XCHF" ],
|
|
// [ "YYW", "YOYOW" ],
|
|
// // ...
|
|
// ],
|
|
// // label
|
|
// // verbose friendly names, BNT > Bancor
|
|
// [
|
|
// [ "BAB", "Bitcoin Cash" ],
|
|
// [ "BCH", "Bitcoin Cash" ],
|
|
// [ "LEO", "Unus Sed LEO" ],
|
|
// [ "LES", "Unus Sed LEO (EOS)" ],
|
|
// [ "LET", "Unus Sed LEO (ERC20)" ],
|
|
// // ...
|
|
// ],
|
|
// // unit
|
|
// // maps symbols to unit of measure where applicable
|
|
// [
|
|
// [ "IOT", "Mi|MegaIOTA" ],
|
|
// ],
|
|
// // undl
|
|
// // maps derivatives symbols to their underlying currency
|
|
// [
|
|
// [ "USTF0", "UST" ],
|
|
// [ "BTCF0", "BTC" ],
|
|
// [ "ETHF0", "ETH" ],
|
|
// ],
|
|
// // pool
|
|
// // maps symbols to underlying network/protocol they operate on
|
|
// [
|
|
// [ 'SAN', 'ETH' ], [ 'OMG', 'ETH' ], [ 'AVT', 'ETH' ], [ "EDO", "ETH" ],
|
|
// [ 'ESS', 'ETH' ], [ 'ATD', 'EOS' ], [ 'ADD', 'EOS' ], [ "MTO", "EOS" ],
|
|
// [ 'PNK', 'ETH' ], [ 'BAB', 'BCH' ], [ 'WLO', 'XLM' ], [ "VLD", "ETH" ],
|
|
// [ 'BTT', 'TRX' ], [ 'IMP', 'ETH' ], [ 'SCR', 'ETH' ], [ "GNO", "ETH" ],
|
|
// // ...
|
|
// ],
|
|
// // explorer
|
|
// // maps symbols to their recognised block explorer URLs
|
|
// [
|
|
// [
|
|
// "AIO",
|
|
// [
|
|
// "https://mainnet.aion.network",
|
|
// "https://mainnet.aion.network/#/account/VAL",
|
|
// "https://mainnet.aion.network/#/transaction/VAL"
|
|
// ]
|
|
// ],
|
|
// // ...
|
|
// ],
|
|
// // fee
|
|
// // maps currencies to their withdrawal fees
|
|
// [
|
|
// ["AAA",[0,0]],
|
|
// ["ABS",[0,131.3]],
|
|
// ["ADA",[0,0.3]],
|
|
// ],
|
|
// ]
|
|
//
|
|
var indexed interface{} = map[string]interface{} {
|
|
"sym": this.IndexBy(this.SafeValue(response, 1, []interface{}{}), 0),
|
|
"label": this.IndexBy(this.SafeValue(response, 2, []interface{}{}), 0),
|
|
"unit": this.IndexBy(this.SafeValue(response, 3, []interface{}{}), 0),
|
|
"undl": this.IndexBy(this.SafeValue(response, 4, []interface{}{}), 0),
|
|
"pool": this.IndexBy(this.SafeValue(response, 5, []interface{}{}), 0),
|
|
"explorer": this.IndexBy(this.SafeValue(response, 6, []interface{}{}), 0),
|
|
"fees": this.IndexBy(this.SafeValue(response, 7, []interface{}{}), 0),
|
|
}
|
|
var ids interface{} = this.SafeValue(response, 0, []interface{}{})
|
|
var result interface{} = map[string]interface{} {}
|
|
for i := 0; IsLessThan(i, GetArrayLength(ids)); i++ {
|
|
var id interface{} = GetValue(ids, i)
|
|
if IsTrue(IsGreaterThanOrEqual(GetIndexOf(id, "F0"), 0)) {
|
|
continue
|
|
}
|
|
var code interface{} = this.SafeCurrencyCode(id)
|
|
var label interface{} = this.SafeValue(GetValue(indexed, "label"), id, []interface{}{})
|
|
var name interface{} = this.SafeString(label, 1)
|
|
var pool interface{} = this.SafeValue(GetValue(indexed, "pool"), id, []interface{}{})
|
|
var rawType interface{} = this.SafeString(pool, 1)
|
|
var isCryptoCoin interface{} = IsTrue((!IsEqual(rawType, nil))) || IsTrue((InOp(GetValue(indexed, "explorer"), id))) // "hacky" solution
|
|
var typeVar interface{} = nil
|
|
if IsTrue(isCryptoCoin) {
|
|
typeVar = "crypto"
|
|
}
|
|
var feeValues interface{} = this.SafeValue(GetValue(indexed, "fees"), id, []interface{}{})
|
|
var fees interface{} = this.SafeValue(feeValues, 1, []interface{}{})
|
|
var fee interface{} = this.SafeNumber(fees, 1)
|
|
var undl interface{} = this.SafeValue(GetValue(indexed, "undl"), id, []interface{}{})
|
|
var precision interface{} = "8" // default precision, todo: fix "magic constants"
|
|
var fid interface{} = Add("f", id)
|
|
AddElementToObject(result, code, map[string]interface{} {
|
|
"id": fid,
|
|
"uppercaseId": id,
|
|
"code": code,
|
|
"info": []interface{}{id, label, pool, feeValues, undl},
|
|
"type": typeVar,
|
|
"name": name,
|
|
"active": true,
|
|
"deposit": nil,
|
|
"withdraw": nil,
|
|
"fee": fee,
|
|
"precision": ParseInt(precision),
|
|
"limits": map[string]interface{} {
|
|
"amount": map[string]interface{} {
|
|
"min": this.ParseNumber(this.ParsePrecision(precision)),
|
|
"max": nil,
|
|
},
|
|
"withdraw": map[string]interface{} {
|
|
"min": fee,
|
|
"max": nil,
|
|
},
|
|
},
|
|
"networks": map[string]interface{} {},
|
|
})
|
|
var networks interface{} = map[string]interface{} {}
|
|
var currencyNetworks interface{} = this.SafeValue(response, 8, []interface{}{})
|
|
var cleanId interface{} = Replace(id, "F0", "")
|
|
for j := 0; IsLessThan(j, GetArrayLength(currencyNetworks)); j++ {
|
|
var pair interface{} = GetValue(currencyNetworks, j)
|
|
var networkId interface{} = this.SafeString(pair, 0)
|
|
var currencyId interface{} = this.SafeString(this.SafeValue(pair, 1, []interface{}{}), 0)
|
|
if IsTrue(IsEqual(currencyId, cleanId)) {
|
|
var network interface{} = this.NetworkIdToCode(networkId)
|
|
AddElementToObject(networks, network, map[string]interface{} {
|
|
"info": networkId,
|
|
"id": ToLower(networkId),
|
|
"network": networkId,
|
|
"active": nil,
|
|
"deposit": nil,
|
|
"withdraw": nil,
|
|
"fee": nil,
|
|
"precision": nil,
|
|
"limits": map[string]interface{} {
|
|
"withdraw": map[string]interface{} {
|
|
"min": nil,
|
|
"max": nil,
|
|
},
|
|
},
|
|
})
|
|
}
|
|
}
|
|
var keysNetworks interface{} = ObjectKeys(networks)
|
|
var networksLength interface{} = GetArrayLength(keysNetworks)
|
|
if IsTrue(IsGreaterThan(networksLength, 0)) {
|
|
AddElementToObject(GetValue(result, code), "networks", networks)
|
|
}
|
|
}
|
|
|
|
ch <- result
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitfinex#fetchBalance
|
|
* @description query for balance and get the amount of funds available for trading or funds locked in orders
|
|
* @see https://docs.bitfinex.com/reference/rest-auth-wallets
|
|
* @param {object} [params] extra parameters specific to the exchange API endpoint
|
|
* @returns {object} a [balance structure]{@link https://docs.ccxt.com/#/?id=balance-structure}
|
|
*/
|
|
func (this *bitfinex) FetchBalance(optionalArgs ...interface{}) <- chan interface{} {
|
|
ch := make(chan interface{})
|
|
go func() interface{} {
|
|
defer close(ch)
|
|
defer ReturnPanicError(ch)
|
|
// this api call does not return the 'used' amount - use the v1 version instead (which also returns zero balances)
|
|
// there is a difference between this and the v1 api, namely trading wallet is called margin in v2
|
|
params := GetArg(optionalArgs, 0, map[string]interface{} {})
|
|
_ = params
|
|
|
|
retRes9378 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes9378)
|
|
var accountsByType interface{} = this.SafeValue(this.Options, "v2AccountsByType", map[string]interface{} {})
|
|
var requestedType interface{} = this.SafeString(params, "type", "exchange")
|
|
var accountType interface{} = this.SafeString(accountsByType, requestedType, requestedType)
|
|
if IsTrue(IsEqual(accountType, nil)) {
|
|
var keys interface{} = ObjectKeys(accountsByType)
|
|
panic(ExchangeError(Add(Add(this.Id, " fetchBalance() type parameter must be one of "), Join(keys, ", "))))
|
|
}
|
|
var isDerivative interface{} = IsEqual(requestedType, "derivatives")
|
|
var query interface{} = this.Omit(params, "type")
|
|
|
|
response:= (<-this.PrivatePostAuthRWallets(query))
|
|
PanicOnError(response)
|
|
var result interface{} = map[string]interface{} {
|
|
"info": response,
|
|
}
|
|
for i := 0; IsLessThan(i, GetArrayLength(response)); i++ {
|
|
var balance interface{} = GetValue(response, i)
|
|
var account interface{} = this.Account()
|
|
var interest interface{} = this.SafeString(balance, 3)
|
|
if IsTrue(!IsEqual(interest, "0")) {
|
|
AddElementToObject(account, "debt", interest)
|
|
}
|
|
var typeVar interface{} = this.SafeString(balance, 0)
|
|
var currencyId interface{} = this.SafeStringLower(balance, 1, "")
|
|
var start interface{} = Subtract(GetLength(currencyId), 2)
|
|
var isDerivativeCode interface{} = IsEqual(Slice(currencyId, start, nil), "f0")
|
|
// this will only filter the derivative codes if the requestedType is 'derivatives'
|
|
var derivativeCondition interface{} = (!IsTrue(isDerivative) || IsTrue(isDerivativeCode))
|
|
if IsTrue(IsTrue((IsEqual(accountType, typeVar))) && IsTrue(derivativeCondition)) {
|
|
var code interface{} = this.SafeCurrencyCode(currencyId)
|
|
AddElementToObject(account, "total", this.SafeString(balance, 2))
|
|
AddElementToObject(account, "free", this.SafeString(balance, 4))
|
|
AddElementToObject(result, code, account)
|
|
}
|
|
}
|
|
|
|
ch <- this.SafeBalance(result)
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitfinex#transfer
|
|
* @description transfer currency internally between wallets on the same account
|
|
* @see https://docs.bitfinex.com/reference/rest-auth-transfer
|
|
* @param {string} code unified currency code
|
|
* @param {float} amount amount to transfer
|
|
* @param {string} fromAccount account to transfer from
|
|
* @param {string} toAccount account to transfer to
|
|
* @param {object} [params] extra parameters specific to the exchange API endpoint
|
|
* @returns {object} a [transfer structure]{@link https://docs.ccxt.com/#/?id=transfer-structure}
|
|
*/
|
|
func (this *bitfinex) Transfer(code interface{}, amount interface{}, fromAccount interface{}, toAccount interface{}, optionalArgs ...interface{}) <- chan interface{} {
|
|
ch := make(chan interface{})
|
|
go func() interface{} {
|
|
defer close(ch)
|
|
defer ReturnPanicError(ch)
|
|
// transferring between derivatives wallet and regular wallet is not documented in their API
|
|
// however we support it in CCXT (from just looking at web inspector)
|
|
params := GetArg(optionalArgs, 0, map[string]interface{} {})
|
|
_ = params
|
|
|
|
retRes9878 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes9878)
|
|
var accountsByType interface{} = this.SafeValue(this.Options, "v2AccountsByType", map[string]interface{} {})
|
|
var fromId interface{} = this.SafeString(accountsByType, fromAccount)
|
|
if IsTrue(IsEqual(fromId, nil)) {
|
|
var keys interface{} = ObjectKeys(accountsByType)
|
|
panic(ArgumentsRequired(Add(Add(this.Id, " transfer() fromAccount must be one of "), Join(keys, ", "))))
|
|
}
|
|
var toId interface{} = this.SafeString(accountsByType, toAccount)
|
|
if IsTrue(IsEqual(toId, nil)) {
|
|
var keys interface{} = ObjectKeys(accountsByType)
|
|
panic(ArgumentsRequired(Add(Add(this.Id, " transfer() toAccount must be one of "), Join(keys, ", "))))
|
|
}
|
|
var currency interface{} = this.Currency(code)
|
|
var fromCurrencyId interface{} = this.ConvertDerivativesId(currency, fromAccount)
|
|
var toCurrencyId interface{} = this.ConvertDerivativesId(currency, toAccount)
|
|
var requestedAmount interface{} = this.CurrencyToPrecision(code, amount)
|
|
// this request is slightly different from v1 fromAccount -> from
|
|
var request interface{} = map[string]interface{} {
|
|
"amount": requestedAmount,
|
|
"currency": fromCurrencyId,
|
|
"currency_to": toCurrencyId,
|
|
"from": fromId,
|
|
"to": toId,
|
|
}
|
|
|
|
response:= (<-this.PrivatePostAuthWTransfer(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
//
|
|
// [
|
|
// 1616451183763,
|
|
// "acc_tf",
|
|
// null,
|
|
// null,
|
|
// [
|
|
// 1616451183763,
|
|
// "exchange",
|
|
// "margin",
|
|
// null,
|
|
// "UST",
|
|
// "UST",
|
|
// null,
|
|
// 1
|
|
// ],
|
|
// null,
|
|
// "SUCCESS",
|
|
// "1.0 Tether USDt transfered from Exchange to Margin"
|
|
// ]
|
|
//
|
|
var error interface{} = this.SafeString(response, 0)
|
|
if IsTrue(IsEqual(error, "error")) {
|
|
var message interface{} = this.SafeString(response, 2, "")
|
|
// same message as in v1
|
|
this.ThrowExactlyMatchedException(GetValue(this.Exceptions, "exact"), message, Add(Add(this.Id, " "), message))
|
|
panic(ExchangeError(Add(Add(this.Id, " "), message)))
|
|
}
|
|
|
|
ch <- this.ParseTransfer(map[string]interface{} {
|
|
"result": response,
|
|
}, currency)
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
func (this *bitfinex) ParseTransfer(transfer interface{}, optionalArgs ...interface{}) interface{} {
|
|
//
|
|
// transfer
|
|
//
|
|
// [
|
|
// 1616451183763,
|
|
// "acc_tf",
|
|
// null,
|
|
// null,
|
|
// [
|
|
// 1616451183763,
|
|
// "exchange",
|
|
// "margin",
|
|
// null,
|
|
// "UST",
|
|
// "UST",
|
|
// null,
|
|
// 1
|
|
// ],
|
|
// null,
|
|
// "SUCCESS",
|
|
// "1.0 Tether USDt transfered from Exchange to Margin"
|
|
// ]
|
|
//
|
|
currency := GetArg(optionalArgs, 0, nil)
|
|
_ = currency
|
|
var result interface{} = this.SafeList(transfer, "result")
|
|
var timestamp interface{} = this.SafeInteger(result, 0)
|
|
var info interface{} = this.SafeValue(result, 4)
|
|
var fromAccount interface{} = this.SafeString(info, 1)
|
|
var toAccount interface{} = this.SafeString(info, 2)
|
|
var currencyId interface{} = this.SafeString(info, 5)
|
|
var status interface{} = this.SafeString(result, 6)
|
|
return map[string]interface{} {
|
|
"id": nil,
|
|
"timestamp": timestamp,
|
|
"datetime": this.Iso8601(timestamp),
|
|
"status": this.ParseTransferStatus(status),
|
|
"amount": this.SafeNumber(info, 7),
|
|
"currency": this.SafeCurrencyCode(currencyId, currency),
|
|
"fromAccount": fromAccount,
|
|
"toAccount": toAccount,
|
|
"info": result,
|
|
}
|
|
}
|
|
func (this *bitfinex) ParseTransferStatus(status interface{}) interface{} {
|
|
var statuses interface{} = map[string]interface{} {
|
|
"SUCCESS": "ok",
|
|
"ERROR": "failed",
|
|
"FAILURE": "failed",
|
|
}
|
|
return this.SafeString(statuses, status, status)
|
|
}
|
|
func (this *bitfinex) ConvertDerivativesId(currency interface{}, typeVar interface{}) interface{} {
|
|
// there is a difference between this and the v1 api, namely trading wallet is called margin in v2
|
|
// {
|
|
// "id": "fUSTF0",
|
|
// "code": "USTF0",
|
|
// "info": [ 'USTF0', [], [], [], [ "USTF0", "UST" ] ],
|
|
var info interface{} = this.SafeValue(currency, "info")
|
|
var transferId interface{} = this.SafeString(info, 0)
|
|
var underlying interface{} = this.SafeValue(info, 4, []interface{}{})
|
|
var currencyId interface{} = nil
|
|
if IsTrue(IsEqual(typeVar, "derivatives")) {
|
|
currencyId = this.SafeString(underlying, 0, transferId)
|
|
var start interface{} = Subtract(GetArrayLength(currencyId), 2)
|
|
var isDerivativeCode interface{} = IsEqual(Slice(currencyId, start, nil), "F0")
|
|
if !IsTrue(isDerivativeCode) {
|
|
currencyId = Add(currencyId, "F0")
|
|
}
|
|
} else if IsTrue(!IsEqual(typeVar, "margin")) {
|
|
currencyId = this.SafeString(underlying, 1, transferId)
|
|
} else {
|
|
currencyId = transferId
|
|
}
|
|
return currencyId
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitfinex#fetchOrderBook
|
|
* @description fetches information on open orders with bid (buy) and ask (sell) prices, volumes and other data
|
|
* @see https://docs.bitfinex.com/reference/rest-public-book
|
|
* @param {string} symbol unified symbol of the market to fetch the order book for
|
|
* @param {int} [limit] the maximum amount of order book entries to return, bitfinex only allows 1, 25, or 100
|
|
* @param {object} [params] extra parameters specific to the exchange API endpoint
|
|
* @returns {object} A dictionary of [order book structures]{@link https://docs.ccxt.com/#/?id=order-book-structure} indexed by market symbols
|
|
*/
|
|
func (this *bitfinex) FetchOrderBook(symbol interface{}, optionalArgs ...interface{}) <- chan interface{} {
|
|
ch := make(chan interface{})
|
|
go func() interface{} {
|
|
defer close(ch)
|
|
defer ReturnPanicError(ch)
|
|
limit := GetArg(optionalArgs, 0, nil)
|
|
_ = limit
|
|
params := GetArg(optionalArgs, 1, map[string]interface{} {})
|
|
_ = params
|
|
|
|
retRes11328 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes11328)
|
|
var precision interface{} = this.SafeValue(this.Options, "precision", "R0")
|
|
var market interface{} = this.Market(symbol)
|
|
var request interface{} = map[string]interface{} {
|
|
"symbol": GetValue(market, "id"),
|
|
"precision": precision,
|
|
}
|
|
if IsTrue(!IsEqual(limit, nil)) {
|
|
AddElementToObject(request, "len", limit)
|
|
}
|
|
var fullRequest interface{} = this.Extend(request, params)
|
|
|
|
orderbook:= (<-this.PublicGetBookSymbolPrecision(fullRequest))
|
|
PanicOnError(orderbook)
|
|
var timestamp interface{} = this.Milliseconds()
|
|
var result interface{} = map[string]interface{} {
|
|
"symbol": GetValue(market, "symbol"),
|
|
"bids": []interface{}{},
|
|
"asks": []interface{}{},
|
|
"timestamp": timestamp,
|
|
"datetime": this.Iso8601(timestamp),
|
|
"nonce": nil,
|
|
}
|
|
var priceIndex interface{} = Ternary(IsTrue((IsEqual(GetValue(fullRequest, "precision"), "R0"))), 1, 0)
|
|
for i := 0; IsLessThan(i, GetArrayLength(orderbook)); i++ {
|
|
var order interface{} = GetValue(orderbook, i)
|
|
var price interface{} = this.SafeNumber(order, priceIndex)
|
|
var signedAmount interface{} = this.SafeString(order, 2)
|
|
var amount interface{} = Precise.StringAbs(signedAmount)
|
|
var side interface{} = Ternary(IsTrue(Precise.StringGt(signedAmount, "0")), "bids", "asks")
|
|
var resultSide interface{} = GetValue(result, side)
|
|
AppendToArray(&resultSide,[]interface{}{price, this.ParseNumber(amount)})
|
|
}
|
|
AddElementToObject(result, "bids", this.SortBy(GetValue(result, "bids"), 0, true))
|
|
AddElementToObject(result, "asks", this.SortBy(GetValue(result, "asks"), 0))
|
|
|
|
ch <- result
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
func (this *bitfinex) ParseTicker(ticker interface{}, optionalArgs ...interface{}) interface{} {
|
|
//
|
|
// on trading pairs (ex. tBTCUSD)
|
|
//
|
|
// {
|
|
// 'result': [
|
|
// SYMBOL,
|
|
// BID,
|
|
// BID_SIZE,
|
|
// ASK,
|
|
// ASK_SIZE,
|
|
// DAILY_CHANGE,
|
|
// DAILY_CHANGE_RELATIVE,
|
|
// LAST_PRICE,
|
|
// VOLUME,
|
|
// HIGH,
|
|
// LOW
|
|
// ]
|
|
// }
|
|
//
|
|
//
|
|
// on funding currencies (ex. fUSD)
|
|
//
|
|
// {
|
|
// 'result': [
|
|
// SYMBOL,
|
|
// FRR,
|
|
// BID,
|
|
// BID_PERIOD,
|
|
// BID_SIZE,
|
|
// ASK,
|
|
// ASK_PERIOD,
|
|
// ASK_SIZE,
|
|
// DAILY_CHANGE,
|
|
// DAILY_CHANGE_RELATIVE,
|
|
// LAST_PRICE,
|
|
// VOLUME,
|
|
// HIGH,
|
|
// LOW,
|
|
// _PLACEHOLDER,
|
|
// _PLACEHOLDER,
|
|
// FRR_AMOUNT_AVAILABLE
|
|
// ]
|
|
// }
|
|
//
|
|
market := GetArg(optionalArgs, 0, nil)
|
|
_ = market
|
|
var result interface{} = this.SafeList(ticker, "result")
|
|
var symbol interface{} = this.SafeSymbol(nil, market)
|
|
var length interface{} = GetArrayLength(result)
|
|
var last interface{} = this.SafeString(result, Subtract(length, 4))
|
|
var percentage interface{} = this.SafeString(result, Subtract(length, 5))
|
|
return this.SafeTicker(map[string]interface{} {
|
|
"symbol": symbol,
|
|
"timestamp": nil,
|
|
"datetime": nil,
|
|
"high": this.SafeString(result, Subtract(length, 2)),
|
|
"low": this.SafeString(result, Subtract(length, 1)),
|
|
"bid": this.SafeString(result, Subtract(length, 10)),
|
|
"bidVolume": this.SafeString(result, Subtract(length, 9)),
|
|
"ask": this.SafeString(result, Subtract(length, 8)),
|
|
"askVolume": this.SafeString(result, Subtract(length, 7)),
|
|
"vwap": nil,
|
|
"open": nil,
|
|
"close": last,
|
|
"last": last,
|
|
"previousClose": nil,
|
|
"change": this.SafeString(result, Subtract(length, 6)),
|
|
"percentage": Precise.StringMul(percentage, "100"),
|
|
"average": nil,
|
|
"baseVolume": this.SafeString(result, Subtract(length, 3)),
|
|
"quoteVolume": nil,
|
|
"info": result,
|
|
}, market)
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitfinex#fetchTickers
|
|
* @description fetches price tickers for multiple markets, statistical information calculated over the past 24 hours for each market
|
|
* @see https://docs.bitfinex.com/reference/rest-public-tickers
|
|
* @param {string[]|undefined} symbols unified symbols of the markets to fetch the ticker for, all market tickers are returned if not assigned
|
|
* @param {object} [params] extra parameters specific to the exchange API endpoint
|
|
* @returns {object} a dictionary of [ticker structures]{@link https://docs.ccxt.com/#/?id=ticker-structure}
|
|
*/
|
|
func (this *bitfinex) FetchTickers(optionalArgs ...interface{}) <- chan interface{} {
|
|
ch := make(chan interface{})
|
|
go func() interface{} {
|
|
defer close(ch)
|
|
defer ReturnPanicError(ch)
|
|
symbols := GetArg(optionalArgs, 0, nil)
|
|
_ = symbols
|
|
params := GetArg(optionalArgs, 1, map[string]interface{} {})
|
|
_ = params
|
|
|
|
retRes12528 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes12528)
|
|
symbols = this.MarketSymbols(symbols)
|
|
var request interface{} = map[string]interface{} {}
|
|
if IsTrue(!IsEqual(symbols, nil)) {
|
|
var ids interface{} = this.MarketIds(symbols)
|
|
AddElementToObject(request, "symbols", Join(ids, ","))
|
|
} else {
|
|
AddElementToObject(request, "symbols", "ALL")
|
|
}
|
|
|
|
tickers:= (<-this.PublicGetTickers(this.Extend(request, params)))
|
|
PanicOnError(tickers)
|
|
//
|
|
// [
|
|
// // on trading pairs (ex. tBTCUSD)
|
|
// [
|
|
// SYMBOL,
|
|
// BID,
|
|
// BID_SIZE,
|
|
// ASK,
|
|
// ASK_SIZE,
|
|
// DAILY_CHANGE,
|
|
// DAILY_CHANGE_RELATIVE,
|
|
// LAST_PRICE,
|
|
// VOLUME,
|
|
// HIGH,
|
|
// LOW
|
|
// ],
|
|
// // on funding currencies (ex. fUSD)
|
|
// [
|
|
// SYMBOL,
|
|
// FRR,
|
|
// BID,
|
|
// BID_PERIOD,
|
|
// BID_SIZE,
|
|
// ASK,
|
|
// ASK_PERIOD,
|
|
// ASK_SIZE,
|
|
// DAILY_CHANGE,
|
|
// DAILY_CHANGE_RELATIVE,
|
|
// LAST_PRICE,
|
|
// VOLUME,
|
|
// HIGH,
|
|
// LOW,
|
|
// _PLACEHOLDER,
|
|
// _PLACEHOLDER,
|
|
// FRR_AMOUNT_AVAILABLE
|
|
// ],
|
|
// ...
|
|
// ]
|
|
//
|
|
var result interface{} = map[string]interface{} {}
|
|
for i := 0; IsLessThan(i, GetArrayLength(tickers)); i++ {
|
|
var ticker interface{} = GetValue(tickers, i)
|
|
var marketId interface{} = this.SafeString(ticker, 0)
|
|
var market interface{} = this.SafeMarket(marketId)
|
|
var symbol interface{} = GetValue(market, "symbol")
|
|
AddElementToObject(result, symbol, this.ParseTicker(map[string]interface{} {
|
|
"result": ticker,
|
|
}, market))
|
|
}
|
|
|
|
ch <- this.FilterByArrayTickers(result, "symbol", symbols)
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitfinex#fetchTicker
|
|
* @description fetches a price ticker, a statistical calculation with the information calculated over the past 24 hours for a specific market
|
|
* @see https://docs.bitfinex.com/reference/rest-public-ticker
|
|
* @param {string} symbol unified symbol of the market to fetch the ticker for
|
|
* @param {object} [params] extra parameters specific to the exchange API endpoint
|
|
* @returns {object} a [ticker structure]{@link https://docs.ccxt.com/#/?id=ticker-structure}
|
|
*/
|
|
func (this *bitfinex) FetchTicker(symbol interface{}, optionalArgs ...interface{}) <- chan interface{} {
|
|
ch := make(chan interface{})
|
|
go func() interface{} {
|
|
defer close(ch)
|
|
defer ReturnPanicError(ch)
|
|
params := GetArg(optionalArgs, 0, map[string]interface{} {})
|
|
_ = params
|
|
|
|
retRes13228 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes13228)
|
|
var market interface{} = this.Market(symbol)
|
|
var request interface{} = map[string]interface{} {
|
|
"symbol": GetValue(market, "id"),
|
|
}
|
|
|
|
ticker:= (<-this.PublicGetTickerSymbol(this.Extend(request, params)))
|
|
PanicOnError(ticker)
|
|
var result interface{} = map[string]interface{} {
|
|
"result": ticker,
|
|
}
|
|
|
|
ch <- this.ParseTicker(result, market)
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
func (this *bitfinex) ParseTrade(trade interface{}, optionalArgs ...interface{}) interface{} {
|
|
//
|
|
// fetchTrades (public)
|
|
//
|
|
// [
|
|
// ID,
|
|
// MTS, // timestamp
|
|
// AMOUNT,
|
|
// PRICE
|
|
// ]
|
|
//
|
|
// fetchMyTrades (private)
|
|
//
|
|
// [
|
|
// ID,
|
|
// PAIR,
|
|
// MTS_CREATE,
|
|
// ORDER_ID,
|
|
// EXEC_AMOUNT,
|
|
// EXEC_PRICE,
|
|
// ORDER_TYPE,
|
|
// ORDER_PRICE,
|
|
// MAKER,
|
|
// FEE,
|
|
// FEE_CURRENCY,
|
|
// ...
|
|
// ]
|
|
//
|
|
market := GetArg(optionalArgs, 0, nil)
|
|
_ = market
|
|
var tradeList interface{} = this.SafeList(trade, "result", []interface{}{})
|
|
var tradeLength interface{} = GetArrayLength(tradeList)
|
|
var isPrivate interface{} = (IsGreaterThan(tradeLength, 5))
|
|
var id interface{} = this.SafeString(tradeList, 0)
|
|
var amountIndex interface{} = Ternary(IsTrue(isPrivate), 4, 2)
|
|
var side interface{} = nil
|
|
var amountString interface{} = this.SafeString(tradeList, amountIndex)
|
|
var priceIndex interface{} = Ternary(IsTrue(isPrivate), 5, 3)
|
|
var priceString interface{} = this.SafeString(tradeList, priceIndex)
|
|
if IsTrue(IsEqual(GetValue(amountString, 0), "-")) {
|
|
side = "sell"
|
|
amountString = Precise.StringAbs(amountString)
|
|
} else {
|
|
side = "buy"
|
|
}
|
|
var orderId interface{} = nil
|
|
var takerOrMaker interface{} = nil
|
|
var typeVar interface{} = nil
|
|
var fee interface{} = nil
|
|
var symbol interface{} = this.SafeSymbol(nil, market)
|
|
var timestampIndex interface{} = Ternary(IsTrue(isPrivate), 2, 1)
|
|
var timestamp interface{} = this.SafeInteger(tradeList, timestampIndex)
|
|
if IsTrue(isPrivate) {
|
|
var marketId interface{} = GetValue(tradeList, 1)
|
|
symbol = this.SafeSymbol(marketId)
|
|
orderId = this.SafeString(tradeList, 3)
|
|
var maker interface{} = this.SafeInteger(tradeList, 8)
|
|
takerOrMaker = Ternary(IsTrue((IsEqual(maker, 1))), "maker", "taker")
|
|
var feeCostString interface{} = this.SafeString(tradeList, 9)
|
|
feeCostString = Precise.StringNeg(feeCostString)
|
|
var feeCurrencyId interface{} = this.SafeString(tradeList, 10)
|
|
var feeCurrency interface{} = this.SafeCurrencyCode(feeCurrencyId)
|
|
fee = map[string]interface{} {
|
|
"cost": feeCostString,
|
|
"currency": feeCurrency,
|
|
}
|
|
var orderType interface{} = GetValue(tradeList, 6)
|
|
typeVar = this.SafeString(GetValue(this.Options, "exchangeTypes"), orderType)
|
|
}
|
|
return this.SafeTrade(map[string]interface{} {
|
|
"id": id,
|
|
"timestamp": timestamp,
|
|
"datetime": this.Iso8601(timestamp),
|
|
"symbol": symbol,
|
|
"order": orderId,
|
|
"side": side,
|
|
"type": typeVar,
|
|
"takerOrMaker": takerOrMaker,
|
|
"price": priceString,
|
|
"amount": amountString,
|
|
"cost": nil,
|
|
"fee": fee,
|
|
"info": tradeList,
|
|
}, market)
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitfinex#fetchTrades
|
|
* @description get the list of most recent trades for a particular symbol
|
|
* @see https://docs.bitfinex.com/reference/rest-public-trades
|
|
* @param {string} symbol unified symbol of the market to fetch trades for
|
|
* @param {int} [since] timestamp in ms of the earliest trade to fetch
|
|
* @param {int} [limit] the maximum amount of trades to fetch, default 120, max 10000
|
|
* @param {object} [params] extra parameters specific to the exchange API endpoint
|
|
* @param {boolean} [params.paginate] default false, when true will automatically paginate by calling this endpoint multiple times. See in the docs all the [available parameters](https://github.com/ccxt/ccxt/wiki/Manual#pagination-params)
|
|
* @param {int} [params.until] the latest time in ms to fetch entries for
|
|
* @returns {Trade[]} a list of [trade structures]{@link https://docs.ccxt.com/#/?id=public-trades}
|
|
*/
|
|
func (this *bitfinex) FetchTrades(symbol interface{}, optionalArgs ...interface{}) <- chan interface{} {
|
|
ch := make(chan interface{})
|
|
go func() interface{} {
|
|
defer close(ch)
|
|
defer ReturnPanicError(ch)
|
|
since := GetArg(optionalArgs, 0, nil)
|
|
_ = since
|
|
limit := GetArg(optionalArgs, 1, nil)
|
|
_ = limit
|
|
params := GetArg(optionalArgs, 2, map[string]interface{} {})
|
|
_ = params
|
|
|
|
retRes14308 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes14308)
|
|
var paginate interface{} = false
|
|
paginateparamsVariable := this.HandleOptionAndParams(params, "fetchTrades", "paginate");
|
|
paginate = GetValue(paginateparamsVariable,0);
|
|
params = GetValue(paginateparamsVariable,1)
|
|
if IsTrue(paginate) {
|
|
|
|
retRes143419 := (<-this.FetchPaginatedCallDynamic("fetchTrades", symbol, since, limit, params, 10000))
|
|
PanicOnError(retRes143419)
|
|
ch <- retRes143419
|
|
return nil
|
|
}
|
|
var market interface{} = this.Market(symbol)
|
|
var sort interface{} = "-1"
|
|
var request interface{} = map[string]interface{} {
|
|
"symbol": GetValue(market, "id"),
|
|
}
|
|
if IsTrue(!IsEqual(since, nil)) {
|
|
AddElementToObject(request, "start", since)
|
|
sort = "1"
|
|
}
|
|
if IsTrue(!IsEqual(limit, nil)) {
|
|
AddElementToObject(request, "limit", mathMin(limit, 10000)) // default 120, max 10000
|
|
}
|
|
AddElementToObject(request, "sort", sort)
|
|
requestparamsVariable := this.HandleUntilOption("end", request, params);
|
|
request = GetValue(requestparamsVariable,0);
|
|
params = GetValue(requestparamsVariable,1)
|
|
|
|
response:= (<-this.PublicGetTradesSymbolHist(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
//
|
|
// [
|
|
// [
|
|
// ID,
|
|
// MTS, // timestamp
|
|
// AMOUNT,
|
|
// PRICE
|
|
// ]
|
|
// ]
|
|
//
|
|
var trades interface{} = this.SortBy(response, 1)
|
|
var tradesList interface{} = []interface{}{}
|
|
for i := 0; IsLessThan(i, GetArrayLength(trades)); i++ {
|
|
AppendToArray(&tradesList,map[string]interface{} {
|
|
"result": GetValue(trades, i),
|
|
}) // convert to array of dicts to match parseOrder signature
|
|
}
|
|
|
|
ch <- this.ParseTrades(tradesList, market, nil, limit)
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitfinex#fetchOHLCV
|
|
* @description fetches historical candlestick data containing the open, high, low, and close price, and the volume of a market
|
|
* @see https://docs.bitfinex.com/reference/rest-public-candles
|
|
* @param {string} symbol unified symbol of the market to fetch OHLCV data for
|
|
* @param {string} timeframe the length of time each candle represents
|
|
* @param {int} [since] timestamp in ms of the earliest candle to fetch
|
|
* @param {int} [limit] the maximum amount of candles to fetch, default 100 max 10000
|
|
* @param {object} [params] extra parameters specific to the exchange API endpoint
|
|
* @returns {int[][]} A list of candles ordered as timestamp, open, high, low, close, volume
|
|
* @param {int} [params.until] timestamp in ms of the latest candle to fetch
|
|
* @param {boolean} [params.paginate] default false, when true will automatically paginate by calling this endpoint multiple times. See in the docs all the [available parameters](https://github.com/ccxt/ccxt/wiki/Manual#pagination-params)
|
|
*/
|
|
func (this *bitfinex) FetchOHLCV(symbol interface{}, optionalArgs ...interface{}) <- chan interface{} {
|
|
ch := make(chan interface{})
|
|
go func() interface{} {
|
|
defer close(ch)
|
|
defer ReturnPanicError(ch)
|
|
timeframe := GetArg(optionalArgs, 0, "1m")
|
|
_ = timeframe
|
|
since := GetArg(optionalArgs, 1, nil)
|
|
_ = since
|
|
limit := GetArg(optionalArgs, 2, 100)
|
|
_ = limit
|
|
params := GetArg(optionalArgs, 3, map[string]interface{} {})
|
|
_ = params
|
|
|
|
retRes14848 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes14848)
|
|
var paginate interface{} = false
|
|
paginateparamsVariable := this.HandleOptionAndParams(params, "fetchOHLCV", "paginate");
|
|
paginate = GetValue(paginateparamsVariable,0);
|
|
params = GetValue(paginateparamsVariable,1)
|
|
if IsTrue(paginate) {
|
|
|
|
retRes148819 := (<-this.FetchPaginatedCallDeterministic("fetchOHLCV", symbol, since, limit, timeframe, params, 10000))
|
|
PanicOnError(retRes148819)
|
|
ch <- retRes148819
|
|
return nil
|
|
}
|
|
var market interface{} = this.Market(symbol)
|
|
if IsTrue(IsEqual(limit, nil)) {
|
|
limit = 10000
|
|
} else {
|
|
limit = mathMin(limit, 10000)
|
|
}
|
|
var request interface{} = map[string]interface{} {
|
|
"symbol": GetValue(market, "id"),
|
|
"timeframe": this.SafeString(this.Timeframes, timeframe, timeframe),
|
|
"sort": 1,
|
|
"limit": limit,
|
|
}
|
|
if IsTrue(!IsEqual(since, nil)) {
|
|
AddElementToObject(request, "start", since)
|
|
}
|
|
requestparamsVariable := this.HandleUntilOption("end", request, params);
|
|
request = GetValue(requestparamsVariable,0);
|
|
params = GetValue(requestparamsVariable,1)
|
|
|
|
response:= (<-this.PublicGetCandlesTradeTimeframeSymbolHist(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
|
|
//
|
|
// [
|
|
// [1591503840000,0.025069,0.025068,0.025069,0.025068,1.97828998],
|
|
// [1591504500000,0.025065,0.025065,0.025065,0.025065,1.0164],
|
|
// [1591504620000,0.025062,0.025062,0.025062,0.025062,0.5],
|
|
// ]
|
|
//
|
|
ch <- this.ParseOHLCVs(response, market, timeframe, since, limit)
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
func (this *bitfinex) ParseOHLCV(ohlcv interface{}, optionalArgs ...interface{}) interface{} {
|
|
//
|
|
// [
|
|
// 1457539800000,
|
|
// 0.02594,
|
|
// 0.02594,
|
|
// 0.02594,
|
|
// 0.02594,
|
|
// 0.1
|
|
// ]
|
|
//
|
|
market := GetArg(optionalArgs, 0, nil)
|
|
_ = market
|
|
return []interface{}{this.SafeInteger(ohlcv, 0), this.SafeNumber(ohlcv, 1), this.SafeNumber(ohlcv, 3), this.SafeNumber(ohlcv, 4), this.SafeNumber(ohlcv, 2), this.SafeNumber(ohlcv, 5)}
|
|
}
|
|
func (this *bitfinex) ParseOrderStatus(status interface{}) interface{} {
|
|
if IsTrue(IsEqual(status, nil)) {
|
|
return status
|
|
}
|
|
var parts interface{} = Split(status, " ")
|
|
var state interface{} = this.SafeString(parts, 0)
|
|
var statuses interface{} = map[string]interface{} {
|
|
"ACTIVE": "open",
|
|
"PARTIALLY": "open",
|
|
"EXECUTED": "closed",
|
|
"CANCELED": "canceled",
|
|
"INSUFFICIENT": "canceled",
|
|
"POSTONLY CANCELED": "canceled",
|
|
"RSN_DUST": "rejected",
|
|
"RSN_PAUSE": "rejected",
|
|
"IOC CANCELED": "canceled",
|
|
"FILLORKILL CANCELED": "canceled",
|
|
}
|
|
return this.SafeString(statuses, state, status)
|
|
}
|
|
func (this *bitfinex) ParseOrderFlags(flags interface{}) interface{} {
|
|
// flags can be added to each other...
|
|
var flagValues interface{} = map[string]interface{} {
|
|
"1024": []interface{}{"reduceOnly"},
|
|
"4096": []interface{}{"postOnly"},
|
|
"5120": []interface{}{"reduceOnly", "postOnly"},
|
|
}
|
|
return this.SafeValue(flagValues, flags, nil)
|
|
}
|
|
func (this *bitfinex) ParseTimeInForce(orderType interface{}) interface{} {
|
|
var orderTypes interface{} = map[string]interface{} {
|
|
"EXCHANGE IOC": "IOC",
|
|
"EXCHANGE FOK": "FOK",
|
|
"IOC": "IOC",
|
|
"FOK": "FOK",
|
|
}
|
|
return this.SafeString(orderTypes, orderType, "GTC")
|
|
}
|
|
func (this *bitfinex) ParseOrder(order interface{}, optionalArgs ...interface{}) interface{} {
|
|
market := GetArg(optionalArgs, 0, nil)
|
|
_ = market
|
|
var orderList interface{} = this.SafeList(order, "result")
|
|
var id interface{} = this.SafeString(orderList, 0)
|
|
var marketId interface{} = this.SafeString(orderList, 3)
|
|
var symbol interface{} = this.SafeSymbol(marketId)
|
|
// https://github.com/ccxt/ccxt/issues/6686
|
|
// const timestamp = this.safeTimestamp (orderObject, 5);
|
|
var timestamp interface{} = this.SafeInteger(orderList, 5)
|
|
var remaining interface{} = Precise.StringAbs(this.SafeString(orderList, 6))
|
|
var signedAmount interface{} = this.SafeString(orderList, 7)
|
|
var amount interface{} = Precise.StringAbs(signedAmount)
|
|
var side interface{} = Ternary(IsTrue(Precise.StringLt(signedAmount, "0")), "sell", "buy")
|
|
var orderType interface{} = this.SafeString(orderList, 8)
|
|
var typeVar interface{} = this.SafeString(this.SafeValue(this.Options, "exchangeTypes"), orderType)
|
|
var timeInForce interface{} = this.ParseTimeInForce(orderType)
|
|
var rawFlags interface{} = this.SafeString(orderList, 12)
|
|
var flags interface{} = this.ParseOrderFlags(rawFlags)
|
|
var postOnly interface{} = false
|
|
if IsTrue(!IsEqual(flags, nil)) {
|
|
for i := 0; IsLessThan(i, GetArrayLength(flags)); i++ {
|
|
if IsTrue(IsEqual(GetValue(flags, i), "postOnly")) {
|
|
postOnly = true
|
|
}
|
|
}
|
|
}
|
|
var price interface{} = this.SafeString(orderList, 16)
|
|
var triggerPrice interface{} = nil
|
|
if IsTrue(IsTrue((IsEqual(orderType, "EXCHANGE STOP"))) || IsTrue((IsEqual(orderType, "EXCHANGE STOP LIMIT")))) {
|
|
price = nil
|
|
triggerPrice = this.SafeString(orderList, 16)
|
|
if IsTrue(IsEqual(orderType, "EXCHANGE STOP LIMIT")) {
|
|
price = this.SafeString(orderList, 19)
|
|
}
|
|
}
|
|
var status interface{} = nil
|
|
var statusString interface{} = this.SafeString(orderList, 13)
|
|
if IsTrue(!IsEqual(statusString, nil)) {
|
|
var parts interface{} = Split(statusString, " @ ")
|
|
status = this.ParseOrderStatus(this.SafeString(parts, 0))
|
|
}
|
|
var average interface{} = this.SafeString(orderList, 17)
|
|
var clientOrderId interface{} = this.SafeString(orderList, 2)
|
|
return this.SafeOrder(map[string]interface{} {
|
|
"info": orderList,
|
|
"id": id,
|
|
"clientOrderId": clientOrderId,
|
|
"timestamp": timestamp,
|
|
"datetime": this.Iso8601(timestamp),
|
|
"lastTradeTimestamp": nil,
|
|
"symbol": symbol,
|
|
"type": typeVar,
|
|
"timeInForce": timeInForce,
|
|
"postOnly": postOnly,
|
|
"side": side,
|
|
"price": price,
|
|
"triggerPrice": triggerPrice,
|
|
"amount": amount,
|
|
"cost": nil,
|
|
"average": average,
|
|
"filled": nil,
|
|
"remaining": remaining,
|
|
"status": status,
|
|
"fee": nil,
|
|
"trades": nil,
|
|
}, market)
|
|
}
|
|
func (this *bitfinex) CreateOrderRequest(symbol interface{}, typeVar interface{}, side interface{}, amount interface{}, optionalArgs ...interface{}) interface{} {
|
|
/**
|
|
* @method
|
|
* @ignore
|
|
* @name bitfinex#createOrderRequest
|
|
* @description helper function to build an order request
|
|
* @param {string} symbol unified symbol of the market to create an order in
|
|
* @param {string} type 'market' or 'limit'
|
|
* @param {string} side 'buy' or 'sell'
|
|
* @param {float} amount how much you want to trade in units of the base currency
|
|
* @param {float} [price] the price of the order, in units of the quote currency, ignored in market orders
|
|
* @param {object} [params] extra parameters specific to the exchange API endpoint
|
|
* @param {float} [params.triggerPrice] The price at which a trigger order is triggered at
|
|
* @param {string} [params.timeInForce] "GTC", "IOC", "FOK", or "PO"
|
|
* @param {bool} [params.postOnly]
|
|
* @param {bool} [params.reduceOnly] Ensures that the executed order does not flip the opened position.
|
|
* @param {int} [params.flags] additional order parameters: 4096 (Post Only), 1024 (Reduce Only), 16384 (OCO), 64 (Hidden), 512 (Close), 524288 (No Var Rates)
|
|
* @param {int} [params.lev] leverage for a derivative order, supported by derivative symbol orders only. The value should be between 1 and 100 inclusive.
|
|
* @param {string} [params.price_traling] The trailing price for a trailing stop order
|
|
* @param {string} [params.price_aux_limit] Order price for stop limit orders
|
|
* @param {string} [params.price_oco_stop] OCO stop price
|
|
* @returns {object} an [order structure]{@link https://github.com/ccxt/ccxt/wiki/Manual#order-structure}
|
|
*/
|
|
price := GetArg(optionalArgs, 0, nil)
|
|
_ = price
|
|
params := GetArg(optionalArgs, 1, map[string]interface{} {})
|
|
_ = params
|
|
var market interface{} = this.Market(symbol)
|
|
var amountString interface{} = this.AmountToPrecision(symbol, amount)
|
|
amountString = Ternary(IsTrue((IsEqual(side, "buy"))), amountString, Precise.StringNeg(amountString))
|
|
var request interface{} = map[string]interface{} {
|
|
"symbol": GetValue(market, "id"),
|
|
"amount": amountString,
|
|
}
|
|
var triggerPrice interface{} = this.SafeString2(params, "stopPrice", "triggerPrice")
|
|
var trailingAmount interface{} = this.SafeString(params, "trailingAmount")
|
|
var timeInForce interface{} = this.SafeString(params, "timeInForce")
|
|
var postOnlyParam interface{} = this.SafeBool(params, "postOnly", false)
|
|
var reduceOnly interface{} = this.SafeBool(params, "reduceOnly", false)
|
|
var clientOrderId interface{} = this.SafeValue2(params, "cid", "clientOrderId")
|
|
var orderType interface{} = ToUpper(typeVar)
|
|
if IsTrue(!IsEqual(trailingAmount, nil)) {
|
|
orderType = "TRAILING STOP"
|
|
AddElementToObject(request, "price_trailing", trailingAmount)
|
|
} else if IsTrue(!IsEqual(triggerPrice, nil)) {
|
|
// request['price'] is taken as triggerPrice for stop orders
|
|
AddElementToObject(request, "price", this.PriceToPrecision(symbol, triggerPrice))
|
|
if IsTrue(IsEqual(typeVar, "limit")) {
|
|
orderType = "STOP LIMIT"
|
|
AddElementToObject(request, "price_aux_limit", this.PriceToPrecision(symbol, price))
|
|
} else {
|
|
orderType = "STOP"
|
|
}
|
|
}
|
|
var ioc interface{} = (IsEqual(timeInForce, "IOC"))
|
|
var fok interface{} = (IsEqual(timeInForce, "FOK"))
|
|
var postOnly interface{} = (IsTrue(postOnlyParam) || IsTrue((IsEqual(timeInForce, "PO"))))
|
|
if IsTrue(IsTrue((IsTrue(ioc) || IsTrue(fok))) && IsTrue((IsEqual(price, nil)))) {
|
|
panic(InvalidOrder(Add(this.Id, " createOrder() requires a price argument with IOC and FOK orders")))
|
|
}
|
|
if IsTrue(IsTrue((IsTrue(ioc) || IsTrue(fok))) && IsTrue((IsEqual(typeVar, "market")))) {
|
|
panic(InvalidOrder(Add(this.Id, " createOrder() does not allow market IOC and FOK orders")))
|
|
}
|
|
if IsTrue(IsTrue((!IsEqual(typeVar, "market"))) && IsTrue((IsEqual(triggerPrice, nil)))) {
|
|
AddElementToObject(request, "price", this.PriceToPrecision(symbol, price))
|
|
}
|
|
if IsTrue(ioc) {
|
|
orderType = "IOC"
|
|
} else if IsTrue(fok) {
|
|
orderType = "FOK"
|
|
}
|
|
var marginMode interface{} = nil
|
|
marginModeparamsVariable := this.HandleMarginModeAndParams("createOrder", params);
|
|
marginMode = GetValue(marginModeparamsVariable,0);
|
|
params = GetValue(marginModeparamsVariable,1)
|
|
if IsTrue(IsTrue(GetValue(market, "spot")) && IsTrue((IsEqual(marginMode, nil)))) {
|
|
// The EXCHANGE prefix is only required for non margin spot markets
|
|
orderType = Add("EXCHANGE ", orderType)
|
|
}
|
|
AddElementToObject(request, "type", orderType)
|
|
// flag values may be summed to combine flags
|
|
var flags interface{} = 0
|
|
if IsTrue(postOnly) {
|
|
flags = this.Sum(flags, 4096)
|
|
}
|
|
if IsTrue(reduceOnly) {
|
|
flags = this.Sum(flags, 1024)
|
|
}
|
|
if IsTrue(!IsEqual(flags, 0)) {
|
|
AddElementToObject(request, "flags", flags)
|
|
}
|
|
if IsTrue(!IsEqual(clientOrderId, nil)) {
|
|
AddElementToObject(request, "cid", clientOrderId)
|
|
}
|
|
params = this.Omit(params, []interface{}{"triggerPrice", "stopPrice", "timeInForce", "postOnly", "reduceOnly", "trailingAmount", "clientOrderId"})
|
|
return this.Extend(request, params)
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitfinex#createOrder
|
|
* @description create an order on the exchange
|
|
* @see https://docs.bitfinex.com/reference/rest-auth-submit-order
|
|
* @param {string} symbol unified CCXT market symbol
|
|
* @param {string} type 'limit' or 'market'
|
|
* @param {string} side 'buy' or 'sell'
|
|
* @param {float} amount the amount of currency to trade
|
|
* @param {float} [price] price of the order
|
|
* @param {object} [params] extra parameters specific to the exchange API endpoint
|
|
* @param {float} [params.triggerPrice] the price that triggers a trigger order
|
|
* @param {string} [params.timeInForce] "GTC", "IOC", "FOK", or "PO"
|
|
* @param {boolean} [params.postOnly] set to true if you want to make a post only order
|
|
* @param {boolean} [params.reduceOnly] indicates that the order is to reduce the size of a position
|
|
* @param {int} [params.flags] additional order parameters: 4096 (Post Only), 1024 (Reduce Only), 16384 (OCO), 64 (Hidden), 512 (Close), 524288 (No Var Rates)
|
|
* @param {int} [params.lev] leverage for a derivative order, supported by derivative symbol orders only. The value should be between 1 and 100 inclusive.
|
|
* @param {string} [params.price_aux_limit] order price for stop limit orders
|
|
* @param {string} [params.price_oco_stop] OCO stop price
|
|
* @param {string} [params.trailingAmount] *swap only* the quote amount to trail away from the current market price
|
|
* @returns {object} an [order structure]{@link https://docs.ccxt.com/#/?id=order-structure}
|
|
*/
|
|
func (this *bitfinex) CreateOrder(symbol interface{}, typeVar interface{}, side interface{}, amount interface{}, optionalArgs ...interface{}) <- chan interface{} {
|
|
ch := make(chan interface{})
|
|
go func() interface{} {
|
|
defer close(ch)
|
|
defer ReturnPanicError(ch)
|
|
price := GetArg(optionalArgs, 0, nil)
|
|
_ = price
|
|
params := GetArg(optionalArgs, 1, map[string]interface{} {})
|
|
_ = params
|
|
|
|
retRes17658 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes17658)
|
|
var market interface{} = this.Market(symbol)
|
|
var request interface{} = this.CreateOrderRequest(symbol, typeVar, side, amount, price, params)
|
|
|
|
response:= (<-this.PrivatePostAuthWOrderSubmit(request))
|
|
PanicOnError(response)
|
|
//
|
|
// [
|
|
// 1653325121, // Timestamp in milliseconds
|
|
// "on-req", // Purpose of notification ('on-req', 'oc-req', "uca", 'fon-req', "foc-req")
|
|
// null, // unique ID of the message
|
|
// null,
|
|
// [
|
|
// [
|
|
// 95412102131, // Order ID
|
|
// null, // Group ID
|
|
// 1653325121798, // Client Order ID
|
|
// "tDOGE:UST", // Market ID
|
|
// 1653325121798, // Millisecond timestamp of creation
|
|
// 1653325121798, // Millisecond timestamp of update
|
|
// -10, // Amount (Positive means buy, negative means sell)
|
|
// -10, // Original amount
|
|
// "EXCHANGE LIMIT", // Type of the order: LIMIT, EXCHANGE LIMIT, MARKET, EXCHANGE MARKET, STOP, EXCHANGE STOP, STOP LIMIT, EXCHANGE STOP LIMIT, TRAILING STOP, EXCHANGE TRAILING STOP, FOK, EXCHANGE FOK, IOC, EXCHANGE IOC.
|
|
// null, // Previous order type (stop-limit orders are converted to limit orders so for them previous type is always STOP)
|
|
// null, // Millisecond timestamp of Time-In-Force: automatic order cancellation
|
|
// null, // _PLACEHOLDER
|
|
// 4096, // Flags, see parseOrderFlags()
|
|
// "ACTIVE", // Order Status, see parseOrderStatus()
|
|
// null, // _PLACEHOLDER
|
|
// null, // _PLACEHOLDER
|
|
// 0.071, // Price (Stop Price for stop-limit orders, Limit Price for limit orders)
|
|
// 0, // Average Price
|
|
// 0, // Trailing Price
|
|
// 0, // Auxiliary Limit price (for STOP LIMIT)
|
|
// null, // _PLACEHOLDER
|
|
// null, // _PLACEHOLDER
|
|
// null, // _PLACEHOLDER
|
|
// 0, // Hidden (0 if false, 1 if true)
|
|
// 0, // Placed ID (If another order caused this order to be placed (OCO) this will be that other order's ID)
|
|
// null, // _PLACEHOLDER
|
|
// null, // _PLACEHOLDER
|
|
// null, // _PLACEHOLDER
|
|
// "API>BFX", // Routing, indicates origin of action: BFX, ETHFX, API>BFX, API>ETHFX
|
|
// null, // _PLACEHOLDER
|
|
// null, // _PLACEHOLDER
|
|
// {"$F7":1} // additional meta information about the order ( $F7 = IS_POST_ONLY (0 if false, 1 if true), $F33 = Leverage (int))
|
|
// ]
|
|
// ],
|
|
// null, // CODE (work in progress)
|
|
// "SUCCESS", // Status of the request
|
|
// "Submitting 1 orders." // Message
|
|
// ]
|
|
//
|
|
var status interface{} = this.SafeString(response, 6)
|
|
if IsTrue(!IsEqual(status, "SUCCESS")) {
|
|
var errorCode interface{} = GetValue(response, 5)
|
|
var errorText interface{} = GetValue(response, 7)
|
|
panic(ExchangeError(Add(Add(Add(Add(Add(Add(Add(this.Id, " "), GetValue(response, 6)), ": "), errorText), " (#"), errorCode), ")")))
|
|
}
|
|
var orders interface{} = this.SafeList(response, 4, []interface{}{})
|
|
var order interface{} = this.SafeList(orders, 0)
|
|
var newOrder interface{} = map[string]interface{} {
|
|
"result": order,
|
|
}
|
|
|
|
ch <- this.ParseOrder(newOrder, market)
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitfinex#createOrders
|
|
* @description create a list of trade orders
|
|
* @see https://docs.bitfinex.com/reference/rest-auth-order-multi
|
|
* @param {Array} orders list of orders to create, each object should contain the parameters required by createOrder, namely symbol, type, side, amount, price and params
|
|
* @param {object} [params] extra parameters specific to the exchange API endpoint
|
|
* @returns {object} an [order structure]{@link https://docs.ccxt.com/#/?id=order-structure}
|
|
*/
|
|
func (this *bitfinex) CreateOrders(orders interface{}, optionalArgs ...interface{}) <- chan interface{} {
|
|
ch := make(chan interface{})
|
|
go func() interface{} {
|
|
defer close(ch)
|
|
defer ReturnPanicError(ch)
|
|
params := GetArg(optionalArgs, 0, map[string]interface{} {})
|
|
_ = params
|
|
|
|
retRes18388 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes18388)
|
|
var ordersRequests interface{} = []interface{}{}
|
|
for i := 0; IsLessThan(i, GetArrayLength(orders)); i++ {
|
|
var rawOrder interface{} = GetValue(orders, i)
|
|
var symbol interface{} = this.SafeString(rawOrder, "symbol")
|
|
var typeVar interface{} = this.SafeString(rawOrder, "type")
|
|
var side interface{} = this.SafeString(rawOrder, "side")
|
|
var amount interface{} = this.SafeNumber(rawOrder, "amount")
|
|
var price interface{} = this.SafeNumber(rawOrder, "price")
|
|
var orderParams interface{} = this.SafeDict(rawOrder, "params", map[string]interface{} {})
|
|
var orderRequest interface{} = this.CreateOrderRequest(symbol, typeVar, side, amount, price, orderParams)
|
|
AppendToArray(&ordersRequests,[]interface{}{"on", orderRequest})
|
|
}
|
|
var request interface{} = map[string]interface{} {
|
|
"ops": ordersRequests,
|
|
}
|
|
|
|
response:= (<-this.PrivatePostAuthWOrderMulti(request))
|
|
PanicOnError(response)
|
|
//
|
|
// [
|
|
// 1706762515553,
|
|
// "ox_multi-req",
|
|
// null,
|
|
// null,
|
|
// [
|
|
// [
|
|
// 1706762515,
|
|
// "on-req",
|
|
// null,
|
|
// null,
|
|
// [
|
|
// [139567428547,null,1706762515551,"tBTCUST",1706762515551,1706762515551,0.0001,0.0001,"EXCHANGE LIMIT",null,null,null,0,"ACTIVE",null,null,35000,0,0,0,null,null,null,0,0,null,null,null,"API>BFX",null,null,{}]
|
|
// ],
|
|
// null,
|
|
// "SUCCESS",
|
|
// "Submitting 1 orders."
|
|
// ],
|
|
// ],
|
|
// null,
|
|
// "SUCCESS",
|
|
// "Submitting 2 order operations."
|
|
// ]
|
|
//
|
|
var results interface{} = []interface{}{}
|
|
var data interface{} = this.SafeList(response, 4, []interface{}{})
|
|
for i := 0; IsLessThan(i, GetArrayLength(data)); i++ {
|
|
var entry interface{} = GetValue(data, i)
|
|
var individualOrder interface{} = GetValue(entry, 4)
|
|
AppendToArray(&results,map[string]interface{} {
|
|
"result": GetValue(individualOrder, 0),
|
|
})
|
|
}
|
|
|
|
ch <- this.ParseOrders(results)
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitfinex#cancelAllOrders
|
|
* @description cancel all open orders
|
|
* @see https://docs.bitfinex.com/reference/rest-auth-cancel-orders-multiple
|
|
* @param {string} symbol unified market symbol, only orders in the market of this symbol are cancelled when symbol is not undefined
|
|
* @param {object} [params] extra parameters specific to the exchange API endpoint
|
|
* @returns {object[]} a list of [order structures]{@link https://docs.ccxt.com/#/?id=order-structure}
|
|
*/
|
|
func (this *bitfinex) CancelAllOrders(optionalArgs ...interface{}) <- chan interface{} {
|
|
ch := make(chan interface{})
|
|
go func() interface{} {
|
|
defer close(ch)
|
|
defer ReturnPanicError(ch)
|
|
symbol := GetArg(optionalArgs, 0, nil)
|
|
_ = symbol
|
|
params := GetArg(optionalArgs, 1, map[string]interface{} {})
|
|
_ = params
|
|
|
|
retRes19008 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes19008)
|
|
var request interface{} = map[string]interface{} {
|
|
"all": 1,
|
|
}
|
|
|
|
response:= (<-this.PrivatePostAuthWOrderCancelMulti(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
var orders interface{} = this.SafeList(response, 4, []interface{}{})
|
|
var ordersList interface{} = []interface{}{}
|
|
for i := 0; IsLessThan(i, GetArrayLength(orders)); i++ {
|
|
AppendToArray(&ordersList,map[string]interface{} {
|
|
"result": GetValue(orders, i),
|
|
})
|
|
}
|
|
|
|
ch <- this.ParseOrders(ordersList)
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitfinex#cancelOrder
|
|
* @description cancels an open order
|
|
* @see https://docs.bitfinex.com/reference/rest-auth-cancel-order
|
|
* @param {string} id order id
|
|
* @param {string} symbol Not used by bitfinex cancelOrder ()
|
|
* @param {object} [params] extra parameters specific to the exchange API endpoint
|
|
* @returns {object} An [order structure]{@link https://docs.ccxt.com/#/?id=order-structure}
|
|
*/
|
|
func (this *bitfinex) CancelOrder(id interface{}, optionalArgs ...interface{}) <- chan interface{} {
|
|
ch := make(chan interface{})
|
|
go func() interface{} {
|
|
defer close(ch)
|
|
defer ReturnPanicError(ch)
|
|
symbol := GetArg(optionalArgs, 0, nil)
|
|
_ = symbol
|
|
params := GetArg(optionalArgs, 1, map[string]interface{} {})
|
|
_ = params
|
|
|
|
retRes19248 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes19248)
|
|
var cid interface{} = this.SafeValue2(params, "cid", "clientOrderId") // client order id
|
|
var request interface{} = nil
|
|
var market interface{} = nil
|
|
if IsTrue(!IsEqual(symbol, nil)) {
|
|
market = this.Market(symbol)
|
|
}
|
|
if IsTrue(!IsEqual(cid, nil)) {
|
|
var cidDate interface{} = this.SafeValue(params, "cidDate") // client order id date
|
|
if IsTrue(IsEqual(cidDate, nil)) {
|
|
panic(InvalidOrder(Add(this.Id, " canceling an order by clientOrderId (\\'cid\\') requires both \\'cid\\' and \\'cid_date\\' (\\'YYYY-MM-DD\\')")))
|
|
}
|
|
request = map[string]interface{} {
|
|
"cid": cid,
|
|
"cid_date": cidDate,
|
|
}
|
|
params = this.Omit(params, []interface{}{"cid", "clientOrderId"})
|
|
} else {
|
|
request = map[string]interface{} {
|
|
"id": ParseInt(id),
|
|
}
|
|
}
|
|
|
|
response:= (<-this.PrivatePostAuthWOrderCancel(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
var order interface{} = this.SafeValue(response, 4)
|
|
var newOrder interface{} = map[string]interface{} {
|
|
"result": order,
|
|
}
|
|
|
|
ch <- this.ParseOrder(newOrder, market)
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitfinex#cancelOrders
|
|
* @description cancel multiple orders at the same time
|
|
* @see https://docs.bitfinex.com/reference/rest-auth-cancel-orders-multiple
|
|
* @param {string[]} ids order ids
|
|
* @param {string} symbol unified market symbol, default is undefined
|
|
* @param {object} [params] extra parameters specific to the exchange API endpoint
|
|
* @returns {object} an array of [order structures]{@link https://docs.ccxt.com/#/?id=order-structure}
|
|
*/
|
|
func (this *bitfinex) CancelOrders(ids interface{}, optionalArgs ...interface{}) <- chan interface{} {
|
|
ch := make(chan interface{})
|
|
go func() interface{} {
|
|
defer close(ch)
|
|
defer ReturnPanicError(ch)
|
|
symbol := GetArg(optionalArgs, 0, nil)
|
|
_ = symbol
|
|
params := GetArg(optionalArgs, 1, map[string]interface{} {})
|
|
_ = params
|
|
|
|
retRes19638 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes19638)
|
|
for i := 0; IsLessThan(i, GetArrayLength(ids)); i++ {
|
|
AddElementToObject(ids, i, this.ParseToNumeric(GetValue(ids, i)))
|
|
}
|
|
var request interface{} = map[string]interface{} {
|
|
"id": ids,
|
|
}
|
|
var market interface{} = nil
|
|
if IsTrue(!IsEqual(symbol, nil)) {
|
|
market = this.Market(symbol)
|
|
}
|
|
|
|
response:= (<-this.PrivatePostAuthWOrderCancelMulti(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
//
|
|
// [
|
|
// 1706740198811,
|
|
// "oc_multi-req",
|
|
// null,
|
|
// null,
|
|
// [
|
|
// [
|
|
// 139530205057,
|
|
// null,
|
|
// 1706740132275,
|
|
// "tBTCF0:USTF0",
|
|
// 1706740132276,
|
|
// 1706740132276,
|
|
// 0.0001,
|
|
// 0.0001,
|
|
// "LIMIT",
|
|
// null,
|
|
// null,
|
|
// null,
|
|
// 0,
|
|
// "ACTIVE",
|
|
// null,
|
|
// null,
|
|
// 39000,
|
|
// 0,
|
|
// 0,
|
|
// 0,
|
|
// null,
|
|
// null,
|
|
// null,
|
|
// 0,
|
|
// 0,
|
|
// null,
|
|
// null,
|
|
// null,
|
|
// "API>BFX",
|
|
// null,
|
|
// null,
|
|
// {
|
|
// "lev": 10,
|
|
// "$F33": 10
|
|
// }
|
|
// ],
|
|
// ],
|
|
// null,
|
|
// "SUCCESS",
|
|
// "Submitting 2 order cancellations."
|
|
// ]
|
|
//
|
|
var orders interface{} = this.SafeList(response, 4, []interface{}{})
|
|
var ordersList interface{} = []interface{}{}
|
|
for i := 0; IsLessThan(i, GetArrayLength(orders)); i++ {
|
|
AppendToArray(&ordersList,map[string]interface{} {
|
|
"result": GetValue(orders, i),
|
|
})
|
|
}
|
|
|
|
ch <- this.ParseOrders(ordersList, market)
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitfinex#fetchOpenOrder
|
|
* @description fetch an open order by it's id
|
|
* @see https://docs.bitfinex.com/reference/rest-auth-retrieve-orders
|
|
* @see https://docs.bitfinex.com/reference/rest-auth-retrieve-orders-by-symbol
|
|
* @param {string} id order id
|
|
* @param {string} symbol unified market symbol, default is undefined
|
|
* @param {object} [params] extra parameters specific to the exchange API endpoint
|
|
* @returns {object} an [order structure]{@link https://docs.ccxt.com/#/?id=order-structure}
|
|
*/
|
|
func (this *bitfinex) FetchOpenOrder(id interface{}, optionalArgs ...interface{}) <- chan interface{} {
|
|
ch := make(chan interface{})
|
|
go func() interface{} {
|
|
defer close(ch)
|
|
defer ReturnPanicError(ch)
|
|
symbol := GetArg(optionalArgs, 0, nil)
|
|
_ = symbol
|
|
params := GetArg(optionalArgs, 1, map[string]interface{} {})
|
|
_ = params
|
|
var request interface{} = map[string]interface{} {
|
|
"id": []interface{}{ParseInt(id)},
|
|
}
|
|
|
|
orders:= (<-this.FetchOpenOrders(symbol, nil, nil, this.Extend(request, params)))
|
|
PanicOnError(orders)
|
|
var order interface{} = this.SafeValue(orders, 0)
|
|
if IsTrue(IsEqual(order, nil)) {
|
|
panic(OrderNotFound(Add(Add(Add(this.Id, " order "), id), " not found")))
|
|
}
|
|
|
|
ch <- order
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitfinex#fetchClosedOrder
|
|
* @description fetch an open order by it's id
|
|
* @see https://docs.bitfinex.com/reference/rest-auth-retrieve-orders
|
|
* @see https://docs.bitfinex.com/reference/rest-auth-retrieve-orders-by-symbol
|
|
* @param {string} id order id
|
|
* @param {string} symbol unified market symbol, default is undefined
|
|
* @param {object} [params] extra parameters specific to the exchange API endpoint
|
|
* @returns {object} an [order structure]{@link https://docs.ccxt.com/#/?id=order-structure}
|
|
*/
|
|
func (this *bitfinex) FetchClosedOrder(id interface{}, optionalArgs ...interface{}) <- chan interface{} {
|
|
ch := make(chan interface{})
|
|
go func() interface{} {
|
|
defer close(ch)
|
|
defer ReturnPanicError(ch)
|
|
symbol := GetArg(optionalArgs, 0, nil)
|
|
_ = symbol
|
|
params := GetArg(optionalArgs, 1, map[string]interface{} {})
|
|
_ = params
|
|
var request interface{} = map[string]interface{} {
|
|
"id": []interface{}{ParseInt(id)},
|
|
}
|
|
|
|
orders:= (<-this.FetchClosedOrders(symbol, nil, nil, this.Extend(request, params)))
|
|
PanicOnError(orders)
|
|
var order interface{} = this.SafeValue(orders, 0)
|
|
if IsTrue(IsEqual(order, nil)) {
|
|
panic(OrderNotFound(Add(Add(Add(this.Id, " order "), id), " not found")))
|
|
}
|
|
|
|
ch <- order
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitfinex#fetchOpenOrders
|
|
* @description fetch all unfilled currently open orders
|
|
* @see https://docs.bitfinex.com/reference/rest-auth-retrieve-orders
|
|
* @see https://docs.bitfinex.com/reference/rest-auth-retrieve-orders-by-symbol
|
|
* @param {string} symbol unified market symbol
|
|
* @param {int} [since] the earliest time in ms to fetch open orders for
|
|
* @param {int} [limit] the maximum number of open orders structures to retrieve
|
|
* @param {object} [params] extra parameters specific to the exchange API endpoint
|
|
* @returns {Order[]} a list of [order structures]{@link https://docs.ccxt.com/#/?id=order-structure}
|
|
*/
|
|
func (this *bitfinex) FetchOpenOrders(optionalArgs ...interface{}) <- chan interface{} {
|
|
ch := make(chan interface{})
|
|
go func() interface{} {
|
|
defer close(ch)
|
|
defer ReturnPanicError(ch)
|
|
symbol := GetArg(optionalArgs, 0, nil)
|
|
_ = symbol
|
|
since := GetArg(optionalArgs, 1, nil)
|
|
_ = since
|
|
limit := GetArg(optionalArgs, 2, nil)
|
|
_ = limit
|
|
params := GetArg(optionalArgs, 3, map[string]interface{} {})
|
|
_ = params
|
|
|
|
retRes20928 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes20928)
|
|
var request interface{} = map[string]interface{} {}
|
|
var market interface{} = nil
|
|
var response interface{} = nil
|
|
if IsTrue(IsEqual(symbol, nil)) {
|
|
|
|
response = (<-this.PrivatePostAuthROrders(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
} else {
|
|
market = this.Market(symbol)
|
|
AddElementToObject(request, "symbol", GetValue(market, "id"))
|
|
|
|
response = (<-this.PrivatePostAuthROrdersSymbol(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
}
|
|
//
|
|
// [
|
|
// [
|
|
// 95408916206, // Order ID
|
|
// null, // Group Order ID
|
|
// 1653322349926, // Client Order ID
|
|
// "tDOGE:UST", // Market ID
|
|
// 1653322349926, // Created Timestamp in milliseconds
|
|
// 1653322349927, // Updated Timestamp in milliseconds
|
|
// -10, // Amount remaining (Positive means buy, negative means sell)
|
|
// -10, // Original amount
|
|
// "EXCHANGE LIMIT", // Order type
|
|
// null, // Previous Order Type
|
|
// null, // _PLACEHOLDER
|
|
// null, // _PLACEHOLDER
|
|
// 0, // Flags, see parseOrderFlags()
|
|
// "ACTIVE", // Order Status, see parseOrderStatus()
|
|
// null, // _PLACEHOLDER
|
|
// null, // _PLACEHOLDER
|
|
// 0.11, // Price
|
|
// 0, // Average Price
|
|
// 0, // Trailing Price
|
|
// 0, // Auxiliary Limit price (for STOP LIMIT)
|
|
// null, // _PLACEHOLDER
|
|
// null, // _PLACEHOLDER
|
|
// null, // _PLACEHOLDER
|
|
// 0, // Hidden (0 if false, 1 if true)
|
|
// 0, // Placed ID (If another order caused this order to be placed (OCO) this will be that other order's ID)
|
|
// null, // _PLACEHOLDER
|
|
// null, // _PLACEHOLDER
|
|
// null, // _PLACEHOLDER
|
|
// "API>BFX", // Routing, indicates origin of action: BFX, ETHFX, API>BFX, API>ETHFX
|
|
// null, // _PLACEHOLDER
|
|
// null, // _PLACEHOLDER
|
|
// {"$F7":1} // additional meta information about the order ( $F7 = IS_POST_ONLY (0 if false, 1 if true), $F33 = Leverage (int))
|
|
// ],
|
|
// ]
|
|
//
|
|
var ordersList interface{} = []interface{}{}
|
|
for i := 0; IsLessThan(i, GetArrayLength(response)); i++ {
|
|
AppendToArray(&ordersList,map[string]interface{} {
|
|
"result": GetValue(response, i),
|
|
})
|
|
}
|
|
|
|
ch <- this.ParseOrders(ordersList, market, since, limit)
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitfinex#fetchClosedOrders
|
|
* @description fetches information on multiple closed orders made by the user
|
|
* @see https://docs.bitfinex.com/reference/rest-auth-retrieve-orders
|
|
* @see https://docs.bitfinex.com/reference/rest-auth-retrieve-orders-by-symbol
|
|
* @param {string} symbol unified market symbol of the market orders were made in
|
|
* @param {int} [since] the earliest time in ms to fetch orders for
|
|
* @param {int} [limit] the maximum number of order structures to retrieve
|
|
* @param {object} [params] extra parameters specific to the exchange API endpoint
|
|
* @param {int} [params.until] the latest time in ms to fetch entries for
|
|
* @param {boolean} [params.paginate] default false, when true will automatically paginate by calling this endpoint multiple times. See in the docs all the [availble parameters](https://github.com/ccxt/ccxt/wiki/Manual#pagination-params)
|
|
* @returns {Order[]} a list of [order structures]{@link https://docs.ccxt.com/#/?id=order-structure}
|
|
*/
|
|
func (this *bitfinex) FetchClosedOrders(optionalArgs ...interface{}) <- chan interface{} {
|
|
ch := make(chan interface{})
|
|
go func() interface{} {
|
|
defer close(ch)
|
|
defer ReturnPanicError(ch)
|
|
// returns the most recent closed or canceled orders up to circa two weeks ago
|
|
symbol := GetArg(optionalArgs, 0, nil)
|
|
_ = symbol
|
|
since := GetArg(optionalArgs, 1, nil)
|
|
_ = since
|
|
limit := GetArg(optionalArgs, 2, nil)
|
|
_ = limit
|
|
params := GetArg(optionalArgs, 3, map[string]interface{} {})
|
|
_ = params
|
|
|
|
retRes21648 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes21648)
|
|
var paginate interface{} = false
|
|
paginateparamsVariable := this.HandleOptionAndParams(params, "fetchClosedOrders", "paginate");
|
|
paginate = GetValue(paginateparamsVariable,0);
|
|
params = GetValue(paginateparamsVariable,1)
|
|
if IsTrue(paginate) {
|
|
|
|
retRes216819 := (<-this.FetchPaginatedCallDynamic("fetchClosedOrders", symbol, since, limit, params))
|
|
PanicOnError(retRes216819)
|
|
ch <- retRes216819
|
|
return nil
|
|
}
|
|
var request interface{} = map[string]interface{} {}
|
|
if IsTrue(!IsEqual(since, nil)) {
|
|
AddElementToObject(request, "start", since)
|
|
}
|
|
if IsTrue(!IsEqual(limit, nil)) {
|
|
AddElementToObject(request, "limit", limit) // default 25, max 2500
|
|
}
|
|
requestparamsVariable := this.HandleUntilOption("end", request, params);
|
|
request = GetValue(requestparamsVariable,0);
|
|
params = GetValue(requestparamsVariable,1)
|
|
var market interface{} = nil
|
|
var response interface{} = nil
|
|
if IsTrue(IsEqual(symbol, nil)) {
|
|
|
|
response = (<-this.PrivatePostAuthROrdersHist(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
} else {
|
|
market = this.Market(symbol)
|
|
AddElementToObject(request, "symbol", GetValue(market, "id"))
|
|
|
|
response = (<-this.PrivatePostAuthROrdersSymbolHist(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
}
|
|
//
|
|
// [
|
|
// [
|
|
// 95412102131, // Order ID
|
|
// null, // Group Order ID
|
|
// 1653325121798, // Client Order ID
|
|
// "tDOGE:UST", // Market ID
|
|
// 1653325122000, // Created Timestamp in milliseconds
|
|
// 1653325122000, // Updated Timestamp in milliseconds
|
|
// -10, // Amount remaining (Positive means buy, negative means sell)
|
|
// -10, // Original amount
|
|
// "EXCHANGE LIMIT", // Order type
|
|
// null, // Previous Order Type
|
|
// null, // Millisecond timestamp of Time-In-Force: automatic order cancellation
|
|
// null, // _PLACEHOLDER
|
|
// "4096", // Flags, see parseOrderFlags()
|
|
// "POSTONLY CANCELED", // Order Status, see parseOrderStatus()
|
|
// null, // _PLACEHOLDER
|
|
// null, // _PLACEHOLDER
|
|
// 0.071, // Price
|
|
// 0, // Average Price
|
|
// 0, // Trailing Price
|
|
// 0, // Auxiliary Limit price (for STOP LIMIT)
|
|
// null, // _PLACEHOLDER
|
|
// null, // _PLACEHOLDER
|
|
// null, // _PLACEHOLDER
|
|
// 0, // Notify (0 if false, 1 if true)
|
|
// 0, // Hidden (0 if false, 1 if true)
|
|
// null, // Placed ID (If another order caused this order to be placed (OCO) this will be that other order's ID)
|
|
// null, // _PLACEHOLDER
|
|
// null, // _PLACEHOLDER
|
|
// "API>BFX", // Routing, indicates origin of action: BFX, ETHFX, API>BFX, API>ETHFX
|
|
// null, // _PLACEHOLDER
|
|
// null, // _PLACEHOLDER
|
|
// {"_$F7":1} // additional meta information about the order ( _$F7 = IS_POST_ONLY (0 if false, 1 if true), _$F33 = Leverage (int))
|
|
// ]
|
|
// ]
|
|
//
|
|
var ordersList interface{} = []interface{}{}
|
|
for i := 0; IsLessThan(i, GetArrayLength(response)); i++ {
|
|
AppendToArray(&ordersList,map[string]interface{} {
|
|
"result": GetValue(response, i),
|
|
})
|
|
}
|
|
|
|
ch <- this.ParseOrders(ordersList, market, since, limit)
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitfinex#fetchOrderTrades
|
|
* @description fetch all the trades made from a single order
|
|
* @see https://docs.bitfinex.com/reference/rest-auth-order-trades
|
|
* @param {string} id order id
|
|
* @param {string} symbol unified market symbol
|
|
* @param {int} [since] the earliest time in ms to fetch trades for
|
|
* @param {int} [limit] the maximum number of trades to retrieve
|
|
* @param {object} [params] extra parameters specific to the exchange API endpoint
|
|
* @returns {object[]} a list of [trade structures]{@link https://docs.ccxt.com/#/?id=trade-structure}
|
|
*/
|
|
func (this *bitfinex) FetchOrderTrades(id interface{}, optionalArgs ...interface{}) <- chan interface{} {
|
|
ch := make(chan interface{})
|
|
go func() interface{} {
|
|
defer close(ch)
|
|
defer ReturnPanicError(ch)
|
|
symbol := GetArg(optionalArgs, 0, nil)
|
|
_ = symbol
|
|
since := GetArg(optionalArgs, 1, nil)
|
|
_ = since
|
|
limit := GetArg(optionalArgs, 2, nil)
|
|
_ = limit
|
|
params := GetArg(optionalArgs, 3, map[string]interface{} {})
|
|
_ = params
|
|
if IsTrue(IsEqual(symbol, nil)) {
|
|
panic(ArgumentsRequired(Add(this.Id, " fetchOrderTrades() requires a symbol argument")))
|
|
}
|
|
|
|
retRes22488 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes22488)
|
|
var market interface{} = this.Market(symbol)
|
|
var orderId interface{} = ParseInt(id)
|
|
var request interface{} = map[string]interface{} {
|
|
"id": orderId,
|
|
"symbol": GetValue(market, "id"),
|
|
}
|
|
// valid for trades upto 10 days old
|
|
|
|
response:= (<-this.PrivatePostAuthROrderSymbolIdTrades(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
var tradesList interface{} = []interface{}{}
|
|
for i := 0; IsLessThan(i, GetArrayLength(response)); i++ {
|
|
AppendToArray(&tradesList,map[string]interface{} {
|
|
"result": GetValue(response, i),
|
|
}) // convert to array of dicts to match parseOrder signature
|
|
}
|
|
|
|
ch <- this.ParseTrades(tradesList, market, since, limit)
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitfinex#fetchMyTrades
|
|
* @description fetch all trades made by the user
|
|
* @see https://docs.bitfinex.com/reference/rest-auth-trades
|
|
* @see https://docs.bitfinex.com/reference/rest-auth-trades-by-symbol
|
|
* @param {string} symbol unified market symbol
|
|
* @param {int} [since] the earliest time in ms to fetch trades for
|
|
* @param {int} [limit] the maximum number of trades structures to retrieve
|
|
* @param {object} [params] extra parameters specific to the exchange API endpoint
|
|
* @returns {Trade[]} a list of [trade structures]{@link https://docs.ccxt.com/#/?id=trade-structure}
|
|
*/
|
|
func (this *bitfinex) FetchMyTrades(optionalArgs ...interface{}) <- chan interface{} {
|
|
ch := make(chan interface{})
|
|
go func() interface{} {
|
|
defer close(ch)
|
|
defer ReturnPanicError(ch)
|
|
symbol := GetArg(optionalArgs, 0, nil)
|
|
_ = symbol
|
|
since := GetArg(optionalArgs, 1, nil)
|
|
_ = since
|
|
limit := GetArg(optionalArgs, 2, nil)
|
|
_ = limit
|
|
params := GetArg(optionalArgs, 3, map[string]interface{} {})
|
|
_ = params
|
|
|
|
retRes22778 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes22778)
|
|
var market interface{} = nil
|
|
var request interface{} = map[string]interface{} {
|
|
"end": this.Milliseconds(),
|
|
}
|
|
if IsTrue(!IsEqual(since, nil)) {
|
|
AddElementToObject(request, "start", since)
|
|
}
|
|
if IsTrue(!IsEqual(limit, nil)) {
|
|
AddElementToObject(request, "limit", limit) // default 25, max 1000
|
|
}
|
|
var response interface{} = nil
|
|
if IsTrue(!IsEqual(symbol, nil)) {
|
|
market = this.Market(symbol)
|
|
AddElementToObject(request, "symbol", GetValue(market, "id"))
|
|
|
|
response = (<-this.PrivatePostAuthRTradesSymbolHist(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
} else {
|
|
|
|
response = (<-this.PrivatePostAuthRTradesHist(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
}
|
|
var tradesList interface{} = []interface{}{}
|
|
for i := 0; IsLessThan(i, GetArrayLength(response)); i++ {
|
|
AppendToArray(&tradesList,map[string]interface{} {
|
|
"result": GetValue(response, i),
|
|
}) // convert to array of dicts to match parseOrder signature
|
|
}
|
|
|
|
ch <- this.ParseTrades(tradesList, market, since, limit)
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitfinex#createDepositAddress
|
|
* @description create a currency deposit address
|
|
* @see https://docs.bitfinex.com/reference/rest-auth-deposit-address
|
|
* @param {string} code unified currency code of the currency for the deposit address
|
|
* @param {object} [params] extra parameters specific to the exchange API endpoint
|
|
* @returns {object} an [address structure]{@link https://docs.ccxt.com/#/?id=address-structure}
|
|
*/
|
|
func (this *bitfinex) CreateDepositAddress(code interface{}, optionalArgs ...interface{}) <- chan interface{} {
|
|
ch := make(chan interface{})
|
|
go func() interface{} {
|
|
defer close(ch)
|
|
defer ReturnPanicError(ch)
|
|
params := GetArg(optionalArgs, 0, map[string]interface{} {})
|
|
_ = params
|
|
|
|
retRes23138 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes23138)
|
|
var request interface{} = map[string]interface{} {
|
|
"op_renew": 1,
|
|
}
|
|
|
|
retRes231715 := (<-this.FetchDepositAddress(code, this.Extend(request, params)))
|
|
PanicOnError(retRes231715)
|
|
ch <- retRes231715
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitfinex#fetchDepositAddress
|
|
* @description fetch the deposit address for a currency associated with this account
|
|
* @see https://docs.bitfinex.com/reference/rest-auth-deposit-address
|
|
* @param {string} code unified currency code
|
|
* @param {object} [params] extra parameters specific to the exchange API endpoint
|
|
* @returns {object} an [address structure]{@link https://docs.ccxt.com/#/?id=address-structure}
|
|
*/
|
|
func (this *bitfinex) FetchDepositAddress(code interface{}, optionalArgs ...interface{}) <- chan interface{} {
|
|
ch := make(chan interface{})
|
|
go func() interface{} {
|
|
defer close(ch)
|
|
defer ReturnPanicError(ch)
|
|
params := GetArg(optionalArgs, 0, map[string]interface{} {})
|
|
_ = params
|
|
|
|
retRes23308 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes23308)
|
|
var currency interface{} = this.Currency(code)
|
|
// if not provided explicitly we will try to match using the currency name
|
|
var network interface{} = this.SafeString(params, "network", code)
|
|
var currencyNetworks interface{} = this.SafeValue(currency, "networks", map[string]interface{} {})
|
|
var currencyNetwork interface{} = this.SafeValue(currencyNetworks, network)
|
|
var networkId interface{} = this.SafeString(currencyNetwork, "id")
|
|
if IsTrue(IsEqual(networkId, nil)) {
|
|
panic(ArgumentsRequired(Add(Add(Add(this.Id, " fetchDepositAddress() could not find a network for \\'"), code), "\\'. You can specify it by providing the \\'network\\' value inside params")))
|
|
}
|
|
var wallet interface{} = this.SafeString(params, "wallet", "exchange") // 'exchange', 'margin', 'funding' and also old labels 'exchange', 'trading', 'deposit', respectively
|
|
params = this.Omit(params, "network", "wallet")
|
|
var request interface{} = map[string]interface{} {
|
|
"method": networkId,
|
|
"wallet": wallet,
|
|
"op_renew": 0,
|
|
}
|
|
|
|
response:= (<-this.PrivatePostAuthWDepositAddress(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
//
|
|
// [
|
|
// 1582269616687, // MTS Millisecond Time Stamp of the update
|
|
// "acc_dep", // TYPE Purpose of notification "acc_dep" for account deposit
|
|
// null, // MESSAGE_ID unique ID of the message
|
|
// null, // not documented
|
|
// [
|
|
// null, // PLACEHOLDER
|
|
// "BITCOIN", // METHOD Method of deposit
|
|
// "BTC", // CURRENCY_CODE Currency code of new address
|
|
// null, // PLACEHOLDER
|
|
// "1BC9PZqpUmjyEB54uggn8TFKj49zSDYzqG", // ADDRESS
|
|
// null, // POOL_ADDRESS
|
|
// ],
|
|
// null, // CODE null or integer work in progress
|
|
// "SUCCESS", // STATUS Status of the notification, SUCCESS, ERROR, FAILURE
|
|
// "success", // TEXT Text of the notification
|
|
// ]
|
|
//
|
|
var result interface{} = this.SafeValue(response, 4, []interface{}{})
|
|
var poolAddress interface{} = this.SafeString(result, 5)
|
|
var address interface{} = Ternary(IsTrue((IsEqual(poolAddress, nil))), this.SafeString(result, 4), poolAddress)
|
|
var tag interface{} = Ternary(IsTrue((IsEqual(poolAddress, nil))), nil, this.SafeString(result, 4))
|
|
this.CheckAddress(address)
|
|
|
|
ch <- map[string]interface{} {
|
|
"currency": code,
|
|
"address": address,
|
|
"tag": tag,
|
|
"network": nil,
|
|
"info": response,
|
|
}
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
func (this *bitfinex) ParseTransactionStatus(status interface{}) interface{} {
|
|
var statuses interface{} = map[string]interface{} {
|
|
"SUCCESS": "ok",
|
|
"COMPLETED": "ok",
|
|
"ERROR": "failed",
|
|
"FAILURE": "failed",
|
|
"CANCELED": "canceled",
|
|
"PENDING APPROVAL": "pending",
|
|
"PENDING": "pending",
|
|
"PENDING REVIEW": "pending",
|
|
"PENDING CANCELLATION": "pending",
|
|
"SENDING": "pending",
|
|
"USER APPROVED": "pending",
|
|
}
|
|
return this.SafeString(statuses, status, status)
|
|
}
|
|
func (this *bitfinex) ParseTransaction(transaction interface{}, optionalArgs ...interface{}) interface{} {
|
|
//
|
|
// withdraw
|
|
//
|
|
// [
|
|
// 1582271520931, // MTS Millisecond Time Stamp of the update
|
|
// "acc_wd-req", // TYPE Purpose of notification "acc_wd-req" account withdrawal request
|
|
// null, // MESSAGE_ID unique ID of the message
|
|
// null, // not documented
|
|
// [
|
|
// 0, // WITHDRAWAL_ID Unique Withdrawal ID
|
|
// null, // PLACEHOLDER
|
|
// "bitcoin", // METHOD Method of withdrawal
|
|
// null, // PAYMENT_ID Payment ID if relevant
|
|
// "exchange", // WALLET Sending wallet
|
|
// 1, // AMOUNT Amount of Withdrawal less fee
|
|
// null, // PLACEHOLDER
|
|
// null, // PLACEHOLDER
|
|
// 0.0004, // WITHDRAWAL_FEE Fee on withdrawal
|
|
// ],
|
|
// null, // CODE null or integer Work in progress
|
|
// "SUCCESS", // STATUS Status of the notification, it may vary over time SUCCESS, ERROR, FAILURE
|
|
// "Invalid bitcoin address (abcdef)", // TEXT Text of the notification
|
|
// ]
|
|
//
|
|
// fetchDepositsWithdrawals
|
|
//
|
|
// [
|
|
// 13293039, // ID
|
|
// "ETH", // CURRENCY
|
|
// "ETHEREUM", // CURRENCY_NAME
|
|
// null,
|
|
// null,
|
|
// 1574175052000, // MTS_STARTED
|
|
// 1574181326000, // MTS_UPDATED
|
|
// null,
|
|
// null,
|
|
// "CANCELED", // STATUS
|
|
// null,
|
|
// null,
|
|
// -0.24, // AMOUNT, negative for withdrawals
|
|
// -0.00135, // FEES
|
|
// null,
|
|
// null,
|
|
// "0x38110e0Fc932CB2BE...........", // DESTINATION_ADDRESS
|
|
// null,
|
|
// null,
|
|
// null,
|
|
// "0x523ec8945500.....................................", // TRANSACTION_ID
|
|
// "Purchase of 100 pizzas", // WITHDRAW_TRANSACTION_NOTE, might also be: null
|
|
// ]
|
|
//
|
|
currency := GetArg(optionalArgs, 0, nil)
|
|
_ = currency
|
|
var transactionLength interface{} = GetArrayLength(transaction)
|
|
var timestamp interface{} = nil
|
|
var updated interface{} = nil
|
|
var code interface{} = nil
|
|
var amount interface{} = nil
|
|
var id interface{} = nil
|
|
var status interface{} = nil
|
|
var tag interface{} = nil
|
|
var typeVar interface{} = nil
|
|
var feeCost interface{} = nil
|
|
var txid interface{} = nil
|
|
var addressTo interface{} = nil
|
|
var network interface{} = nil
|
|
var comment interface{} = nil
|
|
if IsTrue(IsEqual(transactionLength, 8)) {
|
|
var data interface{} = this.SafeValue(transaction, 4, []interface{}{})
|
|
timestamp = this.SafeInteger(transaction, 0)
|
|
if IsTrue(!IsEqual(currency, nil)) {
|
|
code = GetValue(currency, "code")
|
|
}
|
|
feeCost = this.SafeString(data, 8)
|
|
if IsTrue(!IsEqual(feeCost, nil)) {
|
|
feeCost = Precise.StringAbs(feeCost)
|
|
}
|
|
amount = this.SafeNumber(data, 5)
|
|
id = this.SafeInteger(data, 0)
|
|
status = "ok"
|
|
if IsTrue(IsEqual(id, 0)) {
|
|
id = nil
|
|
status = "failed"
|
|
}
|
|
tag = this.SafeString(data, 3)
|
|
typeVar = "withdrawal"
|
|
var networkId interface{} = this.SafeString(data, 2)
|
|
network = this.NetworkIdToCode(ToUpper(networkId)) // withdraw returns in lowercase
|
|
} else if IsTrue(IsEqual(transactionLength, 22)) {
|
|
id = this.SafeString(transaction, 0)
|
|
var currencyId interface{} = this.SafeString(transaction, 1)
|
|
code = this.SafeCurrencyCode(currencyId, currency)
|
|
var networkId interface{} = this.SafeString(transaction, 2)
|
|
network = this.NetworkIdToCode(networkId)
|
|
timestamp = this.SafeInteger(transaction, 5)
|
|
updated = this.SafeInteger(transaction, 6)
|
|
status = this.ParseTransactionStatus(this.SafeString(transaction, 9))
|
|
var signedAmount interface{} = this.SafeString(transaction, 12)
|
|
amount = Precise.StringAbs(signedAmount)
|
|
if IsTrue(!IsEqual(signedAmount, nil)) {
|
|
if IsTrue(Precise.StringLt(signedAmount, "0")) {
|
|
typeVar = "withdrawal"
|
|
} else {
|
|
typeVar = "deposit"
|
|
}
|
|
}
|
|
feeCost = this.SafeString(transaction, 13)
|
|
if IsTrue(!IsEqual(feeCost, nil)) {
|
|
feeCost = Precise.StringAbs(feeCost)
|
|
}
|
|
addressTo = this.SafeString(transaction, 16)
|
|
txid = this.SafeString(transaction, 20)
|
|
comment = this.SafeString(transaction, 21)
|
|
}
|
|
return map[string]interface{} {
|
|
"info": transaction,
|
|
"id": id,
|
|
"txid": txid,
|
|
"type": typeVar,
|
|
"currency": code,
|
|
"network": network,
|
|
"amount": this.ParseNumber(amount),
|
|
"status": status,
|
|
"timestamp": timestamp,
|
|
"datetime": this.Iso8601(timestamp),
|
|
"address": addressTo,
|
|
"addressFrom": nil,
|
|
"addressTo": addressTo,
|
|
"tag": tag,
|
|
"tagFrom": nil,
|
|
"tagTo": tag,
|
|
"updated": updated,
|
|
"comment": comment,
|
|
"internal": nil,
|
|
"fee": map[string]interface{} {
|
|
"currency": code,
|
|
"cost": this.ParseNumber(feeCost),
|
|
"rate": nil,
|
|
},
|
|
}
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitfinex#fetchTradingFees
|
|
* @description fetch the trading fees for multiple markets
|
|
* @see https://docs.bitfinex.com/reference/rest-auth-summary
|
|
* @param {object} [params] extra parameters specific to the exchange API endpoint
|
|
* @returns {object} a dictionary of [fee structures]{@link https://docs.ccxt.com/#/?id=fee-structure} indexed by market symbols
|
|
*/
|
|
func (this *bitfinex) FetchTradingFees(optionalArgs ...interface{}) <- chan interface{} {
|
|
ch := make(chan interface{})
|
|
go func() interface{} {
|
|
defer close(ch)
|
|
defer ReturnPanicError(ch)
|
|
params := GetArg(optionalArgs, 0, map[string]interface{} {})
|
|
_ = params
|
|
|
|
retRes25488 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes25488)
|
|
|
|
response:= (<-this.PrivatePostAuthRSummary(params))
|
|
PanicOnError(response)
|
|
//
|
|
// Response Spec:
|
|
// [
|
|
// PLACEHOLDER,
|
|
// PLACEHOLDER,
|
|
// PLACEHOLDER,
|
|
// PLACEHOLDER,
|
|
// [
|
|
// [
|
|
// MAKER_FEE,
|
|
// MAKER_FEE,
|
|
// MAKER_FEE,
|
|
// PLACEHOLDER,
|
|
// PLACEHOLDER,
|
|
// DERIV_REBATE
|
|
// ],
|
|
// [
|
|
// TAKER_FEE_TO_CRYPTO,
|
|
// TAKER_FEE_TO_STABLE,
|
|
// TAKER_FEE_TO_FIAT,
|
|
// PLACEHOLDER,
|
|
// PLACEHOLDER,
|
|
// DERIV_TAKER_FEE
|
|
// ]
|
|
// ],
|
|
// PLACEHOLDER,
|
|
// PLACEHOLDER,
|
|
// PLACEHOLDER,
|
|
// PLACEHOLDER,
|
|
// {
|
|
// LEO_LEV,
|
|
// LEO_AMOUNT_AVG
|
|
// }
|
|
// ]
|
|
//
|
|
// Example response:
|
|
//
|
|
// [
|
|
// null,
|
|
// null,
|
|
// null,
|
|
// null,
|
|
// [
|
|
// [ 0.001, 0.001, 0.001, null, null, 0.0002 ],
|
|
// [ 0.002, 0.002, 0.002, null, null, 0.00065 ]
|
|
// ],
|
|
// [
|
|
// [
|
|
// {
|
|
// "curr": "Total (USD)",
|
|
// "vol": "0",
|
|
// "vol_safe": "0",
|
|
// "vol_maker": "0",
|
|
// "vol_BFX": "0",
|
|
// "vol_BFX_safe": "0",
|
|
// "vol_BFX_maker": "0"
|
|
// }
|
|
// ],
|
|
// {},
|
|
// 0
|
|
// ],
|
|
// [ null, {}, 0 ],
|
|
// null,
|
|
// null,
|
|
// { leo_lev: "0", leo_amount_avg: "0" }
|
|
// ]
|
|
//
|
|
var result interface{} = map[string]interface{} {}
|
|
var fiat interface{} = this.SafeValue(this.Options, "fiat", map[string]interface{} {})
|
|
var feeData interface{} = this.SafeValue(response, 4, []interface{}{})
|
|
var makerData interface{} = this.SafeValue(feeData, 0, []interface{}{})
|
|
var takerData interface{} = this.SafeValue(feeData, 1, []interface{}{})
|
|
var makerFee interface{} = this.SafeNumber(makerData, 0)
|
|
var makerFeeFiat interface{} = this.SafeNumber(makerData, 2)
|
|
var makerFeeDeriv interface{} = this.SafeNumber(makerData, 5)
|
|
var takerFee interface{} = this.SafeNumber(takerData, 0)
|
|
var takerFeeFiat interface{} = this.SafeNumber(takerData, 2)
|
|
var takerFeeDeriv interface{} = this.SafeNumber(takerData, 5)
|
|
for i := 0; IsLessThan(i, GetArrayLength(this.Symbols)); i++ {
|
|
var symbol interface{} = GetValue(this.Symbols, i)
|
|
var market interface{} = this.Market(symbol)
|
|
var fee interface{} = map[string]interface{} {
|
|
"info": response,
|
|
"symbol": symbol,
|
|
"percentage": true,
|
|
"tierBased": true,
|
|
}
|
|
if IsTrue(InOp(fiat, GetValue(market, "quote"))) {
|
|
AddElementToObject(fee, "maker", makerFeeFiat)
|
|
AddElementToObject(fee, "taker", takerFeeFiat)
|
|
} else if IsTrue(GetValue(market, "contract")) {
|
|
AddElementToObject(fee, "maker", makerFeeDeriv)
|
|
AddElementToObject(fee, "taker", takerFeeDeriv)
|
|
} else {
|
|
AddElementToObject(fee, "maker", makerFee)
|
|
AddElementToObject(fee, "taker", takerFee)
|
|
}
|
|
AddElementToObject(result, symbol, fee)
|
|
}
|
|
|
|
ch <- result
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitfinex#fetchDepositsWithdrawals
|
|
* @description fetch history of deposits and withdrawals
|
|
* @see https://docs.bitfinex.com/reference/movement-info
|
|
* @see https://docs.bitfinex.com/reference/rest-auth-movements
|
|
* @param {string} [code] unified currency code for the currency of the deposit/withdrawals, default is undefined
|
|
* @param {int} [since] timestamp in ms of the earliest deposit/withdrawal, default is undefined
|
|
* @param {int} [limit] max number of deposit/withdrawals to return, default is undefined
|
|
* @param {object} [params] extra parameters specific to the exchange API endpoint
|
|
* @returns {object} a list of [transaction structure]{@link https://docs.ccxt.com/#/?id=transaction-structure}
|
|
*/
|
|
func (this *bitfinex) FetchDepositsWithdrawals(optionalArgs ...interface{}) <- chan interface{} {
|
|
ch := make(chan interface{})
|
|
go func() interface{} {
|
|
defer close(ch)
|
|
defer ReturnPanicError(ch)
|
|
code := GetArg(optionalArgs, 0, nil)
|
|
_ = code
|
|
since := GetArg(optionalArgs, 1, nil)
|
|
_ = since
|
|
limit := GetArg(optionalArgs, 2, nil)
|
|
_ = limit
|
|
params := GetArg(optionalArgs, 3, map[string]interface{} {})
|
|
_ = params
|
|
|
|
retRes26658 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes26658)
|
|
var currency interface{} = nil
|
|
var request interface{} = map[string]interface{} {}
|
|
if IsTrue(!IsEqual(since, nil)) {
|
|
AddElementToObject(request, "start", since)
|
|
}
|
|
if IsTrue(!IsEqual(limit, nil)) {
|
|
AddElementToObject(request, "limit", limit) // max 1000
|
|
}
|
|
var response interface{} = nil
|
|
if IsTrue(!IsEqual(code, nil)) {
|
|
currency = this.Currency(code)
|
|
AddElementToObject(request, "currency", GetValue(currency, "uppercaseId"))
|
|
|
|
response = (<-this.PrivatePostAuthRMovementsCurrencyHist(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
} else {
|
|
|
|
response = (<-this.PrivatePostAuthRMovementsHist(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
}
|
|
|
|
//
|
|
// [
|
|
// [
|
|
// 13293039, // ID
|
|
// "ETH", // CURRENCY
|
|
// "ETHEREUM", // CURRENCY_NAME
|
|
// null,
|
|
// null,
|
|
// 1574175052000, // MTS_STARTED
|
|
// 1574181326000, // MTS_UPDATED
|
|
// null,
|
|
// null,
|
|
// "CANCELED", // STATUS
|
|
// null,
|
|
// null,
|
|
// -0.24, // AMOUNT, negative for withdrawals
|
|
// -0.00135, // FEES
|
|
// null,
|
|
// null,
|
|
// "0x38110e0Fc932CB2BE...........", // DESTINATION_ADDRESS
|
|
// null,
|
|
// null,
|
|
// null,
|
|
// "0x523ec8945500.....................................", // TRANSACTION_ID
|
|
// "Purchase of 100 pizzas", // WITHDRAW_TRANSACTION_NOTE, might also be: null
|
|
// ]
|
|
// ]
|
|
//
|
|
ch <- this.ParseTransactions(response, currency, since, limit)
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitfinex#withdraw
|
|
* @description make a withdrawal
|
|
* @see https://docs.bitfinex.com/reference/rest-auth-withdraw
|
|
* @param {string} code unified currency code
|
|
* @param {float} amount the amount to withdraw
|
|
* @param {string} address the address to withdraw to
|
|
* @param {string} tag
|
|
* @param {object} [params] extra parameters specific to the exchange API endpoint
|
|
* @returns {object} a [transaction structure]{@link https://docs.ccxt.com/#/?id=transaction-structure}
|
|
*/
|
|
func (this *bitfinex) Withdraw(code interface{}, amount interface{}, address interface{}, optionalArgs ...interface{}) <- chan interface{} {
|
|
ch := make(chan interface{})
|
|
go func() interface{} {
|
|
defer close(ch)
|
|
defer ReturnPanicError(ch)
|
|
tag := GetArg(optionalArgs, 0, nil)
|
|
_ = tag
|
|
params := GetArg(optionalArgs, 1, map[string]interface{} {})
|
|
_ = params
|
|
this.CheckAddress(address)
|
|
|
|
retRes27278 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes27278)
|
|
var currency interface{} = this.Currency(code)
|
|
// if not provided explicitly we will try to match using the currency name
|
|
var network interface{} = this.SafeString(params, "network", code)
|
|
params = this.Omit(params, "network")
|
|
var currencyNetworks interface{} = this.SafeValue(currency, "networks", map[string]interface{} {})
|
|
var currencyNetwork interface{} = this.SafeValue(currencyNetworks, network)
|
|
var networkId interface{} = this.SafeString(currencyNetwork, "id")
|
|
if IsTrue(IsEqual(networkId, nil)) {
|
|
panic(ArgumentsRequired(Add(Add(Add(this.Id, " withdraw() could not find a network for \\'"), code), "\\'. You can specify it by providing the \\'network\\' value inside params")))
|
|
}
|
|
var wallet interface{} = this.SafeString(params, "wallet", "exchange") // 'exchange', 'margin', 'funding' and also old labels 'exchange', 'trading', 'deposit', respectively
|
|
params = this.Omit(params, "network", "wallet")
|
|
var request interface{} = map[string]interface{} {
|
|
"method": networkId,
|
|
"wallet": wallet,
|
|
"amount": this.NumberToString(amount),
|
|
"address": address,
|
|
}
|
|
if IsTrue(!IsEqual(tag, nil)) {
|
|
AddElementToObject(request, "payment_id", tag)
|
|
}
|
|
var withdrawOptions interface{} = this.SafeValue(this.Options, "withdraw", map[string]interface{} {})
|
|
var includeFee interface{} = this.SafeBool(withdrawOptions, "includeFee", false)
|
|
if IsTrue(includeFee) {
|
|
AddElementToObject(request, "fee_deduct", 1)
|
|
}
|
|
|
|
response:= (<-this.PrivatePostAuthWWithdraw(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
//
|
|
// [
|
|
// 1582271520931, // MTS Millisecond Time Stamp of the update
|
|
// "acc_wd-req", // TYPE Purpose of notification "acc_wd-req" account withdrawal request
|
|
// null, // MESSAGE_ID unique ID of the message
|
|
// null, // not documented
|
|
// [
|
|
// 0, // WITHDRAWAL_ID Unique Withdrawal ID
|
|
// null, // PLACEHOLDER
|
|
// "bitcoin", // METHOD Method of withdrawal
|
|
// null, // PAYMENT_ID Payment ID if relevant
|
|
// "exchange", // WALLET Sending wallet
|
|
// 1, // AMOUNT Amount of Withdrawal less fee
|
|
// null, // PLACEHOLDER
|
|
// null, // PLACEHOLDER
|
|
// 0.0004, // WITHDRAWAL_FEE Fee on withdrawal
|
|
// ],
|
|
// null, // CODE null or integer Work in progress
|
|
// "SUCCESS", // STATUS Status of the notification, it may vary over time SUCCESS, ERROR, FAILURE
|
|
// "Invalid bitcoin address (abcdef)", // TEXT Text of the notification
|
|
// ]
|
|
//
|
|
// in case of failure:
|
|
//
|
|
// [
|
|
// "error",
|
|
// 10001,
|
|
// "Momentary balance check. Please wait few seconds and try the transfer again."
|
|
// ]
|
|
//
|
|
var statusMessage interface{} = this.SafeString(response, 0)
|
|
if IsTrue(IsEqual(statusMessage, "error")) {
|
|
var feedback interface{} = Add(Add(this.Id, " "), response)
|
|
var message interface{} = this.SafeString(response, 2, "")
|
|
// same message as in v1
|
|
this.ThrowExactlyMatchedException(GetValue(this.Exceptions, "exact"), message, feedback)
|
|
this.ThrowBroadlyMatchedException(GetValue(this.Exceptions, "broad"), message, feedback)
|
|
panic(ExchangeError(feedback))
|
|
}
|
|
var text interface{} = this.SafeString(response, 7)
|
|
if IsTrue(!IsEqual(text, "success")) {
|
|
this.ThrowBroadlyMatchedException(GetValue(this.Exceptions, "broad"), text, text)
|
|
}
|
|
|
|
ch <- this.ParseTransaction(response, currency)
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitfinex#fetchPositions
|
|
* @description fetch all open positions
|
|
* @see https://docs.bitfinex.com/reference/rest-auth-positions
|
|
* @param {string[]|undefined} symbols list of unified market symbols
|
|
* @param {object} [params] extra parameters specific to the exchange API endpoint
|
|
* @returns {object[]} a list of [position structure]{@link https://docs.ccxt.com/#/?id=position-structure}
|
|
*/
|
|
func (this *bitfinex) FetchPositions(optionalArgs ...interface{}) <- chan interface{} {
|
|
ch := make(chan interface{})
|
|
go func() interface{} {
|
|
defer close(ch)
|
|
defer ReturnPanicError(ch)
|
|
symbols := GetArg(optionalArgs, 0, nil)
|
|
_ = symbols
|
|
params := GetArg(optionalArgs, 1, map[string]interface{} {})
|
|
_ = params
|
|
|
|
retRes28118 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes28118)
|
|
symbols = this.MarketSymbols(symbols)
|
|
|
|
response:= (<-this.PrivatePostAuthRPositions(params))
|
|
PanicOnError(response)
|
|
//
|
|
// [
|
|
// [
|
|
// "tBTCUSD", // SYMBOL
|
|
// "ACTIVE", // STATUS
|
|
// 0.0195, // AMOUNT
|
|
// 8565.0267019, // BASE_PRICE
|
|
// 0, // MARGIN_FUNDING
|
|
// 0, // MARGIN_FUNDING_TYPE
|
|
// -0.33455568705000516, // PL
|
|
// -0.0003117550117425625, // PL_PERC
|
|
// 7045.876419249083, // PRICE_LIQ
|
|
// 3.0673001895895604, // LEVERAGE
|
|
// null, // _PLACEHOLDER
|
|
// 142355652, // POSITION_ID
|
|
// 1574002216000, // MTS_CREATE
|
|
// 1574002216000, // MTS_UPDATE
|
|
// null, // _PLACEHOLDER
|
|
// 0, // TYPE
|
|
// null, // _PLACEHOLDER
|
|
// 0, // COLLATERAL
|
|
// 0, // COLLATERAL_MIN
|
|
// // META
|
|
// {
|
|
// "reason":"TRADE",
|
|
// "order_id":34271018124,
|
|
// "liq_stage":null,
|
|
// "trade_price":"8565.0267019",
|
|
// "trade_amount":"0.0195",
|
|
// "order_id_oppo":34277498022
|
|
// }
|
|
// ]
|
|
// ]
|
|
//
|
|
var positionsList interface{} = []interface{}{}
|
|
for i := 0; IsLessThan(i, GetArrayLength(response)); i++ {
|
|
AppendToArray(&positionsList,map[string]interface{} {
|
|
"result": GetValue(response, i),
|
|
})
|
|
}
|
|
|
|
ch <- this.ParsePositions(positionsList, symbols)
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
func (this *bitfinex) ParsePosition(position interface{}, optionalArgs ...interface{}) interface{} {
|
|
//
|
|
// [
|
|
// "tBTCUSD", // SYMBOL
|
|
// "ACTIVE", // STATUS
|
|
// 0.0195, // AMOUNT
|
|
// 8565.0267019, // BASE_PRICE
|
|
// 0, // MARGIN_FUNDING
|
|
// 0, // MARGIN_FUNDING_TYPE
|
|
// -0.33455568705000516, // PL
|
|
// -0.0003117550117425625, // PL_PERC
|
|
// 7045.876419249083, // PRICE_LIQ
|
|
// 3.0673001895895604, // LEVERAGE
|
|
// null, // _PLACEHOLDER
|
|
// 142355652, // POSITION_ID
|
|
// 1574002216000, // MTS_CREATE
|
|
// 1574002216000, // MTS_UPDATE
|
|
// null, // _PLACEHOLDER
|
|
// 0, // TYPE
|
|
// null, // _PLACEHOLDER
|
|
// 0, // COLLATERAL
|
|
// 0, // COLLATERAL_MIN
|
|
// // META
|
|
// {
|
|
// "reason": "TRADE",
|
|
// "order_id": 34271018124,
|
|
// "liq_stage": null,
|
|
// "trade_price": "8565.0267019",
|
|
// "trade_amount": "0.0195",
|
|
// "order_id_oppo": 34277498022
|
|
// }
|
|
// ]
|
|
//
|
|
market := GetArg(optionalArgs, 0, nil)
|
|
_ = market
|
|
var positionList interface{} = this.SafeList(position, "result")
|
|
var marketId interface{} = this.SafeString(positionList, 0)
|
|
var amount interface{} = this.SafeString(positionList, 2)
|
|
var timestamp interface{} = this.SafeInteger(positionList, 12)
|
|
var meta interface{} = this.SafeString(positionList, 19)
|
|
var tradePrice interface{} = this.SafeString(meta, "trade_price")
|
|
var tradeAmount interface{} = this.SafeString(meta, "trade_amount")
|
|
return this.SafePosition(map[string]interface{} {
|
|
"info": positionList,
|
|
"id": this.SafeString(positionList, 11),
|
|
"symbol": this.SafeSymbol(marketId, market),
|
|
"notional": this.ParseNumber(amount),
|
|
"marginMode": "isolated",
|
|
"liquidationPrice": this.SafeNumber(positionList, 8),
|
|
"entryPrice": this.SafeNumber(positionList, 3),
|
|
"unrealizedPnl": this.SafeNumber(positionList, 6),
|
|
"percentage": this.SafeNumber(positionList, 7),
|
|
"contracts": nil,
|
|
"contractSize": nil,
|
|
"markPrice": nil,
|
|
"lastPrice": nil,
|
|
"side": Ternary(IsTrue(Precise.StringGt(amount, "0")), "long", "short"),
|
|
"hedged": nil,
|
|
"timestamp": timestamp,
|
|
"datetime": this.Iso8601(timestamp),
|
|
"lastUpdateTimestamp": this.SafeInteger(positionList, 13),
|
|
"maintenanceMargin": this.SafeNumber(positionList, 18),
|
|
"maintenanceMarginPercentage": nil,
|
|
"collateral": this.SafeNumber(positionList, 17),
|
|
"initialMargin": this.ParseNumber(Precise.StringMul(tradeAmount, tradePrice)),
|
|
"initialMarginPercentage": nil,
|
|
"leverage": this.SafeNumber(positionList, 9),
|
|
"marginRatio": nil,
|
|
"stopLossPrice": nil,
|
|
"takeProfitPrice": nil,
|
|
})
|
|
}
|
|
func (this *bitfinex) Nonce() interface{} {
|
|
return this.Milliseconds()
|
|
}
|
|
func (this *bitfinex) Sign(path interface{}, optionalArgs ...interface{}) interface{} {
|
|
api := GetArg(optionalArgs, 0, "public")
|
|
_ = api
|
|
method := GetArg(optionalArgs, 1, "GET")
|
|
_ = method
|
|
params := GetArg(optionalArgs, 2, map[string]interface{} {})
|
|
_ = params
|
|
headers := GetArg(optionalArgs, 3, nil)
|
|
_ = headers
|
|
body := GetArg(optionalArgs, 4, nil)
|
|
_ = body
|
|
var request interface{} = Add("/", this.ImplodeParams(path, params))
|
|
var query interface{} = this.Omit(params, this.ExtractParams(path))
|
|
if IsTrue(IsEqual(api, "v1")) {
|
|
request = Add(api, request)
|
|
} else {
|
|
request = Add(this.Version, request)
|
|
}
|
|
var url interface{} = Add(Add(GetValue(GetValue(this.Urls, "api"), api), "/"), request)
|
|
if IsTrue(IsEqual(api, "public")) {
|
|
if IsTrue(GetArrayLength(ObjectKeys(query))) {
|
|
url = Add(url, Add("?", this.Urlencode(query)))
|
|
}
|
|
}
|
|
if IsTrue(IsEqual(api, "private")) {
|
|
this.CheckRequiredCredentials()
|
|
var nonce interface{} = ToString(this.Nonce())
|
|
body = this.Json(query)
|
|
var auth interface{} = Add(Add(Add("/api/", request), nonce), body)
|
|
var signature interface{} = this.Hmac(this.Encode(auth), this.Encode(this.Secret), sha384)
|
|
headers = map[string]interface{} {
|
|
"bfx-nonce": nonce,
|
|
"bfx-apikey": this.ApiKey,
|
|
"bfx-signature": signature,
|
|
"Content-Type": "application/json",
|
|
}
|
|
}
|
|
return map[string]interface{} {
|
|
"url": url,
|
|
"method": method,
|
|
"body": body,
|
|
"headers": headers,
|
|
}
|
|
}
|
|
func (this *bitfinex) HandleErrors(statusCode interface{}, statusText interface{}, url interface{}, method interface{}, headers interface{}, body interface{}, response interface{}, requestHeaders interface{}, requestBody interface{}) interface{} {
|
|
// ["error", 11010, "ratelimit: error"]
|
|
if IsTrue(!IsEqual(response, nil)) {
|
|
if !IsTrue(IsArray(response)) {
|
|
var message interface{} = this.SafeString2(response, "message", "error")
|
|
var feedback interface{} = Add(Add(this.Id, " "), body)
|
|
this.ThrowExactlyMatchedException(GetValue(this.Exceptions, "exact"), message, feedback)
|
|
this.ThrowBroadlyMatchedException(GetValue(this.Exceptions, "broad"), message, feedback)
|
|
panic(ExchangeError(Add(Add(this.Id, " "), body)))
|
|
}
|
|
} else if IsTrue(IsEqual(response, "")) {
|
|
panic(ExchangeError(Add(this.Id, " returned empty response")))
|
|
}
|
|
if IsTrue(IsEqual(statusCode, 429)) {
|
|
panic(RateLimitExceeded(Add(Add(this.Id, " "), body)))
|
|
}
|
|
if IsTrue(IsEqual(statusCode, 500)) {
|
|
// See https://docs.bitfinex.com/docs/abbreviations-glossary#section-errorinfo-codes
|
|
var errorCode interface{} = this.SafeString(response, 1, "")
|
|
var errorText interface{} = this.SafeString(response, 2, "")
|
|
var feedback interface{} = Add(Add(this.Id, " "), errorText)
|
|
this.ThrowBroadlyMatchedException(GetValue(this.Exceptions, "broad"), errorText, feedback)
|
|
this.ThrowExactlyMatchedException(GetValue(this.Exceptions, "exact"), errorCode, feedback)
|
|
this.ThrowExactlyMatchedException(GetValue(this.Exceptions, "exact"), errorText, feedback)
|
|
panic(ExchangeError(Add(Add(Add(Add(Add(this.Id, " "), errorText), " (#"), errorCode), ")")))
|
|
}
|
|
return response
|
|
}
|
|
func (this *bitfinex) ParseLedgerEntryType(typeVar interface{}) interface{} {
|
|
if IsTrue(IsEqual(typeVar, nil)) {
|
|
return nil
|
|
} else if IsTrue(IsTrue(IsGreaterThanOrEqual(GetIndexOf(typeVar, "fee"), 0)) || IsTrue(IsGreaterThanOrEqual(GetIndexOf(typeVar, "charged"), 0))) {
|
|
return "fee"
|
|
} else if IsTrue(IsGreaterThanOrEqual(GetIndexOf(typeVar, "rebate"), 0)) {
|
|
return "rebate"
|
|
} else if IsTrue(IsTrue(IsGreaterThanOrEqual(GetIndexOf(typeVar, "deposit"), 0)) || IsTrue(IsGreaterThanOrEqual(GetIndexOf(typeVar, "withdrawal"), 0))) {
|
|
return "transaction"
|
|
} else if IsTrue(IsGreaterThanOrEqual(GetIndexOf(typeVar, "transfer"), 0)) {
|
|
return "transfer"
|
|
} else if IsTrue(IsGreaterThanOrEqual(GetIndexOf(typeVar, "payment"), 0)) {
|
|
return "payout"
|
|
} else if IsTrue(IsTrue(IsGreaterThanOrEqual(GetIndexOf(typeVar, "exchange"), 0)) || IsTrue(IsGreaterThanOrEqual(GetIndexOf(typeVar, "position"), 0))) {
|
|
return "trade"
|
|
} else {
|
|
return typeVar
|
|
}
|
|
}
|
|
func (this *bitfinex) ParseLedgerEntry(item interface{}, optionalArgs ...interface{}) interface{} {
|
|
//
|
|
// [
|
|
// [
|
|
// 2531822314, // ID: Ledger identifier
|
|
// "USD", // CURRENCY: The symbol of the currency (ex. "BTC")
|
|
// null, // PLACEHOLDER
|
|
// 1573521810000, // MTS: Timestamp in milliseconds
|
|
// null, // PLACEHOLDER
|
|
// 0.01644445, // AMOUNT: Amount of funds moved
|
|
// 0, // BALANCE: New balance
|
|
// null, // PLACEHOLDER
|
|
// "Settlement @ 185.79 on wallet margin" // DESCRIPTION: Description of ledger transaction
|
|
// ]
|
|
// ]
|
|
//
|
|
currency := GetArg(optionalArgs, 0, nil)
|
|
_ = currency
|
|
var itemList interface{} = this.SafeList(item, "result", []interface{}{})
|
|
var typeVar interface{} = nil
|
|
var id interface{} = this.SafeString(itemList, 0)
|
|
var currencyId interface{} = this.SafeString(itemList, 1)
|
|
var code interface{} = this.SafeCurrencyCode(currencyId, currency)
|
|
currency = this.SafeCurrency(currencyId, currency)
|
|
var timestamp interface{} = this.SafeInteger(itemList, 3)
|
|
var amount interface{} = this.SafeNumber(itemList, 5)
|
|
var after interface{} = this.SafeNumber(itemList, 6)
|
|
var description interface{} = this.SafeString(itemList, 8)
|
|
if IsTrue(!IsEqual(description, nil)) {
|
|
var parts interface{} = Split(description, " @ ")
|
|
var first interface{} = this.SafeStringLower(parts, 0)
|
|
typeVar = this.ParseLedgerEntryType(first)
|
|
}
|
|
return this.SafeLedgerEntry(map[string]interface{} {
|
|
"info": item,
|
|
"id": id,
|
|
"direction": nil,
|
|
"account": nil,
|
|
"referenceId": id,
|
|
"referenceAccount": nil,
|
|
"type": typeVar,
|
|
"currency": code,
|
|
"amount": amount,
|
|
"timestamp": timestamp,
|
|
"datetime": this.Iso8601(timestamp),
|
|
"before": nil,
|
|
"after": after,
|
|
"status": nil,
|
|
"fee": nil,
|
|
}, currency)
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitfinex#fetchLedger
|
|
* @description fetch the history of changes, actions done by the user or operations that altered the balance of the user
|
|
* @see https://docs.bitfinex.com/reference/rest-auth-ledgers
|
|
* @param {string} [code] unified currency code, default is undefined
|
|
* @param {int} [since] timestamp in ms of the earliest ledger entry, default is undefined
|
|
* @param {int} [limit] max number of ledger entries to return, default is undefined, max is 2500
|
|
* @param {object} [params] extra parameters specific to the exchange API endpoint
|
|
* @param {int} [params.until] timestamp in ms of the latest ledger entry
|
|
* @param {boolean} [params.paginate] default false, when true will automatically paginate by calling this endpoint multiple times. See in the docs all the [available parameters](https://github.com/ccxt/ccxt/wiki/Manual#pagination-params)
|
|
* @returns {object} a [ledger structure]{@link https://docs.ccxt.com/#/?id=ledger}
|
|
*/
|
|
func (this *bitfinex) FetchLedger(optionalArgs ...interface{}) <- chan interface{} {
|
|
ch := make(chan interface{})
|
|
go func() interface{} {
|
|
defer close(ch)
|
|
defer ReturnPanicError(ch)
|
|
code := GetArg(optionalArgs, 0, nil)
|
|
_ = code
|
|
since := GetArg(optionalArgs, 1, nil)
|
|
_ = since
|
|
limit := GetArg(optionalArgs, 2, nil)
|
|
_ = limit
|
|
params := GetArg(optionalArgs, 3, map[string]interface{} {})
|
|
_ = params
|
|
|
|
retRes30738 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes30738)
|
|
var paginate interface{} = false
|
|
paginateparamsVariable := this.HandleOptionAndParams(params, "fetchLedger", "paginate");
|
|
paginate = GetValue(paginateparamsVariable,0);
|
|
params = GetValue(paginateparamsVariable,1)
|
|
if IsTrue(paginate) {
|
|
|
|
retRes307719 := (<-this.FetchPaginatedCallDynamic("fetchLedger", code, since, limit, params, 2500))
|
|
PanicOnError(retRes307719)
|
|
ch <- retRes307719
|
|
return nil
|
|
}
|
|
var currency interface{} = nil
|
|
var request interface{} = map[string]interface{} {}
|
|
if IsTrue(!IsEqual(since, nil)) {
|
|
AddElementToObject(request, "start", since)
|
|
}
|
|
if IsTrue(!IsEqual(limit, nil)) {
|
|
AddElementToObject(request, "limit", limit)
|
|
}
|
|
requestparamsVariable := this.HandleUntilOption("end", request, params);
|
|
request = GetValue(requestparamsVariable,0);
|
|
params = GetValue(requestparamsVariable,1)
|
|
var response interface{} = nil
|
|
if IsTrue(!IsEqual(code, nil)) {
|
|
currency = this.Currency(code)
|
|
AddElementToObject(request, "currency", GetValue(currency, "uppercaseId"))
|
|
|
|
response = (<-this.PrivatePostAuthRLedgersCurrencyHist(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
} else {
|
|
|
|
response = (<-this.PrivatePostAuthRLedgersHist(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
}
|
|
//
|
|
// [
|
|
// [
|
|
// 2531822314, // ID: Ledger identifier
|
|
// "USD", // CURRENCY: The symbol of the currency (ex. "BTC")
|
|
// null, // PLACEHOLDER
|
|
// 1573521810000, // MTS: Timestamp in milliseconds
|
|
// null, // PLACEHOLDER
|
|
// 0.01644445, // AMOUNT: Amount of funds moved
|
|
// 0, // BALANCE: New balance
|
|
// null, // PLACEHOLDER
|
|
// "Settlement @ 185.79 on wallet margin" // DESCRIPTION: Description of ledger transaction
|
|
// ]
|
|
// ]
|
|
//
|
|
var ledgerObjects interface{} = []interface{}{}
|
|
for i := 0; IsLessThan(i, GetArrayLength(response)); i++ {
|
|
var item interface{} = GetValue(response, i)
|
|
AppendToArray(&ledgerObjects,map[string]interface{} {
|
|
"result": item,
|
|
})
|
|
}
|
|
|
|
ch <- this.ParseLedger(ledgerObjects, currency, since, limit)
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitfinex#fetchFundingRates
|
|
* @description fetch the current funding rate for multiple symbols
|
|
* @see https://docs.bitfinex.com/reference/rest-public-derivatives-status
|
|
* @param {string[]} symbols list of unified market symbols
|
|
* @param {object} [params] extra parameters specific to the exchange API endpoint
|
|
* @returns {object[]} a list of [funding rate structures]{@link https://docs.ccxt.com/#/?id=funding-rate-structure}
|
|
*/
|
|
func (this *bitfinex) FetchFundingRates(optionalArgs ...interface{}) <- chan interface{} {
|
|
ch := make(chan interface{})
|
|
go func() interface{} {
|
|
defer close(ch)
|
|
defer ReturnPanicError(ch)
|
|
symbols := GetArg(optionalArgs, 0, nil)
|
|
_ = symbols
|
|
params := GetArg(optionalArgs, 1, map[string]interface{} {})
|
|
_ = params
|
|
if IsTrue(IsEqual(symbols, nil)) {
|
|
panic(ArgumentsRequired(Add(this.Id, " fetchFundingRates() requires a symbols argument")))
|
|
}
|
|
|
|
retRes31328 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes31328)
|
|
var marketIds interface{} = this.MarketIds(symbols)
|
|
var request interface{} = map[string]interface{} {
|
|
"keys": Join(marketIds, ","),
|
|
}
|
|
|
|
response:= (<-this.PublicGetStatusDeriv(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
|
|
//
|
|
// [
|
|
// [
|
|
// "tBTCF0:USTF0",
|
|
// 1691165059000,
|
|
// null,
|
|
// 29297.851276225,
|
|
// 29277.5,
|
|
// null,
|
|
// 36950860.76010306,
|
|
// null,
|
|
// 1691193600000,
|
|
// 0.00000527,
|
|
// 82,
|
|
// null,
|
|
// 0.00014548,
|
|
// null,
|
|
// null,
|
|
// 29278.8925,
|
|
// null,
|
|
// null,
|
|
// 9636.07644994,
|
|
// null,
|
|
// null,
|
|
// null,
|
|
// 0.0005,
|
|
// 0.0025
|
|
// ]
|
|
// ]
|
|
//
|
|
ch <- this.ParseFundingRates(response, symbols)
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitfinex#fetchFundingRateHistory
|
|
* @description fetches historical funding rate prices
|
|
* @see https://docs.bitfinex.com/reference/rest-public-derivatives-status-history
|
|
* @param {string} symbol unified market symbol
|
|
* @param {int} [since] timestamp in ms of the earliest funding rate entry
|
|
* @param {int} [limit] max number of funding rate entrys to return
|
|
* @param {object} [params] extra parameters specific to the exchange API endpoint
|
|
* @param {int} [params.until] timestamp in ms of the latest funding rate
|
|
* @param {boolean} [params.paginate] default false, when true will automatically paginate by calling this endpoint multiple times. See in the docs all the [available parameters](https://github.com/ccxt/ccxt/wiki/Manual#pagination-params)
|
|
* @returns {object} a [funding rate structure]{@link https://docs.ccxt.com/#/?id=funding-rate-structure}
|
|
*/
|
|
func (this *bitfinex) FetchFundingRateHistory(optionalArgs ...interface{}) <- chan interface{} {
|
|
ch := make(chan interface{})
|
|
go func() interface{} {
|
|
defer close(ch)
|
|
defer ReturnPanicError(ch)
|
|
symbol := GetArg(optionalArgs, 0, nil)
|
|
_ = symbol
|
|
since := GetArg(optionalArgs, 1, nil)
|
|
_ = since
|
|
limit := GetArg(optionalArgs, 2, nil)
|
|
_ = limit
|
|
params := GetArg(optionalArgs, 3, map[string]interface{} {})
|
|
_ = params
|
|
if IsTrue(IsEqual(symbol, nil)) {
|
|
panic(ArgumentsRequired(Add(this.Id, " fetchFundingRateHistory() requires a symbol argument")))
|
|
}
|
|
|
|
retRes31888 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes31888)
|
|
var paginate interface{} = false
|
|
paginateparamsVariable := this.HandleOptionAndParams(params, "fetchFundingRateHistory", "paginate");
|
|
paginate = GetValue(paginateparamsVariable,0);
|
|
params = GetValue(paginateparamsVariable,1)
|
|
if IsTrue(paginate) {
|
|
|
|
retRes319219 := (<-this.FetchPaginatedCallDeterministic("fetchFundingRateHistory", symbol, since, limit, "8h", params, 5000))
|
|
PanicOnError(retRes319219)
|
|
ch <- retRes319219
|
|
return nil
|
|
}
|
|
var market interface{} = this.Market(symbol)
|
|
var request interface{} = map[string]interface{} {
|
|
"symbol": GetValue(market, "id"),
|
|
}
|
|
if IsTrue(!IsEqual(since, nil)) {
|
|
AddElementToObject(request, "start", since)
|
|
}
|
|
requestparamsVariable := this.HandleUntilOption("end", request, params);
|
|
request = GetValue(requestparamsVariable,0);
|
|
params = GetValue(requestparamsVariable,1)
|
|
|
|
response:= (<-this.PublicGetStatusDerivSymbolHist(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
//
|
|
// [
|
|
// [
|
|
// "tBTCF0:USTF0",
|
|
// 1691165059000,
|
|
// null,
|
|
// 29297.851276225,
|
|
// 29277.5,
|
|
// null,
|
|
// 36950860.76010306,
|
|
// null,
|
|
// 1691193600000,
|
|
// 0.00000527,
|
|
// 82,
|
|
// null,
|
|
// 0.00014548,
|
|
// null,
|
|
// null,
|
|
// 29278.8925,
|
|
// null,
|
|
// null,
|
|
// 9636.07644994,
|
|
// null,
|
|
// null,
|
|
// null,
|
|
// 0.0005,
|
|
// 0.0025
|
|
// ]
|
|
// ]
|
|
//
|
|
var rates interface{} = []interface{}{}
|
|
for i := 0; IsLessThan(i, GetArrayLength(response)); i++ {
|
|
var fr interface{} = GetValue(response, i)
|
|
var rate interface{} = this.ParseFundingRateHistory(fr, market)
|
|
AppendToArray(&rates,rate)
|
|
}
|
|
var reversedArray interface{} = []interface{}{}
|
|
var rawRates interface{} = this.FilterBySymbolSinceLimit(rates, symbol, since, limit)
|
|
var ratesLength interface{} = GetArrayLength(rawRates)
|
|
for i := 0; IsLessThan(i, ratesLength); i++ {
|
|
var index interface{} = Subtract(Subtract(ratesLength, i), 1)
|
|
var valueAtIndex interface{} = GetValue(rawRates, index)
|
|
AppendToArray(&reversedArray,valueAtIndex)
|
|
}
|
|
|
|
ch <- reversedArray
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
func (this *bitfinex) ParseFundingRate(contract interface{}, optionalArgs ...interface{}) interface{} {
|
|
//
|
|
// [
|
|
// "tBTCF0:USTF0",
|
|
// 1691165059000,
|
|
// null,
|
|
// 29297.851276225,
|
|
// 29277.5,
|
|
// null,
|
|
// 36950860.76010306,
|
|
// null,
|
|
// 1691193600000,
|
|
// 0.00000527,
|
|
// 82,
|
|
// null,
|
|
// 0.00014548,
|
|
// null,
|
|
// null,
|
|
// 29278.8925,
|
|
// null,
|
|
// null,
|
|
// 9636.07644994,
|
|
// null,
|
|
// null,
|
|
// null,
|
|
// 0.0005,
|
|
// 0.0025
|
|
// ]
|
|
//
|
|
market := GetArg(optionalArgs, 0, nil)
|
|
_ = market
|
|
var marketId interface{} = this.SafeString(contract, 0)
|
|
var timestamp interface{} = this.SafeInteger(contract, 1)
|
|
var nextFundingTimestamp interface{} = this.SafeInteger(contract, 8)
|
|
return map[string]interface{} {
|
|
"info": contract,
|
|
"symbol": this.SafeSymbol(marketId, market),
|
|
"markPrice": this.SafeNumber(contract, 15),
|
|
"indexPrice": this.SafeNumber(contract, 3),
|
|
"interestRate": nil,
|
|
"estimatedSettlePrice": nil,
|
|
"timestamp": timestamp,
|
|
"datetime": this.Iso8601(timestamp),
|
|
"fundingRate": this.SafeNumber(contract, 12),
|
|
"fundingTimestamp": nil,
|
|
"fundingDatetime": nil,
|
|
"nextFundingRate": this.SafeNumber(contract, 9),
|
|
"nextFundingTimestamp": nextFundingTimestamp,
|
|
"nextFundingDatetime": this.Iso8601(nextFundingTimestamp),
|
|
"previousFundingRate": nil,
|
|
"previousFundingTimestamp": nil,
|
|
"previousFundingDatetime": nil,
|
|
"interval": nil,
|
|
}
|
|
}
|
|
func (this *bitfinex) ParseFundingRateHistory(contract interface{}, optionalArgs ...interface{}) interface{} {
|
|
//
|
|
// [
|
|
// 1691165494000,
|
|
// null,
|
|
// 29278.95838065,
|
|
// 29260.5,
|
|
// null,
|
|
// 36950860.76010305,
|
|
// null,
|
|
// 1691193600000,
|
|
// 0.00001449,
|
|
// 222,
|
|
// null,
|
|
// 0.00014548,
|
|
// null,
|
|
// null,
|
|
// 29260.005,
|
|
// null,
|
|
// null,
|
|
// 9635.86484562,
|
|
// null,
|
|
// null,
|
|
// null,
|
|
// 0.0005,
|
|
// 0.0025
|
|
// ]
|
|
//
|
|
market := GetArg(optionalArgs, 0, nil)
|
|
_ = market
|
|
var timestamp interface{} = this.SafeInteger(contract, 0)
|
|
var nextFundingTimestamp interface{} = this.SafeInteger(contract, 7)
|
|
return map[string]interface{} {
|
|
"info": contract,
|
|
"symbol": this.SafeSymbol(nil, market),
|
|
"markPrice": this.SafeNumber(contract, 14),
|
|
"indexPrice": this.SafeNumber(contract, 2),
|
|
"interestRate": nil,
|
|
"estimatedSettlePrice": nil,
|
|
"timestamp": timestamp,
|
|
"datetime": this.Iso8601(timestamp),
|
|
"fundingRate": this.SafeNumber(contract, 11),
|
|
"fundingTimestamp": nil,
|
|
"fundingDatetime": nil,
|
|
"nextFundingRate": this.SafeNumber(contract, 8),
|
|
"nextFundingTimestamp": nextFundingTimestamp,
|
|
"nextFundingDatetime": this.Iso8601(nextFundingTimestamp),
|
|
"previousFundingRate": nil,
|
|
"previousFundingTimestamp": nil,
|
|
"previousFundingDatetime": nil,
|
|
}
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitfinex#fetchOpenInterests
|
|
* @description Retrieves the open interest for a list of symbols
|
|
* @see https://docs.bitfinex.com/reference/rest-public-derivatives-status
|
|
* @param {string[]} [symbols] a list of unified CCXT market symbols
|
|
* @param {object} [params] exchange specific parameters
|
|
* @returns {object[]} a list of [open interest structures]{@link https://docs.ccxt.com/#/?id=open-interest-structure}
|
|
*/
|
|
func (this *bitfinex) FetchOpenInterests(optionalArgs ...interface{}) <- chan interface{} {
|
|
ch := make(chan interface{})
|
|
go func() interface{} {
|
|
defer close(ch)
|
|
defer ReturnPanicError(ch)
|
|
symbols := GetArg(optionalArgs, 0, nil)
|
|
_ = symbols
|
|
params := GetArg(optionalArgs, 1, map[string]interface{} {})
|
|
_ = params
|
|
|
|
retRes33658 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes33658)
|
|
symbols = this.MarketSymbols(symbols)
|
|
var marketIds interface{} = []interface{}{"ALL"}
|
|
if IsTrue(!IsEqual(symbols, nil)) {
|
|
marketIds = this.MarketIds(symbols)
|
|
}
|
|
var request interface{} = map[string]interface{} {
|
|
"keys": Join(marketIds, ","),
|
|
}
|
|
|
|
response:= (<-this.PublicGetStatusDeriv(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
|
|
//
|
|
// [
|
|
// [
|
|
// "tXRPF0:USTF0", // market id
|
|
// 1706256986000, // millisecond timestamp
|
|
// null,
|
|
// 0.512705, // derivative mid price
|
|
// 0.512395, // underlying spot mid price
|
|
// null,
|
|
// 37671483.04, // insurance fund balance
|
|
// null,
|
|
// 1706284800000, // timestamp of next funding
|
|
// 0.00002353, // accrued funding for next period
|
|
// 317, // next funding step
|
|
// null,
|
|
// 0, // current funding
|
|
// null,
|
|
// null,
|
|
// 0.5123016, // mark price
|
|
// null,
|
|
// null,
|
|
// 2233562.03115, // open interest in contracts
|
|
// null,
|
|
// null,
|
|
// null,
|
|
// 0.0005, // average spread without funding payment
|
|
// 0.0025 // funding payment cap
|
|
// ]
|
|
// ]
|
|
//
|
|
ch <- this.ParseOpenInterests(response, symbols)
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitfinex#fetchOpenInterest
|
|
* @description retrieves the open interest of a contract trading pair
|
|
* @see https://docs.bitfinex.com/reference/rest-public-derivatives-status
|
|
* @param {string} symbol unified CCXT market symbol
|
|
* @param {object} [params] exchange specific parameters
|
|
* @returns {object} an [open interest structure]{@link https://docs.ccxt.com/#/?id=open-interest-structure}
|
|
*/
|
|
func (this *bitfinex) FetchOpenInterest(symbol interface{}, optionalArgs ...interface{}) <- chan interface{} {
|
|
ch := make(chan interface{})
|
|
go func() interface{} {
|
|
defer close(ch)
|
|
defer ReturnPanicError(ch)
|
|
params := GetArg(optionalArgs, 0, map[string]interface{} {})
|
|
_ = params
|
|
|
|
retRes34188 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes34188)
|
|
var market interface{} = this.Market(symbol)
|
|
var request interface{} = map[string]interface{} {
|
|
"keys": GetValue(market, "id"),
|
|
}
|
|
|
|
response:= (<-this.PublicGetStatusDeriv(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
//
|
|
// [
|
|
// [
|
|
// "tXRPF0:USTF0", // market id
|
|
// 1706256986000, // millisecond timestamp
|
|
// null,
|
|
// 0.512705, // derivative mid price
|
|
// 0.512395, // underlying spot mid price
|
|
// null,
|
|
// 37671483.04, // insurance fund balance
|
|
// null,
|
|
// 1706284800000, // timestamp of next funding
|
|
// 0.00002353, // accrued funding for next period
|
|
// 317, // next funding step
|
|
// null,
|
|
// 0, // current funding
|
|
// null,
|
|
// null,
|
|
// 0.5123016, // mark price
|
|
// null,
|
|
// null,
|
|
// 2233562.03115, // open interest in contracts
|
|
// null,
|
|
// null,
|
|
// null,
|
|
// 0.0005, // average spread without funding payment
|
|
// 0.0025 // funding payment cap
|
|
// ]
|
|
// ]
|
|
//
|
|
var oi interface{} = this.SafeList(response, 0)
|
|
|
|
ch <- this.ParseOpenInterest(oi, market)
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitfinex#fetchOpenInterestHistory
|
|
* @description retrieves the open interest history of a currency
|
|
* @see https://docs.bitfinex.com/reference/rest-public-derivatives-status-history
|
|
* @param {string} symbol unified CCXT market symbol
|
|
* @param {string} timeframe the time period of each row of data, not used by bitfinex
|
|
* @param {int} [since] the time in ms of the earliest record to retrieve as a unix timestamp
|
|
* @param {int} [limit] the number of records in the response
|
|
* @param {object} [params] exchange specific parameters
|
|
* @param {int} [params.until] the time in ms of the latest record to retrieve as a unix timestamp
|
|
* @param {boolean} [params.paginate] default false, when true will automatically paginate by calling this endpoint multiple times. See in the docs all the [available parameters](https://github.com/ccxt/ccxt/wiki/Manual#pagination-params)
|
|
* @returns An array of [open interest structures]{@link https://docs.ccxt.com/#/?id=open-interest-structure}
|
|
*/
|
|
func (this *bitfinex) FetchOpenInterestHistory(symbol interface{}, optionalArgs ...interface{}) <- chan interface{} {
|
|
ch := make(chan interface{})
|
|
go func() interface{} {
|
|
defer close(ch)
|
|
defer ReturnPanicError(ch)
|
|
timeframe := GetArg(optionalArgs, 0, "1m")
|
|
_ = timeframe
|
|
since := GetArg(optionalArgs, 1, nil)
|
|
_ = since
|
|
limit := GetArg(optionalArgs, 2, nil)
|
|
_ = limit
|
|
params := GetArg(optionalArgs, 3, map[string]interface{} {})
|
|
_ = params
|
|
|
|
retRes34738 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes34738)
|
|
var paginate interface{} = false
|
|
paginateparamsVariable := this.HandleOptionAndParams(params, "fetchOpenInterestHistory", "paginate");
|
|
paginate = GetValue(paginateparamsVariable,0);
|
|
params = GetValue(paginateparamsVariable,1)
|
|
if IsTrue(paginate) {
|
|
|
|
retRes347719 := (<-this.FetchPaginatedCallDeterministic("fetchOpenInterestHistory", symbol, since, limit, "8h", params, 5000))
|
|
PanicOnError(retRes347719)
|
|
ch <- retRes347719
|
|
return nil
|
|
}
|
|
var market interface{} = this.Market(symbol)
|
|
var request interface{} = map[string]interface{} {
|
|
"symbol": GetValue(market, "id"),
|
|
}
|
|
if IsTrue(!IsEqual(since, nil)) {
|
|
AddElementToObject(request, "start", since)
|
|
}
|
|
if IsTrue(!IsEqual(limit, nil)) {
|
|
AddElementToObject(request, "limit", limit)
|
|
}
|
|
requestparamsVariable := this.HandleUntilOption("end", request, params);
|
|
request = GetValue(requestparamsVariable,0);
|
|
params = GetValue(requestparamsVariable,1)
|
|
|
|
response:= (<-this.PublicGetStatusDerivSymbolHist(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
|
|
//
|
|
// [
|
|
// [
|
|
// 1706295191000, // timestamp
|
|
// null,
|
|
// 42152.425382, // derivative mid price
|
|
// 42133, // spot mid price
|
|
// null,
|
|
// 37671589.7853521, // insurance fund balance
|
|
// null,
|
|
// 1706313600000, // timestamp of next funding
|
|
// 0.00018734, // accrued funding for next period
|
|
// 3343, // next funding step
|
|
// null,
|
|
// 0.00007587, // current funding
|
|
// null,
|
|
// null,
|
|
// 42134.1, // mark price
|
|
// null,
|
|
// null,
|
|
// 5775.20348804, // open interest number of contracts
|
|
// null,
|
|
// null,
|
|
// null,
|
|
// 0.0005, // average spread without funding payment
|
|
// 0.0025 // funding payment cap
|
|
// ],
|
|
// ]
|
|
//
|
|
ch <- this.ParseOpenInterestsHistory(response, market, since, limit)
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
func (this *bitfinex) ParseOpenInterest(interest interface{}, optionalArgs ...interface{}) interface{} {
|
|
//
|
|
// fetchOpenInterest:
|
|
//
|
|
// [
|
|
// "tXRPF0:USTF0", // market id
|
|
// 1706256986000, // millisecond timestamp
|
|
// null,
|
|
// 0.512705, // derivative mid price
|
|
// 0.512395, // underlying spot mid price
|
|
// null,
|
|
// 37671483.04, // insurance fund balance
|
|
// null,
|
|
// 1706284800000, // timestamp of next funding
|
|
// 0.00002353, // accrued funding for next period
|
|
// 317, // next funding step
|
|
// null,
|
|
// 0, // current funding
|
|
// null,
|
|
// null,
|
|
// 0.5123016, // mark price
|
|
// null,
|
|
// null,
|
|
// 2233562.03115, // open interest in contracts
|
|
// null,
|
|
// null,
|
|
// null,
|
|
// 0.0005, // average spread without funding payment
|
|
// 0.0025 // funding payment cap
|
|
// ]
|
|
//
|
|
// fetchOpenInterestHistory:
|
|
//
|
|
// [
|
|
// 1706295191000, // timestamp
|
|
// null,
|
|
// 42152.425382, // derivative mid price
|
|
// 42133, // spot mid price
|
|
// null,
|
|
// 37671589.7853521, // insurance fund balance
|
|
// null,
|
|
// 1706313600000, // timestamp of next funding
|
|
// 0.00018734, // accrued funding for next period
|
|
// 3343, // next funding step
|
|
// null,
|
|
// 0.00007587, // current funding
|
|
// null,
|
|
// null,
|
|
// 42134.1, // mark price
|
|
// null,
|
|
// null,
|
|
// 5775.20348804, // open interest number of contracts
|
|
// null,
|
|
// null,
|
|
// null,
|
|
// 0.0005, // average spread without funding payment
|
|
// 0.0025 // funding payment cap
|
|
// ]
|
|
//
|
|
market := GetArg(optionalArgs, 0, nil)
|
|
_ = market
|
|
var interestLength interface{} = GetArrayLength(interest)
|
|
var openInterestIndex interface{} = Ternary(IsTrue((IsEqual(interestLength, 23))), 17, 18)
|
|
var timestamp interface{} = this.SafeInteger(interest, 1)
|
|
var marketId interface{} = this.SafeString(interest, 0)
|
|
return this.SafeOpenInterest(map[string]interface{} {
|
|
"symbol": this.SafeSymbol(marketId, market, nil, "swap"),
|
|
"openInterestAmount": this.SafeNumber(interest, openInterestIndex),
|
|
"openInterestValue": nil,
|
|
"timestamp": timestamp,
|
|
"datetime": this.Iso8601(timestamp),
|
|
"info": interest,
|
|
}, market)
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitfinex#fetchLiquidations
|
|
* @description retrieves the public liquidations of a trading pair
|
|
* @see https://docs.bitfinex.com/reference/rest-public-liquidations
|
|
* @param {string} symbol unified CCXT market symbol
|
|
* @param {int} [since] the earliest time in ms to fetch liquidations for
|
|
* @param {int} [limit] the maximum number of liquidation structures to retrieve
|
|
* @param {object} [params] exchange specific parameters
|
|
* @param {int} [params.until] timestamp in ms of the latest liquidation
|
|
* @param {boolean} [params.paginate] default false, when true will automatically paginate by calling this endpoint multiple times. See in the docs all the [available parameters](https://github.com/ccxt/ccxt/wiki/Manual#pagination-params)
|
|
* @returns {object} an array of [liquidation structures]{@link https://docs.ccxt.com/#/?id=liquidation-structure}
|
|
*/
|
|
func (this *bitfinex) FetchLiquidations(symbol interface{}, optionalArgs ...interface{}) <- chan interface{} {
|
|
ch := make(chan interface{})
|
|
go func() interface{} {
|
|
defer close(ch)
|
|
defer ReturnPanicError(ch)
|
|
since := GetArg(optionalArgs, 0, nil)
|
|
_ = since
|
|
limit := GetArg(optionalArgs, 1, nil)
|
|
_ = limit
|
|
params := GetArg(optionalArgs, 2, map[string]interface{} {})
|
|
_ = params
|
|
|
|
retRes36108 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes36108)
|
|
var paginate interface{} = false
|
|
paginateparamsVariable := this.HandleOptionAndParams(params, "fetchLiquidations", "paginate");
|
|
paginate = GetValue(paginateparamsVariable,0);
|
|
params = GetValue(paginateparamsVariable,1)
|
|
if IsTrue(paginate) {
|
|
|
|
retRes361419 := (<-this.FetchPaginatedCallDeterministic("fetchLiquidations", symbol, since, limit, "8h", params, 500))
|
|
PanicOnError(retRes361419)
|
|
ch <- retRes361419
|
|
return nil
|
|
}
|
|
var market interface{} = this.Market(symbol)
|
|
var request interface{} = map[string]interface{} {}
|
|
if IsTrue(!IsEqual(since, nil)) {
|
|
AddElementToObject(request, "start", since)
|
|
}
|
|
if IsTrue(!IsEqual(limit, nil)) {
|
|
AddElementToObject(request, "limit", limit)
|
|
}
|
|
requestparamsVariable := this.HandleUntilOption("end", request, params);
|
|
request = GetValue(requestparamsVariable,0);
|
|
params = GetValue(requestparamsVariable,1)
|
|
|
|
response:= (<-this.PublicGetLiquidationsHist(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
|
|
//
|
|
// [
|
|
// [
|
|
// [
|
|
// "pos",
|
|
// 171085137,
|
|
// 1706395919788,
|
|
// null,
|
|
// "tAVAXF0:USTF0",
|
|
// -8,
|
|
// 32.868,
|
|
// null,
|
|
// 1,
|
|
// 1,
|
|
// null,
|
|
// 33.255
|
|
// ]
|
|
// ],
|
|
// ]
|
|
//
|
|
ch <- this.ParseLiquidations(response, market, since, limit)
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
func (this *bitfinex) ParseLiquidation(liquidation interface{}, optionalArgs ...interface{}) interface{} {
|
|
//
|
|
// [
|
|
// [
|
|
// "pos",
|
|
// 171085137, // position id
|
|
// 1706395919788, // timestamp
|
|
// null,
|
|
// "tAVAXF0:USTF0", // market id
|
|
// -8, // amount in contracts
|
|
// 32.868, // base price
|
|
// null,
|
|
// 1,
|
|
// 1,
|
|
// null,
|
|
// 33.255 // acquired price
|
|
// ]
|
|
// ]
|
|
//
|
|
market := GetArg(optionalArgs, 0, nil)
|
|
_ = market
|
|
var entry interface{} = GetValue(liquidation, 0)
|
|
var timestamp interface{} = this.SafeInteger(entry, 2)
|
|
var marketId interface{} = this.SafeString(entry, 4)
|
|
var contracts interface{} = Precise.StringAbs(this.SafeString(entry, 5))
|
|
var contractSize interface{} = this.SafeString(market, "contractSize")
|
|
var baseValue interface{} = Precise.StringMul(contracts, contractSize)
|
|
var price interface{} = this.SafeString(entry, 11)
|
|
return this.SafeLiquidation(map[string]interface{} {
|
|
"info": entry,
|
|
"symbol": this.SafeSymbol(marketId, market, nil, "contract"),
|
|
"contracts": this.ParseNumber(contracts),
|
|
"contractSize": this.ParseNumber(contractSize),
|
|
"price": this.ParseNumber(price),
|
|
"baseValue": this.ParseNumber(baseValue),
|
|
"quoteValue": this.ParseNumber(Precise.StringMul(baseValue, price)),
|
|
"timestamp": timestamp,
|
|
"datetime": this.Iso8601(timestamp),
|
|
})
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitfinex#setMargin
|
|
* @description either adds or reduces margin in a swap position in order to set the margin to a specific value
|
|
* @see https://docs.bitfinex.com/reference/rest-auth-deriv-pos-collateral-set
|
|
* @param {string} symbol unified market symbol of the market to set margin in
|
|
* @param {float} amount the amount to set the margin to
|
|
* @param {object} [params] parameters specific to the exchange API endpoint
|
|
* @returns {object} A [margin structure]{@link https://github.com/ccxt/ccxt/wiki/Manual#add-margin-structure}
|
|
*/
|
|
func (this *bitfinex) SetMargin(symbol interface{}, amount interface{}, optionalArgs ...interface{}) <- chan interface{} {
|
|
ch := make(chan interface{})
|
|
go func() interface{} {
|
|
defer close(ch)
|
|
defer ReturnPanicError(ch)
|
|
params := GetArg(optionalArgs, 0, map[string]interface{} {})
|
|
_ = params
|
|
|
|
retRes36998 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes36998)
|
|
var market interface{} = this.Market(symbol)
|
|
if !IsTrue(GetValue(market, "swap")) {
|
|
panic(NotSupported(Add(this.Id, " setMargin() only support swap markets")))
|
|
}
|
|
var request interface{} = map[string]interface{} {
|
|
"symbol": GetValue(market, "id"),
|
|
"collateral": this.ParseToNumeric(amount),
|
|
}
|
|
|
|
response:= (<-this.PrivatePostAuthWDerivCollateralSet(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
//
|
|
// [
|
|
// [
|
|
// 1
|
|
// ]
|
|
// ]
|
|
//
|
|
var data interface{} = this.SafeValue(response, 0)
|
|
|
|
ch <- this.ParseMarginModification(data, market)
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
func (this *bitfinex) ParseMarginModification(data interface{}, optionalArgs ...interface{}) interface{} {
|
|
//
|
|
// setMargin
|
|
//
|
|
// [
|
|
// [
|
|
// 1
|
|
// ]
|
|
// ]
|
|
//
|
|
market := GetArg(optionalArgs, 0, nil)
|
|
_ = market
|
|
var marginStatusRaw interface{} = GetValue(data, 0)
|
|
var marginStatus interface{} = Ternary(IsTrue((IsEqual(marginStatusRaw, 1))), "ok", "failed")
|
|
return map[string]interface{} {
|
|
"info": data,
|
|
"symbol": GetValue(market, "symbol"),
|
|
"type": nil,
|
|
"marginMode": "isolated",
|
|
"amount": nil,
|
|
"total": nil,
|
|
"code": nil,
|
|
"status": marginStatus,
|
|
"timestamp": nil,
|
|
"datetime": nil,
|
|
}
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitfinex#fetchOrder
|
|
* @description fetches information on an order made by the user
|
|
* @see https://docs.bitfinex.com/reference/rest-auth-retrieve-orders
|
|
* @see https://docs.bitfinex.com/reference/rest-auth-retrieve-orders-by-symbol
|
|
* @param {string} id the order id
|
|
* @param {string} [symbol] unified symbol of the market the order was made in
|
|
* @param {object} [params] extra parameters specific to the exchange API endpoint
|
|
* @returns {object} an [order structure]{@link https://docs.ccxt.com/#/?id=order-structure}
|
|
*/
|
|
func (this *bitfinex) FetchOrder(id interface{}, optionalArgs ...interface{}) <- chan interface{} {
|
|
ch := make(chan interface{})
|
|
go func() interface{} {
|
|
defer close(ch)
|
|
defer ReturnPanicError(ch)
|
|
symbol := GetArg(optionalArgs, 0, nil)
|
|
_ = symbol
|
|
params := GetArg(optionalArgs, 1, map[string]interface{} {})
|
|
_ = params
|
|
|
|
retRes37588 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes37588)
|
|
var request interface{} = map[string]interface{} {
|
|
"id": []interface{}{this.ParseToNumeric(id)},
|
|
}
|
|
var market interface{} = nil
|
|
var response interface{} = nil
|
|
if IsTrue(IsEqual(symbol, nil)) {
|
|
|
|
response = (<-this.PrivatePostAuthROrders(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
} else {
|
|
market = this.Market(symbol)
|
|
AddElementToObject(request, "symbol", GetValue(market, "id"))
|
|
|
|
response = (<-this.PrivatePostAuthROrdersSymbol(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
}
|
|
//
|
|
// [
|
|
// [
|
|
// 139658969116,
|
|
// null,
|
|
// 1706843908637,
|
|
// "tBTCUST",
|
|
// 1706843908637,
|
|
// 1706843908638,
|
|
// 0.0001,
|
|
// 0.0001,
|
|
// "EXCHANGE LIMIT",
|
|
// null,
|
|
// null,
|
|
// null,
|
|
// 0,
|
|
// "ACTIVE",
|
|
// null,
|
|
// null,
|
|
// 35000,
|
|
// 0,
|
|
// 0,
|
|
// 0,
|
|
// null,
|
|
// null,
|
|
// null,
|
|
// 0,
|
|
// 0,
|
|
// null,
|
|
// null,
|
|
// null,
|
|
// "API>BFX",
|
|
// null,
|
|
// null,
|
|
// {}
|
|
// ]
|
|
// ]
|
|
//
|
|
var order interface{} = this.SafeList(response, 0)
|
|
var newOrder interface{} = map[string]interface{} {
|
|
"result": order,
|
|
}
|
|
|
|
ch <- this.ParseOrder(newOrder, market)
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitfinex#editOrder
|
|
* @description edit a trade order
|
|
* @see https://docs.bitfinex.com/reference/rest-auth-update-order
|
|
* @param {string} id edit order id
|
|
* @param {string} symbol unified symbol of the market to edit an order in
|
|
* @param {string} type 'market' or 'limit'
|
|
* @param {string} side 'buy' or 'sell'
|
|
* @param {float} amount how much you want to trade in units of the base currency
|
|
* @param {float} [price] the price at which the order is to be fulfilled, in units of the quote currency, ignored in market orders
|
|
* @param {object} [params] extra parameters specific to the exchange API endpoint
|
|
* @param {float} [params.triggerPrice] the price that triggers a trigger order
|
|
* @param {boolean} [params.postOnly] set to true if you want to make a post only order
|
|
* @param {boolean} [params.reduceOnly] indicates that the order is to reduce the size of a position
|
|
* @param {int} [params.flags] additional order parameters: 4096 (Post Only), 1024 (Reduce Only), 16384 (OCO), 64 (Hidden), 512 (Close), 524288 (No Var Rates)
|
|
* @param {int} [params.leverage] leverage for a derivative order, supported by derivative symbol orders only, the value should be between 1 and 100 inclusive
|
|
* @param {int} [params.clientOrderId] a unique client order id for the order
|
|
* @param {float} [params.trailingAmount] *swap only* the quote amount to trail away from the current market price
|
|
* @returns {object} an [order structure]{@link https://docs.ccxt.com/#/?id=order-structure}
|
|
*/
|
|
func (this *bitfinex) EditOrder(id interface{}, symbol interface{}, typeVar interface{}, side interface{}, optionalArgs ...interface{}) <- chan interface{} {
|
|
ch := make(chan interface{})
|
|
go func() interface{} {
|
|
defer close(ch)
|
|
defer ReturnPanicError(ch)
|
|
amount := GetArg(optionalArgs, 0, nil)
|
|
_ = amount
|
|
price := GetArg(optionalArgs, 1, nil)
|
|
_ = price
|
|
params := GetArg(optionalArgs, 2, map[string]interface{} {})
|
|
_ = params
|
|
|
|
retRes38368 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes38368)
|
|
var market interface{} = this.Market(symbol)
|
|
var request interface{} = map[string]interface{} {
|
|
"id": this.ParseToNumeric(id),
|
|
}
|
|
if IsTrue(!IsEqual(amount, nil)) {
|
|
var amountString interface{} = this.AmountToPrecision(symbol, amount)
|
|
amountString = Ternary(IsTrue((IsEqual(side, "buy"))), amountString, Precise.StringNeg(amountString))
|
|
AddElementToObject(request, "amount", amountString)
|
|
}
|
|
var triggerPrice interface{} = this.SafeString2(params, "stopPrice", "triggerPrice")
|
|
var trailingAmount interface{} = this.SafeString(params, "trailingAmount")
|
|
var timeInForce interface{} = this.SafeString(params, "timeInForce")
|
|
var postOnlyParam interface{} = this.SafeBool(params, "postOnly", false)
|
|
var reduceOnly interface{} = this.SafeBool(params, "reduceOnly", false)
|
|
var clientOrderId interface{} = this.SafeInteger2(params, "cid", "clientOrderId")
|
|
if IsTrue(!IsEqual(trailingAmount, nil)) {
|
|
AddElementToObject(request, "price_trailing", trailingAmount)
|
|
} else if IsTrue(!IsEqual(triggerPrice, nil)) {
|
|
// request['price'] is taken as triggerPrice for stop orders
|
|
AddElementToObject(request, "price", this.PriceToPrecision(symbol, triggerPrice))
|
|
if IsTrue(IsEqual(typeVar, "limit")) {
|
|
AddElementToObject(request, "price_aux_limit", this.PriceToPrecision(symbol, price))
|
|
}
|
|
}
|
|
var postOnly interface{} = (IsTrue(postOnlyParam) || IsTrue((IsEqual(timeInForce, "PO"))))
|
|
if IsTrue(IsTrue((!IsEqual(typeVar, "market"))) && IsTrue((IsEqual(triggerPrice, nil)))) {
|
|
AddElementToObject(request, "price", this.PriceToPrecision(symbol, price))
|
|
}
|
|
// flag values may be summed to combine flags
|
|
var flags interface{} = 0
|
|
if IsTrue(postOnly) {
|
|
flags = this.Sum(flags, 4096)
|
|
}
|
|
if IsTrue(reduceOnly) {
|
|
flags = this.Sum(flags, 1024)
|
|
}
|
|
if IsTrue(!IsEqual(flags, 0)) {
|
|
AddElementToObject(request, "flags", flags)
|
|
}
|
|
if IsTrue(!IsEqual(clientOrderId, nil)) {
|
|
AddElementToObject(request, "cid", clientOrderId)
|
|
}
|
|
var leverage interface{} = this.SafeInteger2(params, "leverage", "lev")
|
|
if IsTrue(!IsEqual(leverage, nil)) {
|
|
AddElementToObject(request, "lev", leverage)
|
|
}
|
|
params = this.Omit(params, []interface{}{"triggerPrice", "stopPrice", "timeInForce", "postOnly", "reduceOnly", "trailingAmount", "clientOrderId", "leverage"})
|
|
|
|
response:= (<-this.PrivatePostAuthWOrderUpdate(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
//
|
|
// [
|
|
// 1706845376402,
|
|
// "ou-req",
|
|
// null,
|
|
// null,
|
|
// [
|
|
// 139658969116,
|
|
// null,
|
|
// 1706843908637,
|
|
// "tBTCUST",
|
|
// 1706843908637,
|
|
// 1706843908638,
|
|
// 0.0002,
|
|
// 0.0002,
|
|
// "EXCHANGE LIMIT",
|
|
// null,
|
|
// null,
|
|
// null,
|
|
// 0,
|
|
// "ACTIVE",
|
|
// null,
|
|
// null,
|
|
// 35000,
|
|
// 0,
|
|
// 0,
|
|
// 0,
|
|
// null,
|
|
// null,
|
|
// null,
|
|
// 0,
|
|
// 0,
|
|
// null,
|
|
// null,
|
|
// null,
|
|
// "API>BFX",
|
|
// null,
|
|
// null,
|
|
// {}
|
|
// ],
|
|
// null,
|
|
// "SUCCESS",
|
|
// "Submitting update to exchange limit buy order for 0.0002 BTC."
|
|
// ]
|
|
//
|
|
var status interface{} = this.SafeString(response, 6)
|
|
if IsTrue(!IsEqual(status, "SUCCESS")) {
|
|
var errorCode interface{} = GetValue(response, 5)
|
|
var errorText interface{} = GetValue(response, 7)
|
|
panic(ExchangeError(Add(Add(Add(Add(Add(Add(Add(this.Id, " "), GetValue(response, 6)), ": "), errorText), " (#"), errorCode), ")")))
|
|
}
|
|
var order interface{} = this.SafeList(response, 4, []interface{}{})
|
|
var newOrder interface{} = map[string]interface{} {
|
|
"result": order,
|
|
}
|
|
|
|
ch <- this.ParseOrder(newOrder, market)
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
|
|
|
|
func (this *bitfinex) Init(userConfig map[string]interface{}) {
|
|
this.Exchange = Exchange{}
|
|
this.Exchange.InitParent(userConfig, this.Describe().(map[string]interface{}), this)
|
|
this.Exchange.DerivedExchange = this
|
|
}
|