ccxt 4.5.1 → 4.5.3

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 (73) hide show
  1. package/README.md +110 -112
  2. package/dist/ccxt.browser.min.js +3 -3
  3. package/dist/cjs/ccxt.js +1 -9
  4. package/dist/cjs/src/ascendex.js +1 -1
  5. package/dist/cjs/src/base/Exchange.js +11 -0
  6. package/dist/cjs/src/binance.js +25 -25
  7. package/dist/cjs/src/bitget.js +2 -2
  8. package/dist/cjs/src/coincatch.js +2 -2
  9. package/dist/cjs/src/gate.js +27 -12
  10. package/dist/cjs/src/gemini.js +3 -3
  11. package/dist/cjs/src/htx.js +4 -4
  12. package/dist/cjs/src/indodax.js +11 -12
  13. package/dist/cjs/src/kucoinfutures.js +8 -8
  14. package/dist/cjs/src/mexc.js +30 -1
  15. package/dist/cjs/src/okx.js +19 -5
  16. package/dist/cjs/src/poloniex.js +1 -1
  17. package/dist/cjs/src/pro/binance.js +3 -3
  18. package/dist/cjs/src/pro/bitfinex.js +140 -0
  19. package/dist/cjs/src/pro/bitget.js +222 -42
  20. package/dist/cjs/src/pro/bitmart.js +1 -1
  21. package/dist/cjs/src/pro/bybit.js +3 -3
  22. package/dist/cjs/src/pro/gemini.js +7 -2
  23. package/dist/cjs/src/pro/hyperliquid.js +5 -0
  24. package/dist/cjs/src/pro/kraken.js +4 -6
  25. package/dist/cjs/src/pro/kucoin.js +64 -0
  26. package/dist/cjs/src/pro/mexc.js +7 -3
  27. package/dist/cjs/src/zonda.js +12 -0
  28. package/js/ccxt.d.ts +2 -11
  29. package/js/ccxt.js +2 -8
  30. package/js/src/ascendex.js +1 -1
  31. package/js/src/base/Exchange.d.ts +2 -0
  32. package/js/src/base/Exchange.js +11 -0
  33. package/js/src/binance.d.ts +1 -1
  34. package/js/src/binance.js +25 -25
  35. package/js/src/bitget.js +2 -2
  36. package/js/src/coincatch.js +2 -2
  37. package/js/src/gate.js +27 -12
  38. package/js/src/gemini.js +3 -3
  39. package/js/src/htx.js +4 -4
  40. package/js/src/indodax.js +11 -12
  41. package/js/src/kucoinfutures.js +8 -8
  42. package/js/src/mexc.d.ts +3 -0
  43. package/js/src/mexc.js +30 -1
  44. package/js/src/okx.d.ts +4 -2
  45. package/js/src/okx.js +19 -5
  46. package/js/src/poloniex.js +1 -1
  47. package/js/src/pro/binance.js +3 -3
  48. package/js/src/pro/bitfinex.d.ts +30 -0
  49. package/js/src/pro/bitfinex.js +140 -0
  50. package/js/src/pro/bitget.d.ts +10 -0
  51. package/js/src/pro/bitget.js +228 -42
  52. package/js/src/pro/bitmart.js +1 -1
  53. package/js/src/pro/bybit.d.ts +2 -2
  54. package/js/src/pro/bybit.js +3 -3
  55. package/js/src/pro/gemini.d.ts +1 -1
  56. package/js/src/pro/gemini.js +7 -2
  57. package/js/src/pro/hyperliquid.js +5 -0
  58. package/js/src/pro/kraken.js +4 -6
  59. package/js/src/pro/kucoin.d.ts +22 -0
  60. package/js/src/pro/kucoin.js +64 -0
  61. package/js/src/pro/mexc.js +7 -3
  62. package/js/src/zonda.js +12 -0
  63. package/package.json +2 -1
  64. package/js/src/abstract/ellipx.d.ts +0 -28
  65. package/js/src/abstract/ellipx.js +0 -11
  66. package/js/src/abstract/vertex.d.ts +0 -22
  67. package/js/src/abstract/vertex.js +0 -11
  68. package/js/src/ellipx.d.ts +0 -237
  69. package/js/src/ellipx.js +0 -2071
  70. package/js/src/pro/vertex.d.ts +0 -104
  71. package/js/src/pro/vertex.js +0 -999
  72. package/js/src/vertex.d.ts +0 -346
  73. package/js/src/vertex.js +0 -3146
@@ -64,6 +64,7 @@ export default class bitget extends bitgetRest {
64
64
  // WS timeframes differ from REST timeframes
65
65
  'timeframes': {
66
66
  '1m': '1m',
67
+ '3m': '3m',
67
68
  '5m': '5m',
68
69
  '15m': '15m',
69
70
  '30m': '30m',
@@ -486,11 +487,13 @@ export default class bitget extends bitgetRest {
486
487
  * @description watches historical candlestick data containing the open, high, low, close price, and the volume of a market
487
488
  * @see https://www.bitget.com/api-doc/spot/websocket/public/Candlesticks-Channel
488
489
  * @see https://www.bitget.com/api-doc/contract/websocket/public/Candlesticks-Channel
490
+ * @see https://www.bitget.com/api-doc/uta/websocket/public/Candlesticks-Channel
489
491
  * @param {string} symbol unified symbol of the market to fetch OHLCV data for
490
492
  * @param {string} timeframe the length of time each candle represents
491
493
  * @param {int} [since] timestamp in ms of the earliest candle to fetch
492
494
  * @param {int} [limit] the maximum amount of candles to fetch
493
495
  * @param {object} [params] extra parameters specific to the exchange API endpoint
496
+ * @param {boolean} [params.uta] set to true for the unified trading account (uta), defaults to false
494
497
  * @returns {int[][]} A list of candles ordered as timestamp, open, high, low, close, volume
495
498
  */
496
499
  async watchOHLCV(symbol, timeframe = '1m', since = undefined, limit = undefined, params = {}) {
@@ -499,14 +502,26 @@ export default class bitget extends bitgetRest {
499
502
  symbol = market['symbol'];
500
503
  const timeframes = this.safeValue(this.options, 'timeframes');
501
504
  const interval = this.safeString(timeframes, timeframe);
502
- const messageHash = 'candles:' + timeframe + ':' + symbol;
505
+ let messageHash = undefined;
503
506
  let instType = undefined;
504
- [instType, params] = this.getInstType(market, false, params);
507
+ let uta = undefined;
508
+ [uta, params] = this.handleOptionAndParams(params, 'watchOHLCV', 'uta', false);
509
+ [instType, params] = this.getInstType(market, uta, params);
505
510
  const args = {
506
511
  'instType': instType,
507
- 'channel': 'candle' + interval,
508
- 'instId': market['id'],
509
512
  };
513
+ if (uta) {
514
+ args['topic'] = 'kline';
515
+ args['symbol'] = market['id'];
516
+ args['interval'] = interval;
517
+ params['uta'] = true;
518
+ messageHash = 'kline:' + symbol;
519
+ }
520
+ else {
521
+ args['channel'] = 'candle' + interval;
522
+ args['instId'] = market['id'];
523
+ messageHash = 'candles:' + timeframe + ':' + symbol;
524
+ }
510
525
  const ohlcv = await this.watchPublic(messageHash, args, params);
511
526
  if (this.newUpdates) {
512
527
  limit = ohlcv.getLimit(symbol, limit);
@@ -519,17 +534,46 @@ export default class bitget extends bitgetRest {
519
534
  * @description unsubscribe from the ohlcv channel
520
535
  * @see https://www.bitget.com/api-doc/spot/websocket/public/Candlesticks-Channel
521
536
  * @see https://www.bitget.com/api-doc/contract/websocket/public/Candlesticks-Channel
537
+ * @see https://www.bitget.com/api-doc/uta/websocket/public/Candlesticks-Channel
522
538
  * @param {string} symbol unified symbol of the market to unwatch the ohlcv for
523
539
  * @param {string} [timeframe] the period for the ratio, default is 1 minute
524
540
  * @param {object} [params] extra parameters specific to the exchange API endpoint
541
+ * @param {boolean} [params.uta] set to true for the unified trading account (uta), defaults to false
525
542
  * @returns {object} A dictionary of [order book structures]{@link https://docs.ccxt.com/#/?id=order-book-structure} indexed by market symbols
526
543
  */
527
544
  async unWatchOHLCV(symbol, timeframe = '1m', params = {}) {
528
545
  await this.loadMarkets();
529
546
  const timeframes = this.safeDict(this.options, 'timeframes');
530
547
  const interval = this.safeString(timeframes, timeframe);
531
- const channel = 'candle' + interval;
532
- return await this.unWatchChannel(symbol, channel, 'candles:' + timeframe, params);
548
+ let channel = undefined;
549
+ let market = undefined;
550
+ if (symbol !== undefined) {
551
+ market = this.market(symbol);
552
+ }
553
+ let instType = undefined;
554
+ let messageHash = undefined;
555
+ let uta = undefined;
556
+ [uta, params] = this.handleOptionAndParams(params, 'unWatchOHLCV', 'uta', false);
557
+ [instType, params] = this.getInstType(market, uta, params);
558
+ const args = {
559
+ 'instType': instType,
560
+ };
561
+ if (uta) {
562
+ channel = 'kline';
563
+ args['topic'] = channel;
564
+ args['symbol'] = market['id'];
565
+ args['interval'] = interval;
566
+ params['uta'] = true;
567
+ params['interval'] = interval;
568
+ messageHash = channel + symbol;
569
+ }
570
+ else {
571
+ channel = 'candle' + interval;
572
+ args['channel'] = channel;
573
+ args['instId'] = market['id'];
574
+ messageHash = 'candles:' + interval;
575
+ }
576
+ return await this.unWatchChannel(symbol, channel, messageHash, params);
533
577
  }
534
578
  handleOHLCV(client, message) {
535
579
  //
@@ -565,15 +609,47 @@ export default class bitget extends bitgetRest {
565
609
  // "ts": 1701901610417
566
610
  // }
567
611
  //
612
+ // uta
613
+ //
614
+ // {
615
+ // "action": "snapshot",
616
+ // "arg": {
617
+ // "instType": "usdt-futures",
618
+ // "topic": "kline",
619
+ // "symbol": "BTCUSDT",
620
+ // "interval": "1m"
621
+ // },
622
+ // "data": [
623
+ // {
624
+ // "start": "1755564480000",
625
+ // "open": "116286",
626
+ // "close": "116256.2",
627
+ // "high": "116310.2",
628
+ // "low": "116232.8",
629
+ // "volume": "39.7062",
630
+ // "turnover": "4616746.46654"
631
+ // },
632
+ // ],
633
+ // "ts": 1755594421877
634
+ // }
635
+ //
568
636
  const arg = this.safeValue(message, 'arg', {});
569
- const instType = this.safeString(arg, 'instType');
570
- const marketType = (instType === 'SPOT') ? 'spot' : 'contract';
571
- const marketId = this.safeString(arg, 'instId');
637
+ const instType = this.safeStringLower(arg, 'instType');
638
+ const marketType = (instType === 'spot') ? 'spot' : 'contract';
639
+ const marketId = this.safeString2(arg, 'instId', 'symbol');
572
640
  const market = this.safeMarket(marketId, undefined, undefined, marketType);
573
641
  const symbol = market['symbol'];
574
642
  this.ohlcvs[symbol] = this.safeValue(this.ohlcvs, symbol, {});
575
- const channel = this.safeString(arg, 'channel');
576
- const interval = channel.replace('candle', '');
643
+ const channel = this.safeString2(arg, 'channel', 'topic');
644
+ let interval = this.safeString(arg, 'interval');
645
+ let isUta = undefined;
646
+ if (interval === undefined) {
647
+ isUta = false;
648
+ interval = channel.replace('candle', '');
649
+ }
650
+ else {
651
+ isUta = true;
652
+ }
577
653
  const timeframes = this.safeValue(this.options, 'timeframes');
578
654
  const timeframe = this.findTimeframe(interval, timeframes);
579
655
  let stored = this.safeValue(this.ohlcvs[symbol], timeframe);
@@ -587,7 +663,13 @@ export default class bitget extends bitgetRest {
587
663
  const parsed = this.parseWsOHLCV(data[i], market);
588
664
  stored.append(parsed);
589
665
  }
590
- const messageHash = 'candles:' + timeframe + ':' + symbol;
666
+ let messageHash = undefined;
667
+ if (isUta) {
668
+ messageHash = 'kline:' + symbol;
669
+ }
670
+ else {
671
+ messageHash = 'candles:' + timeframe + ':' + symbol;
672
+ }
591
673
  client.resolve(stored, messageHash);
592
674
  }
593
675
  parseWsOHLCV(ohlcv, market = undefined) {
@@ -603,14 +685,26 @@ export default class bitget extends bitgetRest {
603
685
  // "437404.105512" // USDT volume
604
686
  // ]
605
687
  //
688
+ // uta
689
+ //
690
+ // {
691
+ // "start": "1755564480000",
692
+ // "open": "116286",
693
+ // "close": "116256.2",
694
+ // "high": "116310.2",
695
+ // "low": "116232.8",
696
+ // "volume": "39.7062",
697
+ // "turnover": "4616746.46654"
698
+ // }
699
+ //
606
700
  const volumeIndex = (market['inverse']) ? 6 : 5;
607
701
  return [
608
- this.safeInteger(ohlcv, 0),
609
- this.safeNumber(ohlcv, 1),
610
- this.safeNumber(ohlcv, 2),
611
- this.safeNumber(ohlcv, 3),
612
- this.safeNumber(ohlcv, 4),
613
- this.safeNumber(ohlcv, volumeIndex),
702
+ this.safeInteger2(ohlcv, 'start', 0),
703
+ this.safeNumber2(ohlcv, 'open', 1),
704
+ this.safeNumber2(ohlcv, 'high', 2),
705
+ this.safeNumber2(ohlcv, 'low', 3),
706
+ this.safeNumber2(ohlcv, 'close', 4),
707
+ this.safeNumber2(ohlcv, 'volume', volumeIndex),
614
708
  ];
615
709
  }
616
710
  /**
@@ -653,12 +747,23 @@ export default class bitget extends bitgetRest {
653
747
  const market = this.market(symbol);
654
748
  const messageHash = 'unsubscribe:' + messageHashTopic + ':' + market['symbol'];
655
749
  let instType = undefined;
656
- [instType, params] = this.getInstType(market, false, params);
750
+ let uta = undefined;
751
+ [uta, params] = this.handleOptionAndParams(params, 'unWatchChannel', 'uta', false);
752
+ [instType, params] = this.getInstType(market, uta, params);
657
753
  const args = {
658
754
  'instType': instType,
659
- 'channel': channel,
660
- 'instId': market['id'],
661
755
  };
756
+ if (uta) {
757
+ args['topic'] = channel;
758
+ args['symbol'] = market['id'];
759
+ args['interval'] = this.safeString(params, 'interval', '1m');
760
+ params['uta'] = true;
761
+ params = this.omit(params, 'interval');
762
+ }
763
+ else {
764
+ args['channel'] = channel;
765
+ args['instId'] = market['id'];
766
+ }
662
767
  return await this.unWatchPublic(messageHash, args, params);
663
768
  }
664
769
  /**
@@ -824,10 +929,12 @@ export default class bitget extends bitgetRest {
824
929
  * @description get the list of most recent trades for a particular symbol
825
930
  * @see https://www.bitget.com/api-doc/spot/websocket/public/Trades-Channel
826
931
  * @see https://www.bitget.com/api-doc/contract/websocket/public/New-Trades-Channel
932
+ * @see https://www.bitget.com/api-doc/uta/websocket/public/New-Trades-Channel
827
933
  * @param {string} symbol unified symbol of the market to fetch trades for
828
934
  * @param {int} [since] timestamp in ms of the earliest trade to fetch
829
935
  * @param {int} [limit] the maximum amount of trades to fetch
830
936
  * @param {object} [params] extra parameters specific to the exchange API endpoint
937
+ * @param {boolean} [params.uta] set to true for the unified trading account (uta), defaults to false
831
938
  * @returns {object[]} a list of [trade structures]{@link https://docs.ccxt.com/#/?id=public-trades}
832
939
  */
833
940
  async watchTrades(symbol, since = undefined, limit = undefined, params = {}) {
@@ -839,10 +946,12 @@ export default class bitget extends bitgetRest {
839
946
  * @description get the list of most recent trades for a particular symbol
840
947
  * @see https://www.bitget.com/api-doc/spot/websocket/public/Trades-Channel
841
948
  * @see https://www.bitget.com/api-doc/contract/websocket/public/New-Trades-Channel
949
+ * @see https://www.bitget.com/api-doc/uta/websocket/public/New-Trades-Channel
842
950
  * @param {string[]} symbols unified symbol of the market to fetch trades for
843
951
  * @param {int} [since] timestamp in ms of the earliest trade to fetch
844
952
  * @param {int} [limit] the maximum amount of trades to fetch
845
953
  * @param {object} [params] extra parameters specific to the exchange API endpoint
954
+ * @param {boolean} [params.uta] set to true for the unified trading account (uta), defaults to false
846
955
  * @returns {object[]} a list of [trade structures]{@link https://docs.ccxt.com/#/?id=public-trades}
847
956
  */
848
957
  async watchTradesForSymbols(symbols, since = undefined, limit = undefined, params = {}) {
@@ -852,21 +961,28 @@ export default class bitget extends bitgetRest {
852
961
  }
853
962
  await this.loadMarkets();
854
963
  symbols = this.marketSymbols(symbols);
964
+ let uta = undefined;
965
+ [uta, params] = this.handleOptionAndParams(params, 'watchTradesForSymbols', 'uta', false);
855
966
  const topics = [];
856
967
  const messageHashes = [];
857
968
  for (let i = 0; i < symbols.length; i++) {
858
969
  const symbol = symbols[i];
859
970
  const market = this.market(symbol);
860
971
  let instType = undefined;
861
- [instType, params] = this.getInstType(market, false, params);
972
+ [instType, params] = this.getInstType(market, uta, params);
862
973
  const args = {
863
974
  'instType': instType,
864
- 'channel': 'trade',
865
- 'instId': market['id'],
866
975
  };
976
+ const topicOrChannel = uta ? 'topic' : 'channel';
977
+ const symbolOrInstId = uta ? 'symbol' : 'instId';
978
+ args[topicOrChannel] = uta ? 'publicTrade' : 'trade';
979
+ args[symbolOrInstId] = market['id'];
867
980
  topics.push(args);
868
981
  messageHashes.push('trade:' + symbol);
869
982
  }
983
+ if (uta) {
984
+ params['uta'] = true;
985
+ }
870
986
  const trades = await this.watchPublicMultiple(messageHashes, topics, params);
871
987
  if (this.newUpdates) {
872
988
  const first = this.safeValue(trades, 0);
@@ -887,13 +1003,17 @@ export default class bitget extends bitgetRest {
887
1003
  * @description unsubscribe from the trades channel
888
1004
  * @see https://www.bitget.com/api-doc/spot/websocket/public/Trades-Channel
889
1005
  * @see https://www.bitget.com/api-doc/contract/websocket/public/New-Trades-Channel
1006
+ * @see https://www.bitget.com/api-doc/uta/websocket/public/New-Trades-Channel
890
1007
  * @param {string} symbol unified symbol of the market to unwatch the trades for
891
1008
  * @param {object} [params] extra parameters specific to the exchange API endpoint
1009
+ * @param {boolean} [params.uta] set to true for the unified trading account (uta), defaults to false
892
1010
  * @returns {any} status of the unwatch request
893
1011
  */
894
1012
  async unWatchTrades(symbol, params = {}) {
895
- await this.loadMarkets();
896
- return await this.unWatchChannel(symbol, 'trade', 'trade', params);
1013
+ let uta = undefined;
1014
+ [uta, params] = this.handleOptionAndParams(params, 'unWatchTrades', 'uta', false);
1015
+ const channelTopic = uta ? 'publicTrade' : 'trade';
1016
+ return await this.unWatchChannel(symbol, channelTopic, 'trade', params);
897
1017
  }
898
1018
  handleTrades(client, message) {
899
1019
  //
@@ -912,10 +1032,28 @@ export default class bitget extends bitgetRest {
912
1032
  // "ts": 1701910980730
913
1033
  // }
914
1034
  //
1035
+ // uta
1036
+ //
1037
+ // {
1038
+ // "action": "snapshot",
1039
+ // "arg": { "instType": "spot", "topic": "publicTrade", "symbol": "BTCUSDT" },
1040
+ // "data": [
1041
+ // {
1042
+ // "T": "1756287827920",
1043
+ // "P": "110878.5",
1044
+ // "v": "0.07",
1045
+ // "S": "buy",
1046
+ // "L": "1344534089797185550"
1047
+ // "i": "1344534089797185549"
1048
+ // },
1049
+ // ],
1050
+ // "ts": 1701910980730
1051
+ // }
1052
+ //
915
1053
  const arg = this.safeValue(message, 'arg', {});
916
- const instType = this.safeString(arg, 'instType');
917
- const marketType = (instType === 'SPOT') ? 'spot' : 'contract';
918
- const marketId = this.safeString(arg, 'instId');
1054
+ const instType = this.safeStringLower(arg, 'instType');
1055
+ const marketType = (instType === 'spot') ? 'spot' : 'contract';
1056
+ const marketId = this.safeString2(arg, 'instId', 'symbol');
919
1057
  const market = this.safeMarket(marketId, undefined, undefined, marketType);
920
1058
  const symbol = market['symbol'];
921
1059
  let stored = this.safeValue(this.trades, symbol);
@@ -994,13 +1132,24 @@ export default class bitget extends bitgetRest {
994
1132
  // "uTime": "1714471204194"
995
1133
  // }
996
1134
  //
1135
+ // uta
1136
+ //
1137
+ // {
1138
+ // "i": "1344534089797185549", // Fill execution ID
1139
+ // "L": "1344534089797185550", // Execution correlation ID
1140
+ // "p": "110878.5", // Fill price
1141
+ // "v": "0.07", // Fill size
1142
+ // "S": "buy", // Fill side
1143
+ // "T": "1756287827920" // Fill timestamp
1144
+ // }
1145
+ //
997
1146
  const instId = this.safeString2(trade, 'symbol', 'instId');
998
1147
  const posMode = this.safeString(trade, 'posMode');
999
1148
  const defaultType = (posMode !== undefined) ? 'contract' : 'spot';
1000
1149
  if (market === undefined) {
1001
1150
  market = this.safeMarket(instId, undefined, undefined, defaultType);
1002
1151
  }
1003
- const timestamp = this.safeIntegerN(trade, ['uTime', 'cTime', 'ts']);
1152
+ const timestamp = this.safeIntegerN(trade, ['uTime', 'cTime', 'ts', 'T']);
1004
1153
  const feeDetail = this.safeList(trade, 'feeDetail', []);
1005
1154
  const first = this.safeDict(feeDetail, 0);
1006
1155
  let fee = undefined;
@@ -1014,16 +1163,16 @@ export default class bitget extends bitgetRest {
1014
1163
  }
1015
1164
  return this.safeTrade({
1016
1165
  'info': trade,
1017
- 'id': this.safeString(trade, 'tradeId'),
1018
- 'order': this.safeString(trade, 'orderId'),
1166
+ 'id': this.safeString2(trade, 'tradeId', 'i'),
1167
+ 'order': this.safeString2(trade, 'orderId', 'L'),
1019
1168
  'timestamp': timestamp,
1020
1169
  'datetime': this.iso8601(timestamp),
1021
1170
  'symbol': market['symbol'],
1022
1171
  'type': this.safeString(trade, 'orderType'),
1023
- 'side': this.safeString(trade, 'side'),
1172
+ 'side': this.safeString2(trade, 'side', 'S'),
1024
1173
  'takerOrMaker': this.safeString(trade, 'tradeScope'),
1025
- 'price': this.safeString2(trade, 'priceAvg', 'price'),
1026
- 'amount': this.safeString2(trade, 'size', 'baseVolume'),
1174
+ 'price': this.safeStringN(trade, ['priceAvg', 'price', 'P']),
1175
+ 'amount': this.safeStringN(trade, ['size', 'baseVolume', 'v']),
1027
1176
  'cost': this.safeString2(trade, 'amount', 'quoteVolume'),
1028
1177
  'fee': fee,
1029
1178
  }, market);
@@ -2115,6 +2264,18 @@ export default class bitget extends bitgetRest {
2115
2264
  // "ts": 1753230479687
2116
2265
  // }
2117
2266
  //
2267
+ // unsubscribe
2268
+ //
2269
+ // {
2270
+ // "event": "unsubscribe",
2271
+ // "arg": {
2272
+ // "instType": "spot",
2273
+ // "topic": "kline",
2274
+ // "symbol": "BTCUSDT",
2275
+ // "interval": "1m"
2276
+ // }
2277
+ // }
2278
+ //
2118
2279
  if (this.handleErrorMessage(client, message)) {
2119
2280
  return;
2120
2281
  }
@@ -2143,6 +2304,7 @@ export default class bitget extends bitgetRest {
2143
2304
  const methods = {
2144
2305
  'ticker': this.handleTicker,
2145
2306
  'trade': this.handleTrades,
2307
+ 'publicTrade': this.handleTrades,
2146
2308
  'fill': this.handleMyTrades,
2147
2309
  'orders': this.handleOrder,
2148
2310
  'ordersAlgo': this.handleOrder,
@@ -2153,6 +2315,7 @@ export default class bitget extends bitgetRest {
2153
2315
  'positions': this.handlePositions,
2154
2316
  'account-isolated': this.handleBalance,
2155
2317
  'account-crossed': this.handleBalance,
2318
+ 'kline': this.handleOHLCV,
2156
2319
  };
2157
2320
  const arg = this.safeValue(message, 'arg', {});
2158
2321
  const topic = this.safeValue2(arg, 'channel', 'topic', '');
@@ -2215,7 +2378,7 @@ export default class bitget extends bitgetRest {
2215
2378
  const arg = this.safeDict(message, 'arg', {});
2216
2379
  const instType = this.safeStringLower(arg, 'instType');
2217
2380
  const type = (instType === 'spot') ? 'spot' : 'contract';
2218
- const instId = this.safeString(arg, 'instId');
2381
+ const instId = this.safeString2(arg, 'instId', 'symbol');
2219
2382
  const market = this.safeMarket(instId, undefined, undefined, type);
2220
2383
  const symbol = market['symbol'];
2221
2384
  const messageHash = 'unsubscribe:trade:' + market['symbol'];
@@ -2262,18 +2425,38 @@ export default class bitget extends bitgetRest {
2262
2425
  //
2263
2426
  // {"event":"unsubscribe","arg":{"instType":"SPOT","channel":"candle1m","instId":"BTCUSDT"}}
2264
2427
  //
2428
+ // UTA
2429
+ //
2430
+ // {"event":"unsubscribe","arg":{"instType":"spot","topic":"kline","symbol":"BTCUSDT","interval":"1m"}}
2431
+ //
2265
2432
  const arg = this.safeDict(message, 'arg', {});
2266
2433
  const instType = this.safeStringLower(arg, 'instType');
2267
2434
  const type = (instType === 'spot') ? 'spot' : 'contract';
2268
- const instId = this.safeString(arg, 'instId');
2269
- const channel = this.safeString(arg, 'channel');
2270
- const interval = channel.replace('candle', '');
2435
+ const instId = this.safeString2(arg, 'instId', 'symbol');
2436
+ const channel = this.safeString2(arg, 'channel', 'topic');
2437
+ let interval = this.safeString(arg, 'interval');
2438
+ let isUta = undefined;
2439
+ if (interval === undefined) {
2440
+ isUta = false;
2441
+ interval = channel.replace('candle', '');
2442
+ }
2443
+ else {
2444
+ isUta = true;
2445
+ }
2271
2446
  const timeframes = this.safeValue(this.options, 'timeframes');
2272
2447
  const timeframe = this.findTimeframe(interval, timeframes);
2273
2448
  const market = this.safeMarket(instId, undefined, undefined, type);
2274
2449
  const symbol = market['symbol'];
2275
- const messageHash = 'unsubscribe:candles:' + timeframe + ':' + market['symbol'];
2276
- const subMessageHash = 'candles:' + timeframe + ':' + symbol;
2450
+ let messageHash = undefined;
2451
+ let subMessageHash = undefined;
2452
+ if (isUta) {
2453
+ messageHash = 'unsubscribe:kline:' + symbol;
2454
+ subMessageHash = 'kline:' + symbol;
2455
+ }
2456
+ else {
2457
+ messageHash = 'unsubscribe:candles:' + timeframe + ':' + symbol;
2458
+ subMessageHash = 'candles:' + timeframe + ':' + symbol;
2459
+ }
2277
2460
  if (symbol in this.ohlcvs) {
2278
2461
  if (timeframe in this.ohlcvs[symbol]) {
2279
2462
  delete this.ohlcvs[symbol][timeframe];
@@ -2312,7 +2495,7 @@ export default class bitget extends bitgetRest {
2312
2495
  // for now only unWatchOrderBook is supporteod
2313
2496
  this.handleOrderBookUnSubscription(client, message);
2314
2497
  }
2315
- else if (channel === 'trade') {
2498
+ else if ((channel === 'trade') || (channel === 'publicTrade')) {
2316
2499
  this.handleTradesUnSubscription(client, message);
2317
2500
  }
2318
2501
  else if (channel === 'ticker') {
@@ -2321,6 +2504,9 @@ export default class bitget extends bitgetRest {
2321
2504
  else if (channel.startsWith('candle')) {
2322
2505
  this.handleOHLCVUnSubscription(client, message);
2323
2506
  }
2507
+ else if (channel.startsWith('kline')) {
2508
+ this.handleOHLCVUnSubscription(client, message);
2509
+ }
2324
2510
  }
2325
2511
  return message;
2326
2512
  }
@@ -220,7 +220,7 @@ export default class bitmart extends bitmartRest {
220
220
  // "fz_bal":"0.100000000000000000000000000000"
221
221
  // }
222
222
  // ],
223
- // "event_time":"1701632345415",
223
+ // "event_time":"1701632345416",
224
224
  // "event_type":"TRANSACTION_COMPLETED"
225
225
  // }
226
226
  // ],
@@ -117,11 +117,11 @@ export default class bybit extends bybitRest {
117
117
  * @description unWatches a price ticker
118
118
  * @see https://bybit-exchange.github.io/docs/v5/websocket/public/ticker
119
119
  * @see https://bybit-exchange.github.io/docs/v5/websocket/public/etp-ticker
120
- * @param {string[]} symbols unified symbol of the market to fetch the ticker for
120
+ * @param {string[]} symbol unified symbol of the market to fetch the ticker for
121
121
  * @param {object} [params] extra parameters specific to the exchange API endpoint
122
122
  * @returns {object} a [ticker structure]{@link https://docs.ccxt.com/#/?id=ticker-structure}
123
123
  */
124
- unWatchTicker(symbols: string, params?: {}): Promise<any>;
124
+ unWatchTicker(symbol: string, params?: {}): Promise<any>;
125
125
  handleTicker(client: Client, message: any): void;
126
126
  /**
127
127
  * @method
@@ -446,13 +446,13 @@ export default class bybit extends bybitRest {
446
446
  * @description unWatches a price ticker
447
447
  * @see https://bybit-exchange.github.io/docs/v5/websocket/public/ticker
448
448
  * @see https://bybit-exchange.github.io/docs/v5/websocket/public/etp-ticker
449
- * @param {string[]} symbols unified symbol of the market to fetch the ticker for
449
+ * @param {string[]} symbol unified symbol of the market to fetch the ticker for
450
450
  * @param {object} [params] extra parameters specific to the exchange API endpoint
451
451
  * @returns {object} a [ticker structure]{@link https://docs.ccxt.com/#/?id=ticker-structure}
452
452
  */
453
- async unWatchTicker(symbols, params = {}) {
453
+ async unWatchTicker(symbol, params = {}) {
454
454
  await this.loadMarkets();
455
- return await this.unWatchTickers([symbols], params);
455
+ return await this.unWatchTickers([symbol], params);
456
456
  }
457
457
  handleTicker(client, message) {
458
458
  //
@@ -79,7 +79,7 @@ export default class gemini extends geminiRest {
79
79
  */
80
80
  watchBidsAsks(symbols?: Strings, params?: {}): Promise<Tickers>;
81
81
  handleBidsAsksForMultidata(client: Client, rawBidAskChanges: any, timestamp: Int, nonce: Int): void;
82
- helperForWatchMultipleConstruct(itemHashName: string, symbols: string[], params?: {}): Promise<any>;
82
+ helperForWatchMultipleConstruct(itemHashName: string, symbols?: string[], params?: {}): Promise<any>;
83
83
  handleOrderBookForMultidata(client: Client, rawOrderBookChanges: any, timestamp: Int, nonce: Int): void;
84
84
  handleL2Updates(client: Client, message: any): void;
85
85
  /**
@@ -491,11 +491,16 @@ export default class gemini extends geminiRest {
491
491
  currentBidAsk['timestamp'] = timestamp;
492
492
  currentBidAsk['datetime'] = this.iso8601(timestamp);
493
493
  currentBidAsk['info'] = rawBidAskChanges;
494
+ const bidsAsksDict = {};
495
+ bidsAsksDict[symbol] = currentBidAsk;
494
496
  this.bidsasks[symbol] = currentBidAsk;
495
- client.resolve(currentBidAsk, messageHash);
497
+ client.resolve(bidsAsksDict, messageHash);
496
498
  }
497
- async helperForWatchMultipleConstruct(itemHashName, symbols, params = {}) {
499
+ async helperForWatchMultipleConstruct(itemHashName, symbols = undefined, params = {}) {
498
500
  await this.loadMarkets();
501
+ if (symbols === undefined) {
502
+ throw new NotSupported(this.id + ' watchMultiple requires at least one symbol');
503
+ }
499
504
  symbols = this.marketSymbols(symbols, undefined, false, true, true);
500
505
  const firstMarket = this.market(symbols[0]);
501
506
  if (!firstMarket['spot'] && !firstMarket['linear']) {
@@ -99,6 +99,11 @@ export default class hyperliquid extends hyperliquidRest {
99
99
  await this.loadMarkets();
100
100
  const [order, globalParams] = this.parseCreateEditOrderArgs(undefined, symbol, type, side, amount, price, params);
101
101
  const orders = await this.createOrdersWs([order], globalParams);
102
+ const ordersLength = orders.length;
103
+ if (ordersLength === 0) {
104
+ // not sure why but it is happening sometimes
105
+ return this.safeOrder({});
106
+ }
102
107
  const parsedOrder = orders[0];
103
108
  return parsedOrder;
104
109
  }
@@ -1710,7 +1710,7 @@ export default class kraken extends krakenRest {
1710
1710
  //
1711
1711
  const errorMessage = this.safeString2(message, 'errorMessage', 'error');
1712
1712
  if (errorMessage !== undefined) {
1713
- // const requestId = this.safeValue2 (message, 'reqid', 'req_id');
1713
+ const requestId = this.safeString2(message, 'reqid', 'req_id');
1714
1714
  const broad = this.exceptions['ws']['broad'];
1715
1715
  const broadKey = this.findBroadlyMatchedKey(broad, errorMessage);
1716
1716
  let exception = undefined;
@@ -1720,11 +1720,9 @@ export default class kraken extends krakenRest {
1720
1720
  else {
1721
1721
  exception = new broad[broadKey](errorMessage);
1722
1722
  }
1723
- // if (requestId !== undefined) {
1724
- // client.reject (exception, requestId);
1725
- // } else {
1726
- client.reject(exception);
1727
- // }
1723
+ if (requestId !== undefined) {
1724
+ client.reject(exception, requestId);
1725
+ }
1728
1726
  return false;
1729
1727
  }
1730
1728
  return true;
@@ -7,6 +7,7 @@ export default class kucoin extends kucoinRest {
7
7
  negotiateHelper(privateChannel: any, params?: {}): Promise<string>;
8
8
  requestId(): any;
9
9
  subscribe(url: any, messageHash: any, subscriptionHash: any, params?: {}, subscription?: any): Promise<any>;
10
+ unSubscribe(url: any, messageHash: any, topic: any, subscriptionHash: any, params?: {}, subscription?: Dict): Promise<any>;
10
11
  subscribeMultiple(url: any, messageHashes: any, topic: any, subscriptionHashes: any, params?: {}, subscription?: any): Promise<any>;
11
12
  unSubscribeMultiple(url: any, messageHashes: any, topic: any, subscriptionHashes: any, params?: {}, subscription?: Dict): Promise<any>;
12
13
  /**
@@ -19,6 +20,16 @@ export default class kucoin extends kucoinRest {
19
20
  * @returns {object} a [ticker structure]{@link https://docs.ccxt.com/#/?id=ticker-structure}
20
21
  */
21
22
  watchTicker(symbol: string, params?: {}): Promise<Ticker>;
23
+ /**
24
+ * @method
25
+ * @name kucoin#unWatchTicker
26
+ * @description unWatches a price ticker, a statistical calculation with the information calculated over the past 24 hours for a specific market
27
+ * @see https://www.kucoin.com/docs/websocket/spot-trading/public-channels/market-snapshot
28
+ * @param {string} symbol unified symbol of the market to fetch the ticker for
29
+ * @param {object} [params] extra parameters specific to the exchange API endpoint
30
+ * @returns {object} a [ticker structure]{@link https://docs.ccxt.com/#/?id=ticker-structure}
31
+ */
32
+ unWatchTicker(symbol: string, params?: {}): Promise<Ticker>;
22
33
  /**
23
34
  * @method
24
35
  * @name kucoin#watchTickers
@@ -57,6 +68,17 @@ export default class kucoin extends kucoinRest {
57
68
  * @returns {int[][]} A list of candles ordered as timestamp, open, high, low, close, volume
58
69
  */
59
70
  watchOHLCV(symbol: string, timeframe?: string, since?: Int, limit?: Int, params?: {}): Promise<OHLCV[]>;
71
+ /**
72
+ * @method
73
+ * @name kucoin#unWatchOHLCV
74
+ * @description unWatches historical candlestick data containing the open, high, low, and close price, and the volume of a market
75
+ * @see https://www.kucoin.com/docs/websocket/spot-trading/public-channels/klines
76
+ * @param {string} symbol unified symbol of the market to fetch OHLCV data for
77
+ * @param {string} timeframe the length of time each candle represents
78
+ * @param {object} [params] extra parameters specific to the exchange API endpoint
79
+ * @returns {int[][]} A list of candles ordered as timestamp, open, high, low, close, volume
80
+ */
81
+ unWatchOHLCV(symbol: string, timeframe?: string, params?: {}): Promise<OHLCV[]>;
60
82
  handleOHLCV(client: Client, message: any): void;
61
83
  /**
62
84
  * @method