ccxt 4.4.82 → 4.4.85

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (103) hide show
  1. package/README.md +5 -7
  2. package/dist/ccxt.browser.min.js +7 -7
  3. package/dist/cjs/ccxt.js +1 -9
  4. package/dist/cjs/src/apex.js +2 -1
  5. package/dist/cjs/src/base/Exchange.js +15 -2
  6. package/dist/cjs/src/bitget.js +1 -3
  7. package/dist/cjs/src/bitrue.js +14 -35
  8. package/dist/cjs/src/bitso.js +33 -0
  9. package/dist/cjs/src/bitstamp.js +33 -0
  10. package/dist/cjs/src/blofin.js +154 -13
  11. package/dist/cjs/src/btcbox.js +25 -5
  12. package/dist/cjs/src/bybit.js +16 -40
  13. package/dist/cjs/src/cex.js +2 -4
  14. package/dist/cjs/src/coinbase.js +56 -40
  15. package/dist/cjs/src/coinbaseexchange.js +142 -32
  16. package/dist/cjs/src/coincatch.js +14 -67
  17. package/dist/cjs/src/coinex.js +29 -32
  18. package/dist/cjs/src/coinlist.js +16 -15
  19. package/dist/cjs/src/coinmetro.js +22 -11
  20. package/dist/cjs/src/coinone.js +8 -10
  21. package/dist/cjs/src/coinsph.js +126 -1
  22. package/dist/cjs/src/cryptocom.js +111 -1
  23. package/dist/cjs/src/cryptomus.js +43 -89
  24. package/dist/cjs/src/delta.js +76 -36
  25. package/dist/cjs/src/derive.js +46 -10
  26. package/dist/cjs/src/ellipx.js +175 -79
  27. package/dist/cjs/src/gate.js +1 -1
  28. package/dist/cjs/src/gemini.js +3 -5
  29. package/dist/cjs/src/hitbtc.js +56 -69
  30. package/dist/cjs/src/hyperliquid.js +2 -2
  31. package/dist/cjs/src/kraken.js +29 -24
  32. package/dist/cjs/src/kucoinfutures.js +6 -0
  33. package/dist/cjs/src/lbank.js +1 -1
  34. package/dist/cjs/src/paradex.js +119 -3
  35. package/dist/cjs/src/pro/binance.js +31 -33
  36. package/dist/cjs/src/pro/bithumb.js +5 -3
  37. package/dist/cjs/src/pro/kraken.js +289 -79
  38. package/dist/cjs/src/pro/mexc.js +302 -8
  39. package/dist/cjs/src/pro/poloniex.js +6 -2
  40. package/examples/js/cli.js +127 -13
  41. package/js/ccxt.d.ts +2 -11
  42. package/js/ccxt.js +2 -8
  43. package/js/src/abstract/blofin.d.ts +8 -0
  44. package/js/src/abstract/btcbox.d.ts +1 -0
  45. package/js/src/apex.js +2 -1
  46. package/js/src/base/Exchange.d.ts +15 -1
  47. package/js/src/base/Exchange.js +15 -2
  48. package/js/src/base/types.d.ts +3 -0
  49. package/js/src/bitget.js +1 -3
  50. package/js/src/bitrue.js +14 -35
  51. package/js/src/bitso.js +33 -0
  52. package/js/src/bitstamp.js +33 -0
  53. package/js/src/blofin.d.ts +42 -2
  54. package/js/src/blofin.js +154 -13
  55. package/js/src/btcbox.js +25 -5
  56. package/js/src/bybit.js +16 -40
  57. package/js/src/cex.js +2 -4
  58. package/js/src/coinbase.js +56 -40
  59. package/js/src/coinbaseexchange.js +142 -32
  60. package/js/src/coincatch.js +14 -67
  61. package/js/src/coinex.js +28 -29
  62. package/js/src/coinlist.js +16 -15
  63. package/js/src/coinmetro.js +22 -11
  64. package/js/src/coinone.js +8 -10
  65. package/js/src/coinsph.d.ts +10 -1
  66. package/js/src/coinsph.js +126 -1
  67. package/js/src/cryptocom.d.ts +10 -1
  68. package/js/src/cryptocom.js +111 -1
  69. package/js/src/cryptomus.js +43 -89
  70. package/js/src/delta.js +76 -36
  71. package/js/src/derive.js +46 -10
  72. package/js/src/ellipx.d.ts +2 -3
  73. package/js/src/ellipx.js +175 -80
  74. package/js/src/gate.js +1 -1
  75. package/js/src/gemini.js +3 -5
  76. package/js/src/hitbtc.js +56 -69
  77. package/js/src/hyperliquid.js +2 -2
  78. package/js/src/kraken.js +29 -24
  79. package/js/src/kucoinfutures.d.ts +1 -0
  80. package/js/src/kucoinfutures.js +6 -0
  81. package/js/src/lbank.js +1 -1
  82. package/js/src/paradex.d.ts +12 -1
  83. package/js/src/paradex.js +119 -3
  84. package/js/src/pro/binance.d.ts +26 -26
  85. package/js/src/pro/binance.js +31 -33
  86. package/js/src/pro/bithumb.js +5 -3
  87. package/js/src/pro/kraken.d.ts +7 -6
  88. package/js/src/pro/kraken.js +290 -80
  89. package/js/src/pro/mexc.d.ts +58 -0
  90. package/js/src/pro/mexc.js +302 -8
  91. package/js/src/pro/poloniex.d.ts +1 -1
  92. package/js/src/pro/poloniex.js +6 -2
  93. package/package.json +1 -1
  94. package/js/src/abstract/bl3p.d.ts +0 -22
  95. package/js/src/abstract/bl3p.js +0 -11
  96. package/js/src/abstract/idex.d.ts +0 -29
  97. package/js/src/abstract/idex.js +0 -11
  98. package/js/src/bl3p.d.ts +0 -116
  99. package/js/src/bl3p.js +0 -552
  100. package/js/src/idex.d.ts +0 -312
  101. package/js/src/idex.js +0 -1961
  102. package/js/src/pro/idex.d.ts +0 -81
  103. package/js/src/pro/idex.js +0 -720
package/js/src/idex.js DELETED
@@ -1,1961 +0,0 @@
1
- // ----------------------------------------------------------------------------
2
-
3
- // PLEASE DO NOT EDIT THIS FILE, IT IS GENERATED AND WILL BE OVERWRITTEN:
4
- // https://github.com/ccxt/ccxt/blob/master/CONTRIBUTING.md#how-to-contribute-code
5
- // EDIT THE CORRESPONDENT .ts FILE INSTEAD
6
-
7
- // ---------------------------------------------------------------------------
8
- import Exchange from './abstract/idex.js';
9
- import { TICK_SIZE, PAD_WITH_ZERO, ROUND, TRUNCATE } from './base/functions/number.js';
10
- import { InvalidOrder, InsufficientFunds, ExchangeError, ExchangeNotAvailable, DDoSProtection, BadRequest, NotSupported, InvalidAddress, AuthenticationError } from './base/errors.js';
11
- import { Precise } from './base/Precise.js';
12
- import { sha256 } from './static_dependencies/noble-hashes/sha256.js';
13
- import { keccak_256 as keccak } from './static_dependencies/noble-hashes/sha3.js';
14
- import { secp256k1 } from './static_dependencies/noble-curves/secp256k1.js';
15
- import { ecdsa } from './base/functions/crypto.js';
16
- // ---------------------------------------------------------------------------
17
- /**
18
- * @class idex
19
- * @augments Exchange
20
- */
21
- export default class idex extends Exchange {
22
- describe() {
23
- return this.deepExtend(super.describe(), {
24
- 'id': 'idex',
25
- 'name': 'IDEX',
26
- 'countries': ['US'],
27
- 'rateLimit': 1000,
28
- 'version': 'v3',
29
- 'pro': true,
30
- 'dex': true,
31
- 'certified': false,
32
- 'requiresWeb3': true,
33
- 'has': {
34
- 'CORS': undefined,
35
- 'spot': true,
36
- 'margin': false,
37
- 'swap': false,
38
- 'future': false,
39
- 'option': false,
40
- 'addMargin': false,
41
- 'cancelAllOrders': true,
42
- 'cancelOrder': true,
43
- 'cancelOrders': false,
44
- 'closeAllPositions': false,
45
- 'closePosition': false,
46
- 'createDepositAddress': false,
47
- 'createOrder': true,
48
- 'createReduceOnlyOrder': false,
49
- 'createStopLimitOrder': true,
50
- 'createStopMarketOrder': true,
51
- 'createStopOrder': true,
52
- 'fetchBalance': true,
53
- 'fetchBorrowRateHistories': false,
54
- 'fetchBorrowRateHistory': false,
55
- 'fetchClosedOrders': true,
56
- 'fetchCrossBorrowRate': false,
57
- 'fetchCrossBorrowRates': false,
58
- 'fetchCurrencies': true,
59
- 'fetchDeposit': true,
60
- 'fetchDepositAddress': true,
61
- 'fetchDepositAddresses': false,
62
- 'fetchDepositAddressesByNetwork': false,
63
- 'fetchDeposits': true,
64
- 'fetchFundingHistory': false,
65
- 'fetchFundingRate': false,
66
- 'fetchFundingRateHistory': false,
67
- 'fetchFundingRates': false,
68
- 'fetchIndexOHLCV': false,
69
- 'fetchIsolatedBorrowRate': false,
70
- 'fetchIsolatedBorrowRates': false,
71
- 'fetchLeverage': false,
72
- 'fetchLeverageTiers': false,
73
- 'fetchMarginMode': false,
74
- 'fetchMarkets': true,
75
- 'fetchMarkOHLCV': false,
76
- 'fetchMyTrades': true,
77
- 'fetchOHLCV': true,
78
- 'fetchOpenInterestHistory': false,
79
- 'fetchOpenOrders': true,
80
- 'fetchOrder': true,
81
- 'fetchOrderBook': true,
82
- 'fetchOrders': false,
83
- 'fetchPosition': false,
84
- 'fetchPositionHistory': false,
85
- 'fetchPositionMode': false,
86
- 'fetchPositions': false,
87
- 'fetchPositionsForSymbol': false,
88
- 'fetchPositionsHistory': false,
89
- 'fetchPositionsRisk': false,
90
- 'fetchPremiumIndexOHLCV': false,
91
- 'fetchStatus': true,
92
- 'fetchTicker': true,
93
- 'fetchTickers': true,
94
- 'fetchTime': true,
95
- 'fetchTrades': true,
96
- 'fetchTradingFee': false,
97
- 'fetchTradingFees': true,
98
- 'fetchTransactions': false,
99
- 'fetchWithdrawal': true,
100
- 'fetchWithdrawals': true,
101
- 'reduceMargin': false,
102
- 'sandbox': true,
103
- 'setLeverage': false,
104
- 'setMarginMode': false,
105
- 'setPositionMode': false,
106
- 'transfer': false,
107
- 'withdraw': true,
108
- },
109
- 'timeframes': {
110
- '1m': '1m',
111
- '5m': '5m',
112
- '15m': '15m',
113
- '30m': '30m',
114
- '1h': '1h',
115
- '6h': '6h',
116
- '1d': '1d',
117
- },
118
- 'urls': {
119
- 'test': {
120
- 'MATIC': 'https://api-sandbox-matic.idex.io',
121
- },
122
- 'logo': 'https://user-images.githubusercontent.com/51840849/94481303-2f222100-01e0-11eb-97dd-bc14c5943a86.jpg',
123
- 'api': {
124
- 'MATIC': 'https://api-matic.idex.io',
125
- },
126
- 'www': 'https://idex.io',
127
- 'doc': [
128
- 'https://api-docs-v3.idex.io/',
129
- ],
130
- },
131
- 'api': {
132
- 'public': {
133
- 'get': {
134
- 'ping': 1,
135
- 'time': 1,
136
- 'exchange': 1,
137
- 'assets': 1,
138
- 'markets': 1,
139
- 'tickers': 1,
140
- 'candles': 1,
141
- 'trades': 1,
142
- 'orderbook': 1,
143
- },
144
- },
145
- 'private': {
146
- 'get': {
147
- 'user': 1,
148
- 'wallets': 1,
149
- 'balances': 1,
150
- 'orders': 0.1,
151
- 'fills': 0.1,
152
- 'deposits': 1,
153
- 'withdrawals': 1,
154
- 'wsToken': 1,
155
- },
156
- 'post': {
157
- 'wallets': 1,
158
- 'orders': 0.1,
159
- 'orders/test': 0.1,
160
- 'withdrawals': 1,
161
- },
162
- 'delete': {
163
- 'orders': 0.1,
164
- },
165
- },
166
- },
167
- 'options': {
168
- 'defaultTimeInForce': 'gtc',
169
- 'defaultSelfTradePrevention': 'cn',
170
- 'network': 'MATIC',
171
- },
172
- 'features': {
173
- 'spot': {
174
- 'sandbox': false,
175
- 'createOrder': {
176
- 'marginMode': false,
177
- 'triggerPrice': true,
178
- // todo: revise
179
- 'triggerPriceType': {
180
- 'last': true,
181
- 'mark': true,
182
- 'index': true,
183
- },
184
- 'triggerDirection': false,
185
- 'stopLossPrice': false,
186
- 'takeProfitPrice': false,
187
- 'attachedStopLossTakeProfit': undefined,
188
- 'timeInForce': {
189
- 'IOC': true,
190
- 'FOK': true,
191
- 'PO': true,
192
- 'GTD': false,
193
- },
194
- 'hedged': false,
195
- 'selfTradePrevention': true,
196
- 'trailing': false,
197
- 'leverage': false,
198
- 'marketBuyByCost': false,
199
- 'marketBuyRequiresPrice': false,
200
- 'iceberg': false,
201
- },
202
- 'createOrders': undefined,
203
- 'fetchMyTrades': {
204
- 'marginMode': false,
205
- 'limit': 1000,
206
- 'daysBack': 100000,
207
- 'untilDays': 100000,
208
- 'symbolRequired': false,
209
- },
210
- 'fetchOrder': {
211
- 'marginMode': false,
212
- 'trigger': false,
213
- 'trailing': false,
214
- 'symbolRequired': false,
215
- },
216
- 'fetchOpenOrders': {
217
- 'marginMode': false,
218
- 'limit': 1000,
219
- 'trigger': false,
220
- 'trailing': false,
221
- 'symbolRequired': false,
222
- },
223
- 'fetchOrders': undefined,
224
- 'fetchClosedOrders': {
225
- 'marginMode': false,
226
- 'limit': 1000,
227
- 'daysBack': 1000000,
228
- 'daysBackCanceled': 1,
229
- 'untilDays': 1000000,
230
- 'trigger': false,
231
- 'trailing': false,
232
- 'symbolRequired': false,
233
- },
234
- 'fetchOHLCV': {
235
- 'limit': 1000,
236
- },
237
- },
238
- 'swap': {
239
- 'linear': undefined,
240
- 'inverse': undefined,
241
- },
242
- 'future': {
243
- 'linear': undefined,
244
- 'inverse': undefined,
245
- },
246
- },
247
- 'exceptions': {
248
- 'exact': {
249
- 'INVALID_ORDER_QUANTITY': InvalidOrder,
250
- 'INSUFFICIENT_FUNDS': InsufficientFunds,
251
- 'SERVICE_UNAVAILABLE': ExchangeNotAvailable,
252
- 'EXCEEDED_RATE_LIMIT': DDoSProtection,
253
- 'INVALID_PARAMETER': BadRequest,
254
- 'WALLET_NOT_ASSOCIATED': InvalidAddress,
255
- 'INVALID_WALLET_SIGNATURE': AuthenticationError,
256
- },
257
- },
258
- 'requiredCredentials': {
259
- 'walletAddress': true,
260
- 'privateKey': true,
261
- 'apiKey': true,
262
- 'secret': true,
263
- },
264
- 'precisionMode': TICK_SIZE,
265
- 'paddingMode': PAD_WITH_ZERO,
266
- 'commonCurrencies': {},
267
- });
268
- }
269
- priceToPrecision(symbol, price) {
270
- //
271
- // we override priceToPrecision to fix the following issue
272
- // https://github.com/ccxt/ccxt/issues/13367
273
- // {"code":"INVALID_PARAMETER","message":"invalid value provided for request parameter \"price\": all quantities and prices must be below 100 billion, above 0, need to be provided as strings, and always require 4 decimals ending with 4 zeroes"}
274
- //
275
- const market = this.market(symbol);
276
- price = this.decimalToPrecision(price, ROUND, market['precision']['price'], this.precisionMode);
277
- return this.decimalToPrecision(price, TRUNCATE, market['precision']['quote'], TICK_SIZE, PAD_WITH_ZERO);
278
- }
279
- /**
280
- * @method
281
- * @name idex#fetchMarkets
282
- * @description retrieves data on all markets for idex
283
- * @see https://api-docs-v3.idex.io/#get-markets
284
- * @param {object} [params] extra parameters specific to the exchange API endpoint
285
- * @returns {object[]} an array of objects representing market data
286
- */
287
- async fetchMarkets(params = {}) {
288
- const response = await this.publicGetMarkets(params);
289
- //
290
- // [
291
- // {
292
- // "market": "ETH-USDC",
293
- // "type": "hybrid",
294
- // "status": "activeHybrid",
295
- // "baseAsset": "ETH",
296
- // "baseAssetPrecision": "8",
297
- // "quoteAsset": "USDC",
298
- // "quoteAssetPrecision": "8",
299
- // "makerFeeRate": "0.0000",
300
- // "takerFeeRate": "0.2500",
301
- // "takerIdexFeeRate": "0.0500",
302
- // "takerLiquidityProviderFeeRate": "0.2000",
303
- // "tickSize": "0.01000000"
304
- // },
305
- // ]
306
- //
307
- const response2 = await this.publicGetExchange();
308
- //
309
- // {
310
- // "timeZone": "UTC",
311
- // "serverTime": "1654460599952",
312
- // "maticDepositContractAddress": "0x3253a7e75539edaeb1db608ce6ef9aa1ac9126b6",
313
- // "maticCustodyContractAddress": "0x3bcc4eca0a40358558ca8d1bcd2d1dbde63eb468",
314
- // "maticUsdPrice": "0.60",
315
- // "gasPrice": "180",
316
- // "volume24hUsd": "10015814.46",
317
- // "totalVolumeUsd": "1589273533.28",
318
- // "totalTrades": "1534904",
319
- // "totalValueLockedUsd": "12041929.44",
320
- // "idexStakingValueLockedUsd": "20133816.98",
321
- // "idexTokenAddress": "0x9Cb74C8032b007466865f060ad2c46145d45553D",
322
- // "idexUsdPrice": "0.07",
323
- // "idexMarketCapUsd": "48012346.00",
324
- // "makerFeeRate": "0.0000",
325
- // "takerFeeRate": "0.0025",
326
- // "takerIdexFeeRate": "0.0005",
327
- // "takerLiquidityProviderFeeRate": "0.0020",
328
- // "makerTradeMinimum": "10.00000000",
329
- // "takerTradeMinimum": "1.00000000",
330
- // "withdrawMinimum": "0.50000000",
331
- // "liquidityAdditionMinimum": "0.50000000",
332
- // "liquidityRemovalMinimum": "0.40000000",
333
- // "blockConfirmationDelay": "64"
334
- // }
335
- //
336
- const maker = this.safeNumber(response2, 'makerFeeRate');
337
- const taker = this.safeNumber(response2, 'takerFeeRate');
338
- const makerMin = this.safeString(response2, 'makerTradeMinimum');
339
- const takerMin = this.safeString(response2, 'takerTradeMinimum');
340
- const minCostETH = this.parseNumber(Precise.stringMin(makerMin, takerMin));
341
- const result = [];
342
- for (let i = 0; i < response.length; i++) {
343
- const entry = response[i];
344
- const marketId = this.safeString(entry, 'market');
345
- const baseId = this.safeString(entry, 'baseAsset');
346
- const quoteId = this.safeString(entry, 'quoteAsset');
347
- const base = this.safeCurrencyCode(baseId);
348
- const quote = this.safeCurrencyCode(quoteId);
349
- const basePrecision = this.parseNumber(this.parsePrecision(this.safeString(entry, 'baseAssetPrecision')));
350
- const quotePrecision = this.parseNumber(this.parsePrecision(this.safeString(entry, 'quoteAssetPrecision')));
351
- const status = this.safeString(entry, 'status');
352
- let minCost = undefined;
353
- if (quote === 'ETH') {
354
- minCost = minCostETH;
355
- }
356
- result.push({
357
- 'id': marketId,
358
- 'symbol': base + '/' + quote,
359
- 'base': base,
360
- 'quote': quote,
361
- 'settle': undefined,
362
- 'baseId': baseId,
363
- 'quoteId': quoteId,
364
- 'settleId': undefined,
365
- 'type': 'spot',
366
- 'spot': true,
367
- 'margin': false,
368
- 'swap': false,
369
- 'future': false,
370
- 'option': false,
371
- 'active': (status !== 'inactive'),
372
- 'contract': false,
373
- 'linear': undefined,
374
- 'inverse': undefined,
375
- 'taker': taker,
376
- 'maker': maker,
377
- 'contractSize': undefined,
378
- 'expiry': undefined,
379
- 'expiryDatetime': undefined,
380
- 'strike': undefined,
381
- 'optionType': undefined,
382
- 'precision': {
383
- 'amount': basePrecision,
384
- 'price': this.safeNumber(entry, 'tickSize'),
385
- 'base': basePrecision,
386
- 'quote': quotePrecision,
387
- },
388
- 'limits': {
389
- 'leverage': {
390
- 'min': undefined,
391
- 'max': undefined,
392
- },
393
- 'amount': {
394
- 'min': basePrecision,
395
- 'max': undefined,
396
- },
397
- 'price': {
398
- 'min': quotePrecision,
399
- 'max': undefined,
400
- },
401
- 'cost': {
402
- 'min': minCost,
403
- 'max': undefined,
404
- },
405
- },
406
- 'created': undefined,
407
- 'info': entry,
408
- });
409
- }
410
- return result;
411
- }
412
- /**
413
- * @method
414
- * @name idex#fetchTicker
415
- * @description fetches a price ticker, a statistical calculation with the information calculated over the past 24 hours for a specific market
416
- * @see https://api-docs-v3.idex.io/#get-tickers
417
- * @param {string} symbol unified symbol of the market to fetch the ticker for
418
- * @param {object} [params] extra parameters specific to the exchange API endpoint
419
- * @returns {object} a [ticker structure]{@link https://docs.ccxt.com/#/?id=ticker-structure}
420
- */
421
- async fetchTicker(symbol, params = {}) {
422
- await this.loadMarkets();
423
- const market = this.market(symbol);
424
- const request = {
425
- 'market': market['id'],
426
- };
427
- // [
428
- // {
429
- // "market": "DIL-ETH",
430
- // "time": 1598367493008,
431
- // "open": "0.09695361",
432
- // "high": "0.10245881",
433
- // "low": "0.09572507",
434
- // "close": "0.09917079",
435
- // "closeQuantity": "0.71320950",
436
- // "baseVolume": "309.17380612",
437
- // "quoteVolume": "30.57633981",
438
- // "percentChange": "2.28",
439
- // "numTrades": 205,
440
- // "ask": "0.09910476",
441
- // "bid": "0.09688340",
442
- // "sequence": 3902
443
- // }
444
- // ]
445
- const response = await this.publicGetTickers(this.extend(request, params));
446
- const ticker = this.safeDict(response, 0);
447
- return this.parseTicker(ticker, market);
448
- }
449
- /**
450
- * @method
451
- * @name idex#fetchTickers
452
- * @description fetches price tickers for multiple markets, statistical information calculated over the past 24 hours for each market
453
- * @see https://api-docs-v3.idex.io/#get-tickers
454
- * @param {string[]|undefined} symbols unified symbols of the markets to fetch the ticker for, all market tickers are returned if not assigned
455
- * @param {object} [params] extra parameters specific to the exchange API endpoint
456
- * @returns {object} a dictionary of [ticker structures]{@link https://docs.ccxt.com/#/?id=ticker-structure}
457
- */
458
- async fetchTickers(symbols = undefined, params = {}) {
459
- await this.loadMarkets();
460
- // [
461
- // {
462
- // "market": "DIL-ETH",
463
- // "time": 1598367493008,
464
- // "open": "0.09695361",
465
- // "high": "0.10245881",
466
- // "low": "0.09572507",
467
- // "close": "0.09917079",
468
- // "closeQuantity": "0.71320950",
469
- // "baseVolume": "309.17380612",
470
- // "quoteVolume": "30.57633981",
471
- // "percentChange": "2.28",
472
- // "numTrades": 205,
473
- // "ask": "0.09910476",
474
- // "bid": "0.09688340",
475
- // "sequence": 3902
476
- // }, ...
477
- // ]
478
- const response = await this.publicGetTickers(params);
479
- return this.parseTickers(response, symbols);
480
- }
481
- parseTicker(ticker, market = undefined) {
482
- // {
483
- // "market": "DIL-ETH",
484
- // "time": 1598367493008,
485
- // "open": "0.09695361",
486
- // "high": "0.10245881",
487
- // "low": "0.09572507",
488
- // "close": "0.09917079",
489
- // "closeQuantity": "0.71320950",
490
- // "baseVolume": "309.17380612",
491
- // "quoteVolume": "30.57633981",
492
- // "percentChange": "2.28",
493
- // "numTrades": 205,
494
- // "ask": "0.09910476",
495
- // "bid": "0.09688340",
496
- // "sequence": 3902
497
- // }
498
- const marketId = this.safeString(ticker, 'market');
499
- market = this.safeMarket(marketId, market, '-');
500
- const symbol = market['symbol'];
501
- const timestamp = this.safeInteger(ticker, 'time');
502
- const close = this.safeString(ticker, 'close');
503
- return this.safeTicker({
504
- 'symbol': symbol,
505
- 'timestamp': timestamp,
506
- 'datetime': this.iso8601(timestamp),
507
- 'high': this.safeString(ticker, 'high'),
508
- 'low': this.safeString(ticker, 'low'),
509
- 'bid': this.safeString(ticker, 'bid'),
510
- 'bidVolume': undefined,
511
- 'ask': this.safeString(ticker, 'ask'),
512
- 'askVolume': undefined,
513
- 'vwap': undefined,
514
- 'open': this.safeString(ticker, 'open'),
515
- 'close': close,
516
- 'last': close,
517
- 'previousClose': undefined,
518
- 'change': undefined,
519
- 'percentage': this.safeString(ticker, 'percentChange'),
520
- 'average': undefined,
521
- 'baseVolume': this.safeString(ticker, 'baseVolume'),
522
- 'quoteVolume': this.safeString(ticker, 'quoteVolume'),
523
- 'info': ticker,
524
- }, market);
525
- }
526
- /**
527
- * @method
528
- * @name idex#fetchOHLCV
529
- * @description fetches historical candlestick data containing the open, high, low, and close price, and the volume of a market
530
- * @see https://api-docs-v3.idex.io/#get-candles
531
- * @param {string} symbol unified symbol of the market to fetch OHLCV data for
532
- * @param {string} timeframe the length of time each candle represents
533
- * @param {int} [since] timestamp in ms of the earliest candle to fetch
534
- * @param {int} [limit] the maximum amount of candles to fetch
535
- * @param {object} [params] extra parameters specific to the exchange API endpoint
536
- * @returns {int[][]} A list of candles ordered as timestamp, open, high, low, close, volume
537
- */
538
- async fetchOHLCV(symbol, timeframe = '1m', since = undefined, limit = undefined, params = {}) {
539
- await this.loadMarkets();
540
- const market = this.market(symbol);
541
- const request = {
542
- 'market': market['id'],
543
- 'interval': timeframe,
544
- };
545
- if (since !== undefined) {
546
- request['start'] = since;
547
- }
548
- if (limit !== undefined) {
549
- request['limit'] = Math.min(limit, 1000);
550
- }
551
- const response = await this.publicGetCandles(this.extend(request, params));
552
- if (Array.isArray(response)) {
553
- // [
554
- // {
555
- // "start": 1598345580000,
556
- // "open": "0.09771286",
557
- // "high": "0.09771286",
558
- // "low": "0.09771286",
559
- // "close": "0.09771286",
560
- // "volume": "1.45340410",
561
- // "sequence": 3853
562
- // }, ...
563
- // ]
564
- return this.parseOHLCVs(response, market, timeframe, since, limit);
565
- }
566
- else {
567
- // {"nextTime":1595536440000}
568
- return [];
569
- }
570
- }
571
- parseOHLCV(ohlcv, market = undefined) {
572
- // {
573
- // "start": 1598345580000,
574
- // "open": "0.09771286",
575
- // "high": "0.09771286",
576
- // "low": "0.09771286",
577
- // "close": "0.09771286",
578
- // "volume": "1.45340410",
579
- // "sequence": 3853
580
- // }
581
- const timestamp = this.safeInteger(ohlcv, 'start');
582
- const open = this.safeNumber(ohlcv, 'open');
583
- const high = this.safeNumber(ohlcv, 'high');
584
- const low = this.safeNumber(ohlcv, 'low');
585
- const close = this.safeNumber(ohlcv, 'close');
586
- const volume = this.safeNumber(ohlcv, 'volume');
587
- return [timestamp, open, high, low, close, volume];
588
- }
589
- /**
590
- * @method
591
- * @name idex#fetchTrades
592
- * @description get the list of most recent trades for a particular symbol
593
- * @see https://api-docs-v3.idex.io/#get-trades
594
- * @param {string} symbol unified symbol of the market to fetch trades for
595
- * @param {int} [since] timestamp in ms of the earliest trade to fetch
596
- * @param {int} [limit] the maximum amount of trades to fetch
597
- * @param {object} [params] extra parameters specific to the exchange API endpoint
598
- * @returns {Trade[]} a list of [trade structures]{@link https://docs.ccxt.com/#/?id=public-trades}
599
- */
600
- async fetchTrades(symbol, since = undefined, limit = undefined, params = {}) {
601
- await this.loadMarkets();
602
- const market = this.market(symbol);
603
- const request = {
604
- 'market': market['id'],
605
- };
606
- if (since !== undefined) {
607
- request['start'] = since;
608
- }
609
- if (limit !== undefined) {
610
- request['limit'] = Math.min(limit, 1000);
611
- }
612
- // [
613
- // {
614
- // "fillId": "b5467d00-b13e-3fa9-8216-dd66735550fc",
615
- // "price": "0.09771286",
616
- // "quantity": "1.45340410",
617
- // "quoteQuantity": "0.14201627",
618
- // "time": 1598345638994,
619
- // "makerSide": "buy",
620
- // "sequence": 3853
621
- // }, ...
622
- // ]
623
- const response = await this.publicGetTrades(this.extend(request, params));
624
- return this.parseTrades(response, market, since, limit);
625
- }
626
- parseTrade(trade, market = undefined) {
627
- //
628
- // public trades
629
- // {
630
- // "fillId":"a4883704-850b-3c4b-8588-020b5e4c62f1",
631
- // "price":"0.20377008",
632
- // "quantity":"47.58448728",
633
- // "quoteQuantity":"9.69629509",
634
- // "time":1642091300873,
635
- // "makerSide":"buy",
636
- // "type":"hybrid", // one of either: "orderBook", "hybrid", or "pool"
637
- // "sequence":31876
638
- // }
639
- //
640
- // private trades
641
- // {
642
- // "fillId":"83429066-9334-3582-b710-78858b2f0d6b",
643
- // "price":"0.20717368",
644
- // "quantity":"15.00000000",
645
- // "quoteQuantity":"3.10760523",
646
- // "orderBookQuantity":"0.00000003",
647
- // "orderBookQuoteQuantity":"0.00000001",
648
- // "poolQuantity":"14.99999997",
649
- // "poolQuoteQuantity":"3.10760522",
650
- // "time":1642083351215,
651
- // "makerSide":"sell",
652
- // "sequence":31795,
653
- // "market":"IDEX-USDC",
654
- // "orderId":"4fe993f0-747b-11ec-bd08-79d4a0b6e47c",
655
- // "side":"buy",
656
- // "fee":"0.03749989",
657
- // "feeAsset":"IDEX",
658
- // "gas":"0.40507261",
659
- // "liquidity":"taker",
660
- // "type":"hybrid",
661
- // "txId":"0x69f6d82a762d12e3201efd0b3e9cc1969351e3c6ea3cf07c47c66bf24a459815",
662
- // "txStatus":"mined"
663
- // }
664
- //
665
- const id = this.safeString(trade, 'fillId');
666
- const priceString = this.safeString(trade, 'price');
667
- const amountString = this.safeString(trade, 'quantity');
668
- const costString = this.safeString(trade, 'quoteQuantity');
669
- const timestamp = this.safeInteger(trade, 'time');
670
- const marketId = this.safeString(trade, 'market');
671
- const symbol = this.safeSymbol(marketId, market, '-');
672
- // this code handles the duality of public vs private trades
673
- const makerSide = this.safeString(trade, 'makerSide');
674
- const oppositeSide = (makerSide === 'buy') ? 'sell' : 'buy';
675
- const side = this.safeString(trade, 'side', oppositeSide);
676
- const takerOrMaker = this.safeString(trade, 'liquidity', 'taker');
677
- const feeCostString = this.safeString(trade, 'fee');
678
- let fee = undefined;
679
- if (feeCostString !== undefined) {
680
- const feeCurrencyId = this.safeString(trade, 'feeAsset');
681
- fee = {
682
- 'cost': feeCostString,
683
- 'currency': this.safeCurrencyCode(feeCurrencyId),
684
- };
685
- }
686
- const orderId = this.safeString(trade, 'orderId');
687
- return this.safeTrade({
688
- 'info': trade,
689
- 'timestamp': timestamp,
690
- 'datetime': this.iso8601(timestamp),
691
- 'symbol': symbol,
692
- 'id': id,
693
- 'order': orderId,
694
- 'type': 'limit',
695
- 'side': side,
696
- 'takerOrMaker': takerOrMaker,
697
- 'price': priceString,
698
- 'amount': amountString,
699
- 'cost': costString,
700
- 'fee': fee,
701
- }, market);
702
- }
703
- /**
704
- * @method
705
- * @name idex#fetchTradingFees
706
- * @description fetch the trading fees for multiple markets
707
- * @see https://api-docs-v3.idex.io/#get-api-account
708
- * @param {object} [params] extra parameters specific to the exchange API endpoint
709
- * @returns {object} a dictionary of [fee structures]{@link https://docs.ccxt.com/#/?id=fee-structure} indexed by market symbols
710
- */
711
- async fetchTradingFees(params = {}) {
712
- this.checkRequiredCredentials();
713
- await this.loadMarkets();
714
- const nonce = this.uuidv1();
715
- const request = {
716
- 'nonce': nonce,
717
- };
718
- let response = undefined;
719
- response = await this.privateGetUser(this.extend(request, params));
720
- //
721
- // {
722
- // "depositEnabled": true,
723
- // "orderEnabled": true,
724
- // "cancelEnabled": true,
725
- // "withdrawEnabled": true,
726
- // "totalPortfolioValueUsd": "0.00",
727
- // "makerFeeRate": "0.0000",
728
- // "takerFeeRate": "0.0025",
729
- // "takerIdexFeeRate": "0.0005",
730
- // "takerLiquidityProviderFeeRate": "0.0020"
731
- // }
732
- //
733
- const maker = this.safeNumber(response, 'makerFeeRate');
734
- const taker = this.safeNumber(response, 'takerFeeRate');
735
- const result = {};
736
- for (let i = 0; i < this.symbols.length; i++) {
737
- const symbol = this.symbols[i];
738
- result[symbol] = {
739
- 'info': response,
740
- 'symbol': symbol,
741
- 'maker': maker,
742
- 'taker': taker,
743
- 'percentage': true,
744
- 'tierBased': false,
745
- };
746
- }
747
- return result;
748
- }
749
- /**
750
- * @method
751
- * @name idex#fetchOrderBook
752
- * @description fetches information on open orders with bid (buy) and ask (sell) prices, volumes and other data
753
- * @see https://api-docs-v3.idex.io/#get-order-books
754
- * @param {string} symbol unified symbol of the market to fetch the order book for
755
- * @param {int} [limit] the maximum amount of order book entries to return
756
- * @param {object} [params] extra parameters specific to the exchange API endpoint
757
- * @returns {object} A dictionary of [order book structures]{@link https://docs.ccxt.com/#/?id=order-book-structure} indexed by market symbols
758
- */
759
- async fetchOrderBook(symbol, limit = undefined, params = {}) {
760
- await this.loadMarkets();
761
- const market = this.market(symbol);
762
- const request = {
763
- 'market': market['id'],
764
- 'level': 2,
765
- };
766
- if (limit !== undefined) {
767
- request['limit'] = limit;
768
- }
769
- // {
770
- // "sequence": 36416753,
771
- // "bids": [
772
- // [ '0.09672815', "8.22284267", 1 ],
773
- // [ '0.09672814', "1.83685554", 1 ],
774
- // [ '0.09672143', "4.10962617", 1 ],
775
- // [ '0.09658884', "4.03863759", 1 ],
776
- // [ '0.09653781', "3.35730684", 1 ],
777
- // [ '0.09624660', "2.54163586", 1 ],
778
- // [ '0.09617490', "1.93065030", 1 ]
779
- // ],
780
- // "asks": [
781
- // [ '0.09910476', "3.22840154", 1 ],
782
- // [ '0.09940587', "3.39796593", 1 ],
783
- // [ '0.09948189', "4.25088898", 1 ],
784
- // [ '0.09958362', "2.42195784", 1 ],
785
- // [ '0.09974393', "4.25234367", 1 ],
786
- // [ '0.09995250', "3.40192141", 1 ]
787
- // ]
788
- // }
789
- const response = await this.publicGetOrderbook(this.extend(request, params));
790
- const nonce = this.safeInteger(response, 'sequence');
791
- return {
792
- 'symbol': symbol,
793
- 'timestamp': undefined,
794
- 'datetime': undefined,
795
- 'nonce': nonce,
796
- 'bids': this.parseSide(response, 'bids'),
797
- 'asks': this.parseSide(response, 'asks'),
798
- };
799
- }
800
- parseSide(book, side) {
801
- const bookSide = this.safeValue(book, side, []);
802
- const result = [];
803
- for (let i = 0; i < bookSide.length; i++) {
804
- const order = bookSide[i];
805
- const price = this.safeNumber(order, 0);
806
- const amount = this.safeNumber(order, 1);
807
- const orderCount = this.safeInteger(order, 2);
808
- result.push([price, amount, orderCount]);
809
- }
810
- const descending = side === 'bids';
811
- return this.sortBy(result, 0, descending);
812
- }
813
- /**
814
- * @method
815
- * @name idex#fetchCurrencies
816
- * @description fetches all available currencies on an exchange
817
- * @see https://api-docs-v3.idex.io/#get-assets
818
- * @param {object} [params] extra parameters specific to the exchange API endpoint
819
- * @returns {object} an associative dictionary of currencies
820
- */
821
- async fetchCurrencies(params = {}) {
822
- const response = await this.publicGetAssets(params);
823
- //
824
- // [
825
- // {
826
- // "name": "Ethereum",
827
- // "symbol": "ETH",
828
- // "contractAddress": "0x7ceB23fD6bC0adD59E62ac25578270cFf1b9f619",
829
- // "assetDecimals": "18",
830
- // "exchangeDecimals": "8",
831
- // "maticPrice": "3029.38503483"
832
- // },
833
- // ]
834
- //
835
- const result = {};
836
- for (let i = 0; i < response.length; i++) {
837
- const entry = response[i];
838
- const name = this.safeString(entry, 'name');
839
- const currencyId = this.safeString(entry, 'symbol');
840
- const code = this.safeCurrencyCode(currencyId);
841
- const precision = this.parseNumber(this.parsePrecision(this.safeString(entry, 'exchangeDecimals')));
842
- result[code] = {
843
- 'id': currencyId,
844
- 'code': code,
845
- 'info': entry,
846
- 'type': undefined,
847
- 'name': name,
848
- 'active': undefined,
849
- 'deposit': undefined,
850
- 'withdraw': undefined,
851
- 'fee': undefined,
852
- 'precision': precision,
853
- 'limits': {
854
- 'amount': { 'min': precision, 'max': undefined },
855
- 'withdraw': { 'min': precision, 'max': undefined },
856
- },
857
- };
858
- }
859
- return result;
860
- }
861
- parseBalance(response) {
862
- const result = {
863
- 'info': response,
864
- 'timestamp': undefined,
865
- 'datetime': undefined,
866
- };
867
- for (let i = 0; i < response.length; i++) {
868
- const entry = response[i];
869
- const currencyId = this.safeString(entry, 'asset');
870
- const code = this.safeCurrencyCode(currencyId);
871
- const account = this.account();
872
- account['total'] = this.safeString(entry, 'quantity');
873
- account['free'] = this.safeString(entry, 'availableForTrade');
874
- account['used'] = this.safeString(entry, 'locked');
875
- result[code] = account;
876
- }
877
- return this.safeBalance(result);
878
- }
879
- /**
880
- * @method
881
- * @name idex#fetchBalance
882
- * @description query for balance and get the amount of funds available for trading or funds locked in orders
883
- * @see https://api-docs-v3.idex.io/#get-balances
884
- * @param {object} [params] extra parameters specific to the exchange API endpoint
885
- * @returns {object} a [balance structure]{@link https://docs.ccxt.com/#/?id=balance-structure}
886
- */
887
- async fetchBalance(params = {}) {
888
- this.checkRequiredCredentials();
889
- await this.loadMarkets();
890
- const nonce1 = this.uuidv1();
891
- const request = {
892
- 'nonce': nonce1,
893
- 'wallet': this.walletAddress,
894
- };
895
- // [
896
- // {
897
- // "asset": "DIL",
898
- // "quantity": "0.00000000",
899
- // "availableForTrade": "0.00000000",
900
- // "locked": "0.00000000",
901
- // "usdValue": null
902
- // }, ...
903
- // ]
904
- const extendedRequest = this.extend(request, params);
905
- if (extendedRequest['wallet'] === undefined) {
906
- throw new BadRequest(this.id + ' fetchBalance() wallet is undefined, set this.walletAddress or "address" in params');
907
- }
908
- let response = undefined;
909
- try {
910
- response = await this.privateGetBalances(extendedRequest);
911
- }
912
- catch (e) {
913
- if (e instanceof InvalidAddress) {
914
- const walletAddress = extendedRequest['wallet'];
915
- await this.associateWallet(walletAddress);
916
- response = await this.privateGetBalances(extendedRequest);
917
- }
918
- else {
919
- throw e;
920
- }
921
- }
922
- return this.parseBalance(response);
923
- }
924
- /**
925
- * @method
926
- * @name idex#fetchMyTrades
927
- * @description fetch all trades made by the user
928
- * @see https://api-docs-v3.idex.io/#get-fills
929
- * @param {string} symbol unified market symbol
930
- * @param {int} [since] the earliest time in ms to fetch trades for
931
- * @param {int} [limit] the maximum number of trades structures to retrieve
932
- * @param {object} [params] extra parameters specific to the exchange API endpoint
933
- * @returns {Trade[]} a list of [trade structures]{@link https://docs.ccxt.com/#/?id=trade-structure}
934
- */
935
- async fetchMyTrades(symbol = undefined, since = undefined, limit = undefined, params = {}) {
936
- this.checkRequiredCredentials();
937
- await this.loadMarkets();
938
- let market = undefined;
939
- const request = {
940
- 'nonce': this.uuidv1(),
941
- 'wallet': this.walletAddress,
942
- };
943
- if (symbol !== undefined) {
944
- market = this.market(symbol);
945
- request['market'] = market['id'];
946
- }
947
- if (since !== undefined) {
948
- request['start'] = since;
949
- }
950
- if (limit !== undefined) {
951
- request['limit'] = limit;
952
- }
953
- // [
954
- // {
955
- // "fillId": "48582d10-b9bb-3c4b-94d3-e67537cf2472",
956
- // "price": "0.09905990",
957
- // "quantity": "0.40000000",
958
- // "quoteQuantity": "0.03962396",
959
- // "time": 1598873478762,
960
- // "makerSide": "sell",
961
- // "sequence": 5053,
962
- // "market": "DIL-ETH",
963
- // "orderId": "7cdc8e90-eb7d-11ea-9e60-4118569f6e63",
964
- // "side": "buy",
965
- // "fee": "0.00080000",
966
- // "feeAsset": "DIL",
967
- // "gas": "0.00857497",
968
- // "liquidity": "taker",
969
- // "txId": "0xeaa02b112c0b8b61bc02fa1776a2b39d6c614e287c1af90df0a2e591da573e65",
970
- // "txStatus": "mined"
971
- // }
972
- // ]
973
- const extendedRequest = this.extend(request, params);
974
- if (extendedRequest['wallet'] === undefined) {
975
- throw new BadRequest(this.id + ' fetchMyTrades() walletAddress is undefined, set this.walletAddress or "address" in params');
976
- }
977
- let response = undefined;
978
- try {
979
- response = await this.privateGetFills(extendedRequest);
980
- }
981
- catch (e) {
982
- if (e instanceof InvalidAddress) {
983
- const walletAddress = extendedRequest['wallet'];
984
- await this.associateWallet(walletAddress);
985
- response = await this.privateGetFills(extendedRequest);
986
- }
987
- else {
988
- throw e;
989
- }
990
- }
991
- return this.parseTrades(response, market, since, limit);
992
- }
993
- /**
994
- * @method
995
- * @name idex#fetchOrder
996
- * @description fetches information on an order made by the user
997
- * @see https://api-docs-v3.idex.io/#get-orders
998
- * @param {string} id order id
999
- * @param {string} symbol unified symbol of the market the order was made in
1000
- * @param {object} [params] extra parameters specific to the exchange API endpoint
1001
- * @returns {object} An [order structure]{@link https://docs.ccxt.com/#/?id=order-structure}
1002
- */
1003
- async fetchOrder(id, symbol = undefined, params = {}) {
1004
- const request = {
1005
- 'orderId': id,
1006
- };
1007
- return await this.fetchOrdersHelper(symbol, undefined, undefined, this.extend(request, params));
1008
- }
1009
- /**
1010
- * @method
1011
- * @name idex#fetchOpenOrders
1012
- * @description fetch all unfilled currently open orders
1013
- * @see https://api-docs-v3.idex.io/#get-orders
1014
- * @param {string} symbol unified market symbol
1015
- * @param {int} [since] the earliest time in ms to fetch open orders for
1016
- * @param {int} [limit] the maximum number of open orders structures to retrieve
1017
- * @param {object} [params] extra parameters specific to the exchange API endpoint
1018
- * @returns {Order[]} a list of [order structures]{@link https://docs.ccxt.com/#/?id=order-structure}
1019
- */
1020
- async fetchOpenOrders(symbol = undefined, since = undefined, limit = undefined, params = {}) {
1021
- const request = {
1022
- 'closed': false,
1023
- };
1024
- return await this.fetchOrdersHelper(symbol, since, limit, this.extend(request, params));
1025
- }
1026
- /**
1027
- * @method
1028
- * @name idex#fetchClosedOrders
1029
- * @description fetches information on multiple closed orders made by the user
1030
- * @see https://api-docs-v3.idex.io/#get-orders
1031
- * @param {string} symbol unified market symbol of the market orders were made in
1032
- * @param {int} [since] the earliest time in ms to fetch orders for
1033
- * @param {int} [limit] the maximum number of order structures to retrieve
1034
- * @param {object} [params] extra parameters specific to the exchange API endpoint
1035
- * @returns {Order[]} a list of [order structures]{@link https://docs.ccxt.com/#/?id=order-structure}
1036
- */
1037
- async fetchClosedOrders(symbol = undefined, since = undefined, limit = undefined, params = {}) {
1038
- const request = {
1039
- 'closed': true,
1040
- };
1041
- return await this.fetchOrdersHelper(symbol, since, limit, this.extend(request, params));
1042
- }
1043
- async fetchOrdersHelper(symbol = undefined, since = undefined, limit = undefined, params = {}) {
1044
- await this.loadMarkets();
1045
- const request = {
1046
- 'nonce': this.uuidv1(),
1047
- 'wallet': this.walletAddress,
1048
- };
1049
- let market = undefined;
1050
- if (symbol !== undefined) {
1051
- market = this.market(symbol);
1052
- request['market'] = market['id'];
1053
- }
1054
- if (since !== undefined) {
1055
- request['start'] = since;
1056
- }
1057
- if (limit !== undefined) {
1058
- request['limit'] = limit;
1059
- }
1060
- const response = await this.privateGetOrders(this.extend(request, params));
1061
- // fetchClosedOrders / fetchOpenOrders
1062
- // [
1063
- // {
1064
- // "market": "DIL-ETH",
1065
- // "orderId": "7cdc8e90-eb7d-11ea-9e60-4118569f6e63",
1066
- // "wallet": "0x0AB991497116f7F5532a4c2f4f7B1784488628e1",
1067
- // "time": 1598873478650,
1068
- // "status": "filled",
1069
- // "type": "limit",
1070
- // "side": "buy",
1071
- // "originalQuantity": "0.40000000",
1072
- // "executedQuantity": "0.40000000",
1073
- // "cumulativeQuoteQuantity": "0.03962396",
1074
- // "avgExecutionPrice": "0.09905990",
1075
- // "price": "1.00000000",
1076
- // "fills": [
1077
- // {
1078
- // "fillId": "48582d10-b9bb-3c4b-94d3-e67537cf2472",
1079
- // "price": "0.09905990",
1080
- // "quantity": "0.40000000",
1081
- // "quoteQuantity": "0.03962396",
1082
- // "time": 1598873478650,
1083
- // "makerSide": "sell",
1084
- // "sequence": 5053,
1085
- // "fee": "0.00080000",
1086
- // "feeAsset": "DIL",
1087
- // "gas": "0.00857497",
1088
- // "liquidity": "taker",
1089
- // "txId": "0xeaa02b112c0b8b61bc02fa1776a2b39d6c614e287c1af90df0a2e591da573e65",
1090
- // "txStatus": "mined"
1091
- // }
1092
- // ]
1093
- // }
1094
- // ]
1095
- // fetchOrder
1096
- // { market: "DIL-ETH",
1097
- // "orderId": "7cdc8e90-eb7d-11ea-9e60-4118569f6e63",
1098
- // "wallet": "0x0AB991497116f7F5532a4c2f4f7B1784488628e1",
1099
- // "time": 1598873478650,
1100
- // "status": "filled",
1101
- // "type": "limit",
1102
- // "side": "buy",
1103
- // "originalQuantity": "0.40000000",
1104
- // "executedQuantity": "0.40000000",
1105
- // "cumulativeQuoteQuantity": "0.03962396",
1106
- // "avgExecutionPrice": "0.09905990",
1107
- // "price": "1.00000000",
1108
- // "fills":
1109
- // [ { fillId: "48582d10-b9bb-3c4b-94d3-e67537cf2472",
1110
- // "price": "0.09905990",
1111
- // "quantity": "0.40000000",
1112
- // "quoteQuantity": "0.03962396",
1113
- // "time": 1598873478650,
1114
- // "makerSide": "sell",
1115
- // "sequence": 5053,
1116
- // "fee": "0.00080000",
1117
- // "feeAsset": "DIL",
1118
- // "gas": "0.00857497",
1119
- // "liquidity": "taker",
1120
- // "txId": "0xeaa02b112c0b8b61bc02fa1776a2b39d6c614e287c1af90df0a2e591da573e65",
1121
- // "txStatus": "mined" } ] }
1122
- if (Array.isArray(response)) {
1123
- return this.parseOrders(response, market, since, limit);
1124
- }
1125
- else {
1126
- return this.parseOrder(response, market);
1127
- }
1128
- }
1129
- parseOrderStatus(status) {
1130
- // https://docs.idex.io/#order-states-amp-lifecycle
1131
- const statuses = {
1132
- 'active': 'open',
1133
- 'partiallyFilled': 'open',
1134
- 'rejected': 'canceled',
1135
- 'filled': 'closed',
1136
- };
1137
- return this.safeString(statuses, status, status);
1138
- }
1139
- parseOrder(order, market = undefined) {
1140
- //
1141
- // {
1142
- // "market": "DIL-ETH",
1143
- // "orderId": "7cdc8e90-eb7d-11ea-9e60-4118569f6e63",
1144
- // "wallet": "0x0AB991497116f7F5532a4c2f4f7B1784488628e1",
1145
- // "time": 1598873478650,
1146
- // "status": "filled",
1147
- // "type": "limit",
1148
- // "side": "buy",
1149
- // "originalQuantity": "0.40000000",
1150
- // "executedQuantity": "0.40000000",
1151
- // "cumulativeQuoteQuantity": "0.03962396",
1152
- // "avgExecutionPrice": "0.09905990",
1153
- // "price": "1.00000000",
1154
- // "fills": [
1155
- // {
1156
- // "fillId": "48582d10-b9bb-3c4b-94d3-e67537cf2472",
1157
- // "price": "0.09905990",
1158
- // "quantity": "0.40000000",
1159
- // "quoteQuantity": "0.03962396",
1160
- // "time": 1598873478650,
1161
- // "makerSide": "sell",
1162
- // "sequence": 5053,
1163
- // "fee": "0.00080000",
1164
- // "feeAsset": "DIL",
1165
- // "gas": "0.00857497",
1166
- // "liquidity": "taker",
1167
- // "txId": "0xeaa02b112c0b8b61bc02fa1776a2b39d6c614e287c1af90df0a2e591da573e65",
1168
- // "txStatus": "mined"
1169
- // }
1170
- // ]
1171
- // }
1172
- //
1173
- const timestamp = this.safeInteger(order, 'time');
1174
- const fills = this.safeValue(order, 'fills', []);
1175
- const id = this.safeString(order, 'orderId');
1176
- const clientOrderId = this.safeString(order, 'clientOrderId');
1177
- const marketId = this.safeString(order, 'market');
1178
- const side = this.safeString(order, 'side');
1179
- const symbol = this.safeSymbol(marketId, market, '-');
1180
- const type = this.safeString(order, 'type');
1181
- const amount = this.safeString(order, 'originalQuantity');
1182
- const filled = this.safeString(order, 'executedQuantity');
1183
- const average = this.safeString(order, 'avgExecutionPrice');
1184
- const price = this.safeString(order, 'price');
1185
- const rawStatus = this.safeString(order, 'status');
1186
- const timeInForce = this.safeStringUpper(order, 'timeInForce');
1187
- const status = this.parseOrderStatus(rawStatus);
1188
- return this.safeOrder({
1189
- 'info': order,
1190
- 'id': id,
1191
- 'clientOrderId': clientOrderId,
1192
- 'timestamp': timestamp,
1193
- 'datetime': this.iso8601(timestamp),
1194
- 'lastTradeTimestamp': undefined,
1195
- 'symbol': symbol,
1196
- 'type': type,
1197
- 'timeInForce': timeInForce,
1198
- 'postOnly': undefined,
1199
- 'side': side,
1200
- 'price': price,
1201
- 'triggerPrice': undefined,
1202
- 'amount': amount,
1203
- 'cost': undefined,
1204
- 'average': average,
1205
- 'filled': filled,
1206
- 'remaining': undefined,
1207
- 'status': status,
1208
- 'fee': undefined,
1209
- 'trades': fills,
1210
- }, market);
1211
- }
1212
- async associateWallet(walletAddress, params = {}) {
1213
- const nonce = this.uuidv1();
1214
- const noPrefix = this.remove0xPrefix(walletAddress);
1215
- const byteArray = [
1216
- this.base16ToBinary(nonce),
1217
- this.base16ToBinary(noPrefix),
1218
- ];
1219
- const binary = this.binaryConcatArray(byteArray);
1220
- const hash = this.hash(binary, keccak, 'hex');
1221
- const signature = this.signMessageString(hash, this.privateKey);
1222
- // {
1223
- // "address": "0x0AB991497116f7F5532a4c2f4f7B1784488628e1",
1224
- // "totalPortfolioValueUsd": "0.00",
1225
- // "time": 1598468353626
1226
- // }
1227
- const request = {
1228
- 'parameters': {
1229
- 'nonce': nonce,
1230
- 'wallet': walletAddress,
1231
- },
1232
- 'signature': signature,
1233
- };
1234
- const result = await this.privatePostWallets(request);
1235
- return result;
1236
- }
1237
- /**
1238
- * @method
1239
- * @name idex#createOrder
1240
- * @description create a trade order, https://docs.idex.io/#create-order
1241
- * @see https://api-docs-v3.idex.io/#create-order
1242
- * @param {string} symbol unified symbol of the market to create an order in
1243
- * @param {string} type 'market' or 'limit'
1244
- * @param {string} side 'buy' or 'sell'
1245
- * @param {float} amount how much of currency you want to trade in units of base currency
1246
- * @param {float} [price] the price at which the order is to be fulfilled, in units of the quote currency, ignored in market orders
1247
- * @param {object} [params] extra parameters specific to the exchange API endpoint
1248
- * @param {bool} [params.test] set to true to test an order, no order will be created but the request will be validated
1249
- * @returns {object} an [order structure]{@link https://docs.ccxt.com/#/?id=order-structure}
1250
- */
1251
- async createOrder(symbol, type, side, amount, price = undefined, params = {}) {
1252
- this.checkRequiredCredentials();
1253
- await this.loadMarkets();
1254
- const testOrder = this.safeBool(params, 'test', false);
1255
- params = this.omit(params, 'test');
1256
- const market = this.market(symbol);
1257
- const nonce = this.uuidv1();
1258
- let typeEnum = undefined;
1259
- const stopLossTypeEnums = {
1260
- 'stopLoss': 3,
1261
- 'stopLossLimit': 4,
1262
- 'takeProfit': 5,
1263
- 'takeProfitLimit': 6,
1264
- };
1265
- const triggerPrice = this.safeString(params, 'triggerPrice', 'stopPrice');
1266
- let triggerPriceString = undefined;
1267
- if ((type === 'stopLossLimit') || (type === 'takeProfitLimit')) {
1268
- if (triggerPrice === undefined) {
1269
- throw new BadRequest(this.id + ' createOrder() triggerPrice is a required parameter for ' + type + 'orders');
1270
- }
1271
- triggerPriceString = this.priceToPrecision(symbol, triggerPrice);
1272
- }
1273
- const limitTypeEnums = {
1274
- 'limit': 1,
1275
- 'limitMaker': 2,
1276
- };
1277
- let priceString = undefined;
1278
- const typeLower = type.toLowerCase();
1279
- const limitOrder = typeLower.indexOf('limit') >= 0;
1280
- if (type in limitTypeEnums) {
1281
- typeEnum = limitTypeEnums[type];
1282
- priceString = this.priceToPrecision(symbol, price);
1283
- }
1284
- else if (type in stopLossTypeEnums) {
1285
- typeEnum = stopLossTypeEnums[type];
1286
- priceString = this.priceToPrecision(symbol, price);
1287
- }
1288
- else if (type === 'market') {
1289
- typeEnum = 0;
1290
- }
1291
- else {
1292
- throw new BadRequest(this.id + ' ' + type + ' is not a valid order type');
1293
- }
1294
- let amountEnum = 0; // base quantity
1295
- if ('quoteOrderQuantity' in params) {
1296
- if (type !== 'market') {
1297
- throw new NotSupported(this.id + ' createOrder() quoteOrderQuantity is not supported for ' + type + ' orders, only supported for market orders');
1298
- }
1299
- amountEnum = 1;
1300
- amount = this.safeNumber(params, 'quoteOrderQuantity');
1301
- }
1302
- const sideEnum = (side === 'buy') ? 0 : 1;
1303
- const walletBytes = this.remove0xPrefix(this.walletAddress);
1304
- const network = this.safeString(this.options, 'network', 'ETH');
1305
- const orderVersion = this.getSupportedMapping(network, {
1306
- 'ETH': 1,
1307
- 'BSC': 2,
1308
- 'MATIC': 4,
1309
- });
1310
- const amountString = this.amountToPrecision(symbol, amount);
1311
- // https://docs.idex.io/#time-in-force
1312
- const timeInForceEnums = {
1313
- 'gtc': 0,
1314
- 'ioc': 2,
1315
- 'fok': 3,
1316
- };
1317
- const defaultTimeInForce = this.safeString(this.options, 'defaultTimeInForce', 'gtc');
1318
- const timeInForce = this.safeString(params, 'timeInForce', defaultTimeInForce);
1319
- let timeInForceEnum = undefined;
1320
- if (timeInForce in timeInForceEnums) {
1321
- timeInForceEnum = timeInForceEnums[timeInForce];
1322
- }
1323
- else {
1324
- const allOptions = Object.keys(timeInForceEnums);
1325
- const asString = allOptions.join(', ');
1326
- throw new BadRequest(this.id + ' ' + timeInForce + ' is not a valid timeInForce, please choose one of ' + asString);
1327
- }
1328
- // https://docs.idex.io/#self-trade-prevention
1329
- const selfTradePreventionEnums = {
1330
- 'dc': 0,
1331
- 'co': 1,
1332
- 'cn': 2,
1333
- 'cb': 3,
1334
- };
1335
- const defaultSelfTradePrevention = this.safeString(this.options, 'defaultSelfTradePrevention', 'cn');
1336
- const selfTradePrevention = this.safeString(params, 'selfTradePrevention', defaultSelfTradePrevention);
1337
- let selfTradePreventionEnum = undefined;
1338
- if (selfTradePrevention in selfTradePreventionEnums) {
1339
- selfTradePreventionEnum = selfTradePreventionEnums[selfTradePrevention];
1340
- }
1341
- else {
1342
- const allOptions = Object.keys(selfTradePreventionEnums);
1343
- const asString = allOptions.join(', ');
1344
- throw new BadRequest(this.id + ' ' + selfTradePrevention + ' is not a valid selfTradePrevention, please choose one of ' + asString);
1345
- }
1346
- const byteArray = [
1347
- this.numberToBE(orderVersion, 1),
1348
- this.base16ToBinary(nonce),
1349
- this.base16ToBinary(walletBytes),
1350
- this.encode(market['id']),
1351
- this.numberToBE(typeEnum, 1),
1352
- this.numberToBE(sideEnum, 1),
1353
- this.encode(amountString),
1354
- this.numberToBE(amountEnum, 1),
1355
- ];
1356
- if (limitOrder) {
1357
- const encodedPrice = this.encode(priceString);
1358
- byteArray.push(encodedPrice);
1359
- }
1360
- if (type in stopLossTypeEnums) {
1361
- const encodedPrice = this.encode(triggerPriceString || priceString);
1362
- byteArray.push(encodedPrice);
1363
- }
1364
- const clientOrderId = this.safeString(params, 'clientOrderId');
1365
- if (clientOrderId !== undefined) {
1366
- byteArray.push(this.encode(clientOrderId));
1367
- }
1368
- const after = [
1369
- this.numberToBE(timeInForceEnum, 1),
1370
- this.numberToBE(selfTradePreventionEnum, 1),
1371
- this.numberToBE(0, 8), // unused
1372
- ];
1373
- const allBytes = this.arrayConcat(byteArray, after);
1374
- const binary = this.binaryConcatArray(allBytes);
1375
- const hash = this.hash(binary, keccak, 'hex');
1376
- const signature = this.signMessageString(hash, this.privateKey);
1377
- const request = {
1378
- 'parameters': {
1379
- 'nonce': nonce,
1380
- 'market': market['id'],
1381
- 'side': side,
1382
- 'type': type,
1383
- 'wallet': this.walletAddress,
1384
- 'selfTradePrevention': selfTradePrevention,
1385
- },
1386
- 'signature': signature,
1387
- };
1388
- if (type !== 'market') {
1389
- request['parameters']['timeInForce'] = timeInForce;
1390
- }
1391
- if (limitOrder) {
1392
- request['parameters']['price'] = priceString;
1393
- }
1394
- if (type in stopLossTypeEnums) {
1395
- request['parameters']['stopPrice'] = triggerPriceString || priceString;
1396
- }
1397
- if (amountEnum === 0) {
1398
- request['parameters']['quantity'] = amountString;
1399
- }
1400
- else {
1401
- request['parameters']['quoteOrderQuantity'] = amountString;
1402
- }
1403
- if (clientOrderId !== undefined) {
1404
- request['parameters']['clientOrderId'] = clientOrderId;
1405
- }
1406
- // {
1407
- // "market": "DIL-ETH",
1408
- // "orderId": "7cdc8e90-eb7d-11ea-9e60-4118569f6e63",
1409
- // "wallet": "0x0AB991497116f7F5532a4c2f4f7B1784488628e1",
1410
- // "time": 1598873478650,
1411
- // "status": "filled",
1412
- // "type": "limit",
1413
- // "side": "buy",
1414
- // "originalQuantity": "0.40000000",
1415
- // "executedQuantity": "0.40000000",
1416
- // "cumulativeQuoteQuantity": "0.03962396",
1417
- // "price": "1.00000000",
1418
- // "fills": [
1419
- // {
1420
- // "fillId": "48582d10-b9bb-3c4b-94d3-e67537cf2472",
1421
- // "price": "0.09905990",
1422
- // "quantity": "0.40000000",
1423
- // "quoteQuantity": "0.03962396",
1424
- // "time": 1598873478650,
1425
- // "makerSide": "sell",
1426
- // "sequence": 5053,
1427
- // "fee": "0.00080000",
1428
- // "feeAsset": "DIL",
1429
- // "gas": "0.00857497",
1430
- // "liquidity": "taker",
1431
- // "txStatus": "pending"
1432
- // }
1433
- // ],
1434
- // "avgExecutionPrice": "0.09905990"
1435
- // }
1436
- // we don't use extend here because it is a signed endpoint
1437
- let response = undefined;
1438
- if (testOrder) {
1439
- response = await this.privatePostOrdersTest(request);
1440
- }
1441
- else {
1442
- response = await this.privatePostOrders(request);
1443
- }
1444
- return this.parseOrder(response, market);
1445
- }
1446
- /**
1447
- * @method
1448
- * @name idex#withdraw
1449
- * @description make a withdrawal
1450
- * @see https://api-docs-v3.idex.io/#withdraw-funds
1451
- * @param {string} code unified currency code
1452
- * @param {float} amount the amount to withdraw
1453
- * @param {string} address the address to withdraw to
1454
- * @param {string} tag
1455
- * @param {object} [params] extra parameters specific to the exchange API endpoint
1456
- * @returns {object} a [transaction structure]{@link https://docs.ccxt.com/#/?id=transaction-structure}
1457
- */
1458
- async withdraw(code, amount, address, tag = undefined, params = {}) {
1459
- [tag, params] = this.handleWithdrawTagAndParams(tag, params);
1460
- this.checkRequiredCredentials();
1461
- await this.loadMarkets();
1462
- const nonce = this.uuidv1();
1463
- const amountString = this.currencyToPrecision(code, amount);
1464
- const currency = this.currency(code);
1465
- const walletBytes = this.remove0xPrefix(this.walletAddress);
1466
- const byteArray = [
1467
- this.base16ToBinary(nonce),
1468
- this.base16ToBinary(walletBytes),
1469
- this.encode(currency['id']),
1470
- this.encode(amountString),
1471
- this.numberToBE(1, 1), // bool set to true
1472
- ];
1473
- const binary = this.binaryConcatArray(byteArray);
1474
- const hash = this.hash(binary, keccak, 'hex');
1475
- const signature = this.signMessageString(hash, this.privateKey);
1476
- const request = {
1477
- 'parameters': {
1478
- 'nonce': nonce,
1479
- 'wallet': address,
1480
- 'asset': currency['id'],
1481
- 'quantity': amountString,
1482
- },
1483
- 'signature': signature,
1484
- };
1485
- const response = await this.privatePostWithdrawals(request);
1486
- //
1487
- // {
1488
- // "withdrawalId": "a61dcff0-ec4d-11ea-8b83-c78a6ecb3180",
1489
- // "asset": "ETH",
1490
- // "assetContractAddress": "0x0000000000000000000000000000000000000000",
1491
- // "quantity": "0.20000000",
1492
- // "time": 1598962883190,
1493
- // "fee": "0.00024000",
1494
- // "txStatus": "pending",
1495
- // "txId": null
1496
- // }
1497
- //
1498
- return this.parseTransaction(response, currency);
1499
- }
1500
- /**
1501
- * @method
1502
- * @name idex#cancelAllOrders
1503
- * @description cancel all open orders
1504
- * @see https://api-docs-v3.idex.io/#cancel-order
1505
- * @param {string} symbol unified market symbol, only orders in the market of this symbol are cancelled when symbol is not undefined
1506
- * @param {object} [params] extra parameters specific to the exchange API endpoint
1507
- * @returns {object[]} a list of [order structures]{@link https://docs.ccxt.com/#/?id=order-structure}
1508
- */
1509
- async cancelAllOrders(symbol = undefined, params = {}) {
1510
- this.checkRequiredCredentials();
1511
- await this.loadMarkets();
1512
- let market = undefined;
1513
- if (symbol !== undefined) {
1514
- market = this.market(symbol);
1515
- }
1516
- const nonce = this.uuidv1();
1517
- const request = {
1518
- 'parameters': {
1519
- 'nonce': nonce,
1520
- 'wallet': this.walletAddress,
1521
- },
1522
- };
1523
- const walletBytes = this.remove0xPrefix(this.walletAddress);
1524
- const byteArray = [
1525
- this.base16ToBinary(nonce),
1526
- this.base16ToBinary(walletBytes),
1527
- ];
1528
- if (market !== undefined) {
1529
- byteArray.push(this.encode(market['id']));
1530
- request['parameters']['market'] = market['id'];
1531
- }
1532
- const binary = this.binaryConcatArray(byteArray);
1533
- const hash = this.hash(binary, keccak, 'hex');
1534
- const signature = this.signMessageString(hash, this.privateKey);
1535
- request['signature'] = signature;
1536
- // [ { orderId: "688336f0-ec50-11ea-9842-b332f8a34d0e" } ]
1537
- const response = await this.privateDeleteOrders(this.extend(request, params));
1538
- return this.parseOrders(response, market);
1539
- }
1540
- /**
1541
- * @method
1542
- * @name idex#cancelOrder
1543
- * @description cancels an open order
1544
- * @see https://api-docs-v3.idex.io/#cancel-order
1545
- * @param {string} id order id
1546
- * @param {string} symbol unified symbol of the market the order was made in
1547
- * @param {object} [params] extra parameters specific to the exchange API endpoint
1548
- * @returns {object} An [order structure]{@link https://docs.ccxt.com/#/?id=order-structure}
1549
- */
1550
- async cancelOrder(id, symbol = undefined, params = {}) {
1551
- this.checkRequiredCredentials();
1552
- await this.loadMarkets();
1553
- let market = undefined;
1554
- if (symbol !== undefined) {
1555
- market = this.market(symbol);
1556
- }
1557
- const nonce = this.uuidv1();
1558
- const walletBytes = this.remove0xPrefix(this.walletAddress);
1559
- const byteArray = [
1560
- this.base16ToBinary(nonce),
1561
- this.base16ToBinary(walletBytes),
1562
- this.encode(id),
1563
- ];
1564
- const binary = this.binaryConcatArray(byteArray);
1565
- const hash = this.hash(binary, keccak, 'hex');
1566
- const signature = this.signMessageString(hash, this.privateKey);
1567
- const request = {
1568
- 'parameters': {
1569
- 'nonce': nonce,
1570
- 'wallet': this.walletAddress,
1571
- 'orderId': id,
1572
- },
1573
- 'signature': signature,
1574
- };
1575
- // [ { orderId: "688336f0-ec50-11ea-9842-b332f8a34d0e" } ]
1576
- const response = await this.privateDeleteOrders(this.extend(request, params));
1577
- const canceledOrder = this.safeDict(response, 0);
1578
- return this.parseOrder(canceledOrder, market);
1579
- }
1580
- handleErrors(code, reason, url, method, headers, body, response, requestHeaders, requestBody) {
1581
- const errorCode = this.safeString(response, 'code');
1582
- const message = this.safeString(response, 'message');
1583
- if (errorCode !== undefined) {
1584
- this.throwExactlyMatchedException(this.exceptions['exact'], errorCode, message);
1585
- throw new ExchangeError(this.id + ' ' + message);
1586
- }
1587
- return undefined;
1588
- }
1589
- /**
1590
- * @method
1591
- * @name idex#fetchDeposit
1592
- * @description fetch information on a deposit
1593
- * @see https://api-docs-v3.idex.io/#get-deposits
1594
- * @param {string} id deposit id
1595
- * @param {string} code not used by idex fetchDeposit ()
1596
- * @param {object} [params] extra parameters specific to the exchange API endpoint
1597
- * @returns {object} a [transaction structure]{@link https://docs.ccxt.com/#/?id=transaction-structure}
1598
- */
1599
- async fetchDeposit(id, code = undefined, params = {}) {
1600
- await this.loadMarkets();
1601
- const nonce = this.uuidv1();
1602
- const request = {
1603
- 'nonce': nonce,
1604
- 'wallet': this.walletAddress,
1605
- 'depositId': id,
1606
- };
1607
- const response = await this.privateGetDeposits(this.extend(request, params));
1608
- return this.parseTransaction(response);
1609
- }
1610
- /**
1611
- * @method
1612
- * @name idex#fetchDeposits
1613
- * @description fetch all deposits made to an account
1614
- * @see https://api-docs-v3.idex.io/#get-deposits
1615
- * @param {string} code unified currency code
1616
- * @param {int} [since] the earliest time in ms to fetch deposits for
1617
- * @param {int} [limit] the maximum number of deposits structures to retrieve
1618
- * @param {object} [params] extra parameters specific to the exchange API endpoint
1619
- * @returns {object[]} a list of [transaction structures]{@link https://docs.ccxt.com/#/?id=transaction-structure}
1620
- */
1621
- async fetchDeposits(code = undefined, since = undefined, limit = undefined, params = {}) {
1622
- params = this.extend({
1623
- 'method': 'privateGetDeposits',
1624
- }, params);
1625
- return await this.fetchTransactionsHelper(code, since, limit, params);
1626
- }
1627
- /**
1628
- * @method
1629
- * @name idex#fetchStatus
1630
- * @description the latest known information on the availability of the exchange API
1631
- * @see https://api-docs-v3.idex.io/#get-ping
1632
- * @param {object} [params] extra parameters specific to the exchange API endpoint
1633
- * @returns {object} a [status structure]{@link https://docs.ccxt.com/#/?id=exchange-status-structure}
1634
- */
1635
- async fetchStatus(params = {}) {
1636
- const response = await this.publicGetPing(params);
1637
- return {
1638
- 'status': 'ok',
1639
- 'updated': undefined,
1640
- 'eta': undefined,
1641
- 'url': undefined,
1642
- 'info': response,
1643
- };
1644
- }
1645
- /**
1646
- * @method
1647
- * @name idex#fetchTime
1648
- * @description fetches the current integer timestamp in milliseconds from the exchange server
1649
- * @see https://api-docs-v3.idex.io/#get-time
1650
- * @param {object} [params] extra parameters specific to the exchange API endpoint
1651
- * @returns {int} the current integer timestamp in milliseconds from the exchange server
1652
- */
1653
- async fetchTime(params = {}) {
1654
- const response = await this.publicGetTime(params);
1655
- //
1656
- // { serverTime: "1655258263236" }
1657
- //
1658
- return this.safeInteger(response, 'serverTime');
1659
- }
1660
- /**
1661
- * @method
1662
- * @name idex#fetchWithdrawal
1663
- * @description fetch data on a currency withdrawal via the withdrawal id
1664
- * @see https://api-docs-v3.idex.io/#get-withdrawals
1665
- * @param {string} id withdrawal id
1666
- * @param {string} code not used by idex.fetchWithdrawal
1667
- * @param {object} [params] extra parameters specific to the exchange API endpoint
1668
- * @returns {object} a [transaction structure]{@link https://docs.ccxt.com/#/?id=transaction-structure}
1669
- */
1670
- async fetchWithdrawal(id, code = undefined, params = {}) {
1671
- await this.loadMarkets();
1672
- const nonce = this.uuidv1();
1673
- const request = {
1674
- 'nonce': nonce,
1675
- 'wallet': this.walletAddress,
1676
- 'withdrawalId': id,
1677
- };
1678
- const response = await this.privateGetWithdrawals(this.extend(request, params));
1679
- return this.parseTransaction(response);
1680
- }
1681
- /**
1682
- * @method
1683
- * @name idex#fetchWithdrawals
1684
- * @description fetch all withdrawals made from an account
1685
- * @see https://api-docs-v3.idex.io/#get-withdrawals
1686
- * @param {string} code unified currency code
1687
- * @param {int} [since] the earliest time in ms to fetch withdrawals for
1688
- * @param {int} [limit] the maximum number of withdrawals structures to retrieve
1689
- * @param {object} [params] extra parameters specific to the exchange API endpoint
1690
- * @returns {object[]} a list of [transaction structures]{@link https://docs.ccxt.com/#/?id=transaction-structure}
1691
- */
1692
- async fetchWithdrawals(code = undefined, since = undefined, limit = undefined, params = {}) {
1693
- params = this.extend({
1694
- 'method': 'privateGetWithdrawals',
1695
- }, params);
1696
- return await this.fetchTransactionsHelper(code, since, limit, params);
1697
- }
1698
- async fetchTransactionsHelper(code = undefined, since = undefined, limit = undefined, params = {}) {
1699
- await this.loadMarkets();
1700
- const nonce = this.uuidv1();
1701
- const request = {
1702
- 'nonce': nonce,
1703
- 'wallet': this.walletAddress,
1704
- };
1705
- let currency = undefined;
1706
- if (code !== undefined) {
1707
- currency = this.currency(code);
1708
- request['asset'] = currency['id'];
1709
- }
1710
- if (since !== undefined) {
1711
- request['start'] = since;
1712
- }
1713
- if (limit !== undefined) {
1714
- request['limit'] = limit;
1715
- }
1716
- // [
1717
- // {
1718
- // "depositId": "e9970cc0-eb6b-11ea-9e89-09a5ebc1f98e",
1719
- // "asset": "ETH",
1720
- // "quantity": "1.00000000",
1721
- // "txId": "0xcd4aac3171d7131cc9e795568c67938675185ac17641553ef54c8a7c294c8142",
1722
- // "txTime": 1598865853000,
1723
- // "confirmationTime": 1598865930231
1724
- // }
1725
- // ]
1726
- const method = params['method'];
1727
- params = this.omit(params, 'method');
1728
- let response = undefined;
1729
- if (method === 'privateGetDeposits') {
1730
- response = await this.privateGetDeposits(this.extend(request, params));
1731
- }
1732
- else if (method === 'privateGetWithdrawals') {
1733
- response = await this.privateGetWithdrawals(this.extend(request, params));
1734
- }
1735
- else {
1736
- throw new NotSupported(this.id + ' fetchTransactionsHelper() not support this method');
1737
- }
1738
- return this.parseTransactions(response, currency, since, limit);
1739
- }
1740
- parseTransactionStatus(status) {
1741
- const statuses = {
1742
- 'mined': 'ok',
1743
- };
1744
- return this.safeString(statuses, status, status);
1745
- }
1746
- parseTransaction(transaction, currency = undefined) {
1747
- //
1748
- // fetchDeposits
1749
- //
1750
- // {
1751
- // "depositId": "e9970cc0-eb6b-11ea-9e89-09a5ebc1f98f",
1752
- // "asset": "ETH",
1753
- // "quantity": "1.00000000",
1754
- // "txId": "0xcd4aac3171d7131cc9e795568c67938675185ac17641553ef54c8a7c294c8142",
1755
- // "txTime": 1598865853000,
1756
- // "confirmationTime": 1598865930231
1757
- // }
1758
- //
1759
- // fetchWithdrwalas
1760
- //
1761
- // {
1762
- // "withdrawalId": "a62d8760-ec4d-11ea-9fa6-47904c19499b",
1763
- // "asset": "ETH",
1764
- // "assetContractAddress": "0x0000000000000000000000000000000000000000",
1765
- // "quantity": "0.20000000",
1766
- // "time": 1598962883288,
1767
- // "fee": "0.00024000",
1768
- // "txId": "0x305e9cdbaa85ad029f50578d13d31d777c085de573ed5334d95c19116d8c03ce",
1769
- // "txStatus": "mined"
1770
- // }
1771
- //
1772
- // withdraw
1773
- //
1774
- // {
1775
- // "withdrawalId": "a61dcff0-ec4d-11ea-8b83-c78a6ecb3180",
1776
- // "asset": "ETH",
1777
- // "assetContractAddress": "0x0000000000000000000000000000000000000000",
1778
- // "quantity": "0.20000000",
1779
- // "time": 1598962883190,
1780
- // "fee": "0.00024000",
1781
- // "txStatus": "pending",
1782
- // "txId": null
1783
- // }
1784
- //
1785
- let type = undefined;
1786
- if ('depositId' in transaction) {
1787
- type = 'deposit';
1788
- }
1789
- else if (('withdrawId' in transaction) || ('withdrawalId' in transaction)) {
1790
- type = 'withdrawal';
1791
- }
1792
- let id = this.safeString2(transaction, 'depositId', 'withdrawId');
1793
- id = this.safeString(transaction, 'withdrawalId', id);
1794
- const code = this.safeCurrencyCode(this.safeString(transaction, 'asset'), currency);
1795
- const amount = this.safeNumber(transaction, 'quantity');
1796
- const txid = this.safeString(transaction, 'txId');
1797
- const timestamp = this.safeInteger2(transaction, 'txTime', 'time');
1798
- let fee = undefined;
1799
- if ('fee' in transaction) {
1800
- fee = {
1801
- 'cost': this.safeNumber(transaction, 'fee'),
1802
- 'currency': 'ETH',
1803
- };
1804
- }
1805
- const rawStatus = this.safeString(transaction, 'txStatus');
1806
- const status = this.parseTransactionStatus(rawStatus);
1807
- const updated = this.safeInteger(transaction, 'confirmationTime');
1808
- return {
1809
- 'info': transaction,
1810
- 'id': id,
1811
- 'txid': txid,
1812
- 'timestamp': timestamp,
1813
- 'datetime': this.iso8601(timestamp),
1814
- 'network': undefined,
1815
- 'address': undefined,
1816
- 'addressTo': undefined,
1817
- 'addressFrom': undefined,
1818
- 'tag': undefined,
1819
- 'tagTo': undefined,
1820
- 'tagFrom': undefined,
1821
- 'type': type,
1822
- 'amount': amount,
1823
- 'currency': code,
1824
- 'status': status,
1825
- 'updated': updated,
1826
- 'comment': undefined,
1827
- 'internal': undefined,
1828
- 'fee': fee,
1829
- };
1830
- }
1831
- calculateRateLimiterCost(api, method, path, params, config = {}) {
1832
- const hasApiKey = (this.apiKey !== undefined);
1833
- const hasSecret = (this.secret !== undefined);
1834
- const hasWalletAddress = (this.walletAddress !== undefined);
1835
- const hasPrivateKey = (this.privateKey !== undefined);
1836
- const defaultCost = this.safeValue(config, 'cost', 1);
1837
- const authenticated = hasApiKey && hasSecret && hasWalletAddress && hasPrivateKey;
1838
- return authenticated ? (defaultCost / 2) : defaultCost;
1839
- }
1840
- /**
1841
- * @method
1842
- * @name idex#fetchDepositAddress
1843
- * @description fetch the Polygon address of the wallet
1844
- * @see https://api-docs-v3.idex.io/#get-wallets
1845
- * @param {string} code not used by idex
1846
- * @param {object} [params] extra parameters specific to the exchange API endpoint
1847
- * @returns {object} an [address structure]{@link https://docs.ccxt.com/#/?id=address-structure}
1848
- */
1849
- async fetchDepositAddress(code, params = {}) {
1850
- const request = {};
1851
- request['nonce'] = this.uuidv1();
1852
- const response = await this.privateGetWallets(this.extend(request, params));
1853
- //
1854
- // [
1855
- // {
1856
- // address: "0x37A1827CA64C94A26028bDCb43FBDCB0bf6DAf5B",
1857
- // totalPortfolioValueUsd: "0.00",
1858
- // time: "1678342148086"
1859
- // },
1860
- // {
1861
- // address: "0x0Ef3456E616552238B0c562d409507Ed6051A7b3",
1862
- // totalPortfolioValueUsd: "15.90",
1863
- // time: "1691697811659"
1864
- // }
1865
- // ]
1866
- //
1867
- return this.parseDepositAddress(response);
1868
- }
1869
- parseDepositAddress(depositAddress, currency = undefined) {
1870
- //
1871
- // [
1872
- // {
1873
- // address: "0x37A1827CA64C94A26028bDCb43FBDCB0bf6DAf5B",
1874
- // totalPortfolioValueUsd: "0.00",
1875
- // time: "1678342148086"
1876
- // },
1877
- // {
1878
- // address: "0x0Ef3456E616552238B0c562d409507Ed6051A7b3",
1879
- // totalPortfolioValueUsd: "15.90",
1880
- // time: "1691697811659"
1881
- // }
1882
- // ]
1883
- //
1884
- const length = depositAddress.length;
1885
- const entry = this.safeDict(depositAddress, length - 1);
1886
- const address = this.safeString(entry, 'address');
1887
- this.checkAddress(address);
1888
- return {
1889
- 'info': depositAddress,
1890
- 'currency': undefined,
1891
- 'network': 'MATIC',
1892
- 'address': address,
1893
- 'tag': undefined,
1894
- };
1895
- }
1896
- sign(path, api = 'public', method = 'GET', params = {}, headers = undefined, body = undefined) {
1897
- const network = this.safeString(this.options, 'network', 'ETH');
1898
- const version = this.safeString(this.options, 'version', 'v1');
1899
- let url = this.urls['api'][network] + '/' + version + '/' + path;
1900
- const keys = Object.keys(params);
1901
- const length = keys.length;
1902
- let query = undefined;
1903
- if (length > 0) {
1904
- if (method === 'GET') {
1905
- query = this.urlencode(params);
1906
- url = url + '?' + query;
1907
- }
1908
- else {
1909
- body = this.json(params);
1910
- }
1911
- }
1912
- headers = {
1913
- 'Content-Type': 'application/json',
1914
- };
1915
- if (this.apiKey !== undefined) {
1916
- headers['IDEX-API-Key'] = this.apiKey;
1917
- }
1918
- if (api === 'private') {
1919
- let payload = undefined;
1920
- if (method === 'GET') {
1921
- payload = query;
1922
- }
1923
- else {
1924
- payload = body;
1925
- }
1926
- headers['IDEX-HMAC-Signature'] = this.hmac(this.encode(payload), this.encode(this.secret), sha256, 'hex');
1927
- }
1928
- return { 'url': url, 'method': method, 'body': body, 'headers': headers };
1929
- }
1930
- remove0xPrefix(hexData) {
1931
- if (hexData.slice(0, 2) === '0x') {
1932
- return hexData.slice(2);
1933
- }
1934
- else {
1935
- return hexData;
1936
- }
1937
- }
1938
- hashMessage(message) {
1939
- // takes a hex encoded message
1940
- const binaryMessage = this.base16ToBinary(this.remove0xPrefix(message));
1941
- const prefix = this.encode('\x19Ethereum Signed Message:\n' + binaryMessage.byteLength);
1942
- return '0x' + this.hash(this.binaryConcat(prefix, binaryMessage), keccak, 'hex');
1943
- }
1944
- signHash(hash, privateKey) {
1945
- const signature = ecdsa(hash.slice(-64), privateKey.slice(-64), secp256k1, undefined);
1946
- return {
1947
- 'r': '0x' + signature['r'],
1948
- 's': '0x' + signature['s'],
1949
- 'v': 27 + signature['v'],
1950
- };
1951
- }
1952
- signMessage(message, privateKey) {
1953
- return this.signHash(this.hashMessage(message), privateKey.slice(-64));
1954
- }
1955
- signMessageString(message, privateKey) {
1956
- // still takes the input as a hex string
1957
- // same as above but returns a string instead of an object
1958
- const signature = this.signMessage(message, privateKey);
1959
- return signature['r'] + this.remove0xPrefix(signature['s']) + this.binaryToBase16(this.numberToBE(signature['v'], 1));
1960
- }
1961
- }