ccxt 4.4.49__py2.py3-none-any.whl → 4.4.50__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 +1 -1
- ccxt/abstract/binance.py +1 -0
- ccxt/abstract/binancecoinm.py +1 -0
- ccxt/abstract/binanceus.py +1 -0
- ccxt/abstract/binanceusdm.py +1 -0
- ccxt/alpaca.py +62 -1
- ccxt/async_support/__init__.py +1 -1
- ccxt/async_support/alpaca.py +62 -1
- ccxt/async_support/base/exchange.py +1 -1
- ccxt/async_support/binance.py +8 -4
- ccxt/async_support/blofin.py +1 -1
- ccxt/async_support/coinex.py +3 -3
- ccxt/async_support/hollaex.py +12 -16
- ccxt/async_support/kucoin.py +47 -67
- ccxt/async_support/mexc.py +3 -2
- ccxt/async_support/okcoin.py +13 -5
- ccxt/async_support/paymium.py +42 -0
- ccxt/async_support/probit.py +68 -1
- ccxt/async_support/timex.py +67 -0
- ccxt/async_support/tokocrypto.py +81 -4
- ccxt/async_support/tradeogre.py +58 -1
- ccxt/async_support/whitebit.py +10 -4
- ccxt/base/exchange.py +62 -1
- ccxt/binance.py +8 -4
- ccxt/blofin.py +1 -1
- ccxt/coinex.py +3 -3
- ccxt/hollaex.py +12 -16
- ccxt/kucoin.py +47 -67
- ccxt/mexc.py +3 -2
- ccxt/okcoin.py +13 -5
- ccxt/paymium.py +42 -0
- ccxt/pro/__init__.py +1 -1
- ccxt/probit.py +68 -1
- ccxt/timex.py +67 -0
- ccxt/tokocrypto.py +81 -4
- ccxt/tradeogre.py +58 -1
- ccxt/whitebit.py +10 -4
- {ccxt-4.4.49.dist-info → ccxt-4.4.50.dist-info}/METADATA +4 -4
- {ccxt-4.4.49.dist-info → ccxt-4.4.50.dist-info}/RECORD +42 -42
- {ccxt-4.4.49.dist-info → ccxt-4.4.50.dist-info}/LICENSE.txt +0 -0
- {ccxt-4.4.49.dist-info → ccxt-4.4.50.dist-info}/WHEEL +0 -0
- {ccxt-4.4.49.dist-info → ccxt-4.4.50.dist-info}/top_level.txt +0 -0
ccxt/async_support/paymium.py
CHANGED
@@ -113,6 +113,48 @@ class paymium(Exchange, ImplicitAPI):
|
|
113
113
|
},
|
114
114
|
},
|
115
115
|
'precisionMode': TICK_SIZE,
|
116
|
+
'features': {
|
117
|
+
'spot': {
|
118
|
+
'sandbox': False,
|
119
|
+
'createOrder': {
|
120
|
+
'marginMode': False,
|
121
|
+
'triggerPrice': False,
|
122
|
+
'triggerDirection': False,
|
123
|
+
'triggerPriceType': None,
|
124
|
+
'stopLossPrice': False,
|
125
|
+
'takeProfitPrice': False,
|
126
|
+
'attachedStopLossTakeProfit': None,
|
127
|
+
'timeInForce': {
|
128
|
+
'IOC': False,
|
129
|
+
'FOK': False,
|
130
|
+
'PO': False,
|
131
|
+
'GTD': False,
|
132
|
+
},
|
133
|
+
'hedged': False,
|
134
|
+
'trailing': False,
|
135
|
+
'leverage': False,
|
136
|
+
'marketBuyByCost': True, # todo
|
137
|
+
'marketBuyRequiresPrice': False,
|
138
|
+
'selfTradePrevention': False,
|
139
|
+
'iceberg': False,
|
140
|
+
},
|
141
|
+
'createOrders': None,
|
142
|
+
'fetchMyTrades': None,
|
143
|
+
'fetchOrder': None, # todo
|
144
|
+
'fetchOpenOrders': None, # todo
|
145
|
+
'fetchOrders': None, # todo
|
146
|
+
'fetchClosedOrders': None, # todo
|
147
|
+
'fetchOHLCV': None, # todo
|
148
|
+
},
|
149
|
+
'swap': {
|
150
|
+
'linear': None,
|
151
|
+
'inverse': None,
|
152
|
+
},
|
153
|
+
'future': {
|
154
|
+
'linear': None,
|
155
|
+
'inverse': None,
|
156
|
+
},
|
157
|
+
},
|
116
158
|
})
|
117
159
|
|
118
160
|
def parse_balance(self, response) -> Balances:
|
ccxt/async_support/probit.py
CHANGED
@@ -103,7 +103,7 @@ class probit(Exchange, ImplicitAPI):
|
|
103
103
|
'fetchWithdrawal': False,
|
104
104
|
'fetchWithdrawals': True,
|
105
105
|
'reduceMargin': False,
|
106
|
-
'sandbox':
|
106
|
+
'sandbox': False,
|
107
107
|
'setLeverage': False,
|
108
108
|
'setMarginMode': False,
|
109
109
|
'setPositionMode': False,
|
@@ -185,6 +185,73 @@ class probit(Exchange, ImplicitAPI):
|
|
185
185
|
'taker': self.parse_number('0.002'),
|
186
186
|
},
|
187
187
|
},
|
188
|
+
'features': {
|
189
|
+
'spot': {
|
190
|
+
'sandbox': False,
|
191
|
+
'createOrder': {
|
192
|
+
'marginMode': False,
|
193
|
+
'triggerPrice': False,
|
194
|
+
'triggerDirection': False,
|
195
|
+
'triggerPriceType': None,
|
196
|
+
'stopLossPrice': False,
|
197
|
+
'takeProfitPrice': False,
|
198
|
+
'attachedStopLossTakeProfit': None,
|
199
|
+
# todo
|
200
|
+
'timeInForce': {
|
201
|
+
'IOC': True,
|
202
|
+
'FOK': True,
|
203
|
+
'PO': False,
|
204
|
+
'GTD': False,
|
205
|
+
},
|
206
|
+
'hedged': False,
|
207
|
+
'trailing': False,
|
208
|
+
'leverage': False,
|
209
|
+
'marketBuyByCost': True,
|
210
|
+
'marketBuyRequiresPrice': False,
|
211
|
+
'selfTradePrevention': False,
|
212
|
+
'iceberg': False,
|
213
|
+
},
|
214
|
+
'createOrders': None,
|
215
|
+
'fetchMyTrades': {
|
216
|
+
'marginMode': False,
|
217
|
+
'limit': 1000,
|
218
|
+
'daysBack': 100000, # todo
|
219
|
+
'untilDays': 100000, # todo
|
220
|
+
},
|
221
|
+
'fetchOrder': {
|
222
|
+
'marginMode': False,
|
223
|
+
'trigger': False,
|
224
|
+
'trailing': False,
|
225
|
+
},
|
226
|
+
'fetchOpenOrders': {
|
227
|
+
'marginMode': False,
|
228
|
+
'limit': None,
|
229
|
+
'trigger': False,
|
230
|
+
'trailing': False,
|
231
|
+
},
|
232
|
+
'fetchOrders': None,
|
233
|
+
'fetchClosedOrders': {
|
234
|
+
'marginMode': False,
|
235
|
+
'limit': 1000,
|
236
|
+
'daysBack': 100000, # todo
|
237
|
+
'daysBackCanceled': 1, # todo
|
238
|
+
'untilDays': 90,
|
239
|
+
'trigger': False,
|
240
|
+
'trailing': False,
|
241
|
+
},
|
242
|
+
'fetchOHLCV': {
|
243
|
+
'limit': 4000,
|
244
|
+
},
|
245
|
+
},
|
246
|
+
'swap': {
|
247
|
+
'linear': None,
|
248
|
+
'inverse': None,
|
249
|
+
},
|
250
|
+
'future': {
|
251
|
+
'linear': None,
|
252
|
+
'inverse': None,
|
253
|
+
},
|
254
|
+
},
|
188
255
|
'exceptions': {
|
189
256
|
'exact': {
|
190
257
|
'UNAUTHORIZED': AuthenticationError,
|
ccxt/async_support/timex.py
CHANGED
@@ -281,6 +281,73 @@ class timex(Exchange, ImplicitAPI):
|
|
281
281
|
'defaultSort': 'timestamp,asc',
|
282
282
|
'defaultSortOrders': 'createdAt,asc',
|
283
283
|
},
|
284
|
+
'features': {
|
285
|
+
'spot': {
|
286
|
+
'sandbox': False,
|
287
|
+
'createOrder': {
|
288
|
+
'marginMode': False,
|
289
|
+
'triggerPrice': False,
|
290
|
+
'triggerDirection': False,
|
291
|
+
'triggerPriceType': None,
|
292
|
+
'stopLossPrice': False,
|
293
|
+
'takeProfitPrice': False,
|
294
|
+
'attachedStopLossTakeProfit': None,
|
295
|
+
# todo
|
296
|
+
'timeInForce': {
|
297
|
+
'IOC': True,
|
298
|
+
'FOK': True,
|
299
|
+
'PO': False,
|
300
|
+
'GTD': True,
|
301
|
+
},
|
302
|
+
'hedged': False,
|
303
|
+
'trailing': False,
|
304
|
+
'leverage': False,
|
305
|
+
'marketBuyByCost': False,
|
306
|
+
'marketBuyRequiresPrice': False,
|
307
|
+
'selfTradePrevention': False,
|
308
|
+
'iceberg': False,
|
309
|
+
},
|
310
|
+
'createOrders': None,
|
311
|
+
'fetchMyTrades': {
|
312
|
+
'marginMode': False,
|
313
|
+
'limit': 100, # todo
|
314
|
+
'daysBack': 100000, # todo
|
315
|
+
'untilDays': 100000, # todo
|
316
|
+
},
|
317
|
+
'fetchOrder': {
|
318
|
+
'marginMode': False,
|
319
|
+
'trigger': False,
|
320
|
+
'trailing': False,
|
321
|
+
},
|
322
|
+
'fetchOpenOrders': {
|
323
|
+
'marginMode': False,
|
324
|
+
'limit': 100, # todo
|
325
|
+
'trigger': False,
|
326
|
+
'trailing': False,
|
327
|
+
},
|
328
|
+
'fetchOrders': None, # todo
|
329
|
+
'fetchClosedOrders': {
|
330
|
+
'marginMode': False,
|
331
|
+
'limit': 100, # todo
|
332
|
+
'daysBack': 100000, # todo
|
333
|
+
'daysBackCanceled': 1, # todo
|
334
|
+
'untilDays': 100000, # todo
|
335
|
+
'trigger': False,
|
336
|
+
'trailing': False,
|
337
|
+
},
|
338
|
+
'fetchOHLCV': {
|
339
|
+
'limit': None,
|
340
|
+
},
|
341
|
+
},
|
342
|
+
'swap': {
|
343
|
+
'linear': None,
|
344
|
+
'inverse': None,
|
345
|
+
},
|
346
|
+
'future': {
|
347
|
+
'linear': None,
|
348
|
+
'inverse': None,
|
349
|
+
},
|
350
|
+
},
|
284
351
|
})
|
285
352
|
|
286
353
|
async def fetch_time(self, params={}):
|
ccxt/async_support/tokocrypto.py
CHANGED
@@ -619,6 +619,79 @@ class tokocrypto(Exchange, ImplicitAPI):
|
|
619
619
|
'MAX_POSITION': InvalidOrder, # {"code":-2010,"msg":"Filter failure: MAX_POSITION"}
|
620
620
|
},
|
621
621
|
},
|
622
|
+
'features': {
|
623
|
+
'spot': {
|
624
|
+
'sandbox': False,
|
625
|
+
'createOrder': {
|
626
|
+
'marginMode': False,
|
627
|
+
'triggerPrice': True,
|
628
|
+
'triggerDirection': False,
|
629
|
+
'triggerPriceType': None,
|
630
|
+
'stopLossPrice': False, # todo
|
631
|
+
'takeProfitPrice': False, # todo
|
632
|
+
'attachedStopLossTakeProfit': None,
|
633
|
+
'timeInForce': {
|
634
|
+
'IOC': True,
|
635
|
+
'FOK': True,
|
636
|
+
'PO': True,
|
637
|
+
'GTD': False,
|
638
|
+
},
|
639
|
+
'hedged': False,
|
640
|
+
'trailing': False,
|
641
|
+
'leverage': False,
|
642
|
+
'marketBuyByCost': True,
|
643
|
+
'marketBuyRequiresPrice': True,
|
644
|
+
'selfTradePrevention': True, # todo
|
645
|
+
'iceberg': True, # todo
|
646
|
+
},
|
647
|
+
'createOrders': None,
|
648
|
+
'fetchMyTrades': {
|
649
|
+
'marginMode': False,
|
650
|
+
'limit': 1000,
|
651
|
+
'daysBack': 100000, # todo
|
652
|
+
'untilDays': 100000, # todo
|
653
|
+
},
|
654
|
+
'fetchOrder': {
|
655
|
+
'marginMode': False,
|
656
|
+
'trigger': False,
|
657
|
+
'trailing': False,
|
658
|
+
},
|
659
|
+
'fetchOpenOrders': {
|
660
|
+
'marginMode': False,
|
661
|
+
'limit': 1000,
|
662
|
+
'trigger': False,
|
663
|
+
'trailing': False,
|
664
|
+
},
|
665
|
+
'fetchOrders': {
|
666
|
+
'marginMode': False,
|
667
|
+
'limit': 1000,
|
668
|
+
'daysBack': 100000,
|
669
|
+
'untilDays': 100000,
|
670
|
+
'trigger': False,
|
671
|
+
'trailing': False,
|
672
|
+
},
|
673
|
+
'fetchClosedOrders': {
|
674
|
+
'marginMode': False,
|
675
|
+
'limit': 1000,
|
676
|
+
'daysBack': 100000, # todo
|
677
|
+
'daysBackCanceled': 1, # todo
|
678
|
+
'untilDays': 100000, # todo
|
679
|
+
'trigger': False,
|
680
|
+
'trailing': False,
|
681
|
+
},
|
682
|
+
'fetchOHLCV': {
|
683
|
+
'limit': 1000,
|
684
|
+
},
|
685
|
+
},
|
686
|
+
'swap': {
|
687
|
+
'linear': None,
|
688
|
+
'inverse': None,
|
689
|
+
},
|
690
|
+
'future': {
|
691
|
+
'linear': None,
|
692
|
+
'inverse': None,
|
693
|
+
},
|
694
|
+
},
|
622
695
|
})
|
623
696
|
|
624
697
|
def nonce(self):
|
@@ -635,9 +708,14 @@ class tokocrypto(Exchange, ImplicitAPI):
|
|
635
708
|
"""
|
636
709
|
response = await self.publicGetOpenV1CommonTime(params)
|
637
710
|
#
|
711
|
+
# {
|
712
|
+
# "code": 0,
|
713
|
+
# "msg": "Success",
|
714
|
+
# "data": null,
|
715
|
+
# "timestamp": 1737378074159
|
716
|
+
# }
|
638
717
|
#
|
639
|
-
|
640
|
-
return self.safe_integer(response, 'serverTime')
|
718
|
+
return self.safe_integer(response, 'timestamp')
|
641
719
|
|
642
720
|
async def fetch_markets(self, params={}) -> List[Market]:
|
643
721
|
"""
|
@@ -1575,7 +1653,6 @@ class tokocrypto(Exchange, ImplicitAPI):
|
|
1575
1653
|
create a trade order
|
1576
1654
|
|
1577
1655
|
https://www.tokocrypto.com/apidocs/#new-order--signed
|
1578
|
-
https://www.tokocrypto.com/apidocs/#account-trade-list-signed
|
1579
1656
|
|
1580
1657
|
:param str symbol: unified symbol of the market to create an order in
|
1581
1658
|
:param str type: 'market' or 'limit'
|
@@ -1733,7 +1810,7 @@ class tokocrypto(Exchange, ImplicitAPI):
|
|
1733
1810
|
async def fetch_order(self, id: str, symbol: Str = None, params={}):
|
1734
1811
|
"""
|
1735
1812
|
|
1736
|
-
https://www.tokocrypto.com/apidocs/#
|
1813
|
+
https://www.tokocrypto.com/apidocs/#query-order-signed
|
1737
1814
|
|
1738
1815
|
fetches information on an order made by the user
|
1739
1816
|
:param str id: order id
|
ccxt/async_support/tradeogre.py
CHANGED
@@ -164,6 +164,57 @@ class tradeogre(Exchange, ImplicitAPI):
|
|
164
164
|
},
|
165
165
|
'options': {
|
166
166
|
},
|
167
|
+
'features': {
|
168
|
+
'spot': {
|
169
|
+
'sandbox': False,
|
170
|
+
'createOrder': {
|
171
|
+
'marginMode': False,
|
172
|
+
'triggerPrice': False,
|
173
|
+
'triggerDirection': False,
|
174
|
+
'triggerPriceType': None,
|
175
|
+
'stopLossPrice': False,
|
176
|
+
'takeProfitPrice': False,
|
177
|
+
'attachedStopLossTakeProfit': None,
|
178
|
+
'timeInForce': {
|
179
|
+
'IOC': False,
|
180
|
+
'FOK': False,
|
181
|
+
'PO': False,
|
182
|
+
'GTD': False,
|
183
|
+
},
|
184
|
+
'hedged': False,
|
185
|
+
'trailing': False,
|
186
|
+
'leverage': False,
|
187
|
+
'marketBuyByCost': False,
|
188
|
+
'marketBuyRequiresPrice': False,
|
189
|
+
'selfTradePrevention': False,
|
190
|
+
'iceberg': False,
|
191
|
+
},
|
192
|
+
'createOrders': None,
|
193
|
+
'fetchMyTrades': None,
|
194
|
+
'fetchOrder': {
|
195
|
+
'marginMode': False,
|
196
|
+
'trigger': False,
|
197
|
+
'trailing': False,
|
198
|
+
},
|
199
|
+
'fetchOpenOrders': {
|
200
|
+
'marginMode': False,
|
201
|
+
'limit': None,
|
202
|
+
'trigger': False,
|
203
|
+
'trailing': False,
|
204
|
+
},
|
205
|
+
'fetchOrders': None,
|
206
|
+
'fetchClosedOrders': None,
|
207
|
+
'fetchOHLCV': None, # todo
|
208
|
+
},
|
209
|
+
'swap': {
|
210
|
+
'linear': None,
|
211
|
+
'inverse': None,
|
212
|
+
},
|
213
|
+
'future': {
|
214
|
+
'linear': None,
|
215
|
+
'inverse': None,
|
216
|
+
},
|
217
|
+
},
|
167
218
|
})
|
168
219
|
|
169
220
|
async def fetch_markets(self, params={}) -> List[Market]:
|
@@ -442,6 +493,9 @@ class tradeogre(Exchange, ImplicitAPI):
|
|
442
493
|
async def create_order(self, symbol: str, type: OrderType, side: OrderSide, amount: float, price: Num = None, params={}):
|
443
494
|
"""
|
444
495
|
create a trade order
|
496
|
+
|
497
|
+
https://tradeogre.com/help/api#:~:text=u%20%27%7Bpublic%7D%3A%7Bprivate%7D%27-,Submit%20Buy%20Order
|
498
|
+
|
445
499
|
:param str symbol: unified symbol of the market to create an order in
|
446
500
|
:param str type: must be 'limit'
|
447
501
|
:param str side: 'buy' or 'sell'
|
@@ -499,6 +553,9 @@ class tradeogre(Exchange, ImplicitAPI):
|
|
499
553
|
async def fetch_open_orders(self, symbol: Str = None, since: Int = None, limit: Int = None, params={}):
|
500
554
|
"""
|
501
555
|
fetch all unfilled currently open orders
|
556
|
+
|
557
|
+
https://tradeogre.com/help/api#:~:text=%7B%22success%22%3Atrue%7D-,Get%20Orders,-Method%20(POST)
|
558
|
+
|
502
559
|
:param str symbol: unified market symbol of the market orders were made in
|
503
560
|
:param int [since]: the earliest time in ms to fetch orders for
|
504
561
|
:param int [limit]: the maximum number of order structures to retrieve
|
@@ -519,7 +576,7 @@ class tradeogre(Exchange, ImplicitAPI):
|
|
519
576
|
"""
|
520
577
|
fetches information on an order made by the user
|
521
578
|
|
522
|
-
https://
|
579
|
+
https://tradeogre.com/help/api#:~:text=market%22%3A%22XMR%2DBTC%22%7D%5D-,Get%20Order,-Method%20(GET)
|
523
580
|
|
524
581
|
:param str id: order id
|
525
582
|
:param str symbol: unified symbol of the market the order was made in
|
ccxt/async_support/whitebit.py
CHANGED
@@ -272,6 +272,8 @@ class whitebit(Exchange, ImplicitAPI):
|
|
272
272
|
},
|
273
273
|
},
|
274
274
|
'options': {
|
275
|
+
'timeDifference': 0, # the difference between system clock and exchange clock
|
276
|
+
'adjustForTimeDifference': False, # controls the adjustment logic upon instantiation
|
275
277
|
'fiatCurrencies': ['EUR', 'USD', 'RUB', 'UAH'],
|
276
278
|
'fetchBalance': {
|
277
279
|
'account': 'spot',
|
@@ -328,6 +330,8 @@ class whitebit(Exchange, ImplicitAPI):
|
|
328
330
|
:param dict [params]: extra parameters specific to the exchange API endpoint
|
329
331
|
:returns dict[]: an array of objects representing market data
|
330
332
|
"""
|
333
|
+
if self.options['adjustForTimeDifference']:
|
334
|
+
await self.load_time_difference()
|
331
335
|
markets = await self.v4PublicGetMarkets()
|
332
336
|
#
|
333
337
|
# [
|
@@ -1227,7 +1231,7 @@ class whitebit(Exchange, ImplicitAPI):
|
|
1227
1231
|
response = await self.v4PublicGetTime(params)
|
1228
1232
|
#
|
1229
1233
|
# {
|
1230
|
-
# "time":
|
1234
|
+
# "time":1737380046
|
1231
1235
|
# }
|
1232
1236
|
#
|
1233
1237
|
return self.safe_integer(response, 'time')
|
@@ -2514,7 +2518,7 @@ class whitebit(Exchange, ImplicitAPI):
|
|
2514
2518
|
return self.in_array(currency, fiatCurrencies)
|
2515
2519
|
|
2516
2520
|
def nonce(self):
|
2517
|
-
return self.milliseconds()
|
2521
|
+
return self.milliseconds() - self.options['timeDifference']
|
2518
2522
|
|
2519
2523
|
def sign(self, path, api='public', method='GET', params={}, headers=None, body=None):
|
2520
2524
|
query = self.omit(params, self.extract_params(path))
|
@@ -2527,10 +2531,12 @@ class whitebit(Exchange, ImplicitAPI):
|
|
2527
2531
|
url += '?' + self.urlencode(query)
|
2528
2532
|
if accessibility == 'private':
|
2529
2533
|
self.check_required_credentials()
|
2530
|
-
nonce =
|
2534
|
+
nonce = self.nonce()
|
2535
|
+
timestamp = self.parse_to_int(nonce / 1000)
|
2536
|
+
timestampString = str(timestamp)
|
2531
2537
|
secret = self.encode(self.secret)
|
2532
2538
|
request = '/' + 'api' + '/' + version + pathWithParams
|
2533
|
-
body = self.json(self.extend({'request': request, 'nonce':
|
2539
|
+
body = self.json(self.extend({'request': request, 'nonce': timestampString}, params))
|
2534
2540
|
payload = self.string_to_base64(body)
|
2535
2541
|
signature = self.hmac(self.encode(payload), secret, hashlib.sha512)
|
2536
2542
|
headers = {
|
ccxt/base/exchange.py
CHANGED
@@ -4,7 +4,7 @@
|
|
4
4
|
|
5
5
|
# -----------------------------------------------------------------------------
|
6
6
|
|
7
|
-
__version__ = '4.4.
|
7
|
+
__version__ = '4.4.50'
|
8
8
|
|
9
9
|
# -----------------------------------------------------------------------------
|
10
10
|
|
@@ -2876,6 +2876,67 @@ class Exchange(object):
|
|
2876
2876
|
}
|
2877
2877
|
|
2878
2878
|
def safe_currency_structure(self, currency: object):
|
2879
|
+
# derive data from networks: deposit, withdraw, active, fee, limits, precision
|
2880
|
+
networks = self.safe_dict(currency, 'networks', {})
|
2881
|
+
keys = list(networks.keys())
|
2882
|
+
length = len(keys)
|
2883
|
+
if length != 0:
|
2884
|
+
for i in range(0, length):
|
2885
|
+
network = networks[keys[i]]
|
2886
|
+
deposit = self.safe_bool(network, 'deposit')
|
2887
|
+
if currency['deposit'] is None or deposit:
|
2888
|
+
currency['deposit'] = deposit
|
2889
|
+
withdraw = self.safe_bool(network, 'withdraw')
|
2890
|
+
if currency['withdraw'] is None or withdraw:
|
2891
|
+
currency['withdraw'] = withdraw
|
2892
|
+
active = self.safe_bool(network, 'active')
|
2893
|
+
if currency['active'] is None or active:
|
2894
|
+
currency['active'] = active
|
2895
|
+
# find lowest fee(which is more desired)
|
2896
|
+
fee = self.safe_string(network, 'fee')
|
2897
|
+
feeMain = self.safe_string(currency, 'fee')
|
2898
|
+
if feeMain is None or Precise.string_lt(fee, feeMain):
|
2899
|
+
currency['fee'] = self.parse_number(fee)
|
2900
|
+
# find lowest precision(which is more desired)
|
2901
|
+
precision = self.safe_string(network, 'precision')
|
2902
|
+
precisionMain = self.safe_string(currency, 'precision')
|
2903
|
+
if precisionMain is None or Precise.string_lt(precision, precisionMain):
|
2904
|
+
currency['precision'] = self.parse_number(precision)
|
2905
|
+
# limits
|
2906
|
+
limits = self.safe_dict(network, 'limits')
|
2907
|
+
limitsMain = self.safe_dict(currency, 'limits')
|
2908
|
+
if limitsMain is None:
|
2909
|
+
currency['limits'] = {}
|
2910
|
+
# deposits
|
2911
|
+
limitsDeposit = self.safe_dict(limits, 'deposit')
|
2912
|
+
limitsDepositMain = self.safe_dict(limitsMain, 'deposit')
|
2913
|
+
if limitsDepositMain is None:
|
2914
|
+
currency['limits']['deposit'] = {}
|
2915
|
+
limitsDepositMin = self.safe_string(limitsDeposit, 'min')
|
2916
|
+
limitsDepositMax = self.safe_string(limitsDeposit, 'max')
|
2917
|
+
limitsDepositMinMain = self.safe_string(limitsDepositMain, 'min')
|
2918
|
+
limitsDepositMaxMain = self.safe_string(limitsDepositMain, 'max')
|
2919
|
+
# find min
|
2920
|
+
if limitsDepositMinMain is None or Precise.string_lt(limitsDepositMin, limitsDepositMinMain):
|
2921
|
+
currency['limits']['deposit']['min'] = self.parse_number(limitsDepositMin)
|
2922
|
+
# find max
|
2923
|
+
if limitsDepositMaxMain is None or Precise.string_gt(limitsDepositMax, limitsDepositMaxMain):
|
2924
|
+
currency['limits']['deposit']['max'] = self.parse_number(limitsDepositMax)
|
2925
|
+
# withdrawals
|
2926
|
+
limitsWithdraw = self.safe_dict(limits, 'withdraw')
|
2927
|
+
limitsWithdrawMain = self.safe_dict(limitsMain, 'withdraw')
|
2928
|
+
if limitsWithdrawMain is None:
|
2929
|
+
currency['limits']['withdraw'] = {}
|
2930
|
+
limitsWithdrawMin = self.safe_string(limitsWithdraw, 'min')
|
2931
|
+
limitsWithdrawMax = self.safe_string(limitsWithdraw, 'max')
|
2932
|
+
limitsWithdrawMinMain = self.safe_string(limitsWithdrawMain, 'min')
|
2933
|
+
limitsWithdrawMaxMain = self.safe_string(limitsWithdrawMain, 'max')
|
2934
|
+
# find min
|
2935
|
+
if limitsWithdrawMinMain is None or Precise.string_lt(limitsWithdrawMin, limitsWithdrawMinMain):
|
2936
|
+
currency['limits']['withdraw']['min'] = self.parse_number(limitsWithdrawMin)
|
2937
|
+
# find max
|
2938
|
+
if limitsWithdrawMaxMain is None or Precise.string_gt(limitsWithdrawMax, limitsWithdrawMaxMain):
|
2939
|
+
currency['limits']['withdraw']['max'] = self.parse_number(limitsWithdrawMax)
|
2879
2940
|
return self.extend({
|
2880
2941
|
'info': None,
|
2881
2942
|
'id': None,
|
ccxt/binance.py
CHANGED
@@ -502,6 +502,7 @@ class binance(Exchange, ImplicitAPI):
|
|
502
502
|
'portfolio/repay-futures-switch': 3, # Weight(IP): 30 => cost = 0.1 * 30 = 3
|
503
503
|
'portfolio/margin-asset-leverage': 5, # Weight(IP): 50 => cost = 0.1 * 50 = 5
|
504
504
|
'portfolio/balance': 2,
|
505
|
+
'portfolio/negative-balance-exchange-record': 2,
|
505
506
|
# staking
|
506
507
|
'staking/productList': 0.1,
|
507
508
|
'staking/position': 0.1,
|
@@ -5000,11 +5001,13 @@ class binance(Exchange, ImplicitAPI):
|
|
5000
5001
|
until = self.safe_integer(params, 'until')
|
5001
5002
|
if until is not None:
|
5002
5003
|
request['endTime'] = until
|
5003
|
-
if limit is not None:
|
5004
|
-
isFutureOrSwap = (market['swap'] or market['future'])
|
5005
|
-
request['limit'] = min(limit, 1000) if isFutureOrSwap else limit # default = 500, maximum = 1000
|
5006
5004
|
method = self.safe_string(self.options, 'fetchTradesMethod')
|
5007
5005
|
method = self.safe_string_2(params, 'fetchTradesMethod', 'method', method)
|
5006
|
+
if limit is not None:
|
5007
|
+
isFutureOrSwap = (market['swap'] or market['future'])
|
5008
|
+
isHistoricalEndpoint = (method is not None) and (method.find('GetHistoricalTrades') >= 0)
|
5009
|
+
maxLimitForContractHistorical = 500 if isHistoricalEndpoint else 1000
|
5010
|
+
request['limit'] = min(limit, maxLimitForContractHistorical) if isFutureOrSwap else limit # default = 500, maximum = 1000
|
5008
5011
|
params = self.omit(params, ['until', 'fetchTradesMethod'])
|
5009
5012
|
response = None
|
5010
5013
|
if market['option'] or method == 'eapiPublicGetTrades':
|
@@ -6836,6 +6839,7 @@ class binance(Exchange, ImplicitAPI):
|
|
6836
6839
|
:param str symbol: unified market symbol
|
6837
6840
|
:param dict [params]: extra parameters specific to the exchange API endpoint
|
6838
6841
|
:param str [params.trigger]: set to True if you would like to fetch portfolio margin account stop or conditional orders
|
6842
|
+
:param boolean [params.portfolioMargin]: set to True if you would like to fetch for a portfolio margin account
|
6839
6843
|
:returns dict: an `order structure <https://docs.ccxt.com/#/?id=order-structure>`
|
6840
6844
|
"""
|
6841
6845
|
if symbol is None:
|
@@ -10158,7 +10162,7 @@ class binance(Exchange, ImplicitAPI):
|
|
10158
10162
|
# }
|
10159
10163
|
#
|
10160
10164
|
marketId = self.safe_string(position, 'symbol')
|
10161
|
-
market = self.safe_market(marketId, market)
|
10165
|
+
market = self.safe_market(marketId, market, None, 'swap')
|
10162
10166
|
symbol = market['symbol']
|
10163
10167
|
side = self.safe_string_lower(position, 'side')
|
10164
10168
|
quantity = self.safe_string(position, 'quantity')
|
ccxt/blofin.py
CHANGED
ccxt/coinex.py
CHANGED
@@ -480,7 +480,7 @@ class coinex(Exchange, ImplicitAPI):
|
|
480
480
|
'ERC20': 'ERC20',
|
481
481
|
'BRC20': 'BRC20',
|
482
482
|
'SOL': 'SOL',
|
483
|
-
'TON': '
|
483
|
+
'TON': 'TON',
|
484
484
|
'BSV': 'BSV',
|
485
485
|
'AVAXC': 'AVA_C',
|
486
486
|
'AVAXX': 'AVA',
|
@@ -4608,13 +4608,13 @@ class coinex(Exchange, ImplicitAPI):
|
|
4608
4608
|
self.check_address(address)
|
4609
4609
|
self.load_markets()
|
4610
4610
|
currency = self.currency(code)
|
4611
|
-
if tag:
|
4612
|
-
address = address + ':' + tag
|
4613
4611
|
request: dict = {
|
4614
4612
|
'ccy': currency['id'],
|
4615
4613
|
'to_address': address, # must be authorized, inter-user transfer by a registered mobile phone number or an email address is supported
|
4616
4614
|
'amount': self.number_to_string(amount), # the actual amount without fees, https://www.coinex.com/fees
|
4617
4615
|
}
|
4616
|
+
if tag is not None:
|
4617
|
+
request['memo'] = tag
|
4618
4618
|
networkCode = None
|
4619
4619
|
networkCode, params = self.handle_network_code_and_params(params)
|
4620
4620
|
if networkCode is not None:
|
ccxt/hollaex.py
CHANGED
@@ -829,7 +829,7 @@ class hollaex(Exchange, ImplicitAPI):
|
|
829
829
|
|
830
830
|
def fetch_ohlcv(self, symbol: str, timeframe='1m', since: Int = None, limit: Int = None, params={}) -> List[list]:
|
831
831
|
"""
|
832
|
-
|
832
|
+
hollaex has large gaps between candles, so it's recommended to specify since
|
833
833
|
|
834
834
|
https://apidocs.hollaex.com/#chart
|
835
835
|
|
@@ -838,6 +838,7 @@ class hollaex(Exchange, ImplicitAPI):
|
|
838
838
|
:param int [since]: timestamp in ms of the earliest candle to fetch
|
839
839
|
:param int [limit]: the maximum amount of candles to fetch
|
840
840
|
:param dict [params]: extra parameters specific to the exchange API endpoint
|
841
|
+
:param int [params.until]: timestamp in ms of the latest candle to fetch
|
841
842
|
:returns int[][]: A list of candles ordered, open, high, low, close, volume
|
842
843
|
"""
|
843
844
|
self.load_markets()
|
@@ -846,22 +847,17 @@ class hollaex(Exchange, ImplicitAPI):
|
|
846
847
|
'symbol': market['id'],
|
847
848
|
'resolution': self.safe_string(self.timeframes, timeframe, timeframe),
|
848
849
|
}
|
849
|
-
|
850
|
-
|
851
|
-
|
852
|
-
|
853
|
-
|
854
|
-
|
855
|
-
request['
|
856
|
-
request['from'] = start
|
850
|
+
until = self.safe_integer(params, 'until')
|
851
|
+
end = self.seconds()
|
852
|
+
if until is not None:
|
853
|
+
end = self.parse_to_int(until / 1000)
|
854
|
+
defaultSpan = 2592000 # 30 days
|
855
|
+
if since is not None:
|
856
|
+
request['from'] = self.parse_to_int(since / 1000)
|
857
857
|
else:
|
858
|
-
|
859
|
-
|
860
|
-
|
861
|
-
else:
|
862
|
-
start = self.parse_to_int(since / 1000)
|
863
|
-
request['from'] = start
|
864
|
-
request['to'] = self.sum(start, duration * limit)
|
858
|
+
request['from'] = end - defaultSpan
|
859
|
+
request['to'] = end
|
860
|
+
params = self.omit(params, 'until')
|
865
861
|
response = self.publicGetChart(self.extend(request, params))
|
866
862
|
#
|
867
863
|
# [
|