ccxt 4.4.26__py2.py3-none-any.whl → 4.4.28__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.
Files changed (103) hide show
  1. ccxt/__init__.py +1 -1
  2. ccxt/abstract/alpaca.py +2 -0
  3. ccxt/abstract/binance.py +7 -0
  4. ccxt/abstract/binancecoinm.py +7 -0
  5. ccxt/abstract/binanceus.py +7 -0
  6. ccxt/abstract/binanceusdm.py +7 -0
  7. ccxt/abstract/hyperliquid.py +1 -1
  8. ccxt/ace.py +1 -1
  9. ccxt/alpaca.py +186 -6
  10. ccxt/ascendex.py +1 -1
  11. ccxt/async_support/__init__.py +1 -1
  12. ccxt/async_support/ace.py +1 -1
  13. ccxt/async_support/alpaca.py +186 -6
  14. ccxt/async_support/ascendex.py +1 -1
  15. ccxt/async_support/base/exchange.py +19 -1
  16. ccxt/async_support/bequant.py +1 -1
  17. ccxt/async_support/bigone.py +1 -1
  18. ccxt/async_support/binance.py +8 -1
  19. ccxt/async_support/binancecoinm.py +1 -1
  20. ccxt/async_support/binanceus.py +1 -1
  21. ccxt/async_support/binanceusdm.py +1 -1
  22. ccxt/async_support/bingx.py +23 -28
  23. ccxt/async_support/bit2c.py +1 -1
  24. ccxt/async_support/bitbank.py +1 -1
  25. ccxt/async_support/bitbns.py +1 -1
  26. ccxt/async_support/bitfinex.py +1 -1
  27. ccxt/async_support/bitfinex2.py +1 -1
  28. ccxt/async_support/bitflyer.py +1 -1
  29. ccxt/async_support/bitget.py +1 -1
  30. ccxt/async_support/bithumb.py +1 -1
  31. ccxt/async_support/bitmart.py +1 -1
  32. ccxt/async_support/bitmex.py +1 -1
  33. ccxt/async_support/bitopro.py +1 -1
  34. ccxt/async_support/bitrue.py +1 -1
  35. ccxt/async_support/bitso.py +1 -1
  36. ccxt/async_support/bitstamp.py +1 -1
  37. ccxt/async_support/bitteam.py +1 -1
  38. ccxt/async_support/bitvavo.py +1 -1
  39. ccxt/async_support/bl3p.py +1 -1
  40. ccxt/async_support/blockchaincom.py +1 -1
  41. ccxt/async_support/blofin.py +1 -1
  42. ccxt/async_support/btcalpha.py +1 -1
  43. ccxt/async_support/btcbox.py +1 -1
  44. ccxt/async_support/btcmarkets.py +1 -1
  45. ccxt/async_support/btcturk.py +1 -1
  46. ccxt/async_support/bybit.py +4 -1
  47. ccxt/async_support/coinbase.py +89 -11
  48. ccxt/async_support/coinex.py +1 -1
  49. ccxt/async_support/gate.py +20 -16
  50. ccxt/async_support/hyperliquid.py +19 -1
  51. ccxt/async_support/kraken.py +43 -35
  52. ccxt/async_support/lbank.py +97 -2
  53. ccxt/async_support/wavesexchange.py +14 -2
  54. ccxt/base/exchange.py +19 -1
  55. ccxt/bequant.py +1 -1
  56. ccxt/bigone.py +1 -1
  57. ccxt/binance.py +8 -1
  58. ccxt/binancecoinm.py +1 -1
  59. ccxt/binanceus.py +1 -1
  60. ccxt/binanceusdm.py +1 -1
  61. ccxt/bingx.py +23 -28
  62. ccxt/bit2c.py +1 -1
  63. ccxt/bitbank.py +1 -1
  64. ccxt/bitbns.py +1 -1
  65. ccxt/bitfinex.py +1 -1
  66. ccxt/bitfinex2.py +1 -1
  67. ccxt/bitflyer.py +1 -1
  68. ccxt/bitget.py +1 -1
  69. ccxt/bithumb.py +1 -1
  70. ccxt/bitmart.py +1 -1
  71. ccxt/bitmex.py +1 -1
  72. ccxt/bitopro.py +1 -1
  73. ccxt/bitrue.py +1 -1
  74. ccxt/bitso.py +1 -1
  75. ccxt/bitstamp.py +1 -1
  76. ccxt/bitteam.py +1 -1
  77. ccxt/bitvavo.py +1 -1
  78. ccxt/bl3p.py +1 -1
  79. ccxt/blockchaincom.py +1 -1
  80. ccxt/blofin.py +1 -1
  81. ccxt/btcalpha.py +1 -1
  82. ccxt/btcbox.py +1 -1
  83. ccxt/btcmarkets.py +1 -1
  84. ccxt/btcturk.py +1 -1
  85. ccxt/bybit.py +4 -1
  86. ccxt/coinbase.py +89 -11
  87. ccxt/coinex.py +1 -1
  88. ccxt/gate.py +20 -16
  89. ccxt/hyperliquid.py +19 -1
  90. ccxt/kraken.py +43 -35
  91. ccxt/lbank.py +97 -2
  92. ccxt/pro/__init__.py +1 -1
  93. ccxt/pro/binance.py +6 -7
  94. ccxt/pro/bybit.py +1 -1
  95. ccxt/pro/lbank.py +7 -4
  96. ccxt/pro/okx.py +1 -1
  97. ccxt/wavesexchange.py +14 -2
  98. ccxt-4.4.28.dist-info/METADATA +637 -0
  99. {ccxt-4.4.26.dist-info → ccxt-4.4.28.dist-info}/RECORD +102 -102
  100. ccxt-4.4.26.dist-info/METADATA +0 -636
  101. {ccxt-4.4.26.dist-info → ccxt-4.4.28.dist-info}/LICENSE.txt +0 -0
  102. {ccxt-4.4.26.dist-info → ccxt-4.4.28.dist-info}/WHEEL +0 -0
  103. {ccxt-4.4.26.dist-info → ccxt-4.4.28.dist-info}/top_level.txt +0 -0
@@ -104,7 +104,7 @@ class bitso(Exchange, ImplicitAPI):
104
104
  'withdraw': True,
105
105
  },
106
106
  'urls': {
107
- 'logo': 'https://user-images.githubusercontent.com/51840849/87295554-11f98280-c50e-11ea-80d6-15b3bafa8cbf.jpg',
107
+ 'logo': 'https://github.com/user-attachments/assets/178c8e56-9054-4107-b192-5e5053d4f975',
108
108
  'api': {
109
109
  'rest': 'https://bitso.com/api',
110
110
  },
@@ -107,7 +107,7 @@ class bitstamp(Exchange, ImplicitAPI):
107
107
  'withdraw': True,
108
108
  },
109
109
  'urls': {
110
- 'logo': 'https://user-images.githubusercontent.com/1294454/27786377-8c8ab57e-5fe9-11e7-8ea4-2b05b6bcceec.jpg',
110
+ 'logo': 'https://github.com/user-attachments/assets/d5480572-1fee-43cb-b900-d38c522d0024',
111
111
  'api': {
112
112
  'public': 'https://www.bitstamp.net/api',
113
113
  'private': 'https://www.bitstamp.net/api',
@@ -137,7 +137,7 @@ class bitteam(Exchange, ImplicitAPI):
137
137
  '1d': '1D',
138
138
  },
139
139
  'urls': {
140
- 'logo': 'https://github.com/ccxt/ccxt/assets/43336371/cf71fe3d-b8b4-40f2-a906-907661b28793',
140
+ 'logo': 'https://github.com/user-attachments/assets/b41b5e0d-98e5-4bd3-8a6e-aeb230a4a135',
141
141
  'api': {
142
142
  'history': 'https://history.bit.team',
143
143
  'public': 'https://bit.team',
@@ -127,7 +127,7 @@ class bitvavo(Exchange, ImplicitAPI):
127
127
  '1d': '1d',
128
128
  },
129
129
  'urls': {
130
- 'logo': 'https://user-images.githubusercontent.com/1294454/169202626-bd130fc5-fcf9-41bb-8d97-6093225c73cd.jpg',
130
+ 'logo': 'https://github.com/user-attachments/assets/d213155c-8c71-4701-9bd5-45351febc2a8',
131
131
  'api': {
132
132
  'public': 'https://api.bitvavo.com',
133
133
  'private': 'https://api.bitvavo.com',
@@ -82,7 +82,7 @@ class bl3p(Exchange, ImplicitAPI):
82
82
  'ws': False,
83
83
  },
84
84
  'urls': {
85
- 'logo': 'https://user-images.githubusercontent.com/1294454/28501752-60c21b82-6feb-11e7-818b-055ee6d0e754.jpg',
85
+ 'logo': 'https://github.com/user-attachments/assets/75aeb14e-cd48-43c8-8492-dff002dea0be',
86
86
  'api': {
87
87
  'rest': 'https://api.bl3p.eu',
88
88
  },
@@ -82,7 +82,7 @@ class blockchaincom(Exchange, ImplicitAPI):
82
82
  },
83
83
  'timeframes': None,
84
84
  'urls': {
85
- 'logo': 'https://user-images.githubusercontent.com/1294454/147515585-1296e91b-7398-45e5-9d32-f6121538533f.jpeg',
85
+ 'logo': 'https://github.com/user-attachments/assets/975e3054-3399-4363-bcee-ec3c6d63d4e8',
86
86
  'test': {
87
87
  'public': 'https://testnet-api.delta.exchange',
88
88
  'private': 'https://testnet-api.delta.exchange',
@@ -162,7 +162,7 @@ class blofin(Exchange, ImplicitAPI):
162
162
  },
163
163
  'hostname': 'www.blofin.com',
164
164
  'urls': {
165
- 'logo': 'https://github.com/ccxt/ccxt/assets/43336371/255a7b29-341f-4d20-8342-fbfae4932807',
165
+ 'logo': 'https://github.com/user-attachments/assets/518cdf80-f05d-4821-a3e3-d48ceb41d73b',
166
166
  'api': {
167
167
  'rest': 'https://openapi.blofin.com',
168
168
  },
@@ -103,7 +103,7 @@ class btcalpha(Exchange, ImplicitAPI):
103
103
  '1d': 'D',
104
104
  },
105
105
  'urls': {
106
- 'logo': 'https://user-images.githubusercontent.com/1294454/42625213-dabaa5da-85cf-11e8-8f99-aa8f8f7699f0.jpg',
106
+ 'logo': 'https://github.com/user-attachments/assets/dce49f3a-61e5-4ba0-a2fe-41d192fd0e5d',
107
107
  'api': {
108
108
  'rest': 'https://btc-alpha.com/api',
109
109
  },
@@ -88,7 +88,7 @@ class btcbox(Exchange, ImplicitAPI):
88
88
  'ws': False,
89
89
  },
90
90
  'urls': {
91
- 'logo': 'https://user-images.githubusercontent.com/51840849/87327317-98c55400-c53c-11ea-9a11-81f7d951cc74.jpg',
91
+ 'logo': 'https://github.com/user-attachments/assets/1e2cb499-8d0f-4f8f-9464-3c015cfbc76b',
92
92
  'api': {
93
93
  'rest': 'https://www.btcbox.co.jp/api',
94
94
  },
@@ -91,7 +91,7 @@ class btcmarkets(Exchange, ImplicitAPI):
91
91
  'withdraw': True,
92
92
  },
93
93
  'urls': {
94
- 'logo': 'https://user-images.githubusercontent.com/51840849/89731817-b3fb8480-da52-11ea-817f-783b08aaf32b.jpg',
94
+ 'logo': 'https://github.com/user-attachments/assets/8c8d6907-3873-4cc4-ad20-e22fba28247e',
95
95
  'api': {
96
96
  'public': 'https://api.btcmarkets.net',
97
97
  'private': 'https://api.btcmarkets.net',
@@ -93,7 +93,7 @@ class btcturk(Exchange, ImplicitAPI):
93
93
  '1y': '1 y',
94
94
  },
95
95
  'urls': {
96
- 'logo': 'https://user-images.githubusercontent.com/51840849/87153926-efbef500-c2c0-11ea-9842-05b63612c4b9.jpg',
96
+ 'logo': 'https://github.com/user-attachments/assets/10e0a238-9f60-4b06-9dda-edfc7602f1d6',
97
97
  'api': {
98
98
  'public': 'https://api.btcturk.com/api/v2',
99
99
  'private': 'https://api.btcturk.com/api/v1',
@@ -174,7 +174,7 @@ class bybit(Exchange, ImplicitAPI):
174
174
  'public': 'https://api-testnet.{hostname}',
175
175
  'private': 'https://api-testnet.{hostname}',
176
176
  },
177
- 'logo': 'https://user-images.githubusercontent.com/51840849/76547799-daff5b80-649e-11ea-87fb-3be9bac08954.jpg',
177
+ 'logo': 'https://github.com/user-attachments/assets/97a5d0b3-de10-423d-90e1-6620960025ed',
178
178
  'api': {
179
179
  'spot': 'https://api.{hostname}',
180
180
  'futures': 'https://api.{hostname}',
@@ -2488,6 +2488,9 @@ class bybit(Exchange, ImplicitAPI):
2488
2488
  #
2489
2489
  data = self.safe_dict(response, 'result', {})
2490
2490
  tickerList = self.safe_list(data, 'list', [])
2491
+ timestamp = self.safe_integer(response, 'time')
2492
+ for i in range(0, len(tickerList)):
2493
+ tickerList[i]['timestamp'] = timestamp # will be removed inside the parser
2491
2494
  result = self.parse_funding_rates(tickerList)
2492
2495
  return self.filter_by_array(result, 'symbol', symbols)
2493
2496
 
@@ -90,6 +90,7 @@ class coinbase(Exchange, ImplicitAPI):
90
90
  'fetchDepositAddresses': False,
91
91
  'fetchDepositAddressesByNetwork': True,
92
92
  'fetchDeposits': True,
93
+ 'fetchDepositsWithdrawals': True,
93
94
  'fetchFundingHistory': False,
94
95
  'fetchFundingRate': False,
95
96
  'fetchFundingRateHistory': False,
@@ -758,8 +759,14 @@ class coinbase(Exchange, ImplicitAPI):
758
759
  :param int [since]: the earliest time in ms to fetch withdrawals for
759
760
  :param int [limit]: the maximum number of withdrawals structures to retrieve
760
761
  :param dict [params]: extra parameters specific to the exchange API endpoint
762
+ :param str [params.currencyType]: "fiat" or "crypto"
761
763
  :returns dict[]: a list of `transaction structures <https://docs.ccxt.com/#/?id=transaction-structure>`
762
764
  """
765
+ currencyType = None
766
+ currencyType, params = self.handle_option_and_params(params, 'fetchWithdrawals', 'currencyType')
767
+ if currencyType == 'crypto':
768
+ results = await self.fetch_transactions_with_method('v2PrivateGetAccountsAccountIdTransactions', code, since, limit, params)
769
+ return self.filter_by_array(results, 'type', 'withdrawal', False)
763
770
  return await self.fetch_transactions_with_method('v2PrivateGetAccountsAccountIdWithdrawals', code, since, limit, params)
764
771
 
765
772
  async def fetch_deposits(self, code: Str = None, since: Int = None, limit: Int = None, params={}) -> List[Transaction]:
@@ -770,10 +777,30 @@ class coinbase(Exchange, ImplicitAPI):
770
777
  :param int [since]: the earliest time in ms to fetch deposits for
771
778
  :param int [limit]: the maximum number of deposits structures to retrieve
772
779
  :param dict [params]: extra parameters specific to the exchange API endpoint
780
+ :param str [params.currencyType]: "fiat" or "crypto"
773
781
  :returns dict[]: a list of `transaction structures <https://docs.ccxt.com/#/?id=transaction-structure>`
774
782
  """
783
+ currencyType = None
784
+ currencyType, params = self.handle_option_and_params(params, 'fetchWithdrawals', 'currencyType')
785
+ if currencyType == 'crypto':
786
+ results = await self.fetch_transactions_with_method('v2PrivateGetAccountsAccountIdTransactions', code, since, limit, params)
787
+ return self.filter_by_array(results, 'type', 'deposit', False)
775
788
  return await self.fetch_transactions_with_method('v2PrivateGetAccountsAccountIdDeposits', code, since, limit, params)
776
789
 
790
+ async def fetch_deposits_withdrawals(self, code: Str = None, since: Int = None, limit: Int = None, params={}) -> List[Transaction]:
791
+ """
792
+ fetch history of deposits and withdrawals
793
+ :see: https://docs.cdp.coinbase.com/coinbase-app/docs/api-transactions
794
+ :param str [code]: unified currency code for the currency of the deposit/withdrawals, default is None
795
+ :param int [since]: timestamp in ms of the earliest deposit/withdrawal, default is None
796
+ :param int [limit]: max number of deposit/withdrawals to return, default = 50, Min: 1, Max: 100
797
+ :param dict [params]: extra parameters specific to the exchange API endpoint
798
+ :returns dict: a list of `transaction structure <https://docs.ccxt.com/#/?id=transaction-structure>`
799
+ """
800
+ await self.load_markets()
801
+ results = await self.fetch_transactions_with_method('v2PrivateGetAccountsAccountIdTransactions', code, since, limit, params)
802
+ return self.filter_by_array(results, 'type', ['deposit', 'withdrawal'], False)
803
+
777
804
  def parse_transaction_status(self, status: Str):
778
805
  statuses: dict = {
779
806
  'created': 'pending',
@@ -897,16 +924,59 @@ class coinbase(Exchange, ImplicitAPI):
897
924
  # "hide_native_amount": False
898
925
  # }
899
926
  #
927
+ #
928
+ # crypto deposit & withdrawal(using `/transactions` endpoint)
929
+ # {
930
+ # "amount": {
931
+ # "amount": "0.00014200",(negative for withdrawal)
932
+ # "currency": "BTC"
933
+ # },
934
+ # "created_at": "2024-03-29T15:48:30Z",
935
+ # "id": "0031a605-241d-514d-a97b-d4b99f3225d3",
936
+ # "idem": "092a979b-017e-4403-940a-2ca57811f442", # field present only in case of withdrawal
937
+ # "native_amount": {
938
+ # "amount": "9.85",(negative for withdrawal)
939
+ # "currency": "USD"
940
+ # },
941
+ # "network": {
942
+ # "status": "pending", # if status is `off_blockchain` then no more other fields are hasattr(self, present) object
943
+ # "hash": "5jYuvrNsvX2DZoMnzGYzVpYxJLfYu4GSK3xetG1H5LHrSovsuFCFYdFMwNRoiht3s6fBk92MM8QLLnz65xuEFTrE",
944
+ # "network_name": "solana",
945
+ # "transaction_fee": {
946
+ # "amount": "0.000100000",
947
+ # "currency": "SOL"
948
+ # }
949
+ # },
950
+ # "resource": "transaction",
951
+ # "resource_path": "/v2/accounts/dc504b1c-248e-5b68-a3b0-b991f7fa84e6/transactions/0031a605-241d-514d-a97b-d4b99f3225d3",
952
+ # "status": "completed",
953
+ # "type": "send",
954
+ # "from": { # in some cases, field might be present for deposit
955
+ # "id": "7fd10cd7-b091-5cee-ba41-c29e49a7cccf",
956
+ # "name": "Coinbase",
957
+ # "resource": "user"
958
+ # },
959
+ # "to": { # field only present for withdrawal
960
+ # "address": "5HA12BNthAvBwNYARYf9y5MqqCpB4qhCNFCs1Qw48ACE",
961
+ # "resource": "address"
962
+ # },
963
+ # "description": "C3 - One Time BTC Credit . Reference Case # 123.", # in some cases, field might be present for deposit
964
+ # }
965
+ #
900
966
  transactionType = self.safe_string(transaction, 'type')
901
967
  amountAndCurrencyObject = None
902
968
  feeObject = None
969
+ network = self.safe_dict(transaction, 'network', {})
903
970
  if transactionType == 'send':
904
- network = self.safe_dict(transaction, 'network', {})
905
- amountAndCurrencyObject = self.safe_dict(network, 'transaction_amount', {})
971
+ amountAndCurrencyObject = self.safe_dict(network, 'transaction_amount')
906
972
  feeObject = self.safe_dict(network, 'transaction_fee', {})
907
973
  else:
908
- amountAndCurrencyObject = self.safe_dict(transaction, 'subtotal', {})
974
+ amountAndCurrencyObject = self.safe_dict(transaction, 'subtotal')
909
975
  feeObject = self.safe_dict(transaction, 'fee', {})
976
+ if amountAndCurrencyObject is None:
977
+ amountAndCurrencyObject = self.safe_dict(transaction, 'amount')
978
+ amountString = self.safe_string(amountAndCurrencyObject, 'amount')
979
+ amountStringAbs = Precise.string_abs(amountString)
910
980
  status = self.parse_transaction_status(self.safe_string(transaction, 'status'))
911
981
  if status is None:
912
982
  committed = self.safe_bool(transaction, 'committed')
@@ -915,23 +985,31 @@ class coinbase(Exchange, ImplicitAPI):
915
985
  currencyId = self.safe_string(amountAndCurrencyObject, 'currency')
916
986
  feeCurrencyId = self.safe_string(feeObject, 'currency')
917
987
  datetime = self.safe_string(transaction, 'created_at')
918
- toObject = self.safe_dict(transaction, 'to', {})
919
- toAddress = self.safe_string(toObject, 'address')
988
+ resource = self.safe_string(transaction, 'resource')
989
+ type = resource
990
+ if not self.in_array(type, ['deposit', 'withdrawal']):
991
+ if Precise.string_gt(amountString, '0'):
992
+ type = 'deposit'
993
+ elif Precise.string_lt(amountString, '0'):
994
+ type = 'withdrawal'
995
+ toObject = self.safe_dict(transaction, 'to')
996
+ addressTo = self.safe_string(toObject, 'address')
997
+ networkId = self.safe_string(network, 'network_name')
920
998
  return {
921
999
  'info': transaction,
922
1000
  'id': id,
923
- 'txid': id,
1001
+ 'txid': self.safe_string(network, 'hash', id),
924
1002
  'timestamp': self.parse8601(datetime),
925
1003
  'datetime': datetime,
926
- 'network': None,
927
- 'address': toAddress,
928
- 'addressTo': toAddress,
1004
+ 'network': self.network_id_to_code(networkId),
1005
+ 'address': addressTo,
1006
+ 'addressTo': addressTo,
929
1007
  'addressFrom': None,
930
1008
  'tag': None,
931
1009
  'tagTo': None,
932
1010
  'tagFrom': None,
933
- 'type': self.safe_string(transaction, 'resource'),
934
- 'amount': self.safe_number(amountAndCurrencyObject, 'amount'),
1011
+ 'type': type,
1012
+ 'amount': self.parse_number(amountStringAbs),
935
1013
  'currency': self.safe_currency_code(currencyId, currency),
936
1014
  'status': status,
937
1015
  'updated': self.parse8601(self.safe_string(transaction, 'updated_at')),
@@ -4673,7 +4673,7 @@ class coinex(Exchange, ImplicitAPI):
4673
4673
  await self.load_markets()
4674
4674
  currency = self.currency(code)
4675
4675
  amountToPrecision = self.currency_to_precision(code, amount)
4676
- accountsByType = self.safe_dict(self.options, 'accountsById', {})
4676
+ accountsByType = self.safe_dict(self.options, 'accountsByType', {})
4677
4677
  fromId = self.safe_string(accountsByType, fromAccount, fromAccount)
4678
4678
  toId = self.safe_string(accountsByType, toAccount, toAccount)
4679
4679
  request: dict = {
@@ -923,22 +923,26 @@ class gate(Exchange, ImplicitAPI):
923
923
  """
924
924
  unifiedAccount = self.safe_bool(self.options, 'unifiedAccount')
925
925
  if unifiedAccount is None:
926
- response = await self.privateAccountGetDetail(params)
927
- #
928
- # {
929
- # "user_id": 10406147,
930
- # "ip_whitelist": [],
931
- # "currency_pairs": [],
932
- # "key": {
933
- # "mode": 1
934
- # },
935
- # "tier": 0,
936
- # "tier_expire_time": "0001-01-01T00:00:00Z",
937
- # "copy_trading_role": 0
938
- # }
939
- #
940
- result = self.safe_dict(response, 'key', {})
941
- self.options['unifiedAccount'] = self.safe_integer(result, 'mode') == 2
926
+ try:
927
+ #
928
+ # {
929
+ # "user_id": 10406147,
930
+ # "ip_whitelist": [],
931
+ # "currency_pairs": [],
932
+ # "key": {
933
+ # "mode": 1
934
+ # },
935
+ # "tier": 0,
936
+ # "tier_expire_time": "0001-01-01T00:00:00Z",
937
+ # "copy_trading_role": 0
938
+ # }
939
+ #
940
+ response = await self.privateAccountGetDetail(params)
941
+ result = self.safe_dict(response, 'key', {})
942
+ self.options['unifiedAccount'] = self.safe_integer(result, 'mode') == 2
943
+ except Exception as e:
944
+ # if the request fails, the unifiedAccount is disabled
945
+ self.options['unifiedAccount'] = False
942
946
 
943
947
  async def upgrade_unified_trade_account(self, params={}):
944
948
  return await self.privateUnifiedPutUnifiedMode(params)
@@ -157,7 +157,17 @@ class hyperliquid(Exchange, ImplicitAPI):
157
157
  'api': {
158
158
  'public': {
159
159
  'post': {
160
- 'info': 1,
160
+ 'info': {
161
+ 'cost': 20,
162
+ 'byType': {
163
+ 'l2Book': 2,
164
+ 'allMids': 2,
165
+ 'clearinghouseState': 2,
166
+ 'orderStatus': 2,
167
+ 'spotClearinghouseState': 2,
168
+ 'exchangeStatus': 2,
169
+ },
170
+ },
161
171
  },
162
172
  },
163
173
  'private': {
@@ -2852,6 +2862,14 @@ class hyperliquid(Exchange, ImplicitAPI):
2852
2862
  body = self.json(params)
2853
2863
  return {'url': url, 'method': method, 'body': body, 'headers': headers}
2854
2864
 
2865
+ def calculate_rate_limiter_cost(self, api, method, path, params, config={}):
2866
+ if ('byType' in config) and ('type' in params):
2867
+ type = params['type']
2868
+ byType = config['byType']
2869
+ if type in byType:
2870
+ return byType[type]
2871
+ return self.safe_value(config, 'cost', 1)
2872
+
2855
2873
  def parse_create_order_args(self, symbol: str, type: OrderType, side: OrderSide, amount: float, price: Num = None, params={}):
2856
2874
  market = self.market(symbol)
2857
2875
  vaultAddress = self.safe_string(params, 'vaultAddress')
@@ -1436,7 +1436,7 @@ class kraken(Exchange, ImplicitAPI):
1436
1436
  # {
1437
1437
  # "error": [],
1438
1438
  # "result": {
1439
- # "descr": {order: 'buy 0.02100000 ETHUSDT @ limit 330.00'},
1439
+ # "descr": {order: 'buy 0.02100000 ETHUSDT @ limit 330.00'}, # see more examples in "parseOrder"
1440
1440
  # "txid": ['OEKVV2-IH52O-TPL6GZ']
1441
1441
  # }
1442
1442
  # }
@@ -1496,9 +1496,10 @@ class kraken(Exchange, ImplicitAPI):
1496
1496
 
1497
1497
  def parse_order_type(self, status):
1498
1498
  statuses: dict = {
1499
+ # we dont add "space" delimited orders here(eg. stop loss) because they need separate parsing
1499
1500
  'take-profit': 'market',
1500
- 'stop-loss-limit': 'limit',
1501
1501
  'stop-loss': 'market',
1502
+ 'stop-loss-limit': 'limit',
1502
1503
  'take-profit-limit': 'limit',
1503
1504
  'trailing-stop-limit': 'limit',
1504
1505
  }
@@ -1506,30 +1507,19 @@ class kraken(Exchange, ImplicitAPI):
1506
1507
 
1507
1508
  def parse_order(self, order: dict, market: Market = None) -> Order:
1508
1509
  #
1509
- # createOrder for regular orders
1510
+ # createOrder
1510
1511
  #
1511
1512
  # {
1512
- # "descr": {order: 'buy 0.02100000 ETHUSDT @ limit 330.00'},
1513
+ # "descr": {
1514
+ # "order": "buy 0.02100000 ETHUSDT @ limit 330.00" # limit orders
1515
+ # "buy 0.12345678 ETHUSDT @ market" # market order
1516
+ # "sell 0.28002676 ETHUSDT @ stop loss 0.0123 -> limit 0.0.1222" # stop order
1517
+ # "sell 0.00100000 ETHUSDT @ stop loss 2677.00 -> limit 2577.00 with 5:1 leverage"
1518
+ # "buy 0.10000000 LTCUSDT @ take profit 75.00000 -> limit 74.00000"
1519
+ # "sell 10.00000000 XRPEUR @ trailing stop +50.0000%" # trailing stop
1520
+ # },
1513
1521
  # "txid": ['OEKVV2-IH52O-TPL6GZ']
1514
1522
  # }
1515
- # {
1516
- # "txid": ["TX_ID_HERE"],
1517
- # "descr": {"order":"buy 0.12345678 ETHEUR @ market"},
1518
- # }
1519
- #
1520
- #
1521
- # createOrder for stop orders
1522
- #
1523
- # {
1524
- # "txid":["OSILNC-VQI5Q-775ZDQ"],
1525
- # "descr":{"order":"sell 167.28002676 ADAXBT @ stop loss 0.00003280 -> limit 0.00003212"}
1526
- # }
1527
- #
1528
- #
1529
- # {
1530
- # "txid":["OVHMJV-BZW2V-6NZFWF"],
1531
- # "descr":{"order":"sell 0.00100000 ETHUSD @ stop loss 2677.00 -> limit 2577.00 with 5:1 leverage"}
1532
- # }
1533
1523
  #
1534
1524
  # editOrder
1535
1525
  #
@@ -1607,24 +1597,29 @@ class kraken(Exchange, ImplicitAPI):
1607
1597
  else:
1608
1598
  orderDescription = self.safe_string(order, 'descr')
1609
1599
  side = None
1610
- type = None
1600
+ rawType = None
1611
1601
  marketId = None
1612
1602
  price = None
1613
1603
  amount = None
1614
- stopPrice = None
1604
+ triggerPrice = None
1615
1605
  if orderDescription is not None:
1616
1606
  parts = orderDescription.split(' ')
1617
1607
  side = self.safe_string(parts, 0)
1618
1608
  amount = self.safe_string(parts, 1)
1619
1609
  marketId = self.safe_string(parts, 2)
1620
- type = self.safe_string(parts, 4)
1621
- if type == 'stop':
1622
- stopPrice = self.safe_string(parts, 6)
1610
+ part4 = self.safe_string(parts, 4)
1611
+ part5 = self.safe_string(parts, 5)
1612
+ if part4 == 'limit' or part4 == 'market':
1613
+ rawType = part4 # eg, limit, market
1614
+ else:
1615
+ rawType = part4 + ' ' + part5 # eg. stop loss, take profit, trailing stop
1616
+ if rawType == 'stop loss' or rawType == 'take profit':
1617
+ triggerPrice = self.safe_string(parts, 6)
1623
1618
  price = self.safe_string(parts, 9)
1624
- elif type == 'limit':
1619
+ elif rawType == 'limit':
1625
1620
  price = self.safe_string(parts, 5)
1626
1621
  side = self.safe_string(description, 'type', side)
1627
- type = self.safe_string(description, 'ordertype', type)
1622
+ rawType = self.safe_string(description, 'ordertype', rawType) # orderType has dash, e.g. trailing-stop
1628
1623
  marketId = self.safe_string(description, 'pair', marketId)
1629
1624
  foundMarket = self.find_market_by_altname_or_id(marketId)
1630
1625
  symbol = None
@@ -1676,15 +1671,28 @@ class kraken(Exchange, ImplicitAPI):
1676
1671
  trades.append(self.safe_trade({'id': rawTrade, 'orderId': id, 'symbol': symbol, 'info': {}}))
1677
1672
  else:
1678
1673
  trades.append(rawTrade)
1679
- stopPrice = self.omit_zero(self.safe_string(order, 'stopprice', stopPrice))
1674
+ # in #24192 PR, self field is not something consistent/actual
1675
+ # triggerPrice = self.omit_zero(self.safe_string(order, 'stopprice', triggerPrice))
1680
1676
  stopLossPrice = None
1681
1677
  takeProfitPrice = None
1682
- if type.startswith('take-profit'):
1678
+ # the dashed strings are not provided from fields(eg. fetch order)
1679
+ # while spaced strings from "order" sentence(when other fields not available)
1680
+ if rawType.startswith('take-profit'):
1683
1681
  takeProfitPrice = self.safe_string(description, 'price')
1684
1682
  price = self.omit_zero(self.safe_string(description, 'price2'))
1685
- elif type.startswith('stop-loss'):
1683
+ elif rawType.startswith('stop-loss'):
1686
1684
  stopLossPrice = self.safe_string(description, 'price')
1687
1685
  price = self.omit_zero(self.safe_string(description, 'price2'))
1686
+ elif rawType == 'take profit':
1687
+ takeProfitPrice = triggerPrice
1688
+ elif rawType == 'stop loss':
1689
+ stopLossPrice = triggerPrice
1690
+ finalType = self.parse_order_type(rawType)
1691
+ # unlike from endpoints which provide eg: "take-profit-limit"
1692
+ # for "space-delimited" orders we dont have market/limit suffixes, their format is
1693
+ # eg: `stop loss > limit 123`, so we need to parse them manually
1694
+ if self.in_array(finalType, ['stop loss', 'take profit']):
1695
+ finalType = 'market' if (price is None) else 'limit'
1688
1696
  return self.safe_order({
1689
1697
  'id': id,
1690
1698
  'clientOrderId': clientOrderId,
@@ -1694,13 +1702,13 @@ class kraken(Exchange, ImplicitAPI):
1694
1702
  'lastTradeTimestamp': None,
1695
1703
  'status': status,
1696
1704
  'symbol': symbol,
1697
- 'type': self.parse_order_type(type),
1705
+ 'type': finalType,
1698
1706
  'timeInForce': None,
1699
1707
  'postOnly': isPostOnly,
1700
1708
  'side': side,
1701
1709
  'price': price,
1702
- 'stopPrice': stopPrice,
1703
- 'triggerPrice': stopPrice,
1710
+ 'stopPrice': triggerPrice,
1711
+ 'triggerPrice': triggerPrice,
1704
1712
  'takeProfitPrice': takeProfitPrice,
1705
1713
  'stopLossPrice': stopLossPrice,
1706
1714
  'cost': None,