ccxt 4.3.35__py2.py3-none-any.whl → 4.3.37__py2.py3-none-any.whl

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.
ccxt/__init__.py CHANGED
@@ -22,7 +22,7 @@
22
22
 
23
23
  # ----------------------------------------------------------------------------
24
24
 
25
- __version__ = '4.3.35'
25
+ __version__ = '4.3.37'
26
26
 
27
27
  # ----------------------------------------------------------------------------
28
28
 
ccxt/abstract/bitbay.py CHANGED
@@ -34,6 +34,10 @@ class ImplicitAPI:
34
34
  v1_01private_get_balances_bitbay_balance = v1_01PrivateGetBalancesBITBAYBalance = Entry('balances/BITBAY/balance', 'v1_01Private', 'GET', {})
35
35
  v1_01private_get_fiat_cantor_rate_baseid_quoteid = v1_01PrivateGetFiatCantorRateBaseIdQuoteId = Entry('fiat_cantor/rate/{baseId}/{quoteId}', 'v1_01Private', 'GET', {})
36
36
  v1_01private_get_fiat_cantor_history = v1_01PrivateGetFiatCantorHistory = Entry('fiat_cantor/history', 'v1_01Private', 'GET', {})
37
+ v1_01private_get_client_payments_v2_customer_crypto_currency_channels_deposit = v1_01PrivateGetClientPaymentsV2CustomerCryptoCurrencyChannelsDeposit = Entry('client_payments/v2/customer/crypto/{currency}/channels/deposit', 'v1_01Private', 'GET', {})
38
+ v1_01private_get_client_payments_v2_customer_crypto_currency_channels_withdrawal = v1_01PrivateGetClientPaymentsV2CustomerCryptoCurrencyChannelsWithdrawal = Entry('client_payments/v2/customer/crypto/{currency}/channels/withdrawal', 'v1_01Private', 'GET', {})
39
+ v1_01private_get_client_payments_v2_customer_crypto_deposit_fee = v1_01PrivateGetClientPaymentsV2CustomerCryptoDepositFee = Entry('client_payments/v2/customer/crypto/deposit/fee', 'v1_01Private', 'GET', {})
40
+ v1_01private_get_client_payments_v2_customer_crypto_withdrawal_fee = v1_01PrivateGetClientPaymentsV2CustomerCryptoWithdrawalFee = Entry('client_payments/v2/customer/crypto/withdrawal/fee', 'v1_01Private', 'GET', {})
37
41
  v1_01private_post_trading_offer_symbol = v1_01PrivatePostTradingOfferSymbol = Entry('trading/offer/{symbol}', 'v1_01Private', 'POST', {})
38
42
  v1_01private_post_trading_stop_offer_symbol = v1_01PrivatePostTradingStopOfferSymbol = Entry('trading/stop/offer/{symbol}', 'v1_01Private', 'POST', {})
39
43
  v1_01private_post_trading_config_symbol = v1_01PrivatePostTradingConfigSymbol = Entry('trading/config/{symbol}', 'v1_01Private', 'POST', {})
@@ -42,6 +46,8 @@ class ImplicitAPI:
42
46
  v1_01private_post_fiat_cantor_exchange = v1_01PrivatePostFiatCantorExchange = Entry('fiat_cantor/exchange', 'v1_01Private', 'POST', {})
43
47
  v1_01private_post_api_payments_withdrawals_crypto = v1_01PrivatePostApiPaymentsWithdrawalsCrypto = Entry('api_payments/withdrawals/crypto', 'v1_01Private', 'POST', {})
44
48
  v1_01private_post_api_payments_withdrawals_fiat = v1_01PrivatePostApiPaymentsWithdrawalsFiat = Entry('api_payments/withdrawals/fiat', 'v1_01Private', 'POST', {})
49
+ v1_01private_post_client_payments_v2_customer_crypto_deposit = v1_01PrivatePostClientPaymentsV2CustomerCryptoDeposit = Entry('client_payments/v2/customer/crypto/deposit', 'v1_01Private', 'POST', {})
50
+ v1_01private_post_client_payments_v2_customer_crypto_withdrawal = v1_01PrivatePostClientPaymentsV2CustomerCryptoWithdrawal = Entry('client_payments/v2/customer/crypto/withdrawal', 'v1_01Private', 'POST', {})
45
51
  v1_01private_delete_trading_offer_symbol_id_side_price = v1_01PrivateDeleteTradingOfferSymbolIdSidePrice = Entry('trading/offer/{symbol}/{id}/{side}/{price}', 'v1_01Private', 'DELETE', {})
46
52
  v1_01private_delete_trading_stop_offer_symbol_id_side_price = v1_01PrivateDeleteTradingStopOfferSymbolIdSidePrice = Entry('trading/stop/offer/{symbol}/{id}/{side}/{price}', 'v1_01Private', 'DELETE', {})
47
53
  v1_01private_put_balances_bitbay_balance_id = v1_01PrivatePutBalancesBITBAYBalanceId = Entry('balances/BITBAY/balance/{id}', 'v1_01Private', 'PUT', {})
ccxt/abstract/kraken.py CHANGED
@@ -6,13 +6,13 @@ class ImplicitAPI:
6
6
  zendesk_get_201893608 = zendeskGet201893608 = Entry('201893608', 'zendesk', 'GET', {})
7
7
  public_get_assets = publicGetAssets = Entry('Assets', 'public', 'GET', {'cost': 1})
8
8
  public_get_assetpairs = publicGetAssetPairs = Entry('AssetPairs', 'public', 'GET', {'cost': 1})
9
- public_get_depth = publicGetDepth = Entry('Depth', 'public', 'GET', {'cost': 1})
10
- public_get_ohlc = publicGetOHLC = Entry('OHLC', 'public', 'GET', {'cost': 1})
9
+ public_get_depth = publicGetDepth = Entry('Depth', 'public', 'GET', {'cost': 1.2})
10
+ public_get_ohlc = publicGetOHLC = Entry('OHLC', 'public', 'GET', {'cost': 1.2})
11
11
  public_get_spread = publicGetSpread = Entry('Spread', 'public', 'GET', {'cost': 1})
12
12
  public_get_systemstatus = publicGetSystemStatus = Entry('SystemStatus', 'public', 'GET', {'cost': 1})
13
13
  public_get_ticker = publicGetTicker = Entry('Ticker', 'public', 'GET', {'cost': 1})
14
14
  public_get_time = publicGetTime = Entry('Time', 'public', 'GET', {'cost': 1})
15
- public_get_trades = publicGetTrades = Entry('Trades', 'public', 'GET', {'cost': 1})
15
+ public_get_trades = publicGetTrades = Entry('Trades', 'public', 'GET', {'cost': 1.2})
16
16
  private_post_addorder = privatePostAddOrder = Entry('AddOrder', 'private', 'POST', {'cost': 0})
17
17
  private_post_addorderbatch = privatePostAddOrderBatch = Entry('AddOrderBatch', 'private', 'POST', {'cost': 0})
18
18
  private_post_addexport = privatePostAddExport = Entry('AddExport', 'private', 'POST', {'cost': 3})
ccxt/abstract/zonda.py CHANGED
@@ -34,6 +34,10 @@ class ImplicitAPI:
34
34
  v1_01private_get_balances_bitbay_balance = v1_01PrivateGetBalancesBITBAYBalance = Entry('balances/BITBAY/balance', 'v1_01Private', 'GET', {})
35
35
  v1_01private_get_fiat_cantor_rate_baseid_quoteid = v1_01PrivateGetFiatCantorRateBaseIdQuoteId = Entry('fiat_cantor/rate/{baseId}/{quoteId}', 'v1_01Private', 'GET', {})
36
36
  v1_01private_get_fiat_cantor_history = v1_01PrivateGetFiatCantorHistory = Entry('fiat_cantor/history', 'v1_01Private', 'GET', {})
37
+ v1_01private_get_client_payments_v2_customer_crypto_currency_channels_deposit = v1_01PrivateGetClientPaymentsV2CustomerCryptoCurrencyChannelsDeposit = Entry('client_payments/v2/customer/crypto/{currency}/channels/deposit', 'v1_01Private', 'GET', {})
38
+ v1_01private_get_client_payments_v2_customer_crypto_currency_channels_withdrawal = v1_01PrivateGetClientPaymentsV2CustomerCryptoCurrencyChannelsWithdrawal = Entry('client_payments/v2/customer/crypto/{currency}/channels/withdrawal', 'v1_01Private', 'GET', {})
39
+ v1_01private_get_client_payments_v2_customer_crypto_deposit_fee = v1_01PrivateGetClientPaymentsV2CustomerCryptoDepositFee = Entry('client_payments/v2/customer/crypto/deposit/fee', 'v1_01Private', 'GET', {})
40
+ v1_01private_get_client_payments_v2_customer_crypto_withdrawal_fee = v1_01PrivateGetClientPaymentsV2CustomerCryptoWithdrawalFee = Entry('client_payments/v2/customer/crypto/withdrawal/fee', 'v1_01Private', 'GET', {})
37
41
  v1_01private_post_trading_offer_symbol = v1_01PrivatePostTradingOfferSymbol = Entry('trading/offer/{symbol}', 'v1_01Private', 'POST', {})
38
42
  v1_01private_post_trading_stop_offer_symbol = v1_01PrivatePostTradingStopOfferSymbol = Entry('trading/stop/offer/{symbol}', 'v1_01Private', 'POST', {})
39
43
  v1_01private_post_trading_config_symbol = v1_01PrivatePostTradingConfigSymbol = Entry('trading/config/{symbol}', 'v1_01Private', 'POST', {})
@@ -42,6 +46,8 @@ class ImplicitAPI:
42
46
  v1_01private_post_fiat_cantor_exchange = v1_01PrivatePostFiatCantorExchange = Entry('fiat_cantor/exchange', 'v1_01Private', 'POST', {})
43
47
  v1_01private_post_api_payments_withdrawals_crypto = v1_01PrivatePostApiPaymentsWithdrawalsCrypto = Entry('api_payments/withdrawals/crypto', 'v1_01Private', 'POST', {})
44
48
  v1_01private_post_api_payments_withdrawals_fiat = v1_01PrivatePostApiPaymentsWithdrawalsFiat = Entry('api_payments/withdrawals/fiat', 'v1_01Private', 'POST', {})
49
+ v1_01private_post_client_payments_v2_customer_crypto_deposit = v1_01PrivatePostClientPaymentsV2CustomerCryptoDeposit = Entry('client_payments/v2/customer/crypto/deposit', 'v1_01Private', 'POST', {})
50
+ v1_01private_post_client_payments_v2_customer_crypto_withdrawal = v1_01PrivatePostClientPaymentsV2CustomerCryptoWithdrawal = Entry('client_payments/v2/customer/crypto/withdrawal', 'v1_01Private', 'POST', {})
45
51
  v1_01private_delete_trading_offer_symbol_id_side_price = v1_01PrivateDeleteTradingOfferSymbolIdSidePrice = Entry('trading/offer/{symbol}/{id}/{side}/{price}', 'v1_01Private', 'DELETE', {})
46
52
  v1_01private_delete_trading_stop_offer_symbol_id_side_price = v1_01PrivateDeleteTradingStopOfferSymbolIdSidePrice = Entry('trading/stop/offer/{symbol}/{id}/{side}/{price}', 'v1_01Private', 'DELETE', {})
47
53
  v1_01private_put_balances_bitbay_balance_id = v1_01PrivatePutBalancesBITBAYBalanceId = Entry('balances/BITBAY/balance/{id}', 'v1_01Private', 'PUT', {})
@@ -4,7 +4,7 @@
4
4
 
5
5
  # -----------------------------------------------------------------------------
6
6
 
7
- __version__ = '4.3.35'
7
+ __version__ = '4.3.37'
8
8
 
9
9
  # -----------------------------------------------------------------------------
10
10
 
@@ -2,7 +2,7 @@
2
2
 
3
3
  # -----------------------------------------------------------------------------
4
4
 
5
- __version__ = '4.3.35'
5
+ __version__ = '4.3.37'
6
6
 
7
7
  # -----------------------------------------------------------------------------
8
8
 
@@ -1017,7 +1017,7 @@ class bingx(Exchange, ImplicitAPI):
1017
1017
  if time == 0:
1018
1018
  time = None
1019
1019
  cost = self.safe_string(trade, 'quoteQty')
1020
- type = 'spot' if (cost is None) else 'swap'
1020
+ # type = 'spot' if (cost is None) else 'swap'; self is not reliable
1021
1021
  currencyId = self.safe_string_n(trade, ['currency', 'N', 'commissionAsset'])
1022
1022
  currencyCode = self.safe_currency_code(currencyId)
1023
1023
  m = self.safe_bool(trade, 'm')
@@ -1048,7 +1048,7 @@ class bingx(Exchange, ImplicitAPI):
1048
1048
  'info': trade,
1049
1049
  'timestamp': time,
1050
1050
  'datetime': self.iso8601(time),
1051
- 'symbol': self.safe_symbol(marketId, market, '-', type),
1051
+ 'symbol': self.safe_symbol(marketId, market, '-'),
1052
1052
  'order': self.safe_string_2(trade, 'orderId', 'i'),
1053
1053
  'type': self.safe_string_lower(trade, 'o'),
1054
1054
  'side': self.parse_order_side(side),
@@ -2570,7 +2570,9 @@ class bingx(Exchange, ImplicitAPI):
2570
2570
  #
2571
2571
  else:
2572
2572
  raise BadRequest(self.id + ' cancelAllOrders is only supported for spot and swap markets.')
2573
- return response
2573
+ data = self.safe_dict(response, 'data', {})
2574
+ orders = self.safe_list_2(data, 'success', 'orders', [])
2575
+ return self.parse_orders(orders)
2574
2576
 
2575
2577
  async def cancel_orders(self, ids: List[str], symbol: Str = None, params={}):
2576
2578
  """
@@ -2606,42 +2608,70 @@ class bingx(Exchange, ImplicitAPI):
2606
2608
  spotReqKey = 'clientOrderIDs' if areClientOrderIds else 'orderIds'
2607
2609
  request[spotReqKey] = ','.join(parsedIds)
2608
2610
  response = await self.spotV1PrivatePostTradeCancelOrders(self.extend(request, params))
2611
+ #
2612
+ # {
2613
+ # "code": 0,
2614
+ # "msg": "",
2615
+ # "debugMsg": "",
2616
+ # "data": {
2617
+ # "orders": [
2618
+ # {
2619
+ # "symbol": "SOL-USDT",
2620
+ # "orderId": 1795970045910614016,
2621
+ # "transactTime": 1717027601111,
2622
+ # "price": "180.25",
2623
+ # "stopPrice": "0",
2624
+ # "origQty": "0.03",
2625
+ # "executedQty": "0",
2626
+ # "cummulativeQuoteQty": "0",
2627
+ # "status": "CANCELED",
2628
+ # "type": "LIMIT",
2629
+ # "side": "SELL",
2630
+ # "clientOrderID": ""
2631
+ # },
2632
+ # ...
2633
+ # ]
2634
+ # }
2635
+ # }
2636
+ #
2609
2637
  else:
2610
2638
  if areClientOrderIds:
2611
2639
  request['clientOrderIDList'] = self.json(parsedIds)
2612
2640
  else:
2613
2641
  request['orderIdList'] = parsedIds
2614
2642
  response = await self.swapV2PrivateDeleteTradeBatchOrders(self.extend(request, params))
2615
- #
2616
- # {
2617
- # "code": 0,
2618
- # "msg": "",
2619
- # "data": {
2620
- # "success": [
2621
- # {
2622
- # "symbol": "LINK-USDT",
2623
- # "orderId": 1597783850786750464,
2624
- # "side": "BUY",
2625
- # "positionSide": "LONG",
2626
- # "type": "TRIGGER_MARKET",
2627
- # "origQty": "5.0",
2628
- # "price": "5.5710",
2629
- # "executedQty": "0.0",
2630
- # "avgPrice": "0.0000",
2631
- # "cumQuote": "0",
2632
- # "stopPrice": "5.0000",
2633
- # "profit": "0.0000",
2634
- # "commission": "0.000000",
2635
- # "status": "CANCELLED",
2636
- # "time": 1669776330000,
2637
- # "updateTime": 1672370837000
2638
- # }
2639
- # ],
2640
- # "failed": null
2641
- # }
2642
- # }
2643
- #
2644
- return response
2643
+ #
2644
+ # {
2645
+ # "code": 0,
2646
+ # "msg": "",
2647
+ # "data": {
2648
+ # "success": [
2649
+ # {
2650
+ # "symbol": "LINK-USDT",
2651
+ # "orderId": 1597783850786750464,
2652
+ # "side": "BUY",
2653
+ # "positionSide": "LONG",
2654
+ # "type": "TRIGGER_MARKET",
2655
+ # "origQty": "5.0",
2656
+ # "price": "5.5710",
2657
+ # "executedQty": "0.0",
2658
+ # "avgPrice": "0.0000",
2659
+ # "cumQuote": "0",
2660
+ # "stopPrice": "5.0000",
2661
+ # "profit": "0.0000",
2662
+ # "commission": "0.000000",
2663
+ # "status": "CANCELLED",
2664
+ # "time": 1669776330000,
2665
+ # "updateTime": 1672370837000
2666
+ # }
2667
+ # ],
2668
+ # "failed": null
2669
+ # }
2670
+ # }
2671
+ #
2672
+ data = self.safe_dict(response, 'data', {})
2673
+ success = self.safe_list_2(data, 'success', 'orders', [])
2674
+ return self.parse_orders(success)
2645
2675
 
2646
2676
  async def cancel_all_orders_after(self, timeout: Int, params={}):
2647
2677
  """
@@ -448,7 +448,8 @@ class bit2c(Exchange, ImplicitAPI):
448
448
  request: dict = {
449
449
  'id': id,
450
450
  }
451
- return await self.privatePostOrderCancelOrder(self.extend(request, params))
451
+ response = await self.privatePostOrderCancelOrder(self.extend(request, params))
452
+ return self.parse_order(response)
452
453
 
453
454
  async def fetch_open_orders(self, symbol: Str = None, since: Int = None, limit: Int = None, params={}) -> List[Order]:
454
455
  """
@@ -669,8 +669,31 @@ class bitbank(Exchange, ImplicitAPI):
669
669
  'pair': market['id'],
670
670
  }
671
671
  response = await self.privatePostUserSpotCancelOrder(self.extend(request, params))
672
+ #
673
+ # {
674
+ # "success": 1,
675
+ # "data": {
676
+ # "order_id": 0,
677
+ # "pair": "string",
678
+ # "side": "string",
679
+ # "type": "string",
680
+ # "start_amount": "string",
681
+ # "remaining_amount": "string",
682
+ # "executed_amount": "string",
683
+ # "price": "string",
684
+ # "post_only": False,
685
+ # "average_price": "string",
686
+ # "ordered_at": 0,
687
+ # "expire_at": 0,
688
+ # "canceled_at": 0,
689
+ # "triggered_at": 0,
690
+ # "trigger_price": "string",
691
+ # "status": "string"
692
+ # }
693
+ # }
694
+ #
672
695
  data = self.safe_value(response, 'data')
673
- return data
696
+ return self.parse_order(data)
674
697
 
675
698
  async def fetch_order(self, id: str, symbol: Str = None, params={}):
676
699
  """
@@ -687,6 +710,28 @@ class bitbank(Exchange, ImplicitAPI):
687
710
  'pair': market['id'],
688
711
  }
689
712
  response = await self.privateGetUserSpotOrder(self.extend(request, params))
713
+ #
714
+ # {
715
+ # "success": 1,
716
+ # "data": {
717
+ # "order_id": 0,
718
+ # "pair": "string",
719
+ # "side": "string",
720
+ # "type": "string",
721
+ # "start_amount": "string",
722
+ # "remaining_amount": "string",
723
+ # "executed_amount": "string",
724
+ # "price": "string",
725
+ # "post_only": False,
726
+ # "average_price": "string",
727
+ # "ordered_at": 0,
728
+ # "expire_at": 0,
729
+ # "triggered_at": 0,
730
+ # "triger_price": "string",
731
+ # "status": "string"
732
+ # }
733
+ # }
734
+ #
690
735
  data = self.safe_dict(response, 'data')
691
736
  return self.parse_order(data, market)
692
737
 
@@ -1250,6 +1250,7 @@ class bitget(Exchange, ImplicitAPI):
1250
1250
  '40712': InsufficientFunds, # Insufficient margin
1251
1251
  '40713': ExchangeError, # Cannot exceed the maximum transferable margin amount
1252
1252
  '40714': ExchangeError, # No direct margin call is allowed
1253
+ '40762': InsufficientFunds, # {"code":"40762","msg":"The order amount exceeds the balance","requestTime":1716572156622,"data":null}
1253
1254
  '40768': OrderNotFound, # Order does not exist"
1254
1255
  '41114': OnMaintenance, # {"code":"41114","msg":"The current trading pair is under maintenance, please refer to the official announcement for the opening time","requestTime":1679196062544,"data":null}
1255
1256
  '43011': InvalidOrder, # The parameter does not meet the specification executePrice <= 0
@@ -4139,18 +4140,23 @@ class bitget(Exchange, ImplicitAPI):
4139
4140
  marginMode = 'cross'
4140
4141
  marginModeRequest = 'crossed' if (marginMode == 'cross') else 'isolated'
4141
4142
  request['marginMode'] = marginModeRequest
4142
- oneWayMode = self.safe_bool(params, 'oneWayMode', False)
4143
- params = self.omit(params, 'oneWayMode')
4143
+ hedged = None
4144
+ hedged, params = self.handle_param_bool(params, 'hedged', False)
4145
+ # backward compatibility for `oneWayMode`
4146
+ oneWayMode = None
4147
+ oneWayMode, params = self.handle_param_bool(params, 'oneWayMode')
4148
+ if oneWayMode is not None:
4149
+ hedged = not oneWayMode
4144
4150
  requestSide = side
4145
4151
  if reduceOnly:
4146
- if oneWayMode:
4152
+ if not hedged:
4147
4153
  request['reduceOnly'] = 'YES'
4148
4154
  else:
4149
4155
  # on bitget hedge mode if the position is long the side is always buy, and if the position is short the side is always sell
4150
4156
  requestSide = 'sell' if (side == 'buy') else 'buy'
4151
4157
  request['tradeSide'] = 'Close'
4152
4158
  else:
4153
- if not oneWayMode:
4159
+ if hedged:
4154
4160
  request['tradeSide'] = 'Open'
4155
4161
  request['side'] = requestSide
4156
4162
  elif marketType == 'spot':
@@ -1180,9 +1180,9 @@ class bitmart(Exchange, ImplicitAPI):
1180
1180
  market = self.safe_market(marketId, market)
1181
1181
  symbol = market['symbol']
1182
1182
  last = self.safe_string_2(ticker, 'close_24h', 'last_price')
1183
- percentage = Precise.string_abs(self.safe_string(ticker, 'price_change_percent_24h'))
1183
+ percentage = self.safe_string(ticker, 'price_change_percent_24h')
1184
1184
  if percentage is None:
1185
- percentage = Precise.string_abs(Precise.string_mul(self.safe_string(ticker, 'fluctuation'), '100'))
1185
+ percentage = Precise.string_mul(self.safe_string(ticker, 'fluctuation'), '100')
1186
1186
  baseVolume = self.safe_string(ticker, 'base_volume_24h')
1187
1187
  quoteVolume = self.safe_string(ticker, 'quote_volume_24h')
1188
1188
  if quoteVolume is None:
ccxt/async_support/htx.py CHANGED
@@ -57,6 +57,8 @@ class htx(Exchange, ImplicitAPI):
57
57
  'cancelAllOrdersAfter': True,
58
58
  'cancelOrder': True,
59
59
  'cancelOrders': True,
60
+ 'closeAllPositions': False,
61
+ 'closePosition': True,
60
62
  'createDepositAddress': None,
61
63
  'createMarketBuyOrderWithCost': True,
62
64
  'createMarketOrderWithCost': False,
@@ -5004,7 +5006,7 @@ class htx(Exchange, ImplicitAPI):
5004
5006
  :param float [params.stopLossPrice]: *contract only* the price a stop-loss order is triggered at
5005
5007
  :param float [params.takeProfitPrice]: *contract only* the price a take-profit order is triggered at
5006
5008
  :param str [params.operator]: *spot and margin only* gte or lte, trigger price condition
5007
- :param str [params.offset]: *contract only* 'open', 'close', or 'both', required in hedge mode
5009
+ :param str [params.offset]: *contract only* 'both'(linear only), 'open', or 'close', required in hedge mode and for inverse markets
5008
5010
  :param bool [params.postOnly]: *contract only* True or False
5009
5011
  :param int [params.leverRate]: *contract only* required for all contract orders except tpsl, leverage greater than 20x requires prior approval of high-leverage agreement
5010
5012
  :param str [params.timeInForce]: supports 'IOC' and 'FOK'
@@ -5054,6 +5056,9 @@ class htx(Exchange, ImplicitAPI):
5054
5056
  else:
5055
5057
  response = await self.contractPrivatePostLinearSwapApiV1SwapCrossOrder(contractRequest)
5056
5058
  elif market['inverse']:
5059
+ offset = self.safe_string(params, 'offset')
5060
+ if offset is None:
5061
+ raise ArgumentsRequired(self.id + ' createOrder() requires an extra parameter params["offset"] to be set to "open" or "close" when placing orders in inverse markets')
5057
5062
  if market['swap']:
5058
5063
  if isStop:
5059
5064
  response = await self.contractPrivatePostSwapApiV1SwapTriggerOrder(contractRequest)
@@ -6935,14 +6940,19 @@ class htx(Exchange, ImplicitAPI):
6935
6940
  fetch all open positions
6936
6941
  :param str[]|None symbols: list of unified market symbols
6937
6942
  :param dict [params]: extra parameters specific to the exchange API endpoint
6943
+ :param str [params.subType]: 'linear' or 'inverse'
6944
+ :param str [params.type]: *inverse only* 'future', or 'swap'
6945
+ :param str [params.marginMode]: *linear only* 'cross' or 'isolated'
6938
6946
  :returns dict[]: a list of `position structure <https://docs.ccxt.com/#/?id=position-structure>`
6939
6947
  """
6940
6948
  await self.load_markets()
6941
6949
  symbols = self.market_symbols(symbols)
6942
6950
  market = None
6943
6951
  if symbols is not None:
6944
- first = self.safe_string(symbols, 0)
6945
- market = self.market(first)
6952
+ symbolsLength = len(symbols)
6953
+ if symbolsLength > 0:
6954
+ first = self.safe_string(symbols, 0)
6955
+ market = self.market(first)
6946
6956
  marginMode = None
6947
6957
  marginMode, params = self.handle_margin_mode_and_params('fetchPositions', params, 'cross')
6948
6958
  subType = None
@@ -8386,6 +8396,57 @@ class htx(Exchange, ImplicitAPI):
8386
8396
  'datetime': self.iso8601(timestamp),
8387
8397
  })
8388
8398
 
8399
+ async def close_position(self, symbol: str, side: OrderSide = None, params={}) -> Order:
8400
+ """
8401
+ closes open positions for a contract market, requires 'amount' in params, unlike other exchanges
8402
+ :see: https://huobiapi.github.io/docs/usdt_swap/v1/en/#isolated-place-lightning-close-order # USDT-M(isolated)
8403
+ :see: https://huobiapi.github.io/docs/usdt_swap/v1/en/#cross-place-lightning-close-position # USDT-M(cross)
8404
+ :see: https://huobiapi.github.io/docs/coin_margined_swap/v1/en/#place-lightning-close-order # Coin-M swap
8405
+ :see: https://huobiapi.github.io/docs/dm/v1/en/#place-flash-close-order # Coin-M futures
8406
+ :param str symbol: unified CCXT market symbol
8407
+ :param str side: 'buy' or 'sell', the side of the closing order, opposite side side
8408
+ :param dict [params]: extra parameters specific to the okx api endpoint
8409
+ :param str [params.clientOrderId]: client needs to provide unique API and have to maintain the API themselves afterwards. [1, 9223372036854775807]
8410
+ :param dict [params.marginMode]: 'cross' or 'isolated', required for linear markets
8411
+ *
8412
+ * EXCHANGE SPECIFIC PARAMETERS
8413
+ :param number [params.amount]: order quantity
8414
+ :param str [params.order_price_type]: 'lightning' by default, 'lightning_fok': lightning fok type, 'lightning_ioc': lightning ioc type 'market' by default, 'market': market order type, 'lightning_fok': lightning
8415
+ :returns dict: `an order structure <https://docs.ccxt.com/#/?id=position-structure>`
8416
+ """
8417
+ await self.load_markets()
8418
+ market = self.market(symbol)
8419
+ clientOrderId = self.safe_string(params, 'clientOrderId')
8420
+ if not market['contract']:
8421
+ raise BadRequest(self.id + ' closePosition() symbol supports contract markets only')
8422
+ self.check_required_argument('closePosition', side, 'side')
8423
+ request: dict = {
8424
+ 'contract_code': market['id'],
8425
+ 'direction': side,
8426
+ }
8427
+ if clientOrderId is not None:
8428
+ request['client_order_id'] = clientOrderId
8429
+ if market['inverse']:
8430
+ amount = self.safe_string_2(params, 'volume', 'amount')
8431
+ if amount is None:
8432
+ raise ArgumentsRequired(self.id + ' closePosition() requires an extra argument params["amount"] for inverse markets')
8433
+ request['volume'] = self.amount_to_precision(symbol, amount)
8434
+ params = self.omit(params, ['clientOrderId', 'volume', 'amount'])
8435
+ response = None
8436
+ if market['inverse']: # Coin-M
8437
+ if market['swap']:
8438
+ response = await self.contractPrivatePostSwapApiV1SwapLightningClosePosition(self.extend(request, params))
8439
+ else: # future
8440
+ response = await self.contractPrivatePostApiV1LightningClosePosition(self.extend(request, params))
8441
+ else: # USDT-M
8442
+ marginMode = None
8443
+ marginMode, params = self.handle_margin_mode_and_params('closePosition', params, 'cross')
8444
+ if marginMode == 'cross':
8445
+ response = await self.contractPrivatePostLinearSwapApiV1SwapCrossLightningClosePosition(self.extend(request, params))
8446
+ else: # isolated
8447
+ response = await self.contractPrivatePostLinearSwapApiV1SwapLightningClosePosition(self.extend(request, params))
8448
+ return self.parse_order(response, market)
8449
+
8389
8450
  async def set_position_mode(self, hedged: bool, symbol: Str = None, params={}):
8390
8451
  """
8391
8452
  set hedged to True or False
@@ -179,13 +179,13 @@ class kraken(Exchange, ImplicitAPI):
179
179
  # rate-limits explained in comment in the top of self file
180
180
  'Assets': 1,
181
181
  'AssetPairs': 1,
182
- 'Depth': 1,
183
- 'OHLC': 1,
182
+ 'Depth': 1.2,
183
+ 'OHLC': 1.2, # 1.2 because 1 triggers too many requests immediately
184
184
  'Spread': 1,
185
185
  'SystemStatus': 1,
186
186
  'Ticker': 1,
187
187
  'Time': 1,
188
- 'Trades': 1,
188
+ 'Trades': 1.2,
189
189
  },
190
190
  },
191
191
  'private': {
@@ -761,8 +761,8 @@ class kraken(Exchange, ImplicitAPI):
761
761
  return {
762
762
  'info': response,
763
763
  'symbol': market['symbol'],
764
- 'maker': self.safe_number(symbolMakerFee, 'fee'),
765
- 'taker': self.safe_number(symbolTakerFee, 'fee'),
764
+ 'maker': self.parse_number(Precise.string_div(self.safe_string(symbolMakerFee, 'fee'), '100')),
765
+ 'taker': self.parse_number(Precise.string_div(self.safe_string(symbolTakerFee, 'fee'), '100')),
766
766
  'percentage': True,
767
767
  'tierBased': True,
768
768
  }
@@ -407,7 +407,10 @@ class paymium(Exchange, ImplicitAPI):
407
407
  request: dict = {
408
408
  'uuid': id,
409
409
  }
410
- return await self.privateDeleteUserOrdersUuidCancel(self.extend(request, params))
410
+ response = await self.privateDeleteUserOrdersUuidCancel(self.extend(request, params))
411
+ return self.safe_order({
412
+ 'info': response,
413
+ })
411
414
 
412
415
  async def transfer(self, code: str, amount: float, fromAccount: str, toAccount: str, params={}) -> TransferEntry:
413
416
  """
@@ -1341,7 +1341,27 @@ class whitebit(Exchange, ImplicitAPI):
1341
1341
  'market': market['id'],
1342
1342
  'orderId': int(id),
1343
1343
  }
1344
- return await self.v4PrivatePostOrderCancel(self.extend(request, params))
1344
+ response = await self.v4PrivatePostOrderCancel(self.extend(request, params))
1345
+ #
1346
+ # {
1347
+ # "orderId": 4180284841, # order id
1348
+ # "clientOrderId": "customId11", # custom order identifier; "clientOrderId": "" - if not specified.
1349
+ # "market": "BTC_USDT", # deal market
1350
+ # "side": "buy", # order side
1351
+ # "type": "stop market", # order type
1352
+ # "timestamp": 1595792396.165973, # current timestamp
1353
+ # "dealMoney": "0", # if order finished - amount in money currency that is finished
1354
+ # "dealStock": "0", # if order finished - amount in stock currency that is finished
1355
+ # "amount": "0.001", # amount
1356
+ # "takerFee": "0.001", # maker fee ratio. If the number less than 0.0001 - it will be rounded to zero
1357
+ # "makerFee": "0.001", # maker fee ratio. If the number less than 0.0001 - it will be rounded to zero
1358
+ # "left": "0.001", # if order not finished - rest of the amount that must be finished
1359
+ # "dealFee": "0", # fee in money that you pay if order is finished
1360
+ # "price": "40000", # price if price isset
1361
+ # "activation_price": "40000" # activation price if activation price is set
1362
+ # }
1363
+ #
1364
+ return self.parse_order(response)
1345
1365
 
1346
1366
  async def cancel_all_orders(self, symbol: Str = None, params={}):
1347
1367
  """
@@ -1378,7 +1398,7 @@ class whitebit(Exchange, ImplicitAPI):
1378
1398
  #
1379
1399
  # []
1380
1400
  #
1381
- return response
1401
+ return self.parse_orders(response, market)
1382
1402
 
1383
1403
  async def cancel_all_orders_after(self, timeout: Int, params={}):
1384
1404
  """
@@ -1588,7 +1608,7 @@ class whitebit(Exchange, ImplicitAPI):
1588
1608
 
1589
1609
  def parse_order(self, order: dict, market: Market = None) -> Order:
1590
1610
  #
1591
- # createOrder, fetchOpenOrders
1611
+ # createOrder, fetchOpenOrders, cancelOrder
1592
1612
  #
1593
1613
  # {
1594
1614
  # "orderId":105687928629,
@@ -1603,6 +1623,7 @@ class whitebit(Exchange, ImplicitAPI):
1603
1623
  # "takerFee":"0.001",
1604
1624
  # "makerFee":"0",
1605
1625
  # "left":"100",
1626
+ # "price": "40000", # price if price isset
1606
1627
  # "dealFee":"0",
1607
1628
  # "activation_price":"0.065" # stop price(if stop limit or stop market)
1608
1629
  # }
@@ -2138,8 +2138,10 @@ class woofipro(Exchange, ImplicitAPI):
2138
2138
 
2139
2139
  def sign_hash(self, hash, privateKey):
2140
2140
  signature = self.ecdsa(hash[-64:], privateKey[-64:], 'secp256k1', None)
2141
+ r = signature['r']
2142
+ s = signature['s']
2141
2143
  v = self.int_to_base16(self.sum(27, signature['v']))
2142
- return '0x' + signature['r'].rjust(64, '0') + signature['s'].rjust(64, '0') + v
2144
+ return '0x' + r.rjust(64, '0') + s.rjust(64, '0') + v
2143
2145
 
2144
2146
  def sign_message(self, message, privateKey):
2145
2147
  return self.sign_hash(self.hash_message(message), privateKey[-64:])
@@ -461,7 +461,23 @@ class zaif(Exchange, ImplicitAPI):
461
461
  request: dict = {
462
462
  'order_id': id,
463
463
  }
464
- return await self.privatePostCancelOrder(self.extend(request, params))
464
+ response = await self.privatePostCancelOrder(self.extend(request, params))
465
+ #
466
+ # {
467
+ # "success": 1,
468
+ # "return": {
469
+ # "order_id": 184,
470
+ # "funds": {
471
+ # "jpy": 15320,
472
+ # "btc": 1.392,
473
+ # "mona": 2600,
474
+ # "kaori": 0.1
475
+ # }
476
+ # }
477
+ # }
478
+ #
479
+ data = self.safe_dict(response, 'return')
480
+ return self.parse_order(data)
465
481
 
466
482
  def parse_order(self, order: dict, market: Market = None) -> Order:
467
483
  #
@@ -474,6 +490,18 @@ class zaif(Exchange, ImplicitAPI):
474
490
  # "comment" : "demo"
475
491
  # }
476
492
  #
493
+ # cancelOrder
494
+ #
495
+ # {
496
+ # "order_id": 184,
497
+ # "funds": {
498
+ # "jpy": 15320,
499
+ # "btc": 1.392,
500
+ # "mona": 2600,
501
+ # "kaori": 0.1
502
+ # }
503
+ # }
504
+ #
477
505
  side = self.safe_string(order, 'action')
478
506
  side = 'buy' if (side == 'bid') else 'sell'
479
507
  timestamp = self.safe_timestamp(order, 'timestamp')
@@ -481,7 +509,7 @@ class zaif(Exchange, ImplicitAPI):
481
509
  symbol = self.safe_symbol(marketId, market, '_')
482
510
  price = self.safe_string(order, 'price')
483
511
  amount = self.safe_string(order, 'amount')
484
- id = self.safe_string(order, 'id')
512
+ id = self.safe_string_2(order, 'id', 'order_id')
485
513
  return self.safe_order({
486
514
  'id': id,
487
515
  'clientOrderId': None,