ccxt 4.2.92 → 4.2.94

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 (52) hide show
  1. package/README.md +3 -3
  2. package/build.sh +1 -1
  3. package/dist/ccxt.browser.js +807 -175
  4. package/dist/ccxt.browser.min.js +3 -3
  5. package/dist/cjs/ccxt.js +1 -1
  6. package/dist/cjs/src/base/Exchange.js +50 -9
  7. package/dist/cjs/src/base/functions/encode.js +4 -4
  8. package/dist/cjs/src/binance.js +63 -2
  9. package/dist/cjs/src/bitget.js +139 -0
  10. package/dist/cjs/src/coinex.js +0 -30
  11. package/dist/cjs/src/digifinex.js +1 -22
  12. package/dist/cjs/src/okx.js +153 -0
  13. package/dist/cjs/src/pro/kraken.js +107 -17
  14. package/dist/cjs/src/pro/krakenfutures.js +117 -40
  15. package/dist/cjs/src/pro/kucoin.js +30 -19
  16. package/dist/cjs/src/probit.js +3 -4
  17. package/dist/cjs/src/woo.js +139 -0
  18. package/examples/js/cli.js +4 -1
  19. package/examples/ts/cli.ts +4 -1
  20. package/js/ccxt.d.ts +3 -3
  21. package/js/ccxt.js +1 -1
  22. package/js/src/abstract/binance.d.ts +1 -0
  23. package/js/src/abstract/binancecoinm.d.ts +1 -0
  24. package/js/src/abstract/binanceus.d.ts +1 -0
  25. package/js/src/abstract/binanceusdm.d.ts +1 -0
  26. package/js/src/base/Exchange.d.ts +16 -10
  27. package/js/src/base/Exchange.js +50 -9
  28. package/js/src/base/functions/encode.d.ts +1 -1
  29. package/js/src/base/functions/encode.js +4 -4
  30. package/js/src/base/functions/rsa.d.ts +1 -1
  31. package/js/src/base/types.d.ts +12 -0
  32. package/js/src/binance.d.ts +1 -0
  33. package/js/src/binance.js +63 -2
  34. package/js/src/bitget.d.ts +4 -1
  35. package/js/src/bitget.js +139 -0
  36. package/js/src/coinex.d.ts +0 -1
  37. package/js/src/coinex.js +0 -30
  38. package/js/src/digifinex.d.ts +0 -1
  39. package/js/src/digifinex.js +1 -49
  40. package/js/src/okx.d.ts +4 -1
  41. package/js/src/okx.js +153 -0
  42. package/js/src/pro/kraken.d.ts +6 -1
  43. package/js/src/pro/kraken.js +107 -17
  44. package/js/src/pro/krakenfutures.d.ts +8 -2
  45. package/js/src/pro/krakenfutures.js +117 -40
  46. package/js/src/pro/kucoin.js +30 -19
  47. package/js/src/probit.d.ts +1 -1
  48. package/js/src/probit.js +3 -4
  49. package/js/src/woo.d.ts +4 -1
  50. package/js/src/woo.js +139 -0
  51. package/package.json +1 -1
  52. package/skip-tests.json +4 -0
@@ -7639,6 +7639,8 @@ class Exchange {
7639
7639
  'fetchClosedOrder': undefined,
7640
7640
  'fetchClosedOrders': undefined,
7641
7641
  'fetchClosedOrdersWs': undefined,
7642
+ 'fetchConvertCurrencies': undefined,
7643
+ 'fetchConvertQuote': undefined,
7642
7644
  'fetchCrossBorrowRate': undefined,
7643
7645
  'fetchCrossBorrowRates': undefined,
7644
7646
  'fetchCurrencies': 'emulated',
@@ -10398,6 +10400,16 @@ class Exchange {
10398
10400
  }
10399
10401
  return result;
10400
10402
  }
10403
+ marketsForSymbols(symbols = undefined) {
10404
+ if (symbols === undefined) {
10405
+ return symbols;
10406
+ }
10407
+ const result = [];
10408
+ for (let i = 0; i < symbols.length; i++) {
10409
+ result.push(this.market(symbols[i]));
10410
+ }
10411
+ return result;
10412
+ }
10401
10413
  marketSymbols(symbols = undefined, type = undefined, allowEmpty = true, sameTypeOnly = false, sameSubTypeOnly = false) {
10402
10414
  if (symbols === undefined) {
10403
10415
  if (!allowEmpty) {
@@ -10667,14 +10679,34 @@ class Exchange {
10667
10679
  // marketIdKey should only be undefined when response is a dictionary
10668
10680
  symbols = this.marketSymbols(symbols);
10669
10681
  const tiers = {};
10670
- for (let i = 0; i < response.length; i++) {
10671
- const item = response[i];
10672
- const id = this.safeString(item, marketIdKey);
10673
- const market = this.safeMarket(id, undefined, undefined, 'swap');
10674
- const symbol = market['symbol'];
10675
- const contract = this.safeBool(market, 'contract', false);
10676
- if (contract && ((symbols === undefined) || this.inArray(symbol, symbols))) {
10677
- tiers[symbol] = this.parseMarketLeverageTiers(item, market);
10682
+ let symbolsLength = 0;
10683
+ if (symbols !== undefined) {
10684
+ symbolsLength = symbols.length;
10685
+ }
10686
+ const noSymbols = (symbols === undefined) || (symbolsLength === 0);
10687
+ if (Array.isArray(response)) {
10688
+ for (let i = 0; i < response.length; i++) {
10689
+ const item = response[i];
10690
+ const id = this.safeString(item, marketIdKey);
10691
+ const market = this.safeMarket(id, undefined, undefined, 'swap');
10692
+ const symbol = market['symbol'];
10693
+ const contract = this.safeBool(market, 'contract', false);
10694
+ if (contract && (noSymbols || this.inArray(symbol, symbols))) {
10695
+ tiers[symbol] = this.parseMarketLeverageTiers(item, market);
10696
+ }
10697
+ }
10698
+ }
10699
+ else {
10700
+ const keys = Object.keys(response);
10701
+ for (let i = 0; i < keys.length; i++) {
10702
+ const marketId = keys[i];
10703
+ const item = response[marketId];
10704
+ const market = this.safeMarket(marketId, undefined, undefined, 'swap');
10705
+ const symbol = market['symbol'];
10706
+ const contract = this.safeBool(market, 'contract', false);
10707
+ if (contract && (noSymbols || this.inArray(symbol, symbols))) {
10708
+ tiers[symbol] = this.parseMarketLeverageTiers(item, market);
10709
+ }
10678
10710
  }
10679
10711
  }
10680
10712
  return tiers;
@@ -11726,6 +11758,9 @@ class Exchange {
11726
11758
  async fetchOption(symbol, params = {}) {
11727
11759
  throw new _errors_js__WEBPACK_IMPORTED_MODULE_3__.NotSupported(this.id + ' fetchOption() is not supported yet');
11728
11760
  }
11761
+ async fetchConvertQuote(fromCode, toCode, amount = undefined, params = {}) {
11762
+ throw new _errors_js__WEBPACK_IMPORTED_MODULE_3__.NotSupported(this.id + ' fetchConvertQuote() is not supported yet');
11763
+ }
11729
11764
  async fetchDepositsWithdrawals(code = undefined, since = undefined, limit = undefined, params = {}) {
11730
11765
  /**
11731
11766
  * @method
@@ -12274,6 +12309,9 @@ class Exchange {
12274
12309
  const fees = await this.fetchTradingFees(params);
12275
12310
  return this.safeDict(fees, symbol);
12276
12311
  }
12312
+ async fetchConvertCurrencies(params = {}) {
12313
+ throw new _errors_js__WEBPACK_IMPORTED_MODULE_3__.NotSupported(this.id + ' fetchConvertCurrencies() is not supported yet');
12314
+ }
12277
12315
  parseOpenInterest(interest, market = undefined) {
12278
12316
  throw new _errors_js__WEBPACK_IMPORTED_MODULE_3__.NotSupported(this.id + ' parseOpenInterest () is not supported yet');
12279
12317
  }
@@ -12971,7 +13009,10 @@ class Exchange {
12971
13009
  return leverageStructures;
12972
13010
  }
12973
13011
  parseLeverage(leverage, market = undefined) {
12974
- throw new _errors_js__WEBPACK_IMPORTED_MODULE_3__.NotSupported(this.id + ' parseLeverage() is not supported yet');
13012
+ throw new _errors_js__WEBPACK_IMPORTED_MODULE_3__.NotSupported(this.id + ' parseLeverage () is not supported yet');
13013
+ }
13014
+ parseConversion(conversion, fromCurrency = undefined, toCurrency = undefined) {
13015
+ throw new _errors_js__WEBPACK_IMPORTED_MODULE_3__.NotSupported(this.id + ' parseConversion () is not supported yet');
12975
13016
  }
12976
13017
  convertExpireDate(date) {
12977
13018
  // parse YYMMDD to datetime string
@@ -13987,13 +14028,13 @@ function crc32(str, signed = false) {
13987
14028
 
13988
14029
 
13989
14030
  /* ------------------------------------------------------------------------ */
13990
- const json = (data, params = undefined) => JSON.stringify(data), isJsonEncodedObject = object => ((typeof object === 'string') &&
14031
+ const json = (data, params = undefined) => JSON.stringify(data), isJsonEncodedObject = (object) => ((typeof object === 'string') &&
13991
14032
  (object.length >= 2) &&
13992
- ((object[0] === '{') || (object[0] === '['))), binaryToString = _static_dependencies_scure_base_index_js__WEBPACK_IMPORTED_MODULE_1__/* .utf8 */ .KA.encode, stringToBinary = _static_dependencies_scure_base_index_js__WEBPACK_IMPORTED_MODULE_1__/* .utf8 */ .KA.decode, stringToBase64 = string => _static_dependencies_scure_base_index_js__WEBPACK_IMPORTED_MODULE_1__/* .base64 */ .US.encode(_static_dependencies_scure_base_index_js__WEBPACK_IMPORTED_MODULE_1__/* .utf8 */ .KA.decode(string)), base64ToString = string => _static_dependencies_scure_base_index_js__WEBPACK_IMPORTED_MODULE_1__/* .utf8 */ .KA.encode(_static_dependencies_scure_base_index_js__WEBPACK_IMPORTED_MODULE_1__/* .base64 */ .US.decode(string)), base64ToBinary = _static_dependencies_scure_base_index_js__WEBPACK_IMPORTED_MODULE_1__/* .base64 */ .US.decode, binaryToBase64 = _static_dependencies_scure_base_index_js__WEBPACK_IMPORTED_MODULE_1__/* .base64 */ .US.encode, base16ToBinary = _static_dependencies_scure_base_index_js__WEBPACK_IMPORTED_MODULE_1__/* .base16 */ .YU.decode, binaryToBase16 = _static_dependencies_scure_base_index_js__WEBPACK_IMPORTED_MODULE_1__/* .base16 */ .YU.encode, base58ToBinary = _static_dependencies_scure_base_index_js__WEBPACK_IMPORTED_MODULE_1__/* .base58 */ .Jq.decode, binaryToBase58 = _static_dependencies_scure_base_index_js__WEBPACK_IMPORTED_MODULE_1__/* .base58 */ .Jq.encode, binaryConcat = _static_dependencies_noble_curves_abstract_utils_js__WEBPACK_IMPORTED_MODULE_2__/* .concatBytes */ .eV, binaryConcatArray = (arr) => (0,_static_dependencies_noble_curves_abstract_utils_js__WEBPACK_IMPORTED_MODULE_2__/* .concatBytes */ .eV)(...arr), urlencode = object => _static_dependencies_qs_index_cjs__WEBPACK_IMPORTED_MODULE_0___default().stringify(object), urlencodeNested = object => _static_dependencies_qs_index_cjs__WEBPACK_IMPORTED_MODULE_0___default().stringify(object) // implemented only in python
13993
- , urlencodeWithArrayRepeat = object => _static_dependencies_qs_index_cjs__WEBPACK_IMPORTED_MODULE_0___default().stringify(object, { arrayFormat: 'repeat' }), rawencode = object => _static_dependencies_qs_index_cjs__WEBPACK_IMPORTED_MODULE_0___default().stringify(object, { encode: false }), encode = _static_dependencies_scure_base_index_js__WEBPACK_IMPORTED_MODULE_1__/* .utf8 */ .KA.decode // lol
14033
+ ((object[0] === '{') || (object[0] === '['))), binaryToString = _static_dependencies_scure_base_index_js__WEBPACK_IMPORTED_MODULE_1__/* .utf8 */ .KA.encode, stringToBinary = _static_dependencies_scure_base_index_js__WEBPACK_IMPORTED_MODULE_1__/* .utf8 */ .KA.decode, stringToBase64 = (string) => _static_dependencies_scure_base_index_js__WEBPACK_IMPORTED_MODULE_1__/* .base64 */ .US.encode(_static_dependencies_scure_base_index_js__WEBPACK_IMPORTED_MODULE_1__/* .utf8 */ .KA.decode(string)), base64ToString = (string) => _static_dependencies_scure_base_index_js__WEBPACK_IMPORTED_MODULE_1__/* .utf8 */ .KA.encode(_static_dependencies_scure_base_index_js__WEBPACK_IMPORTED_MODULE_1__/* .base64 */ .US.decode(string)), base64ToBinary = _static_dependencies_scure_base_index_js__WEBPACK_IMPORTED_MODULE_1__/* .base64 */ .US.decode, binaryToBase64 = _static_dependencies_scure_base_index_js__WEBPACK_IMPORTED_MODULE_1__/* .base64 */ .US.encode, base16ToBinary = _static_dependencies_scure_base_index_js__WEBPACK_IMPORTED_MODULE_1__/* .base16 */ .YU.decode, binaryToBase16 = _static_dependencies_scure_base_index_js__WEBPACK_IMPORTED_MODULE_1__/* .base16 */ .YU.encode, base58ToBinary = _static_dependencies_scure_base_index_js__WEBPACK_IMPORTED_MODULE_1__/* .base58 */ .Jq.decode, binaryToBase58 = _static_dependencies_scure_base_index_js__WEBPACK_IMPORTED_MODULE_1__/* .base58 */ .Jq.encode, binaryConcat = _static_dependencies_noble_curves_abstract_utils_js__WEBPACK_IMPORTED_MODULE_2__/* .concatBytes */ .eV, binaryConcatArray = (arr) => (0,_static_dependencies_noble_curves_abstract_utils_js__WEBPACK_IMPORTED_MODULE_2__/* .concatBytes */ .eV)(...arr), urlencode = (object) => _static_dependencies_qs_index_cjs__WEBPACK_IMPORTED_MODULE_0___default().stringify(object), urlencodeNested = (object) => _static_dependencies_qs_index_cjs__WEBPACK_IMPORTED_MODULE_0___default().stringify(object) // implemented only in python
14034
+ , urlencodeWithArrayRepeat = (object) => _static_dependencies_qs_index_cjs__WEBPACK_IMPORTED_MODULE_0___default().stringify(object, { arrayFormat: 'repeat' }), rawencode = (object) => _static_dependencies_qs_index_cjs__WEBPACK_IMPORTED_MODULE_0___default().stringify(object, { encode: false }), encode = _static_dependencies_scure_base_index_js__WEBPACK_IMPORTED_MODULE_1__/* .utf8 */ .KA.decode // lol
13994
14035
  , decode = _static_dependencies_scure_base_index_js__WEBPACK_IMPORTED_MODULE_1__/* .utf8 */ .KA.encode
13995
14036
  // Url-safe-base64 without equals signs, with + replaced by - and slashes replaced by underscores
13996
- , urlencodeBase64 = base64string => base64string.replace(/[=]+$/, '')
14037
+ , urlencodeBase64 = (base64string) => base64string.replace(/[=]+$/, '')
13997
14038
  .replace(/\+/g, '-')
13998
14039
  .replace(/\//g, '_'), numberToLE = (n, padding) => (0,_static_dependencies_noble_curves_abstract_utils_js__WEBPACK_IMPORTED_MODULE_2__/* .numberToBytesLE */ .S5)(BigInt(n), padding), numberToBE = (n, padding) => (0,_static_dependencies_noble_curves_abstract_utils_js__WEBPACK_IMPORTED_MODULE_2__/* .numberToBytesBE */ .tL)(BigInt(n), padding);
13999
14040
  function packb(req) {
@@ -18718,6 +18759,8 @@ class binance extends _abstract_binance_js__WEBPACK_IMPORTED_MODULE_0__/* ["defa
18718
18759
  'fetchCanceledOrders': 'emulated',
18719
18760
  'fetchClosedOrder': false,
18720
18761
  'fetchClosedOrders': 'emulated',
18762
+ 'fetchConvertCurrencies': true,
18763
+ 'fetchConvertQuote': false,
18721
18764
  'fetchCrossBorrowRate': true,
18722
18765
  'fetchCrossBorrowRates': false,
18723
18766
  'fetchCurrencies': true,
@@ -19617,6 +19660,7 @@ class binance extends _abstract_binance_js__WEBPACK_IMPORTED_MODULE_0__/* ["defa
19617
19660
  },
19618
19661
  'post': {
19619
19662
  'order/oco': 0.2,
19663
+ 'orderList/oco': 0.2,
19620
19664
  'sor/order': 0.2,
19621
19665
  'sor/order/test': 0.2,
19622
19666
  'order': 0.2,
@@ -22884,11 +22928,14 @@ class binance extends _abstract_binance_js__WEBPACK_IMPORTED_MODULE_0__/* ["defa
22884
22928
  'interval': this.safeString(this.timeframes, timeframe, timeframe),
22885
22929
  'limit': limit,
22886
22930
  };
22931
+ const marketId = market['id'];
22887
22932
  if (price === 'index') {
22888
- request['pair'] = market['id']; // Index price takes this argument instead of symbol
22933
+ const parts = marketId.split('_');
22934
+ const pair = this.safeString(parts, 0);
22935
+ request['pair'] = pair; // Index price takes this argument instead of symbol
22889
22936
  }
22890
22937
  else {
22891
- request['symbol'] = market['id'];
22938
+ request['symbol'] = marketId;
22892
22939
  }
22893
22940
  // const duration = this.parseTimeframe (timeframe);
22894
22941
  if (since !== undefined) {
@@ -31233,6 +31280,61 @@ class binance extends _abstract_binance_js__WEBPACK_IMPORTED_MODULE_0__/* ["defa
31233
31280
  const modifications = this.parseMarginModifications(response);
31234
31281
  return this.filterBySymbolSinceLimit(modifications, symbol, since, limit);
31235
31282
  }
31283
+ async fetchConvertCurrencies(params = {}) {
31284
+ /**
31285
+ * @method
31286
+ * @name binance#fetchConvertCurrencies
31287
+ * @description fetches all available currencies that can be converted
31288
+ * @see https://binance-docs.github.io/apidocs/spot/en/#query-order-quantity-precision-per-asset-user_data
31289
+ * @param {object} [params] extra parameters specific to the exchange API endpoint
31290
+ * @returns {object} an associative dictionary of currencies
31291
+ */
31292
+ await this.loadMarkets();
31293
+ const response = await this.sapiGetConvertAssetInfo(params);
31294
+ //
31295
+ // [
31296
+ // {
31297
+ // "asset": "BTC",
31298
+ // "fraction": 8
31299
+ // },
31300
+ // ]
31301
+ //
31302
+ const result = {};
31303
+ for (let i = 0; i < response.length; i++) {
31304
+ const entry = response[i];
31305
+ const id = this.safeString(entry, 'asset');
31306
+ const code = this.safeCurrencyCode(id);
31307
+ result[code] = {
31308
+ 'info': entry,
31309
+ 'id': id,
31310
+ 'code': code,
31311
+ 'networks': undefined,
31312
+ 'type': undefined,
31313
+ 'name': undefined,
31314
+ 'active': undefined,
31315
+ 'deposit': undefined,
31316
+ 'withdraw': undefined,
31317
+ 'fee': undefined,
31318
+ 'precision': this.safeInteger(entry, 'fraction'),
31319
+ 'limits': {
31320
+ 'amount': {
31321
+ 'min': undefined,
31322
+ 'max': undefined,
31323
+ },
31324
+ 'withdraw': {
31325
+ 'min': undefined,
31326
+ 'max': undefined,
31327
+ },
31328
+ 'deposit': {
31329
+ 'min': undefined,
31330
+ 'max': undefined,
31331
+ },
31332
+ },
31333
+ 'created': undefined,
31334
+ };
31335
+ }
31336
+ return result;
31337
+ }
31236
31338
  }
31237
31339
 
31238
31340
 
@@ -45875,6 +45977,8 @@ class bitget extends _abstract_bitget_js__WEBPACK_IMPORTED_MODULE_0__/* ["defaul
45875
45977
  'fetchCanceledAndClosedOrders': true,
45876
45978
  'fetchCanceledOrders': true,
45877
45979
  'fetchClosedOrders': true,
45980
+ 'fetchConvertCurrencies': true,
45981
+ 'fetchConvertQuote': true,
45878
45982
  'fetchCrossBorrowRate': true,
45879
45983
  'fetchCrossBorrowRates': false,
45880
45984
  'fetchCurrencies': true,
@@ -54254,6 +54358,143 @@ class bitget extends _abstract_bitget_js__WEBPACK_IMPORTED_MODULE_0__/* ["defaul
54254
54358
  'marginMode': marginType,
54255
54359
  };
54256
54360
  }
54361
+ async fetchConvertQuote(fromCode, toCode, amount = undefined, params = {}) {
54362
+ /**
54363
+ * @method
54364
+ * @name bitget#fetchConvertQuote
54365
+ * @description fetch a quote for converting from one currency to another
54366
+ * @see https://www.bitget.com/api-doc/common/convert/Get-Quoted-Price
54367
+ * @param {string} fromCode the currency that you want to sell and convert from
54368
+ * @param {string} toCode the currency that you want to buy and convert into
54369
+ * @param {float} [amount] how much you want to trade in units of the from currency
54370
+ * @param {object} [params] extra parameters specific to the exchange API endpoint
54371
+ * @returns {object} a [conversion structure]{@link https://docs.ccxt.com/#/?id=conversion-structure}
54372
+ */
54373
+ await this.loadMarkets();
54374
+ const request = {
54375
+ 'fromCoin': fromCode.toUpperCase(),
54376
+ 'toCoin': toCode.toUpperCase(),
54377
+ 'fromCoinSize': this.numberToString(amount),
54378
+ };
54379
+ const response = await this.privateConvertGetV2ConvertQuotedPrice(this.extend(request, params));
54380
+ //
54381
+ // {
54382
+ // "code": "00000",
54383
+ // "msg": "success",
54384
+ // "requestTime": 1712121940158,
54385
+ // "data": {
54386
+ // "fromCoin": "USDT",
54387
+ // "fromCoinSize": "5",
54388
+ // "cnvtPrice": "0.9993007892377704",
54389
+ // "toCoin": "USDC",
54390
+ // "toCoinSize": "4.99650394",
54391
+ // "traceId": "1159288930228187140",
54392
+ // "fee": "0"
54393
+ // }
54394
+ // }
54395
+ //
54396
+ const data = this.safeDict(response, 'data', {});
54397
+ const fromCurrencyId = this.safeString(data, 'fromCoin', fromCode);
54398
+ const fromCurrency = this.currency(fromCurrencyId);
54399
+ const toCurrencyId = this.safeString(data, 'toCoin', toCode);
54400
+ const toCurrency = this.currency(toCurrencyId);
54401
+ return this.parseConversion(data, fromCurrency, toCurrency);
54402
+ }
54403
+ parseConversion(conversion, fromCurrency = undefined, toCurrency = undefined) {
54404
+ //
54405
+ // fetchConvertQuote
54406
+ //
54407
+ // {
54408
+ // "fromCoin": "USDT",
54409
+ // "fromCoinSize": "5",
54410
+ // "cnvtPrice": "0.9993007892377704",
54411
+ // "toCoin": "USDC",
54412
+ // "toCoinSize": "4.99650394",
54413
+ // "traceId": "1159288930228187140",
54414
+ // "fee": "0"
54415
+ // }
54416
+ //
54417
+ const timestamp = this.safeInteger(conversion, 'ts');
54418
+ const fromCoin = this.safeString(conversion, 'fromCoin');
54419
+ const fromCode = this.safeCurrencyCode(fromCoin, fromCurrency);
54420
+ const to = this.safeString(conversion, 'toCoin');
54421
+ const toCode = this.safeCurrencyCode(to, toCurrency);
54422
+ return {
54423
+ 'info': conversion,
54424
+ 'timestamp': timestamp,
54425
+ 'datetime': this.iso8601(timestamp),
54426
+ 'id': this.safeString(conversion, 'traceId'),
54427
+ 'fromCurrency': fromCode,
54428
+ 'fromAmount': this.safeNumber(conversion, 'fromCoinSize'),
54429
+ 'toCurrency': toCode,
54430
+ 'toAmount': this.safeNumber(conversion, 'toCoinSize'),
54431
+ 'price': this.safeNumber(conversion, 'cnvtPrice'),
54432
+ 'fee': this.safeNumber(conversion, 'fee'),
54433
+ };
54434
+ }
54435
+ async fetchConvertCurrencies(params = {}) {
54436
+ /**
54437
+ * @method
54438
+ * @name bitget#fetchConvertCurrencies
54439
+ * @description fetches all available currencies that can be converted
54440
+ * @see https://www.bitget.com/api-doc/common/convert/Get-Convert-Currencies
54441
+ * @param {object} [params] extra parameters specific to the exchange API endpoint
54442
+ * @returns {object} an associative dictionary of currencies
54443
+ */
54444
+ await this.loadMarkets();
54445
+ const response = await this.privateConvertGetV2ConvertCurrencies(params);
54446
+ //
54447
+ // {
54448
+ // "code": "00000",
54449
+ // "msg": "success",
54450
+ // "requestTime": 1712121755897,
54451
+ // "data": [
54452
+ // {
54453
+ // "coin": "BTC",
54454
+ // "available": "0.00009850",
54455
+ // "maxAmount": "0.756266",
54456
+ // "minAmount": "0.00001"
54457
+ // },
54458
+ // ]
54459
+ // }
54460
+ //
54461
+ const result = {};
54462
+ const data = this.safeList(response, 'data', []);
54463
+ for (let i = 0; i < data.length; i++) {
54464
+ const entry = data[i];
54465
+ const id = this.safeString(entry, 'coin');
54466
+ const code = this.safeCurrencyCode(id);
54467
+ result[code] = {
54468
+ 'info': entry,
54469
+ 'id': id,
54470
+ 'code': code,
54471
+ 'networks': undefined,
54472
+ 'type': undefined,
54473
+ 'name': undefined,
54474
+ 'active': undefined,
54475
+ 'deposit': undefined,
54476
+ 'withdraw': this.safeNumber(entry, 'available'),
54477
+ 'fee': undefined,
54478
+ 'precision': undefined,
54479
+ 'limits': {
54480
+ 'amount': {
54481
+ 'min': this.safeNumber(entry, 'minAmount'),
54482
+ 'max': this.safeNumber(entry, 'maxAmount'),
54483
+ },
54484
+ 'withdraw': {
54485
+ 'min': undefined,
54486
+ 'max': undefined,
54487
+ },
54488
+ 'deposit': {
54489
+ 'min': undefined,
54490
+ 'max': undefined,
54491
+ },
54492
+ },
54493
+ 'created': undefined,
54494
+ };
54495
+ }
54496
+ return result;
54497
+ }
54257
54498
  handleErrors(code, reason, url, method, headers, body, response, requestHeaders, requestBody) {
54258
54499
  if (!response) {
54259
54500
  return undefined; // fallback to default error handler
@@ -107258,36 +107499,6 @@ class coinex extends _abstract_coinex_js__WEBPACK_IMPORTED_MODULE_0__/* ["defaul
107258
107499
  const data = this.safeValue(response, 'data', {});
107259
107500
  return this.parseLeverageTiers(data, symbols, undefined);
107260
107501
  }
107261
- parseLeverageTiers(response, symbols = undefined, marketIdKey = undefined) {
107262
- //
107263
- // {
107264
- // "BTCUSD": [
107265
- // ["500001", "100", "0.005"],
107266
- // ["1000001", "50", "0.01"],
107267
- // ["2000001", "30", "0.015"],
107268
- // ["5000001", "20", "0.02"],
107269
- // ["10000001", "15", "0.025"],
107270
- // ["20000001", "10", "0.03"]
107271
- // ],
107272
- // ...
107273
- // }
107274
- //
107275
- const tiers = {};
107276
- const marketIds = Object.keys(response);
107277
- for (let i = 0; i < marketIds.length; i++) {
107278
- const marketId = marketIds[i];
107279
- const market = this.safeMarket(marketId, undefined, undefined, 'spot');
107280
- const symbol = this.safeString(market, 'symbol');
107281
- let symbolsLength = 0;
107282
- if (symbols !== undefined) {
107283
- symbolsLength = symbols.length;
107284
- }
107285
- if (symbol !== undefined && (symbolsLength === 0 || this.inArray(symbols, symbol))) {
107286
- tiers[symbol] = this.parseMarketLeverageTiers(response[marketId], market);
107287
- }
107288
- }
107289
- return tiers;
107290
- }
107291
107502
  parseMarketLeverageTiers(item, market = undefined) {
107292
107503
  const tiers = [];
107293
107504
  let minNotional = 0;
@@ -134193,55 +134404,7 @@ class digifinex extends _abstract_digifinex_js__WEBPACK_IMPORTED_MODULE_0__/* ["
134193
134404
  //
134194
134405
  const data = this.safeValue(response, 'data', []);
134195
134406
  symbols = this.marketSymbols(symbols);
134196
- return this.parseLeverageTiers(data, symbols, 'symbol');
134197
- }
134198
- parseLeverageTiers(response, symbols = undefined, marketIdKey = undefined) {
134199
- //
134200
- // [
134201
- // {
134202
- // "instrument_id": "BTCUSDTPERP",
134203
- // "type": "REAL",
134204
- // "contract_type": "PERPETUAL",
134205
- // "base_currency": "BTC",
134206
- // "quote_currency": "USDT",
134207
- // "clear_currency": "USDT",
134208
- // "contract_value": "0.001",
134209
- // "contract_value_currency": "BTC",
134210
- // "is_inverse": false,
134211
- // "is_trading": true,
134212
- // "status": "ONLINE",
134213
- // "price_precision": 1,
134214
- // "tick_size": "0.1",
134215
- // "min_order_amount": 1,
134216
- // "open_max_limits": [
134217
- // {
134218
- // "leverage": "50",
134219
- // "max_limit": "1000000"
134220
- // }
134221
- // ]
134222
- // },
134223
- // ]
134224
- //
134225
- const tiers = {};
134226
- const result = {};
134227
- for (let i = 0; i < response.length; i++) {
134228
- const entry = response[i];
134229
- const marketId = this.safeString(entry, 'instrument_id');
134230
- const market = this.safeMarket(marketId);
134231
- const symbol = this.safeSymbol(marketId, market);
134232
- let symbolsLength = 0;
134233
- tiers[symbol] = this.parseMarketLeverageTiers(response[i], market);
134234
- if (symbols !== undefined) {
134235
- symbolsLength = symbols.length;
134236
- if (this.inArray(symbol, symbols)) {
134237
- result[symbol] = this.parseMarketLeverageTiers(response[i], market);
134238
- }
134239
- }
134240
- if (symbol !== undefined && (symbolsLength === 0 || this.inArray(symbols, symbol))) {
134241
- result[symbol] = this.parseMarketLeverageTiers(response[i], market);
134242
- }
134243
- }
134244
- return result;
134407
+ return this.parseLeverageTiers(data, symbols, 'instrument_id');
134245
134408
  }
134246
134409
  async fetchMarketLeverageTiers(symbol, params = {}) {
134247
134410
  /**
@@ -207031,6 +207194,8 @@ class okx extends _abstract_okx_js__WEBPACK_IMPORTED_MODULE_0__/* ["default"] */
207031
207194
  'fetchCanceledOrders': true,
207032
207195
  'fetchClosedOrder': undefined,
207033
207196
  'fetchClosedOrders': true,
207197
+ 'fetchConvertCurrencies': true,
207198
+ 'fetchConvertQuote': true,
207034
207199
  'fetchCrossBorrowRate': true,
207035
207200
  'fetchCrossBorrowRates': true,
207036
207201
  'fetchCurrencies': true,
@@ -214575,6 +214740,157 @@ class okx extends _abstract_okx_js__WEBPACK_IMPORTED_MODULE_0__/* ["default"] */
214575
214740
  'quoteVolume': undefined,
214576
214741
  };
214577
214742
  }
214743
+ async fetchConvertQuote(fromCode, toCode, amount = undefined, params = {}) {
214744
+ /**
214745
+ * @method
214746
+ * @name okx#fetchConvertQuote
214747
+ * @description fetch a quote for converting from one currency to another
214748
+ * @see https://www.okx.com/docs-v5/en/#funding-account-rest-api-estimate-quote
214749
+ * @param {string} fromCode the currency that you want to sell and convert from
214750
+ * @param {string} toCode the currency that you want to buy and convert into
214751
+ * @param {float} [amount] how much you want to trade in units of the from currency
214752
+ * @param {object} [params] extra parameters specific to the exchange API endpoint
214753
+ * @returns {object} a [conversion structure]{@link https://docs.ccxt.com/#/?id=conversion-structure}
214754
+ */
214755
+ await this.loadMarkets();
214756
+ const request = {
214757
+ 'baseCcy': fromCode.toUpperCase(),
214758
+ 'quoteCcy': toCode.toUpperCase(),
214759
+ 'rfqSzCcy': fromCode.toUpperCase(),
214760
+ 'rfqSz': this.numberToString(amount),
214761
+ 'side': 'sell',
214762
+ };
214763
+ const response = await this.privatePostAssetConvertEstimateQuote(this.extend(request, params));
214764
+ //
214765
+ // {
214766
+ // "code": "0",
214767
+ // "data": [
214768
+ // {
214769
+ // "baseCcy": "ETH",
214770
+ // "baseSz": "0.01023052",
214771
+ // "clQReqId": "",
214772
+ // "cnvtPx": "2932.40104429",
214773
+ // "origRfqSz": "30",
214774
+ // "quoteCcy": "USDT",
214775
+ // "quoteId": "quoterETH-USDT16461885104612381",
214776
+ // "quoteSz": "30",
214777
+ // "quoteTime": "1646188510461",
214778
+ // "rfqSz": "30",
214779
+ // "rfqSzCcy": "USDT",
214780
+ // "side": "buy",
214781
+ // "ttlMs": "10000"
214782
+ // }
214783
+ // ],
214784
+ // "msg": ""
214785
+ // }
214786
+ //
214787
+ const data = this.safeList(response, 'data', []);
214788
+ const result = this.safeDict(data, 0, {});
214789
+ const fromCurrencyId = this.safeString(result, 'baseCcy', fromCode);
214790
+ const fromCurrency = this.currency(fromCurrencyId);
214791
+ const toCurrencyId = this.safeString(result, 'quoteCcy', toCode);
214792
+ const toCurrency = this.currency(toCurrencyId);
214793
+ return this.parseConversion(result, fromCurrency, toCurrency);
214794
+ }
214795
+ parseConversion(conversion, fromCurrency = undefined, toCurrency = undefined) {
214796
+ //
214797
+ // fetchConvertQuote
214798
+ //
214799
+ // {
214800
+ // "baseCcy": "ETH",
214801
+ // "baseSz": "0.01023052",
214802
+ // "clQReqId": "",
214803
+ // "cnvtPx": "2932.40104429",
214804
+ // "origRfqSz": "30",
214805
+ // "quoteCcy": "USDT",
214806
+ // "quoteId": "quoterETH-USDT16461885104612381",
214807
+ // "quoteSz": "30",
214808
+ // "quoteTime": "1646188510461",
214809
+ // "rfqSz": "30",
214810
+ // "rfqSzCcy": "USDT",
214811
+ // "side": "buy",
214812
+ // "ttlMs": "10000"
214813
+ // }
214814
+ //
214815
+ const timestamp = this.safeInteger(conversion, 'quoteTime');
214816
+ const fromCoin = this.safeString(conversion, 'baseCcy');
214817
+ const fromCode = this.safeCurrencyCode(fromCoin, fromCurrency);
214818
+ const to = this.safeString(conversion, 'quoteCcy');
214819
+ const toCode = this.safeCurrencyCode(to, toCurrency);
214820
+ return {
214821
+ 'info': conversion,
214822
+ 'timestamp': timestamp,
214823
+ 'datetime': this.iso8601(timestamp),
214824
+ 'id': this.safeString(conversion, 'clQReqId'),
214825
+ 'fromCurrency': fromCode,
214826
+ 'fromAmount': this.safeNumber(conversion, 'baseSz'),
214827
+ 'toCurrency': toCode,
214828
+ 'toAmount': this.safeNumber(conversion, 'quoteSz'),
214829
+ 'price': this.safeNumber(conversion, 'cnvtPx'),
214830
+ 'fee': undefined,
214831
+ };
214832
+ }
214833
+ async fetchConvertCurrencies(params = {}) {
214834
+ /**
214835
+ * @method
214836
+ * @name okx#fetchConvertCurrencies
214837
+ * @description fetches all available currencies that can be converted
214838
+ * @see https://www.okx.com/docs-v5/en/#funding-account-rest-api-get-convert-currencies
214839
+ * @param {object} [params] extra parameters specific to the exchange API endpoint
214840
+ * @returns {object} an associative dictionary of currencies
214841
+ */
214842
+ await this.loadMarkets();
214843
+ const response = await this.privateGetAssetConvertCurrencies(params);
214844
+ //
214845
+ // {
214846
+ // "code": "0",
214847
+ // "data": [
214848
+ // {
214849
+ // "ccy": "BTC",
214850
+ // "max": "",
214851
+ // "min": ""
214852
+ // },
214853
+ // ],
214854
+ // "msg": ""
214855
+ // }
214856
+ //
214857
+ const result = {};
214858
+ const data = this.safeList(response, 'data', []);
214859
+ for (let i = 0; i < data.length; i++) {
214860
+ const entry = data[i];
214861
+ const id = this.safeString(entry, 'ccy');
214862
+ const code = this.safeCurrencyCode(id);
214863
+ result[code] = {
214864
+ 'info': entry,
214865
+ 'id': id,
214866
+ 'code': code,
214867
+ 'networks': undefined,
214868
+ 'type': undefined,
214869
+ 'name': undefined,
214870
+ 'active': undefined,
214871
+ 'deposit': undefined,
214872
+ 'withdraw': undefined,
214873
+ 'fee': undefined,
214874
+ 'precision': undefined,
214875
+ 'limits': {
214876
+ 'amount': {
214877
+ 'min': this.safeNumber(entry, 'min'),
214878
+ 'max': this.safeNumber(entry, 'max'),
214879
+ },
214880
+ 'withdraw': {
214881
+ 'min': undefined,
214882
+ 'max': undefined,
214883
+ },
214884
+ 'deposit': {
214885
+ 'min': undefined,
214886
+ 'max': undefined,
214887
+ },
214888
+ },
214889
+ 'created': undefined,
214890
+ };
214891
+ }
214892
+ return result;
214893
+ }
214578
214894
  handleErrors(httpCode, reason, url, method, headers, body, response, requestHeaders, requestBody) {
214579
214895
  if (!response) {
214580
214896
  return undefined; // fallback to default error handler
@@ -264078,10 +264394,12 @@ class kraken extends _kraken_js__WEBPACK_IMPORTED_MODULE_0__/* ["default"] */ .Z
264078
264394
  'watchMyTrades': true,
264079
264395
  'watchOHLCV': true,
264080
264396
  'watchOrderBook': true,
264397
+ 'watchOrderBookForSymbols': true,
264081
264398
  'watchOrders': true,
264082
264399
  'watchTicker': true,
264083
- 'watchTickers': false,
264400
+ 'watchTickers': true,
264084
264401
  'watchTrades': true,
264402
+ 'watchTradesForSymbols': true,
264085
264403
  'createOrderWs': true,
264086
264404
  'editOrderWs': true,
264087
264405
  'cancelOrderWs': true,
@@ -264372,10 +264690,9 @@ class kraken extends _kraken_js__WEBPACK_IMPORTED_MODULE_0__/* ["default"] */ .Z
264372
264690
  // ]
264373
264691
  //
264374
264692
  const wsName = message[3];
264375
- const name = 'ticker';
264376
- const messageHash = name + ':' + wsName;
264377
264693
  const market = this.safeValue(this.options['marketsByWsName'], wsName);
264378
264694
  const symbol = market['symbol'];
264695
+ const messageHash = this.getMessageHash('ticker', undefined, symbol);
264379
264696
  const ticker = message[1];
264380
264697
  const vwap = this.safeString(ticker['p'], 0);
264381
264698
  let quoteVolume = undefined;
@@ -264406,9 +264723,6 @@ class kraken extends _kraken_js__WEBPACK_IMPORTED_MODULE_0__/* ["default"] */ .Z
264406
264723
  'quoteVolume': quoteVolume,
264407
264724
  'info': ticker,
264408
264725
  });
264409
- // todo add support for multiple tickers (may be tricky)
264410
- // kraken confirms multi-pair subscriptions separately one by one
264411
- // trigger correct watchTickers calls upon receiving any of symbols
264412
264726
  this.tickers[symbol] = result;
264413
264727
  client.resolve(result, messageHash);
264414
264728
  }
@@ -264426,9 +264740,9 @@ class kraken extends _kraken_js__WEBPACK_IMPORTED_MODULE_0__/* ["default"] */ .Z
264426
264740
  //
264427
264741
  const wsName = this.safeString(message, 3);
264428
264742
  const name = this.safeString(message, 2);
264429
- const messageHash = name + ':' + wsName;
264430
264743
  const market = this.safeValue(this.options['marketsByWsName'], wsName);
264431
264744
  const symbol = market['symbol'];
264745
+ const messageHash = this.getMessageHash(name, undefined, symbol);
264432
264746
  let stored = this.safeValue(this.trades, symbol);
264433
264747
  if (stored === undefined) {
264434
264748
  const limit = this.safeInteger(this.options, 'tradesLimit', 1000);
@@ -264529,25 +264843,61 @@ class kraken extends _kraken_js__WEBPACK_IMPORTED_MODULE_0__/* ["default"] */ .Z
264529
264843
  * @param {object} [params] extra parameters specific to the exchange API endpoint
264530
264844
  * @returns {object} a [ticker structure]{@link https://docs.ccxt.com/#/?id=ticker-structure}
264531
264845
  */
264532
- return await this.watchPublic('ticker', symbol, params);
264846
+ await this.loadMarkets();
264847
+ symbol = this.symbol(symbol);
264848
+ const tickers = await this.watchTickers([symbol], params);
264849
+ return tickers[symbol];
264850
+ }
264851
+ async watchTickers(symbols = undefined, params = {}) {
264852
+ /**
264853
+ * @method
264854
+ * @name kraken#watchTickers
264855
+ * @description watches a price ticker, a statistical calculation with the information calculated over the past 24 hours for a specific market
264856
+ * @param {string} symbol unified symbol of the market to fetch the ticker for
264857
+ * @param {object} [params] extra parameters specific to the exchange API endpoint
264858
+ * @returns {object} a [ticker structure]{@link https://docs.ccxt.com/#/?id=ticker-structure}
264859
+ */
264860
+ await this.loadMarkets();
264861
+ symbols = this.marketSymbols(symbols, undefined, false);
264862
+ const ticker = await this.watchMultiHelper('ticker', 'ticker', symbols, undefined, params);
264863
+ if (this.newUpdates) {
264864
+ const result = {};
264865
+ result[ticker['symbol']] = ticker;
264866
+ return result;
264867
+ }
264868
+ return this.filterByArray(this.tickers, 'symbol', symbols);
264533
264869
  }
264534
264870
  async watchTrades(symbol, since = undefined, limit = undefined, params = {}) {
264535
264871
  /**
264536
264872
  * @method
264537
264873
  * @name kraken#watchTrades
264538
264874
  * @description get the list of most recent trades for a particular symbol
264875
+ * @see https://docs.kraken.com/websockets/#message-trade
264539
264876
  * @param {string} symbol unified symbol of the market to fetch trades for
264540
264877
  * @param {int} [since] timestamp in ms of the earliest trade to fetch
264541
264878
  * @param {int} [limit] the maximum amount of trades to fetch
264542
264879
  * @param {object} [params] extra parameters specific to the exchange API endpoint
264543
264880
  * @returns {object[]} a list of [trade structures]{@link https://docs.ccxt.com/#/?id=public-trades}
264544
264881
  */
264545
- await this.loadMarkets();
264546
- symbol = this.symbol(symbol);
264547
- const name = 'trade';
264548
- const trades = await this.watchPublic(name, symbol, params);
264882
+ return await this.watchTradesForSymbols([symbol], since, limit, params);
264883
+ }
264884
+ async watchTradesForSymbols(symbols, since = undefined, limit = undefined, params = {}) {
264885
+ /**
264886
+ * @method
264887
+ * @name kraken#watchTradesForSymbols
264888
+ * @see https://docs.kraken.com/websockets/#message-trade
264889
+ * @description get the list of most recent trades for a list of symbols
264890
+ * @param {string[]} symbols unified symbol of the market to fetch trades for
264891
+ * @param {int} [since] timestamp in ms of the earliest trade to fetch
264892
+ * @param {int} [limit] the maximum amount of trades to fetch
264893
+ * @param {object} [params] extra parameters specific to the exchange API endpoint
264894
+ * @returns {object[]} a list of [trade structures]{@link https://docs.ccxt.com/#/?id=public-trades}
264895
+ */
264896
+ const trades = await this.watchMultiHelper('trade', 'trade', symbols, undefined, params);
264549
264897
  if (this.newUpdates) {
264550
- limit = trades.getLimit(symbol, limit);
264898
+ const first = this.safeList(trades, 0);
264899
+ const tradeSymbol = this.safeString(first, 'symbol');
264900
+ limit = trades.getLimit(tradeSymbol, limit);
264551
264901
  }
264552
264902
  return this.filterBySinceLimit(trades, since, limit, 'timestamp', true);
264553
264903
  }
@@ -264556,15 +264906,28 @@ class kraken extends _kraken_js__WEBPACK_IMPORTED_MODULE_0__/* ["default"] */ .Z
264556
264906
  * @method
264557
264907
  * @name kraken#watchOrderBook
264558
264908
  * @description watches information on open orders with bid (buy) and ask (sell) prices, volumes and other data
264909
+ * @see https://docs.kraken.com/websockets/#message-book
264559
264910
  * @param {string} symbol unified symbol of the market to fetch the order book for
264560
264911
  * @param {int} [limit] the maximum amount of order book entries to return
264561
264912
  * @param {object} [params] extra parameters specific to the exchange API endpoint
264562
264913
  * @returns {object} A dictionary of [order book structures]{@link https://docs.ccxt.com/#/?id=order-book-structure} indexed by market symbols
264563
264914
  */
264564
- const name = 'book';
264915
+ return await this.watchOrderBookForSymbols([symbol], limit, params);
264916
+ }
264917
+ async watchOrderBookForSymbols(symbols, limit = undefined, params = {}) {
264918
+ /**
264919
+ * @method
264920
+ * @name kraken#watchOrderBookForSymbols
264921
+ * @description watches information on open orders with bid (buy) and ask (sell) prices, volumes and other data
264922
+ * @see https://docs.kraken.com/websockets/#message-book
264923
+ * @param {string[]} symbols unified array of symbols
264924
+ * @param {int} [limit] the maximum amount of order book entries to return
264925
+ * @param {object} [params] extra parameters specific to the exchange API endpoint
264926
+ * @returns {object} A dictionary of [order book structures]{@link https://docs.ccxt.com/#/?id=order-book-structure} indexed by market symbols
264927
+ */
264565
264928
  const request = {};
264566
264929
  if (limit !== undefined) {
264567
- if ((limit === 10) || (limit === 25) || (limit === 100) || (limit === 500) || (limit === 1000)) {
264930
+ if (this.inArray(limit, [10, 25, 100, 500, 1000])) {
264568
264931
  request['subscription'] = {
264569
264932
  'depth': limit, // default 10, valid options 10, 25, 100, 500, 1000
264570
264933
  };
@@ -264573,7 +264936,7 @@ class kraken extends _kraken_js__WEBPACK_IMPORTED_MODULE_0__/* ["default"] */ .Z
264573
264936
  throw new _base_errors_js__WEBPACK_IMPORTED_MODULE_1__.NotSupported(this.id + ' watchOrderBook accepts limit values of 10, 25, 100, 500 and 1000 only');
264574
264937
  }
264575
264938
  }
264576
- const orderbook = await this.watchPublic(name, symbol, this.extend(request, params));
264939
+ const orderbook = await this.watchMultiHelper('orderbook', 'book', symbols, { 'limit': limit }, this.extend(request, params));
264577
264940
  return orderbook.limit();
264578
264941
  }
264579
264942
  async watchOHLCV(symbol, timeframe = '1m', since = undefined, limit = undefined, params = {}) {
@@ -264702,7 +265065,7 @@ class kraken extends _kraken_js__WEBPACK_IMPORTED_MODULE_0__/* ["default"] */ .Z
264702
265065
  const market = this.safeValue(this.options['marketsByWsName'], wsName);
264703
265066
  const symbol = market['symbol'];
264704
265067
  let timestamp = undefined;
264705
- const messageHash = 'book:' + wsName;
265068
+ const messageHash = this.getMessageHash('orderbook', undefined, symbol);
264706
265069
  // if this is a snapshot
264707
265070
  if ('as' in message[1]) {
264708
265071
  // todo get depth from marketsByWsName
@@ -264783,6 +265146,7 @@ class kraken extends _kraken_js__WEBPACK_IMPORTED_MODULE_0__/* ["default"] */ .Z
264783
265146
  if (localChecksum !== c) {
264784
265147
  const error = new _base_errors_js__WEBPACK_IMPORTED_MODULE_1__.InvalidNonce(this.id + ' invalid checksum');
264785
265148
  client.reject(error, messageHash);
265149
+ return;
264786
265150
  }
264787
265151
  }
264788
265152
  orderbook['symbol'] = symbol;
@@ -265310,6 +265674,48 @@ class kraken extends _kraken_js__WEBPACK_IMPORTED_MODULE_0__/* ["default"] */ .Z
265310
265674
  'trades': trades,
265311
265675
  });
265312
265676
  }
265677
+ async watchMultiHelper(unifiedName, channelName, symbols = undefined, subscriptionArgs = undefined, params = {}) {
265678
+ await this.loadMarkets();
265679
+ // symbols are required
265680
+ symbols = this.marketSymbols(symbols, undefined, false, true, false);
265681
+ const messageHashes = [];
265682
+ for (let i = 0; i < symbols.length; i++) {
265683
+ messageHashes.push(this.getMessageHash(unifiedName, undefined, this.symbol(symbols[i])));
265684
+ }
265685
+ // for WS subscriptions, we can't use .marketIds (symbols), instead a custom is field needed
265686
+ const markets = this.marketsForSymbols(symbols);
265687
+ const wsMarketIds = [];
265688
+ for (let i = 0; i < markets.length; i++) {
265689
+ const wsMarketId = this.safeString(markets[i]['info'], 'wsname');
265690
+ wsMarketIds.push(wsMarketId);
265691
+ }
265692
+ const request = {
265693
+ 'event': 'subscribe',
265694
+ 'reqid': this.requestId(),
265695
+ 'pair': wsMarketIds,
265696
+ 'subscription': {
265697
+ 'name': channelName,
265698
+ },
265699
+ };
265700
+ const url = this.urls['api']['ws']['public'];
265701
+ return await this.watchMultiple(url, messageHashes, this.extend(request, params), messageHashes, subscriptionArgs);
265702
+ }
265703
+ getMessageHash(unifiedElementName, subChannelName = undefined, symbol = undefined) {
265704
+ // unifiedElementName can be : orderbook, trade, ticker, bidask ...
265705
+ // subChannelName only applies to channel that needs specific variation (i.e. depth_50, depth_100..) to be selected
265706
+ const withSymbol = symbol !== undefined;
265707
+ let messageHash = unifiedElementName;
265708
+ if (!withSymbol) {
265709
+ messageHash += 's';
265710
+ }
265711
+ else {
265712
+ messageHash += '@' + symbol;
265713
+ }
265714
+ if (subChannelName !== undefined) {
265715
+ messageHash += '#' + subChannelName;
265716
+ }
265717
+ return messageHash;
265718
+ }
265313
265719
  handleSubscriptionStatus(client, message) {
265314
265720
  //
265315
265721
  // public
@@ -265456,9 +265862,12 @@ class krakenfutures extends _krakenfutures_js__WEBPACK_IMPORTED_MODULE_0__/* ["d
265456
265862
  'fetchTradesWs': false,
265457
265863
  'watchOHLCV': false,
265458
265864
  'watchOrderBook': true,
265865
+ 'watchOrderBookForSymbols': true,
265459
265866
  'watchTicker': true,
265460
265867
  'watchTickers': true,
265868
+ 'watchBidsAsks': true,
265461
265869
  'watchTrades': true,
265870
+ 'watchTradesForSymbols': true,
265462
265871
  'watchBalance': true,
265463
265872
  // 'watchStatus': true, // https://docs.futures.kraken.com/#websocket-api-public-feeds-heartbeat
265464
265873
  'watchOrders': true,
@@ -265479,12 +265888,6 @@ class krakenfutures extends _krakenfutures_js__WEBPACK_IMPORTED_MODULE_0__/* ["d
265479
265888
  'OHLCVLimit': 1000,
265480
265889
  'connectionLimit': 100,
265481
265890
  'requestLimit': 100,
265482
- 'watchTicker': {
265483
- 'method': 'ticker', // or ticker_lite
265484
- },
265485
- 'watchTickers': {
265486
- 'method': 'ticker', // or ticker_lite
265487
- },
265488
265891
  'fetchBalance': {
265489
265892
  'type': undefined,
265490
265893
  },
@@ -265522,6 +265925,20 @@ class krakenfutures extends _krakenfutures_js__WEBPACK_IMPORTED_MODULE_0__/* ["d
265522
265925
  }
265523
265926
  return future;
265524
265927
  }
265928
+ async watchOrderBookForSymbols(symbols, limit = undefined, params = {}) {
265929
+ /**
265930
+ * @method
265931
+ * @name krakenfutures#watchOrderBookForSymbols
265932
+ * @description watches information on open orders with bid (buy) and ask (sell) prices, volumes and other data
265933
+ * @see https://docs.futures.kraken.com/#websocket-api-public-feeds-challenge
265934
+ * @param {string[]} symbols unified array of symbols
265935
+ * @param {int} [limit] the maximum amount of order book entries to return
265936
+ * @param {object} [params] extra parameters specific to the exchange API endpoint
265937
+ * @returns {object} A dictionary of [order book structures]{@link https://docs.ccxt.com/#/?id=order-book-structure} indexed by market symbols
265938
+ */
265939
+ const orderbook = await this.watchMultiHelper('orderbook', 'book', symbols, { 'limit': limit }, params);
265940
+ return orderbook.limit();
265941
+ }
265525
265942
  async subscribePublic(name, symbols, params = {}) {
265526
265943
  /**
265527
265944
  * @ignore
@@ -265589,34 +266006,49 @@ class krakenfutures extends _krakenfutures_js__WEBPACK_IMPORTED_MODULE_0__/* ["d
265589
266006
  * @param {object} [params] extra parameters specific to the exchange API endpoint
265590
266007
  * @returns {object} a [ticker structure]{@link https://docs.ccxt.com/#/?id=ticker-structure}
265591
266008
  */
265592
- const options = this.safeValue(this.options, 'watchTicker');
265593
- const method = this.safeString(options, 'method', 'ticker'); // or ticker_lite
265594
- const name = this.safeString(params, 'method', method);
265595
- params = this.omit(params, ['method']);
265596
- return await this.subscribePublic(name, [symbol], params);
266009
+ await this.loadMarkets();
266010
+ symbol = this.symbol(symbol);
266011
+ const tickers = await this.watchTickers([symbol], params);
266012
+ return tickers[symbol];
265597
266013
  }
265598
266014
  async watchTickers(symbols = undefined, params = {}) {
265599
266015
  /**
265600
266016
  * @method
265601
- * @name krakenfutures#watchTicker
266017
+ * @name krakenfutures#watchTickers
265602
266018
  * @description watches a price ticker, a statistical calculation with the information calculated over the past 24 hours for a specific market
265603
- * @see https://docs.futures.kraken.com/#websocket-api-public-feeds-ticker-lite
266019
+ * @see https://docs.futures.kraken.com/#websocket-api-public-feeds-ticker
265604
266020
  * @param {string} symbol unified symbol of the market to fetch the ticker for
265605
266021
  * @param {object} [params] extra parameters specific to the exchange API endpoint
265606
266022
  * @returns {object} a [ticker structure]{@link https://docs.ccxt.com/#/?id=ticker-structure}
265607
266023
  */
265608
- const method = this.safeString(this.options, 'watchTickerMethod', 'ticker'); // or ticker_lite
265609
- const name = this.safeString2(params, 'method', 'watchTickerMethod', method);
265610
- params = this.omit(params, ['watchTickerMethod', 'method']);
266024
+ await this.loadMarkets();
265611
266025
  symbols = this.marketSymbols(symbols, undefined, false);
265612
- const ticker = await this.subscribePublic(name, symbols, params);
266026
+ const ticker = await this.watchMultiHelper('ticker', 'ticker', symbols, undefined, params);
265613
266027
  if (this.newUpdates) {
265614
- const tickers = {};
265615
- tickers[ticker['symbol']] = ticker;
265616
- return tickers;
266028
+ const result = {};
266029
+ result[ticker['symbol']] = ticker;
266030
+ return result;
265617
266031
  }
265618
266032
  return this.filterByArray(this.tickers, 'symbol', symbols);
265619
266033
  }
266034
+ async watchBidsAsks(symbols = undefined, params = {}) {
266035
+ /**
266036
+ * @method
266037
+ * @name krakenfutures#watchBidsAsks
266038
+ * @see https://docs.futures.kraken.com/#websocket-api-public-feeds-ticker-lite
266039
+ * @description watches best bid & ask for symbols
266040
+ * @param {string[]} symbols unified symbol of the market to fetch the ticker for
266041
+ * @param {object} [params] extra parameters specific to the exchange API endpoint
266042
+ * @returns {object} a [ticker structure]{@link https://docs.ccxt.com/#/?id=ticker-structure}
266043
+ */
266044
+ const ticker = await this.watchMultiHelper('bidask', 'ticker_lite', symbols, undefined, params);
266045
+ if (this.newUpdates) {
266046
+ const result = {};
266047
+ result[ticker['symbol']] = ticker;
266048
+ return result;
266049
+ }
266050
+ return this.filterByArray(this.bidsasks, 'symbol', symbols);
266051
+ }
265620
266052
  async watchTrades(symbol = undefined, since = undefined, limit = undefined, params = {}) {
265621
266053
  /**
265622
266054
  * @method
@@ -265629,11 +266061,25 @@ class krakenfutures extends _krakenfutures_js__WEBPACK_IMPORTED_MODULE_0__/* ["d
265629
266061
  * @param {object} [params] extra parameters specific to the exchange API endpoint
265630
266062
  * @returns {object[]} a list of [trade structures]{@link https://docs.ccxt.com/#/?id=public-trades}
265631
266063
  */
265632
- await this.loadMarkets();
265633
- const name = 'trade';
265634
- const trades = await this.subscribePublic(name, [symbol], params);
266064
+ return await this.watchTradesForSymbols([symbol], since, limit, params);
266065
+ }
266066
+ async watchTradesForSymbols(symbols, since = undefined, limit = undefined, params = {}) {
266067
+ /**
266068
+ * @method
266069
+ * @name krakenfutures#watchTradesForSymbols
266070
+ * @see https://docs.futures.kraken.com/#websocket-api-public-feeds-trade
266071
+ * @description get the list of most recent trades for a list of symbols
266072
+ * @param {string[]} symbols unified symbol of the market to fetch trades for
266073
+ * @param {int} [since] timestamp in ms of the earliest trade to fetch
266074
+ * @param {int} [limit] the maximum amount of trades to fetch
266075
+ * @param {object} [params] extra parameters specific to the exchange API endpoint
266076
+ * @returns {object[]} a list of [trade structures]{@link https://docs.ccxt.com/#/?id=public-trades}
266077
+ */
266078
+ const trades = await this.watchMultiHelper('trade', 'trade', symbols, undefined, params);
265635
266079
  if (this.newUpdates) {
265636
- limit = trades.getLimit(symbol, limit);
266080
+ const first = this.safeList(trades, 0);
266081
+ const tradeSymbol = this.safeString(first, 'symbol');
266082
+ limit = trades.getLimit(tradeSymbol, limit);
265637
266083
  }
265638
266084
  return this.filterBySinceLimit(trades, since, limit, 'timestamp', true);
265639
266085
  }
@@ -265648,8 +266094,7 @@ class krakenfutures extends _krakenfutures_js__WEBPACK_IMPORTED_MODULE_0__/* ["d
265648
266094
  * @param {object} [params] extra parameters specific to the exchange API endpoint
265649
266095
  * @returns {object} A dictionary of [order book structures]{@link https://docs.ccxt.com/#/?id=order-book-structure} indexed by market symbols
265650
266096
  */
265651
- const orderbook = await this.subscribePublic('book', [symbol], params);
265652
- return orderbook.limit();
266097
+ return await this.watchOrderBookForSymbols([symbol], limit, params);
265653
266098
  }
265654
266099
  async watchPositions(symbols = undefined, since = undefined, limit = undefined, params = {}) {
265655
266100
  /**
@@ -265897,7 +266342,7 @@ class krakenfutures extends _krakenfutures_js__WEBPACK_IMPORTED_MODULE_0__/* ["d
265897
266342
  if (marketId !== undefined) {
265898
266343
  const market = this.market(marketId);
265899
266344
  const symbol = market['symbol'];
265900
- const messageHash = 'trade:' + symbol;
266345
+ const messageHash = this.getMessageHash('trade', undefined, symbol);
265901
266346
  if (this.safeList(this.trades, symbol) === undefined) {
265902
266347
  const tradesLimit = this.safeInteger(this.options, 'tradesLimit', 1000);
265903
266348
  this.trades[symbol] = new _base_ws_Cache_js__WEBPACK_IMPORTED_MODULE_1__/* .ArrayCache */ .ZL(tradesLimit);
@@ -265919,7 +266364,6 @@ class krakenfutures extends _krakenfutures_js__WEBPACK_IMPORTED_MODULE_0__/* ["d
265919
266364
  }
265920
266365
  client.resolve(tradesArray, messageHash);
265921
266366
  }
265922
- return message;
265923
266367
  }
265924
266368
  parseWsTrade(trade, market = undefined) {
265925
266369
  //
@@ -266345,7 +266789,16 @@ class krakenfutures extends _krakenfutures_js__WEBPACK_IMPORTED_MODULE_0__/* ["d
266345
266789
  // "volumeQuote": 19628180
266346
266790
  // }
266347
266791
  //
266348
- // ticker_lite
266792
+ const marketId = this.safeString(message, 'product_id');
266793
+ if (marketId !== undefined) {
266794
+ const ticker = this.parseWsTicker(message);
266795
+ const symbol = ticker['symbol'];
266796
+ this.tickers[symbol] = ticker;
266797
+ const messageHash = this.getMessageHash('ticker', undefined, symbol);
266798
+ client.resolve(ticker, messageHash);
266799
+ }
266800
+ }
266801
+ handleBidAsk(client, message) {
266349
266802
  //
266350
266803
  // {
266351
266804
  // "feed": "ticker_lite",
@@ -266363,16 +266816,13 @@ class krakenfutures extends _krakenfutures_js__WEBPACK_IMPORTED_MODULE_0__/* ["d
266363
266816
  // }
266364
266817
  //
266365
266818
  const marketId = this.safeString(message, 'product_id');
266366
- const feed = this.safeString(message, 'feed');
266367
266819
  if (marketId !== undefined) {
266368
266820
  const ticker = this.parseWsTicker(message);
266369
266821
  const symbol = ticker['symbol'];
266370
- this.tickers[symbol] = ticker;
266371
- const messageHash = feed + ':' + symbol;
266822
+ this.bidsasks[symbol] = ticker;
266823
+ const messageHash = this.getMessageHash('bidask', undefined, symbol);
266372
266824
  client.resolve(ticker, messageHash);
266373
266825
  }
266374
- client.resolve(this.tickers, feed);
266375
- return message;
266376
266826
  }
266377
266827
  parseWsTicker(ticker, market = undefined) {
266378
266828
  //
@@ -266484,14 +266934,14 @@ class krakenfutures extends _krakenfutures_js__WEBPACK_IMPORTED_MODULE_0__/* ["d
266484
266934
  const marketId = this.safeString(message, 'product_id');
266485
266935
  const market = this.safeMarket(marketId);
266486
266936
  const symbol = market['symbol'];
266487
- const messageHash = 'book:' + symbol;
266488
- const subscription = this.safeValue(client.subscriptions, messageHash, {});
266937
+ const messageHash = this.getMessageHash('orderbook', undefined, symbol);
266938
+ const subscription = this.safeDict(client.subscriptions, messageHash, {});
266489
266939
  const limit = this.safeInteger(subscription, 'limit');
266490
266940
  const timestamp = this.safeInteger(message, 'timestamp');
266491
266941
  this.orderbooks[symbol] = this.orderBook({}, limit);
266492
266942
  const orderbook = this.orderbooks[symbol];
266493
- const bids = this.safeValue(message, 'bids');
266494
- const asks = this.safeValue(message, 'asks');
266943
+ const bids = this.safeList(message, 'bids');
266944
+ const asks = this.safeList(message, 'asks');
266495
266945
  for (let i = 0; i < bids.length; i++) {
266496
266946
  const bid = bids[i];
266497
266947
  const price = this.safeNumber(bid, 'price');
@@ -266526,7 +266976,7 @@ class krakenfutures extends _krakenfutures_js__WEBPACK_IMPORTED_MODULE_0__/* ["d
266526
266976
  const marketId = this.safeString(message, 'product_id');
266527
266977
  const market = this.safeMarket(marketId);
266528
266978
  const symbol = market['symbol'];
266529
- const messageHash = 'book:' + symbol;
266979
+ const messageHash = this.getMessageHash('orderbook', undefined, symbol);
266530
266980
  const orderbook = this.orderbooks[symbol];
266531
266981
  const side = this.safeString(message, 'side');
266532
266982
  const price = this.safeNumber(message, 'price');
@@ -266853,6 +267303,39 @@ class krakenfutures extends _krakenfutures_js__WEBPACK_IMPORTED_MODULE_0__/* ["d
266853
267303
  },
266854
267304
  });
266855
267305
  }
267306
+ async watchMultiHelper(unifiedName, channelName, symbols = undefined, subscriptionArgs = undefined, params = {}) {
267307
+ await this.loadMarkets();
267308
+ // symbols are required
267309
+ symbols = this.marketSymbols(symbols, undefined, false, true, false);
267310
+ const messageHashes = [];
267311
+ for (let i = 0; i < symbols.length; i++) {
267312
+ messageHashes.push(this.getMessageHash(unifiedName, undefined, this.symbol(symbols[i])));
267313
+ }
267314
+ const marketIds = this.marketIds(symbols);
267315
+ const request = {
267316
+ 'event': 'subscribe',
267317
+ 'feed': channelName,
267318
+ 'product_ids': marketIds,
267319
+ };
267320
+ const url = this.urls['api']['ws'];
267321
+ return await this.watchMultiple(url, messageHashes, this.extend(request, params), messageHashes, subscriptionArgs);
267322
+ }
267323
+ getMessageHash(unifiedElementName, subChannelName = undefined, symbol = undefined) {
267324
+ // unifiedElementName can be : orderbook, trade, ticker, bidask ...
267325
+ // subChannelName only applies to channel that needs specific variation (i.e. depth_50, depth_100..) to be selected
267326
+ const withSymbol = symbol !== undefined;
267327
+ let messageHash = unifiedElementName;
267328
+ if (!withSymbol) {
267329
+ messageHash += 's';
267330
+ }
267331
+ else {
267332
+ messageHash += ':' + symbol;
267333
+ }
267334
+ if (subChannelName !== undefined) {
267335
+ messageHash += '#' + subChannelName;
267336
+ }
267337
+ return messageHash;
267338
+ }
266856
267339
  handleErrorMessage(client, message) {
266857
267340
  //
266858
267341
  // {
@@ -266883,10 +267366,10 @@ class krakenfutures extends _krakenfutures_js__WEBPACK_IMPORTED_MODULE_0__/* ["d
266883
267366
  const feed = this.safeString(message, 'feed');
266884
267367
  const methods = {
266885
267368
  'ticker': this.handleTicker,
267369
+ 'ticker_lite': this.handleBidAsk,
266886
267370
  'trade': this.handleTrade,
266887
267371
  'trade_snapshot': this.handleTrade,
266888
267372
  // 'heartbeat': this.handleStatus,
266889
- 'ticker_lite': this.handleTicker,
266890
267373
  'book': this.handleOrderBook,
266891
267374
  'book_snapshot': this.handleOrderBookSnapshot,
266892
267375
  'open_orders_verbose': this.handleOrder,
@@ -267123,22 +267606,46 @@ class kucoin extends _kucoin_js__WEBPACK_IMPORTED_MODULE_0__/* ["default"] */ .Z
267123
267606
  /**
267124
267607
  * @method
267125
267608
  * @name kucoin#watchTickers
267609
+ * @see https://www.kucoin.com/docs/websocket/spot-trading/public-channels/ticker
267126
267610
  * @description watches a price ticker, a statistical calculation with the information calculated over the past 24 hours for all markets of a specific list
267127
267611
  * @param {string[]} symbols unified symbol of the market to fetch the ticker for
267128
267612
  * @param {object} [params] extra parameters specific to the exchange API endpoint
267613
+ * @param {string} [params.method] either '/market/snapshot' or '/market/ticker' default is '/market/ticker'
267129
267614
  * @returns {object} a [ticker structure]{@link https://docs.ccxt.com/#/?id=ticker-structure}
267130
267615
  */
267131
267616
  await this.loadMarkets();
267132
267617
  symbols = this.marketSymbols(symbols);
267133
- let messageHash = 'tickers';
267618
+ const messageHash = 'tickers';
267619
+ let method = undefined;
267620
+ [method, params] = this.handleOptionAndParams(params, 'watchTickers', 'method', '/market/ticker');
267621
+ const messageHashes = [];
267622
+ const topics = [];
267134
267623
  if (symbols !== undefined) {
267135
- messageHash = 'tickers::' + symbols.join(',');
267624
+ for (let i = 0; i < symbols.length; i++) {
267625
+ const symbol = symbols[i];
267626
+ messageHashes.push('ticker:' + symbol);
267627
+ const market = this.market(symbol);
267628
+ topics.push(method + ':' + market['id']);
267629
+ }
267136
267630
  }
267137
267631
  const url = await this.negotiate(false);
267138
- const topic = '/market/ticker:all';
267139
- const tickers = await this.subscribe(url, messageHash, topic, params);
267140
- if (this.newUpdates) {
267141
- return tickers;
267632
+ let tickers = undefined;
267633
+ if (symbols === undefined) {
267634
+ const allTopic = method + ':all';
267635
+ tickers = await this.subscribe(url, messageHash, allTopic, params);
267636
+ if (this.newUpdates) {
267637
+ return tickers;
267638
+ }
267639
+ }
267640
+ else {
267641
+ const marketIds = this.marketIds(symbols);
267642
+ const symbolsTopic = method + ':' + marketIds.join(',');
267643
+ tickers = await this.subscribeMultiple(url, messageHashes, symbolsTopic, topics, params);
267644
+ if (this.newUpdates) {
267645
+ const newDict = {};
267646
+ newDict[tickers['symbol']] = tickers;
267647
+ return newDict;
267648
+ }
267142
267649
  }
267143
267650
  return this.filterByArray(this.tickers, 'symbol', symbols);
267144
267651
  }
@@ -267222,19 +267729,6 @@ class kucoin extends _kucoin_js__WEBPACK_IMPORTED_MODULE_0__/* ["default"] */ .Z
267222
267729
  const allTickers = {};
267223
267730
  allTickers[symbol] = ticker;
267224
267731
  client.resolve(allTickers, 'tickers');
267225
- const messageHashes = this.findMessageHashes(client, 'tickers::');
267226
- for (let i = 0; i < messageHashes.length; i++) {
267227
- const currentMessageHash = messageHashes[i];
267228
- const parts = currentMessageHash.split('::');
267229
- const symbolsString = parts[1];
267230
- const symbols = symbolsString.split(',');
267231
- const tickers = this.filterByArray(this.tickers, 'symbol', symbols);
267232
- const tickersSymbols = Object.keys(tickers);
267233
- const numTickers = tickersSymbols.length;
267234
- if (numTickers > 0) {
267235
- client.resolve(tickers, currentMessageHash);
267236
- }
267237
- }
267238
267732
  }
267239
267733
  async watchBidsAsks(symbols = undefined, params = {}) {
267240
267734
  /**
@@ -285290,12 +285784,11 @@ class probit extends _abstract_probit_js__WEBPACK_IMPORTED_MODULE_0__/* ["defaul
285290
285784
  const result = await this.fetchTransactions(code, since, limit, this.extend(request, params));
285291
285785
  return result;
285292
285786
  }
285293
- async fetchTransactions(code = undefined, since = undefined, limit = undefined, params = {}) {
285787
+ async fetchDepositsWithdrawals(code = undefined, since = undefined, limit = undefined, params = {}) {
285294
285788
  /**
285295
285789
  * @method
285296
- * @name probit#fetchTransactions
285297
- * @deprecated
285298
- * @description use fetchDepositsWithdrawals instead
285790
+ * @name probit#fetchDepositsWithdrawals
285791
+ * @description fetch history of deposits and withdrawals
285299
285792
  * @see https://docs-en.probit.com/reference/transferpayment
285300
285793
  * @param {string} code unified currency code
285301
285794
  * @param {int} [since] the earliest time in ms to fetch transactions for
@@ -312511,6 +313004,8 @@ class woo extends _abstract_woo_js__WEBPACK_IMPORTED_MODULE_0__/* ["default"] */
312511
313004
  'fetchCanceledOrders': false,
312512
313005
  'fetchClosedOrder': false,
312513
313006
  'fetchClosedOrders': true,
313007
+ 'fetchConvertCurrencies': true,
313008
+ 'fetchConvertQuote': true,
312514
313009
  'fetchCurrencies': true,
312515
313010
  'fetchDepositAddress': true,
312516
313011
  'fetchDeposits': true,
@@ -315439,6 +315934,143 @@ class woo extends _abstract_woo_js__WEBPACK_IMPORTED_MODULE_0__/* ["default"] */
315439
315934
  'takeProfitPrice': undefined,
315440
315935
  });
315441
315936
  }
315937
+ async fetchConvertQuote(fromCode, toCode, amount = undefined, params = {}) {
315938
+ /**
315939
+ * @method
315940
+ * @name woo#fetchConvertQuote
315941
+ * @description fetch a quote for converting from one currency to another
315942
+ * @see https://docs.woo.org/#get-quote-rfq
315943
+ * @param {string} fromCode the currency that you want to sell and convert from
315944
+ * @param {string} toCode the currency that you want to buy and convert into
315945
+ * @param {float} [amount] how much you want to trade in units of the from currency
315946
+ * @param {object} [params] extra parameters specific to the exchange API endpoint
315947
+ * @returns {object} a [conversion structure]{@link https://docs.ccxt.com/#/?id=conversion-structure}
315948
+ */
315949
+ await this.loadMarkets();
315950
+ const request = {
315951
+ 'sellToken': fromCode.toUpperCase(),
315952
+ 'buyToken': toCode.toUpperCase(),
315953
+ 'sellQuantity': this.numberToString(amount),
315954
+ };
315955
+ const response = await this.v3PrivateGetConvertRfq(this.extend(request, params));
315956
+ //
315957
+ // {
315958
+ // "success": true,
315959
+ // "data": {
315960
+ // "quoteId": 123123123,
315961
+ // "counterPartyId": "",
315962
+ // "sellToken": "ETH",
315963
+ // "sellQuantity": "0.0445",
315964
+ // "buyToken": "USDT",
315965
+ // "buyQuantity": "33.45",
315966
+ // "buyPrice": "6.77",
315967
+ // "expireTimestamp": 1659084466000,
315968
+ // "message": 1659084466000
315969
+ // }
315970
+ // }
315971
+ //
315972
+ const data = this.safeDict(response, 'data', {});
315973
+ const fromCurrencyId = this.safeString(data, 'sellToken', fromCode);
315974
+ const fromCurrency = this.currency(fromCurrencyId);
315975
+ const toCurrencyId = this.safeString(data, 'buyToken', toCode);
315976
+ const toCurrency = this.currency(toCurrencyId);
315977
+ return this.parseConversion(data, fromCurrency, toCurrency);
315978
+ }
315979
+ parseConversion(conversion, fromCurrency = undefined, toCurrency = undefined) {
315980
+ //
315981
+ // fetchConvertQuote
315982
+ //
315983
+ // {
315984
+ // "quoteId": 123123123,
315985
+ // "counterPartyId": "",
315986
+ // "sellToken": "ETH",
315987
+ // "sellQuantity": "0.0445",
315988
+ // "buyToken": "USDT",
315989
+ // "buyQuantity": "33.45",
315990
+ // "buyPrice": "6.77",
315991
+ // "expireTimestamp": 1659084466000,
315992
+ // "message": 1659084466000
315993
+ // }
315994
+ //
315995
+ const timestamp = this.safeInteger(conversion, 'expireTimestamp');
315996
+ const fromCoin = this.safeString(conversion, 'sellToken');
315997
+ const fromCode = this.safeCurrencyCode(fromCoin, fromCurrency);
315998
+ const to = this.safeString(conversion, 'buyToken');
315999
+ const toCode = this.safeCurrencyCode(to, toCurrency);
316000
+ return {
316001
+ 'info': conversion,
316002
+ 'timestamp': timestamp,
316003
+ 'datetime': this.iso8601(timestamp),
316004
+ 'id': this.safeString(conversion, 'quoteId'),
316005
+ 'fromCurrency': fromCode,
316006
+ 'fromAmount': this.safeNumber(conversion, 'sellQuantity'),
316007
+ 'toCurrency': toCode,
316008
+ 'toAmount': this.safeNumber(conversion, 'buyQuantity'),
316009
+ 'price': this.safeNumber(conversion, 'buyPrice'),
316010
+ 'fee': undefined,
316011
+ };
316012
+ }
316013
+ async fetchConvertCurrencies(params = {}) {
316014
+ /**
316015
+ * @method
316016
+ * @name woo#fetchConvertCurrencies
316017
+ * @description fetches all available currencies that can be converted
316018
+ * @see https://docs.woo.org/#get-quote-asset-info
316019
+ * @param {object} [params] extra parameters specific to the exchange API endpoint
316020
+ * @returns {object} an associative dictionary of currencies
316021
+ */
316022
+ await this.loadMarkets();
316023
+ const response = await this.v3PrivateGetConvertAssetInfo(params);
316024
+ //
316025
+ // {
316026
+ // "success": true,
316027
+ // "rows": [
316028
+ // {
316029
+ // "token": "BTC",
316030
+ // "tick": 0.0001,
316031
+ // "createdTime": "1575014248.99", // Unix epoch time in seconds
316032
+ // "updatedTime": "1575014248.99" // Unix epoch time in seconds
316033
+ // },
316034
+ // ]
316035
+ // }
316036
+ //
316037
+ const result = {};
316038
+ const data = this.safeList(response, 'rows', []);
316039
+ for (let i = 0; i < data.length; i++) {
316040
+ const entry = data[i];
316041
+ const id = this.safeString(entry, 'token');
316042
+ const code = this.safeCurrencyCode(id);
316043
+ result[code] = {
316044
+ 'info': entry,
316045
+ 'id': id,
316046
+ 'code': code,
316047
+ 'networks': undefined,
316048
+ 'type': undefined,
316049
+ 'name': undefined,
316050
+ 'active': undefined,
316051
+ 'deposit': undefined,
316052
+ 'withdraw': undefined,
316053
+ 'fee': undefined,
316054
+ 'precision': this.safeNumber(entry, 'tick'),
316055
+ 'limits': {
316056
+ 'amount': {
316057
+ 'min': undefined,
316058
+ 'max': undefined,
316059
+ },
316060
+ 'withdraw': {
316061
+ 'min': undefined,
316062
+ 'max': undefined,
316063
+ },
316064
+ 'deposit': {
316065
+ 'min': undefined,
316066
+ 'max': undefined,
316067
+ },
316068
+ },
316069
+ 'created': this.safeTimestamp(entry, 'createdTime'),
316070
+ };
316071
+ }
316072
+ return result;
316073
+ }
315442
316074
  defaultNetworkCodeForCurrency(code) {
315443
316075
  const currencyItem = this.currency(code);
315444
316076
  const networks = currencyItem['networks'];
@@ -325612,7 +326244,7 @@ SOFTWARE.
325612
326244
 
325613
326245
  //-----------------------------------------------------------------------------
325614
326246
  // this is updated by vss.js when building
325615
- const version = '4.2.92';
326247
+ const version = '4.2.94';
325616
326248
  _src_base_Exchange_js__WEBPACK_IMPORTED_MODULE_0__/* .Exchange */ .e.ccxtVersion = version;
325617
326249
  //-----------------------------------------------------------------------------
325618
326250