ccxt 4.2.84 → 4.2.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 (164) hide show
  1. package/README.md +3 -3
  2. package/build.sh +1 -1
  3. package/dist/ccxt.browser.js +867 -904
  4. package/dist/ccxt.browser.min.js +4 -4
  5. package/dist/cjs/ccxt.js +1 -1
  6. package/dist/cjs/src/ace.js +5 -5
  7. package/dist/cjs/src/ascendex.js +8 -8
  8. package/dist/cjs/src/base/Exchange.js +76 -14
  9. package/dist/cjs/src/bigone.js +12 -12
  10. package/dist/cjs/src/binance.js +23 -35
  11. package/dist/cjs/src/bingx.js +13 -9
  12. package/dist/cjs/src/bit2c.js +1 -1
  13. package/dist/cjs/src/bitbank.js +8 -8
  14. package/dist/cjs/src/bitbns.js +5 -5
  15. package/dist/cjs/src/bitfinex.js +1 -1
  16. package/dist/cjs/src/bitfinex2.js +1 -1
  17. package/dist/cjs/src/bitget.js +30 -24
  18. package/dist/cjs/src/bithumb.js +5 -5
  19. package/dist/cjs/src/bitmart.js +16 -16
  20. package/dist/cjs/src/bitopro.js +1 -1
  21. package/dist/cjs/src/bitrue.js +4 -4
  22. package/dist/cjs/src/bitso.js +5 -5
  23. package/dist/cjs/src/bitstamp.js +1 -1
  24. package/dist/cjs/src/bitteam.js +8 -8
  25. package/dist/cjs/src/bl3p.js +1 -1
  26. package/dist/cjs/src/btcturk.js +6 -6
  27. package/dist/cjs/src/bybit.js +31 -95
  28. package/dist/cjs/src/coincheck.js +4 -4
  29. package/dist/cjs/src/coinex.js +11 -11
  30. package/dist/cjs/src/coinlist.js +7 -7
  31. package/dist/cjs/src/coinmate.js +4 -4
  32. package/dist/cjs/src/coinmetro.js +3 -3
  33. package/dist/cjs/src/coinone.js +5 -5
  34. package/dist/cjs/src/coinspot.js +2 -2
  35. package/dist/cjs/src/cryptocom.js +17 -17
  36. package/dist/cjs/src/currencycom.js +1 -1
  37. package/dist/cjs/src/delta.js +0 -8
  38. package/dist/cjs/src/deribit.js +16 -92
  39. package/dist/cjs/src/digifinex.js +8 -8
  40. package/dist/cjs/src/exmo.js +8 -8
  41. package/dist/cjs/src/gate.js +0 -8
  42. package/dist/cjs/src/hitbtc.js +5 -4
  43. package/dist/cjs/src/hollaex.js +7 -7
  44. package/dist/cjs/src/htx.js +7 -7
  45. package/dist/cjs/src/huobijp.js +3 -3
  46. package/dist/cjs/src/idex.js +2 -2
  47. package/dist/cjs/src/independentreserve.js +2 -2
  48. package/dist/cjs/src/indodax.js +2 -2
  49. package/dist/cjs/src/kraken.js +8 -8
  50. package/dist/cjs/src/krakenfutures.js +6 -6
  51. package/dist/cjs/src/kucoin.js +5 -1
  52. package/dist/cjs/src/kucoinfutures.js +8 -8
  53. package/dist/cjs/src/kuna.js +16 -16
  54. package/dist/cjs/src/latoken.js +2 -2
  55. package/dist/cjs/src/lbank.js +10 -10
  56. package/dist/cjs/src/luno.js +4 -4
  57. package/dist/cjs/src/mercado.js +5 -5
  58. package/dist/cjs/src/mexc.js +6 -6
  59. package/dist/cjs/src/ndax.js +1 -1
  60. package/dist/cjs/src/novadax.js +9 -9
  61. package/dist/cjs/src/oceanex.js +7 -7
  62. package/dist/cjs/src/okcoin.js +13 -13
  63. package/dist/cjs/src/okx.js +23 -31
  64. package/dist/cjs/src/onetrading.js +4 -4
  65. package/dist/cjs/src/p2b.js +7 -7
  66. package/dist/cjs/src/phemex.js +12 -12
  67. package/dist/cjs/src/poloniexfutures.js +5 -5
  68. package/dist/cjs/src/pro/binance.js +167 -121
  69. package/dist/cjs/src/pro/kucoin.js +6 -7
  70. package/dist/cjs/src/pro/okx.js +19 -2
  71. package/dist/cjs/src/probit.js +11 -11
  72. package/dist/cjs/src/timex.js +7 -7
  73. package/dist/cjs/src/tokocrypto.js +9 -9
  74. package/dist/cjs/src/wavesexchange.js +3 -3
  75. package/dist/cjs/src/whitebit.js +5 -5
  76. package/dist/cjs/src/woo.js +1 -1
  77. package/dist/cjs/src/zaif.js +1 -1
  78. package/dist/cjs/src/zonda.js +7 -7
  79. package/examples/js/cli.js +0 -1
  80. package/examples/ts/cli.ts +0 -1
  81. package/js/ccxt.d.ts +1 -1
  82. package/js/ccxt.js +1 -1
  83. package/js/src/ace.js +5 -5
  84. package/js/src/ascendex.js +8 -8
  85. package/js/src/base/Exchange.d.ts +4 -3
  86. package/js/src/base/Exchange.js +76 -14
  87. package/js/src/bigone.js +12 -12
  88. package/js/src/binance.d.ts +0 -1
  89. package/js/src/binance.js +23 -35
  90. package/js/src/bingx.js +13 -9
  91. package/js/src/bit2c.js +1 -1
  92. package/js/src/bitbank.js +8 -8
  93. package/js/src/bitbns.js +5 -5
  94. package/js/src/bitfinex.js +1 -1
  95. package/js/src/bitfinex2.js +1 -1
  96. package/js/src/bitget.js +30 -24
  97. package/js/src/bithumb.js +5 -5
  98. package/js/src/bitmart.js +16 -16
  99. package/js/src/bitopro.js +1 -1
  100. package/js/src/bitrue.js +4 -4
  101. package/js/src/bitso.js +5 -5
  102. package/js/src/bitstamp.js +1 -1
  103. package/js/src/bitteam.js +8 -8
  104. package/js/src/bl3p.js +1 -1
  105. package/js/src/btcturk.js +6 -6
  106. package/js/src/bybit.d.ts +0 -3
  107. package/js/src/bybit.js +31 -95
  108. package/js/src/coincheck.js +4 -4
  109. package/js/src/coinex.js +11 -11
  110. package/js/src/coinlist.js +7 -7
  111. package/js/src/coinmate.js +4 -4
  112. package/js/src/coinmetro.js +3 -3
  113. package/js/src/coinone.js +5 -5
  114. package/js/src/coinspot.js +2 -2
  115. package/js/src/cryptocom.js +17 -17
  116. package/js/src/currencycom.js +1 -1
  117. package/js/src/delta.d.ts +0 -1
  118. package/js/src/delta.js +0 -8
  119. package/js/src/deribit.d.ts +0 -3
  120. package/js/src/deribit.js +16 -92
  121. package/js/src/digifinex.js +8 -8
  122. package/js/src/exmo.js +8 -8
  123. package/js/src/gate.d.ts +0 -1
  124. package/js/src/gate.js +0 -8
  125. package/js/src/hitbtc.js +5 -4
  126. package/js/src/hollaex.js +7 -7
  127. package/js/src/htx.js +7 -7
  128. package/js/src/huobijp.js +3 -3
  129. package/js/src/idex.js +2 -2
  130. package/js/src/independentreserve.js +2 -2
  131. package/js/src/indodax.js +2 -2
  132. package/js/src/kraken.js +8 -8
  133. package/js/src/krakenfutures.js +6 -6
  134. package/js/src/kucoin.js +5 -1
  135. package/js/src/kucoinfutures.js +8 -8
  136. package/js/src/kuna.js +16 -16
  137. package/js/src/latoken.js +2 -2
  138. package/js/src/lbank.js +10 -10
  139. package/js/src/luno.js +4 -4
  140. package/js/src/mercado.js +5 -5
  141. package/js/src/mexc.js +6 -6
  142. package/js/src/ndax.js +1 -1
  143. package/js/src/novadax.js +9 -9
  144. package/js/src/oceanex.js +7 -7
  145. package/js/src/okcoin.js +13 -13
  146. package/js/src/okx.d.ts +0 -1
  147. package/js/src/okx.js +23 -31
  148. package/js/src/onetrading.js +4 -4
  149. package/js/src/p2b.js +7 -7
  150. package/js/src/phemex.js +12 -12
  151. package/js/src/poloniexfutures.js +5 -5
  152. package/js/src/pro/binance.d.ts +5 -1
  153. package/js/src/pro/binance.js +168 -122
  154. package/js/src/pro/kucoin.js +6 -7
  155. package/js/src/pro/okx.js +19 -2
  156. package/js/src/probit.js +11 -11
  157. package/js/src/timex.js +7 -7
  158. package/js/src/tokocrypto.js +9 -9
  159. package/js/src/wavesexchange.js +3 -3
  160. package/js/src/whitebit.js +5 -5
  161. package/js/src/woo.js +1 -1
  162. package/js/src/zaif.js +1 -1
  163. package/js/src/zonda.js +7 -7
  164. package/package.json +1 -1
@@ -567,7 +567,7 @@ class p2b extends p2b$1 {
567
567
  // current_time: '1699255571.413828'
568
568
  // }
569
569
  //
570
- const result = this.safeValue(response, 'result', []);
570
+ const result = this.safeList(response, 'result', []);
571
571
  return this.parseTrades(result, market, since, limit);
572
572
  }
573
573
  parseTrade(trade, market = undefined) {
@@ -684,7 +684,7 @@ class p2b extends p2b$1 {
684
684
  // current_time: '1699256375.030494'
685
685
  // }
686
686
  //
687
- const result = this.safeValue(response, 'result', []);
687
+ const result = this.safeList(response, 'result', []);
688
688
  return this.parseOHLCVs(result, market, timeframe, since, limit);
689
689
  }
690
690
  parseOHLCV(ohlcv, market = undefined) {
@@ -819,7 +819,7 @@ class p2b extends p2b$1 {
819
819
  // }
820
820
  // }
821
821
  //
822
- const result = this.safeValue(response, 'result');
822
+ const result = this.safeDict(response, 'result');
823
823
  return this.parseOrder(result, market);
824
824
  }
825
825
  async cancelOrder(id, symbol = undefined, params = {}) {
@@ -865,7 +865,7 @@ class p2b extends p2b$1 {
865
865
  // }
866
866
  // }
867
867
  //
868
- const result = this.safeValue(response, 'result');
868
+ const result = this.safeDict(response, 'result');
869
869
  return this.parseOrder(result);
870
870
  }
871
871
  async fetchOpenOrders(symbol = undefined, since = undefined, limit = undefined, params = {}) {
@@ -920,7 +920,7 @@ class p2b extends p2b$1 {
920
920
  // ]
921
921
  // }
922
922
  //
923
- const result = this.safeValue(response, 'result', []);
923
+ const result = this.safeList(response, 'result', []);
924
924
  return this.parseOrders(result, market, since, limit);
925
925
  }
926
926
  async fetchOrderTrades(id, symbol = undefined, since = undefined, limit = undefined, params = {}) {
@@ -972,7 +972,7 @@ class p2b extends p2b$1 {
972
972
  // }
973
973
  //
974
974
  const result = this.safeValue(response, 'result', {});
975
- const records = this.safeValue(result, 'records', []);
975
+ const records = this.safeList(result, 'records', []);
976
976
  return this.parseTrades(records, market, since, limit);
977
977
  }
978
978
  async fetchMyTrades(symbol = undefined, since = undefined, limit = undefined, params = {}) {
@@ -1048,7 +1048,7 @@ class p2b extends p2b$1 {
1048
1048
  // }
1049
1049
  //
1050
1050
  const result = this.safeValue(response, 'result', {});
1051
- const deals = this.safeValue(result, 'deals', []);
1051
+ const deals = this.safeList(result, 'deals', []);
1052
1052
  return this.parseTrades(deals, market, since, limit);
1053
1053
  }
1054
1054
  async fetchClosedOrders(symbol = undefined, since = undefined, limit = undefined, params = {}) {
@@ -1295,7 +1295,7 @@ class phemex extends phemex$1 {
1295
1295
  // }
1296
1296
  //
1297
1297
  const data = this.safeValue(response, 'data', {});
1298
- const rows = this.safeValue(data, 'rows', []);
1298
+ const rows = this.safeList(data, 'rows', []);
1299
1299
  return this.parseOHLCVs(rows, market, timeframe, since, userLimit);
1300
1300
  }
1301
1301
  parseTicker(ticker, market = undefined) {
@@ -1458,7 +1458,7 @@ class phemex extends phemex$1 {
1458
1458
  // }
1459
1459
  // }
1460
1460
  //
1461
- const result = this.safeValue(response, 'result', {});
1461
+ const result = this.safeDict(response, 'result', {});
1462
1462
  return this.parseTicker(result, market);
1463
1463
  }
1464
1464
  async fetchTickers(symbols = undefined, params = {}) {
@@ -1494,7 +1494,7 @@ class phemex extends phemex$1 {
1494
1494
  else {
1495
1495
  response = await this.v2GetMdV2Ticker24hrAll(query);
1496
1496
  }
1497
- const result = this.safeValue(response, 'result', []);
1497
+ const result = this.safeList(response, 'result', []);
1498
1498
  return this.parseTickers(result, symbols);
1499
1499
  }
1500
1500
  async fetchTrades(symbol, since = undefined, limit = undefined, params = {}) {
@@ -2723,7 +2723,7 @@ class phemex extends phemex$1 {
2723
2723
  // }
2724
2724
  // }
2725
2725
  //
2726
- const data = this.safeValue(response, 'data', {});
2726
+ const data = this.safeDict(response, 'data', {});
2727
2727
  return this.parseOrder(data, market);
2728
2728
  }
2729
2729
  async editOrder(id, symbol, type = undefined, side = undefined, amount = undefined, price = undefined, params = {}) {
@@ -2802,7 +2802,7 @@ class phemex extends phemex$1 {
2802
2802
  else {
2803
2803
  response = await this.privatePutSpotOrders(this.extend(request, params));
2804
2804
  }
2805
- const data = this.safeValue(response, 'data', {});
2805
+ const data = this.safeDict(response, 'data', {});
2806
2806
  return this.parseOrder(data, market);
2807
2807
  }
2808
2808
  async cancelOrder(id, symbol = undefined, params = {}) {
@@ -2847,7 +2847,7 @@ class phemex extends phemex$1 {
2847
2847
  else {
2848
2848
  response = await this.privateDeleteSpotOrders(this.extend(request, params));
2849
2849
  }
2850
- const data = this.safeValue(response, 'data', {});
2850
+ const data = this.safeDict(response, 'data', {});
2851
2851
  return this.parseOrder(data, market);
2852
2852
  }
2853
2853
  async cancelAllOrders(symbol = undefined, params = {}) {
@@ -2971,7 +2971,7 @@ class phemex extends phemex$1 {
2971
2971
  response = await this.privateGetSpotOrders(this.extend(request, params));
2972
2972
  }
2973
2973
  const data = this.safeValue(response, 'data', {});
2974
- const rows = this.safeValue(data, 'rows', data);
2974
+ const rows = this.safeList(data, 'rows', data);
2975
2975
  return this.parseOrders(rows, market, since, limit);
2976
2976
  }
2977
2977
  async fetchOpenOrders(symbol = undefined, since = undefined, limit = undefined, params = {}) {
@@ -3020,7 +3020,7 @@ class phemex extends phemex$1 {
3020
3020
  return this.parseOrders(data, market, since, limit);
3021
3021
  }
3022
3022
  else {
3023
- const rows = this.safeValue(data, 'rows', []);
3023
+ const rows = this.safeList(data, 'rows', []);
3024
3024
  return this.parseOrders(rows, market, since, limit);
3025
3025
  }
3026
3026
  }
@@ -3107,7 +3107,7 @@ class phemex extends phemex$1 {
3107
3107
  return this.parseOrders(data, market, since, limit);
3108
3108
  }
3109
3109
  else {
3110
- const rows = this.safeValue(data, 'rows', []);
3110
+ const rows = this.safeList(data, 'rows', []);
3111
3111
  return this.parseOrders(rows, market, since, limit);
3112
3112
  }
3113
3113
  }
@@ -4228,7 +4228,7 @@ class phemex extends phemex$1 {
4228
4228
  //
4229
4229
  //
4230
4230
  const data = this.safeValue(response, 'data', {});
4231
- const riskLimits = this.safeValue(data, 'riskLimits');
4231
+ const riskLimits = this.safeList(data, 'riskLimits');
4232
4232
  return this.parseLeverageTiers(riskLimits, symbols, 'symbol');
4233
4233
  }
4234
4234
  parseMarketLeverageTiers(info, market = undefined) {
@@ -4490,7 +4490,7 @@ class phemex extends phemex$1 {
4490
4490
  // }
4491
4491
  //
4492
4492
  const data = this.safeValue(response, 'data', {});
4493
- const transfers = this.safeValue(data, 'rows', []);
4493
+ const transfers = this.safeList(data, 'rows', []);
4494
4494
  return this.parseTransfers(transfers, currency, since, limit);
4495
4495
  }
4496
4496
  parseTransfer(transfer, currency = undefined) {
@@ -4713,7 +4713,7 @@ class phemex extends phemex$1 {
4713
4713
  // }
4714
4714
  // }
4715
4715
  //
4716
- const data = this.safeValue(response, 'data', {});
4716
+ const data = this.safeDict(response, 'data', {});
4717
4717
  return this.parseTransaction(data, currency);
4718
4718
  }
4719
4719
  handleErrors(httpCode, reason, url, method, headers, body, response, requestHeaders, requestBody) {
@@ -676,7 +676,7 @@ class poloniexfutures extends poloniexfutures$1 {
676
676
  // },
677
677
  // }
678
678
  //
679
- const trades = this.safeValue(response, 'data', []);
679
+ const trades = this.safeList(response, 'data', []);
680
680
  return this.parseTrades(trades, market, since, limit);
681
681
  }
682
682
  async fetchTime(params = {}) {
@@ -749,7 +749,7 @@ class poloniexfutures extends poloniexfutures$1 {
749
749
  // ]
750
750
  // }
751
751
  //
752
- const data = this.safeValue(response, 'data', []);
752
+ const data = this.safeList(response, 'data', []);
753
753
  return this.parseOHLCVs(data, market, timeframe, since, limit);
754
754
  }
755
755
  parseBalance(response) {
@@ -1009,7 +1009,7 @@ class poloniexfutures extends poloniexfutures$1 {
1009
1009
  // ]
1010
1010
  // }
1011
1011
  //
1012
- const data = this.safeValue(response, 'data');
1012
+ const data = this.safeList(response, 'data');
1013
1013
  return this.parsePositions(data, symbols);
1014
1014
  }
1015
1015
  parsePosition(position, market = undefined) {
@@ -1463,7 +1463,7 @@ class poloniexfutures extends poloniexfutures$1 {
1463
1463
  // }
1464
1464
  //
1465
1465
  const market = (symbol !== undefined) ? this.market(symbol) : undefined;
1466
- const responseData = this.safeValue(response, 'data');
1466
+ const responseData = this.safeDict(response, 'data');
1467
1467
  return this.parseOrder(responseData, market);
1468
1468
  }
1469
1469
  parseOrder(order, market = undefined) {
@@ -1699,7 +1699,7 @@ class poloniexfutures extends poloniexfutures$1 {
1699
1699
  // }
1700
1700
  //
1701
1701
  const data = this.safeValue(response, 'data', {});
1702
- const trades = this.safeValue(data, 'items', {});
1702
+ const trades = this.safeList(data, 'items', []);
1703
1703
  return this.parseTrades(trades, market, since, limit);
1704
1704
  }
1705
1705
  async setMarginMode(marginMode, symbol = undefined, params = {}) {
@@ -17,6 +17,7 @@ class binance extends binance$1 {
17
17
  'has': {
18
18
  'ws': true,
19
19
  'watchBalance': true,
20
+ 'watchBidsAsks': true,
20
21
  'watchMyTrades': true,
21
22
  'watchOHLCV': true,
22
23
  'watchOHLCVForSymbols': false,
@@ -98,10 +99,10 @@ class binance extends binance$1 {
98
99
  'name': 'trade', // 'trade' or 'aggTrade'
99
100
  },
100
101
  'watchTicker': {
101
- 'name': 'ticker', // ticker = 1000ms L1+OHLCV, bookTicker = real-time L1
102
+ 'name': 'ticker', // ticker or miniTicker or ticker_<window_size>
102
103
  },
103
104
  'watchTickers': {
104
- 'name': 'ticker', // ticker or miniTicker or bookTicker
105
+ 'name': 'ticker', // ticker or miniTicker or ticker_<window_size>
105
106
  },
106
107
  'watchOHLCV': {
107
108
  'name': 'kline', // or indexPriceKline or markPriceKline (coin-m futures)
@@ -122,6 +123,15 @@ class binance extends binance$1 {
122
123
  'ws': {
123
124
  'cost': 5,
124
125
  },
126
+ 'tickerChannelsMap': {
127
+ '24hrTicker': 'ticker',
128
+ '24hrMiniTicker': 'miniTicker',
129
+ // rolling window tickers
130
+ '1hTicker': 'ticker_1h',
131
+ '4hTicker': 'ticker_4h',
132
+ '1dTicker': 'ticker_1d',
133
+ 'bookTicker': 'bookTicker',
134
+ },
125
135
  },
126
136
  });
127
137
  }
@@ -935,34 +945,13 @@ class binance extends binance$1 {
935
945
  * @description watches a price ticker, a statistical calculation with the information calculated over the past 24 hours for a specific market
936
946
  * @param {string} symbol unified symbol of the market to fetch the ticker for
937
947
  * @param {object} [params] extra parameters specific to the exchange API endpoint
938
- * @param {string} [params.name] stream to use can be ticker or bookTicker
948
+ * @param {string} [params.name] stream to use can be ticker or miniTicker
939
949
  * @returns {object} a [ticker structure]{@link https://docs.ccxt.com/#/?id=ticker-structure}
940
950
  */
941
951
  await this.loadMarkets();
942
- const market = this.market(symbol);
943
- const marketId = market['lowercaseId'];
944
- let type = market['type'];
945
- if (market['contract']) {
946
- type = market['linear'] ? 'future' : 'delivery';
947
- }
948
- const options = this.safeValue(this.options, 'watchTicker', {});
949
- let name = this.safeString(options, 'name', 'ticker');
950
- name = this.safeString(params, 'name', name);
951
- params = this.omit(params, 'name');
952
- const messageHash = marketId + '@' + name;
953
- const url = this.urls['api']['ws'][type] + '/' + this.stream(type, messageHash);
954
- const requestId = this.requestId(url);
955
- const request = {
956
- 'method': 'SUBSCRIBE',
957
- 'params': [
958
- messageHash,
959
- ],
960
- 'id': requestId,
961
- };
962
- const subscribe = {
963
- 'id': requestId,
964
- };
965
- return await this.watch(url, messageHash, this.extend(request, params), messageHash, subscribe);
952
+ symbol = this.symbol(symbol);
953
+ const tickers = await this.watchTickers([symbol], this.extend(params, { 'callerMethodName': 'watchTicker' }));
954
+ return tickers[symbol];
966
955
  }
967
956
  async watchTickers(symbols = undefined, params = {}) {
968
957
  /**
@@ -973,61 +962,108 @@ class binance extends binance$1 {
973
962
  * @param {object} [params] extra parameters specific to the exchange API endpoint
974
963
  * @returns {object} a [ticker structure]{@link https://docs.ccxt.com/#/?id=ticker-structure}
975
964
  */
976
- await this.loadMarkets();
977
- symbols = this.marketSymbols(symbols, undefined, true, true, true);
978
- const marketIds = this.marketIds(symbols);
979
- let market = undefined;
980
- let type = undefined;
981
- if (symbols !== undefined) {
982
- market = this.market(symbols[0]);
965
+ let channelName = undefined;
966
+ [channelName, params] = this.handleOptionAndParams(params, 'watchTickers', 'name', 'ticker');
967
+ if (channelName === 'bookTicker') {
968
+ throw new errors.BadRequest(this.id + ' deprecation notice - to subscribe for bids-asks, use watch_bids_asks() method instead');
983
969
  }
984
- [type, params] = this.handleMarketTypeAndParams('watchTickers', market, params);
970
+ const newTickers = await this.watchMultiTickerHelper('watchTickers', channelName, symbols, params);
971
+ if (this.newUpdates) {
972
+ return newTickers;
973
+ }
974
+ return this.filterByArray(this.tickers, 'symbol', symbols);
975
+ }
976
+ async watchBidsAsks(symbols = undefined, params = {}) {
977
+ /**
978
+ * @method
979
+ * @name binance#watchBidsAsks
980
+ * @see https://binance-docs.github.io/apidocs/spot/en/#individual-symbol-book-ticker-streams
981
+ * @see https://binance-docs.github.io/apidocs/futures/en/#all-book-tickers-stream
982
+ * @see https://binance-docs.github.io/apidocs/delivery/en/#all-book-tickers-stream
983
+ * @description watches best bid & ask for symbols
984
+ * @param {string[]} symbols unified symbol of the market to fetch the ticker for
985
+ * @param {object} [params] extra parameters specific to the exchange API endpoint
986
+ * @returns {object} a [ticker structure]{@link https://docs.ccxt.com/#/?id=ticker-structure}
987
+ */
988
+ const result = await this.watchMultiTickerHelper('watchBidsAsks', 'bookTicker', symbols, params);
989
+ if (this.newUpdates) {
990
+ return result;
991
+ }
992
+ return this.filterByArray(this.tickers, 'symbol', symbols);
993
+ }
994
+ async watchMultiTickerHelper(methodName, channelName, symbols = undefined, params = {}) {
995
+ await this.loadMarkets();
996
+ symbols = this.marketSymbols(symbols, undefined, true, false, true);
997
+ let firstMarket = undefined;
998
+ let marketType = undefined;
999
+ const symbolsDefined = (symbols !== undefined);
1000
+ if (symbolsDefined) {
1001
+ firstMarket = this.market(symbols[0]);
1002
+ }
1003
+ [marketType, params] = this.handleMarketTypeAndParams(methodName, firstMarket, params);
985
1004
  let subType = undefined;
986
- [subType, params] = this.handleSubTypeAndParams('watchTickers', market, params);
987
- if (this.isLinear(type, subType)) {
988
- type = 'future';
1005
+ [subType, params] = this.handleSubTypeAndParams(methodName, firstMarket, params);
1006
+ let rawMarketType = undefined;
1007
+ if (this.isLinear(marketType, subType)) {
1008
+ rawMarketType = 'future';
989
1009
  }
990
- else if (this.isInverse(type, subType)) {
991
- type = 'delivery';
1010
+ else if (this.isInverse(marketType, subType)) {
1011
+ rawMarketType = 'delivery';
992
1012
  }
993
- const options = this.safeValue(this.options, 'watchTickers', {});
994
- let name = this.safeString(options, 'name', 'ticker');
995
- name = this.safeString(params, 'name', name);
996
- params = this.omit(params, 'name');
997
- let wsParams = [];
998
- let messageHash = 'tickers';
999
- if (symbols !== undefined) {
1000
- messageHash = 'tickers::' + symbols.join(',');
1013
+ else if (marketType === 'spot') {
1014
+ rawMarketType = marketType;
1001
1015
  }
1002
- if (name === 'bookTicker') {
1003
- if (marketIds === undefined) {
1004
- throw new errors.ArgumentsRequired(this.id + ' watchTickers() requires symbols for bookTicker');
1005
- }
1006
- // simulate watchTickers with subscribe multiple individual bookTicker topic
1007
- for (let i = 0; i < marketIds.length; i++) {
1008
- wsParams.push(marketIds[i].toLowerCase() + '@bookTicker');
1016
+ else {
1017
+ throw new errors.NotSupported(this.id + ' ' + methodName + '() does not support options markets');
1018
+ }
1019
+ const isBidAsk = (channelName === 'bookTicker');
1020
+ const subscriptionArgs = [];
1021
+ const messageHashes = [];
1022
+ if (symbolsDefined) {
1023
+ for (let i = 0; i < symbols.length; i++) {
1024
+ const symbol = symbols[i];
1025
+ const market = this.market(symbol);
1026
+ subscriptionArgs.push(market['lowercaseId'] + '@' + channelName);
1027
+ messageHashes.push(this.getMessageHash(channelName, market['symbol'], isBidAsk));
1009
1028
  }
1010
1029
  }
1011
1030
  else {
1012
- wsParams = [
1013
- '!' + name + '@arr',
1014
- ];
1031
+ if (isBidAsk) {
1032
+ if (marketType === 'spot') {
1033
+ throw new errors.ArgumentsRequired(this.id + ' ' + methodName + '() requires symbols for this channel for spot markets');
1034
+ }
1035
+ subscriptionArgs.push('!' + channelName);
1036
+ }
1037
+ else {
1038
+ subscriptionArgs.push('!' + channelName + '@arr');
1039
+ }
1040
+ messageHashes.push(this.getMessageHash(channelName, undefined, isBidAsk));
1015
1041
  }
1016
- const url = this.urls['api']['ws'][type] + '/' + this.stream(type, messageHash);
1042
+ let streamHash = channelName;
1043
+ if (symbolsDefined) {
1044
+ streamHash = channelName + '::' + symbols.join(',');
1045
+ }
1046
+ const url = this.urls['api']['ws'][rawMarketType] + '/' + this.stream(rawMarketType, streamHash);
1017
1047
  const requestId = this.requestId(url);
1018
1048
  const request = {
1019
1049
  'method': 'SUBSCRIBE',
1020
- 'params': wsParams,
1050
+ 'params': subscriptionArgs,
1021
1051
  'id': requestId,
1022
1052
  };
1023
1053
  const subscribe = {
1024
1054
  'id': requestId,
1025
1055
  };
1026
- const newTickers = await this.watch(url, messageHash, this.extend(request, params), messageHash, subscribe);
1027
- if (this.newUpdates) {
1028
- return newTickers;
1056
+ const result = await this.watchMultiple(url, messageHashes, this.deepExtend(request, params), subscriptionArgs, subscribe);
1057
+ // for efficiency, we have two type of returned structure here - if symbols array was provided, then individual
1058
+ // ticker dict comes in, otherwise all-tickers dict comes in
1059
+ if (!symbolsDefined) {
1060
+ return result;
1061
+ }
1062
+ else {
1063
+ const newDict = {};
1064
+ newDict[result['symbol']] = result;
1065
+ return newDict;
1029
1066
  }
1030
- return this.filterByArray(this.tickers, 'symbol', symbols);
1031
1067
  }
1032
1068
  parseWsTicker(message, marketType) {
1033
1069
  //
@@ -1111,11 +1147,24 @@ class binance extends binance$1 {
1111
1147
  'info': message,
1112
1148
  }, market);
1113
1149
  }
1114
- handleTicker(client, message) {
1150
+ handleBidsAsks(client, message) {
1151
+ //
1152
+ // arrives one symbol dict or array of symbol dicts
1153
+ //
1154
+ // {
1155
+ // "u": 7488717758,
1156
+ // "s": "BTCUSDT",
1157
+ // "b": "28621.74000000",
1158
+ // "B": "1.43278800",
1159
+ // "a": "28621.75000000",
1160
+ // "A": "2.52500800"
1161
+ // }
1162
+ //
1163
+ this.handleTickersAndBidsAsks(client, message, 'bidasks');
1164
+ }
1165
+ handleTickers(client, message) {
1115
1166
  //
1116
- // 24hr rolling window ticker statistics for a single symbol
1117
- // These are NOT the statistics of the UTC day, but a 24hr rolling window for the previous 24hrs
1118
- // Update Speed 1000ms
1167
+ // arrives one symbol dict or array of symbol dicts
1119
1168
  //
1120
1169
  // {
1121
1170
  // "e": "24hrTicker", // event type
@@ -1143,39 +1192,14 @@ class binance extends binance$1 {
1143
1192
  // "n": 163222, // total number of trades
1144
1193
  // }
1145
1194
  //
1146
- let event = this.safeString(message, 'e', 'bookTicker');
1147
- if (event === '24hrTicker') {
1148
- event = 'ticker';
1149
- }
1150
- else if (event === '24hrMiniTicker') {
1151
- event = 'miniTicker';
1152
- }
1153
- const wsMarketId = this.safeStringLower(message, 's');
1154
- const messageHash = wsMarketId + '@' + event;
1155
- const isSpot = ((client.url.indexOf('/stream') > -1) || (client.url.indexOf('/testnet.binance') > -1));
1156
- const marketType = (isSpot) ? 'spot' : 'contract';
1157
- const result = this.parseWsTicker(message, marketType);
1158
- const symbol = result['symbol'];
1159
- this.tickers[symbol] = result;
1160
- client.resolve(result, messageHash);
1161
- if (event === 'bookTicker') {
1162
- // watch bookTickers
1163
- client.resolve(result, '!' + 'bookTicker@arr');
1164
- const messageHashes = this.findMessageHashes(client, 'tickers::');
1165
- for (let i = 0; i < messageHashes.length; i++) {
1166
- const currentMessageHash = messageHashes[i];
1167
- const parts = currentMessageHash.split('::');
1168
- const symbolsString = parts[1];
1169
- const symbols = symbolsString.split(',');
1170
- if (this.inArray(symbol, symbols)) {
1171
- client.resolve(result, currentMessageHash);
1172
- }
1173
- }
1174
- }
1195
+ this.handleTickersAndBidsAsks(client, message, 'tickers');
1175
1196
  }
1176
- handleTickers(client, message) {
1197
+ handleTickersAndBidsAsks(client, message, methodType) {
1177
1198
  const isSpot = ((client.url.indexOf('/stream') > -1) || (client.url.indexOf('/testnet.binance') > -1));
1178
1199
  const marketType = (isSpot) ? 'spot' : 'contract';
1200
+ const isBidAsk = (methodType === 'bidasks');
1201
+ let channelName = undefined;
1202
+ const resolvedMessageHashes = [];
1179
1203
  let rawTickers = [];
1180
1204
  const newTickers = {};
1181
1205
  if (Array.isArray(message)) {
@@ -1186,25 +1210,42 @@ class binance extends binance$1 {
1186
1210
  }
1187
1211
  for (let i = 0; i < rawTickers.length; i++) {
1188
1212
  const ticker = rawTickers[i];
1189
- const result = this.parseWsTicker(ticker, marketType);
1190
- const symbol = result['symbol'];
1191
- this.tickers[symbol] = result;
1192
- newTickers[symbol] = result;
1193
- }
1194
- const messageHashes = this.findMessageHashes(client, 'tickers::');
1195
- for (let i = 0; i < messageHashes.length; i++) {
1196
- const messageHash = messageHashes[i];
1197
- const parts = messageHash.split('::');
1198
- const symbolsString = parts[1];
1199
- const symbols = symbolsString.split(',');
1200
- const tickers = this.filterByArray(newTickers, 'symbol', symbols);
1201
- const tickersSymbols = Object.keys(tickers);
1202
- const numTickers = tickersSymbols.length;
1203
- if (numTickers > 0) {
1204
- client.resolve(tickers, messageHash);
1213
+ let event = this.safeString(ticker, 'e');
1214
+ if (isBidAsk) {
1215
+ event = 'bookTicker'; // as noted in `handleMessage`, bookTicker doesn't have identifier, so manually set here
1216
+ }
1217
+ channelName = this.safeString(this.options['tickerChannelsMap'], event, event);
1218
+ if (channelName === undefined) {
1219
+ continue;
1220
+ }
1221
+ const parsedTicker = this.parseWsTicker(ticker, marketType);
1222
+ const symbol = parsedTicker['symbol'];
1223
+ newTickers[symbol] = parsedTicker;
1224
+ if (isBidAsk) {
1225
+ this.bidsasks[symbol] = parsedTicker;
1226
+ }
1227
+ else {
1228
+ this.tickers[symbol] = parsedTicker;
1205
1229
  }
1230
+ const messageHash = this.getMessageHash(channelName, symbol, isBidAsk);
1231
+ resolvedMessageHashes.push(messageHash);
1232
+ client.resolve(parsedTicker, messageHash);
1233
+ }
1234
+ // resolve batch endpoint
1235
+ const length = resolvedMessageHashes.length;
1236
+ if (length > 0) {
1237
+ const batchMessageHash = this.getMessageHash(channelName, undefined, isBidAsk);
1238
+ client.resolve(newTickers, batchMessageHash);
1239
+ }
1240
+ }
1241
+ getMessageHash(channelName, symbol, isBidAsk) {
1242
+ const prefix = isBidAsk ? 'bidask' : 'ticker';
1243
+ if (symbol !== undefined) {
1244
+ return prefix + ':' + channelName + '@' + symbol;
1245
+ }
1246
+ else {
1247
+ return prefix + 's' + ':' + channelName;
1206
1248
  }
1207
- client.resolve(newTickers, 'tickers');
1208
1249
  }
1209
1250
  signParams(params = {}) {
1210
1251
  this.checkRequiredCredentials();
@@ -3009,11 +3050,17 @@ class binance extends binance$1 {
3009
3050
  'kline': this.handleOHLCV,
3010
3051
  'markPrice_kline': this.handleOHLCV,
3011
3052
  'indexPrice_kline': this.handleOHLCV,
3053
+ '1hTicker@arr': this.handleTickers,
3054
+ '4hTicker@arr': this.handleTickers,
3055
+ '1dTicker@arr': this.handleTickers,
3012
3056
  '24hrTicker@arr': this.handleTickers,
3013
3057
  '24hrMiniTicker@arr': this.handleTickers,
3014
- '24hrTicker': this.handleTicker,
3015
- '24hrMiniTicker': this.handleTicker,
3016
- 'bookTicker': this.handleTicker,
3058
+ '1hTicker': this.handleTickers,
3059
+ '4hTicker': this.handleTickers,
3060
+ '1dTicker': this.handleTickers,
3061
+ '24hrTicker': this.handleTickers,
3062
+ '24hrMiniTicker': this.handleTickers,
3063
+ 'bookTicker': this.handleBidsAsks,
3017
3064
  'outboundAccountPosition': this.handleBalance,
3018
3065
  'balanceUpdate': this.handleBalance,
3019
3066
  'ACCOUNT_UPDATE': this.handleAcountUpdate,
@@ -3043,9 +3090,8 @@ class binance extends binance$1 {
3043
3090
  // "A": "2.52500800"
3044
3091
  // }
3045
3092
  //
3046
- if (event === undefined) {
3047
- this.handleTicker(client, message);
3048
- this.handleTickers(client, message);
3093
+ if (event === undefined && ('a' in message) && ('b' in message)) {
3094
+ this.handleBidsAsks(client, message);
3049
3095
  }
3050
3096
  }
3051
3097
  else {
@@ -887,18 +887,17 @@ class kucoin extends kucoin$1 {
887
887
  return this.filterBySymbolSinceLimit(trades, symbol, since, limit, true);
888
888
  }
889
889
  handleMyTrade(client, message) {
890
- let trades = this.myTrades;
891
- if (trades === undefined) {
890
+ if (this.myTrades === undefined) {
892
891
  const limit = this.safeInteger(this.options, 'tradesLimit', 1000);
893
- trades = new Cache.ArrayCacheBySymbolById(limit);
892
+ this.myTrades = new Cache.ArrayCacheBySymbolById(limit);
894
893
  }
895
- const data = this.safeValue(message, 'data');
894
+ const data = this.safeDict(message, 'data');
896
895
  const parsed = this.parseWsTrade(data);
897
- trades.append(parsed);
896
+ this.myTrades.append(parsed);
898
897
  const messageHash = 'myTrades';
899
- client.resolve(trades, messageHash);
898
+ client.resolve(this.myTrades, messageHash);
900
899
  const symbolSpecificMessageHash = messageHash + ':' + parsed['symbol'];
901
- client.resolve(trades, symbolSpecificMessageHash);
900
+ client.resolve(this.myTrades, symbolSpecificMessageHash);
902
901
  }
903
902
  parseWsTrade(trade, market = undefined) {
904
903
  //
@@ -487,14 +487,31 @@ class okx extends okx$1 {
487
487
  * @name okx#watchOrderBookForSymbols
488
488
  * @description watches information on open orders with bid (buy) and ask (sell) prices, volumes and other data
489
489
  * @param {string[]} symbols unified array of symbols
490
- * @param {int} [limit] the maximum amount of order book entries to return
490
+ * @param {int} [limit] 1,5, 400, 50 (l2-tbt, vip4+) or 40000 (vip5+) the maximum amount of order book entries to return
491
491
  * @param {object} [params] extra parameters specific to the exchange API endpoint
492
492
  * @returns {object} A dictionary of [order book structures]{@link https://docs.ccxt.com/#/?id=order-book-structure} indexed by market symbols
493
493
  */
494
494
  await this.loadMarkets();
495
495
  symbols = this.marketSymbols(symbols);
496
496
  const options = this.safeValue(this.options, 'watchOrderBook', {});
497
- const depth = this.safeString(options, 'depth', 'books');
497
+ let depth = this.safeString(options, 'depth', 'books');
498
+ if (limit !== undefined) {
499
+ if (limit === 1) {
500
+ depth = 'bbo-tbt';
501
+ }
502
+ else if (limit > 1 && limit <= 5) {
503
+ depth = 'books5';
504
+ }
505
+ else if (limit === 400) {
506
+ depth = 'books';
507
+ }
508
+ else if (limit === 50) {
509
+ depth = 'books50-l2-tbt'; // Make sure you have VIP4 and above
510
+ }
511
+ else if (limit === 4000) {
512
+ depth = 'books-l2-tbt'; // Make sure you have VIP5 and above
513
+ }
514
+ }
498
515
  if ((depth === 'books-l2-tbt') || (depth === 'books50-l2-tbt')) {
499
516
  await this.authenticate({ 'access': 'public' });
500
517
  }