ccxt 4.3.86 → 4.3.87

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 (41) hide show
  1. package/README.md +6 -5
  2. package/dist/ccxt.browser.min.js +3 -3
  3. package/dist/cjs/ccxt.js +2 -1
  4. package/dist/cjs/src/base/errors.js +8 -1
  5. package/dist/cjs/src/bingx.js +7 -1
  6. package/dist/cjs/src/hashkey.js +3 -4
  7. package/dist/cjs/src/kraken.js +37 -6
  8. package/dist/cjs/src/pro/bitget.js +164 -19
  9. package/dist/cjs/src/pro/p2b.js +34 -7
  10. package/dist/cjs/src/pro/poloniex.js +36 -3
  11. package/dist/cjs/src/pro/poloniexfutures.js +1 -0
  12. package/dist/cjs/src/pro/probit.js +2 -0
  13. package/dist/cjs/src/pro/upbit.js +48 -3
  14. package/dist/cjs/src/pro/vertex.js +1 -0
  15. package/dist/cjs/src/pro/wazirx.js +3 -0
  16. package/dist/cjs/src/pro/whitebit.js +9 -0
  17. package/dist/cjs/src/upbit.js +1 -1
  18. package/js/ccxt.d.ts +3 -3
  19. package/js/ccxt.js +3 -3
  20. package/js/src/base/errorHierarchy.d.ts +1 -0
  21. package/js/src/base/errorHierarchy.js +1 -0
  22. package/js/src/base/errors.d.ts +5 -1
  23. package/js/src/base/errors.js +8 -2
  24. package/js/src/bingx.js +7 -1
  25. package/js/src/hashkey.js +3 -4
  26. package/js/src/kraken.js +37 -6
  27. package/js/src/pro/bitget.d.ts +8 -0
  28. package/js/src/pro/bitget.js +165 -20
  29. package/js/src/pro/p2b.d.ts +1 -0
  30. package/js/src/pro/p2b.js +34 -7
  31. package/js/src/pro/poloniex.d.ts +1 -0
  32. package/js/src/pro/poloniex.js +36 -3
  33. package/js/src/pro/poloniexfutures.js +1 -0
  34. package/js/src/pro/probit.js +2 -0
  35. package/js/src/pro/upbit.d.ts +1 -0
  36. package/js/src/pro/upbit.js +48 -3
  37. package/js/src/pro/vertex.js +1 -0
  38. package/js/src/pro/wazirx.js +3 -0
  39. package/js/src/pro/whitebit.js +9 -0
  40. package/js/src/upbit.js +1 -1
  41. package/package.json +1 -1
@@ -6,7 +6,7 @@
6
6
 
7
7
  // ---------------------------------------------------------------------------
8
8
  import bitgetRest from '../bitget.js';
9
- import { AuthenticationError, BadRequest, ArgumentsRequired, ChecksumError, ExchangeError, RateLimitExceeded } from '../base/errors.js';
9
+ import { AuthenticationError, BadRequest, ArgumentsRequired, ChecksumError, ExchangeError, RateLimitExceeded, UnsubscribeError } from '../base/errors.js';
10
10
  import { Precise } from '../base/Precise.js';
11
11
  import { ArrayCache, ArrayCacheBySymbolById, ArrayCacheBySymbolBySide, ArrayCacheByTimestamp } from '../base/ws/Cache.js';
12
12
  import { sha256 } from '../static_dependencies/noble-hashes/sha256.js';
@@ -134,6 +134,19 @@ export default class bitget extends bitgetRest {
134
134
  };
135
135
  return await this.watchPublic(messageHash, args, params);
136
136
  }
137
+ async unWatchTicker(symbol, params = {}) {
138
+ /**
139
+ * @method
140
+ * @name bitget#unWatchTicker
141
+ * @description unsubscribe from the ticker channel
142
+ * @see https://www.bitget.com/api-doc/spot/websocket/public/Tickers-Channel
143
+ * @see https://www.bitget.com/api-doc/contract/websocket/public/Tickers-Channel
144
+ * @param {string} symbol unified symbol of the market to unwatch the ticker for
145
+ * @returns {any} status of the unwatch request
146
+ */
147
+ await this.loadMarkets();
148
+ return await this.unWatchChannel(symbol, 'ticker', 'ticker', params);
149
+ }
137
150
  async watchTickers(symbols = undefined, params = {}) {
138
151
  /**
139
152
  * @method
@@ -346,6 +359,22 @@ export default class bitget extends bitgetRest {
346
359
  }
347
360
  return this.filterBySinceLimit(ohlcv, since, limit, 0, true);
348
361
  }
362
+ async unWatchOHLCV(symbol, timeframe = '1m', params = {}) {
363
+ /**
364
+ * @method
365
+ * @name bitget#unWatchOHLCV
366
+ * @description unsubscribe from the ohlcv channel
367
+ * @see https://www.bitget.com/api-doc/spot/websocket/public/Candlesticks-Channel
368
+ * @see https://www.bitget.com/api-doc/contract/websocket/public/Candlesticks-Channel
369
+ * @param {string} symbol unified symbol of the market to unwatch the ohlcv for
370
+ * @returns {object} A dictionary of [order book structures]{@link https://docs.ccxt.com/#/?id=order-book-structure} indexed by market symbols
371
+ */
372
+ await this.loadMarkets();
373
+ const timeframes = this.safeDict(this.options, 'timeframes');
374
+ const interval = this.safeString(timeframes, timeframe);
375
+ const channel = 'candle' + interval;
376
+ return await this.unWatchChannel(symbol, channel, 'candles:' + timeframe, params);
377
+ }
349
378
  handleOHLCV(client, message) {
350
379
  //
351
380
  // {
@@ -454,14 +483,18 @@ export default class bitget extends bitgetRest {
454
483
  * @returns {object} A dictionary of [order book structures]{@link https://docs.ccxt.com/#/?id=order-book-structure} indexed by market symbols
455
484
  */
456
485
  await this.loadMarkets();
457
- const market = this.market(symbol);
458
- const messageHash = 'unsubscribe:orderbook:' + market['symbol'];
459
486
  let channel = 'books';
460
487
  const limit = this.safeInteger(params, 'limit');
461
488
  if ((limit === 1) || (limit === 5) || (limit === 15)) {
462
489
  params = this.omit(params, 'limit');
463
490
  channel += limit.toString();
464
491
  }
492
+ return await this.unWatchChannel(symbol, channel, 'orderbook', params);
493
+ }
494
+ async unWatchChannel(symbol, channel, messageHashTopic, params = {}) {
495
+ await this.loadMarkets();
496
+ const market = this.market(symbol);
497
+ const messageHash = 'unsubscribe:' + messageHashTopic + ':' + market['symbol'];
465
498
  let instType = undefined;
466
499
  [instType, params] = this.getInstType(market, params);
467
500
  const args = {
@@ -685,6 +718,19 @@ export default class bitget extends bitgetRest {
685
718
  }
686
719
  return this.filterBySinceLimit(trades, since, limit, 'timestamp', true);
687
720
  }
721
+ async unWatchTrades(symbol, params = {}) {
722
+ /**
723
+ * @method
724
+ * @name bitget#unWatchTrades
725
+ * @description unsubscribe from the trades channel
726
+ * @see https://www.bitget.com/api-doc/spot/websocket/public/Trades-Channel
727
+ * @see https://www.bitget.com/api-doc/contract/websocket/public/New-Trades-Channel
728
+ * @param {string} symbol unified symbol of the market to unwatch the trades for
729
+ * @returns {any} status of the unwatch request
730
+ */
731
+ await this.loadMarkets();
732
+ return await this.unWatchChannel(symbol, 'trade', 'trade', params);
733
+ }
688
734
  handleTrades(client, message) {
689
735
  //
690
736
  // {
@@ -1871,6 +1917,112 @@ export default class bitget extends bitgetRest {
1871
1917
  //
1872
1918
  return message;
1873
1919
  }
1920
+ handleOrderBookUnSubscription(client, message) {
1921
+ //
1922
+ // {"event":"unsubscribe","arg":{"instType":"SPOT","channel":"books","instId":"BTCUSDT"}}
1923
+ //
1924
+ const arg = this.safeDict(message, 'arg', {});
1925
+ const instType = this.safeStringLower(arg, 'instType');
1926
+ const type = (instType === 'spot') ? 'spot' : 'contract';
1927
+ const instId = this.safeString(arg, 'instId');
1928
+ const market = this.safeMarket(instId, undefined, undefined, type);
1929
+ const symbol = market['symbol'];
1930
+ const messageHash = 'unsubscribe:orderbook:' + market['symbol'];
1931
+ const subMessageHash = 'orderbook:' + symbol;
1932
+ if (symbol in this.orderbooks) {
1933
+ delete this.orderbooks[symbol];
1934
+ }
1935
+ if (subMessageHash in client.subscriptions) {
1936
+ delete client.subscriptions[subMessageHash];
1937
+ }
1938
+ if (messageHash in client.subscriptions) {
1939
+ delete client.subscriptions[messageHash];
1940
+ }
1941
+ const error = new UnsubscribeError(this.id + 'orderbook ' + symbol);
1942
+ client.reject(error, subMessageHash);
1943
+ client.resolve(true, messageHash);
1944
+ }
1945
+ handleTradesUnSubscription(client, message) {
1946
+ //
1947
+ // {"event":"unsubscribe","arg":{"instType":"SPOT","channel":"trade","instId":"BTCUSDT"}}
1948
+ //
1949
+ const arg = this.safeDict(message, 'arg', {});
1950
+ const instType = this.safeStringLower(arg, 'instType');
1951
+ const type = (instType === 'spot') ? 'spot' : 'contract';
1952
+ const instId = this.safeString(arg, 'instId');
1953
+ const market = this.safeMarket(instId, undefined, undefined, type);
1954
+ const symbol = market['symbol'];
1955
+ const messageHash = 'unsubscribe:trade:' + market['symbol'];
1956
+ const subMessageHash = 'trade:' + symbol;
1957
+ if (symbol in this.trades) {
1958
+ delete this.trades[symbol];
1959
+ }
1960
+ if (subMessageHash in client.subscriptions) {
1961
+ delete client.subscriptions[subMessageHash];
1962
+ }
1963
+ if (messageHash in client.subscriptions) {
1964
+ delete client.subscriptions[messageHash];
1965
+ }
1966
+ const error = new UnsubscribeError(this.id + 'trades ' + symbol);
1967
+ client.reject(error, subMessageHash);
1968
+ client.resolve(true, messageHash);
1969
+ }
1970
+ handleTickerUnSubscription(client, message) {
1971
+ //
1972
+ // {"event":"unsubscribe","arg":{"instType":"SPOT","channel":"trade","instId":"BTCUSDT"}}
1973
+ //
1974
+ const arg = this.safeDict(message, 'arg', {});
1975
+ const instType = this.safeStringLower(arg, 'instType');
1976
+ const type = (instType === 'spot') ? 'spot' : 'contract';
1977
+ const instId = this.safeString(arg, 'instId');
1978
+ const market = this.safeMarket(instId, undefined, undefined, type);
1979
+ const symbol = market['symbol'];
1980
+ const messageHash = 'unsubscribe:ticker:' + market['symbol'];
1981
+ const subMessageHash = 'ticker:' + symbol;
1982
+ if (symbol in this.tickers) {
1983
+ delete this.tickers[symbol];
1984
+ }
1985
+ if (subMessageHash in client.subscriptions) {
1986
+ delete client.subscriptions[subMessageHash];
1987
+ }
1988
+ if (messageHash in client.subscriptions) {
1989
+ delete client.subscriptions[messageHash];
1990
+ }
1991
+ const error = new UnsubscribeError(this.id + 'ticker ' + symbol);
1992
+ client.reject(error, subMessageHash);
1993
+ client.resolve(true, messageHash);
1994
+ }
1995
+ handleOHLCVUnSubscription(client, message) {
1996
+ //
1997
+ // {"event":"unsubscribe","arg":{"instType":"SPOT","channel":"candle1m","instId":"BTCUSDT"}}
1998
+ //
1999
+ const arg = this.safeDict(message, 'arg', {});
2000
+ const instType = this.safeStringLower(arg, 'instType');
2001
+ const type = (instType === 'spot') ? 'spot' : 'contract';
2002
+ const instId = this.safeString(arg, 'instId');
2003
+ const channel = this.safeString(arg, 'channel');
2004
+ const interval = channel.replace('candle', '');
2005
+ const timeframes = this.safeValue(this.options, 'timeframes');
2006
+ const timeframe = this.findTimeframe(interval, timeframes);
2007
+ const market = this.safeMarket(instId, undefined, undefined, type);
2008
+ const symbol = market['symbol'];
2009
+ const messageHash = 'unsubscribe:candles:' + timeframe + ':' + market['symbol'];
2010
+ const subMessageHash = 'candles:' + timeframe + ':' + symbol;
2011
+ if (symbol in this.ohlcvs) {
2012
+ if (timeframe in this.ohlcvs[symbol]) {
2013
+ delete this.ohlcvs[symbol][timeframe];
2014
+ }
2015
+ }
2016
+ if (subMessageHash in client.subscriptions) {
2017
+ delete client.subscriptions[subMessageHash];
2018
+ }
2019
+ if (messageHash in client.subscriptions) {
2020
+ delete client.subscriptions[messageHash];
2021
+ }
2022
+ const error = new UnsubscribeError(this.id + ' ohlcv ' + timeframe + ' ' + symbol);
2023
+ client.reject(error, subMessageHash);
2024
+ client.resolve(true, messageHash);
2025
+ }
1874
2026
  handleUnSubscriptionStatus(client, message) {
1875
2027
  //
1876
2028
  // {
@@ -1900,23 +2052,16 @@ export default class bitget extends bitgetRest {
1900
2052
  const channel = this.safeString(arg, 'channel');
1901
2053
  if (channel === 'books') {
1902
2054
  // for now only unWatchOrderBook is supporteod
1903
- const instType = this.safeStringLower(arg, 'instType');
1904
- const type = (instType === 'spot') ? 'spot' : 'contract';
1905
- const instId = this.safeString(arg, 'instId');
1906
- const market = this.safeMarket(instId, undefined, undefined, type);
1907
- const symbol = market['symbol'];
1908
- const messageHash = 'unsubscribe:orderbook:' + market['symbol'];
1909
- const subMessageHash = 'orderbook:' + symbol;
1910
- if (symbol in this.orderbooks) {
1911
- delete this.orderbooks[symbol];
1912
- }
1913
- if (subMessageHash in client.subscriptions) {
1914
- delete client.subscriptions[subMessageHash];
1915
- }
1916
- if (messageHash in client.subscriptions) {
1917
- delete client.subscriptions[messageHash];
1918
- }
1919
- client.resolve(true, messageHash);
2055
+ this.handleOrderBookUnSubscription(client, message);
2056
+ }
2057
+ else if (channel === 'trade') {
2058
+ this.handleTradesUnSubscription(client, message);
2059
+ }
2060
+ else if (channel === 'ticker') {
2061
+ this.handleTickerUnSubscription(client, message);
2062
+ }
2063
+ else if (channel.startsWith('candle')) {
2064
+ this.handleOHLCVUnSubscription(client, message);
1920
2065
  }
1921
2066
  }
1922
2067
  return message;
@@ -7,6 +7,7 @@ export default class p2b extends p2bRest {
7
7
  watchOHLCV(symbol: string, timeframe?: string, since?: Int, limit?: Int, params?: {}): Promise<OHLCV[]>;
8
8
  watchTicker(symbol: string, params?: {}): Promise<Ticker>;
9
9
  watchTrades(symbol: string, since?: Int, limit?: Int, params?: {}): Promise<Trade[]>;
10
+ watchTradesForSymbols(symbols: string[], since?: Int, limit?: Int, params?: {}): Promise<Trade[]>;
10
11
  watchOrderBook(symbol: string, limit?: Int, params?: {}): Promise<OrderBook>;
11
12
  handleOHLCV(client: Client, message: any): any;
12
13
  handleTrade(client: Client, message: any): any;
package/js/src/pro/p2b.js CHANGED
@@ -32,6 +32,7 @@ export default class p2b extends p2bRest {
32
32
  'watchTicker': true,
33
33
  'watchTickers': false,
34
34
  'watchTrades': true,
35
+ 'watchTradesForSymbols': true,
35
36
  },
36
37
  'urls': {
37
38
  'api': {
@@ -147,15 +148,41 @@ export default class p2b extends p2bRest {
147
148
  * @param {object} [params] extra parameters specific to the exchange API endpoint
148
149
  * @returns {object[]} a list of [trade structures]{@link https://docs.ccxt.com/#/?id=public-trades}
149
150
  */
151
+ return await this.watchTradesForSymbols([symbol], since, limit, params);
152
+ }
153
+ async watchTradesForSymbols(symbols, since = undefined, limit = undefined, params = {}) {
154
+ /**
155
+ * @method
156
+ * @name p2b#watchTradesForSymbols
157
+ * @description get the list of most recent trades for a list of symbols
158
+ * @see https://github.com/P2B-team/P2B-WSS-Public/blob/main/wss_documentation.md#deals
159
+ * @param {string[]} symbols unified symbol of the market to fetch trades for
160
+ * @param {int} [since] timestamp in ms of the earliest trade to fetch
161
+ * @param {int} [limit] the maximum amount of trades to fetch
162
+ * @param {object} [params] extra parameters specific to the exchange API endpoint
163
+ * @returns {object[]} a list of [trade structures]{@link https://docs.ccxt.com/#/?id=public-trades}
164
+ */
150
165
  await this.loadMarkets();
151
- const market = this.market(symbol);
152
- const request = [
153
- market['id'],
154
- ];
155
- const messageHash = 'deals::' + market['symbol'];
156
- const trades = await this.subscribe('deals.subscribe', messageHash, request, params);
166
+ symbols = this.marketSymbols(symbols, undefined, false, true, true);
167
+ const messageHashes = [];
168
+ if (symbols !== undefined) {
169
+ for (let i = 0; i < symbols.length; i++) {
170
+ messageHashes.push('deals::' + symbols[i]);
171
+ }
172
+ }
173
+ const marketIds = this.marketIds(symbols);
174
+ const url = this.urls['api']['ws'];
175
+ const subscribe = {
176
+ 'method': 'deals.subscribe',
177
+ 'params': marketIds,
178
+ 'id': this.milliseconds(),
179
+ };
180
+ const query = this.extend(subscribe, params);
181
+ const trades = await this.watchMultiple(url, messageHashes, query, messageHashes);
157
182
  if (this.newUpdates) {
158
- limit = trades.getLimit(symbol, limit);
183
+ const first = this.safeValue(trades, 0);
184
+ const tradeSymbol = this.safeString(first, 'symbol');
185
+ limit = trades.getLimit(tradeSymbol, limit);
159
186
  }
160
187
  return this.filterBySinceLimit(trades, since, limit, 'timestamp', true);
161
188
  }
@@ -15,6 +15,7 @@ export default class poloniex extends poloniexRest {
15
15
  watchTicker(symbol: string, params?: {}): Promise<Ticker>;
16
16
  watchTickers(symbols?: Strings, params?: {}): Promise<Tickers>;
17
17
  watchTrades(symbol: string, since?: Int, limit?: Int, params?: {}): Promise<Trade[]>;
18
+ watchTradesForSymbols(symbols: string[], since?: Int, limit?: Int, params?: {}): Promise<Trade[]>;
18
19
  watchOrderBook(symbol: string, limit?: Int, params?: {}): Promise<OrderBook>;
19
20
  watchOrders(symbol?: Str, since?: Int, limit?: Int, params?: {}): Promise<Order[]>;
20
21
  watchMyTrades(symbol?: Str, since?: Int, limit?: Int, params?: {}): Promise<Trade[]>;
@@ -21,6 +21,7 @@ export default class poloniex extends poloniexRest {
21
21
  'watchTicker': true,
22
22
  'watchTickers': true,
23
23
  'watchTrades': true,
24
+ 'watchTradesForSymbols': true,
24
25
  'watchBalance': true,
25
26
  'watchStatus': false,
26
27
  'watchOrders': true,
@@ -398,12 +399,44 @@ export default class poloniex extends poloniexRest {
398
399
  * @param {object} [params] extra parameters specific to the exchange API endpoint
399
400
  * @returns {object[]} a list of [trade structures]{@link https://docs.ccxt.com/#/?id=public-trades}
400
401
  */
402
+ return await this.watchTradesForSymbols([symbol], since, limit, params);
403
+ }
404
+ async watchTradesForSymbols(symbols, since = undefined, limit = undefined, params = {}) {
405
+ /**
406
+ * @method
407
+ * @name poloniex#watchTradesForSymbols
408
+ * @description get the list of most recent trades for a list of symbols
409
+ * @see https://api-docs.poloniex.com/spot/websocket/market-data#trades
410
+ * @param {string[]} symbols unified symbol of the market to fetch trades for
411
+ * @param {int} [since] timestamp in ms of the earliest trade to fetch
412
+ * @param {int} [limit] the maximum amount of trades to fetch
413
+ * @param {object} [params] extra parameters specific to the exchange API endpoint
414
+ * @returns {object[]} a list of [trade structures]{@link https://docs.ccxt.com/#/?id=public-trades}
415
+ */
401
416
  await this.loadMarkets();
402
- symbol = this.symbol(symbol);
417
+ symbols = this.marketSymbols(symbols, undefined, false, true, true);
403
418
  const name = 'trades';
404
- const trades = await this.subscribe(name, name, false, [symbol], params);
419
+ const url = this.urls['api']['ws']['public'];
420
+ const marketIds = this.marketIds(symbols);
421
+ const subscribe = {
422
+ 'event': 'subscribe',
423
+ 'channel': [
424
+ name,
425
+ ],
426
+ 'symbols': marketIds,
427
+ };
428
+ const request = this.extend(subscribe, params);
429
+ const messageHashes = [];
430
+ if (symbols !== undefined) {
431
+ for (let i = 0; i < symbols.length; i++) {
432
+ messageHashes.push(name + '::' + symbols[i]);
433
+ }
434
+ }
435
+ const trades = await this.watchMultiple(url, messageHashes, request, messageHashes);
405
436
  if (this.newUpdates) {
406
- limit = trades.getLimit(symbol, limit);
437
+ const first = this.safeValue(trades, 0);
438
+ const tradeSymbol = this.safeString(first, 'symbol');
439
+ limit = trades.getLimit(tradeSymbol, limit);
407
440
  }
408
441
  return this.filterBySinceLimit(trades, since, limit, 'timestamp', true);
409
442
  }
@@ -28,6 +28,7 @@ export default class poloniexfutures extends poloniexfuturesRest {
28
28
  'watchTicker': true,
29
29
  'watchTickers': false,
30
30
  'watchTrades': true,
31
+ 'watchTradesForSymbols': false,
31
32
  'watchBalance': true,
32
33
  'watchOrders': true,
33
34
  'watchMyTrades': false,
@@ -18,6 +18,7 @@ export default class probit extends probitRest {
18
18
  'watchTicker': true,
19
19
  'watchTickers': false,
20
20
  'watchTrades': true,
21
+ 'watchTradesForSymbols': false,
21
22
  'watchMyTrades': true,
22
23
  'watchOrders': true,
23
24
  'watchOrderBook': true,
@@ -225,6 +226,7 @@ export default class probit extends probitRest {
225
226
  * @method
226
227
  * @name probit#watchMyTrades
227
228
  * @description get the list of trades associated with the user
229
+ * @see https://docs-en.probit.com/reference/trade_history
228
230
  * @param {string} symbol unified symbol of the market to fetch trades for
229
231
  * @param {int} [since] timestamp in ms of the earliest trade to fetch
230
232
  * @param {int} [limit] the maximum amount of trades to fetch
@@ -6,6 +6,7 @@ export default class upbit extends upbitRest {
6
6
  watchPublic(symbol: string, channel: any, params?: {}): Promise<any>;
7
7
  watchTicker(symbol: string, params?: {}): Promise<Ticker>;
8
8
  watchTrades(symbol: string, since?: Int, limit?: Int, params?: {}): Promise<Trade[]>;
9
+ watchTradesForSymbols(symbols: string[], since?: Int, limit?: Int, params?: {}): Promise<Trade[]>;
9
10
  watchOrderBook(symbol: string, limit?: Int, params?: {}): Promise<OrderBook>;
10
11
  handleTicker(client: Client, message: any): void;
11
12
  handleOrderBook(client: Client, message: any): void;
@@ -18,6 +18,7 @@ export default class upbit extends upbitRest {
18
18
  'watchOrderBook': true,
19
19
  'watchTicker': true,
20
20
  'watchTrades': true,
21
+ 'watchTradesForSymbols': true,
21
22
  'watchOrders': true,
22
23
  'watchMyTrades': true,
23
24
  'watchBalance': true,
@@ -82,11 +83,55 @@ export default class upbit extends upbitRest {
82
83
  * @param {object} [params] extra parameters specific to the exchange API endpoint
83
84
  * @returns {object[]} a list of [trade structures]{@link https://docs.ccxt.com/#/?id=public-trades}
84
85
  */
86
+ return await this.watchTradesForSymbols([symbol], since, limit, params);
87
+ }
88
+ async watchTradesForSymbols(symbols, since = undefined, limit = undefined, params = {}) {
89
+ /**
90
+ * @method
91
+ * @name upbit#watchTradesForSymbols
92
+ * @description get the list of most recent trades for a list of symbols
93
+ * @see https://global-docs.upbit.com/reference/websocket-trade
94
+ * @param {string[]} symbols unified symbol of the market to fetch trades for
95
+ * @param {int} [since] timestamp in ms of the earliest trade to fetch
96
+ * @param {int} [limit] the maximum amount of trades to fetch
97
+ * @param {object} [params] extra parameters specific to the exchange API endpoint
98
+ * @returns {object[]} a list of [trade structures]{@link https://docs.ccxt.com/#/?id=public-trades}
99
+ */
85
100
  await this.loadMarkets();
86
- symbol = this.symbol(symbol);
87
- const trades = await this.watchPublic(symbol, 'trade');
101
+ symbols = this.marketSymbols(symbols, undefined, false, true, true);
102
+ const channel = 'trade';
103
+ const messageHashes = [];
104
+ const url = this.implodeParams(this.urls['api']['ws'], {
105
+ 'hostname': this.hostname,
106
+ });
107
+ if (symbols !== undefined) {
108
+ for (let i = 0; i < symbols.length; i++) {
109
+ const market = this.market(symbols[i]);
110
+ const marketId = market['id'];
111
+ const symbol = market['symbol'];
112
+ this.options[channel] = this.safeValue(this.options, channel, {});
113
+ this.options[channel][symbol] = true;
114
+ messageHashes.push(channel + ':' + marketId);
115
+ }
116
+ }
117
+ const optionSymbols = Object.keys(this.options[channel]);
118
+ const marketIds = this.marketIds(optionSymbols);
119
+ const request = [
120
+ {
121
+ 'ticket': this.uuid(),
122
+ },
123
+ {
124
+ 'type': channel,
125
+ 'codes': marketIds,
126
+ // 'isOnlySnapshot': false,
127
+ // 'isOnlyRealtime': false,
128
+ },
129
+ ];
130
+ const trades = await this.watchMultiple(url, messageHashes, request, messageHashes);
88
131
  if (this.newUpdates) {
89
- limit = trades.getLimit(symbol, limit);
132
+ const first = this.safeValue(trades, 0);
133
+ const tradeSymbol = this.safeString(first, 'symbol');
134
+ limit = trades.getLimit(tradeSymbol, limit);
90
135
  }
91
136
  return this.filterBySinceLimit(trades, since, limit, 'timestamp', true);
92
137
  }
@@ -23,6 +23,7 @@ export default class vertex extends vertexRest {
23
23
  'watchTicker': true,
24
24
  'watchTickers': false,
25
25
  'watchTrades': true,
26
+ 'watchTradesForSymbols': false,
26
27
  'watchPositions': true,
27
28
  },
28
29
  'urls': {
@@ -18,6 +18,7 @@ export default class wazirx extends wazirxRest {
18
18
  'watchTicker': true,
19
19
  'watchTickers': true,
20
20
  'watchTrades': true,
21
+ 'watchTradesForSymbols': false,
21
22
  'watchMyTrades': true,
22
23
  'watchOrders': true,
23
24
  'watchOrderBook': true,
@@ -287,6 +288,7 @@ export default class wazirx extends wazirxRest {
287
288
  * @method
288
289
  * @name wazirx#watchTrades
289
290
  * @description get the list of most recent trades for a particular symbol
291
+ * @see https://docs.wazirx.com/#trade-streams
290
292
  * @param {string} symbol unified symbol of the market to fetch trades for
291
293
  * @param {int} [since] timestamp in ms of the earliest trade to fetch
292
294
  * @param {int} [limit] the maximum amount of trades to fetch
@@ -384,6 +386,7 @@ export default class wazirx extends wazirxRest {
384
386
  * @method
385
387
  * @name wazirx#watchOHLCV
386
388
  * @description watches historical candlestick data containing the open, high, low, and close price, and the volume of a market
389
+ * @see https://docs.wazirx.com/#kline-candlestick-stream
387
390
  * @param {string} symbol unified symbol of the market to fetch OHLCV data for
388
391
  * @param {string} timeframe the length of time each candle represents
389
392
  * @param {int} [since] timestamp in ms of the earliest candle to fetch
@@ -22,6 +22,7 @@ export default class whitebit extends whitebitRest {
22
22
  'watchOrders': true,
23
23
  'watchTicker': true,
24
24
  'watchTrades': true,
25
+ 'watchTradesForSymbols': false,
25
26
  },
26
27
  'urls': {
27
28
  'api': {
@@ -64,6 +65,7 @@ export default class whitebit extends whitebitRest {
64
65
  * @method
65
66
  * @name whitebit#watchOHLCV
66
67
  * @description watches historical candlestick data containing the open, high, low, and close price, and the volume of a market
68
+ * @see https://docs.whitebit.com/public/websocket/#kline
67
69
  * @param {string} symbol unified symbol of the market to fetch OHLCV data for
68
70
  * @param {string} timeframe the length of time each candle represents
69
71
  * @param {int} [since] timestamp in ms of the earliest candle to fetch
@@ -138,6 +140,7 @@ export default class whitebit extends whitebitRest {
138
140
  * @method
139
141
  * @name whitebit#watchOrderBook
140
142
  * @description watches information on open orders with bid (buy) and ask (sell) prices, volumes and other data
143
+ * @see https://docs.whitebit.com/public/websocket/#market-depth
141
144
  * @param {string} symbol unified symbol of the market to fetch the order book for
142
145
  * @param {int} [limit] the maximum amount of order book entries to return
143
146
  * @param {object} [params] extra parameters specific to the exchange API endpoint
@@ -243,6 +246,7 @@ export default class whitebit extends whitebitRest {
243
246
  * @method
244
247
  * @name whitebit#watchTicker
245
248
  * @description watches a price ticker, a statistical calculation with the information calculated over the past 24 hours for a specific market
249
+ * @see https://docs.whitebit.com/public/websocket/#market-statistics
246
250
  * @param {string} symbol unified symbol of the market to fetch the ticker for
247
251
  * @param {object} [params] extra parameters specific to the exchange API endpoint
248
252
  * @returns {object} a [ticker structure]{@link https://docs.ccxt.com/#/?id=ticker-structure}
@@ -309,6 +313,7 @@ export default class whitebit extends whitebitRest {
309
313
  * @method
310
314
  * @name whitebit#watchTrades
311
315
  * @description get the list of most recent trades for a particular symbol
316
+ * @see https://docs.whitebit.com/public/websocket/#market-trades
312
317
  * @param {string} symbol unified symbol of the market to fetch trades for
313
318
  * @param {int} [since] timestamp in ms of the earliest trade to fetch
314
319
  * @param {int} [limit] the maximum amount of trades to fetch
@@ -375,6 +380,7 @@ export default class whitebit extends whitebitRest {
375
380
  * @method
376
381
  * @name whitebit#watchMyTrades
377
382
  * @description watches trades made by the user
383
+ * @see https://docs.whitebit.com/private/websocket/#deals
378
384
  * @param {str} symbol unified market symbol
379
385
  * @param {int} [since] the earliest time in ms to fetch trades for
380
386
  * @param {int} [limit] the maximum number of trades structures to retrieve
@@ -474,6 +480,7 @@ export default class whitebit extends whitebitRest {
474
480
  * @method
475
481
  * @name whitebit#watchOrders
476
482
  * @description watches information on multiple orders made by the user
483
+ * @see https://docs.whitebit.com/private/websocket/#orders-pending
477
484
  * @param {string} symbol unified market symbol of the market orders were made in
478
485
  * @param {int} [since] the earliest time in ms to fetch orders for
479
486
  * @param {int} [limit] the maximum number of order structures to retrieve
@@ -649,6 +656,8 @@ export default class whitebit extends whitebitRest {
649
656
  * @method
650
657
  * @name whitebit#watchBalance
651
658
  * @description watch balance and get the amount of funds available for trading or funds locked in orders
659
+ * @see https://docs.whitebit.com/private/websocket/#balance-spot
660
+ * @see https://docs.whitebit.com/private/websocket/#balance-margin
652
661
  * @param {object} [params] extra parameters specific to the exchange API endpoint
653
662
  * @param {str} [params.type] spot or contract if not provided this.options['defaultType'] is used
654
663
  * @returns {object} a [balance structure]{@link https://docs.ccxt.com/#/?id=balance-structure}
package/js/src/upbit.js CHANGED
@@ -2004,7 +2004,7 @@ export default class upbit extends Exchange {
2004
2004
  headers['Content-Type'] = 'application/json';
2005
2005
  }
2006
2006
  if (hasQuery) {
2007
- auth = this.urlencode(query);
2007
+ auth = this.rawencode(query);
2008
2008
  }
2009
2009
  if (auth !== undefined) {
2010
2010
  const hash = this.hash(this.encode(auth), sha512);
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "ccxt",
3
- "version": "4.3.86",
3
+ "version": "4.3.87",
4
4
  "description": "A JavaScript / TypeScript / Python / C# / PHP cryptocurrency trading library with support for 100+ exchanges",
5
5
  "unpkg": "dist/ccxt.browser.min.js",
6
6
  "type": "module",