2840 lines
116 KiB
Go
2840 lines
116 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 bitstamp struct {
|
|
Exchange
|
|
|
|
}
|
|
|
|
func NewBitstampCore() bitstamp {
|
|
p := bitstamp{}
|
|
setDefaults(&p)
|
|
return p
|
|
}
|
|
|
|
func (this *bitstamp) Describe() interface{} {
|
|
return this.DeepExtend(this.Exchange.Describe(), map[string]interface{} {
|
|
"id": "bitstamp",
|
|
"name": "Bitstamp",
|
|
"countries": []interface{}{"GB"},
|
|
"rateLimit": 75,
|
|
"version": "v2",
|
|
"userAgent": GetValue(this.UserAgents, "chrome"),
|
|
"pro": true,
|
|
"has": map[string]interface{} {
|
|
"CORS": true,
|
|
"spot": true,
|
|
"margin": false,
|
|
"swap": false,
|
|
"future": false,
|
|
"option": false,
|
|
"addMargin": false,
|
|
"cancelAllOrders": true,
|
|
"cancelOrder": true,
|
|
"closeAllPositions": false,
|
|
"closePosition": false,
|
|
"createOrder": true,
|
|
"createReduceOnlyOrder": false,
|
|
"createStopLimitOrder": false,
|
|
"createStopMarketOrder": false,
|
|
"createStopOrder": false,
|
|
"fetchBalance": true,
|
|
"fetchBorrowRateHistories": false,
|
|
"fetchBorrowRateHistory": false,
|
|
"fetchCrossBorrowRate": false,
|
|
"fetchCrossBorrowRates": false,
|
|
"fetchCurrencies": true,
|
|
"fetchDepositAddress": true,
|
|
"fetchDepositAddresses": false,
|
|
"fetchDepositAddressesByNetwork": false,
|
|
"fetchDepositsWithdrawals": true,
|
|
"fetchDepositWithdrawFee": "emulated",
|
|
"fetchDepositWithdrawFees": true,
|
|
"fetchFundingHistory": false,
|
|
"fetchFundingRate": false,
|
|
"fetchFundingRateHistory": false,
|
|
"fetchFundingRates": false,
|
|
"fetchIndexOHLCV": false,
|
|
"fetchIsolatedBorrowRate": false,
|
|
"fetchIsolatedBorrowRates": false,
|
|
"fetchLedger": true,
|
|
"fetchLeverage": false,
|
|
"fetchMarginMode": false,
|
|
"fetchMarkets": true,
|
|
"fetchMarkOHLCV": false,
|
|
"fetchMyTrades": true,
|
|
"fetchOHLCV": true,
|
|
"fetchOpenInterestHistory": false,
|
|
"fetchOpenOrders": true,
|
|
"fetchOrder": true,
|
|
"fetchOrderBook": true,
|
|
"fetchPosition": false,
|
|
"fetchPositionHistory": false,
|
|
"fetchPositionMode": false,
|
|
"fetchPositions": false,
|
|
"fetchPositionsForSymbol": false,
|
|
"fetchPositionsHistory": false,
|
|
"fetchPositionsRisk": false,
|
|
"fetchPremiumIndexOHLCV": false,
|
|
"fetchTicker": true,
|
|
"fetchTickers": true,
|
|
"fetchTrades": true,
|
|
"fetchTradingFee": true,
|
|
"fetchTradingFees": true,
|
|
"fetchTransactionFees": true,
|
|
"fetchTransactions": "emulated",
|
|
"fetchWithdrawals": true,
|
|
"reduceMargin": false,
|
|
"setLeverage": false,
|
|
"setMarginMode": false,
|
|
"setPositionMode": false,
|
|
"transfer": true,
|
|
"withdraw": true,
|
|
},
|
|
"urls": map[string]interface{} {
|
|
"logo": "https://github.com/user-attachments/assets/d5480572-1fee-43cb-b900-d38c522d0024",
|
|
"api": map[string]interface{} {
|
|
"public": "https://www.bitstamp.net/api",
|
|
"private": "https://www.bitstamp.net/api",
|
|
},
|
|
"www": "https://www.bitstamp.net",
|
|
"doc": "https://www.bitstamp.net/api",
|
|
},
|
|
"timeframes": map[string]interface{} {
|
|
"1m": "60",
|
|
"3m": "180",
|
|
"5m": "300",
|
|
"15m": "900",
|
|
"30m": "1800",
|
|
"1h": "3600",
|
|
"2h": "7200",
|
|
"4h": "14400",
|
|
"6h": "21600",
|
|
"12h": "43200",
|
|
"1d": "86400",
|
|
"1w": "259200",
|
|
},
|
|
"requiredCredentials": map[string]interface{} {
|
|
"apiKey": true,
|
|
"secret": true,
|
|
},
|
|
"api": map[string]interface{} {
|
|
"public": map[string]interface{} {
|
|
"get": map[string]interface{} {
|
|
"ohlc/{pair}/": 1,
|
|
"order_book/{pair}/": 1,
|
|
"ticker/": 1,
|
|
"ticker_hour/{pair}/": 1,
|
|
"ticker/{pair}/": 1,
|
|
"transactions/{pair}/": 1,
|
|
"trading-pairs-info/": 1,
|
|
"currencies/": 1,
|
|
"eur_usd/": 1,
|
|
"travel_rule/vasps/": 1,
|
|
},
|
|
},
|
|
"private": map[string]interface{} {
|
|
"get": map[string]interface{} {
|
|
"travel_rule/contacts/": 1,
|
|
"contacts/{contact_uuid}/": 1,
|
|
"earn/subscriptions/": 1,
|
|
"earn/transactions/": 1,
|
|
},
|
|
"post": map[string]interface{} {
|
|
"account_balances/": 1,
|
|
"account_balances/{currency}/": 1,
|
|
"balance/": 1,
|
|
"balance/{pair}/": 1,
|
|
"bch_withdrawal/": 1,
|
|
"bch_address/": 1,
|
|
"user_transactions/": 1,
|
|
"user_transactions/{pair}/": 1,
|
|
"crypto-transactions/": 1,
|
|
"open_order": 1,
|
|
"open_orders/all/": 1,
|
|
"open_orders/{pair}/": 1,
|
|
"order_status/": 1,
|
|
"cancel_order/": 1,
|
|
"cancel_all_orders/": 1,
|
|
"cancel_all_orders/{pair}/": 1,
|
|
"buy/{pair}/": 1,
|
|
"buy/market/{pair}/": 1,
|
|
"buy/instant/{pair}/": 1,
|
|
"sell/{pair}/": 1,
|
|
"sell/market/{pair}/": 1,
|
|
"sell/instant/{pair}/": 1,
|
|
"transfer-to-main/": 1,
|
|
"transfer-from-main/": 1,
|
|
"my_trading_pairs/": 1,
|
|
"fees/trading/": 1,
|
|
"fees/trading/{market_symbol}": 1,
|
|
"fees/withdrawal/": 1,
|
|
"fees/withdrawal/{currency}/": 1,
|
|
"withdrawal-requests/": 1,
|
|
"withdrawal/open/": 1,
|
|
"withdrawal/status/": 1,
|
|
"withdrawal/cancel/": 1,
|
|
"liquidation_address/new/": 1,
|
|
"liquidation_address/info/": 1,
|
|
"btc_unconfirmed/": 1,
|
|
"websockets_token/": 1,
|
|
"btc_withdrawal/": 1,
|
|
"btc_address/": 1,
|
|
"ripple_withdrawal/": 1,
|
|
"ripple_address/": 1,
|
|
"ltc_withdrawal/": 1,
|
|
"ltc_address/": 1,
|
|
"eth_withdrawal/": 1,
|
|
"eth_address/": 1,
|
|
"xrp_withdrawal/": 1,
|
|
"xrp_address/": 1,
|
|
"xlm_withdrawal/": 1,
|
|
"xlm_address/": 1,
|
|
"pax_withdrawal/": 1,
|
|
"pax_address/": 1,
|
|
"link_withdrawal/": 1,
|
|
"link_address/": 1,
|
|
"usdc_withdrawal/": 1,
|
|
"usdc_address/": 1,
|
|
"omg_withdrawal/": 1,
|
|
"omg_address/": 1,
|
|
"dai_withdrawal/": 1,
|
|
"dai_address/": 1,
|
|
"knc_withdrawal/": 1,
|
|
"knc_address/": 1,
|
|
"mkr_withdrawal/": 1,
|
|
"mkr_address/": 1,
|
|
"zrx_withdrawal/": 1,
|
|
"zrx_address/": 1,
|
|
"gusd_withdrawal/": 1,
|
|
"gusd_address/": 1,
|
|
"aave_withdrawal/": 1,
|
|
"aave_address/": 1,
|
|
"bat_withdrawal/": 1,
|
|
"bat_address/": 1,
|
|
"uma_withdrawal/": 1,
|
|
"uma_address/": 1,
|
|
"snx_withdrawal/": 1,
|
|
"snx_address/": 1,
|
|
"uni_withdrawal/": 1,
|
|
"uni_address/": 1,
|
|
"yfi_withdrawal/": 1,
|
|
"yfi_address/": 1,
|
|
"audio_withdrawal/": 1,
|
|
"audio_address/": 1,
|
|
"crv_withdrawal/": 1,
|
|
"crv_address/": 1,
|
|
"algo_withdrawal/": 1,
|
|
"algo_address/": 1,
|
|
"comp_withdrawal/": 1,
|
|
"comp_address/": 1,
|
|
"grt_withdrawal/": 1,
|
|
"grt_address/": 1,
|
|
"usdt_withdrawal/": 1,
|
|
"usdt_address/": 1,
|
|
"eurt_withdrawal/": 1,
|
|
"eurt_address/": 1,
|
|
"matic_withdrawal/": 1,
|
|
"matic_address/": 1,
|
|
"sushi_withdrawal/": 1,
|
|
"sushi_address/": 1,
|
|
"chz_withdrawal/": 1,
|
|
"chz_address/": 1,
|
|
"enj_withdrawal/": 1,
|
|
"enj_address/": 1,
|
|
"alpha_withdrawal/": 1,
|
|
"alpha_address/": 1,
|
|
"ftt_withdrawal/": 1,
|
|
"ftt_address/": 1,
|
|
"storj_withdrawal/": 1,
|
|
"storj_address/": 1,
|
|
"axs_withdrawal/": 1,
|
|
"axs_address/": 1,
|
|
"sand_withdrawal/": 1,
|
|
"sand_address/": 1,
|
|
"hbar_withdrawal/": 1,
|
|
"hbar_address/": 1,
|
|
"rgt_withdrawal/": 1,
|
|
"rgt_address/": 1,
|
|
"fet_withdrawal/": 1,
|
|
"fet_address/": 1,
|
|
"skl_withdrawal/": 1,
|
|
"skl_address/": 1,
|
|
"cel_withdrawal/": 1,
|
|
"cel_address/": 1,
|
|
"sxp_withdrawal/": 1,
|
|
"sxp_address/": 1,
|
|
"ada_withdrawal/": 1,
|
|
"ada_address/": 1,
|
|
"slp_withdrawal/": 1,
|
|
"slp_address/": 1,
|
|
"ftm_withdrawal/": 1,
|
|
"ftm_address/": 1,
|
|
"perp_withdrawal/": 1,
|
|
"perp_address/": 1,
|
|
"dydx_withdrawal/": 1,
|
|
"dydx_address/": 1,
|
|
"gala_withdrawal/": 1,
|
|
"gala_address/": 1,
|
|
"shib_withdrawal/": 1,
|
|
"shib_address/": 1,
|
|
"amp_withdrawal/": 1,
|
|
"amp_address/": 1,
|
|
"sgb_withdrawal/": 1,
|
|
"sgb_address/": 1,
|
|
"avax_withdrawal/": 1,
|
|
"avax_address/": 1,
|
|
"wbtc_withdrawal/": 1,
|
|
"wbtc_address/": 1,
|
|
"ctsi_withdrawal/": 1,
|
|
"ctsi_address/": 1,
|
|
"cvx_withdrawal/": 1,
|
|
"cvx_address/": 1,
|
|
"imx_withdrawal/": 1,
|
|
"imx_address/": 1,
|
|
"nexo_withdrawal/": 1,
|
|
"nexo_address/": 1,
|
|
"ust_withdrawal/": 1,
|
|
"ust_address/": 1,
|
|
"ant_withdrawal/": 1,
|
|
"ant_address/": 1,
|
|
"gods_withdrawal/": 1,
|
|
"gods_address/": 1,
|
|
"rad_withdrawal/": 1,
|
|
"rad_address/": 1,
|
|
"band_withdrawal/": 1,
|
|
"band_address/": 1,
|
|
"inj_withdrawal/": 1,
|
|
"inj_address/": 1,
|
|
"rly_withdrawal/": 1,
|
|
"rly_address/": 1,
|
|
"rndr_withdrawal/": 1,
|
|
"rndr_address/": 1,
|
|
"vega_withdrawal/": 1,
|
|
"vega_address/": 1,
|
|
"1inch_withdrawal/": 1,
|
|
"1inch_address/": 1,
|
|
"ens_withdrawal/": 1,
|
|
"ens_address/": 1,
|
|
"mana_withdrawal/": 1,
|
|
"mana_address/": 1,
|
|
"lrc_withdrawal/": 1,
|
|
"lrc_address/": 1,
|
|
"ape_withdrawal/": 1,
|
|
"ape_address/": 1,
|
|
"mpl_withdrawal/": 1,
|
|
"mpl_address/": 1,
|
|
"euroc_withdrawal/": 1,
|
|
"euroc_address/": 1,
|
|
"sol_withdrawal/": 1,
|
|
"sol_address/": 1,
|
|
"dot_withdrawal/": 1,
|
|
"dot_address/": 1,
|
|
"near_withdrawal/": 1,
|
|
"near_address/": 1,
|
|
"doge_withdrawal/": 1,
|
|
"doge_address/": 1,
|
|
"flr_withdrawal/": 1,
|
|
"flr_address/": 1,
|
|
"dgld_withdrawal/": 1,
|
|
"dgld_address/": 1,
|
|
"ldo_withdrawal/": 1,
|
|
"ldo_address/": 1,
|
|
"travel_rule/contacts/": 1,
|
|
"earn/subscribe/": 1,
|
|
"earn/subscriptions/setting/": 1,
|
|
"earn/unsubscribe": 1,
|
|
"wecan_withdrawal/": 1,
|
|
"wecan_address/": 1,
|
|
"trac_withdrawal/": 1,
|
|
"trac_address/": 1,
|
|
"eurcv_withdrawal/": 1,
|
|
"eurcv_address/": 1,
|
|
"pyusd_withdrawal/": 1,
|
|
"pyusd_address/": 1,
|
|
"lmwr_withdrawal/": 1,
|
|
"lmwr_address/": 1,
|
|
"pepe_withdrawal/": 1,
|
|
"pepe_address/": 1,
|
|
"blur_withdrawal/": 1,
|
|
"blur_address/": 1,
|
|
"vext_withdrawal/": 1,
|
|
"vext_address/": 1,
|
|
"cspr_withdrawal/": 1,
|
|
"cspr_address/": 1,
|
|
"vchf_withdrawal/": 1,
|
|
"vchf_address/": 1,
|
|
"veur_withdrawal/": 1,
|
|
"veur_address/": 1,
|
|
"truf_withdrawal/": 1,
|
|
"truf_address/": 1,
|
|
"wif_withdrawal/": 1,
|
|
"wif_address/": 1,
|
|
"smt_withdrawal/": 1,
|
|
"smt_address/": 1,
|
|
"sui_withdrawal/": 1,
|
|
"sui_address/": 1,
|
|
"jup_withdrawal/": 1,
|
|
"jup_address/": 1,
|
|
"ondo_withdrawal/": 1,
|
|
"ondo_address/": 1,
|
|
"boba_withdrawal/": 1,
|
|
"boba_address/": 1,
|
|
"pyth_withdrawal/": 1,
|
|
"pyth_address/": 1,
|
|
},
|
|
},
|
|
},
|
|
"fees": map[string]interface{} {
|
|
"trading": map[string]interface{} {
|
|
"tierBased": true,
|
|
"percentage": true,
|
|
"taker": this.ParseNumber("0.004"),
|
|
"maker": this.ParseNumber("0.004"),
|
|
"tiers": map[string]interface{} {
|
|
"taker": []interface{}{[]interface{}{this.ParseNumber("0"), this.ParseNumber("0.004")}, []interface{}{this.ParseNumber("10000"), this.ParseNumber("0.003")}, []interface{}{this.ParseNumber("100000"), this.ParseNumber("0.002")}, []interface{}{this.ParseNumber("500000"), this.ParseNumber("0.0018")}, []interface{}{this.ParseNumber("1500000"), this.ParseNumber("0.0016")}, []interface{}{this.ParseNumber("5000000"), this.ParseNumber("0.0012")}, []interface{}{this.ParseNumber("20000000"), this.ParseNumber("0.001")}, []interface{}{this.ParseNumber("50000000"), this.ParseNumber("0.0008")}, []interface{}{this.ParseNumber("100000000"), this.ParseNumber("0.0006")}, []interface{}{this.ParseNumber("250000000"), this.ParseNumber("0.0005")}, []interface{}{this.ParseNumber("1000000000"), this.ParseNumber("0.0003")}},
|
|
"maker": []interface{}{[]interface{}{this.ParseNumber("0"), this.ParseNumber("0.003")}, []interface{}{this.ParseNumber("10000"), this.ParseNumber("0.002")}, []interface{}{this.ParseNumber("100000"), this.ParseNumber("0.001")}, []interface{}{this.ParseNumber("500000"), this.ParseNumber("0.0008")}, []interface{}{this.ParseNumber("1500000"), this.ParseNumber("0.0006")}, []interface{}{this.ParseNumber("5000000"), this.ParseNumber("0.0003")}, []interface{}{this.ParseNumber("20000000"), this.ParseNumber("0.002")}, []interface{}{this.ParseNumber("50000000"), this.ParseNumber("0.0001")}, []interface{}{this.ParseNumber("100000000"), this.ParseNumber("0")}, []interface{}{this.ParseNumber("250000000"), this.ParseNumber("0")}, []interface{}{this.ParseNumber("1000000000"), this.ParseNumber("0")}},
|
|
},
|
|
},
|
|
"funding": map[string]interface{} {
|
|
"tierBased": false,
|
|
"percentage": false,
|
|
"withdraw": map[string]interface{} {},
|
|
"deposit": map[string]interface{} {
|
|
"BTC": 0,
|
|
"BCH": 0,
|
|
"LTC": 0,
|
|
"ETH": 0,
|
|
"XRP": 0,
|
|
"XLM": 0,
|
|
"PAX": 0,
|
|
"USD": 7.5,
|
|
"EUR": 0,
|
|
},
|
|
},
|
|
},
|
|
"precisionMode": TICK_SIZE,
|
|
"commonCurrencies": map[string]interface{} {
|
|
"UST": "USTC",
|
|
},
|
|
"options": map[string]interface{} {
|
|
"networksById": map[string]interface{} {
|
|
"bitcoin-cash": "BCH",
|
|
"bitcoin": "BTC",
|
|
"ethereum": "ERC20",
|
|
"litecoin": "LTC",
|
|
"stellar": "XLM",
|
|
"xrpl": "XRP",
|
|
"tron": "TRC20",
|
|
"algorand": "ALGO",
|
|
"flare": "FLR",
|
|
"hedera": "HBAR",
|
|
"cardana": "ADA",
|
|
"songbird": "FLR",
|
|
"avalanche-c-chain": "AVAX",
|
|
"solana": "SOL",
|
|
"polkadot": "DOT",
|
|
"near": "NEAR",
|
|
"doge": "DOGE",
|
|
"sui": "SUI",
|
|
"casper": "CSRP",
|
|
},
|
|
},
|
|
"exceptions": map[string]interface{} {
|
|
"exact": map[string]interface{} {
|
|
"No permission found": PermissionDenied,
|
|
"API key not found": AuthenticationError,
|
|
"IP address not allowed": PermissionDenied,
|
|
"Invalid nonce": InvalidNonce,
|
|
"Invalid signature": AuthenticationError,
|
|
"Authentication failed": AuthenticationError,
|
|
"Missing key, signature and nonce parameters": AuthenticationError,
|
|
"Wrong API key format": AuthenticationError,
|
|
"Your account is frozen": PermissionDenied,
|
|
"Please update your profile with your FATCA information, before using API.": PermissionDenied,
|
|
"Order not found.": OrderNotFound,
|
|
"Price is more than 20% below market price.": InvalidOrder,
|
|
"Bitstamp.net is under scheduled maintenance. We\\'ll be back soon.": OnMaintenance,
|
|
"Order could not be placed.": ExchangeNotAvailable,
|
|
"Invalid offset.": BadRequest,
|
|
},
|
|
"broad": map[string]interface{} {
|
|
"Minimum order size is": InvalidOrder,
|
|
"Check your account balance for details.": InsufficientFunds,
|
|
"Ensure this value has at least": InvalidAddress,
|
|
"Ensure that there are no more than": InvalidOrder,
|
|
},
|
|
},
|
|
"features": map[string]interface{} {
|
|
"spot": map[string]interface{} {
|
|
"sandbox": false,
|
|
"createOrder": map[string]interface{} {
|
|
"marginMode": false,
|
|
"triggerPrice": false,
|
|
"triggerPriceType": nil,
|
|
"triggerDirection": false,
|
|
"stopLossPrice": false,
|
|
"takeProfitPrice": false,
|
|
"attachedStopLossTakeProfit": nil,
|
|
"timeInForce": map[string]interface{} {
|
|
"IOC": true,
|
|
"FOK": true,
|
|
"PO": true,
|
|
"GTD": true,
|
|
},
|
|
"hedged": false,
|
|
"trailing": false,
|
|
"leverage": false,
|
|
"marketBuyByCost": false,
|
|
"marketBuyRequiresPrice": false,
|
|
"selfTradePrevention": false,
|
|
"iceberg": false,
|
|
},
|
|
"createOrders": nil,
|
|
"fetchMyTrades": map[string]interface{} {
|
|
"marginMode": false,
|
|
"limit": 1000,
|
|
"daysBack": nil,
|
|
"untilDays": 30,
|
|
"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": nil,
|
|
"fetchOHLCV": map[string]interface{} {
|
|
"limit": 1000,
|
|
},
|
|
},
|
|
"swap": map[string]interface{} {
|
|
"linear": nil,
|
|
"inverse": nil,
|
|
},
|
|
"future": map[string]interface{} {
|
|
"linear": nil,
|
|
"inverse": nil,
|
|
},
|
|
},
|
|
})
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitstamp#fetchMarkets
|
|
* @description retrieves data on all markets for bitstamp
|
|
* @see https://www.bitstamp.net/api/#tag/Market-info/operation/GetTradingPairsInfo
|
|
* @param {object} [params] extra parameters specific to the exchange API endpoint
|
|
* @returns {object[]} an array of objects representing market data
|
|
*/
|
|
func (this *bitstamp) 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
|
|
|
|
response:= (<-this.FetchMarketsFromCache(params))
|
|
PanicOnError(response)
|
|
//
|
|
// [
|
|
// {
|
|
// "trading": "Enabled",
|
|
// "base_decimals": 8,
|
|
// "url_symbol": "btcusd",
|
|
// "name": "BTC/USD",
|
|
// "instant_and_market_orders": "Enabled",
|
|
// "minimum_order": "20.0 USD",
|
|
// "counter_decimals": 2,
|
|
// "description": "Bitcoin / U.S. dollar"
|
|
// }
|
|
// ]
|
|
//
|
|
var result interface{} = []interface{}{}
|
|
for i := 0; IsLessThan(i, GetArrayLength(response)); i++ {
|
|
var market interface{} = GetValue(response, i)
|
|
var name interface{} = this.SafeString(market, "name")
|
|
basequoteVariable := Split(name, "/");
|
|
base := GetValue(basequoteVariable,0);
|
|
quote := GetValue(basequoteVariable,1)
|
|
var baseId interface{} = ToLower(base)
|
|
var quoteId interface{} = ToLower(quote)
|
|
base = this.SafeCurrencyCode(base)
|
|
quote = this.SafeCurrencyCode(quote)
|
|
var minimumOrder interface{} = this.SafeString(market, "minimum_order")
|
|
var parts interface{} = Split(minimumOrder, " ")
|
|
var status interface{} = this.SafeString(market, "trading")
|
|
AppendToArray(&result,map[string]interface{} {
|
|
"id": this.SafeString(market, "url_symbol"),
|
|
"marketId": Add(Add(baseId, "_"), quoteId),
|
|
"symbol": Add(Add(base, "/"), quote),
|
|
"base": base,
|
|
"quote": quote,
|
|
"settle": nil,
|
|
"baseId": baseId,
|
|
"quoteId": quoteId,
|
|
"settleId": nil,
|
|
"type": "spot",
|
|
"spot": true,
|
|
"margin": false,
|
|
"future": false,
|
|
"swap": false,
|
|
"option": false,
|
|
"active": (IsEqual(status, "Enabled")),
|
|
"contract": false,
|
|
"linear": nil,
|
|
"inverse": nil,
|
|
"contractSize": nil,
|
|
"expiry": nil,
|
|
"expiryDatetime": nil,
|
|
"strike": nil,
|
|
"optionType": nil,
|
|
"precision": map[string]interface{} {
|
|
"amount": this.ParseNumber(this.ParsePrecision(this.SafeString(market, "base_decimals"))),
|
|
"price": this.ParseNumber(this.ParsePrecision(this.SafeString(market, "counter_decimals"))),
|
|
},
|
|
"limits": map[string]interface{} {
|
|
"leverage": map[string]interface{} {
|
|
"min": nil,
|
|
"max": nil,
|
|
},
|
|
"amount": map[string]interface{} {
|
|
"min": nil,
|
|
"max": nil,
|
|
},
|
|
"price": map[string]interface{} {
|
|
"min": nil,
|
|
"max": nil,
|
|
},
|
|
"cost": map[string]interface{} {
|
|
"min": this.SafeNumber(parts, 0),
|
|
"max": nil,
|
|
},
|
|
},
|
|
"created": nil,
|
|
"info": market,
|
|
})
|
|
}
|
|
|
|
ch <- result
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
func (this *bitstamp) ConstructCurrencyObject(id interface{}, code interface{}, name interface{}, precision interface{}, minCost interface{}, originalPayload interface{}) interface{} {
|
|
var currencyType interface{} = "crypto"
|
|
var description interface{} = this.Describe()
|
|
if IsTrue(this.IsFiat(code)) {
|
|
currencyType = "fiat"
|
|
}
|
|
var tickSize interface{} = this.ParseNumber(this.ParsePrecision(this.NumberToString(precision)))
|
|
return map[string]interface{} {
|
|
"id": id,
|
|
"code": code,
|
|
"info": originalPayload,
|
|
"type": currencyType,
|
|
"name": name,
|
|
"active": true,
|
|
"deposit": nil,
|
|
"withdraw": nil,
|
|
"fee": this.SafeNumber(GetValue(GetValue(GetValue(description, "fees"), "funding"), "withdraw"), code),
|
|
"precision": tickSize,
|
|
"limits": map[string]interface{} {
|
|
"amount": map[string]interface{} {
|
|
"min": tickSize,
|
|
"max": nil,
|
|
},
|
|
"price": map[string]interface{} {
|
|
"min": tickSize,
|
|
"max": nil,
|
|
},
|
|
"cost": map[string]interface{} {
|
|
"min": minCost,
|
|
"max": nil,
|
|
},
|
|
"withdraw": map[string]interface{} {
|
|
"min": nil,
|
|
"max": nil,
|
|
},
|
|
},
|
|
"networks": map[string]interface{} {},
|
|
}
|
|
}
|
|
func (this *bitstamp) FetchMarketsFromCache(optionalArgs ...interface{}) <- chan interface{} {
|
|
ch := make(chan interface{})
|
|
go func() interface{} {
|
|
defer close(ch)
|
|
defer ReturnPanicError(ch)
|
|
// this method is now redundant
|
|
// currencies are now fetched before markets
|
|
params := GetArg(optionalArgs, 0, map[string]interface{} {})
|
|
_ = params
|
|
var options interface{} = this.SafeValue(this.Options, "fetchMarkets", map[string]interface{} {})
|
|
var timestamp interface{} = this.SafeInteger(options, "timestamp")
|
|
var expires interface{} = this.SafeInteger(options, "expires", 1000)
|
|
var now interface{} = this.Milliseconds()
|
|
if IsTrue(IsTrue((IsEqual(timestamp, nil))) || IsTrue((IsGreaterThan((Subtract(now, timestamp)), expires)))) {
|
|
|
|
response:= (<-this.PublicGetTradingPairsInfo(params))
|
|
PanicOnError(response)
|
|
AddElementToObject(this.Options, "fetchMarkets", this.Extend(options, map[string]interface{} {
|
|
"response": response,
|
|
"timestamp": now,
|
|
}))
|
|
}
|
|
|
|
ch <- this.SafeValue(GetValue(this.Options, "fetchMarkets"), "response")
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitstamp#fetchCurrencies
|
|
* @description fetches all available currencies on an exchange
|
|
* @see https://www.bitstamp.net/api/#tag/Market-info/operation/GetTradingPairsInfo
|
|
* @param {object} [params] extra parameters specific to the exchange API endpoint
|
|
* @returns {object} an associative dictionary of currencies
|
|
*/
|
|
func (this *bitstamp) 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
|
|
|
|
response:= (<-this.FetchMarketsFromCache(params))
|
|
PanicOnError(response)
|
|
//
|
|
// [
|
|
// {
|
|
// "trading": "Enabled",
|
|
// "base_decimals": 8,
|
|
// "url_symbol": "btcusd",
|
|
// "name": "BTC/USD",
|
|
// "instant_and_market_orders": "Enabled",
|
|
// "minimum_order": "20.0 USD",
|
|
// "counter_decimals": 2,
|
|
// "description": "Bitcoin / U.S. dollar"
|
|
// },
|
|
// ]
|
|
//
|
|
var result interface{} = map[string]interface{} {}
|
|
for i := 0; IsLessThan(i, GetArrayLength(response)); i++ {
|
|
var market interface{} = GetValue(response, i)
|
|
var name interface{} = this.SafeString(market, "name")
|
|
basequoteVariable := Split(name, "/");
|
|
base := GetValue(basequoteVariable,0);
|
|
quote := GetValue(basequoteVariable,1)
|
|
var baseId interface{} = ToLower(base)
|
|
var quoteId interface{} = ToLower(quote)
|
|
base = this.SafeCurrencyCode(base)
|
|
quote = this.SafeCurrencyCode(quote)
|
|
var description interface{} = this.SafeString(market, "description")
|
|
baseDescriptionquoteDescriptionVariable := Split(description, " / ");
|
|
baseDescription := GetValue(baseDescriptionquoteDescriptionVariable,0);
|
|
quoteDescription := GetValue(baseDescriptionquoteDescriptionVariable,1)
|
|
var minimumOrder interface{} = this.SafeString(market, "minimum_order")
|
|
var parts interface{} = Split(minimumOrder, " ")
|
|
var cost interface{} = GetValue(parts, 0)
|
|
if !IsTrue((InOp(result, base))) {
|
|
var baseDecimals interface{} = this.SafeInteger(market, "base_decimals")
|
|
AddElementToObject(result, base, this.ConstructCurrencyObject(baseId, base, baseDescription, baseDecimals, nil, market))
|
|
}
|
|
if !IsTrue((InOp(result, quote))) {
|
|
var counterDecimals interface{} = this.SafeInteger(market, "counter_decimals")
|
|
AddElementToObject(result, quote, this.ConstructCurrencyObject(quoteId, quote, quoteDescription, counterDecimals, this.ParseNumber(cost), market))
|
|
}
|
|
}
|
|
|
|
ch <- result
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitstamp#fetchOrderBook
|
|
* @description fetches information on open orders with bid (buy) and ask (sell) prices, volumes and other data
|
|
* @see https://www.bitstamp.net/api/#tag/Order-book/operation/GetOrderBook
|
|
* @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
|
|
* @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 *bitstamp) 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
|
|
|
|
retRes7698 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes7698)
|
|
var market interface{} = this.Market(symbol)
|
|
var request interface{} = map[string]interface{} {
|
|
"pair": GetValue(market, "id"),
|
|
}
|
|
|
|
response:= (<-this.PublicGetOrderBookPair(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
//
|
|
// {
|
|
// "timestamp": "1583652948",
|
|
// "microtimestamp": "1583652948955826",
|
|
// "bids": [
|
|
// [ "8750.00", "1.33685271" ],
|
|
// [ "8749.39", "0.07700000" ],
|
|
// [ "8746.98", "0.07400000" ],
|
|
// ]
|
|
// "asks": [
|
|
// [ "8754.10", "1.51995636" ],
|
|
// [ "8754.71", "1.40000000" ],
|
|
// [ "8754.72", "2.50000000" ],
|
|
// ]
|
|
// }
|
|
//
|
|
var microtimestamp interface{} = this.SafeInteger(response, "microtimestamp")
|
|
var timestamp interface{} = this.ParseToInt(Divide(microtimestamp, 1000))
|
|
var orderbook interface{} = this.ParseOrderBook(response, GetValue(market, "symbol"), timestamp)
|
|
AddElementToObject(orderbook, "nonce", microtimestamp)
|
|
|
|
ch <- orderbook
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
func (this *bitstamp) ParseTicker(ticker interface{}, optionalArgs ...interface{}) interface{} {
|
|
//
|
|
// {
|
|
// "timestamp": "1686068944",
|
|
// "high": "26252",
|
|
// "last": "26216",
|
|
// "bid": "26208",
|
|
// "vwap": "25681",
|
|
// "volume": "3563.13819902",
|
|
// "low": "25350",
|
|
// "ask": "26211",
|
|
// "open": "25730",
|
|
// "open_24": "25895",
|
|
// "percent_change_24": "1.24",
|
|
// "pair": "BTC/USD"
|
|
// }
|
|
//
|
|
market := GetArg(optionalArgs, 0, nil)
|
|
_ = market
|
|
var marketId interface{} = this.SafeString(ticker, "pair")
|
|
var symbol interface{} = this.SafeSymbol(marketId, market, nil)
|
|
var timestamp interface{} = this.SafeTimestamp(ticker, "timestamp")
|
|
var vwap interface{} = this.SafeString(ticker, "vwap")
|
|
var baseVolume interface{} = this.SafeString(ticker, "volume")
|
|
var quoteVolume interface{} = Precise.StringMul(baseVolume, vwap)
|
|
var last interface{} = this.SafeString(ticker, "last")
|
|
return this.SafeTicker(map[string]interface{} {
|
|
"symbol": symbol,
|
|
"timestamp": timestamp,
|
|
"datetime": this.Iso8601(timestamp),
|
|
"high": this.SafeString(ticker, "high"),
|
|
"low": this.SafeString(ticker, "low"),
|
|
"bid": this.SafeString(ticker, "bid"),
|
|
"bidVolume": nil,
|
|
"ask": this.SafeString(ticker, "ask"),
|
|
"askVolume": nil,
|
|
"vwap": vwap,
|
|
"open": this.SafeString(ticker, "open"),
|
|
"close": last,
|
|
"last": last,
|
|
"previousClose": nil,
|
|
"change": nil,
|
|
"percentage": nil,
|
|
"average": nil,
|
|
"baseVolume": baseVolume,
|
|
"quoteVolume": quoteVolume,
|
|
"info": ticker,
|
|
}, market)
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitstamp#fetchTicker
|
|
* @description fetches a price ticker, a statistical calculation with the information calculated over the past 24 hours for a specific market
|
|
* @see https://www.bitstamp.net/api/#tag/Tickers/operation/GetMarketTicker
|
|
* @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 *bitstamp) 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
|
|
|
|
retRes8568 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes8568)
|
|
var market interface{} = this.Market(symbol)
|
|
var request interface{} = map[string]interface{} {
|
|
"pair": GetValue(market, "id"),
|
|
}
|
|
|
|
ticker:= (<-this.PublicGetTickerPair(this.Extend(request, params)))
|
|
PanicOnError(ticker)
|
|
|
|
//
|
|
// {
|
|
// "timestamp": "1686068944",
|
|
// "high": "26252",
|
|
// "last": "26216",
|
|
// "bid": "26208",
|
|
// "vwap": "25681",
|
|
// "volume": "3563.13819902",
|
|
// "low": "25350",
|
|
// "ask": "26211",
|
|
// "open": "25730",
|
|
// "open_24": "25895",
|
|
// "percent_change_24": "1.24"
|
|
// }
|
|
//
|
|
ch <- this.ParseTicker(ticker, market)
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitstamp#fetchTickers
|
|
* @description fetches price tickers for multiple markets, statistical information calculated over the past 24 hours for each market
|
|
* @see https://www.bitstamp.net/api/#tag/Tickers/operation/GetCurrencyPairTickers
|
|
* @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 *bitstamp) 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
|
|
|
|
retRes8908 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes8908)
|
|
|
|
response:= (<-this.PublicGetTicker(params))
|
|
PanicOnError(response)
|
|
|
|
//
|
|
// {
|
|
// "timestamp": "1686068944",
|
|
// "high": "26252",
|
|
// "last": "26216",
|
|
// "bid": "26208",
|
|
// "vwap": "25681",
|
|
// "volume": "3563.13819902",
|
|
// "low": "25350",
|
|
// "ask": "26211",
|
|
// "open": "25730",
|
|
// "open_24": "25895",
|
|
// "percent_change_24": "1.24",
|
|
// "pair": "BTC/USD"
|
|
// }
|
|
//
|
|
ch <- this.ParseTickers(response, symbols)
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
func (this *bitstamp) GetCurrencyIdFromTransaction(transaction interface{}) interface{} {
|
|
//
|
|
// {
|
|
// "fee": "0.00000000",
|
|
// "btc_usd": "0.00",
|
|
// "datetime": XXX,
|
|
// "usd": 0.0,
|
|
// "btc": 0.0,
|
|
// "eth": "0.05000000",
|
|
// "type": "0",
|
|
// "id": XXX,
|
|
// "eur": 0.0
|
|
// }
|
|
//
|
|
var currencyId interface{} = this.SafeStringLower(transaction, "currency")
|
|
if IsTrue(!IsEqual(currencyId, nil)) {
|
|
return currencyId
|
|
}
|
|
transaction = this.Omit(transaction, []interface{}{"fee", "price", "datetime", "type", "status", "id"})
|
|
var ids interface{} = ObjectKeys(transaction)
|
|
for i := 0; IsLessThan(i, GetArrayLength(ids)); i++ {
|
|
var id interface{} = GetValue(ids, i)
|
|
if IsTrue(IsLessThan(GetIndexOf(id, "_"), 0)) {
|
|
var value interface{} = this.SafeInteger(transaction, id)
|
|
if IsTrue(IsTrue((!IsEqual(value, nil))) && IsTrue((!IsEqual(value, 0)))) {
|
|
return id
|
|
}
|
|
}
|
|
}
|
|
return nil
|
|
}
|
|
func (this *bitstamp) GetMarketFromTrade(trade interface{}) interface{} {
|
|
trade = this.Omit(trade, []interface{}{"fee", "price", "datetime", "tid", "type", "order_id", "side"})
|
|
var currencyIds interface{} = ObjectKeys(trade)
|
|
var numCurrencyIds interface{} = GetArrayLength(currencyIds)
|
|
if IsTrue(IsGreaterThan(numCurrencyIds, 2)) {
|
|
panic(ExchangeError(Add(Add(Add(Add(this.Id, " getMarketFromTrade() too many keys: "), this.Json(currencyIds)), " in the trade: "), this.Json(trade))))
|
|
}
|
|
if IsTrue(IsEqual(numCurrencyIds, 2)) {
|
|
var marketId interface{} = Add(GetValue(currencyIds, 0), GetValue(currencyIds, 1))
|
|
if IsTrue(InOp(this.Markets_by_id, marketId)) {
|
|
return this.SafeMarket(marketId)
|
|
}
|
|
marketId = Add(GetValue(currencyIds, 1), GetValue(currencyIds, 0))
|
|
if IsTrue(InOp(this.Markets_by_id, marketId)) {
|
|
return this.SafeMarket(marketId)
|
|
}
|
|
}
|
|
return nil
|
|
}
|
|
func (this *bitstamp) ParseTrade(trade interface{}, optionalArgs ...interface{}) interface{} {
|
|
//
|
|
// fetchTrades (public)
|
|
//
|
|
// {
|
|
// "date": "1637845199",
|
|
// "tid": "209895701",
|
|
// "amount": "0.00500000",
|
|
// "type": "0", // Transaction type: 0 - buy; 1 - sell
|
|
// "price": "4451.25"
|
|
// }
|
|
//
|
|
// fetchMyTrades, trades returned within fetchOrder (private)
|
|
//
|
|
// {
|
|
// "fee": "0.11128",
|
|
// "eth_usdt": 4451.25,
|
|
// "datetime": "2021-11-25 12:59:59.322000",
|
|
// "usdt": "-22.26",
|
|
// "order_id": 1429545880227846,
|
|
// "usd": 0,
|
|
// "btc": 0,
|
|
// "eth": "0.00500000",
|
|
// "type": "2", // Transaction type: 0 - deposit; 1 - withdrawal; 2 - market trade; 14 - sub account transfer; 25 - credited with staked assets; 26 - sent assets to staking; 27 - staking reward; 32 - referral reward; 35 - inter account transfer.
|
|
// "id": 209895701,
|
|
// "eur": 0
|
|
// }
|
|
//
|
|
// from fetchOrder (private)
|
|
//
|
|
// {
|
|
// "fee": "0.11128",
|
|
// "price": "4451.25000000",
|
|
// "datetime": "2021-11-25 12:59:59.322000",
|
|
// "usdt": "22.25625000",
|
|
// "tid": 209895701,
|
|
// "eth": "0.00500000",
|
|
// "type": 2 // Transaction type: 0 - deposit; 1 - withdrawal; 2 - market trade
|
|
// }
|
|
//
|
|
market := GetArg(optionalArgs, 0, nil)
|
|
_ = market
|
|
var id interface{} = this.SafeString2(trade, "id", "tid")
|
|
var symbol interface{} = nil
|
|
var side interface{} = nil
|
|
var priceString interface{} = this.SafeString(trade, "price")
|
|
var amountString interface{} = this.SafeString(trade, "amount")
|
|
var orderId interface{} = this.SafeString(trade, "order_id")
|
|
var typeVar interface{} = nil
|
|
var costString interface{} = this.SafeString(trade, "cost")
|
|
var rawMarketId interface{} = nil
|
|
if IsTrue(IsEqual(market, nil)) {
|
|
var keys interface{} = ObjectKeys(trade)
|
|
for i := 0; IsLessThan(i, GetArrayLength(keys)); i++ {
|
|
var currentKey interface{} = GetValue(keys, i)
|
|
if IsTrue(IsTrue(!IsEqual(currentKey, "order_id")) && IsTrue(IsGreaterThanOrEqual(GetIndexOf(currentKey, "_"), 0))) {
|
|
rawMarketId = currentKey
|
|
market = this.SafeMarket(rawMarketId, market, "_")
|
|
}
|
|
}
|
|
}
|
|
// if the market is still not defined
|
|
// try to deduce it from used keys
|
|
if IsTrue(IsEqual(market, nil)) {
|
|
market = this.GetMarketFromTrade(trade)
|
|
}
|
|
var feeCostString interface{} = this.SafeString(trade, "fee")
|
|
var feeCurrency interface{} = GetValue(market, "quote")
|
|
var priceId interface{} = Ternary(IsTrue((!IsEqual(rawMarketId, nil))), rawMarketId, GetValue(market, "marketId"))
|
|
priceString = this.SafeString(trade, priceId, priceString)
|
|
amountString = this.SafeString(trade, GetValue(market, "baseId"), amountString)
|
|
costString = this.SafeString(trade, GetValue(market, "quoteId"), costString)
|
|
symbol = GetValue(market, "symbol")
|
|
var datetimeString interface{} = this.SafeString2(trade, "date", "datetime")
|
|
var timestamp interface{} = nil
|
|
if IsTrue(!IsEqual(datetimeString, nil)) {
|
|
if IsTrue(IsGreaterThanOrEqual(GetIndexOf(datetimeString, " "), 0)) {
|
|
// iso8601
|
|
timestamp = this.Parse8601(datetimeString)
|
|
} else {
|
|
// string unix epoch in seconds
|
|
timestamp = ParseInt(datetimeString)
|
|
timestamp = Multiply(timestamp, 1000)
|
|
}
|
|
}
|
|
// if it is a private trade
|
|
if IsTrue(InOp(trade, "id")) {
|
|
if IsTrue(!IsEqual(amountString, nil)) {
|
|
var isAmountNeg interface{} = Precise.StringLt(amountString, "0")
|
|
if IsTrue(isAmountNeg) {
|
|
side = "sell"
|
|
amountString = Precise.StringNeg(amountString)
|
|
} else {
|
|
side = "buy"
|
|
}
|
|
}
|
|
} else {
|
|
side = this.SafeString(trade, "type")
|
|
if IsTrue(IsEqual(side, "1")) {
|
|
side = "sell"
|
|
} else if IsTrue(IsEqual(side, "0")) {
|
|
side = "buy"
|
|
} else {
|
|
side = nil
|
|
}
|
|
}
|
|
if IsTrue(!IsEqual(costString, nil)) {
|
|
costString = Precise.StringAbs(costString)
|
|
}
|
|
var fee interface{} = nil
|
|
if IsTrue(!IsEqual(feeCostString, nil)) {
|
|
fee = map[string]interface{} {
|
|
"cost": feeCostString,
|
|
"currency": feeCurrency,
|
|
}
|
|
}
|
|
return this.SafeTrade(map[string]interface{} {
|
|
"id": id,
|
|
"info": trade,
|
|
"timestamp": timestamp,
|
|
"datetime": this.Iso8601(timestamp),
|
|
"symbol": symbol,
|
|
"order": orderId,
|
|
"type": typeVar,
|
|
"side": side,
|
|
"takerOrMaker": nil,
|
|
"price": priceString,
|
|
"amount": amountString,
|
|
"cost": costString,
|
|
"fee": fee,
|
|
}, market)
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitstamp#fetchTrades
|
|
* @description get the list of most recent trades for a particular symbol
|
|
* @see https://www.bitstamp.net/api/#tag/Transactions-public/operation/GetTransactions
|
|
* @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
|
|
* @param {object} [params] extra parameters specific to the exchange API endpoint
|
|
* @returns {Trade[]} a list of [trade structures]{@link https://docs.ccxt.com/#/?id=public-trades}
|
|
*/
|
|
func (this *bitstamp) 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
|
|
|
|
retRes11218 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes11218)
|
|
var market interface{} = this.Market(symbol)
|
|
var request interface{} = map[string]interface{} {
|
|
"pair": GetValue(market, "id"),
|
|
"time": "hour",
|
|
}
|
|
|
|
response:= (<-this.PublicGetTransactionsPair(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
|
|
//
|
|
// [
|
|
// {
|
|
// "date": "1551814435",
|
|
// "tid": "83581898",
|
|
// "price": "0.03532850",
|
|
// "type": "1",
|
|
// "amount": "0.85945907"
|
|
// },
|
|
// {
|
|
// "date": "1551814434",
|
|
// "tid": "83581896",
|
|
// "price": "0.03532851",
|
|
// "type": "1",
|
|
// "amount": "11.34130961"
|
|
// },
|
|
// ]
|
|
//
|
|
ch <- this.ParseTrades(response, market, since, limit)
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
func (this *bitstamp) ParseOHLCV(ohlcv interface{}, optionalArgs ...interface{}) interface{} {
|
|
//
|
|
// {
|
|
// "high": "9064.77",
|
|
// "timestamp": "1593961440",
|
|
// "volume": "18.49436608",
|
|
// "low": "9040.87",
|
|
// "close": "9064.77",
|
|
// "open": "9040.87"
|
|
// }
|
|
//
|
|
market := GetArg(optionalArgs, 0, nil)
|
|
_ = market
|
|
return []interface{}{this.SafeTimestamp(ohlcv, "timestamp"), this.SafeNumber(ohlcv, "open"), this.SafeNumber(ohlcv, "high"), this.SafeNumber(ohlcv, "low"), this.SafeNumber(ohlcv, "close"), this.SafeNumber(ohlcv, "volume")}
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitstamp#fetchOHLCV
|
|
* @description fetches historical candlestick data containing the open, high, low, and close price, and the volume of a market
|
|
* @see https://www.bitstamp.net/api/#tag/Market-info/operation/GetOHLCData
|
|
* @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
|
|
* @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
|
|
*/
|
|
func (this *bitstamp) 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, nil)
|
|
_ = limit
|
|
params := GetArg(optionalArgs, 3, map[string]interface{} {})
|
|
_ = params
|
|
|
|
retRes11838 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes11838)
|
|
var market interface{} = this.Market(symbol)
|
|
var request interface{} = map[string]interface{} {
|
|
"pair": GetValue(market, "id"),
|
|
"step": this.SafeString(this.Timeframes, timeframe, timeframe),
|
|
}
|
|
var duration interface{} = this.ParseTimeframe(timeframe)
|
|
if IsTrue(IsEqual(limit, nil)) {
|
|
if IsTrue(IsEqual(since, nil)) {
|
|
AddElementToObject(request, "limit", 1000) // we need to specify an allowed amount of `limit` if no `since` is set and there is no default limit by exchange
|
|
} else {
|
|
limit = 1000
|
|
var start interface{} = this.ParseToInt(Divide(since, 1000))
|
|
AddElementToObject(request, "start", start)
|
|
AddElementToObject(request, "end", this.Sum(start, Multiply(duration, (Subtract(limit, 1)))))
|
|
AddElementToObject(request, "limit", limit)
|
|
}
|
|
} else {
|
|
if IsTrue(!IsEqual(since, nil)) {
|
|
var start interface{} = this.ParseToInt(Divide(since, 1000))
|
|
AddElementToObject(request, "start", start)
|
|
AddElementToObject(request, "end", this.Sum(start, Multiply(duration, (Subtract(limit, 1)))))
|
|
}
|
|
AddElementToObject(request, "limit", mathMin(limit, 1000)) // min 1, max 1000
|
|
}
|
|
|
|
response:= (<-this.PublicGetOhlcPair(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
//
|
|
// {
|
|
// "data": {
|
|
// "pair": "BTC/USD",
|
|
// "ohlc": [
|
|
// {"high": "9064.77", "timestamp": "1593961440", "volume": "18.49436608", "low": "9040.87", "close": "9064.77", "open": "9040.87"},
|
|
// {"high": "9071.59", "timestamp": "1593961500", "volume": "3.48631711", "low": "9058.76", "close": "9061.07", "open": "9064.66"},
|
|
// {"high": "9067.33", "timestamp": "1593961560", "volume": "0.04142833", "low": "9061.94", "close": "9061.94", "open": "9067.33"},
|
|
// ],
|
|
// }
|
|
// }
|
|
//
|
|
var data interface{} = this.SafeValue(response, "data", map[string]interface{} {})
|
|
var ohlc interface{} = this.SafeList(data, "ohlc", []interface{}{})
|
|
|
|
ch <- this.ParseOHLCVs(ohlc, market, timeframe, since, limit)
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
func (this *bitstamp) ParseBalance(response interface{}) interface{} {
|
|
var result interface{} = map[string]interface{} {
|
|
"info": response,
|
|
"timestamp": nil,
|
|
"datetime": nil,
|
|
}
|
|
if IsTrue(IsEqual(response, nil)) {
|
|
response = []interface{}{}
|
|
}
|
|
for i := 0; IsLessThan(i, GetArrayLength(response)); i++ {
|
|
var currencyBalance interface{} = GetValue(response, i)
|
|
var currencyId interface{} = this.SafeString(currencyBalance, "currency")
|
|
var currencyCode interface{} = this.SafeCurrencyCode(currencyId)
|
|
var account interface{} = this.Account()
|
|
AddElementToObject(account, "free", this.SafeString(currencyBalance, "available"))
|
|
AddElementToObject(account, "used", this.SafeString(currencyBalance, "reserved"))
|
|
AddElementToObject(account, "total", this.SafeString(currencyBalance, "total"))
|
|
AddElementToObject(result, currencyCode, account)
|
|
}
|
|
return this.SafeBalance(result)
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitstamp#fetchBalance
|
|
* @description query for balance and get the amount of funds available for trading or funds locked in orders
|
|
* @see https://www.bitstamp.net/api/#tag/Account-balances/operation/GetAccountBalances
|
|
* @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 *bitstamp) FetchBalance(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
|
|
|
|
retRes12578 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes12578)
|
|
|
|
response:= (<-this.PrivatePostAccountBalances(params))
|
|
PanicOnError(response)
|
|
|
|
//
|
|
// [
|
|
// {
|
|
// "currency": "usdt",
|
|
// "total": "7.00000",
|
|
// "available": "7.00000",
|
|
// "reserved": "0.00000"
|
|
// },
|
|
// ...
|
|
// ]
|
|
//
|
|
ch <- this.ParseBalance(response)
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitstamp#fetchTradingFee
|
|
* @description fetch the trading fees for a market
|
|
* @see https://www.bitstamp.net/api/#tag/Fees/operation/GetTradingFeesForCurrency
|
|
* @param {string} symbol unified market symbol
|
|
* @param {object} [params] extra parameters specific to the exchange API endpoint
|
|
* @returns {object} a [fee structure]{@link https://docs.ccxt.com/#/?id=fee-structure}
|
|
*/
|
|
func (this *bitstamp) FetchTradingFee(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
|
|
|
|
retRes12838 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes12838)
|
|
var market interface{} = this.Market(symbol)
|
|
var request interface{} = map[string]interface{} {
|
|
"market_symbol": GetValue(market, "id"),
|
|
}
|
|
|
|
response:= (<-this.PrivatePostFeesTrading(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
//
|
|
// [
|
|
// {
|
|
// "currency_pair": "btcusd",
|
|
// "fees":
|
|
// {
|
|
// "maker": "0.15000",
|
|
// "taker": "0.16000"
|
|
// },
|
|
// "market": "btcusd"
|
|
// }
|
|
// ...
|
|
// ]
|
|
//
|
|
var tradingFeesByMarketId interface{} = this.IndexBy(response, "currency_pair")
|
|
var tradingFee interface{} = this.SafeDict(tradingFeesByMarketId, GetValue(market, "id"))
|
|
|
|
ch <- this.ParseTradingFee(tradingFee, market)
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
func (this *bitstamp) ParseTradingFee(fee interface{}, optionalArgs ...interface{}) interface{} {
|
|
market := GetArg(optionalArgs, 0, nil)
|
|
_ = market
|
|
var marketId interface{} = this.SafeString(fee, "market")
|
|
var fees interface{} = this.SafeDict(fee, "fees", map[string]interface{} {})
|
|
return map[string]interface{} {
|
|
"info": fee,
|
|
"symbol": this.SafeSymbol(marketId, market),
|
|
"maker": this.SafeNumber(fees, "maker"),
|
|
"taker": this.SafeNumber(fees, "taker"),
|
|
"percentage": nil,
|
|
"tierBased": nil,
|
|
}
|
|
}
|
|
func (this *bitstamp) ParseTradingFees(fees interface{}) interface{} {
|
|
var result interface{} = map[string]interface{} {
|
|
"info": fees,
|
|
}
|
|
var symbols interface{} = this.Symbols
|
|
for i := 0; IsLessThan(i, GetArrayLength(symbols)); i++ {
|
|
var symbol interface{} = GetValue(symbols, i)
|
|
var fee interface{} = this.ParseTradingFee(GetValue(fees, i))
|
|
AddElementToObject(result, symbol, fee)
|
|
}
|
|
return result
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitstamp#fetchTradingFees
|
|
* @description fetch the trading fees for multiple markets
|
|
* @see https://www.bitstamp.net/api/#tag/Fees/operation/GetAllTradingFees
|
|
* @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 *bitstamp) 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
|
|
|
|
retRes13418 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes13418)
|
|
|
|
response:= (<-this.PrivatePostFeesTrading(params))
|
|
PanicOnError(response)
|
|
|
|
//
|
|
// [
|
|
// {
|
|
// "currency_pair": "btcusd",
|
|
// "fees":
|
|
// {
|
|
// "maker": "0.15000",
|
|
// "taker": "0.16000"
|
|
// },
|
|
// "market": "btcusd"
|
|
// }
|
|
// ...
|
|
// ]
|
|
//
|
|
ch <- this.ParseTradingFees(response)
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitstamp#fetchTransactionFees
|
|
* @deprecated
|
|
* @description please use fetchDepositWithdrawFees instead
|
|
* @see https://www.bitstamp.net/api/#tag/Fees
|
|
* @param {string[]|undefined} codes list of unified currency codes
|
|
* @param {object} [params] extra parameters specific to the exchange API endpoint
|
|
* @returns {object[]} a list of [fee structures]{@link https://docs.ccxt.com/#/?id=fee-structure}
|
|
*/
|
|
func (this *bitstamp) FetchTransactionFees(optionalArgs ...interface{}) <- chan interface{} {
|
|
ch := make(chan interface{})
|
|
go func() interface{} {
|
|
defer close(ch)
|
|
defer ReturnPanicError(ch)
|
|
codes := GetArg(optionalArgs, 0, nil)
|
|
_ = codes
|
|
params := GetArg(optionalArgs, 1, map[string]interface{} {})
|
|
_ = params
|
|
|
|
retRes13718 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes13718)
|
|
|
|
response:= (<-this.PrivatePostFeesWithdrawal(params))
|
|
PanicOnError(response)
|
|
|
|
//
|
|
// [
|
|
// {
|
|
// "currency": "btc",
|
|
// "fee": "0.00015000",
|
|
// "network": "bitcoin"
|
|
// }
|
|
// ...
|
|
// ]
|
|
//
|
|
ch <- this.ParseTransactionFees(response)
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
func (this *bitstamp) ParseTransactionFees(response interface{}, optionalArgs ...interface{}) interface{} {
|
|
codes := GetArg(optionalArgs, 0, nil)
|
|
_ = codes
|
|
var result interface{} = map[string]interface{} {}
|
|
var currencies interface{} = this.IndexBy(response, "currency")
|
|
var ids interface{} = ObjectKeys(currencies)
|
|
for i := 0; IsLessThan(i, GetArrayLength(ids)); i++ {
|
|
var id interface{} = GetValue(ids, i)
|
|
var fees interface{} = this.SafeValue(response, i, map[string]interface{} {})
|
|
var code interface{} = this.SafeCurrencyCode(id)
|
|
if IsTrue(IsTrue((!IsEqual(codes, nil))) && !IsTrue(this.InArray(code, codes))) {
|
|
continue
|
|
}
|
|
AddElementToObject(result, code, map[string]interface{} {
|
|
"withdraw_fee": this.SafeNumber(fees, "fee"),
|
|
"deposit": map[string]interface{} {},
|
|
"info": this.SafeDict(currencies, id),
|
|
})
|
|
}
|
|
return result
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitstamp#fetchDepositWithdrawFees
|
|
* @description fetch deposit and withdraw fees
|
|
* @see https://www.bitstamp.net/api/#tag/Fees/operation/GetAllWithdrawalFees
|
|
* @param {string[]|undefined} codes list of unified currency codes
|
|
* @param {object} [params] extra parameters specific to the exchange API endpoint
|
|
* @returns {object[]} a list of [fee structures]{@link https://docs.ccxt.com/#/?id=fee-structure}
|
|
*/
|
|
func (this *bitstamp) FetchDepositWithdrawFees(optionalArgs ...interface{}) <- chan interface{} {
|
|
ch := make(chan interface{})
|
|
go func() interface{} {
|
|
defer close(ch)
|
|
defer ReturnPanicError(ch)
|
|
codes := GetArg(optionalArgs, 0, nil)
|
|
_ = codes
|
|
params := GetArg(optionalArgs, 1, map[string]interface{} {})
|
|
_ = params
|
|
|
|
retRes14168 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes14168)
|
|
|
|
response:= (<-this.PrivatePostFeesWithdrawal(params))
|
|
PanicOnError(response)
|
|
//
|
|
// [
|
|
// {
|
|
// "currency": "btc",
|
|
// "fee": "0.00015000",
|
|
// "network": "bitcoin"
|
|
// }
|
|
// ...
|
|
// ]
|
|
//
|
|
var responseByCurrencyId interface{} = this.GroupBy(response, "currency")
|
|
|
|
ch <- this.ParseDepositWithdrawFees(responseByCurrencyId, codes)
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
func (this *bitstamp) ParseDepositWithdrawFee(fee interface{}, optionalArgs ...interface{}) interface{} {
|
|
currency := GetArg(optionalArgs, 0, nil)
|
|
_ = currency
|
|
var result interface{} = this.DepositWithdrawFee(fee)
|
|
for j := 0; IsLessThan(j, GetArrayLength(fee)); j++ {
|
|
var networkEntry interface{} = GetValue(fee, j)
|
|
var networkId interface{} = this.SafeString(networkEntry, "network")
|
|
var networkCode interface{} = this.NetworkIdToCode(networkId)
|
|
var withdrawFee interface{} = this.SafeNumber(networkEntry, "fee")
|
|
AddElementToObject(result, "withdraw", map[string]interface{} {
|
|
"fee": withdrawFee,
|
|
"percentage": nil,
|
|
})
|
|
AddElementToObject(GetValue(result, "networks"), networkCode, map[string]interface{} {
|
|
"withdraw": map[string]interface{} {
|
|
"fee": withdrawFee,
|
|
"percentage": nil,
|
|
},
|
|
"deposit": map[string]interface{} {
|
|
"fee": nil,
|
|
"percentage": nil,
|
|
},
|
|
})
|
|
}
|
|
return result
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitstamp#createOrder
|
|
* @description create a trade order
|
|
* @see https://www.bitstamp.net/api/#tag/Orders/operation/OpenInstantBuyOrder
|
|
* @see https://www.bitstamp.net/api/#tag/Orders/operation/OpenMarketBuyOrder
|
|
* @see https://www.bitstamp.net/api/#tag/Orders/operation/OpenLimitBuyOrder
|
|
* @see https://www.bitstamp.net/api/#tag/Orders/operation/OpenInstantSellOrder
|
|
* @see https://www.bitstamp.net/api/#tag/Orders/operation/OpenMarketSellOrder
|
|
* @see https://www.bitstamp.net/api/#tag/Orders/operation/OpenLimitSellOrder
|
|
* @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 of currency you want to trade in units of 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
|
|
* @returns {object} an [order structure]{@link https://docs.ccxt.com/#/?id=order-structure}
|
|
*/
|
|
func (this *bitstamp) 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
|
|
|
|
retRes14768 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes14768)
|
|
var market interface{} = this.Market(symbol)
|
|
var request interface{} = map[string]interface{} {
|
|
"pair": GetValue(market, "id"),
|
|
"amount": this.AmountToPrecision(symbol, amount),
|
|
}
|
|
var clientOrderId interface{} = this.SafeString2(params, "client_order_id", "clientOrderId")
|
|
if IsTrue(!IsEqual(clientOrderId, nil)) {
|
|
AddElementToObject(request, "client_order_id", clientOrderId)
|
|
params = this.Omit(params, []interface{}{"clientOrderId"})
|
|
}
|
|
var response interface{} = nil
|
|
var capitalizedSide interface{} = this.Capitalize(side)
|
|
if IsTrue(IsEqual(typeVar, "market")) {
|
|
if IsTrue(IsEqual(capitalizedSide, "Buy")) {
|
|
|
|
response = (<-this.PrivatePostBuyMarketPair(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
} else {
|
|
|
|
response = (<-this.PrivatePostSellMarketPair(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
}
|
|
} else if IsTrue(IsEqual(typeVar, "instant")) {
|
|
if IsTrue(IsEqual(capitalizedSide, "Buy")) {
|
|
|
|
response = (<-this.PrivatePostBuyInstantPair(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
} else {
|
|
|
|
response = (<-this.PrivatePostSellInstantPair(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
}
|
|
} else {
|
|
AddElementToObject(request, "price", this.PriceToPrecision(symbol, price))
|
|
if IsTrue(IsEqual(capitalizedSide, "Buy")) {
|
|
|
|
response = (<-this.PrivatePostBuyPair(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
} else {
|
|
|
|
response = (<-this.PrivatePostSellPair(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
}
|
|
}
|
|
var order interface{} = this.ParseOrder(response, market)
|
|
AddElementToObject(order, "type", typeVar)
|
|
|
|
ch <- order
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitstamp#cancelOrder
|
|
* @description cancels an open order
|
|
* @see https://www.bitstamp.net/api/#tag/Orders/operation/CancelOrder
|
|
* @param {string} id 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 *bitstamp) 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
|
|
|
|
retRes15258 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes15258)
|
|
var request interface{} = map[string]interface{} {
|
|
"id": id,
|
|
}
|
|
|
|
response:= (<-this.PrivatePostCancelOrder(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
|
|
//
|
|
// {
|
|
// "id": 1453282316578816,
|
|
// "amount": "0.02035278",
|
|
// "price": "2100.45",
|
|
// "type": 0,
|
|
// "market": "BTC/USD"
|
|
// }
|
|
//
|
|
ch <- this.ParseOrder(response)
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitstamp#cancelAllOrders
|
|
* @description cancel all open orders
|
|
* @see https://www.bitstamp.net/api/#tag/Orders/operation/CancelAllOrders
|
|
* @see https://www.bitstamp.net/api/#tag/Orders/operation/CancelOrdersForMarket
|
|
* @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 *bitstamp) 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
|
|
|
|
retRes15538 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes15538)
|
|
var market interface{} = nil
|
|
var request interface{} = map[string]interface{} {}
|
|
var response interface{} = nil
|
|
if IsTrue(!IsEqual(symbol, nil)) {
|
|
market = this.Market(symbol)
|
|
AddElementToObject(request, "pair", GetValue(market, "id"))
|
|
|
|
response = (<-this.PrivatePostCancelAllOrdersPair(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
} else {
|
|
|
|
response = (<-this.PrivatePostCancelAllOrders(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
}
|
|
//
|
|
// {
|
|
// "canceled": [
|
|
// {
|
|
// "id": 1453282316578816,
|
|
// "amount": "0.02035278",
|
|
// "price": "2100.45",
|
|
// "type": 0,
|
|
// "currency_pair": "BTC/USD",
|
|
// "market": "BTC/USD"
|
|
// }
|
|
// ],
|
|
// "success": true
|
|
// }
|
|
//
|
|
var canceled interface{} = this.SafeList(response, "canceled")
|
|
|
|
ch <- this.ParseOrders(canceled)
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
func (this *bitstamp) ParseOrderStatus(status interface{}) interface{} {
|
|
var statuses interface{} = map[string]interface{} {
|
|
"In Queue": "open",
|
|
"Open": "open",
|
|
"Finished": "closed",
|
|
"Canceled": "canceled",
|
|
}
|
|
return this.SafeString(statuses, status, status)
|
|
}
|
|
func (this *bitstamp) FetchOrderStatus(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
|
|
|
|
retRes15948 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes15948)
|
|
var clientOrderId interface{} = this.SafeValue2(params, "client_order_id", "clientOrderId")
|
|
var request interface{} = map[string]interface{} {}
|
|
if IsTrue(!IsEqual(clientOrderId, nil)) {
|
|
AddElementToObject(request, "client_order_id", clientOrderId)
|
|
params = this.Omit(params, []interface{}{"client_order_id", "clientOrderId"})
|
|
} else {
|
|
AddElementToObject(request, "id", id)
|
|
}
|
|
|
|
response:= (<-this.PrivatePostOrderStatus(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
|
|
ch <- this.ParseOrderStatus(this.SafeString(response, "status"))
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitstamp#fetchOrder
|
|
* @description fetches information on an order made by the user
|
|
* @see https://www.bitstamp.net/api/#tag/Orders/operation/GetOrderStatus
|
|
* @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 *bitstamp) 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
|
|
|
|
retRes16188 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes16188)
|
|
var market interface{} = nil
|
|
if IsTrue(!IsEqual(symbol, nil)) {
|
|
market = this.Market(symbol)
|
|
}
|
|
var clientOrderId interface{} = this.SafeValue2(params, "client_order_id", "clientOrderId")
|
|
var request interface{} = map[string]interface{} {}
|
|
if IsTrue(!IsEqual(clientOrderId, nil)) {
|
|
AddElementToObject(request, "client_order_id", clientOrderId)
|
|
params = this.Omit(params, []interface{}{"client_order_id", "clientOrderId"})
|
|
} else {
|
|
AddElementToObject(request, "id", id)
|
|
}
|
|
|
|
response:= (<-this.PrivatePostOrderStatus(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
|
|
//
|
|
// {
|
|
// "status": "Finished",
|
|
// "id": 1429545880227846,
|
|
// "amount_remaining": "0.00000000",
|
|
// "transactions": [
|
|
// {
|
|
// "fee": "0.11128",
|
|
// "price": "4451.25000000",
|
|
// "datetime": "2021-11-25 12:59:59.322000",
|
|
// "usdt": "22.25625000",
|
|
// "tid": 209895701,
|
|
// "eth": "0.00500000",
|
|
// "type": 2
|
|
// }
|
|
// ]
|
|
// }
|
|
//
|
|
ch <- this.ParseOrder(response, market)
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitstamp#fetchMyTrades
|
|
* @description fetch all trades made by the user
|
|
* @see https://www.bitstamp.net/api/#tag/Transactions-private/operation/GetUserTransactions
|
|
* @see https://www.bitstamp.net/api/#tag/Transactions-private/operation/GetUserTransactionsForMarket
|
|
* @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 *bitstamp) 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
|
|
|
|
retRes16668 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes16668)
|
|
var request interface{} = map[string]interface{} {}
|
|
var method interface{} = "privatePostUserTransactions"
|
|
var market interface{} = nil
|
|
if IsTrue(!IsEqual(symbol, nil)) {
|
|
market = this.Market(symbol)
|
|
AddElementToObject(request, "pair", GetValue(market, "id"))
|
|
method = Add(method, "Pair")
|
|
}
|
|
if IsTrue(!IsEqual(limit, nil)) {
|
|
AddElementToObject(request, "limit", limit)
|
|
}
|
|
|
|
response:= (<-this.callDynamically(method, this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
var result interface{} = this.FilterBy(response, "type", "2")
|
|
|
|
ch <- this.ParseTrades(result, market, since, limit)
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitstamp#fetchDepositsWithdrawals
|
|
* @description fetch history of deposits and withdrawals
|
|
* @see https://www.bitstamp.net/api/#tag/Transactions-private/operation/GetUserTransactions
|
|
* @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 *bitstamp) 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
|
|
|
|
retRes16958 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes16958)
|
|
var request interface{} = map[string]interface{} {}
|
|
if IsTrue(!IsEqual(limit, nil)) {
|
|
AddElementToObject(request, "limit", limit)
|
|
}
|
|
|
|
response:= (<-this.PrivatePostUserTransactions(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
//
|
|
// [
|
|
// {
|
|
// "fee": "0.00000000",
|
|
// "btc_usd": "0.00",
|
|
// "id": 1234567894,
|
|
// "usd": 0,
|
|
// "btc": 0,
|
|
// "datetime": "2018-09-08 09:00:31",
|
|
// "type": "1",
|
|
// "xrp": "-20.00000000",
|
|
// "eur": 0,
|
|
// },
|
|
// {
|
|
// "fee": "0.00000000",
|
|
// "btc_usd": "0.00",
|
|
// "id": 1134567891,
|
|
// "usd": 0,
|
|
// "btc": 0,
|
|
// "datetime": "2018-09-07 18:47:52",
|
|
// "type": "0",
|
|
// "xrp": "20.00000000",
|
|
// "eur": 0,
|
|
// },
|
|
// ]
|
|
//
|
|
var currency interface{} = nil
|
|
if IsTrue(!IsEqual(code, nil)) {
|
|
currency = this.Currency(code)
|
|
}
|
|
var transactions interface{} = this.FilterByArray(response, "type", []interface{}{"0", "1"}, false)
|
|
|
|
ch <- this.ParseTransactions(transactions, currency, since, limit)
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitstamp#fetchWithdrawals
|
|
* @description fetch all withdrawals made from an account
|
|
* @see https://www.bitstamp.net/api/#tag/Withdrawals/operation/GetWithdrawalRequests
|
|
* @param {string} code unified currency code
|
|
* @param {int} [since] the earliest time in ms to fetch withdrawals for
|
|
* @param {int} [limit] the maximum number of withdrawals structures to retrieve
|
|
* @param {object} [params] extra parameters specific to the exchange API endpoint
|
|
* @returns {object[]} a list of [transaction structures]{@link https://docs.ccxt.com/#/?id=transaction-structure}
|
|
*/
|
|
func (this *bitstamp) FetchWithdrawals(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
|
|
|
|
retRes17478 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes17478)
|
|
var request interface{} = map[string]interface{} {}
|
|
if IsTrue(!IsEqual(since, nil)) {
|
|
AddElementToObject(request, "timedelta", Subtract(this.Milliseconds(), since))
|
|
} else {
|
|
AddElementToObject(request, "timedelta", 50000000) // use max bitstamp approved value
|
|
}
|
|
|
|
response:= (<-this.PrivatePostWithdrawalRequests(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
|
|
//
|
|
// [
|
|
// {
|
|
// "status": 2,
|
|
// "datetime": "2018-10-17 10:58:13",
|
|
// "currency": "BTC",
|
|
// "amount": "0.29669259",
|
|
// "address": "aaaaa",
|
|
// "type": 1,
|
|
// "id": 111111,
|
|
// "transaction_id": "xxxx",
|
|
// },
|
|
// {
|
|
// "status": 2,
|
|
// "datetime": "2018-10-17 10:55:17",
|
|
// "currency": "ETH",
|
|
// "amount": "1.11010664",
|
|
// "address": "aaaa",
|
|
// "type": 16,
|
|
// "id": 222222,
|
|
// "transaction_id": "xxxxx",
|
|
// },
|
|
// ]
|
|
//
|
|
ch <- this.ParseTransactions(response, nil, since, limit)
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
func (this *bitstamp) ParseTransaction(transaction interface{}, optionalArgs ...interface{}) interface{} {
|
|
//
|
|
// fetchDepositsWithdrawals
|
|
//
|
|
// {
|
|
// "fee": "0.00000000",
|
|
// "btc_usd": "0.00",
|
|
// "id": 1234567894,
|
|
// "usd": 0,
|
|
// "btc": 0,
|
|
// "datetime": "2018-09-08 09:00:31",
|
|
// "type": "1",
|
|
// "xrp": "-20.00000000",
|
|
// "eur": 0,
|
|
// }
|
|
//
|
|
// fetchWithdrawals
|
|
//
|
|
// {
|
|
// "status": 2,
|
|
// "datetime": "2018-10-17 10:58:13",
|
|
// "currency": "BTC",
|
|
// "amount": "0.29669259",
|
|
// "address": "aaaaa",
|
|
// "type": 1,
|
|
// "id": 111111,
|
|
// "transaction_id": "xxxx",
|
|
// }
|
|
//
|
|
// {
|
|
// "id": 3386432,
|
|
// "type": 14,
|
|
// "amount": "863.21332500",
|
|
// "status": 2,
|
|
// "address": "rE1sdh25BJQ3qFwngiTBwaq3zPGGYcrjp1?dt=1455",
|
|
// "currency": "XRP",
|
|
// "datetime": "2018-01-05 15:27:55",
|
|
// "transaction_id": "001743B03B0C79BA166A064AC0142917B050347B4CB23BA2AB4B91B3C5608F4C"
|
|
// }
|
|
//
|
|
currency := GetArg(optionalArgs, 0, nil)
|
|
_ = currency
|
|
var timestamp interface{} = this.Parse8601(this.SafeString(transaction, "datetime"))
|
|
var currencyId interface{} = this.GetCurrencyIdFromTransaction(transaction)
|
|
var code interface{} = this.SafeCurrencyCode(currencyId, currency)
|
|
var feeCost interface{} = this.SafeString(transaction, "fee")
|
|
var feeCurrency interface{} = nil
|
|
var amount interface{} = nil
|
|
if IsTrue(InOp(transaction, "amount")) {
|
|
amount = this.SafeString(transaction, "amount")
|
|
} else if IsTrue(!IsEqual(currency, nil)) {
|
|
amount = this.SafeString(transaction, GetValue(currency, "id"), amount)
|
|
feeCurrency = GetValue(currency, "code")
|
|
} else if IsTrue(IsTrue((!IsEqual(code, nil))) && IsTrue((!IsEqual(currencyId, nil)))) {
|
|
amount = this.SafeString(transaction, currencyId, amount)
|
|
feeCurrency = code
|
|
}
|
|
if IsTrue(!IsEqual(amount, nil)) {
|
|
// withdrawals have a negative amount
|
|
amount = Precise.StringAbs(amount)
|
|
}
|
|
var status interface{} = "ok"
|
|
if IsTrue(InOp(transaction, "status")) {
|
|
status = this.ParseTransactionStatus(this.SafeString(transaction, "status"))
|
|
}
|
|
var typeVar interface{} = nil
|
|
if IsTrue(InOp(transaction, "type")) {
|
|
// from fetchDepositsWithdrawals
|
|
var rawType interface{} = this.SafeString(transaction, "type")
|
|
if IsTrue(IsEqual(rawType, "0")) {
|
|
typeVar = "deposit"
|
|
} else if IsTrue(IsEqual(rawType, "1")) {
|
|
typeVar = "withdrawal"
|
|
}
|
|
} else {
|
|
// from fetchWithdrawals
|
|
typeVar = "withdrawal"
|
|
}
|
|
var tag interface{} = nil
|
|
var address interface{} = this.SafeString(transaction, "address")
|
|
if IsTrue(!IsEqual(address, nil)) {
|
|
// dt (destination tag) is embedded into the address field
|
|
var addressParts interface{} = Split(address, "?dt=")
|
|
var numParts interface{} = GetArrayLength(addressParts)
|
|
if IsTrue(IsGreaterThan(numParts, 1)) {
|
|
address = GetValue(addressParts, 0)
|
|
tag = GetValue(addressParts, 1)
|
|
}
|
|
}
|
|
var fee interface{} = map[string]interface{} {
|
|
"currency": nil,
|
|
"cost": nil,
|
|
"rate": nil,
|
|
}
|
|
if IsTrue(!IsEqual(feeCost, nil)) {
|
|
fee = map[string]interface{} {
|
|
"currency": feeCurrency,
|
|
"cost": feeCost,
|
|
"rate": nil,
|
|
}
|
|
}
|
|
return map[string]interface{} {
|
|
"info": transaction,
|
|
"id": this.SafeString(transaction, "id"),
|
|
"txid": this.SafeString(transaction, "transaction_id"),
|
|
"type": typeVar,
|
|
"currency": code,
|
|
"network": nil,
|
|
"amount": this.ParseNumber(amount),
|
|
"status": status,
|
|
"timestamp": timestamp,
|
|
"datetime": this.Iso8601(timestamp),
|
|
"address": address,
|
|
"addressFrom": nil,
|
|
"addressTo": address,
|
|
"tag": tag,
|
|
"tagFrom": nil,
|
|
"tagTo": tag,
|
|
"updated": nil,
|
|
"comment": nil,
|
|
"internal": nil,
|
|
"fee": fee,
|
|
}
|
|
}
|
|
func (this *bitstamp) ParseTransactionStatus(status interface{}) interface{} {
|
|
//
|
|
// withdrawals:
|
|
// 0 (open), 1 (in process), 2 (finished), 3 (canceled) or 4 (failed).
|
|
//
|
|
var statuses interface{} = map[string]interface{} {
|
|
"0": "pending",
|
|
"1": "pending",
|
|
"2": "ok",
|
|
"3": "canceled",
|
|
"4": "failed",
|
|
}
|
|
return this.SafeString(statuses, status, status)
|
|
}
|
|
func (this *bitstamp) ParseOrder(order interface{}, optionalArgs ...interface{}) interface{} {
|
|
//
|
|
// from fetch order:
|
|
// { status: "Finished",
|
|
// "id": 731693945,
|
|
// "client_order_id": '',
|
|
// "transactions":
|
|
// [ { fee: "0.000019",
|
|
// "price": "0.00015803",
|
|
// "datetime": "2018-01-07 10:45:34.132551",
|
|
// "btc": "0.0079015000000000",
|
|
// "tid": 42777395,
|
|
// "type": 2,
|
|
// "xrp": "50.00000000" } ] }
|
|
//
|
|
// partially filled order:
|
|
// { "id": 468646390,
|
|
// "client_order_id": "",
|
|
// "status": "Canceled",
|
|
// "transactions": [{
|
|
// "eth": "0.23000000",
|
|
// "fee": "0.09",
|
|
// "tid": 25810126,
|
|
// "usd": "69.8947000000000000",
|
|
// "type": 2,
|
|
// "price": "303.89000000",
|
|
// "datetime": "2017-11-11 07:22:20.710567"
|
|
// }]}
|
|
//
|
|
// from create order response:
|
|
// {
|
|
// "price": "0.00008012",
|
|
// "client_order_id": '',
|
|
// "currency_pair": "XRP/BTC",
|
|
// "datetime": "2019-01-31 21:23:36",
|
|
// "amount": "15.00000000",
|
|
// "type": "0",
|
|
// "id": "2814205012"
|
|
// }
|
|
//
|
|
// cancelOrder
|
|
//
|
|
// {
|
|
// "id": 1453282316578816,
|
|
// "amount": "0.02035278",
|
|
// "price": "2100.45",
|
|
// "type": 0,
|
|
// "market": "BTC/USD"
|
|
// }
|
|
//
|
|
market := GetArg(optionalArgs, 0, nil)
|
|
_ = market
|
|
var id interface{} = this.SafeString(order, "id")
|
|
var clientOrderId interface{} = this.SafeString(order, "client_order_id")
|
|
var side interface{} = this.SafeString(order, "type")
|
|
if IsTrue(!IsEqual(side, nil)) {
|
|
side = Ternary(IsTrue((IsEqual(side, "1"))), "sell", "buy")
|
|
}
|
|
// there is no timestamp from fetchOrder
|
|
var timestamp interface{} = this.Parse8601(this.SafeString(order, "datetime"))
|
|
var marketId interface{} = this.SafeStringLower(order, "currency_pair")
|
|
var symbol interface{} = this.SafeSymbol(marketId, market, "/")
|
|
var status interface{} = this.ParseOrderStatus(this.SafeString(order, "status"))
|
|
var amount interface{} = this.SafeString(order, "amount")
|
|
var transactions interface{} = this.SafeValue(order, "transactions", []interface{}{})
|
|
var price interface{} = this.SafeString(order, "price")
|
|
return this.SafeOrder(map[string]interface{} {
|
|
"id": id,
|
|
"clientOrderId": clientOrderId,
|
|
"datetime": this.Iso8601(timestamp),
|
|
"timestamp": timestamp,
|
|
"lastTradeTimestamp": nil,
|
|
"status": status,
|
|
"symbol": symbol,
|
|
"type": nil,
|
|
"timeInForce": nil,
|
|
"postOnly": nil,
|
|
"side": side,
|
|
"price": price,
|
|
"triggerPrice": nil,
|
|
"cost": nil,
|
|
"amount": amount,
|
|
"filled": nil,
|
|
"remaining": nil,
|
|
"trades": transactions,
|
|
"fee": nil,
|
|
"info": order,
|
|
"average": nil,
|
|
}, market)
|
|
}
|
|
func (this *bitstamp) ParseLedgerEntryType(typeVar interface{}) interface{} {
|
|
var types interface{} = map[string]interface{} {
|
|
"0": "transaction",
|
|
"1": "transaction",
|
|
"2": "trade",
|
|
"14": "transfer",
|
|
}
|
|
return this.SafeString(types, typeVar, typeVar)
|
|
}
|
|
func (this *bitstamp) ParseLedgerEntry(item interface{}, optionalArgs ...interface{}) interface{} {
|
|
//
|
|
// [
|
|
// {
|
|
// "fee": "0.00000000",
|
|
// "btc_usd": "0.00",
|
|
// "id": 1234567894,
|
|
// "usd": 0,
|
|
// "btc": 0,
|
|
// "datetime": "2018-09-08 09:00:31",
|
|
// "type": "1",
|
|
// "xrp": "-20.00000000",
|
|
// "eur": 0,
|
|
// },
|
|
// {
|
|
// "fee": "0.00000000",
|
|
// "btc_usd": "0.00",
|
|
// "id": 1134567891,
|
|
// "usd": 0,
|
|
// "btc": 0,
|
|
// "datetime": "2018-09-07 18:47:52",
|
|
// "type": "0",
|
|
// "xrp": "20.00000000",
|
|
// "eur": 0,
|
|
// },
|
|
// ]
|
|
//
|
|
currency := GetArg(optionalArgs, 0, nil)
|
|
_ = currency
|
|
var typeVar interface{} = this.ParseLedgerEntryType(this.SafeString(item, "type"))
|
|
if IsTrue(IsEqual(typeVar, "trade")) {
|
|
var parsedTrade interface{} = this.ParseTrade(item)
|
|
var market interface{} = nil
|
|
var keys interface{} = ObjectKeys(item)
|
|
for i := 0; IsLessThan(i, GetArrayLength(keys)); i++ {
|
|
if IsTrue(IsGreaterThanOrEqual(GetIndexOf(GetValue(keys, i), "_"), 0)) {
|
|
var marketId interface{} = Replace(GetValue(keys, i), "_", "")
|
|
market = this.SafeMarket(marketId, market)
|
|
}
|
|
}
|
|
// if the market is still not defined
|
|
// try to deduce it from used keys
|
|
if IsTrue(IsEqual(market, nil)) {
|
|
market = this.GetMarketFromTrade(item)
|
|
}
|
|
var direction interface{} = Ternary(IsTrue((IsEqual(GetValue(parsedTrade, "side"), "buy"))), "in", "out")
|
|
return this.SafeLedgerEntry(map[string]interface{} {
|
|
"info": item,
|
|
"id": GetValue(parsedTrade, "id"),
|
|
"timestamp": GetValue(parsedTrade, "timestamp"),
|
|
"datetime": GetValue(parsedTrade, "datetime"),
|
|
"direction": direction,
|
|
"account": nil,
|
|
"referenceId": GetValue(parsedTrade, "order"),
|
|
"referenceAccount": nil,
|
|
"type": typeVar,
|
|
"currency": GetValue(market, "base"),
|
|
"amount": GetValue(parsedTrade, "amount"),
|
|
"before": nil,
|
|
"after": nil,
|
|
"status": "ok",
|
|
"fee": GetValue(parsedTrade, "fee"),
|
|
}, currency)
|
|
} else {
|
|
var parsedTransaction interface{} = this.ParseTransaction(item, currency)
|
|
var direction interface{} = nil
|
|
if IsTrue(InOp(item, "amount")) {
|
|
var amount interface{} = this.SafeString(item, "amount")
|
|
direction = Ternary(IsTrue(Precise.StringGt(amount, "0")), "in", "out")
|
|
} else if IsTrue(IsTrue((InOp(parsedTransaction, "currency"))) && IsTrue(!IsEqual(GetValue(parsedTransaction, "currency"), nil))) {
|
|
var currencyCode interface{} = this.SafeString(parsedTransaction, "currency")
|
|
currency = this.Currency(currencyCode)
|
|
var amount interface{} = this.SafeString(item, GetValue(currency, "id"))
|
|
direction = Ternary(IsTrue(Precise.StringGt(amount, "0")), "in", "out")
|
|
}
|
|
return this.SafeLedgerEntry(map[string]interface{} {
|
|
"info": item,
|
|
"id": GetValue(parsedTransaction, "id"),
|
|
"timestamp": GetValue(parsedTransaction, "timestamp"),
|
|
"datetime": GetValue(parsedTransaction, "datetime"),
|
|
"direction": direction,
|
|
"account": nil,
|
|
"referenceId": GetValue(parsedTransaction, "txid"),
|
|
"referenceAccount": nil,
|
|
"type": typeVar,
|
|
"currency": GetValue(parsedTransaction, "currency"),
|
|
"amount": GetValue(parsedTransaction, "amount"),
|
|
"before": nil,
|
|
"after": nil,
|
|
"status": GetValue(parsedTransaction, "status"),
|
|
"fee": GetValue(parsedTransaction, "fee"),
|
|
}, currency)
|
|
}
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitstamp#fetchLedger
|
|
* @description fetch the history of changes, actions done by the user or operations that altered the balance of the user
|
|
* @see https://www.bitstamp.net/api/#tag/Transactions-private/operation/GetUserTransactions
|
|
* @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
|
|
* @param {object} [params] extra parameters specific to the exchange API endpoint
|
|
* @returns {object} a [ledger structure]{@link https://docs.ccxt.com/#/?id=ledger}
|
|
*/
|
|
func (this *bitstamp) 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
|
|
|
|
retRes21248 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes21248)
|
|
var request interface{} = map[string]interface{} {}
|
|
if IsTrue(!IsEqual(limit, nil)) {
|
|
AddElementToObject(request, "limit", limit)
|
|
}
|
|
|
|
response:= (<-this.PrivatePostUserTransactions(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
var currency interface{} = nil
|
|
if IsTrue(!IsEqual(code, nil)) {
|
|
currency = this.Currency(code)
|
|
}
|
|
|
|
ch <- this.ParseLedger(response, currency, since, limit)
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitstamp#fetchOpenOrders
|
|
* @description fetch all unfilled currently open orders
|
|
* @see https://www.bitstamp.net/api/#tag/Orders/operation/GetAllOpenOrders
|
|
* @see https://www.bitstamp.net/api/#tag/Orders/operation/GetOpenOrdersForMarket
|
|
* @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 *bitstamp) 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
|
|
var market interface{} = nil
|
|
|
|
retRes21518 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes21518)
|
|
if IsTrue(!IsEqual(symbol, nil)) {
|
|
market = this.Market(symbol)
|
|
}
|
|
|
|
response:= (<-this.PrivatePostOpenOrdersAll(params))
|
|
PanicOnError(response)
|
|
|
|
//
|
|
// [
|
|
// {
|
|
// "price": "0.00008012",
|
|
// "currency_pair": "XRP/BTC",
|
|
// "client_order_id": '',
|
|
// "datetime": "2019-01-31 21:23:36",
|
|
// "amount": "15.00000000",
|
|
// "type": "0",
|
|
// "id": "2814205012",
|
|
// }
|
|
// ]
|
|
//
|
|
ch <- this.ParseOrders(response, market, since, limit, map[string]interface{} {
|
|
"status": "open",
|
|
"type": "limit",
|
|
})
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
func (this *bitstamp) GetCurrencyName(code interface{}) interface{} {
|
|
/**
|
|
* @ignore
|
|
* @method
|
|
* @param {string} code Unified currency code
|
|
* @returns {string} lowercase version of code
|
|
*/
|
|
return ToLower(code)
|
|
}
|
|
func (this *bitstamp) IsFiat(code interface{}) interface{} {
|
|
return IsTrue(IsTrue(IsEqual(code, "USD")) || IsTrue(IsEqual(code, "EUR"))) || IsTrue(IsEqual(code, "GBP"))
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitstamp#fetchDepositAddress
|
|
* @description fetch the deposit address for a currency associated with this account
|
|
* @see https://www.bitstamp.net/api/#tag/Deposits/operation/GetCryptoDepositAddress
|
|
* @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 *bitstamp) 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
|
|
if IsTrue(this.IsFiat(code)) {
|
|
panic(NotSupported(Add(Add(Add(this.Id, " fiat fetchDepositAddress() for "), code), " is not supported!")))
|
|
}
|
|
var name interface{} = this.GetCurrencyName(code)
|
|
var method interface{} = Add(Add("privatePost", this.Capitalize(name)), "Address")
|
|
|
|
response:= (<-this.callDynamically(method, params))
|
|
PanicOnError(response)
|
|
var address interface{} = this.SafeString(response, "address")
|
|
var tag interface{} = this.SafeString2(response, "memo_id", "destination_tag")
|
|
this.CheckAddress(address)
|
|
|
|
ch <- map[string]interface{} {
|
|
"info": response,
|
|
"currency": code,
|
|
"network": nil,
|
|
"address": address,
|
|
"tag": tag,
|
|
}
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitstamp#withdraw
|
|
* @description make a withdrawal
|
|
* @see https://www.bitstamp.net/api/#tag/Withdrawals/operation/RequestFiatWithdrawal
|
|
* @see https://www.bitstamp.net/api/#tag/Withdrawals/operation/RequestCryptoWithdrawal
|
|
* @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 *bitstamp) Withdraw(code interface{}, amount interface{}, address interface{}, optionalArgs ...interface{}) <- chan interface{} {
|
|
ch := make(chan interface{})
|
|
go func() interface{} {
|
|
defer close(ch)
|
|
defer ReturnPanicError(ch)
|
|
// For fiat withdrawals please provide all required additional parameters in the 'params'
|
|
// Check https://www.bitstamp.net/api/ under 'Open bank withdrawal' for list and description.
|
|
tag := GetArg(optionalArgs, 0, nil)
|
|
_ = tag
|
|
params := GetArg(optionalArgs, 1, map[string]interface{} {})
|
|
_ = params
|
|
tagparamsVariable := this.HandleWithdrawTagAndParams(tag, params);
|
|
tag = GetValue(tagparamsVariable,0);
|
|
params = GetValue(tagparamsVariable,1)
|
|
|
|
retRes22348 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes22348)
|
|
this.CheckAddress(address)
|
|
var request interface{} = map[string]interface{} {
|
|
"amount": amount,
|
|
}
|
|
var currency interface{} = nil
|
|
var method interface{} = nil
|
|
if !IsTrue(this.IsFiat(code)) {
|
|
var name interface{} = this.GetCurrencyName(code)
|
|
method = Add(Add("privatePost", this.Capitalize(name)), "Withdrawal")
|
|
if IsTrue(IsEqual(code, "XRP")) {
|
|
if IsTrue(!IsEqual(tag, nil)) {
|
|
AddElementToObject(request, "destination_tag", tag)
|
|
}
|
|
} else if IsTrue(IsTrue(IsEqual(code, "XLM")) || IsTrue(IsEqual(code, "HBAR"))) {
|
|
if IsTrue(!IsEqual(tag, nil)) {
|
|
AddElementToObject(request, "memo_id", tag)
|
|
}
|
|
}
|
|
AddElementToObject(request, "address", address)
|
|
} else {
|
|
method = "privatePostWithdrawalOpen"
|
|
currency = this.Currency(code)
|
|
AddElementToObject(request, "iban", address)
|
|
AddElementToObject(request, "account_currency", GetValue(currency, "id"))
|
|
}
|
|
|
|
response:= (<-this.callDynamically(method, this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
|
|
ch <- this.ParseTransaction(response, currency)
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
/**
|
|
* @method
|
|
* @name bitstamp#transfer
|
|
* @description transfer currency internally between wallets on the same account
|
|
* @see https://www.bitstamp.net/api/#tag/Sub-account/operation/TransferFromMainToSub
|
|
* @see https://www.bitstamp.net/api/#tag/Sub-account/operation/TransferFromSubToMain
|
|
* @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 *bitstamp) 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)
|
|
params := GetArg(optionalArgs, 0, map[string]interface{} {})
|
|
_ = params
|
|
|
|
retRes22788 := (<-this.LoadMarkets())
|
|
PanicOnError(retRes22788)
|
|
var currency interface{} = this.Currency(code)
|
|
var request interface{} = map[string]interface{} {
|
|
"amount": this.ParseToNumeric(this.CurrencyToPrecision(code, amount)),
|
|
"currency": ToUpper(GetValue(currency, "id")),
|
|
}
|
|
var response interface{} = nil
|
|
if IsTrue(IsEqual(fromAccount, "main")) {
|
|
AddElementToObject(request, "subAccount", toAccount)
|
|
|
|
response = (<-this.PrivatePostTransferFromMain(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
} else if IsTrue(IsEqual(toAccount, "main")) {
|
|
AddElementToObject(request, "subAccount", fromAccount)
|
|
|
|
response = (<-this.PrivatePostTransferToMain(this.Extend(request, params)))
|
|
PanicOnError(response)
|
|
} else {
|
|
panic(BadRequest(Add(this.Id, " transfer() only supports from or to main")))
|
|
}
|
|
//
|
|
// { status: 'ok' }
|
|
//
|
|
var transfer interface{} = this.ParseTransfer(response, currency)
|
|
AddElementToObject(transfer, "amount", amount)
|
|
AddElementToObject(transfer, "fromAccount", fromAccount)
|
|
AddElementToObject(transfer, "toAccount", toAccount)
|
|
|
|
ch <- transfer
|
|
return nil
|
|
|
|
}()
|
|
return ch
|
|
}
|
|
func (this *bitstamp) ParseTransfer(transfer interface{}, optionalArgs ...interface{}) interface{} {
|
|
//
|
|
// { status: 'ok' }
|
|
//
|
|
currency := GetArg(optionalArgs, 0, nil)
|
|
_ = currency
|
|
var status interface{} = this.SafeString(transfer, "status")
|
|
return map[string]interface{} {
|
|
"info": transfer,
|
|
"id": nil,
|
|
"timestamp": nil,
|
|
"datetime": nil,
|
|
"currency": GetValue(currency, "code"),
|
|
"amount": nil,
|
|
"fromAccount": nil,
|
|
"toAccount": nil,
|
|
"status": this.ParseTransferStatus(status),
|
|
}
|
|
}
|
|
func (this *bitstamp) ParseTransferStatus(status interface{}) interface{} {
|
|
var statuses interface{} = map[string]interface{} {
|
|
"ok": "ok",
|
|
"error": "failed",
|
|
}
|
|
return this.SafeString(statuses, status, status)
|
|
}
|
|
func (this *bitstamp) Nonce() interface{} {
|
|
return this.Milliseconds()
|
|
}
|
|
func (this *bitstamp) 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 url interface{} = Add(GetValue(GetValue(this.Urls, "api"), api), "/")
|
|
url = Add(url, Add(this.Version, "/"))
|
|
url = Add(url, this.ImplodeParams(path, params))
|
|
var query interface{} = this.Omit(params, this.ExtractParams(path))
|
|
if IsTrue(IsEqual(api, "public")) {
|
|
if IsTrue(GetArrayLength(ObjectKeys(query))) {
|
|
url = Add(url, Add("?", this.Urlencode(query)))
|
|
}
|
|
} else {
|
|
this.CheckRequiredCredentials()
|
|
var xAuth interface{} = Add("BITSTAMP ", this.ApiKey)
|
|
var xAuthNonce interface{} = this.Uuid()
|
|
var xAuthTimestamp interface{} = ToString(this.Milliseconds())
|
|
var xAuthVersion interface{} = "v2"
|
|
var contentType interface{} = ""
|
|
headers = map[string]interface{} {
|
|
"X-Auth": xAuth,
|
|
"X-Auth-Nonce": xAuthNonce,
|
|
"X-Auth-Timestamp": xAuthTimestamp,
|
|
"X-Auth-Version": xAuthVersion,
|
|
}
|
|
if IsTrue(IsEqual(method, "POST")) {
|
|
if IsTrue(GetArrayLength(ObjectKeys(query))) {
|
|
body = this.Urlencode(query)
|
|
contentType = "application/x-www-form-urlencoded"
|
|
AddElementToObject(headers, "Content-Type", contentType)
|
|
} else {
|
|
// sending an empty POST request will trigger
|
|
// an API0020 error returned by the exchange
|
|
// therefore for empty requests we send a dummy object
|
|
// https://github.com/ccxt/ccxt/issues/6846
|
|
body = this.Urlencode(map[string]interface{} {
|
|
"foo": "bar",
|
|
})
|
|
contentType = "application/x-www-form-urlencoded"
|
|
AddElementToObject(headers, "Content-Type", contentType)
|
|
}
|
|
}
|
|
var authBody interface{} = Ternary(IsTrue(body), body, "")
|
|
var auth interface{} = Add(Add(Add(Add(Add(Add(Add(xAuth, method), Replace(url, "https://", "")), contentType), xAuthNonce), xAuthTimestamp), xAuthVersion), authBody)
|
|
var signature interface{} = this.Hmac(this.Encode(auth), this.Encode(this.Secret), sha256)
|
|
AddElementToObject(headers, "X-Auth-Signature", signature)
|
|
}
|
|
return map[string]interface{} {
|
|
"url": url,
|
|
"method": method,
|
|
"body": body,
|
|
"headers": headers,
|
|
}
|
|
}
|
|
func (this *bitstamp) HandleErrors(httpCode interface{}, reason interface{}, url interface{}, method interface{}, headers interface{}, body interface{}, response interface{}, requestHeaders interface{}, requestBody interface{}) interface{} {
|
|
if IsTrue(IsEqual(response, nil)) {
|
|
return nil
|
|
}
|
|
//
|
|
// {"error": "No permission found"} // fetchDepositAddress returns this on apiKeys that don't have the permission required
|
|
// {"status": "error", "reason": {"__all__": ["Minimum order size is 5.0 EUR."]}}
|
|
// reuse of a nonce gives: { status: 'error', reason: 'Invalid nonce', code: 'API0004' }
|
|
//
|
|
var status interface{} = this.SafeString(response, "status")
|
|
var error interface{} = this.SafeValue(response, "error")
|
|
if IsTrue(IsTrue((IsEqual(status, "error"))) || IsTrue((!IsEqual(error, nil)))) {
|
|
var errors interface{} = []interface{}{}
|
|
if IsTrue(IsString(error)) {
|
|
AppendToArray(&errors,error)
|
|
} else if IsTrue(!IsEqual(error, nil)) {
|
|
var keys interface{} = ObjectKeys(error)
|
|
for i := 0; IsLessThan(i, GetArrayLength(keys)); i++ {
|
|
var key interface{} = GetValue(keys, i)
|
|
var value interface{} = this.SafeValue(error, key)
|
|
if IsTrue(IsArray(value)) {
|
|
errors = this.ArrayConcat(errors, value)
|
|
} else {
|
|
AppendToArray(&errors,value)
|
|
}
|
|
}
|
|
}
|
|
var reasonInner interface{} = this.SafeValue(response, "reason", map[string]interface{} {})
|
|
if IsTrue(IsString(reasonInner)) {
|
|
AppendToArray(&errors,reasonInner)
|
|
} else {
|
|
var all interface{} = this.SafeValue(reasonInner, "__all__", []interface{}{})
|
|
for i := 0; IsLessThan(i, GetArrayLength(all)); i++ {
|
|
AppendToArray(&errors,GetValue(all, i))
|
|
}
|
|
}
|
|
var code interface{} = this.SafeString(response, "code")
|
|
if IsTrue(IsEqual(code, "API0005")) {
|
|
panic(AuthenticationError(Add(this.Id, " invalid signature, use the uid for the main account if you have subaccounts")))
|
|
}
|
|
var feedback interface{} = Add(Add(this.Id, " "), body)
|
|
for i := 0; IsLessThan(i, GetArrayLength(errors)); i++ {
|
|
var value interface{} = GetValue(errors, i)
|
|
this.ThrowExactlyMatchedException(GetValue(this.Exceptions, "exact"), value, feedback)
|
|
this.ThrowBroadlyMatchedException(GetValue(this.Exceptions, "broad"), value, feedback)
|
|
}
|
|
panic(ExchangeError(feedback))
|
|
}
|
|
return nil
|
|
}
|
|
|
|
|
|
func (this *bitstamp) Init(userConfig map[string]interface{}) {
|
|
this.Exchange = Exchange{}
|
|
this.Exchange.InitParent(userConfig, this.Describe().(map[string]interface{}), this)
|
|
this.Exchange.DerivedExchange = this
|
|
}
|