UNPKG

consequunturatque

Version:

A JavaScript / Python / PHP cryptocurrency trading library with support for 130+ exchanges

1,199 lines (1,170 loc) 62 kB
'use strict'; // --------------------------------------------------------------------------- const Exchange = require ('./base/Exchange'); const { ExchangeError, InsufficientFunds, BadRequest, BadSymbol, InvalidOrder, AuthenticationError, ArgumentsRequired, OrderNotFound, ExchangeNotAvailable } = require ('./base/errors'); const { TICK_SIZE } = require ('./base/functions/number'); const Precise = require ('./base/Precise'); // --------------------------------------------------------------------------- module.exports = class delta extends Exchange { describe () { return this.deepExtend (super.describe (), { 'id': 'delta', 'name': 'Delta Exchange', 'countries': [ 'VC' ], // Saint Vincent and the Grenadines 'rateLimit': 300, 'version': 'v2', // new metainfo interface 'has': { 'cancelAllOrders': true, 'cancelOrder': true, 'createOrder': true, 'editOrder': true, 'fetchBalance': true, 'fetchClosedOrders': true, 'fetchDepositAddress': true, 'fetchCurrencies': true, 'fetchLedger': true, 'fetchMarkets': true, 'fetchMyTrades': true, 'fetchOHLCV': true, 'fetchOpenOrders': true, 'fetchOrderBook': true, 'fetchStatus': true, 'fetchTicker': true, 'fetchTickers': true, 'fetchTime': true, 'fetchTrades': true, }, 'timeframes': { '1m': '1m', '3m': '3m', '5m': '5m', '15m': '15m', '30m': '30m', '1h': '1h', '2h': '2h', '4h': '4h', '6h': '6h', '1d': '1d', '7d': '7d', '1w': '1w', '2w': '2w', '1M': '30d', }, 'urls': { 'logo': 'https://user-images.githubusercontent.com/1294454/99450025-3be60a00-2931-11eb-9302-f4fd8d8589aa.jpg', 'test': { 'public': 'https://testnet-api.delta.exchange', 'private': 'https://testnet-api.delta.exchange', }, 'api': { 'public': 'https://api.delta.exchange', 'private': 'https://api.delta.exchange', }, 'www': 'https://www.delta.exchange', 'doc': [ 'https://docs.delta.exchange', ], 'fees': 'https://www.delta.exchange/fees', 'referral': 'https://www.delta.exchange/app/signup/?code=IULYNB', }, 'api': { 'public': { 'get': [ 'assets', 'settings', 'indices', 'products', 'tickers', 'tickers/{symbol}', 'l2orderbook/{symbol}', 'trades/{symbol}', 'history/candles', 'history/sparklines', ], }, 'private': { 'get': [ 'orders', 'orders/leverage', 'positions', 'positions/margined', 'orders/history', 'fills', 'fills/history/download/csv', 'wallet/balances', 'wallet/transactions', 'wallet/transactions/download', 'deposits/address', ], 'post': [ 'orders', 'orders/batch', 'orders/leverage', 'positions/change_margin', ], 'put': [ 'orders', 'orders/batch', ], 'delete': [ 'orders', 'orders/all', 'orders/batch', ], }, }, 'fees': { 'trading': { 'tierBased': true, 'percentage': true, 'taker': 0.15 / 100, 'maker': 0.10 / 100, 'tiers': { 'taker': [ [0, 0.15 / 100], [100, 0.13 / 100], [250, 0.13 / 100], [1000, 0.1 / 100], [5000, 0.09 / 100], [10000, 0.075 / 100], [20000, 0.065 / 100], ], 'maker': [ [0, 0.1 / 100], [100, 0.1 / 100], [250, 0.09 / 100], [1000, 0.075 / 100], [5000, 0.06 / 100], [10000, 0.05 / 100], [20000, 0.05 / 100], ], }, }, }, 'precisionMode': TICK_SIZE, 'requiredCredentials': { 'apiKey': true, 'secret': false, }, 'exceptions': { 'exact': { // Margin required to place order with selected leverage and quantity is insufficient. 'insufficient_margin': InsufficientFunds, // {"error":{"code":"insufficient_margin","context":{"available_balance":"0.000000000000000000","required_additional_balance":"1.618626000000000000000000000"}},"success":false} 'order_size_exceed_available': InvalidOrder, // The order book doesn't have sufficient liquidity, hence the order couldnt be filled, for example, ioc orders 'risk_limits_breached': BadRequest, // orders couldn't be placed as it will breach allowed risk limits. 'invalid_contract': BadSymbol, // The contract/product is either doesn't exist or has already expired. 'immediate_liquidation': InvalidOrder, // Order will cause immediate liquidation. 'out_of_bankruptcy': InvalidOrder, // Order prices are out of position bankruptcy limits. 'self_matching_disrupted_post_only': InvalidOrder, // Self matching is not allowed during auction. 'immediate_execution_post_only': InvalidOrder, // orders couldn't be placed as it includes post only orders which will be immediately executed 'bad_schema': BadRequest, // {"error":{"code":"bad_schema","context":{"schema_errors":[{"code":"validation_error","message":"id is required","param":""}]}},"success":false} 'invalid_api_key': AuthenticationError, // {"success":false,"error":{"code":"invalid_api_key"}} 'invalid_signature': AuthenticationError, // {"success":false,"error":{"code":"invalid_signature"}} 'open_order_not_found': OrderNotFound, // {"error":{"code":"open_order_not_found"},"success":false} 'unavailable': ExchangeNotAvailable, // {"error":{"code":"unavailable"},"success":false} }, 'broad': { }, }, }); } async fetchTime (params = {}) { const response = await this.publicGetSettings (params); // // { // "result":{ // "server_time":1605472733766141, // "deto_referral_mining_daily_reward":"25000", // "deto_total_reward_pool":"100000000", // "deto_trade_mining_daily_reward":"75000", // "kyc_deposit_limit":"20", // "kyc_withdrawal_limit":"2", // "under_maintenance":"false" // }, // "success":true // } // const result = this.safeValue (response, 'result', {}); return this.safeIntegerProduct (result, 'server_time', 0.001); } async fetchStatus (params = {}) { const response = await this.publicGetSettings (params); const result = this.safeValue (response, 'result', {}); const underMaintenance = this.safeValue (result, 'under_maintenance'); const status = (underMaintenance === 'true') ? 'maintenance' : 'ok'; const updated = this.safeIntegerProduct (result, 'server_time', 0.001); this.status = this.extend (this.status, { 'status': status, 'updated': updated, }); return this.status; } async fetchCurrencies (params = {}) { const response = await this.publicGetAssets (params); // // { // "result":[ // { // "base_withdrawal_fee":"0.0005", // "deposit_status":"enabled", // "id":2, // "interest_credit":true, // "interest_slabs":[ // {"limit":"0.1","rate":"0"}, // {"limit":"1","rate":"0.05"}, // {"limit":"5","rate":"0.075"}, // {"limit":"10","rate":"0.1"}, // {"limit":"9999999999999999","rate":"0"} // ], // "kyc_deposit_limit":"10", // "kyc_withdrawal_limit":"2", // "min_withdrawal_amount":"0.001", // "minimum_precision":4, // "name":"Bitcoin", // "precision":8, // "sort_priority":1, // "symbol":"BTC", // "variable_withdrawal_fee":"0", // "withdrawal_status":"enabled" // }, // ], // "success":true // } // const currencies = this.safeValue (response, 'result', []); const result = {}; for (let i = 0; i < currencies.length; i++) { const currency = currencies[i]; const id = this.safeString (currency, 'symbol'); const numericId = this.safeInteger (currency, 'id'); const code = this.safeCurrencyCode (id); const depositStatus = this.safeString (currency, 'deposit_status'); const withdrawalStatus = this.safeString (currency, 'withdrawal_status'); const depositsEnabled = (depositStatus === 'enabled'); const withdrawalsEnabled = (withdrawalStatus === 'enabled'); const active = depositsEnabled && withdrawalsEnabled; const precision = this.safeInteger (currency, 'precision'); result[code] = { 'id': id, 'numericId': numericId, 'code': code, 'name': this.safeString (currency, 'name'), 'info': currency, // the original payload 'active': active, 'fee': this.safeNumber (currency, 'base_withdrawal_fee'), 'precision': 1 / Math.pow (10, precision), 'limits': { 'amount': { 'min': undefined, 'max': undefined }, 'withdraw': { 'min': this.safeNumber (currency, 'min_withdrawal_amount'), 'max': undefined, }, }, }; } return result; } async loadMarkets (reload = false, params = {}) { const markets = await super.loadMarkets (reload, params); const currenciesByNumericId = this.safeValue (this.options, 'currenciesByNumericId'); if ((currenciesByNumericId === undefined) || reload) { this.options['currenciesByNumericId'] = this.indexBy (this.currencies, 'numericId'); } const marketsByNumericId = this.safeValue (this.options, 'marketsByNumericId'); if ((marketsByNumericId === undefined) || reload) { this.options['marketsByNumericId'] = this.indexBy (this.markets, 'numericId'); } return markets; } async fetchMarkets (params = {}) { const response = await this.publicGetProducts (params); // // { // "meta":{ // "after":null, // "before":null, // "limit":100, // "total_count":81 // }, // "result":[ // { // "annualized_funding":"5.475000000000000000", // "is_quanto":false, // "ui_config":{ // "default_trading_view_candle":"15", // "leverage_slider_values":[1,3,5,10,25,50], // "price_clubbing_values":[0.001,0.005,0.05,0.1,0.5,1,5], // "show_bracket_orders":false, // "sort_priority":29, // "tags":[] // }, // "basis_factor_max_limit":"0.15", // "symbol":"P-LINK-D-151120", // "id":1584, // "default_leverage":"5.000000000000000000", // "maker_commission_rate":"0.0005", // "contract_unit_currency":"LINK", // "strike_price":"12.507948", // "settling_asset":{ // // asset structure // }, // "auction_start_time":null, // "auction_finish_time":null, // "settlement_time":"2020-11-15T12:00:00Z", // "launch_time":"2020-11-14T11:55:05Z", // "spot_index":{ // // index structure // }, // "trading_status":"operational", // "tick_size":"0.001", // "position_size_limit":100000, // "notional_type":"vanilla", // vanilla, inverse // "price_band":"0.4", // "barrier_price":null, // "description":"Daily LINK PUT options quoted in USDT and settled in USDT", // "insurance_fund_margin_contribution":"1", // "quoting_asset":{ // // asset structure // }, // "liquidation_penalty_factor":"0.2", // "product_specs":{"max_volatility":3,"min_volatility":0.3,"spot_price_band":"0.40"}, // "initial_margin_scaling_factor":"0.0001", // "underlying_asset":{ // // asset structure // }, // "state":"live", // "contract_value":"1", // "initial_margin":"2", // "impact_size":5000, // "settlement_price":null, // "contract_type":"put_options", // put_options, call_options, move_options, perpetual_futures, interest_rate_swaps, futures, spreads // "taker_commission_rate":"0.0005", // "maintenance_margin":"1", // "short_description":"LINK Daily PUT Options", // "maintenance_margin_scaling_factor":"0.00005", // "funding_method":"mark_price", // "max_leverage_notional":"20000" // }, // ], // "success":true // } // const markets = this.safeValue (response, 'result', []); const result = []; for (let i = 0; i < markets.length; i++) { const market = markets[i]; let type = this.safeString (market, 'contract_type'); // const settlingAsset = this.safeValue (market, 'settling_asset', {}); const quotingAsset = this.safeValue (market, 'quoting_asset', {}); const underlyingAsset = this.safeValue (market, 'underlying_asset', {}); const baseId = this.safeString (underlyingAsset, 'symbol'); const quoteId = this.safeString (quotingAsset, 'symbol'); const id = this.safeString (market, 'symbol'); const numericId = this.safeInteger (market, 'id'); const base = this.safeCurrencyCode (baseId); const quote = this.safeCurrencyCode (quoteId); let symbol = id; let swap = false; let future = false; let option = false; if (type === 'perpetual_futures') { type = 'swap'; swap = true; future = false; option = false; if (id.indexOf ('_') < 0) { symbol = base + '/' + quote; } } else if ((type === 'call_options') || (type === 'put_options') || (type === 'move_options')) { type = 'option'; swap = false; option = true; future = false; } else if (type === 'futures') { type = 'future'; swap = false; option = false; future = true; } const precision = { 'amount': 1.0, // number of contracts 'price': this.safeNumber (market, 'tick_size'), }; const limits = { 'amount': { 'min': 1.0, 'max': this.safeNumber (market, 'position_size_limit'), }, 'price': { 'min': precision['price'], 'max': undefined, }, 'cost': { 'min': this.safeNumber (market, 'min_size'), 'max': undefined, }, }; const state = this.safeString (market, 'state'); const active = (state === 'live'); const maker = this.safeNumber (market, 'maker_commission_rate'); const taker = this.safeNumber (market, 'taker_commission_rate'); result.push ({ 'id': id, 'numericId': numericId, 'symbol': symbol, 'base': base, 'quote': quote, 'baseId': baseId, 'quoteId': quoteId, 'type': type, 'option': option, 'swap': swap, 'future': future, 'maker': maker, 'taker': taker, 'precision': precision, 'limits': limits, 'info': market, 'active': active, }); } return result; } parseTicker (ticker, market = undefined) { // // fetchTicker, fetchTickers // // { // "close":15837.5, // "high":16354, // "low":15751.5, // "mark_price":"15820.100867", // "open":16140.5, // "product_id":139, // "size":640552, // "spot_price":"15827.050000000001", // "symbol":"BTCUSDT", // "timestamp":1605373550208262, // "turnover":10298630.3735, // "turnover_symbol":"USDT", // "turnover_usd":10298630.3735, // "volume":640.5520000000001 // } // const timestamp = this.safeIntegerProduct (ticker, 'timestamp', 0.001); const marketId = this.safeString (ticker, 'symbol'); const symbol = this.safeSymbol (marketId, market); const last = this.safeNumber (ticker, 'close'); const open = this.safeNumber (ticker, 'open'); let change = undefined; let average = undefined; let percentage = undefined; if ((open !== undefined) && (last !== undefined)) { change = last - open; average = this.sum (last, open) / 2; if (open !== 0.0) { percentage = (change / open) * 100; } } const baseVolume = this.safeNumber (ticker, 'volume'); const quoteVolume = this.safeNumber (ticker, 'turnover'); const vwap = this.vwap (baseVolume, quoteVolume); return { 'symbol': symbol, 'timestamp': timestamp, 'datetime': this.iso8601 (timestamp), 'high': this.safeNumber (ticker, 'high'), 'low': this.safeNumber (ticker, 'low'), 'bid': undefined, 'bidVolume': undefined, 'ask': undefined, 'askVolume': undefined, 'vwap': vwap, 'open': open, 'close': last, 'last': last, 'previousClose': undefined, 'change': change, 'percentage': percentage, 'average': average, 'baseVolume': baseVolume, 'quoteVolume': quoteVolume, 'info': ticker, }; } async fetchTicker (symbol, params = {}) { await this.loadMarkets (); const market = this.market (symbol); const request = { 'symbol': market['id'], }; const response = await this.publicGetTickersSymbol (this.extend (request, params)); // // { // "result":{ // "close":15837.5, // "high":16354, // "low":15751.5, // "mark_price":"15820.100867", // "open":16140.5, // "product_id":139, // "size":640552, // "spot_price":"15827.050000000001", // "symbol":"BTCUSDT", // "timestamp":1605373550208262, // "turnover":10298630.3735, // "turnover_symbol":"USDT", // "turnover_usd":10298630.3735, // "volume":640.5520000000001 // }, // "success":true // } // const result = this.safeValue (response, 'result', {}); return this.parseTicker (result, market); } async fetchTickers (symbols = undefined, params = {}) { await this.loadMarkets (); const response = await this.publicGetTickers (params); // // { // "result":[ // { // "close":0.003966, // "high":0.004032, // "low":0.003606, // "mark_price":"0.00396328", // "open":0.003996, // "product_id":1327, // "size":6242, // "spot_price":"0.0039555", // "symbol":"AAVEBTC", // "timestamp":1605374143864107, // "turnover":23.997904999999996, // "turnover_symbol":"BTC", // "turnover_usd":387957.4544782897, // "volume":6242 // }, // ], // "success":true // } // const tickers = this.safeValue (response, 'result', []); const result = {}; for (let i = 0; i < tickers.length; i++) { const ticker = this.parseTicker (tickers[i]); const symbol = ticker['symbol']; result[symbol] = ticker; } return this.filterByArray (result, 'symbol', symbols); } async fetchOrderBook (symbol, limit = undefined, params = {}) { await this.loadMarkets (); const request = { 'symbol': this.marketId (symbol), }; if (limit !== undefined) { request['depth'] = limit; } const response = await this.publicGetL2orderbookSymbol (this.extend (request, params)); // // { // "result":{ // "buy":[ // {"price":"15814.0","size":912}, // {"price":"15813.5","size":1279}, // {"price":"15813.0","size":1634}, // ], // "sell":[ // {"price":"15814.5","size":625}, // {"price":"15815.0","size":982}, // {"price":"15815.5","size":1328}, // ], // "symbol":"BTCUSDT" // }, // "success":true // } // const result = this.safeValue (response, 'result', {}); return this.parseOrderBook (result, symbol, undefined, 'buy', 'sell', 'price', 'size'); } parseTrade (trade, market = undefined) { // // public fetchTrades // // { // "buyer_role":"maker", // "price":"15896.5", // "seller_role":"taker", // "size":241, // "symbol":"BTCUSDT", // "timestamp":1605376684714595 // } // // private fetchMyTrades // // { // "commission":"0.008335000000000000", // "created_at":"2020-11-16T19:07:19Z", // "fill_type":"normal", // "id":"e7ff05c233a74245b72381f8dd91d1ce", // "meta_data":{ // "effective_commission_rate":"0.0005", // "order_price":"16249", // "order_size":1, // "order_type":"market_order", // "order_unfilled_size":0, // "trading_fee_credits_used":"0" // }, // "order_id":"152999629", // "price":"16669", // "product":{ // "contract_type":"perpetual_futures", // "contract_unit_currency":"BTC", // "contract_value":"0.001", // "id":139, // "notional_type":"vanilla", // "quoting_asset":{"minimum_precision":2,"precision":6,"symbol":"USDT"}, // "settling_asset":{"minimum_precision":2,"precision":6,"symbol":"USDT"}, // "symbol":"BTCUSDT", // "tick_size":"0.5", // "underlying_asset":{"minimum_precision":4,"precision":8,"symbol":"BTC"} // }, // "product_id":139, // "role":"taker", // "side":"sell", // "size":1 // } // const id = this.safeString (trade, 'id'); const orderId = this.safeString (trade, 'order_id'); let timestamp = this.parse8601 (this.safeString (trade, 'created_at')); timestamp = this.safeIntegerProduct (trade, 'timestamp', 0.001, timestamp); const priceString = this.safeString (trade, 'price'); const amountString = this.safeString (trade, 'size'); const price = this.parseNumber (priceString); const amount = this.parseNumber (amountString); const cost = this.parseNumber (Precise.stringMul (priceString, amountString)); const product = this.safeValue (trade, 'product', {}); const marketId = this.safeString (product, 'symbol'); const symbol = this.safeSymbol (marketId, market); const sellerRole = this.safeString (trade, 'seller_role'); let side = this.safeString (trade, 'side'); if (side === undefined) { if (sellerRole === 'taker') { side = 'sell'; } else if (sellerRole === 'maker') { side = 'buy'; } } const takerOrMaker = this.safeString (trade, 'role'); const metaData = this.safeValue (trade, 'meta_data', {}); let type = this.safeString (metaData, 'order_type'); if (type !== undefined) { type = type.replace ('_order', ''); } const feeCost = this.safeNumber (trade, 'commission'); let fee = undefined; if (feeCost !== undefined) { const settlingAsset = this.safeValue (product, 'settling_asset', {}); const feeCurrencyId = this.safeString (settlingAsset, 'symbol'); const feeCurrencyCode = this.safeCurrencyCode (feeCurrencyId); fee = { 'cost': feeCost, 'currency': feeCurrencyCode, }; } return { 'id': id, 'order': orderId, 'timestamp': timestamp, 'datetime': this.iso8601 (timestamp), 'symbol': symbol, 'type': type, 'side': side, 'price': price, 'amount': amount, 'cost': cost, 'takerOrMaker': takerOrMaker, 'fee': fee, 'info': trade, }; } async fetchTrades (symbol, since = undefined, limit = undefined, params = {}) { await this.loadMarkets (); const market = this.market (symbol); const request = { 'symbol': market['id'], }; const response = await this.publicGetTradesSymbol (this.extend (request, params)); // // { // "result":[ // { // "buyer_role":"maker", // "price":"15896.5", // "seller_role":"taker", // "size":241, // "symbol":"BTCUSDT", // "timestamp":1605376684714595 // } // ], // "success":true // } // const result = this.safeValue (response, 'result', []); return this.parseTrades (result, market, since, limit); } parseOHLCV (ohlcv, market = undefined) { // // { // "time":1605393120, // "open":15989, // "high":15989, // "low":15987.5, // "close":15987.5, // "volume":565 // } // return [ this.safeTimestamp (ohlcv, 'time'), this.safeNumber (ohlcv, 'open'), this.safeNumber (ohlcv, 'high'), this.safeNumber (ohlcv, 'low'), this.safeNumber (ohlcv, 'close'), this.safeNumber (ohlcv, 'volume'), ]; } async fetchOHLCV (symbol, timeframe = '1m', since = undefined, limit = undefined, params = {}) { await this.loadMarkets (); const market = this.market (symbol); const request = { 'symbol': market['id'], 'resolution': this.timeframes[timeframe], }; const duration = this.parseTimeframe (timeframe); limit = limit ? limit : 2000; // max 2000 if (since === undefined) { const end = this.seconds (); request['end'] = end; request['start'] = end - limit * duration; } else { const start = parseInt (since / 1000); request['start'] = start; request['end'] = this.sum (start, limit * duration); } const response = await this.publicGetHistoryCandles (this.extend (request, params)); // // { // "success":true, // "result":[ // {"time":1605393120,"open":15989,"high":15989,"low":15987.5,"close":15987.5,"volume":565}, // {"time":1605393180,"open":15966,"high":15966,"low":15959,"close":15959,"volume":24}, // {"time":1605393300,"open":15973,"high":15973,"low":15973,"close":15973,"volume":1288}, // ] // } // const result = this.safeValue (response, 'result', []); return this.parseOHLCVs (result, market, timeframe, since, limit); } async fetchBalance (params = {}) { await this.loadMarkets (); const response = await this.privateGetWalletBalances (params); // // { // "result":[ // { // "asset_id":1, // "available_balance":"0", // "balance":"0", // "commission":"0", // "id":154883, // "interest_credit":"0", // "order_margin":"0", // "pending_referral_bonus":"0", // "pending_trading_fee_credit":"0", // "position_margin":"0", // "trading_fee_credit":"0", // "user_id":22142 // }, // ], // "success":true // } // const balances = this.safeValue (response, 'result', []); const result = { 'info': response }; const currenciesByNumericId = this.safeValue (this.options, 'currenciesByNumericId', {}); for (let i = 0; i < balances.length; i++) { const balance = balances[i]; const currencyId = this.safeString (balance, 'asset_id'); const currency = this.safeValue (currenciesByNumericId, currencyId); const code = (currency === undefined) ? currencyId : currency['code']; const account = this.account (); account['total'] = this.safeString (balance, 'balance'); account['free'] = this.safeString (balance, 'available_balance'); result[code] = account; } return this.parseBalance (result, false); } async fetchPosition (symbol, params = undefined) { await this.loadMarkets (); const market = this.market (symbol); const request = { 'product_id': market['numericId'], }; const response = await this.privateGetPositions (this.extend (request, params)); // // { // "result":{ // "entry_price":null, // "size":0, // "timestamp":1605454074268079 // }, // "success":true // } // const result = this.safeValue (response, 'result', {}); return result; } async fetchPositions (symbols = undefined, params = {}) { await this.loadMarkets (); const response = await this.privateGetPositionsMargined (params); // // { // "success": true, // "result": [ // { // "user_id": 0, // "size": 0, // "entry_price": "string", // "margin": "string", // "liquidation_price": "string", // "bankruptcy_price": "string", // "adl_level": 0, // "product_id": 0 // } // ] // } // const result = this.safeValue (response, 'result', []); return result; } parseOrderStatus (status) { const statuses = { 'open': 'open', 'pending': 'open', 'closed': 'closed', 'cancelled': 'canceled', }; return this.safeString (statuses, status, status); } parseOrder (order, market = undefined) { // // createOrder, cancelOrder, editOrder, fetchOpenOrders, fetchClosedOrders // // { // "average_fill_price":null, // "bracket_order":null, // "bracket_stop_loss_limit_price":null, // "bracket_stop_loss_price":null, // "bracket_take_profit_limit_price":null, // "bracket_take_profit_price":null, // "bracket_trail_amount":null, // "cancellation_reason":null, // "client_order_id":null, // "close_on_trigger":"false", // "commission":"0", // "created_at":"2020-11-16T02:38:26Z", // "id":152870626, // "limit_price":"10000", // "meta_data":{"source":"api"}, // "order_type":"limit_order", // "paid_commission":"0", // "product_id":139, // "reduce_only":false, // "side":"buy", // "size":0, // "state":"open", // "stop_order_type":null, // "stop_price":null, // "stop_trigger_method":"mark_price", // "time_in_force":"gtc", // "trail_amount":null, // "unfilled_size":0, // "user_id":22142 // } // const id = this.safeString (order, 'id'); const clientOrderId = this.safeString (order, 'client_order_id'); const timestamp = this.parse8601 (this.safeString (order, 'created_at')); const marketId = this.safeString (order, 'product_id'); const marketsByNumericId = this.safeValue (this.options, 'marketsByNumericId', {}); market = this.safeValue (marketsByNumericId, marketId, market); const symbol = (market === undefined) ? marketId : market['symbol']; const status = this.parseOrderStatus (this.safeString (order, 'state')); const side = this.safeString (order, 'side'); let type = this.safeString (order, 'order_type'); type = type.replace ('_order', ''); const price = this.safeNumber (order, 'limit_price'); const amount = this.safeNumber (order, 'size'); const remaining = this.safeNumber (order, 'unfilled_size'); const average = this.safeNumber (order, 'average_fill_price'); let fee = undefined; const feeCost = this.safeNumber (order, 'paid_commission'); if (feeCost !== undefined) { let feeCurrencyCode = undefined; if (market !== undefined) { const settlingAsset = this.safeValue (market['info'], 'settling_asset', {}); const feeCurrencyId = this.safeString (settlingAsset, 'symbol'); feeCurrencyCode = this.safeCurrencyCode (feeCurrencyId); } fee = { 'cost': feeCost, 'currency': feeCurrencyCode, }; } return this.safeOrder ({ 'info': order, 'id': id, 'clientOrderId': clientOrderId, 'timestamp': timestamp, 'datetime': this.iso8601 (timestamp), 'lastTradeTimestamp': undefined, 'symbol': symbol, 'type': type, 'side': side, 'price': price, 'amount': amount, 'cost': undefined, 'average': average, 'filled': undefined, 'remaining': remaining, 'status': status, 'fee': fee, 'trades': undefined, }); } async createOrder (symbol, type, side, amount, price = undefined, params = {}) { await this.loadMarkets (); const orderType = type + '_order'; const market = this.market (symbol); const request = { 'product_id': market['numericId'], // 'limit_price': this.priceToPrecision (symbol, price), 'size': this.amountToPrecision (symbol, amount), 'side': side, 'order_type': orderType, // 'client_order_id': 'string', // 'time_in_force': 'gtc', // gtc, ioc, fok // 'post_only': 'false', // 'true', // 'reduce_only': 'false', // 'true', }; if (type === 'limit') { request['limit_price'] = this.priceToPrecision (symbol, price); } const clientOrderId = this.safeString2 (params, 'clientOrderId', 'client_order_id'); params = this.omit (params, [ 'clientOrderId', 'client_order_id' ]); if (clientOrderId !== undefined) { request['client_order_id'] = clientOrderId; } const response = await this.privatePostOrders (this.extend (request, params)); // // { // "result":{ // "average_fill_price":null, // "bracket_order":null, // "bracket_stop_loss_limit_price":null, // "bracket_stop_loss_price":null, // "bracket_take_profit_limit_price":null, // "bracket_take_profit_price":null, // "bracket_trail_amount":null, // "cancellation_reason":null, // "client_order_id":null, // "close_on_trigger":"false", // "commission":"0", // "created_at":"2020-11-16T02:38:26Z", // "id":152870626, // "limit_price":"10000", // "meta_data":{"source":"api"}, // "order_type":"limit_order", // "paid_commission":"0", // "product_id":139, // "reduce_only":false, // "side":"buy", // "size":0, // "state":"open", // "stop_order_type":null, // "stop_price":null, // "stop_trigger_method":"mark_price", // "time_in_force":"gtc", // "trail_amount":null, // "unfilled_size":0, // "user_id":22142 // }, // "success":true // } // const result = this.safeValue (response, 'result', {}); return this.parseOrder (result, market); } async editOrder (id, symbol, type, side, amount, price = undefined, params = {}) { await this.loadMarkets (); const market = this.market (symbol); const request = { 'id': parseInt (id), 'product_id': market['numericId'], // 'limit_price': this.priceToPrecision (symbol, price), // 'size': this.amountToPrecision (symbol, amount), }; if (amount !== undefined) { request['size'] = parseInt (this.amountToPrecision (symbol, amount)); } if (price !== undefined) { request['limit_price'] = this.priceToPrecision (symbol, price); } const response = await this.privatePutOrders (this.extend (request, params)); // // { // "success": true, // "result": { // "id": "ashb1212", // "product_id": 27, // "limit_price": "9200", // "side": "buy", // "size": 100, // "unfilled_size": 50, // "user_id": 1, // "order_type": "limit_order", // "state": "open", // "created_at": "..." // } // } // const result = this.safeValue (response, 'result'); return this.parseOrder (result, market); } async cancelOrder (id, symbol = undefined, params = {}) { if (symbol === undefined) { throw new ArgumentsRequired (this.id + ' cancelOrder() requires a symbol argument'); } await this.loadMarkets (); const market = this.market (symbol); const request = { 'id': parseInt (id), 'product_id': market['numericId'], }; const response = await this.privateDeleteOrders (this.extend (request, params)); // // { // "result":{ // "average_fill_price":null, // "bracket_order":null, // "bracket_stop_loss_limit_price":null, // "bracket_stop_loss_price":null, // "bracket_take_profit_limit_price":null, // "bracket_take_profit_price":null, // "bracket_trail_amount":null, // "cancellation_reason":"cancelled_by_user", // "client_order_id":null, // "close_on_trigger":"false", // "commission":"0", // "created_at":"2020-11-16T02:38:26Z", // "id":152870626, // "limit_price":"10000", // "meta_data":{"source":"api"}, // "order_type":"limit_order", // "paid_commission":"0", // "product_id":139, // "reduce_only":false, // "side":"buy", // "size":0, // "state":"cancelled", // "stop_order_type":null, // "stop_price":null, // "stop_trigger_method":"mark_price", // "time_in_force":"gtc", // "trail_amount":null, // "unfilled_size":0, // "user_id":22142 // }, // "success":true // } // const result = this.safeValue (response, 'result'); return this.parseOrder (result, market); } async cancelAllOrders (symbol = undefined, params = {}) { if (symbol === undefined) { throw new ArgumentsRequired (this.id + ' cancelAllOrders() requires a symbol argument'); } await this.loadMarkets (); const market = this.market (symbol); const request = { 'product_id': market['numericId'], // 'cancel_limit_orders': 'true', // 'cancel_stop_orders': 'true', }; const response = this.privateDeleteOrdersAll (this.extend (request, params)); // // { // "result":{}, // "success":true // } // return response; } async fetchOpenOrders (symbol = undefined, since = undefined, limit = undefined, params = {}) { return await this.fetchOrdersWithMethod ('privateGetOrders', symbol, since, limit, params); } async fetchClosedOrders (symbol = undefined, since = undefined, limit = undefined, params = {}) { return await this.fetchOrdersWithMethod ('privateGetOrdersHistory', symbol, since, limit, params); } async fetchOrdersWithMethod (method, symbol = undefined, since = undefined, limit = undefined, params = {}) { await this.loadMarkets (); const request = { // 'product_ids': market['id'], // comma-separated // 'contract_types': types, // comma-separated, futures, perpetual_futures, call_options, put_options, interest_rate_swaps, move_options, spreads // 'order_types': types, // comma-separated, market, limit, stop_market, stop_limit, all_stop // 'start_time': since * 1000, // 'end_time': this.microseconds (), // 'after': string, // after cursor for pagination // 'before': string, // before cursor for pagination // 'page_size': limit, // number of records per page }; let market = undefined; if (symbol !== undefined) { market = this.market (symbol); request['product_ids'] = market['numericId']; // accepts a comma-separated list of ids } if (since !== undefined) { request['start_time'] = since.toString () + '000'; } if (limit !== undefined) { request['page_size'] = limit; } const response = await this[method] (this.extend (request, params)); // // { // "success": true, // "result": [ // { // "id": "ashb1212", // "product_id": 27, // "limit_price": "9200", // "side": "buy", // "size": 100, // "unfilled_size": 50, // "user_id": 1, // "order_type": "limit_order", // "state": "open", // "created_at": "..." // } // ], // "meta": { // "after": "string", // "before": "string" // } // } // const res