ccxt 4.2.77__py2.py3-none-any.whl → 4.4.48__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 +36 -14
- ccxt/abstract/alpaca.py +4 -0
- ccxt/abstract/bigone.py +1 -1
- ccxt/abstract/binance.py +112 -48
- ccxt/abstract/binancecoinm.py +112 -48
- ccxt/abstract/binanceus.py +147 -83
- ccxt/abstract/binanceusdm.py +112 -48
- ccxt/abstract/bingx.py +133 -78
- ccxt/abstract/bitbank.py +5 -0
- ccxt/abstract/bitfinex.py +136 -65
- ccxt/abstract/bitfinex1.py +69 -0
- ccxt/abstract/bitflyer.py +1 -0
- ccxt/abstract/bitget.py +8 -1
- ccxt/abstract/bitmart.py +13 -1
- ccxt/abstract/bitopro.py +1 -0
- ccxt/abstract/bitpanda.py +0 -12
- ccxt/abstract/bitrue.py +3 -3
- ccxt/abstract/bitstamp.py +26 -3
- ccxt/abstract/blofin.py +24 -0
- ccxt/abstract/btcbox.py +1 -0
- ccxt/abstract/bybit.py +29 -14
- ccxt/abstract/cex.py +28 -29
- ccxt/abstract/coinbase.py +6 -0
- ccxt/abstract/coinbaseadvanced.py +94 -0
- ccxt/abstract/{coinbasepro.py → coinbaseexchange.py} +1 -0
- ccxt/abstract/coinbaseinternational.py +1 -1
- ccxt/abstract/coincatch.py +94 -0
- ccxt/abstract/coinex.py +233 -123
- ccxt/abstract/coinmetro.py +1 -0
- ccxt/abstract/cryptocom.py +14 -0
- ccxt/abstract/defx.py +69 -0
- ccxt/abstract/deribit.py +1 -0
- ccxt/abstract/digifinex.py +1 -0
- ccxt/abstract/ellipx.py +25 -0
- ccxt/abstract/gate.py +20 -0
- ccxt/abstract/gateio.py +20 -0
- ccxt/abstract/gemini.py +1 -0
- ccxt/abstract/hashkey.py +67 -0
- ccxt/abstract/hyperliquid.py +1 -1
- ccxt/abstract/independentreserve.py +6 -0
- ccxt/abstract/kraken.py +4 -3
- ccxt/abstract/krakenfutures.py +4 -0
- ccxt/abstract/kucoin.py +24 -0
- ccxt/abstract/kucoinfutures.py +34 -0
- ccxt/abstract/luno.py +2 -0
- ccxt/abstract/mexc.py +4 -0
- ccxt/abstract/myokx.py +340 -0
- ccxt/abstract/oceanex.py +5 -0
- ccxt/abstract/okx.py +30 -0
- ccxt/abstract/onetrading.py +0 -12
- ccxt/abstract/oxfun.py +34 -0
- ccxt/abstract/paradex.py +40 -0
- ccxt/abstract/phemex.py +1 -0
- ccxt/abstract/upbit.py +4 -0
- ccxt/abstract/vertex.py +19 -0
- ccxt/abstract/whitebit.py +31 -1
- ccxt/abstract/woo.py +6 -2
- ccxt/abstract/woofipro.py +119 -0
- ccxt/abstract/xt.py +153 -0
- ccxt/abstract/zonda.py +6 -0
- ccxt/ace.py +164 -60
- ccxt/alpaca.py +727 -63
- ccxt/ascendex.py +395 -249
- ccxt/async_support/__init__.py +36 -14
- ccxt/async_support/ace.py +164 -60
- ccxt/async_support/alpaca.py +727 -63
- ccxt/async_support/ascendex.py +396 -249
- ccxt/async_support/base/exchange.py +531 -155
- ccxt/async_support/base/ws/aiohttp_client.py +28 -5
- ccxt/async_support/base/ws/cache.py +3 -2
- ccxt/async_support/base/ws/client.py +26 -5
- ccxt/async_support/base/ws/fast_client.py +4 -3
- ccxt/async_support/base/ws/functions.py +1 -1
- ccxt/async_support/base/ws/future.py +40 -31
- ccxt/async_support/base/ws/order_book_side.py +3 -0
- ccxt/async_support/bequant.py +1 -1
- ccxt/async_support/bigone.py +329 -202
- ccxt/async_support/binance.py +3030 -1087
- ccxt/async_support/binancecoinm.py +2 -1
- ccxt/async_support/binanceus.py +12 -1
- ccxt/async_support/binanceusdm.py +3 -1
- ccxt/async_support/bingx.py +3104 -880
- ccxt/async_support/bit2c.py +119 -38
- ccxt/async_support/bitbank.py +215 -76
- ccxt/async_support/bitbns.py +124 -53
- ccxt/async_support/bitfinex.py +3236 -1078
- ccxt/async_support/bitfinex1.py +1711 -0
- ccxt/async_support/bitflyer.py +238 -49
- ccxt/async_support/bitget.py +1513 -563
- ccxt/async_support/bithumb.py +199 -65
- ccxt/async_support/bitmart.py +1320 -435
- ccxt/async_support/bitmex.py +308 -111
- ccxt/async_support/bitopro.py +256 -96
- ccxt/async_support/bitrue.py +365 -233
- ccxt/async_support/bitso.py +201 -89
- ccxt/async_support/bitstamp.py +438 -269
- ccxt/async_support/bitteam.py +179 -73
- ccxt/async_support/bitvavo.py +180 -70
- ccxt/async_support/bl3p.py +92 -25
- ccxt/async_support/blockchaincom.py +193 -79
- ccxt/async_support/blofin.py +392 -148
- ccxt/async_support/btcalpha.py +161 -55
- ccxt/async_support/btcbox.py +250 -34
- ccxt/async_support/btcmarkets.py +232 -85
- ccxt/async_support/btcturk.py +159 -60
- ccxt/async_support/bybit.py +2231 -1193
- ccxt/async_support/cex.py +1409 -1329
- ccxt/async_support/coinbase.py +1454 -287
- ccxt/async_support/coinbaseadvanced.py +17 -0
- ccxt/async_support/{coinbasepro.py → coinbaseexchange.py} +233 -99
- ccxt/async_support/coinbaseinternational.py +428 -88
- ccxt/async_support/coincatch.py +5152 -0
- ccxt/async_support/coincheck.py +121 -38
- ccxt/async_support/coinex.py +4020 -3339
- ccxt/async_support/coinlist.py +273 -116
- ccxt/async_support/coinmate.py +204 -97
- ccxt/async_support/coinmetro.py +203 -110
- ccxt/async_support/coinone.py +142 -68
- ccxt/async_support/coinsph.py +206 -89
- ccxt/async_support/coinspot.py +137 -62
- ccxt/async_support/cryptocom.py +515 -185
- ccxt/async_support/currencycom.py +203 -85
- ccxt/async_support/defx.py +2066 -0
- ccxt/async_support/delta.py +404 -109
- ccxt/async_support/deribit.py +557 -323
- ccxt/async_support/digifinex.py +340 -223
- ccxt/async_support/ellipx.py +1826 -0
- ccxt/async_support/exmo.py +259 -128
- ccxt/async_support/gate.py +1472 -463
- ccxt/async_support/gemini.py +206 -84
- ccxt/async_support/hashkey.py +4164 -0
- ccxt/async_support/hitbtc.py +334 -178
- ccxt/async_support/hollaex.py +134 -83
- ccxt/async_support/htx.py +1095 -563
- ccxt/async_support/huobijp.py +105 -56
- ccxt/async_support/hyperliquid.py +1633 -268
- ccxt/async_support/idex.py +148 -95
- ccxt/async_support/independentreserve.py +236 -31
- ccxt/async_support/indodax.py +165 -62
- ccxt/async_support/kraken.py +871 -354
- ccxt/async_support/krakenfutures.py +324 -100
- ccxt/async_support/kucoin.py +917 -357
- ccxt/async_support/kucoinfutures.py +1004 -149
- ccxt/async_support/kuna.py +138 -106
- ccxt/async_support/latoken.py +135 -79
- ccxt/async_support/lbank.py +290 -113
- ccxt/async_support/luno.py +112 -62
- ccxt/async_support/lykke.py +104 -55
- ccxt/async_support/mercado.py +36 -29
- ccxt/async_support/mexc.py +995 -429
- ccxt/async_support/myokx.py +43 -0
- ccxt/async_support/ndax.py +163 -82
- ccxt/async_support/novadax.py +121 -75
- ccxt/async_support/oceanex.py +175 -59
- ccxt/async_support/okcoin.py +222 -163
- ccxt/async_support/okx.py +1776 -454
- ccxt/async_support/onetrading.py +132 -414
- ccxt/async_support/oxfun.py +2832 -0
- ccxt/async_support/p2b.py +79 -51
- ccxt/async_support/paradex.py +2017 -0
- ccxt/async_support/paymium.py +56 -32
- ccxt/async_support/phemex.py +572 -196
- ccxt/async_support/poloniex.py +218 -95
- ccxt/async_support/poloniexfutures.py +260 -92
- ccxt/async_support/probit.py +143 -110
- ccxt/async_support/timex.py +123 -70
- ccxt/async_support/tokocrypto.py +129 -93
- ccxt/async_support/tradeogre.py +39 -25
- ccxt/async_support/upbit.py +322 -113
- ccxt/async_support/vertex.py +2983 -0
- ccxt/async_support/wavesexchange.py +227 -173
- ccxt/async_support/wazirx.py +145 -65
- ccxt/async_support/whitebit.py +533 -138
- ccxt/async_support/woo.py +1137 -296
- ccxt/async_support/woofipro.py +2716 -0
- ccxt/async_support/xt.py +4628 -0
- ccxt/async_support/yobit.py +160 -92
- ccxt/async_support/zaif.py +80 -33
- ccxt/async_support/zonda.py +140 -69
- ccxt/base/errors.py +51 -20
- ccxt/base/exchange.py +1722 -480
- ccxt/base/precise.py +10 -0
- ccxt/base/types.py +223 -4
- ccxt/bequant.py +1 -1
- ccxt/bigone.py +329 -202
- ccxt/binance.py +3030 -1087
- ccxt/binancecoinm.py +2 -1
- ccxt/binanceus.py +12 -1
- ccxt/binanceusdm.py +3 -1
- ccxt/bingx.py +3104 -880
- ccxt/bit2c.py +119 -38
- ccxt/bitbank.py +215 -76
- ccxt/bitbns.py +124 -53
- ccxt/bitfinex.py +3235 -1078
- ccxt/bitfinex1.py +1710 -0
- ccxt/bitflyer.py +238 -49
- ccxt/bitget.py +1513 -563
- ccxt/bithumb.py +198 -65
- ccxt/bitmart.py +1320 -435
- ccxt/bitmex.py +308 -111
- ccxt/bitopro.py +256 -96
- ccxt/bitrue.py +365 -233
- ccxt/bitso.py +201 -89
- ccxt/bitstamp.py +438 -269
- ccxt/bitteam.py +179 -73
- ccxt/bitvavo.py +180 -70
- ccxt/bl3p.py +92 -25
- ccxt/blockchaincom.py +193 -79
- ccxt/blofin.py +392 -148
- ccxt/btcalpha.py +161 -55
- ccxt/btcbox.py +250 -34
- ccxt/btcmarkets.py +232 -85
- ccxt/btcturk.py +159 -60
- ccxt/bybit.py +2231 -1193
- ccxt/cex.py +1408 -1329
- ccxt/coinbase.py +1454 -287
- ccxt/coinbaseadvanced.py +17 -0
- ccxt/{coinbasepro.py → coinbaseexchange.py} +233 -99
- ccxt/coinbaseinternational.py +428 -88
- ccxt/coincatch.py +5152 -0
- ccxt/coincheck.py +121 -38
- ccxt/coinex.py +4020 -3339
- ccxt/coinlist.py +273 -116
- ccxt/coinmate.py +204 -97
- ccxt/coinmetro.py +203 -110
- ccxt/coinone.py +142 -68
- ccxt/coinsph.py +206 -89
- ccxt/coinspot.py +137 -62
- ccxt/cryptocom.py +515 -185
- ccxt/currencycom.py +203 -85
- ccxt/defx.py +2065 -0
- ccxt/delta.py +404 -109
- ccxt/deribit.py +557 -323
- ccxt/digifinex.py +340 -223
- ccxt/ellipx.py +1826 -0
- ccxt/exmo.py +259 -128
- ccxt/gate.py +1472 -463
- ccxt/gemini.py +206 -84
- ccxt/hashkey.py +4164 -0
- ccxt/hitbtc.py +334 -178
- ccxt/hollaex.py +134 -83
- ccxt/htx.py +1095 -563
- ccxt/huobijp.py +105 -56
- ccxt/hyperliquid.py +1632 -268
- ccxt/idex.py +148 -95
- ccxt/independentreserve.py +235 -31
- ccxt/indodax.py +165 -62
- ccxt/kraken.py +871 -354
- ccxt/krakenfutures.py +324 -100
- ccxt/kucoin.py +917 -357
- ccxt/kucoinfutures.py +1004 -149
- ccxt/kuna.py +138 -106
- ccxt/latoken.py +135 -79
- ccxt/lbank.py +290 -113
- ccxt/luno.py +112 -62
- ccxt/lykke.py +104 -55
- ccxt/mercado.py +36 -29
- ccxt/mexc.py +994 -429
- ccxt/myokx.py +43 -0
- ccxt/ndax.py +163 -82
- ccxt/novadax.py +121 -75
- ccxt/oceanex.py +175 -59
- ccxt/okcoin.py +222 -163
- ccxt/okx.py +1776 -454
- ccxt/onetrading.py +132 -414
- ccxt/oxfun.py +2831 -0
- ccxt/p2b.py +79 -51
- ccxt/paradex.py +2017 -0
- ccxt/paymium.py +56 -32
- ccxt/phemex.py +572 -196
- ccxt/poloniex.py +218 -95
- ccxt/poloniexfutures.py +260 -92
- ccxt/pro/__init__.py +29 -5
- ccxt/pro/alpaca.py +32 -17
- ccxt/pro/ascendex.py +62 -14
- ccxt/pro/bequant.py +4 -0
- ccxt/pro/binance.py +1596 -329
- ccxt/pro/binancecoinm.py +1 -0
- ccxt/pro/binanceus.py +2 -9
- ccxt/pro/binanceusdm.py +2 -0
- ccxt/pro/bingx.py +527 -134
- ccxt/pro/bitcoincom.py +4 -1
- ccxt/pro/bitfinex.py +731 -266
- ccxt/pro/bitfinex1.py +635 -0
- ccxt/pro/bitget.py +726 -357
- ccxt/pro/bithumb.py +380 -0
- ccxt/pro/bitmart.py +138 -39
- ccxt/pro/bitmex.py +199 -40
- ccxt/pro/bitopro.py +25 -13
- ccxt/pro/bitrue.py +31 -32
- ccxt/pro/bitstamp.py +7 -6
- ccxt/pro/bitvavo.py +203 -81
- ccxt/pro/blockchaincom.py +30 -17
- ccxt/pro/blofin.py +692 -0
- ccxt/pro/bybit.py +791 -82
- ccxt/pro/cex.py +99 -51
- ccxt/pro/coinbase.py +220 -30
- ccxt/{async_support/hitbtc3.py → pro/coinbaseadvanced.py} +5 -5
- ccxt/pro/{coinbasepro.py → coinbaseexchange.py} +19 -19
- ccxt/pro/coinbaseinternational.py +193 -30
- ccxt/pro/coincatch.py +1464 -0
- ccxt/pro/coincheck.py +11 -6
- ccxt/pro/coinex.py +965 -665
- ccxt/pro/coinone.py +17 -10
- ccxt/pro/cryptocom.py +446 -66
- ccxt/pro/currencycom.py +11 -10
- ccxt/pro/defx.py +832 -0
- ccxt/pro/deribit.py +167 -31
- ccxt/pro/exmo.py +252 -20
- ccxt/pro/gate.py +729 -64
- ccxt/pro/gemini.py +44 -26
- ccxt/pro/hashkey.py +802 -0
- ccxt/pro/hitbtc.py +208 -103
- ccxt/pro/hollaex.py +25 -9
- ccxt/pro/htx.py +83 -39
- ccxt/pro/huobijp.py +17 -16
- ccxt/pro/hyperliquid.py +502 -31
- ccxt/pro/idex.py +28 -13
- ccxt/pro/independentreserve.py +21 -16
- ccxt/pro/kraken.py +298 -51
- ccxt/pro/krakenfutures.py +166 -75
- ccxt/pro/kucoin.py +395 -77
- ccxt/pro/kucoinfutures.py +400 -99
- ccxt/pro/lbank.py +52 -31
- ccxt/pro/luno.py +12 -10
- ccxt/pro/mexc.py +400 -50
- ccxt/pro/myokx.py +28 -0
- ccxt/pro/ndax.py +25 -12
- ccxt/pro/okcoin.py +28 -9
- ccxt/pro/okx.py +935 -124
- ccxt/pro/onetrading.py +41 -24
- ccxt/pro/oxfun.py +1054 -0
- ccxt/pro/p2b.py +100 -24
- ccxt/pro/paradex.py +352 -0
- ccxt/pro/phemex.py +92 -33
- ccxt/pro/poloniex.py +128 -49
- ccxt/pro/poloniexfutures.py +53 -32
- ccxt/pro/probit.py +92 -85
- ccxt/pro/upbit.py +401 -8
- ccxt/pro/vertex.py +943 -0
- ccxt/pro/wazirx.py +46 -28
- ccxt/pro/whitebit.py +65 -12
- ccxt/pro/woo.py +437 -65
- ccxt/pro/woofipro.py +1271 -0
- ccxt/pro/xt.py +1067 -0
- ccxt/probit.py +143 -110
- ccxt/static_dependencies/__init__.py +1 -1
- ccxt/static_dependencies/lark/__init__.py +38 -0
- ccxt/static_dependencies/lark/__pyinstaller/__init__.py +6 -0
- ccxt/static_dependencies/lark/__pyinstaller/hook-lark.py +14 -0
- ccxt/static_dependencies/lark/ast_utils.py +59 -0
- ccxt/static_dependencies/lark/common.py +86 -0
- ccxt/static_dependencies/lark/exceptions.py +292 -0
- ccxt/static_dependencies/lark/grammar.py +130 -0
- ccxt/static_dependencies/lark/grammars/__init__.py +0 -0
- ccxt/static_dependencies/lark/indenter.py +143 -0
- ccxt/static_dependencies/lark/lark.py +658 -0
- ccxt/static_dependencies/lark/lexer.py +678 -0
- ccxt/static_dependencies/lark/load_grammar.py +1428 -0
- ccxt/static_dependencies/lark/parse_tree_builder.py +391 -0
- ccxt/static_dependencies/lark/parser_frontends.py +257 -0
- ccxt/static_dependencies/lark/parsers/__init__.py +0 -0
- ccxt/static_dependencies/lark/parsers/cyk.py +340 -0
- ccxt/static_dependencies/lark/parsers/earley.py +314 -0
- ccxt/static_dependencies/lark/parsers/earley_common.py +42 -0
- ccxt/static_dependencies/lark/parsers/earley_forest.py +801 -0
- ccxt/static_dependencies/lark/parsers/grammar_analysis.py +203 -0
- ccxt/static_dependencies/lark/parsers/lalr_analysis.py +332 -0
- ccxt/static_dependencies/lark/parsers/lalr_interactive_parser.py +158 -0
- ccxt/static_dependencies/lark/parsers/lalr_parser.py +122 -0
- ccxt/static_dependencies/lark/parsers/lalr_parser_state.py +110 -0
- ccxt/static_dependencies/lark/parsers/xearley.py +165 -0
- ccxt/static_dependencies/lark/py.typed +0 -0
- ccxt/static_dependencies/lark/reconstruct.py +107 -0
- ccxt/static_dependencies/lark/tools/__init__.py +70 -0
- ccxt/static_dependencies/lark/tools/nearley.py +202 -0
- ccxt/static_dependencies/lark/tools/serialize.py +32 -0
- ccxt/static_dependencies/lark/tools/standalone.py +196 -0
- ccxt/static_dependencies/lark/tree.py +267 -0
- ccxt/static_dependencies/lark/tree_matcher.py +186 -0
- ccxt/static_dependencies/lark/tree_templates.py +180 -0
- ccxt/static_dependencies/lark/utils.py +343 -0
- ccxt/static_dependencies/lark/visitors.py +596 -0
- ccxt/static_dependencies/marshmallow/__init__.py +81 -0
- ccxt/static_dependencies/marshmallow/base.py +65 -0
- ccxt/static_dependencies/marshmallow/class_registry.py +94 -0
- ccxt/static_dependencies/marshmallow/decorators.py +231 -0
- ccxt/static_dependencies/marshmallow/error_store.py +60 -0
- ccxt/static_dependencies/marshmallow/exceptions.py +71 -0
- ccxt/static_dependencies/marshmallow/fields.py +2114 -0
- ccxt/static_dependencies/marshmallow/orderedset.py +89 -0
- ccxt/static_dependencies/marshmallow/py.typed +0 -0
- ccxt/static_dependencies/marshmallow/schema.py +1228 -0
- ccxt/static_dependencies/marshmallow/types.py +12 -0
- ccxt/static_dependencies/marshmallow/utils.py +378 -0
- ccxt/static_dependencies/marshmallow/validate.py +678 -0
- ccxt/static_dependencies/marshmallow/warnings.py +2 -0
- ccxt/static_dependencies/marshmallow_dataclass/__init__.py +1047 -0
- ccxt/static_dependencies/marshmallow_dataclass/collection_field.py +51 -0
- ccxt/static_dependencies/marshmallow_dataclass/lazy_class_attribute.py +45 -0
- ccxt/static_dependencies/marshmallow_dataclass/mypy.py +71 -0
- ccxt/static_dependencies/marshmallow_dataclass/py.typed +0 -0
- ccxt/static_dependencies/marshmallow_dataclass/typing.py +14 -0
- ccxt/static_dependencies/marshmallow_dataclass/union_field.py +82 -0
- ccxt/static_dependencies/marshmallow_oneofschema/__init__.py +1 -0
- ccxt/static_dependencies/marshmallow_oneofschema/one_of_schema.py +193 -0
- ccxt/static_dependencies/marshmallow_oneofschema/py.typed +0 -0
- ccxt/static_dependencies/starknet/__init__.py +0 -0
- ccxt/static_dependencies/starknet/cairo/__init__.py +0 -0
- ccxt/static_dependencies/starknet/cairo/data_types.py +123 -0
- ccxt/static_dependencies/starknet/cairo/deprecated_parse/__init__.py +0 -0
- ccxt/static_dependencies/starknet/cairo/deprecated_parse/cairo_types.py +77 -0
- ccxt/static_dependencies/starknet/cairo/deprecated_parse/parser.py +46 -0
- ccxt/static_dependencies/starknet/cairo/deprecated_parse/parser_transformer.py +138 -0
- ccxt/static_dependencies/starknet/cairo/felt.py +64 -0
- ccxt/static_dependencies/starknet/cairo/type_parser.py +121 -0
- ccxt/static_dependencies/starknet/cairo/v1/__init__.py +0 -0
- ccxt/static_dependencies/starknet/cairo/v1/type_parser.py +59 -0
- ccxt/static_dependencies/starknet/cairo/v2/__init__.py +0 -0
- ccxt/static_dependencies/starknet/cairo/v2/type_parser.py +77 -0
- ccxt/static_dependencies/starknet/ccxt_utils.py +7 -0
- ccxt/static_dependencies/starknet/common.py +15 -0
- ccxt/static_dependencies/starknet/constants.py +39 -0
- ccxt/static_dependencies/starknet/hash/__init__.py +0 -0
- ccxt/static_dependencies/starknet/hash/address.py +79 -0
- ccxt/static_dependencies/starknet/hash/compiled_class_hash_objects.py +111 -0
- ccxt/static_dependencies/starknet/hash/selector.py +16 -0
- ccxt/static_dependencies/starknet/hash/storage.py +12 -0
- ccxt/static_dependencies/starknet/hash/utils.py +78 -0
- ccxt/static_dependencies/starknet/models/__init__.py +0 -0
- ccxt/static_dependencies/starknet/models/typed_data.py +45 -0
- ccxt/static_dependencies/starknet/serialization/__init__.py +24 -0
- ccxt/static_dependencies/starknet/serialization/_calldata_reader.py +40 -0
- ccxt/static_dependencies/starknet/serialization/_context.py +142 -0
- ccxt/static_dependencies/starknet/serialization/data_serializers/__init__.py +10 -0
- ccxt/static_dependencies/starknet/serialization/data_serializers/_common.py +82 -0
- ccxt/static_dependencies/starknet/serialization/data_serializers/array_serializer.py +43 -0
- ccxt/static_dependencies/starknet/serialization/data_serializers/bool_serializer.py +37 -0
- ccxt/static_dependencies/starknet/serialization/data_serializers/byte_array_serializer.py +66 -0
- ccxt/static_dependencies/starknet/serialization/data_serializers/cairo_data_serializer.py +71 -0
- ccxt/static_dependencies/starknet/serialization/data_serializers/enum_serializer.py +71 -0
- ccxt/static_dependencies/starknet/serialization/data_serializers/felt_serializer.py +50 -0
- ccxt/static_dependencies/starknet/serialization/data_serializers/named_tuple_serializer.py +58 -0
- ccxt/static_dependencies/starknet/serialization/data_serializers/option_serializer.py +43 -0
- ccxt/static_dependencies/starknet/serialization/data_serializers/output_serializer.py +40 -0
- ccxt/static_dependencies/starknet/serialization/data_serializers/payload_serializer.py +72 -0
- ccxt/static_dependencies/starknet/serialization/data_serializers/struct_serializer.py +36 -0
- ccxt/static_dependencies/starknet/serialization/data_serializers/tuple_serializer.py +36 -0
- ccxt/static_dependencies/starknet/serialization/data_serializers/uint256_serializer.py +76 -0
- ccxt/static_dependencies/starknet/serialization/data_serializers/uint_serializer.py +100 -0
- ccxt/static_dependencies/starknet/serialization/data_serializers/unit_serializer.py +32 -0
- ccxt/static_dependencies/starknet/serialization/errors.py +10 -0
- ccxt/static_dependencies/starknet/serialization/factory.py +229 -0
- ccxt/static_dependencies/starknet/serialization/function_serialization_adapter.py +110 -0
- ccxt/static_dependencies/starknet/serialization/tuple_dataclass.py +59 -0
- ccxt/static_dependencies/starknet/utils/__init__.py +0 -0
- ccxt/static_dependencies/starknet/utils/constructor_args_translator.py +86 -0
- ccxt/static_dependencies/starknet/utils/iterable.py +13 -0
- ccxt/static_dependencies/starknet/utils/schema.py +13 -0
- ccxt/static_dependencies/starknet/utils/typed_data.py +182 -0
- ccxt/static_dependencies/starkware/__init__.py +0 -0
- ccxt/static_dependencies/starkware/crypto/__init__.py +0 -0
- ccxt/static_dependencies/starkware/crypto/fast_pedersen_hash.py +50 -0
- ccxt/static_dependencies/starkware/crypto/math_utils.py +78 -0
- ccxt/static_dependencies/starkware/crypto/signature.py +2344 -0
- ccxt/static_dependencies/starkware/crypto/utils.py +63 -0
- ccxt/static_dependencies/sympy/__init__.py +0 -0
- ccxt/static_dependencies/sympy/core/__init__.py +0 -0
- ccxt/static_dependencies/sympy/core/intfunc.py +35 -0
- ccxt/static_dependencies/sympy/external/__init__.py +0 -0
- ccxt/static_dependencies/sympy/external/gmpy.py +345 -0
- ccxt/static_dependencies/sympy/external/importtools.py +187 -0
- ccxt/static_dependencies/sympy/external/ntheory.py +637 -0
- ccxt/static_dependencies/sympy/external/pythonmpq.py +341 -0
- ccxt/static_dependencies/typing_inspect/__init__.py +0 -0
- ccxt/static_dependencies/typing_inspect/typing_inspect.py +851 -0
- ccxt/test/{test_async.py → tests_async.py} +456 -391
- ccxt/test/tests_helpers.py +285 -0
- ccxt/test/tests_init.py +39 -0
- ccxt/test/{test_sync.py → tests_sync.py} +456 -393
- ccxt/timex.py +123 -70
- ccxt/tokocrypto.py +129 -93
- ccxt/tradeogre.py +39 -25
- ccxt/upbit.py +322 -113
- ccxt/vertex.py +2983 -0
- ccxt/wavesexchange.py +227 -173
- ccxt/wazirx.py +145 -65
- ccxt/whitebit.py +533 -138
- ccxt/woo.py +1137 -296
- ccxt/woofipro.py +2716 -0
- ccxt/xt.py +4627 -0
- ccxt/yobit.py +159 -92
- ccxt/zaif.py +80 -33
- ccxt/zonda.py +140 -69
- ccxt-4.4.48.dist-info/LICENSE.txt +21 -0
- ccxt-4.4.48.dist-info/METADATA +646 -0
- ccxt-4.4.48.dist-info/RECORD +669 -0
- {ccxt-4.2.77.dist-info → ccxt-4.4.48.dist-info}/WHEEL +1 -1
- ccxt/abstract/bitbay.py +0 -47
- ccxt/abstract/bitfinex2.py +0 -139
- ccxt/abstract/hitbtc3.py +0 -115
- ccxt/async_support/bitbay.py +0 -17
- ccxt/async_support/bitfinex2.py +0 -3496
- ccxt/async_support/flowbtc.py +0 -34
- ccxt/bitbay.py +0 -17
- ccxt/bitfinex2.py +0 -3496
- ccxt/flowbtc.py +0 -34
- ccxt/hitbtc3.py +0 -16
- ccxt/pro/bitfinex2.py +0 -1081
- ccxt/test/base/__init__.py +0 -28
- ccxt/test/base/test_account.py +0 -26
- ccxt/test/base/test_balance.py +0 -56
- ccxt/test/base/test_borrow_interest.py +0 -35
- ccxt/test/base/test_borrow_rate.py +0 -32
- ccxt/test/base/test_calculate_fee.py +0 -51
- ccxt/test/base/test_crypto.py +0 -127
- ccxt/test/base/test_currency.py +0 -76
- ccxt/test/base/test_datetime.py +0 -103
- ccxt/test/base/test_decimal_to_precision.py +0 -392
- ccxt/test/base/test_deep_extend.py +0 -68
- ccxt/test/base/test_deposit_withdrawal.py +0 -50
- ccxt/test/base/test_exchange_datetime_functions.py +0 -76
- ccxt/test/base/test_funding_rate_history.py +0 -29
- ccxt/test/base/test_last_price.py +0 -32
- ccxt/test/base/test_ledger_entry.py +0 -45
- ccxt/test/base/test_ledger_item.py +0 -48
- ccxt/test/base/test_leverage_tier.py +0 -33
- ccxt/test/base/test_margin_mode.py +0 -24
- ccxt/test/base/test_margin_modification.py +0 -35
- ccxt/test/base/test_market.py +0 -190
- ccxt/test/base/test_number.py +0 -411
- ccxt/test/base/test_ohlcv.py +0 -32
- ccxt/test/base/test_open_interest.py +0 -32
- ccxt/test/base/test_order.py +0 -64
- ccxt/test/base/test_order_book.py +0 -63
- ccxt/test/base/test_position.py +0 -60
- ccxt/test/base/test_shared_methods.py +0 -345
- ccxt/test/base/test_status.py +0 -24
- ccxt/test/base/test_throttle.py +0 -126
- ccxt/test/base/test_ticker.py +0 -86
- ccxt/test/base/test_trade.py +0 -47
- ccxt/test/base/test_trading_fee.py +0 -26
- ccxt/test/base/test_transaction.py +0 -39
- ccxt-4.2.77.dist-info/METADATA +0 -626
- ccxt-4.2.77.dist-info/RECORD +0 -534
- {ccxt-4.2.77.dist-info → ccxt-4.4.48.dist-info}/top_level.txt +0 -0
ccxt/kucoin.py
CHANGED
@@ -8,9 +8,10 @@ from ccxt.abstract.kucoin import ImplicitAPI
|
|
8
8
|
import hashlib
|
9
9
|
import math
|
10
10
|
import json
|
11
|
-
from ccxt.base.types import Account, Balances, Currency, Int, Market, Num, Order, OrderBook, OrderRequest, OrderSide, OrderType, Str, Strings, Ticker, Tickers, Trade, Transaction, TransferEntry
|
11
|
+
from ccxt.base.types import Account, Balances, BorrowInterest, Bool, Currencies, Currency, DepositAddress, Int, LedgerEntry, Market, Num, Order, OrderBook, OrderRequest, OrderSide, OrderType, Str, Strings, Ticker, Tickers, Trade, TradingFeeInterface, Transaction, TransferEntry
|
12
12
|
from typing import List
|
13
13
|
from ccxt.base.errors import ExchangeError
|
14
|
+
from ccxt.base.errors import AuthenticationError
|
14
15
|
from ccxt.base.errors import PermissionDenied
|
15
16
|
from ccxt.base.errors import AccountSuspended
|
16
17
|
from ccxt.base.errors import ArgumentsRequired
|
@@ -24,7 +25,7 @@ from ccxt.base.errors import NotSupported
|
|
24
25
|
from ccxt.base.errors import RateLimitExceeded
|
25
26
|
from ccxt.base.errors import ExchangeNotAvailable
|
26
27
|
from ccxt.base.errors import InvalidNonce
|
27
|
-
from ccxt.base.
|
28
|
+
from ccxt.base.decimal_to_precision import TRUNCATE
|
28
29
|
from ccxt.base.decimal_to_precision import TICK_SIZE
|
29
30
|
from ccxt.base.precise import Precise
|
30
31
|
|
@@ -77,6 +78,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
77
78
|
'fetchCrossBorrowRates': False,
|
78
79
|
'fetchCurrencies': True,
|
79
80
|
'fetchDepositAddress': True,
|
81
|
+
'fetchDepositAddresses': False,
|
80
82
|
'fetchDepositAddressesByNetwork': True,
|
81
83
|
'fetchDeposits': True,
|
82
84
|
'fetchDepositWithdrawFee': True,
|
@@ -91,10 +93,13 @@ class kucoin(Exchange, ImplicitAPI):
|
|
91
93
|
'fetchL3OrderBook': True,
|
92
94
|
'fetchLedger': True,
|
93
95
|
'fetchLeverageTiers': False,
|
96
|
+
'fetchMarginAdjustmentHistory': False,
|
94
97
|
'fetchMarginMode': False,
|
95
98
|
'fetchMarketLeverageTiers': False,
|
96
99
|
'fetchMarkets': True,
|
97
100
|
'fetchMarkOHLCV': False,
|
101
|
+
'fetchMarkPrice': True,
|
102
|
+
'fetchMarkPrices': True,
|
98
103
|
'fetchMyTrades': True,
|
99
104
|
'fetchOHLCV': True,
|
100
105
|
'fetchOpenInterest': False,
|
@@ -105,7 +110,9 @@ class kucoin(Exchange, ImplicitAPI):
|
|
105
110
|
'fetchOrderBooks': False,
|
106
111
|
'fetchOrdersByStatus': True,
|
107
112
|
'fetchOrderTrades': True,
|
113
|
+
'fetchPositionHistory': False,
|
108
114
|
'fetchPositionMode': False,
|
115
|
+
'fetchPositionsHistory': False,
|
109
116
|
'fetchPremiumIndexOHLCV': False,
|
110
117
|
'fetchStatus': True,
|
111
118
|
'fetchTicker': True,
|
@@ -119,7 +126,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
119
126
|
'fetchWithdrawals': True,
|
120
127
|
'repayCrossMargin': True,
|
121
128
|
'repayIsolatedMargin': True,
|
122
|
-
'setLeverage':
|
129
|
+
'setLeverage': True,
|
123
130
|
'setMarginMode': False,
|
124
131
|
'setPositionMode': False,
|
125
132
|
'signIn': False,
|
@@ -136,6 +143,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
136
143
|
'futuresPublic': 'https://api-futures.kucoin.com',
|
137
144
|
'webExchange': 'https://kucoin.com/_api',
|
138
145
|
'broker': 'https://api-broker.kucoin.com',
|
146
|
+
'earn': 'https://api.kucoin.com',
|
139
147
|
},
|
140
148
|
'www': 'https://www.kucoin.com',
|
141
149
|
'doc': [
|
@@ -173,7 +181,9 @@ class kucoin(Exchange, ImplicitAPI):
|
|
173
181
|
'status': 4.5, # 3PW
|
174
182
|
# margin trading
|
175
183
|
'mark-price/{symbol}/current': 3, # 2PW
|
184
|
+
'mark-price/all-symbols': 3,
|
176
185
|
'margin/config': 25, # 25SW
|
186
|
+
'announcements': 20, # 20W
|
177
187
|
},
|
178
188
|
'post': {
|
179
189
|
# ws
|
@@ -212,8 +222,10 @@ class kucoin(Exchange, ImplicitAPI):
|
|
212
222
|
'market/orderbook/level{level}': 3, # 3SW
|
213
223
|
'market/orderbook/level2': 3, # 3SW
|
214
224
|
'market/orderbook/level3': 3, # 3SW
|
225
|
+
'hf/accounts/opened': 2, #
|
215
226
|
'hf/orders/active': 2, # 2SW
|
216
227
|
'hf/orders/active/symbols': 2, # 2SW
|
228
|
+
'hf/margin/order/active/symbols': 2, # 2SW
|
217
229
|
'hf/orders/done': 2, # 2SW
|
218
230
|
'hf/orders/{orderId}': 2, # 2SW
|
219
231
|
'hf/orders/client-order/{clientOid}': 2, # 2SW
|
@@ -242,6 +254,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
242
254
|
'margin/currencies': 20, # 20SW
|
243
255
|
'risk/limit/strategy': 20, # 20SW(Deprecate)
|
244
256
|
'isolated/symbols': 20, # 20SW
|
257
|
+
'margin/symbols': 5,
|
245
258
|
'isolated/account/{symbol}': 50, # 50SW
|
246
259
|
'margin/borrow': 15, # 15SW
|
247
260
|
'margin/repay': 15, # 15SW
|
@@ -252,6 +265,9 @@ class kucoin(Exchange, ImplicitAPI):
|
|
252
265
|
'purchase/orders': 10, # 10SW
|
253
266
|
# broker
|
254
267
|
'broker/api/rebase/download': 3,
|
268
|
+
'migrate/user/account/status': 3,
|
269
|
+
# affiliate
|
270
|
+
'affiliate/inviter/statistics': 30,
|
255
271
|
},
|
256
272
|
'post': {
|
257
273
|
# account
|
@@ -291,6 +307,8 @@ class kucoin(Exchange, ImplicitAPI):
|
|
291
307
|
'lend/purchase/update': 10, # 10SW
|
292
308
|
# ws
|
293
309
|
'bullet-private': 10, # 10SW
|
310
|
+
'position/update-user-leverage': 5,
|
311
|
+
'deposit-address/create': 20,
|
294
312
|
},
|
295
313
|
'delete': {
|
296
314
|
# account
|
@@ -403,6 +421,10 @@ class kucoin(Exchange, ImplicitAPI):
|
|
403
421
|
'broker/nd/account': 2,
|
404
422
|
'broker/nd/account/apikey': 2,
|
405
423
|
'broker/nd/rebase/download': 3,
|
424
|
+
'asset/ndbroker/deposit/list': 1,
|
425
|
+
'broker/nd/transfer/detail': 1,
|
426
|
+
'broker/nd/deposit/detail': 1,
|
427
|
+
'broker/nd/withdraw/detail': 1,
|
406
428
|
},
|
407
429
|
'post': {
|
408
430
|
'broker/nd/transfer': 1,
|
@@ -414,6 +436,25 @@ class kucoin(Exchange, ImplicitAPI):
|
|
414
436
|
'broker/nd/account/apikey': 3,
|
415
437
|
},
|
416
438
|
},
|
439
|
+
'earn': {
|
440
|
+
'get': {
|
441
|
+
'otc-loan/loan': 1,
|
442
|
+
'otc-loan/accounts': 1,
|
443
|
+
'earn/redeem-preview': 7.5, # 5EW
|
444
|
+
'earn/saving/products': 7.5, # 5EW
|
445
|
+
'earn/hold-assets': 7.5, # 5EW
|
446
|
+
'earn/promotion/products': 7.5, # 5EW
|
447
|
+
'earn/kcs-staking/products': 7.5, # 5EW
|
448
|
+
'earn/staking/products': 7.5, # 5EW
|
449
|
+
'earn/eth-staking/products': 7.5, # 5EW
|
450
|
+
},
|
451
|
+
'post': {
|
452
|
+
'earn/orders': 7.5, # 5EW
|
453
|
+
},
|
454
|
+
'delete': {
|
455
|
+
'earn/orders': 7.5, # 5EW
|
456
|
+
},
|
457
|
+
},
|
417
458
|
},
|
418
459
|
'timeframes': {
|
419
460
|
'1m': '1min',
|
@@ -434,6 +475,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
434
475
|
'precisionMode': TICK_SIZE,
|
435
476
|
'exceptions': {
|
436
477
|
'exact': {
|
478
|
+
'The order does not exist.': OrderNotFound,
|
437
479
|
'order not exist': OrderNotFound,
|
438
480
|
'order not exist.': OrderNotFound, # duplicated error temporarily
|
439
481
|
'order_not_exist': OrderNotFound, # {"code":"order_not_exist","msg":"order_not_exist"} ¯\_(ツ)_/¯
|
@@ -441,6 +483,8 @@ class kucoin(Exchange, ImplicitAPI):
|
|
441
483
|
'Order size below the minimum requirement.': InvalidOrder, # {"code":"400100","msg":"Order size below the minimum requirement."}
|
442
484
|
'The withdrawal amount is below the minimum requirement.': ExchangeError, # {"code":"400100","msg":"The withdrawal amount is below the minimum requirement."}
|
443
485
|
'Unsuccessful! Exceeded the max. funds out-transfer limit': InsufficientFunds, # {"code":"200000","msg":"Unsuccessful! Exceeded the max. funds out-transfer limit"}
|
486
|
+
'The amount increment is invalid.': BadRequest,
|
487
|
+
'The quantity is below the minimum requirement.': InvalidOrder, # {"msg":"The quantity is below the minimum requirement.","code":"400100"}
|
444
488
|
'400': BadRequest,
|
445
489
|
'401': AuthenticationError,
|
446
490
|
'403': NotSupported,
|
@@ -464,6 +508,56 @@ class kucoin(Exchange, ImplicitAPI):
|
|
464
508
|
'130202': ExchangeError, # The system is renewing the loan automatically. Please try again later
|
465
509
|
'130203': InsufficientFunds, # Insufficient account balance
|
466
510
|
'130204': BadRequest, # As the total lending amount for platform leverage reaches the platform's maximum position limit, the system suspends the borrowing function of leverage
|
511
|
+
'130301': InsufficientFunds, # Insufficient account balance
|
512
|
+
'130302': PermissionDenied, # Your relevant permission rights have been restricted, you can contact customer service for processing
|
513
|
+
'130303': NotSupported, # The current trading pair does not support isolated positions
|
514
|
+
'130304': NotSupported, # The trading function of the current trading pair is not enabled
|
515
|
+
'130305': NotSupported, # The current trading pair does not support cross position
|
516
|
+
'130306': NotSupported, # The account has not opened leveraged trading
|
517
|
+
'130307': NotSupported, # Please reopen the leverage agreement
|
518
|
+
'130308': InvalidOrder, # Position renewal freeze
|
519
|
+
'130309': InvalidOrder, # Position forced liquidation freeze
|
520
|
+
'130310': ExchangeError, # Abnormal leverage account status
|
521
|
+
'130311': InvalidOrder, # Failed to place an order, triggering buy limit
|
522
|
+
'130312': InvalidOrder, # Trigger global position limit, suspend buying
|
523
|
+
'130313': InvalidOrder, # Trigger global position limit, suspend selling
|
524
|
+
'130314': InvalidOrder, # Trigger the global position limit and prompt the remaining quantity available for purchase
|
525
|
+
'130315': NotSupported, # This feature has been suspended due to country restrictions
|
526
|
+
'126000': ExchangeError, # Abnormal margin trading
|
527
|
+
'126001': NotSupported, # Users currently do not support high frequency
|
528
|
+
'126002': ExchangeError, # There is a risk problem in your account and transactions are temporarily not allowed!
|
529
|
+
'126003': InvalidOrder, # The commission amount is less than the minimum transaction amount for a single commission
|
530
|
+
'126004': ExchangeError, # Trading pair does not exist or is prohibited
|
531
|
+
'126005': PermissionDenied, # This trading pair requires advanced KYC certification before trading
|
532
|
+
'126006': ExchangeError, # Trading pair is not available
|
533
|
+
'126007': ExchangeError, # Trading pair suspended
|
534
|
+
'126009': ExchangeError, # Trading pair is suspended from creating orders
|
535
|
+
'126010': ExchangeError, # Trading pair suspended order cancellation
|
536
|
+
'126011': ExchangeError, # There are too many orders in the order
|
537
|
+
'126013': InsufficientFunds, # Insufficient account balance
|
538
|
+
'126015': ExchangeError, # It is prohibited to place orders on self trading pair
|
539
|
+
'126021': NotSupported, # This digital asset does not support user participation in your region, thank you for your understanding!
|
540
|
+
'126022': InvalidOrder, # The final transaction price of your order will trigger the price protection strategy. To protect the price from deviating too much, please place an order again.
|
541
|
+
'126027': InvalidOrder, # Only limit orders are supported
|
542
|
+
'126028': InvalidOrder, # Only limit orders are supported before the specified time
|
543
|
+
'126029': InvalidOrder, # The maximum order price is: xxx
|
544
|
+
'126030': InvalidOrder, # The minimum order price is: xxx
|
545
|
+
'126033': InvalidOrder, # Duplicate order
|
546
|
+
'126034': InvalidOrder, # Failed to create take profit and stop loss order
|
547
|
+
'126036': InvalidOrder, # Failed to create margin order
|
548
|
+
'126037': ExchangeError, # Due to country and region restrictions, self function has been suspended!
|
549
|
+
'126038': ExchangeError, # Third-party service call failed(internal exception)
|
550
|
+
'126039': ExchangeError, # Third-party service call failed, reason: xxx
|
551
|
+
'126041': ExchangeError, # clientTimestamp parameter error
|
552
|
+
'126042': ExchangeError, # Exceeded maximum position limit
|
553
|
+
'126043': OrderNotFound, # Order does not exist
|
554
|
+
'126044': InvalidOrder, # clientOid duplicate
|
555
|
+
'126045': NotSupported, # This digital asset does not support user participation in your region, thank you for your understanding!
|
556
|
+
'126046': NotSupported, # This digital asset does not support your IP region, thank you for your understanding!
|
557
|
+
'126047': PermissionDenied, # Please complete identity verification
|
558
|
+
'126048': PermissionDenied, # Please complete authentication for the master account
|
559
|
+
'135005': ExchangeError, # Margin order query business abnormality
|
560
|
+
'135018': ExchangeError, # Margin order query service abnormality
|
467
561
|
'200004': InsufficientFunds,
|
468
562
|
'210014': InvalidOrder, # {"code":"210014","msg":"Exceeds the max. borrowing amount, the remaining amount you can borrow: 0USDT"}
|
469
563
|
'210021': InsufficientFunds, # {"code":"210021","msg":"Balance not enough"}
|
@@ -480,20 +574,25 @@ class kucoin(Exchange, ImplicitAPI):
|
|
480
574
|
'400006': AuthenticationError,
|
481
575
|
'400007': AuthenticationError,
|
482
576
|
'400008': NotSupported,
|
483
|
-
'400100': InsufficientFunds, # {"msg":"account.available.amount","code":"400100"}
|
577
|
+
'400100': InsufficientFunds, # {"msg":"account.available.amount","code":"400100"} or {"msg":"Withdrawal amount is below the minimum requirement.","code":"400100"}
|
484
578
|
'400200': InvalidOrder, # {"code":"400200","msg":"Forbidden to place an order"}
|
579
|
+
'400330': InvalidOrder, # {"msg":"Order price can't deviate from NAV by 50%","code":"400330"}
|
485
580
|
'400350': InvalidOrder, # {"code":"400350","msg":"Upper limit for holding: 10,000USDT, you can still buy 10,000USDT worth of coin."}
|
486
581
|
'400370': InvalidOrder, # {"code":"400370","msg":"Max. price: 0.02500000000000000000"}
|
487
582
|
'400400': BadRequest, # Parameter error
|
583
|
+
'400401': AuthenticationError, # User is not logged in
|
488
584
|
'400500': InvalidOrder, # {"code":"400500","msg":"Your located country/region is currently not supported for the trading of self token"}
|
489
585
|
'400600': BadSymbol, # {"code":"400600","msg":"validation.createOrder.symbolNotAvailable"}
|
490
586
|
'400760': InvalidOrder, # {"code":"400760","msg":"order price should be more than XX"}
|
491
587
|
'401000': BadRequest, # {"code":"401000","msg":"The interface has been deprecated"}
|
588
|
+
'408000': BadRequest, # Network timeout, please try again later
|
492
589
|
'411100': AccountSuspended,
|
493
590
|
'415000': BadRequest, # {"code":"415000","msg":"Unsupported Media Type"}
|
494
591
|
'400303': PermissionDenied, # {"msg":"To enjoy the full range of our products and services, we kindly request you complete the identity verification process.","code":"400303"}
|
495
592
|
'500000': ExchangeNotAvailable, # {"code":"500000","msg":"Internal Server Error"}
|
496
593
|
'260220': InvalidAddress, # {"code": "260220", "msg": "deposit.address.not.exists"}
|
594
|
+
'600100': InsufficientFunds, # {"msg":"Funds below the minimum requirement.","code":"600100"}
|
595
|
+
'600101': InvalidOrder, # {"msg":"The order funds should more then 0.1 USDT.","code":"600101"}
|
497
596
|
'900014': BadRequest, # {"code":"900014","msg":"Invalid chainId"}
|
498
597
|
},
|
499
598
|
'broad': {
|
@@ -551,11 +650,17 @@ class kucoin(Exchange, ImplicitAPI):
|
|
551
650
|
'BIFI': 'BIFIF',
|
552
651
|
'VAI': 'VAIOT',
|
553
652
|
'WAX': 'WAXP',
|
653
|
+
'ALT': 'APTOSLAUNCHTOKEN',
|
654
|
+
'KALT': 'ALT', # ALTLAYER
|
655
|
+
'FUD': 'FTX Users\' Debt',
|
554
656
|
},
|
555
657
|
'options': {
|
658
|
+
'hf': None, # would be auto set to `true/false` after first load
|
556
659
|
'version': 'v1',
|
557
660
|
'symbolSeparator': '-',
|
558
661
|
'fetchMyTradesMethod': 'private_get_fills',
|
662
|
+
'timeDifference': 0, # the difference between system clock and Binance clock
|
663
|
+
'adjustForTimeDifference': False, # controls the adjustment logic upon instantiation
|
559
664
|
'fetchCurrencies': {
|
560
665
|
'webApiEnable': True, # fetches from WEB
|
561
666
|
'webApiRetries': 1,
|
@@ -575,6 +680,8 @@ class kucoin(Exchange, ImplicitAPI):
|
|
575
680
|
'currencies': 'v3',
|
576
681
|
'currencies/{currency}': 'v3',
|
577
682
|
'symbols': 'v2',
|
683
|
+
'mark-price/all-symbols': 'v3',
|
684
|
+
'announcements': 'v3',
|
578
685
|
},
|
579
686
|
},
|
580
687
|
'private': {
|
@@ -599,6 +706,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
599
706
|
'oco/orders': 'v3',
|
600
707
|
# margin trading
|
601
708
|
'hf/margin/orders/active': 'v3',
|
709
|
+
'hf/margin/order/active/symbols': 'v3',
|
602
710
|
'hf/margin/orders/done': 'v3',
|
603
711
|
'hf/margin/orders/{orderId}': 'v3',
|
604
712
|
'hf/margin/orders/client-order/{clientOid}': 'v3',
|
@@ -612,6 +720,10 @@ class kucoin(Exchange, ImplicitAPI):
|
|
612
720
|
'project/marketInterestRate': 'v3',
|
613
721
|
'redeem/orders': 'v3',
|
614
722
|
'purchase/orders': 'v3',
|
723
|
+
'migrate/user/account/status': 'v3',
|
724
|
+
'margin/symbols': 'v3',
|
725
|
+
'affiliate/inviter/statistics': 'v2',
|
726
|
+
'asset/ndbroker/deposit/list': 'v1',
|
615
727
|
},
|
616
728
|
'POST': {
|
617
729
|
# account
|
@@ -621,6 +733,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
621
733
|
'accounts/sub-transfer': 'v2',
|
622
734
|
'accounts/inner-transfer': 'v2',
|
623
735
|
'transfer-out': 'v3',
|
736
|
+
'deposit-address/create': 'v3',
|
624
737
|
# spot trading
|
625
738
|
'oco/order': 'v3',
|
626
739
|
# margin trading
|
@@ -631,6 +744,8 @@ class kucoin(Exchange, ImplicitAPI):
|
|
631
744
|
'purchase': 'v3',
|
632
745
|
'redeem': 'v3',
|
633
746
|
'lend/purchase/update': 'v3',
|
747
|
+
'position/update-user-leverage': 'v3',
|
748
|
+
'withdrawals': 'v3',
|
634
749
|
},
|
635
750
|
'DELETE': {
|
636
751
|
# account
|
@@ -678,7 +793,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
678
793
|
'hf': 'trade_hf',
|
679
794
|
},
|
680
795
|
'networks': {
|
681
|
-
'
|
796
|
+
'BRC20': 'btc',
|
682
797
|
'BTCNATIVESEGWIT': 'bech32',
|
683
798
|
'ERC20': 'eth',
|
684
799
|
'TRC20': 'trx',
|
@@ -696,7 +811,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
696
811
|
'TLOS': 'tlos', # tlosevm is different
|
697
812
|
'CFX': 'cfx',
|
698
813
|
'ACA': 'aca',
|
699
|
-
'
|
814
|
+
'OP': 'optimism',
|
700
815
|
'ONT': 'ont',
|
701
816
|
'GLMR': 'glmr',
|
702
817
|
'CSPR': 'cspr',
|
@@ -815,6 +930,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
815
930
|
'TRUE': 'true',
|
816
931
|
'CS': 'cs',
|
817
932
|
'ORAI': 'orai',
|
933
|
+
'BASE': 'base',
|
818
934
|
# below will be uncommented after consensus
|
819
935
|
# 'BITCOINDIAMON': 'bcd',
|
820
936
|
# 'BITCOINGOLD': 'btg',
|
@@ -890,15 +1006,85 @@ class kucoin(Exchange, ImplicitAPI):
|
|
890
1006
|
'spot': 'TRADE',
|
891
1007
|
},
|
892
1008
|
},
|
1009
|
+
'features': {
|
1010
|
+
'spot': {
|
1011
|
+
'sandbox': False,
|
1012
|
+
'createOrder': {
|
1013
|
+
'marginMode': True,
|
1014
|
+
'triggerPrice': True,
|
1015
|
+
'triggerPriceType': None,
|
1016
|
+
'triggerDirection': False,
|
1017
|
+
'stopLossPrice': True,
|
1018
|
+
'takeProfitPrice': True,
|
1019
|
+
'attachedStopLossTakeProfit': None, # not supported
|
1020
|
+
'timeInForce': {
|
1021
|
+
'IOC': True,
|
1022
|
+
'FOK': True,
|
1023
|
+
'PO': True,
|
1024
|
+
'GTD': True,
|
1025
|
+
},
|
1026
|
+
'hedged': False,
|
1027
|
+
'trailing': False,
|
1028
|
+
'leverage': False,
|
1029
|
+
'marketBuyByCost': True,
|
1030
|
+
'marketBuyRequiresPrice': False,
|
1031
|
+
'selfTradePrevention': True, # todo implement
|
1032
|
+
'iceberg': True, # todo implement
|
1033
|
+
},
|
1034
|
+
'createOrders': {
|
1035
|
+
'max': 5,
|
1036
|
+
},
|
1037
|
+
'fetchMyTrades': {
|
1038
|
+
'marginMode': True,
|
1039
|
+
'limit': None,
|
1040
|
+
'daysBack': None,
|
1041
|
+
'untilDays': 7, # per implementation comments
|
1042
|
+
},
|
1043
|
+
'fetchOrder': {
|
1044
|
+
'marginMode': False,
|
1045
|
+
'trigger': True,
|
1046
|
+
'trailing': False,
|
1047
|
+
},
|
1048
|
+
'fetchOpenOrders': {
|
1049
|
+
'marginMode': True,
|
1050
|
+
'limit': 500,
|
1051
|
+
'trigger': True,
|
1052
|
+
'trailing': False,
|
1053
|
+
},
|
1054
|
+
'fetchOrders': None,
|
1055
|
+
'fetchClosedOrders': {
|
1056
|
+
'marginMode': True,
|
1057
|
+
'limit': 500,
|
1058
|
+
'daysBack': None,
|
1059
|
+
'daysBackCanceled': None,
|
1060
|
+
'untilDays': 7,
|
1061
|
+
'trigger': True,
|
1062
|
+
'trailing': False,
|
1063
|
+
},
|
1064
|
+
'fetchOHLCV': {
|
1065
|
+
'limit': 1500,
|
1066
|
+
},
|
1067
|
+
},
|
1068
|
+
'swap': {
|
1069
|
+
'linear': None,
|
1070
|
+
'inverse': None,
|
1071
|
+
},
|
1072
|
+
'future': {
|
1073
|
+
'linear': None,
|
1074
|
+
'inverse': None,
|
1075
|
+
},
|
1076
|
+
},
|
893
1077
|
})
|
894
1078
|
|
895
1079
|
def nonce(self):
|
896
|
-
return self.milliseconds()
|
1080
|
+
return self.milliseconds() - self.options['timeDifference']
|
897
1081
|
|
898
1082
|
def fetch_time(self, params={}):
|
899
1083
|
"""
|
900
1084
|
fetches the current integer timestamp in milliseconds from the exchange server
|
901
|
-
|
1085
|
+
|
1086
|
+
https://docs.kucoin.com/#server-time
|
1087
|
+
|
902
1088
|
:param dict [params]: extra parameters specific to the exchange API endpoint
|
903
1089
|
:returns int: the current integer timestamp in milliseconds from the exchange server
|
904
1090
|
"""
|
@@ -915,7 +1101,9 @@ class kucoin(Exchange, ImplicitAPI):
|
|
915
1101
|
def fetch_status(self, params={}):
|
916
1102
|
"""
|
917
1103
|
the latest known information on the availability of the exchange API
|
918
|
-
|
1104
|
+
|
1105
|
+
https://docs.kucoin.com/#service-status
|
1106
|
+
|
919
1107
|
:param dict [params]: extra parameters specific to the exchange API endpoint
|
920
1108
|
:returns dict: a `status structure <https://docs.ccxt.com/#/?id=exchange-status-structure>`
|
921
1109
|
"""
|
@@ -939,15 +1127,20 @@ class kucoin(Exchange, ImplicitAPI):
|
|
939
1127
|
'info': response,
|
940
1128
|
}
|
941
1129
|
|
942
|
-
def fetch_markets(self, params={}):
|
1130
|
+
def fetch_markets(self, params={}) -> List[Market]:
|
943
1131
|
"""
|
944
1132
|
retrieves data on all markets for kucoin
|
945
|
-
|
946
|
-
|
1133
|
+
|
1134
|
+
https://docs.kucoin.com/#get-symbols-list-deprecated
|
1135
|
+
https://docs.kucoin.com/#get-all-tickers
|
1136
|
+
|
947
1137
|
:param dict [params]: extra parameters specific to the exchange API endpoint
|
948
1138
|
:returns dict[]: an array of objects representing market data
|
949
1139
|
"""
|
950
|
-
|
1140
|
+
fetchTickersFees = None
|
1141
|
+
fetchTickersFees, params = self.handle_option_and_params(params, 'fetchMarkets', 'fetchTickersFees', True)
|
1142
|
+
promises = []
|
1143
|
+
promises.append(self.publicGetSymbols(params))
|
951
1144
|
#
|
952
1145
|
# {
|
953
1146
|
# "code": "200000",
|
@@ -970,59 +1163,102 @@ class kucoin(Exchange, ImplicitAPI):
|
|
970
1163
|
# "isMarginEnabled": True,
|
971
1164
|
# "enableTrading": True
|
972
1165
|
# },
|
973
|
-
# ]
|
974
|
-
# }
|
975
1166
|
#
|
976
|
-
|
977
|
-
|
978
|
-
|
979
|
-
|
1167
|
+
credentialsSet = self.check_required_credentials(False)
|
1168
|
+
requestMarginables = credentialsSet and self.safe_bool(params, 'marginables', True)
|
1169
|
+
if requestMarginables:
|
1170
|
+
promises.append(self.privateGetMarginSymbols(params)) # cross margin symbols
|
1171
|
+
#
|
1172
|
+
# {
|
1173
|
+
# "code": "200000",
|
1174
|
+
# "data": {
|
1175
|
+
# "timestamp": 1719393213421,
|
1176
|
+
# "items": [
|
1177
|
+
# {
|
1178
|
+
# # same object market, with one additional field:
|
1179
|
+
# "minFunds": "0.1"
|
1180
|
+
# },
|
1181
|
+
#
|
1182
|
+
promises.append(self.privateGetIsolatedSymbols(params)) # isolated margin symbols
|
1183
|
+
#
|
1184
|
+
# {
|
1185
|
+
# "code": "200000",
|
1186
|
+
# "data": [
|
1187
|
+
# {
|
1188
|
+
# "symbol": "NKN-USDT",
|
1189
|
+
# "symbolName": "NKN-USDT",
|
1190
|
+
# "baseCurrency": "NKN",
|
1191
|
+
# "quoteCurrency": "USDT",
|
1192
|
+
# "maxLeverage": 5,
|
1193
|
+
# "flDebtRatio": "0.97",
|
1194
|
+
# "tradeEnable": True,
|
1195
|
+
# "autoRenewMaxDebtRatio": "0.96",
|
1196
|
+
# "baseBorrowEnable": True,
|
1197
|
+
# "quoteBorrowEnable": True,
|
1198
|
+
# "baseTransferInEnable": True,
|
1199
|
+
# "quoteTransferInEnable": True,
|
1200
|
+
# "baseBorrowCoefficient": "1",
|
1201
|
+
# "quoteBorrowCoefficient": "1"
|
1202
|
+
# },
|
1203
|
+
#
|
980
1204
|
if fetchTickersFees:
|
981
|
-
|
982
|
-
|
983
|
-
|
984
|
-
|
985
|
-
|
986
|
-
|
987
|
-
|
988
|
-
|
989
|
-
|
990
|
-
|
991
|
-
|
992
|
-
|
993
|
-
|
994
|
-
|
995
|
-
|
996
|
-
|
997
|
-
|
998
|
-
|
999
|
-
|
1000
|
-
|
1001
|
-
|
1002
|
-
|
1003
|
-
|
1004
|
-
|
1005
|
-
|
1006
|
-
|
1007
|
-
|
1008
|
-
|
1009
|
-
|
1010
|
-
|
1011
|
-
|
1012
|
-
|
1205
|
+
promises.append(self.publicGetMarketAllTickers(params))
|
1206
|
+
#
|
1207
|
+
# {
|
1208
|
+
# "code": "200000",
|
1209
|
+
# "data": {
|
1210
|
+
# "time":1602832092060,
|
1211
|
+
# "ticker":[
|
1212
|
+
# {
|
1213
|
+
# "symbol": "BTC-USDT", # symbol
|
1214
|
+
# "symbolName":"BTC-USDT", # Name of trading pairs, it would change after renaming
|
1215
|
+
# "buy": "11328.9", # bestAsk
|
1216
|
+
# "sell": "11329", # bestBid
|
1217
|
+
# "changeRate": "-0.0055", # 24h change rate
|
1218
|
+
# "changePrice": "-63.6", # 24h change price
|
1219
|
+
# "high": "11610", # 24h highest price
|
1220
|
+
# "low": "11200", # 24h lowest price
|
1221
|
+
# "vol": "2282.70993217", # 24h volume,the aggregated trading volume in BTC
|
1222
|
+
# "volValue": "25984946.157790431", # 24h total, the trading volume in quote currency of last 24 hours
|
1223
|
+
# "last": "11328.9", # last price
|
1224
|
+
# "averagePrice": "11360.66065903", # 24h average transaction price yesterday
|
1225
|
+
# "takerFeeRate": "0.001", # Basic Taker Fee
|
1226
|
+
# "makerFeeRate": "0.001", # Basic Maker Fee
|
1227
|
+
# "takerCoefficient": "1", # Taker Fee Coefficient
|
1228
|
+
# "makerCoefficient": "1" # Maker Fee Coefficient
|
1229
|
+
# }
|
1230
|
+
#
|
1231
|
+
if credentialsSet:
|
1232
|
+
# load migration status for account
|
1233
|
+
promises.append(self.load_migration_status())
|
1234
|
+
responses = promises
|
1235
|
+
symbolsData = self.safe_list(responses[0], 'data')
|
1236
|
+
crossData = self.safe_dict(responses[1], 'data', {}) if requestMarginables else {}
|
1237
|
+
crossItems = self.safe_list(crossData, 'items', [])
|
1238
|
+
crossById = self.index_by(crossItems, 'symbol')
|
1239
|
+
isolatedData = responses[2] if requestMarginables else {}
|
1240
|
+
isolatedItems = self.safe_list(isolatedData, 'data', [])
|
1241
|
+
isolatedById = self.index_by(isolatedItems, 'symbol')
|
1242
|
+
tickersIdx = 3 if requestMarginables else 1
|
1243
|
+
tickersResponse = self.safe_dict(responses, tickersIdx, {})
|
1244
|
+
tickerItems = self.safe_list(self.safe_dict(tickersResponse, 'data', {}), 'ticker', [])
|
1245
|
+
tickersById = self.index_by(tickerItems, 'symbol')
|
1013
1246
|
result = []
|
1014
|
-
for i in range(0, len(
|
1015
|
-
market =
|
1247
|
+
for i in range(0, len(symbolsData)):
|
1248
|
+
market = symbolsData[i]
|
1016
1249
|
id = self.safe_string(market, 'symbol')
|
1017
1250
|
baseId, quoteId = id.split('-')
|
1018
1251
|
base = self.safe_currency_code(baseId)
|
1019
1252
|
quote = self.safe_currency_code(quoteId)
|
1020
1253
|
# quoteIncrement = self.safe_number(market, 'quoteIncrement')
|
1021
|
-
ticker = self.safe_dict(
|
1254
|
+
ticker = self.safe_dict(tickersById, id, {})
|
1022
1255
|
makerFeeRate = self.safe_string(ticker, 'makerFeeRate')
|
1023
1256
|
takerFeeRate = self.safe_string(ticker, 'takerFeeRate')
|
1024
1257
|
makerCoefficient = self.safe_string(ticker, 'makerCoefficient')
|
1025
1258
|
takerCoefficient = self.safe_string(ticker, 'takerCoefficient')
|
1259
|
+
hasCrossMargin = (id in crossById)
|
1260
|
+
hasIsolatedMargin = (id in isolatedById)
|
1261
|
+
isMarginable = self.safe_bool(market, 'isMarginEnabled', False) or hasCrossMargin or hasIsolatedMargin
|
1026
1262
|
result.append({
|
1027
1263
|
'id': id,
|
1028
1264
|
'symbol': base + '/' + quote,
|
@@ -1034,7 +1270,11 @@ class kucoin(Exchange, ImplicitAPI):
|
|
1034
1270
|
'settleId': None,
|
1035
1271
|
'type': 'spot',
|
1036
1272
|
'spot': True,
|
1037
|
-
'margin':
|
1273
|
+
'margin': isMarginable,
|
1274
|
+
'marginModes': {
|
1275
|
+
'cross': hasCrossMargin,
|
1276
|
+
'isolated': hasIsolatedMargin,
|
1277
|
+
},
|
1038
1278
|
'swap': False,
|
1039
1279
|
'future': False,
|
1040
1280
|
'option': False,
|
@@ -1074,12 +1314,40 @@ class kucoin(Exchange, ImplicitAPI):
|
|
1074
1314
|
'created': None,
|
1075
1315
|
'info': market,
|
1076
1316
|
})
|
1317
|
+
if self.options['adjustForTimeDifference']:
|
1318
|
+
self.load_time_difference()
|
1077
1319
|
return result
|
1078
1320
|
|
1079
|
-
def
|
1321
|
+
def load_migration_status(self, force: bool = False):
|
1322
|
+
"""
|
1323
|
+
:param boolean force: load account state for non hf
|
1324
|
+
loads the migration status for the account(hf or not)
|
1325
|
+
|
1326
|
+
https://www.kucoin.com/docs/rest/spot-trading/spot-hf-trade-pro-account/get-user-type
|
1327
|
+
|
1328
|
+
"""
|
1329
|
+
if not ('hf' in self.options) or (self.options['hf'] is None) or force:
|
1330
|
+
result: dict = self.privateGetHfAccountsOpened()
|
1331
|
+
self.options['hf'] = self.safe_bool(result, 'data')
|
1332
|
+
|
1333
|
+
def handle_hf_and_params(self, params={}):
|
1334
|
+
migrated: Bool = self.safe_bool(self.options, 'hf', False)
|
1335
|
+
loadedHf: Bool = None
|
1336
|
+
if migrated is not None:
|
1337
|
+
if migrated:
|
1338
|
+
loadedHf = True
|
1339
|
+
else:
|
1340
|
+
loadedHf = False
|
1341
|
+
hf: Bool = self.safe_bool(params, 'hf', loadedHf)
|
1342
|
+
params = self.omit(params, 'hf')
|
1343
|
+
return [hf, params]
|
1344
|
+
|
1345
|
+
def fetch_currencies(self, params={}) -> Currencies:
|
1080
1346
|
"""
|
1081
1347
|
fetches all available currencies on an exchange
|
1082
|
-
|
1348
|
+
|
1349
|
+
https://docs.kucoin.com/#get-currencies
|
1350
|
+
|
1083
1351
|
:param dict params: extra parameters specific to the exchange API endpoint
|
1084
1352
|
:returns dict: an associative dictionary of currencies
|
1085
1353
|
"""
|
@@ -1101,8 +1369,10 @@ class kucoin(Exchange, ImplicitAPI):
|
|
1101
1369
|
# "chains":[
|
1102
1370
|
# {
|
1103
1371
|
# "chainName":"ERC20",
|
1104
|
-
# "
|
1372
|
+
# "chainId": "eth"
|
1105
1373
|
# "withdrawalMinSize":"2999",
|
1374
|
+
# "depositMinSize":null,
|
1375
|
+
# "withdrawFeeRate":"0",
|
1106
1376
|
# "withdrawalMinFee":"2999",
|
1107
1377
|
# "isWithdrawEnabled":false,
|
1108
1378
|
# "isDepositEnabled":false,
|
@@ -1151,12 +1421,12 @@ class kucoin(Exchange, ImplicitAPI):
|
|
1151
1421
|
# }
|
1152
1422
|
#
|
1153
1423
|
responses = promises
|
1154
|
-
currenciesResponse = self.
|
1155
|
-
currenciesData = self.
|
1156
|
-
additionalResponse = self.
|
1157
|
-
additionalData = self.
|
1424
|
+
currenciesResponse = self.safe_dict(responses, 0, {})
|
1425
|
+
currenciesData = self.safe_list(currenciesResponse, 'data', [])
|
1426
|
+
additionalResponse = self.safe_dict(responses, 1, {})
|
1427
|
+
additionalData = self.safe_list(additionalResponse, 'data', [])
|
1158
1428
|
additionalDataGrouped = self.group_by(additionalData, 'currency')
|
1159
|
-
result = {}
|
1429
|
+
result: dict = {}
|
1160
1430
|
for i in range(0, len(currenciesData)):
|
1161
1431
|
entry = currenciesData[i]
|
1162
1432
|
id = self.safe_string(entry, 'currency')
|
@@ -1164,9 +1434,9 @@ class kucoin(Exchange, ImplicitAPI):
|
|
1164
1434
|
code = self.safe_currency_code(id)
|
1165
1435
|
isWithdrawEnabled = None
|
1166
1436
|
isDepositEnabled = None
|
1167
|
-
networks = {}
|
1437
|
+
networks: dict = {}
|
1168
1438
|
chains = self.safe_list(entry, 'chains', [])
|
1169
|
-
extraChainsData = self.index_by(self.
|
1439
|
+
extraChainsData = self.index_by(self.safe_list(additionalDataGrouped, id, []), 'chain')
|
1170
1440
|
rawPrecision = self.safe_string(entry, 'precision')
|
1171
1441
|
precision = self.parse_number(self.parse_precision(rawPrecision))
|
1172
1442
|
chainsLength = len(chains)
|
@@ -1177,7 +1447,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
1177
1447
|
for j in range(0, chainsLength):
|
1178
1448
|
chain = chains[j]
|
1179
1449
|
chainId = self.safe_string(chain, 'chainId')
|
1180
|
-
networkCode = self.network_id_to_code(chainId)
|
1450
|
+
networkCode = self.network_id_to_code(chainId, code)
|
1181
1451
|
chainWithdrawEnabled = self.safe_bool(chain, 'isWithdrawEnabled', False)
|
1182
1452
|
if isWithdrawEnabled is None:
|
1183
1453
|
isWithdrawEnabled = chainWithdrawEnabled
|
@@ -1205,7 +1475,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
1205
1475
|
'max': None,
|
1206
1476
|
},
|
1207
1477
|
'deposit': {
|
1208
|
-
'min': self.safe_number(
|
1478
|
+
'min': self.safe_number(chain, 'depositMinSize'),
|
1209
1479
|
'max': None,
|
1210
1480
|
},
|
1211
1481
|
},
|
@@ -1231,7 +1501,9 @@ class kucoin(Exchange, ImplicitAPI):
|
|
1231
1501
|
def fetch_accounts(self, params={}) -> List[Account]:
|
1232
1502
|
"""
|
1233
1503
|
fetch all the accounts associated with a profile
|
1234
|
-
|
1504
|
+
|
1505
|
+
https://docs.kucoin.com/#list-accounts
|
1506
|
+
|
1235
1507
|
:param dict [params]: extra parameters specific to the exchange API endpoint
|
1236
1508
|
:returns dict: a dictionary of `account structures <https://docs.ccxt.com/#/?id=account-structure>` indexed by the account type
|
1237
1509
|
"""
|
@@ -1279,14 +1551,16 @@ class kucoin(Exchange, ImplicitAPI):
|
|
1279
1551
|
def fetch_transaction_fee(self, code: str, params={}):
|
1280
1552
|
"""
|
1281
1553
|
*DEPRECATED* please use fetchDepositWithdrawFee instead
|
1282
|
-
|
1554
|
+
|
1555
|
+
https://docs.kucoin.com/#get-withdrawal-quotas
|
1556
|
+
|
1283
1557
|
:param str code: unified currency code
|
1284
1558
|
:param dict params: extra parameters specific to the exchange API endpoint
|
1285
1559
|
:returns dict: a `fee structure <https://docs.ccxt.com/#/?id=fee-structure>`
|
1286
1560
|
"""
|
1287
1561
|
self.load_markets()
|
1288
1562
|
currency = self.currency(code)
|
1289
|
-
request = {
|
1563
|
+
request: dict = {
|
1290
1564
|
'currency': currency['id'],
|
1291
1565
|
}
|
1292
1566
|
networkCode = None
|
@@ -1294,8 +1568,8 @@ class kucoin(Exchange, ImplicitAPI):
|
|
1294
1568
|
if networkCode is not None:
|
1295
1569
|
request['chain'] = self.network_code_to_id(networkCode).lower()
|
1296
1570
|
response = self.privateGetWithdrawalsQuotas(self.extend(request, params))
|
1297
|
-
data = self.
|
1298
|
-
withdrawFees = {}
|
1571
|
+
data = self.safe_dict(response, 'data', {})
|
1572
|
+
withdrawFees: dict = {}
|
1299
1573
|
withdrawFees[code] = self.safe_number(data, 'withdrawMinFee')
|
1300
1574
|
return {
|
1301
1575
|
'info': response,
|
@@ -1306,7 +1580,9 @@ class kucoin(Exchange, ImplicitAPI):
|
|
1306
1580
|
def fetch_deposit_withdraw_fee(self, code: str, params={}):
|
1307
1581
|
"""
|
1308
1582
|
fetch the fee for deposits and withdrawals
|
1309
|
-
|
1583
|
+
|
1584
|
+
https://docs.kucoin.com/#get-withdrawal-quotas
|
1585
|
+
|
1310
1586
|
:param str code: unified currency code
|
1311
1587
|
:param dict [params]: extra parameters specific to the exchange API endpoint
|
1312
1588
|
:param str [params.network]: The chain of currency. This only apply for multi-chain currency, and there is no need for single chain currency; you can query the chain through the response of the GET /api/v2/currencies/{currency} interface
|
@@ -1314,7 +1590,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
1314
1590
|
"""
|
1315
1591
|
self.load_markets()
|
1316
1592
|
currency = self.currency(code)
|
1317
|
-
request = {
|
1593
|
+
request: dict = {
|
1318
1594
|
'currency': currency['id'],
|
1319
1595
|
}
|
1320
1596
|
networkCode = None
|
@@ -1359,32 +1635,28 @@ class kucoin(Exchange, ImplicitAPI):
|
|
1359
1635
|
# "chain": "ERC20"
|
1360
1636
|
# }
|
1361
1637
|
#
|
1362
|
-
|
1638
|
+
minWithdrawFee = self.safe_number(fee, 'withdrawMinFee')
|
1639
|
+
result: dict = {
|
1363
1640
|
'info': fee,
|
1364
1641
|
'withdraw': {
|
1642
|
+
'fee': minWithdrawFee,
|
1643
|
+
'percentage': False,
|
1644
|
+
},
|
1645
|
+
'deposit': {
|
1365
1646
|
'fee': None,
|
1366
1647
|
'percentage': None,
|
1367
1648
|
},
|
1649
|
+
'networks': {},
|
1650
|
+
}
|
1651
|
+
networkId = self.safe_string(fee, 'chain')
|
1652
|
+
networkCode = self.network_id_to_code(networkId, self.safe_string(currency, 'code'))
|
1653
|
+
result['networks'][networkCode] = {
|
1654
|
+
'withdraw': minWithdrawFee,
|
1368
1655
|
'deposit': {
|
1369
1656
|
'fee': None,
|
1370
1657
|
'percentage': None,
|
1371
1658
|
},
|
1372
|
-
'networks': {},
|
1373
1659
|
}
|
1374
|
-
isWithdrawEnabled = self.safe_bool(fee, 'isWithdrawEnabled')
|
1375
|
-
if isWithdrawEnabled:
|
1376
|
-
result['withdraw']['fee'] = self.safe_number_2(fee, 'withdrawalMinFee', 'withdrawMinFee')
|
1377
|
-
result['withdraw']['percentage'] = False
|
1378
|
-
networkId = self.safe_string(fee, 'chain')
|
1379
|
-
if networkId:
|
1380
|
-
networkCode = self.network_id_to_code(networkId, self.safe_string(currency, 'code'))
|
1381
|
-
result['networks'][networkCode] = {
|
1382
|
-
'withdraw': result['withdraw'],
|
1383
|
-
'deposit': {
|
1384
|
-
'fee': None,
|
1385
|
-
'percentage': None,
|
1386
|
-
},
|
1387
|
-
}
|
1388
1660
|
return result
|
1389
1661
|
|
1390
1662
|
def is_futures_method(self, methodName, params):
|
@@ -1404,7 +1676,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
1404
1676
|
params = self.omit(params, 'type')
|
1405
1677
|
return(type == 'contract') or (type == 'future') or (type == 'futures') # * (type == 'futures') deprecated, use(type == 'future')
|
1406
1678
|
|
1407
|
-
def parse_ticker(self, ticker, market: Market = None) -> Ticker:
|
1679
|
+
def parse_ticker(self, ticker: dict, market: Market = None) -> Ticker:
|
1408
1680
|
#
|
1409
1681
|
# {
|
1410
1682
|
# "symbol": "BTC-USDT", # symbol
|
@@ -1470,7 +1742,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
1470
1742
|
symbol = market['symbol']
|
1471
1743
|
baseVolume = self.safe_string(ticker, 'vol')
|
1472
1744
|
quoteVolume = self.safe_string(ticker, 'volValue')
|
1473
|
-
timestamp = self.
|
1745
|
+
timestamp = self.safe_integer_n(ticker, ['time', 'datetime', 'timePoint'])
|
1474
1746
|
return self.safe_ticker({
|
1475
1747
|
'symbol': symbol,
|
1476
1748
|
'timestamp': timestamp,
|
@@ -1491,13 +1763,16 @@ class kucoin(Exchange, ImplicitAPI):
|
|
1491
1763
|
'average': self.safe_string(ticker, 'averagePrice'),
|
1492
1764
|
'baseVolume': baseVolume,
|
1493
1765
|
'quoteVolume': quoteVolume,
|
1766
|
+
'markPrice': self.safe_string(ticker, 'value'),
|
1494
1767
|
'info': ticker,
|
1495
1768
|
}, market)
|
1496
1769
|
|
1497
1770
|
def fetch_tickers(self, symbols: Strings = None, params={}) -> Tickers:
|
1498
1771
|
"""
|
1499
1772
|
fetches price tickers for multiple markets, statistical information calculated over the past 24 hours for each market
|
1500
|
-
|
1773
|
+
|
1774
|
+
https://docs.kucoin.com/#get-all-tickers
|
1775
|
+
|
1501
1776
|
:param str[]|None symbols: unified symbols of the markets to fetch the ticker for, all market tickers are returned if not assigned
|
1502
1777
|
:param dict [params]: extra parameters specific to the exchange API endpoint
|
1503
1778
|
:returns dict: a dictionary of `ticker structures <https://docs.ccxt.com/#/?id=ticker-structure>`
|
@@ -1536,7 +1811,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
1536
1811
|
data = self.safe_dict(response, 'data', {})
|
1537
1812
|
tickers = self.safe_list(data, 'ticker', [])
|
1538
1813
|
time = self.safe_integer(data, 'time')
|
1539
|
-
result = {}
|
1814
|
+
result: dict = {}
|
1540
1815
|
for i in range(0, len(tickers)):
|
1541
1816
|
tickers[i]['time'] = time
|
1542
1817
|
ticker = self.parse_ticker(tickers[i])
|
@@ -1545,17 +1820,35 @@ class kucoin(Exchange, ImplicitAPI):
|
|
1545
1820
|
result[symbol] = ticker
|
1546
1821
|
return self.filter_by_array_tickers(result, 'symbol', symbols)
|
1547
1822
|
|
1823
|
+
def fetch_mark_prices(self, symbols: Strings = None, params={}) -> Tickers:
|
1824
|
+
"""
|
1825
|
+
fetches the mark price for multiple markets
|
1826
|
+
|
1827
|
+
https://www.kucoin.com/docs/rest/margin-trading/margin-info/get-all-margin-trading-pairs-mark-prices
|
1828
|
+
|
1829
|
+
:param str[] [symbols]: unified symbols of the markets to fetch the ticker for, all market tickers are returned if not assigned
|
1830
|
+
:param dict [params]: extra parameters specific to the exchange API endpoint
|
1831
|
+
:returns dict: a dictionary of `ticker structures <https://docs.ccxt.com/#/?id=ticker-structure>`
|
1832
|
+
"""
|
1833
|
+
self.load_markets()
|
1834
|
+
symbols = self.market_symbols(symbols)
|
1835
|
+
response = self.publicGetMarkPriceAllSymbols(params)
|
1836
|
+
data = self.safe_list(response, 'data', [])
|
1837
|
+
return self.parse_tickers(data)
|
1838
|
+
|
1548
1839
|
def fetch_ticker(self, symbol: str, params={}) -> Ticker:
|
1549
1840
|
"""
|
1550
1841
|
fetches a price ticker, a statistical calculation with the information calculated over the past 24 hours for a specific market
|
1551
|
-
|
1842
|
+
|
1843
|
+
https://docs.kucoin.com/#get-24hr-stats
|
1844
|
+
|
1552
1845
|
:param str symbol: unified symbol of the market to fetch the ticker for
|
1553
1846
|
:param dict [params]: extra parameters specific to the exchange API endpoint
|
1554
1847
|
:returns dict: a `ticker structure <https://docs.ccxt.com/#/?id=ticker-structure>`
|
1555
1848
|
"""
|
1556
1849
|
self.load_markets()
|
1557
1850
|
market = self.market(symbol)
|
1558
|
-
request = {
|
1851
|
+
request: dict = {
|
1559
1852
|
'symbol': market['id'],
|
1560
1853
|
}
|
1561
1854
|
response = self.publicGetMarketStats(self.extend(request, params))
|
@@ -1582,7 +1875,28 @@ class kucoin(Exchange, ImplicitAPI):
|
|
1582
1875
|
# }
|
1583
1876
|
# }
|
1584
1877
|
#
|
1585
|
-
|
1878
|
+
data = self.safe_dict(response, 'data', {})
|
1879
|
+
return self.parse_ticker(data, market)
|
1880
|
+
|
1881
|
+
def fetch_mark_price(self, symbol: str, params={}) -> Ticker:
|
1882
|
+
"""
|
1883
|
+
fetches the mark price for a specific market
|
1884
|
+
|
1885
|
+
https://www.kucoin.com/docs/rest/margin-trading/margin-info/get-mark-price
|
1886
|
+
|
1887
|
+
:param str symbol: unified symbol of the market to fetch the ticker for
|
1888
|
+
:param dict [params]: extra parameters specific to the exchange API endpoint
|
1889
|
+
:returns dict: a `ticker structure <https://docs.ccxt.com/#/?id=ticker-structure>`
|
1890
|
+
"""
|
1891
|
+
self.load_markets()
|
1892
|
+
market = self.market(symbol)
|
1893
|
+
request: dict = {
|
1894
|
+
'symbol': market['id'],
|
1895
|
+
}
|
1896
|
+
response = self.publicGetMarkPriceSymbolCurrent(self.extend(request, params))
|
1897
|
+
#
|
1898
|
+
data = self.safe_dict(response, 'data', {})
|
1899
|
+
return self.parse_ticker(data, market)
|
1586
1900
|
|
1587
1901
|
def parse_ohlcv(self, ohlcv, market: Market = None) -> list:
|
1588
1902
|
#
|
@@ -1608,7 +1922,9 @@ class kucoin(Exchange, ImplicitAPI):
|
|
1608
1922
|
def fetch_ohlcv(self, symbol: str, timeframe='1m', since: Int = None, limit: Int = None, params={}) -> List[list]:
|
1609
1923
|
"""
|
1610
1924
|
fetches historical candlestick data containing the open, high, low, and close price, and the volume of a market
|
1611
|
-
|
1925
|
+
|
1926
|
+
https://docs.kucoin.com/#get-klines
|
1927
|
+
|
1612
1928
|
:param str symbol: unified symbol of the market to fetch OHLCV data for
|
1613
1929
|
:param str timeframe: the length of time each candle represents
|
1614
1930
|
:param int [since]: timestamp in ms of the earliest candle to fetch
|
@@ -1624,7 +1940,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
1624
1940
|
return self.fetch_paginated_call_deterministic('fetchOHLCV', symbol, since, limit, timeframe, params, 1500)
|
1625
1941
|
market = self.market(symbol)
|
1626
1942
|
marketId = market['id']
|
1627
|
-
request = {
|
1943
|
+
request: dict = {
|
1628
1944
|
'symbol': marketId,
|
1629
1945
|
'type': self.safe_string(self.timeframes, timeframe, timeframe),
|
1630
1946
|
}
|
@@ -1659,7 +1975,9 @@ class kucoin(Exchange, ImplicitAPI):
|
|
1659
1975
|
|
1660
1976
|
def create_deposit_address(self, code: str, params={}):
|
1661
1977
|
"""
|
1662
|
-
|
1978
|
+
|
1979
|
+
https://www.kucoin.com/docs/rest/funding/deposit/create-deposit-address-v3-
|
1980
|
+
|
1663
1981
|
create a currency deposit address
|
1664
1982
|
:param str code: unified currency code of the currency for the deposit address
|
1665
1983
|
:param dict [params]: extra parameters specific to the exchange API endpoint
|
@@ -1668,24 +1986,38 @@ class kucoin(Exchange, ImplicitAPI):
|
|
1668
1986
|
"""
|
1669
1987
|
self.load_markets()
|
1670
1988
|
currency = self.currency(code)
|
1671
|
-
request = {
|
1989
|
+
request: dict = {
|
1672
1990
|
'currency': currency['id'],
|
1673
1991
|
}
|
1674
1992
|
networkCode = None
|
1675
1993
|
networkCode, params = self.handle_network_code_and_params(params)
|
1676
1994
|
if networkCode is not None:
|
1677
|
-
request['chain'] = self.network_code_to_id(networkCode)
|
1678
|
-
response = self.
|
1995
|
+
request['chain'] = self.network_code_to_id(networkCode) # docs mention "chain-name", but seems "chain-id" is used, like in "fetchDepositAddress"
|
1996
|
+
response = self.privatePostDepositAddressCreate(self.extend(request, params))
|
1679
1997
|
# {"code":"260000","msg":"Deposit address already exists."}
|
1680
|
-
#
|
1681
|
-
#
|
1998
|
+
#
|
1999
|
+
# {
|
2000
|
+
# "code": "200000",
|
2001
|
+
# "data": {
|
2002
|
+
# "address": "0x2336d1834faab10b2dac44e468f2627138417431",
|
2003
|
+
# "memo": null,
|
2004
|
+
# "chainId": "bsc",
|
2005
|
+
# "to": "MAIN",
|
2006
|
+
# "expirationDate": 0,
|
2007
|
+
# "currency": "BNB",
|
2008
|
+
# "chainName": "BEP20"
|
2009
|
+
# }
|
2010
|
+
# }
|
2011
|
+
#
|
1682
2012
|
data = self.safe_dict(response, 'data', {})
|
1683
2013
|
return self.parse_deposit_address(data, currency)
|
1684
2014
|
|
1685
|
-
def fetch_deposit_address(self, code: str, params={}):
|
2015
|
+
def fetch_deposit_address(self, code: str, params={}) -> DepositAddress:
|
1686
2016
|
"""
|
1687
2017
|
fetch the deposit address for a currency associated with self account
|
1688
|
-
|
2018
|
+
|
2019
|
+
https://docs.kucoin.com/#get-deposit-addresses-v2
|
2020
|
+
|
1689
2021
|
:param str code: unified currency code
|
1690
2022
|
:param dict [params]: extra parameters specific to the exchange API endpoint
|
1691
2023
|
:param str [params.network]: the blockchain network name
|
@@ -1693,7 +2025,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
1693
2025
|
"""
|
1694
2026
|
self.load_markets()
|
1695
2027
|
currency = self.currency(code)
|
1696
|
-
request = {
|
2028
|
+
request: dict = {
|
1697
2029
|
'currency': currency['id'],
|
1698
2030
|
# for USDT - OMNI, ERC20, TRC20, default is ERC20
|
1699
2031
|
# for BTC - Native, Segwit, TRC20, the parameters are bech32, btc, trx, default is Native
|
@@ -1714,28 +2046,30 @@ class kucoin(Exchange, ImplicitAPI):
|
|
1714
2046
|
raise ExchangeError(self.id + ' fetchDepositAddress() returned an empty response, you might try to run createDepositAddress() first and try again')
|
1715
2047
|
return self.parse_deposit_address(data, currency)
|
1716
2048
|
|
1717
|
-
def parse_deposit_address(self, depositAddress, currency: Currency = None):
|
2049
|
+
def parse_deposit_address(self, depositAddress, currency: Currency = None) -> DepositAddress:
|
1718
2050
|
address = self.safe_string(depositAddress, 'address')
|
1719
2051
|
# BCH/BSV is returned with a "bitcoincash:" prefix, which we cut off here and only keep the address
|
1720
2052
|
if address is not None:
|
1721
2053
|
address = address.replace('bitcoincash:', '')
|
1722
2054
|
code = None
|
1723
2055
|
if currency is not None:
|
1724
|
-
code = currency['id']
|
2056
|
+
code = self.safe_currency_code(currency['id'])
|
1725
2057
|
if code != 'NIM':
|
1726
2058
|
# contains spaces
|
1727
2059
|
self.check_address(address)
|
1728
2060
|
return {
|
1729
2061
|
'info': depositAddress,
|
1730
2062
|
'currency': code,
|
2063
|
+
'network': self.network_id_to_code(self.safe_string(depositAddress, 'chainId')),
|
1731
2064
|
'address': address,
|
1732
2065
|
'tag': self.safe_string(depositAddress, 'memo'),
|
1733
|
-
'network': self.network_id_to_code(self.safe_string(depositAddress, 'chain')),
|
1734
2066
|
}
|
1735
2067
|
|
1736
|
-
def fetch_deposit_addresses_by_network(self, code: str, params={}):
|
2068
|
+
def fetch_deposit_addresses_by_network(self, code: str, params={}) -> List[DepositAddress]:
|
1737
2069
|
"""
|
1738
|
-
|
2070
|
+
|
2071
|
+
https://docs.kucoin.com/#get-deposit-addresses-v2
|
2072
|
+
|
1739
2073
|
fetch the deposit address for a currency associated with self account
|
1740
2074
|
:param str code: unified currency code
|
1741
2075
|
:param dict [params]: extra parameters specific to the exchange API endpoint
|
@@ -1743,7 +2077,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
1743
2077
|
"""
|
1744
2078
|
self.load_markets()
|
1745
2079
|
currency = self.currency(code)
|
1746
|
-
request = {
|
2080
|
+
request: dict = {
|
1747
2081
|
'currency': currency['id'],
|
1748
2082
|
}
|
1749
2083
|
version = self.options['versions']['private']['GET']['deposit-addresses']
|
@@ -1767,15 +2101,17 @@ class kucoin(Exchange, ImplicitAPI):
|
|
1767
2101
|
self.options['versions']['private']['GET']['deposit-addresses'] = version
|
1768
2102
|
chains = self.safe_list(response, 'data', [])
|
1769
2103
|
parsed = self.parse_deposit_addresses(chains, [currency['code']], False, {
|
1770
|
-
'currency': currency['
|
2104
|
+
'currency': currency['code'],
|
1771
2105
|
})
|
1772
2106
|
return self.index_by(parsed, 'network')
|
1773
2107
|
|
1774
2108
|
def fetch_order_book(self, symbol: str, limit: Int = None, params={}) -> OrderBook:
|
1775
2109
|
"""
|
1776
2110
|
fetches information on open orders with bid(buy) and ask(sell) prices, volumes and other data
|
1777
|
-
|
1778
|
-
|
2111
|
+
|
2112
|
+
https://www.kucoin.com/docs/rest/spot-trading/market-data/get-part-order-book-aggregated-
|
2113
|
+
https://www.kucoin.com/docs/rest/spot-trading/market-data/get-full-order-book-aggregated-
|
2114
|
+
|
1779
2115
|
:param str symbol: unified symbol of the market to fetch the order book for
|
1780
2116
|
:param int [limit]: the maximum amount of order book entries to return
|
1781
2117
|
:param dict [params]: extra parameters specific to the exchange API endpoint
|
@@ -1784,7 +2120,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
1784
2120
|
self.load_markets()
|
1785
2121
|
market = self.market(symbol)
|
1786
2122
|
level = self.safe_integer(params, 'level', 2)
|
1787
|
-
request = {'symbol': market['id']}
|
2123
|
+
request: dict = {'symbol': market['id']}
|
1788
2124
|
isAuthenticated = self.check_required_credentials(False)
|
1789
2125
|
response = None
|
1790
2126
|
if not isAuthenticated or limit is not None:
|
@@ -1849,49 +2185,56 @@ class kucoin(Exchange, ImplicitAPI):
|
|
1849
2185
|
def create_order(self, symbol: str, type: OrderType, side: OrderSide, amount: float, price: Num = None, params={}):
|
1850
2186
|
"""
|
1851
2187
|
Create an order on the exchange
|
1852
|
-
|
1853
|
-
|
1854
|
-
|
1855
|
-
|
1856
|
-
|
1857
|
-
|
2188
|
+
|
2189
|
+
https://docs.kucoin.com/spot#place-a-new-order
|
2190
|
+
https://docs.kucoin.com/spot#place-a-new-order-2
|
2191
|
+
https://docs.kucoin.com/spot#place-a-margin-order
|
2192
|
+
https://docs.kucoin.com/spot-hf/#place-hf-order
|
2193
|
+
https://www.kucoin.com/docs/rest/spot-trading/orders/place-order-test
|
2194
|
+
https://www.kucoin.com/docs/rest/margin-trading/orders/place-margin-order-test
|
2195
|
+
https://www.kucoin.com/docs/rest/spot-trading/spot-hf-trade-pro-account/sync-place-hf-order
|
2196
|
+
|
1858
2197
|
:param str symbol: Unified CCXT market symbol
|
1859
2198
|
:param str type: 'limit' or 'market'
|
1860
2199
|
:param str side: 'buy' or 'sell'
|
1861
2200
|
:param float amount: the amount of currency to trade
|
1862
|
-
:param float [price]:
|
2201
|
+
:param float [price]: the price at which the order is to be fulfilled, in units of the quote currency, ignored in market orders
|
1863
2202
|
:param dict [params]: extra parameters specific to the exchange API endpoint
|
1864
2203
|
:param float [params.triggerPrice]: The price at which a trigger order is triggered at
|
1865
2204
|
:param str [params.marginMode]: 'cross', # cross(cross mode) and isolated(isolated mode), set to cross by default, the isolated mode will be released soon, stay tuned
|
1866
2205
|
:param str [params.timeInForce]: GTC, GTT, IOC, or FOK, default is GTC, limit orders only
|
1867
2206
|
:param str [params.postOnly]: Post only flag, invalid when timeInForce is IOC or FOK
|
1868
|
-
|
1869
|
-
|
2207
|
+
|
2208
|
+
EXCHANGE SPECIFIC PARAMETERS
|
1870
2209
|
:param str [params.clientOid]: client order id, defaults to uuid if not passed
|
1871
2210
|
:param str [params.remark]: remark for the order, length cannot exceed 100 utf8 characters
|
1872
2211
|
:param str [params.tradeType]: 'TRADE', # TRADE, MARGIN_TRADE # not used with margin orders
|
1873
|
-
|
2212
|
+
limit orders ---------------------------------------------------
|
1874
2213
|
:param float [params.cancelAfter]: long, # cancel after n seconds, requires timeInForce to be GTT
|
1875
2214
|
:param bool [params.hidden]: False, # Order will not be displayed in the order book
|
1876
2215
|
:param bool [params.iceberg]: False, # Only a portion of the order is displayed in the order book
|
1877
2216
|
:param str [params.visibleSize]: self.amount_to_precision(symbol, visibleSize), # The maximum visible size of an iceberg order
|
1878
|
-
|
2217
|
+
market orders --------------------------------------------------
|
1879
2218
|
:param str [params.funds]: # Amount of quote currency to use
|
1880
|
-
|
1881
|
-
:param str [params.stop]: Either loss or entry, the default is loss. Requires
|
1882
|
-
|
2219
|
+
stop orders ----------------------------------------------------
|
2220
|
+
:param str [params.stop]: Either loss or entry, the default is loss. Requires triggerPrice to be defined
|
2221
|
+
margin orders --------------------------------------------------
|
1883
2222
|
:param float [params.leverage]: Leverage size of the order
|
1884
2223
|
:param str [params.stp]: '', # self trade prevention, CN, CO, CB or DC
|
1885
2224
|
:param bool [params.autoBorrow]: False, # The system will first borrow you funds at the optimal interest rate and then place an order for you
|
1886
2225
|
:param bool [params.hf]: False, # True for hf order
|
1887
2226
|
:param bool [params.test]: set to True to test an order, no order will be created but the request will be validated
|
2227
|
+
:param bool [params.sync]: set to True to use the hf sync call
|
1888
2228
|
:returns dict: an `order structure <https://docs.ccxt.com/#/?id=order-structure>`
|
1889
2229
|
"""
|
1890
2230
|
self.load_markets()
|
1891
2231
|
market = self.market(symbol)
|
1892
2232
|
testOrder = self.safe_bool(params, 'test', False)
|
1893
2233
|
params = self.omit(params, 'test')
|
1894
|
-
|
2234
|
+
hf = None
|
2235
|
+
hf, params = self.handle_hf_and_params(params)
|
2236
|
+
useSync = False
|
2237
|
+
useSync, params = self.handle_option_and_params(params, 'createOrder', 'sync', False)
|
1895
2238
|
triggerPrice, stopLossPrice, takeProfitPrice = self.handle_trigger_prices(params)
|
1896
2239
|
tradeType = self.safe_string(params, 'tradeType') # keep it for backward compatibility
|
1897
2240
|
isTriggerOrder = (triggerPrice or stopLossPrice or takeProfitPrice)
|
@@ -1904,14 +2247,18 @@ class kucoin(Exchange, ImplicitAPI):
|
|
1904
2247
|
if testOrder:
|
1905
2248
|
if isMarginOrder:
|
1906
2249
|
response = self.privatePostMarginOrderTest(orderRequest)
|
2250
|
+
elif hf:
|
2251
|
+
response = self.privatePostHfOrdersTest(orderRequest)
|
1907
2252
|
else:
|
1908
2253
|
response = self.privatePostOrdersTest(orderRequest)
|
1909
|
-
elif isHf:
|
1910
|
-
response = self.privatePostHfOrders(orderRequest)
|
1911
2254
|
elif isTriggerOrder:
|
1912
2255
|
response = self.privatePostStopOrder(orderRequest)
|
1913
2256
|
elif isMarginOrder:
|
1914
2257
|
response = self.privatePostMarginOrder(orderRequest)
|
2258
|
+
elif useSync:
|
2259
|
+
response = self.privatePostHfOrdersSync(orderRequest)
|
2260
|
+
elif hf:
|
2261
|
+
response = self.privatePostHfOrders(orderRequest)
|
1915
2262
|
else:
|
1916
2263
|
response = self.privatePostOrders(orderRequest)
|
1917
2264
|
#
|
@@ -1928,7 +2275,9 @@ class kucoin(Exchange, ImplicitAPI):
|
|
1928
2275
|
def create_market_order_with_cost(self, symbol: str, side: OrderSide, cost: float, params={}):
|
1929
2276
|
"""
|
1930
2277
|
create a market order by providing the symbol, side and cost
|
1931
|
-
|
2278
|
+
|
2279
|
+
https://www.kucoin.com/docs/rest/spot-trading/orders/place-order
|
2280
|
+
|
1932
2281
|
:param str symbol: unified symbol of the market to create an order in
|
1933
2282
|
:param str side: 'buy' or 'sell'
|
1934
2283
|
:param float cost: how much you want to trade in units of the quote currency
|
@@ -1936,13 +2285,17 @@ class kucoin(Exchange, ImplicitAPI):
|
|
1936
2285
|
:returns dict: an `order structure <https://docs.ccxt.com/#/?id=order-structure>`
|
1937
2286
|
"""
|
1938
2287
|
self.load_markets()
|
1939
|
-
|
1940
|
-
|
2288
|
+
req = {
|
2289
|
+
'cost': cost,
|
2290
|
+
}
|
2291
|
+
return self.create_order(symbol, 'market', side, 0, None, self.extend(req, params))
|
1941
2292
|
|
1942
2293
|
def create_market_buy_order_with_cost(self, symbol: str, cost: float, params={}):
|
1943
2294
|
"""
|
1944
2295
|
create a market buy order by providing the symbol and cost
|
1945
|
-
|
2296
|
+
|
2297
|
+
https://www.kucoin.com/docs/rest/spot-trading/orders/place-order
|
2298
|
+
|
1946
2299
|
:param str symbol: unified symbol of the market to create an order in
|
1947
2300
|
:param float cost: how much you want to trade in units of the quote currency
|
1948
2301
|
:param dict [params]: extra parameters specific to the exchange API endpoint
|
@@ -1954,7 +2307,9 @@ class kucoin(Exchange, ImplicitAPI):
|
|
1954
2307
|
def create_market_sell_order_with_cost(self, symbol: str, cost: float, params={}):
|
1955
2308
|
"""
|
1956
2309
|
create a market sell order by providing the symbol and cost
|
1957
|
-
|
2310
|
+
|
2311
|
+
https://www.kucoin.com/docs/rest/spot-trading/orders/place-order
|
2312
|
+
|
1958
2313
|
:param str symbol: unified symbol of the market to create an order in
|
1959
2314
|
:param float cost: how much you want to trade in units of the quote currency
|
1960
2315
|
:param dict [params]: extra parameters specific to the exchange API endpoint
|
@@ -1966,11 +2321,15 @@ class kucoin(Exchange, ImplicitAPI):
|
|
1966
2321
|
def create_orders(self, orders: List[OrderRequest], params={}):
|
1967
2322
|
"""
|
1968
2323
|
create a list of trade orders
|
1969
|
-
|
1970
|
-
|
2324
|
+
|
2325
|
+
https://www.kucoin.com/docs/rest/spot-trading/orders/place-multiple-orders
|
2326
|
+
https://www.kucoin.com/docs/rest/spot-trading/spot-hf-trade-pro-account/place-multiple-hf-orders
|
2327
|
+
https://www.kucoin.com/docs/rest/spot-trading/spot-hf-trade-pro-account/sync-place-multiple-hf-orders
|
2328
|
+
|
1971
2329
|
:param Array orders: list of orders to create, each object should contain the parameters required by createOrder, namely symbol, type, side, amount, price and params
|
1972
2330
|
:param dict [params]: extra parameters specific to the exchange API endpoint
|
1973
2331
|
:param bool [params.hf]: False, # True for hf orders
|
2332
|
+
:param bool [params.sync]: False, # True to use the hf sync call
|
1974
2333
|
:returns dict: an `order structure <https://docs.ccxt.com/#/?id=order-structure>`
|
1975
2334
|
"""
|
1976
2335
|
self.load_markets()
|
@@ -1994,14 +2353,18 @@ class kucoin(Exchange, ImplicitAPI):
|
|
1994
2353
|
orderRequest = self.create_order_request(marketId, type, side, amount, price, orderParams)
|
1995
2354
|
ordersRequests.append(orderRequest)
|
1996
2355
|
market = self.market(symbol)
|
1997
|
-
request = {
|
2356
|
+
request: dict = {
|
1998
2357
|
'symbol': market['id'],
|
1999
2358
|
'orderList': ordersRequests,
|
2000
2359
|
}
|
2001
|
-
hf =
|
2002
|
-
params = self.
|
2360
|
+
hf = None
|
2361
|
+
hf, params = self.handle_hf_and_params(params)
|
2362
|
+
useSync = False
|
2363
|
+
useSync, params = self.handle_option_and_params(params, 'createOrders', 'sync', False)
|
2003
2364
|
response = None
|
2004
|
-
if
|
2365
|
+
if useSync:
|
2366
|
+
response = self.privatePostHfOrdersMultiSync(self.extend(request, params))
|
2367
|
+
elif hf:
|
2005
2368
|
response = self.privatePostHfOrdersMulti(self.extend(request, params))
|
2006
2369
|
else:
|
2007
2370
|
response = self.privatePostOrdersMulti(self.extend(request, params))
|
@@ -2039,12 +2402,19 @@ class kucoin(Exchange, ImplicitAPI):
|
|
2039
2402
|
data = self.safe_list(data, 'data', [])
|
2040
2403
|
return self.parse_orders(data)
|
2041
2404
|
|
2405
|
+
def market_order_amount_to_precision(self, symbol: str, amount):
|
2406
|
+
market = self.market(symbol)
|
2407
|
+
result = self.decimal_to_precision(amount, TRUNCATE, market['info']['quoteIncrement'], self.precisionMode, self.paddingMode)
|
2408
|
+
if result == '0':
|
2409
|
+
raise InvalidOrder(self.id + ' amount of ' + market['symbol'] + ' must be greater than minimum amount precision of ' + self.number_to_string(market['precision']['amount']))
|
2410
|
+
return result
|
2411
|
+
|
2042
2412
|
def create_order_request(self, symbol: str, type: OrderType, side: OrderSide, amount: float, price: Num = None, params={}):
|
2043
2413
|
market = self.market(symbol)
|
2044
2414
|
# required param, cannot be used twice
|
2045
2415
|
clientOrderId = self.safe_string_2(params, 'clientOid', 'clientOrderId', self.uuid())
|
2046
2416
|
params = self.omit(params, ['clientOid', 'clientOrderId'])
|
2047
|
-
request = {
|
2417
|
+
request: dict = {
|
2048
2418
|
'clientOid': clientOrderId,
|
2049
2419
|
'side': side,
|
2050
2420
|
'symbol': market['id'],
|
@@ -2059,7 +2429,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
2059
2429
|
if quoteAmount is not None:
|
2060
2430
|
params = self.omit(params, ['cost', 'funds'])
|
2061
2431
|
# kucoin uses base precision even for quote values
|
2062
|
-
costString = self.
|
2432
|
+
costString = self.market_order_amount_to_precision(symbol, quoteAmount)
|
2063
2433
|
request['funds'] = costString
|
2064
2434
|
else:
|
2065
2435
|
amountString = self.amount_to_precision(symbol, amount)
|
@@ -2099,20 +2469,22 @@ class kucoin(Exchange, ImplicitAPI):
|
|
2099
2469
|
def edit_order(self, id: str, symbol: str, type: OrderType, side: OrderSide, amount: Num = None, price: Num = None, params={}):
|
2100
2470
|
"""
|
2101
2471
|
edit an order, kucoin currently only supports the modification of HF orders
|
2102
|
-
|
2472
|
+
|
2473
|
+
https://docs.kucoin.com/spot-hf/#modify-order
|
2474
|
+
|
2103
2475
|
:param str id: order id
|
2104
2476
|
:param str symbol: unified symbol of the market to create an order in
|
2105
2477
|
:param str type: not used
|
2106
2478
|
:param str side: not used
|
2107
2479
|
:param float amount: how much of the currency you want to trade in units of the base currency
|
2108
|
-
:param float [price]: the price at which the order is to be
|
2480
|
+
:param float [price]: the price at which the order is to be fulfilled, in units of the quote currency, ignored in market orders
|
2109
2481
|
:param dict [params]: extra parameters specific to the exchange API endpoint
|
2110
2482
|
:param str [params.clientOrderId]: client order id, defaults to id if not passed
|
2111
2483
|
:returns dict: an `order structure <https://docs.ccxt.com/#/?id=order-structure>`
|
2112
2484
|
"""
|
2113
2485
|
self.load_markets()
|
2114
2486
|
market = self.market(symbol)
|
2115
|
-
request = {
|
2487
|
+
request: dict = {
|
2116
2488
|
'symbol': market['id'],
|
2117
2489
|
}
|
2118
2490
|
clientOrderId = self.safe_string_2(params, 'clientOid', 'clientOrderId')
|
@@ -2139,78 +2511,149 @@ class kucoin(Exchange, ImplicitAPI):
|
|
2139
2511
|
def cancel_order(self, id: str, symbol: Str = None, params={}):
|
2140
2512
|
"""
|
2141
2513
|
cancels an open order
|
2142
|
-
|
2143
|
-
|
2144
|
-
|
2145
|
-
|
2146
|
-
|
2147
|
-
|
2514
|
+
|
2515
|
+
https://docs.kucoin.com/spot#cancel-an-order
|
2516
|
+
https://docs.kucoin.com/spot#cancel-an-order-2
|
2517
|
+
https://docs.kucoin.com/spot#cancel-single-order-by-clientoid
|
2518
|
+
https://docs.kucoin.com/spot#cancel-single-order-by-clientoid-2
|
2519
|
+
https://docs.kucoin.com/spot-hf/#cancel-orders-by-orderid
|
2520
|
+
https://docs.kucoin.com/spot-hf/#cancel-order-by-clientoid
|
2521
|
+
https://www.kucoin.com/docs/rest/spot-trading/spot-hf-trade-pro-account/sync-cancel-hf-order-by-orderid
|
2522
|
+
https://www.kucoin.com/docs/rest/spot-trading/spot-hf-trade-pro-account/sync-cancel-hf-order-by-clientoid
|
2523
|
+
|
2148
2524
|
:param str id: order id
|
2149
2525
|
:param str symbol: unified symbol of the market the order was made in
|
2150
2526
|
:param dict [params]: extra parameters specific to the exchange API endpoint
|
2151
|
-
:param bool [params.
|
2527
|
+
:param bool [params.trigger]: True if cancelling a stop order
|
2152
2528
|
:param bool [params.hf]: False, # True for hf order
|
2529
|
+
:param bool [params.sync]: False, # True to use the hf sync call
|
2153
2530
|
:returns: Response from the exchange
|
2154
2531
|
"""
|
2155
2532
|
self.load_markets()
|
2156
|
-
request = {}
|
2533
|
+
request: dict = {}
|
2157
2534
|
clientOrderId = self.safe_string_2(params, 'clientOid', 'clientOrderId')
|
2158
|
-
|
2159
|
-
hf =
|
2160
|
-
|
2535
|
+
trigger = self.safe_bool_2(params, 'stop', 'trigger', False)
|
2536
|
+
hf = None
|
2537
|
+
hf, params = self.handle_hf_and_params(params)
|
2538
|
+
useSync = False
|
2539
|
+
useSync, params = self.handle_option_and_params(params, 'cancelOrder', 'sync', False)
|
2540
|
+
if hf or useSync:
|
2161
2541
|
if symbol is None:
|
2162
2542
|
raise ArgumentsRequired(self.id + ' cancelOrder() requires a symbol parameter for hf orders')
|
2163
2543
|
market = self.market(symbol)
|
2164
2544
|
request['symbol'] = market['id']
|
2165
2545
|
response = None
|
2166
|
-
params = self.omit(params, ['clientOid', 'clientOrderId', 'stop', '
|
2546
|
+
params = self.omit(params, ['clientOid', 'clientOrderId', 'stop', 'trigger'])
|
2167
2547
|
if clientOrderId is not None:
|
2168
2548
|
request['clientOid'] = clientOrderId
|
2169
|
-
if
|
2549
|
+
if trigger:
|
2170
2550
|
response = self.privateDeleteStopOrderCancelOrderByClientOid(self.extend(request, params))
|
2551
|
+
#
|
2552
|
+
# {
|
2553
|
+
# code: '200000',
|
2554
|
+
# data: {
|
2555
|
+
# cancelledOrderId: 'vs8lgpiuao41iaft003khbbk',
|
2556
|
+
# clientOid: '123456'
|
2557
|
+
# }
|
2558
|
+
# }
|
2559
|
+
#
|
2560
|
+
elif useSync:
|
2561
|
+
response = self.privateDeleteHfOrdersSyncClientOrderClientOid(self.extend(request, params))
|
2171
2562
|
elif hf:
|
2172
2563
|
response = self.privateDeleteHfOrdersClientOrderClientOid(self.extend(request, params))
|
2564
|
+
#
|
2565
|
+
# {
|
2566
|
+
# "code": "200000",
|
2567
|
+
# "data": {
|
2568
|
+
# "clientOid": "6d539dc614db3"
|
2569
|
+
# }
|
2570
|
+
# }
|
2571
|
+
#
|
2173
2572
|
else:
|
2174
2573
|
response = self.privateDeleteOrderClientOrderClientOid(self.extend(request, params))
|
2574
|
+
#
|
2575
|
+
# {
|
2576
|
+
# code: '200000',
|
2577
|
+
# data: {
|
2578
|
+
# cancelledOrderId: '665e580f6660500007aba341',
|
2579
|
+
# clientOid: '1234567',
|
2580
|
+
# cancelledOcoOrderIds: null
|
2581
|
+
# }
|
2582
|
+
# }
|
2583
|
+
#
|
2584
|
+
response = self.safe_dict(response, 'data')
|
2585
|
+
return self.parse_order(response)
|
2175
2586
|
else:
|
2176
2587
|
request['orderId'] = id
|
2177
|
-
if
|
2588
|
+
if trigger:
|
2178
2589
|
response = self.privateDeleteStopOrderOrderId(self.extend(request, params))
|
2590
|
+
#
|
2591
|
+
# {
|
2592
|
+
# code: '200000',
|
2593
|
+
# data: {cancelledOrderIds: ['vs8lgpiuaco91qk8003vebu9']}
|
2594
|
+
# }
|
2595
|
+
#
|
2596
|
+
elif useSync:
|
2597
|
+
response = self.privateDeleteHfOrdersSyncOrderId(self.extend(request, params))
|
2179
2598
|
elif hf:
|
2180
2599
|
response = self.privateDeleteHfOrdersOrderId(self.extend(request, params))
|
2600
|
+
#
|
2601
|
+
# {
|
2602
|
+
# "code": "200000",
|
2603
|
+
# "data": {
|
2604
|
+
# "orderId": "630625dbd9180300014c8d52"
|
2605
|
+
# }
|
2606
|
+
# }
|
2607
|
+
#
|
2608
|
+
response = self.safe_dict(response, 'data')
|
2609
|
+
return self.parse_order(response)
|
2181
2610
|
else:
|
2182
2611
|
response = self.privateDeleteOrdersOrderId(self.extend(request, params))
|
2183
|
-
|
2612
|
+
#
|
2613
|
+
# {
|
2614
|
+
# code: '200000',
|
2615
|
+
# data: {cancelledOrderIds: ['665e4fbe28051a0007245c41']}
|
2616
|
+
# }
|
2617
|
+
#
|
2618
|
+
data = self.safe_dict(response, 'data')
|
2619
|
+
orderIds = self.safe_list(data, 'cancelledOrderIds', [])
|
2620
|
+
orderId = self.safe_string(orderIds, 0)
|
2621
|
+
return self.safe_order({
|
2622
|
+
'info': data,
|
2623
|
+
'id': orderId,
|
2624
|
+
})
|
2184
2625
|
|
2185
2626
|
def cancel_all_orders(self, symbol: Str = None, params={}):
|
2186
2627
|
"""
|
2187
2628
|
cancel all open orders
|
2188
|
-
|
2189
|
-
|
2190
|
-
|
2629
|
+
|
2630
|
+
https://docs.kucoin.com/spot#cancel-all-orders
|
2631
|
+
https://docs.kucoin.com/spot#cancel-orders
|
2632
|
+
https://docs.kucoin.com/spot-hf/#cancel-all-hf-orders-by-symbol
|
2633
|
+
|
2191
2634
|
:param str symbol: unified market symbol, only orders in the market of self symbol are cancelled when symbol is not None
|
2192
2635
|
:param dict [params]: extra parameters specific to the exchange API endpoint
|
2193
|
-
:param bool [params.
|
2636
|
+
:param bool [params.trigger]: *invalid for isolated margin* True if cancelling all stop orders
|
2194
2637
|
:param str [params.marginMode]: 'cross' or 'isolated'
|
2195
2638
|
:param str [params.orderIds]: *stop orders only* Comma seperated order IDs
|
2196
|
-
:param bool [params.stop]: True if cancelling a stop order
|
2197
2639
|
:param bool [params.hf]: False, # True for hf order
|
2198
2640
|
:returns: Response from the exchange
|
2199
2641
|
"""
|
2200
2642
|
self.load_markets()
|
2201
|
-
request = {}
|
2202
|
-
|
2203
|
-
hf =
|
2204
|
-
params = self.
|
2643
|
+
request: dict = {}
|
2644
|
+
trigger = self.safe_bool(params, 'stop', False)
|
2645
|
+
hf = None
|
2646
|
+
hf, params = self.handle_hf_and_params(params)
|
2647
|
+
params = self.omit(params, 'stop')
|
2205
2648
|
marginMode, query = self.handle_margin_mode_and_params('cancelAllOrders', params)
|
2206
2649
|
if symbol is not None:
|
2207
2650
|
request['symbol'] = self.market_id(symbol)
|
2208
2651
|
if marginMode is not None:
|
2209
2652
|
request['tradeType'] = self.options['marginModes'][marginMode]
|
2210
|
-
if marginMode == 'isolated' and
|
2653
|
+
if marginMode == 'isolated' and trigger:
|
2211
2654
|
raise BadRequest(self.id + ' cancelAllOrders does not support isolated margin for stop orders')
|
2212
2655
|
response = None
|
2213
|
-
if
|
2656
|
+
if trigger:
|
2214
2657
|
response = self.privateDeleteStopOrderCancel(self.extend(request, query))
|
2215
2658
|
elif hf:
|
2216
2659
|
if symbol is None:
|
@@ -2224,38 +2667,42 @@ class kucoin(Exchange, ImplicitAPI):
|
|
2224
2667
|
def fetch_orders_by_status(self, status, symbol: Str = None, since: Int = None, limit: Int = None, params={}):
|
2225
2668
|
"""
|
2226
2669
|
fetch a list of orders
|
2227
|
-
|
2228
|
-
|
2229
|
-
|
2230
|
-
|
2670
|
+
|
2671
|
+
https://docs.kucoin.com/spot#list-orders
|
2672
|
+
https://docs.kucoin.com/spot#list-stop-orders
|
2673
|
+
https://docs.kucoin.com/spot-hf/#obtain-list-of-active-hf-orders
|
2674
|
+
https://docs.kucoin.com/spot-hf/#obtain-list-of-filled-hf-orders
|
2675
|
+
|
2231
2676
|
:param str status: *not used for stop orders* 'open' or 'closed'
|
2232
2677
|
:param str symbol: unified market symbol
|
2233
2678
|
:param int [since]: timestamp in ms of the earliest order
|
2234
2679
|
:param int [limit]: max number of orders to return
|
2235
2680
|
:param dict [params]: exchange specific params
|
2236
2681
|
:param int [params.until]: end time in ms
|
2237
|
-
:param bool [params.stop]: True if fetching stop orders
|
2238
2682
|
:param str [params.side]: buy or sell
|
2239
2683
|
:param str [params.type]: limit, market, limit_stop or market_stop
|
2240
2684
|
:param str [params.tradeType]: TRADE for spot trading, MARGIN_TRADE for Margin Trading
|
2241
|
-
:param int [params.currentPage]: *
|
2242
|
-
:param str [params.orderIds]: *
|
2243
|
-
:param bool [params.
|
2685
|
+
:param int [params.currentPage]: *trigger orders only* current page
|
2686
|
+
:param str [params.orderIds]: *trigger orders only* comma seperated order ID list
|
2687
|
+
:param bool [params.trigger]: True if fetching a trigger order
|
2244
2688
|
:param bool [params.hf]: False, # True for hf order
|
2245
2689
|
:returns: An `array of order structures <https://docs.ccxt.com/#/?id=order-structure>`
|
2246
2690
|
"""
|
2247
2691
|
self.load_markets()
|
2248
2692
|
lowercaseStatus = status.lower()
|
2249
|
-
until = self.
|
2250
|
-
|
2251
|
-
hf =
|
2252
|
-
params = self.
|
2693
|
+
until = self.safe_integer(params, 'until')
|
2694
|
+
trigger = self.safe_bool_2(params, 'stop', 'trigger', False)
|
2695
|
+
hf = None
|
2696
|
+
hf, params = self.handle_hf_and_params(params)
|
2697
|
+
if hf and (symbol is None):
|
2698
|
+
raise ArgumentsRequired(self.id + ' fetchOrdersByStatus() requires a symbol parameter for hf orders')
|
2699
|
+
params = self.omit(params, ['stop', 'trigger', 'till', 'until'])
|
2253
2700
|
marginMode, query = self.handle_margin_mode_and_params('fetchOrdersByStatus', params)
|
2254
2701
|
if lowercaseStatus == 'open':
|
2255
2702
|
lowercaseStatus = 'active'
|
2256
2703
|
elif lowercaseStatus == 'closed':
|
2257
2704
|
lowercaseStatus = 'done'
|
2258
|
-
request = {
|
2705
|
+
request: dict = {
|
2259
2706
|
'status': lowercaseStatus,
|
2260
2707
|
}
|
2261
2708
|
market = None
|
@@ -2270,7 +2717,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
2270
2717
|
request['endAt'] = until
|
2271
2718
|
request['tradeType'] = self.safe_string(self.options['marginModes'], marginMode, 'TRADE')
|
2272
2719
|
response = None
|
2273
|
-
if
|
2720
|
+
if trigger:
|
2274
2721
|
response = self.privateGetStopOrder(self.extend(request, query))
|
2275
2722
|
elif hf:
|
2276
2723
|
if lowercaseStatus == 'active':
|
@@ -2322,26 +2769,31 @@ class kucoin(Exchange, ImplicitAPI):
|
|
2322
2769
|
# ]
|
2323
2770
|
# }
|
2324
2771
|
# }
|
2772
|
+
listData = self.safe_list(response, 'data')
|
2773
|
+
if listData is not None:
|
2774
|
+
return self.parse_orders(listData, market, since, limit)
|
2325
2775
|
responseData = self.safe_dict(response, 'data', {})
|
2326
|
-
orders = self.
|
2776
|
+
orders = self.safe_list(responseData, 'items', [])
|
2327
2777
|
return self.parse_orders(orders, market, since, limit)
|
2328
2778
|
|
2329
2779
|
def fetch_closed_orders(self, symbol: Str = None, since: Int = None, limit: Int = None, params={}) -> List[Order]:
|
2330
2780
|
"""
|
2331
2781
|
fetches information on multiple closed orders made by the user
|
2332
|
-
|
2333
|
-
|
2334
|
-
|
2335
|
-
|
2782
|
+
|
2783
|
+
https://docs.kucoin.com/spot#list-orders
|
2784
|
+
https://docs.kucoin.com/spot#list-stop-orders
|
2785
|
+
https://docs.kucoin.com/spot-hf/#obtain-list-of-active-hf-orders
|
2786
|
+
https://docs.kucoin.com/spot-hf/#obtain-list-of-filled-hf-orders
|
2787
|
+
|
2336
2788
|
:param str symbol: unified market symbol of the market orders were made in
|
2337
2789
|
:param int [since]: the earliest time in ms to fetch orders for
|
2338
2790
|
:param int [limit]: the maximum number of order structures to retrieve
|
2339
2791
|
:param dict [params]: extra parameters specific to the exchange API endpoint
|
2340
|
-
:param int [params.
|
2792
|
+
:param int [params.until]: end time in ms
|
2341
2793
|
:param str [params.side]: buy or sell
|
2342
2794
|
:param str [params.type]: limit, market, limit_stop or market_stop
|
2343
2795
|
:param str [params.tradeType]: TRADE for spot trading, MARGIN_TRADE for Margin Trading
|
2344
|
-
:param bool [params.
|
2796
|
+
:param bool [params.trigger]: True if fetching a trigger order
|
2345
2797
|
:param bool [params.hf]: False, # True for hf order
|
2346
2798
|
:param boolean [params.paginate]: default False, when True will automatically paginate by calling self endpoint multiple times. See in the docs all the [availble parameters](https://github.com/ccxt/ccxt/wiki/Manual#pagination-params)
|
2347
2799
|
:returns Order[]: a list of `order structures <https://docs.ccxt.com/#/?id=order-structure>`
|
@@ -2356,22 +2808,23 @@ class kucoin(Exchange, ImplicitAPI):
|
|
2356
2808
|
def fetch_open_orders(self, symbol: Str = None, since: Int = None, limit: Int = None, params={}) -> List[Order]:
|
2357
2809
|
"""
|
2358
2810
|
fetch all unfilled currently open orders
|
2359
|
-
|
2360
|
-
|
2361
|
-
|
2362
|
-
|
2811
|
+
|
2812
|
+
https://docs.kucoin.com/spot#list-orders
|
2813
|
+
https://docs.kucoin.com/spot#list-stop-orders
|
2814
|
+
https://docs.kucoin.com/spot-hf/#obtain-list-of-active-hf-orders
|
2815
|
+
https://docs.kucoin.com/spot-hf/#obtain-list-of-filled-hf-orders
|
2816
|
+
|
2363
2817
|
:param str symbol: unified market symbol
|
2364
2818
|
:param int [since]: the earliest time in ms to fetch open orders for
|
2365
2819
|
:param int [limit]: the maximum number of open orders structures to retrieve
|
2366
2820
|
:param dict [params]: extra parameters specific to the exchange API endpoint
|
2367
|
-
:param int [params.
|
2368
|
-
:param bool [params.
|
2821
|
+
:param int [params.until]: end time in ms
|
2822
|
+
:param bool [params.trigger]: True if fetching trigger orders
|
2369
2823
|
:param str [params.side]: buy or sell
|
2370
2824
|
:param str [params.type]: limit, market, limit_stop or market_stop
|
2371
2825
|
:param str [params.tradeType]: TRADE for spot trading, MARGIN_TRADE for Margin Trading
|
2372
|
-
:param int [params.currentPage]: *
|
2373
|
-
:param str [params.orderIds]: *
|
2374
|
-
:param bool [params.stop]: True if fetching a stop order
|
2826
|
+
:param int [params.currentPage]: *trigger orders only* current page
|
2827
|
+
:param str [params.orderIds]: *trigger orders only* comma seperated order ID list
|
2375
2828
|
:param bool [params.hf]: False, # True for hf order
|
2376
2829
|
:param boolean [params.paginate]: default False, when True will automatically paginate by calling self endpoint multiple times. See in the docs all the [availble parameters](https://github.com/ccxt/ccxt/wiki/Manual#pagination-params)
|
2377
2830
|
:returns Order[]: a list of `order structures <https://docs.ccxt.com/#/?id=order-structure>`
|
@@ -2386,25 +2839,28 @@ class kucoin(Exchange, ImplicitAPI):
|
|
2386
2839
|
def fetch_order(self, id: str, symbol: Str = None, params={}):
|
2387
2840
|
"""
|
2388
2841
|
fetch an order
|
2389
|
-
|
2390
|
-
|
2391
|
-
|
2392
|
-
|
2393
|
-
|
2394
|
-
|
2842
|
+
|
2843
|
+
https://docs.kucoin.com/spot#get-an-order
|
2844
|
+
https://docs.kucoin.com/spot#get-single-active-order-by-clientoid
|
2845
|
+
https://docs.kucoin.com/spot#get-single-order-info
|
2846
|
+
https://docs.kucoin.com/spot#get-single-order-by-clientoid
|
2847
|
+
https://docs.kucoin.com/spot-hf/#details-of-a-single-hf-order
|
2848
|
+
https://docs.kucoin.com/spot-hf/#obtain-details-of-a-single-hf-order-using-clientoid
|
2849
|
+
|
2395
2850
|
:param str id: Order id
|
2396
|
-
:param str symbol: not sent to exchange except for
|
2851
|
+
:param str symbol: not sent to exchange except for trigger orders with clientOid, but used internally by CCXT to filter
|
2397
2852
|
:param dict [params]: exchange specific parameters
|
2398
|
-
:param bool [params.
|
2853
|
+
:param bool [params.trigger]: True if fetching a trigger order
|
2399
2854
|
:param bool [params.hf]: False, # True for hf order
|
2400
2855
|
:param bool [params.clientOid]: unique order id created by users to identify their orders
|
2401
2856
|
:returns: An `order structure <https://docs.ccxt.com/#/?id=order-structure>`
|
2402
2857
|
"""
|
2403
2858
|
self.load_markets()
|
2404
|
-
request = {}
|
2859
|
+
request: dict = {}
|
2405
2860
|
clientOrderId = self.safe_string_2(params, 'clientOid', 'clientOrderId')
|
2406
|
-
|
2407
|
-
hf =
|
2861
|
+
trigger = self.safe_bool_2(params, 'stop', 'trigger', False)
|
2862
|
+
hf = None
|
2863
|
+
hf, params = self.handle_hf_and_params(params)
|
2408
2864
|
market = None
|
2409
2865
|
if symbol is not None:
|
2410
2866
|
market = self.market(symbol)
|
@@ -2412,11 +2868,11 @@ class kucoin(Exchange, ImplicitAPI):
|
|
2412
2868
|
if symbol is None:
|
2413
2869
|
raise ArgumentsRequired(self.id + ' fetchOrder() requires a symbol parameter for hf orders')
|
2414
2870
|
request['symbol'] = market['id']
|
2415
|
-
params = self.omit(params, ['stop', '
|
2871
|
+
params = self.omit(params, ['stop', 'clientOid', 'clientOrderId', 'trigger'])
|
2416
2872
|
response = None
|
2417
2873
|
if clientOrderId is not None:
|
2418
2874
|
request['clientOid'] = clientOrderId
|
2419
|
-
if
|
2875
|
+
if trigger:
|
2420
2876
|
if symbol is not None:
|
2421
2877
|
request['symbol'] = market['id']
|
2422
2878
|
response = self.privateGetStopOrderQueryOrderByClientOid(self.extend(request, params))
|
@@ -2431,7 +2887,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
2431
2887
|
if id is None:
|
2432
2888
|
raise InvalidOrder(self.id + ' fetchOrder() requires an order id')
|
2433
2889
|
request['orderId'] = id
|
2434
|
-
if
|
2890
|
+
if trigger:
|
2435
2891
|
response = self.privateGetStopOrderOrderId(self.extend(request, params))
|
2436
2892
|
elif hf:
|
2437
2893
|
response = self.privateGetHfOrdersOrderId(self.extend(request, params))
|
@@ -2442,7 +2898,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
2442
2898
|
responseData = self.safe_value(responseData, 0)
|
2443
2899
|
return self.parse_order(responseData, market)
|
2444
2900
|
|
2445
|
-
def parse_order(self, order, market: Market = None) -> Order:
|
2901
|
+
def parse_order(self, order: dict, market: Market = None) -> Order:
|
2446
2902
|
#
|
2447
2903
|
# createOrder
|
2448
2904
|
#
|
@@ -2569,7 +3025,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
2569
3025
|
feeCurrencyId = self.safe_string(order, 'feeCurrency')
|
2570
3026
|
cancelExist = self.safe_bool(order, 'cancelExist', False)
|
2571
3027
|
responseStop = self.safe_string(order, 'stop')
|
2572
|
-
|
3028
|
+
trigger = responseStop is not None
|
2573
3029
|
stopTriggered = self.safe_bool(order, 'stopTriggered', False)
|
2574
3030
|
isActive = self.safe_bool_2(order, 'isActive', 'active')
|
2575
3031
|
responseStatus = self.safe_string(order, 'status')
|
@@ -2579,7 +3035,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
2579
3035
|
status = 'open'
|
2580
3036
|
else:
|
2581
3037
|
status = 'closed'
|
2582
|
-
if
|
3038
|
+
if trigger:
|
2583
3039
|
if responseStatus == 'NEW':
|
2584
3040
|
status = 'open'
|
2585
3041
|
elif not isActive and not stopTriggered:
|
@@ -2588,10 +3044,9 @@ class kucoin(Exchange, ImplicitAPI):
|
|
2588
3044
|
status = 'canceled'
|
2589
3045
|
if responseStatus == 'fail':
|
2590
3046
|
status = 'rejected'
|
2591
|
-
stopPrice = self.safe_number(order, 'stopPrice')
|
2592
3047
|
return self.safe_order({
|
2593
3048
|
'info': order,
|
2594
|
-
'id': self.safe_string_n(order, ['id', 'orderId', 'newOrderId']),
|
3049
|
+
'id': self.safe_string_n(order, ['id', 'orderId', 'newOrderId', 'cancelledOrderId']),
|
2595
3050
|
'clientOrderId': self.safe_string(order, 'clientOid'),
|
2596
3051
|
'symbol': self.safe_symbol(marketId, market, '-'),
|
2597
3052
|
'type': self.safe_string(order, 'type'),
|
@@ -2600,8 +3055,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
2600
3055
|
'side': self.safe_string(order, 'side'),
|
2601
3056
|
'amount': self.safe_string(order, 'size'),
|
2602
3057
|
'price': self.safe_string(order, 'price'), # price is zero for market order, omitZero is called in safeOrder2
|
2603
|
-
'
|
2604
|
-
'triggerPrice': stopPrice,
|
3058
|
+
'triggerPrice': self.safe_number(order, 'stopPrice'),
|
2605
3059
|
'cost': self.safe_string(order, 'dealFunds'),
|
2606
3060
|
'filled': self.safe_string(order, 'dealSize'),
|
2607
3061
|
'remaining': None,
|
@@ -2613,15 +3067,17 @@ class kucoin(Exchange, ImplicitAPI):
|
|
2613
3067
|
},
|
2614
3068
|
'status': status,
|
2615
3069
|
'lastTradeTimestamp': None,
|
2616
|
-
'average':
|
3070
|
+
'average': self.safe_string(order, 'avgDealPrice'),
|
2617
3071
|
'trades': None,
|
2618
3072
|
}, market)
|
2619
3073
|
|
2620
3074
|
def fetch_order_trades(self, id: str, symbol: Str = None, since: Int = None, limit: Int = None, params={}):
|
2621
3075
|
"""
|
2622
3076
|
fetch all the trades made from a single order
|
2623
|
-
|
2624
|
-
|
3077
|
+
|
3078
|
+
https://docs.kucoin.com/#list-fills
|
3079
|
+
https://docs.kucoin.com/spot-hf/#transaction-details
|
3080
|
+
|
2625
3081
|
:param str id: order id
|
2626
3082
|
:param str symbol: unified market symbol
|
2627
3083
|
:param int [since]: the earliest time in ms to fetch trades for
|
@@ -2629,15 +3085,17 @@ class kucoin(Exchange, ImplicitAPI):
|
|
2629
3085
|
:param dict [params]: extra parameters specific to the exchange API endpoint
|
2630
3086
|
:returns dict[]: a list of `trade structures <https://docs.ccxt.com/#/?id=trade-structure>`
|
2631
3087
|
"""
|
2632
|
-
request = {
|
3088
|
+
request: dict = {
|
2633
3089
|
'orderId': id,
|
2634
3090
|
}
|
2635
3091
|
return self.fetch_my_trades(symbol, since, limit, self.extend(request, params))
|
2636
3092
|
|
2637
3093
|
def fetch_my_trades(self, symbol: Str = None, since: Int = None, limit: Int = None, params={}):
|
2638
3094
|
"""
|
2639
|
-
|
2640
|
-
|
3095
|
+
|
3096
|
+
https://docs.kucoin.com/#list-fills
|
3097
|
+
https://docs.kucoin.com/spot-hf/#transaction-details
|
3098
|
+
|
2641
3099
|
fetch all trades made by the user
|
2642
3100
|
:param str symbol: unified market symbol
|
2643
3101
|
:param int [since]: the earliest time in ms to fetch trades for
|
@@ -2653,8 +3111,9 @@ class kucoin(Exchange, ImplicitAPI):
|
|
2653
3111
|
paginate, params = self.handle_option_and_params(params, 'fetchMyTrades', 'paginate')
|
2654
3112
|
if paginate:
|
2655
3113
|
return self.fetch_paginated_call_dynamic('fetchMyTrades', symbol, since, limit, params)
|
2656
|
-
request = {}
|
2657
|
-
hf =
|
3114
|
+
request: dict = {}
|
3115
|
+
hf = None
|
3116
|
+
hf, params = self.handle_hf_and_params(params)
|
2658
3117
|
if hf and symbol is None:
|
2659
3118
|
raise ArgumentsRequired(self.id + ' fetchMyTrades() requires a symbol parameter for hf orders')
|
2660
3119
|
market = None
|
@@ -2668,6 +3127,10 @@ class kucoin(Exchange, ImplicitAPI):
|
|
2668
3127
|
response = None
|
2669
3128
|
request, params = self.handle_until_option('endAt', request, params)
|
2670
3129
|
if hf:
|
3130
|
+
# does not return trades earlier than 2019-02-18T00:00:00Z
|
3131
|
+
if since is not None:
|
3132
|
+
# only returns trades up to one week after the since param
|
3133
|
+
request['startAt'] = since
|
2671
3134
|
response = self.privateGetHfFills(self.extend(request, params))
|
2672
3135
|
elif method == 'private_get_fills':
|
2673
3136
|
# does not return trades earlier than 2019-02-18T00:00:00Z
|
@@ -2734,7 +3197,9 @@ class kucoin(Exchange, ImplicitAPI):
|
|
2734
3197
|
def fetch_trades(self, symbol: str, since: Int = None, limit: Int = None, params={}) -> List[Trade]:
|
2735
3198
|
"""
|
2736
3199
|
get the list of most recent trades for a particular symbol
|
2737
|
-
|
3200
|
+
|
3201
|
+
https://www.kucoin.com/docs/rest/spot-trading/market-data/get-trade-histories
|
3202
|
+
|
2738
3203
|
:param str symbol: unified symbol of the market to fetch trades for
|
2739
3204
|
:param int [since]: timestamp in ms of the earliest trade to fetch
|
2740
3205
|
:param int [limit]: the maximum amount of trades to fetch
|
@@ -2743,7 +3208,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
2743
3208
|
"""
|
2744
3209
|
self.load_markets()
|
2745
3210
|
market = self.market(symbol)
|
2746
|
-
request = {
|
3211
|
+
request: dict = {
|
2747
3212
|
'symbol': market['id'],
|
2748
3213
|
}
|
2749
3214
|
# pagination is not supported on the exchange side anymore
|
@@ -2771,7 +3236,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
2771
3236
|
trades = self.safe_list(response, 'data', [])
|
2772
3237
|
return self.parse_trades(trades, market, since, limit)
|
2773
3238
|
|
2774
|
-
def parse_trade(self, trade, market: Market = None) -> Trade:
|
3239
|
+
def parse_trade(self, trade: dict, market: Market = None) -> Trade:
|
2775
3240
|
#
|
2776
3241
|
# fetchTrades(public)
|
2777
3242
|
#
|
@@ -2896,17 +3361,19 @@ class kucoin(Exchange, ImplicitAPI):
|
|
2896
3361
|
'fee': fee,
|
2897
3362
|
}, market)
|
2898
3363
|
|
2899
|
-
def fetch_trading_fee(self, symbol: str, params={}):
|
3364
|
+
def fetch_trading_fee(self, symbol: str, params={}) -> TradingFeeInterface:
|
2900
3365
|
"""
|
2901
3366
|
fetch the trading fees for a market
|
2902
|
-
|
3367
|
+
|
3368
|
+
https://www.kucoin.com/docs/rest/funding/trade-fee/trading-pair-actual-fee-spot-margin-trade_hf
|
3369
|
+
|
2903
3370
|
:param str symbol: unified market symbol
|
2904
3371
|
:param dict [params]: extra parameters specific to the exchange API endpoint
|
2905
3372
|
:returns dict: a `fee structure <https://docs.ccxt.com/#/?id=fee-structure>`
|
2906
3373
|
"""
|
2907
3374
|
self.load_markets()
|
2908
3375
|
market = self.market(symbol)
|
2909
|
-
request = {
|
3376
|
+
request: dict = {
|
2910
3377
|
'symbols': market['id'],
|
2911
3378
|
}
|
2912
3379
|
response = self.privateGetTradeFees(self.extend(request, params))
|
@@ -2934,10 +3401,12 @@ class kucoin(Exchange, ImplicitAPI):
|
|
2934
3401
|
'tierBased': True,
|
2935
3402
|
}
|
2936
3403
|
|
2937
|
-
def withdraw(self, code: str, amount: float, address, tag=None, params={}):
|
3404
|
+
def withdraw(self, code: str, amount: float, address: str, tag=None, params={}) -> Transaction:
|
2938
3405
|
"""
|
2939
3406
|
make a withdrawal
|
2940
|
-
|
3407
|
+
|
3408
|
+
https://www.kucoin.com/docs/rest/funding/withdrawals/apply-withdraw-v3-
|
3409
|
+
|
2941
3410
|
:param str code: unified currency code
|
2942
3411
|
:param float amount: the amount to withdraw
|
2943
3412
|
:param str address: the address to withdraw to
|
@@ -2949,10 +3418,10 @@ class kucoin(Exchange, ImplicitAPI):
|
|
2949
3418
|
self.load_markets()
|
2950
3419
|
self.check_address(address)
|
2951
3420
|
currency = self.currency(code)
|
2952
|
-
request = {
|
3421
|
+
request: dict = {
|
2953
3422
|
'currency': currency['id'],
|
2954
|
-
'
|
2955
|
-
'
|
3423
|
+
'toAddress': address,
|
3424
|
+
'withdrawType': 'ADDRESS',
|
2956
3425
|
# 'memo': tag,
|
2957
3426
|
# 'isInner': False, # internal transfer or external withdrawal
|
2958
3427
|
# 'remark': 'optional',
|
@@ -2964,13 +3433,14 @@ class kucoin(Exchange, ImplicitAPI):
|
|
2964
3433
|
networkCode, params = self.handle_network_code_and_params(params)
|
2965
3434
|
if networkCode is not None:
|
2966
3435
|
request['chain'] = self.network_code_to_id(networkCode).lower()
|
3436
|
+
request['amount'] = float(self.currency_to_precision(code, amount, networkCode))
|
2967
3437
|
includeFee = None
|
2968
3438
|
includeFee, params = self.handle_option_and_params(params, 'withdraw', 'includeFee', False)
|
2969
3439
|
if includeFee:
|
2970
3440
|
request['feeDeductType'] = 'INTERNAL'
|
2971
3441
|
response = self.privatePostWithdrawals(self.extend(request, params))
|
2972
3442
|
#
|
2973
|
-
#
|
3443
|
+
# the id is inside "data"
|
2974
3444
|
#
|
2975
3445
|
# {
|
2976
3446
|
# "code": 200000,
|
@@ -2982,8 +3452,8 @@ class kucoin(Exchange, ImplicitAPI):
|
|
2982
3452
|
data = self.safe_dict(response, 'data', {})
|
2983
3453
|
return self.parse_transaction(data, currency)
|
2984
3454
|
|
2985
|
-
def parse_transaction_status(self, status):
|
2986
|
-
statuses = {
|
3455
|
+
def parse_transaction_status(self, status: Str):
|
3456
|
+
statuses: dict = {
|
2987
3457
|
'SUCCESS': 'ok',
|
2988
3458
|
'PROCESSING': 'pending',
|
2989
3459
|
'WALLET_PROCESSING': 'pending',
|
@@ -2991,7 +3461,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
2991
3461
|
}
|
2992
3462
|
return self.safe_string(statuses, status, status)
|
2993
3463
|
|
2994
|
-
def parse_transaction(self, transaction, currency: Currency = None) -> Transaction:
|
3464
|
+
def parse_transaction(self, transaction: dict, currency: Currency = None) -> Transaction:
|
2995
3465
|
#
|
2996
3466
|
# fetchDeposits
|
2997
3467
|
#
|
@@ -3098,8 +3568,10 @@ class kucoin(Exchange, ImplicitAPI):
|
|
3098
3568
|
def fetch_deposits(self, code: Str = None, since: Int = None, limit: Int = None, params={}) -> List[Transaction]:
|
3099
3569
|
"""
|
3100
3570
|
fetch all deposits made to an account
|
3101
|
-
|
3102
|
-
|
3571
|
+
|
3572
|
+
https://www.kucoin.com/docs/rest/funding/deposit/get-deposit-list
|
3573
|
+
https://www.kucoin.com/docs/rest/funding/deposit/get-v1-historical-deposits-list
|
3574
|
+
|
3103
3575
|
:param str code: unified currency code
|
3104
3576
|
:param int [since]: the earliest time in ms to fetch deposits for
|
3105
3577
|
:param int [limit]: the maximum number of deposits structures to retrieve
|
@@ -3113,7 +3585,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
3113
3585
|
paginate, params = self.handle_option_and_params(params, 'fetchDeposits', 'paginate')
|
3114
3586
|
if paginate:
|
3115
3587
|
return self.fetch_paginated_call_dynamic('fetchDeposits', code, since, limit, params)
|
3116
|
-
request = {}
|
3588
|
+
request: dict = {}
|
3117
3589
|
currency = None
|
3118
3590
|
if code is not None:
|
3119
3591
|
currency = self.currency(code)
|
@@ -3168,14 +3640,17 @@ class kucoin(Exchange, ImplicitAPI):
|
|
3168
3640
|
# }
|
3169
3641
|
# }
|
3170
3642
|
#
|
3171
|
-
|
3172
|
-
|
3643
|
+
data = self.safe_dict(response, 'data', {})
|
3644
|
+
items = self.safe_list(data, 'items', [])
|
3645
|
+
return self.parse_transactions(items, currency, since, limit, {'type': 'deposit'})
|
3173
3646
|
|
3174
3647
|
def fetch_withdrawals(self, code: Str = None, since: Int = None, limit: Int = None, params={}) -> List[Transaction]:
|
3175
3648
|
"""
|
3176
3649
|
fetch all withdrawals made from an account
|
3177
|
-
|
3178
|
-
|
3650
|
+
|
3651
|
+
https://www.kucoin.com/docs/rest/funding/withdrawals/get-withdrawals-list
|
3652
|
+
https://www.kucoin.com/docs/rest/funding/withdrawals/get-v1-historical-withdrawals-list
|
3653
|
+
|
3179
3654
|
:param str code: unified currency code
|
3180
3655
|
:param int [since]: the earliest time in ms to fetch withdrawals for
|
3181
3656
|
:param int [limit]: the maximum number of withdrawals structures to retrieve
|
@@ -3189,7 +3664,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
3189
3664
|
paginate, params = self.handle_option_and_params(params, 'fetchWithdrawals', 'paginate')
|
3190
3665
|
if paginate:
|
3191
3666
|
return self.fetch_paginated_call_dynamic('fetchWithdrawals', code, since, limit, params)
|
3192
|
-
request = {}
|
3667
|
+
request: dict = {}
|
3193
3668
|
currency = None
|
3194
3669
|
if code is not None:
|
3195
3670
|
currency = self.currency(code)
|
@@ -3245,14 +3720,15 @@ class kucoin(Exchange, ImplicitAPI):
|
|
3245
3720
|
# }
|
3246
3721
|
# }
|
3247
3722
|
#
|
3248
|
-
|
3249
|
-
|
3723
|
+
data = self.safe_dict(response, 'data', {})
|
3724
|
+
items = self.safe_list(data, 'items', [])
|
3725
|
+
return self.parse_transactions(items, currency, since, limit, {'type': 'withdrawal'})
|
3250
3726
|
|
3251
3727
|
def parse_balance_helper(self, entry):
|
3252
3728
|
account = self.account()
|
3253
|
-
account['used'] = self.
|
3254
|
-
account['free'] = self.
|
3255
|
-
account['total'] = self.
|
3729
|
+
account['used'] = self.safe_string_2(entry, 'holdBalance', 'hold')
|
3730
|
+
account['free'] = self.safe_string_2(entry, 'availableBalance', 'available')
|
3731
|
+
account['total'] = self.safe_string_2(entry, 'totalBalance', 'total')
|
3256
3732
|
debt = self.safe_string(entry, 'liability')
|
3257
3733
|
interest = self.safe_string(entry, 'interest')
|
3258
3734
|
account['debt'] = Precise.string_add(debt, interest)
|
@@ -3261,9 +3737,11 @@ class kucoin(Exchange, ImplicitAPI):
|
|
3261
3737
|
def fetch_balance(self, params={}) -> Balances:
|
3262
3738
|
"""
|
3263
3739
|
query for balance and get the amount of funds available for trading or funds locked in orders
|
3264
|
-
|
3265
|
-
|
3266
|
-
|
3740
|
+
|
3741
|
+
https://www.kucoin.com/docs/rest/account/basic-info/get-account-list-spot-margin-trade_hf
|
3742
|
+
https://www.kucoin.com/docs/rest/funding/funding-overview/get-account-detail-margin
|
3743
|
+
https://www.kucoin.com/docs/rest/funding/funding-overview/get-account-detail-isolated-margin
|
3744
|
+
|
3267
3745
|
:param dict [params]: extra parameters specific to the exchange API endpoint
|
3268
3746
|
:param dict [params.marginMode]: 'cross' or 'isolated', margin type for fetching margin balance
|
3269
3747
|
:param dict [params.type]: extra parameters specific to the exchange API endpoint
|
@@ -3280,15 +3758,15 @@ class kucoin(Exchange, ImplicitAPI):
|
|
3280
3758
|
accountsByType = self.safe_dict(self.options, 'accountsByType')
|
3281
3759
|
type = self.safe_string(accountsByType, requestedType, requestedType)
|
3282
3760
|
params = self.omit(params, 'type')
|
3283
|
-
|
3284
|
-
|
3761
|
+
hf = None
|
3762
|
+
hf, params = self.handle_hf_and_params(params)
|
3763
|
+
if hf and (type != 'main'):
|
3285
3764
|
type = 'trade_hf'
|
3286
|
-
params = self.omit(params, 'hf')
|
3287
3765
|
marginMode, query = self.handle_margin_mode_and_params('fetchBalance', params)
|
3288
3766
|
response = None
|
3289
|
-
request = {}
|
3767
|
+
request: dict = {}
|
3290
3768
|
isolated = (marginMode == 'isolated') or (type == 'isolated')
|
3291
|
-
cross = (marginMode == 'cross') or (type == '
|
3769
|
+
cross = (marginMode == 'cross') or (type == 'margin')
|
3292
3770
|
if isolated:
|
3293
3771
|
if currency is not None:
|
3294
3772
|
request['balanceCurrency'] = currency['id']
|
@@ -3301,7 +3779,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
3301
3779
|
request['type'] = type
|
3302
3780
|
response = self.privateGetAccounts(self.extend(request, query))
|
3303
3781
|
#
|
3304
|
-
# Spot
|
3782
|
+
# Spot
|
3305
3783
|
#
|
3306
3784
|
# {
|
3307
3785
|
# "code": "200000",
|
@@ -3317,35 +3795,59 @@ class kucoin(Exchange, ImplicitAPI):
|
|
3317
3795
|
# ]
|
3318
3796
|
# }
|
3319
3797
|
#
|
3798
|
+
# Cross
|
3799
|
+
#
|
3800
|
+
# {
|
3801
|
+
# "code": "200000",
|
3802
|
+
# "data": {
|
3803
|
+
# "debtRatio": "0",
|
3804
|
+
# "accounts": [
|
3805
|
+
# {
|
3806
|
+
# "currency": "USDT",
|
3807
|
+
# "totalBalance": "5",
|
3808
|
+
# "availableBalance": "5",
|
3809
|
+
# "holdBalance": "0",
|
3810
|
+
# "liability": "0",
|
3811
|
+
# "maxBorrowSize": "20"
|
3812
|
+
# },
|
3813
|
+
# ]
|
3814
|
+
# }
|
3815
|
+
# }
|
3816
|
+
#
|
3320
3817
|
# Isolated
|
3321
3818
|
#
|
3322
3819
|
# {
|
3323
3820
|
# "code": "200000",
|
3324
3821
|
# "data": {
|
3325
|
-
# "
|
3326
|
-
# "
|
3822
|
+
# "totalAssetOfQuoteCurrency": "0",
|
3823
|
+
# "totalLiabilityOfQuoteCurrency": "0",
|
3824
|
+
# "timestamp": 1712085661155,
|
3327
3825
|
# "assets": [
|
3328
3826
|
# {
|
3329
3827
|
# "symbol": "MANA-USDT",
|
3330
|
-
# "status": "
|
3828
|
+
# "status": "EFFECTIVE",
|
3331
3829
|
# "debtRatio": "0",
|
3332
3830
|
# "baseAsset": {
|
3333
3831
|
# "currency": "MANA",
|
3334
|
-
# "
|
3335
|
-
# "
|
3336
|
-
# "
|
3832
|
+
# "borrowEnabled": True,
|
3833
|
+
# "transferInEnabled": True,
|
3834
|
+
# "total": "0",
|
3835
|
+
# "hold": "0",
|
3836
|
+
# "available": "0",
|
3337
3837
|
# "liability": "0",
|
3338
3838
|
# "interest": "0",
|
3339
|
-
# "
|
3839
|
+
# "maxBorrowSize": "0"
|
3340
3840
|
# },
|
3341
3841
|
# "quoteAsset": {
|
3342
3842
|
# "currency": "USDT",
|
3343
|
-
# "
|
3344
|
-
# "
|
3345
|
-
# "
|
3843
|
+
# "borrowEnabled": True,
|
3844
|
+
# "transferInEnabled": True,
|
3845
|
+
# "total": "0",
|
3846
|
+
# "hold": "0",
|
3847
|
+
# "available": "0",
|
3346
3848
|
# "liability": "0",
|
3347
3849
|
# "interest": "0",
|
3348
|
-
# "
|
3850
|
+
# "maxBorrowSize": "0"
|
3349
3851
|
# }
|
3350
3852
|
# },
|
3351
3853
|
# ...
|
@@ -3353,13 +3855,14 @@ class kucoin(Exchange, ImplicitAPI):
|
|
3353
3855
|
# }
|
3354
3856
|
# }
|
3355
3857
|
#
|
3356
|
-
data =
|
3357
|
-
result = {
|
3858
|
+
data = None
|
3859
|
+
result: dict = {
|
3358
3860
|
'info': response,
|
3359
3861
|
'timestamp': None,
|
3360
3862
|
'datetime': None,
|
3361
3863
|
}
|
3362
3864
|
if isolated:
|
3865
|
+
data = self.safe_dict(response, 'data', {})
|
3363
3866
|
assets = self.safe_value(data, 'assets', data)
|
3364
3867
|
for i in range(0, len(assets)):
|
3365
3868
|
entry = assets[i]
|
@@ -3369,11 +3872,12 @@ class kucoin(Exchange, ImplicitAPI):
|
|
3369
3872
|
quote = self.safe_dict(entry, 'quoteAsset', {})
|
3370
3873
|
baseCode = self.safe_currency_code(self.safe_string(base, 'currency'))
|
3371
3874
|
quoteCode = self.safe_currency_code(self.safe_string(quote, 'currency'))
|
3372
|
-
subResult = {}
|
3875
|
+
subResult: dict = {}
|
3373
3876
|
subResult[baseCode] = self.parse_balance_helper(base)
|
3374
3877
|
subResult[quoteCode] = self.parse_balance_helper(quote)
|
3375
3878
|
result[symbol] = self.safe_balance(subResult)
|
3376
3879
|
elif cross:
|
3880
|
+
data = self.safe_dict(response, 'data', {})
|
3377
3881
|
accounts = self.safe_list(data, 'accounts', [])
|
3378
3882
|
for i in range(0, len(accounts)):
|
3379
3883
|
balance = accounts[i]
|
@@ -3381,6 +3885,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
3381
3885
|
codeInner = self.safe_currency_code(currencyId)
|
3382
3886
|
result[codeInner] = self.parse_balance_helper(balance)
|
3383
3887
|
else:
|
3888
|
+
data = self.safe_list(response, 'data', [])
|
3384
3889
|
for i in range(0, len(data)):
|
3385
3890
|
balance = data[i]
|
3386
3891
|
balanceType = self.safe_string(balance, 'type')
|
@@ -3398,9 +3903,11 @@ class kucoin(Exchange, ImplicitAPI):
|
|
3398
3903
|
def transfer(self, code: str, amount: float, fromAccount: str, toAccount: str, params={}) -> TransferEntry:
|
3399
3904
|
"""
|
3400
3905
|
transfer currency internally between wallets on the same account
|
3401
|
-
|
3402
|
-
|
3403
|
-
|
3906
|
+
|
3907
|
+
https://www.kucoin.com/docs/rest/funding/transfer/inner-transfer
|
3908
|
+
https://docs.kucoin.com/futures/#transfer-funds-to-kucoin-main-account-2
|
3909
|
+
https://docs.kucoin.com/spot-hf/#internal-funds-transfers-in-high-frequency-trading-accounts
|
3910
|
+
|
3404
3911
|
:param str code: unified currency code
|
3405
3912
|
:param float amount: amount to transfer
|
3406
3913
|
:param str fromAccount: account to transfer from
|
@@ -3418,7 +3925,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
3418
3925
|
if fromId == 'contract':
|
3419
3926
|
if toId != 'main':
|
3420
3927
|
raise ExchangeError(self.id + ' transfer() only supports transferring from futures account to main account')
|
3421
|
-
request = {
|
3928
|
+
request: dict = {
|
3422
3929
|
'currency': currency['id'],
|
3423
3930
|
'amount': requestedAmount,
|
3424
3931
|
}
|
@@ -3453,7 +3960,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
3453
3960
|
data = self.safe_dict(response, 'data')
|
3454
3961
|
return self.parse_transfer(data, currency)
|
3455
3962
|
else:
|
3456
|
-
request = {
|
3963
|
+
request: dict = {
|
3457
3964
|
'currency': currency['id'],
|
3458
3965
|
'amount': requestedAmount,
|
3459
3966
|
}
|
@@ -3480,7 +3987,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
3480
3987
|
data = self.safe_dict(response, 'data')
|
3481
3988
|
return self.parse_transfer(data, currency)
|
3482
3989
|
|
3483
|
-
def parse_transfer(self, transfer, currency: Currency = None):
|
3990
|
+
def parse_transfer(self, transfer: dict, currency: Currency = None) -> TransferEntry:
|
3484
3991
|
#
|
3485
3992
|
# transfer(spot)
|
3486
3993
|
#
|
@@ -3535,14 +4042,14 @@ class kucoin(Exchange, ImplicitAPI):
|
|
3535
4042
|
'info': transfer,
|
3536
4043
|
}
|
3537
4044
|
|
3538
|
-
def parse_transfer_status(self, status):
|
3539
|
-
statuses = {
|
4045
|
+
def parse_transfer_status(self, status: Str) -> Str:
|
4046
|
+
statuses: dict = {
|
3540
4047
|
'PROCESSING': 'pending',
|
3541
4048
|
}
|
3542
4049
|
return self.safe_string(statuses, status, status)
|
3543
4050
|
|
3544
4051
|
def parse_ledger_entry_type(self, type):
|
3545
|
-
types = {
|
4052
|
+
types: dict = {
|
3546
4053
|
'Assets Transferred in After Upgrading': 'transfer', # Assets Transferred in After V1 to V2 Upgrading
|
3547
4054
|
'Deposit': 'transaction', # Deposit
|
3548
4055
|
'Withdrawal': 'transaction', # Withdrawal
|
@@ -3585,7 +4092,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
3585
4092
|
}
|
3586
4093
|
return self.safe_string(types, type, type)
|
3587
4094
|
|
3588
|
-
def parse_ledger_entry(self, item, currency: Currency = None):
|
4095
|
+
def parse_ledger_entry(self, item: dict, currency: Currency = None) -> LedgerEntry:
|
3589
4096
|
#
|
3590
4097
|
# {
|
3591
4098
|
# "id": "611a1e7c6a053300067a88d9", #unique key for each ledger entry
|
@@ -3603,6 +4110,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
3603
4110
|
id = self.safe_string(item, 'id')
|
3604
4111
|
currencyId = self.safe_string(item, 'currency')
|
3605
4112
|
code = self.safe_currency_code(currencyId, currency)
|
4113
|
+
currency = self.safe_currency(currencyId, currency)
|
3606
4114
|
amount = self.safe_number(item, 'amount')
|
3607
4115
|
balanceAfter = None
|
3608
4116
|
# balanceAfter = self.safe_number(item, 'balance'); only returns zero string
|
@@ -3645,7 +4153,8 @@ class kucoin(Exchange, ImplicitAPI):
|
|
3645
4153
|
if feeCost != '0':
|
3646
4154
|
feeCurrency = code
|
3647
4155
|
fee = {'cost': self.parse_number(feeCost), 'currency': feeCurrency}
|
3648
|
-
return {
|
4156
|
+
return self.safe_ledger_entry({
|
4157
|
+
'info': item,
|
3649
4158
|
'id': id,
|
3650
4159
|
'direction': direction,
|
3651
4160
|
'account': account,
|
@@ -3660,33 +4169,34 @@ class kucoin(Exchange, ImplicitAPI):
|
|
3660
4169
|
'after': balanceAfter, # None
|
3661
4170
|
'status': None,
|
3662
4171
|
'fee': fee,
|
3663
|
-
|
3664
|
-
}
|
4172
|
+
}, currency)
|
3665
4173
|
|
3666
|
-
def fetch_ledger(self, code: Str = None, since: Int = None, limit: Int = None, params={}):
|
4174
|
+
def fetch_ledger(self, code: Str = None, since: Int = None, limit: Int = None, params={}) -> List[LedgerEntry]:
|
3667
4175
|
"""
|
3668
|
-
|
3669
|
-
|
3670
|
-
|
3671
|
-
|
3672
|
-
|
4176
|
+
fetch the history of changes, actions done by the user or operations that altered the balance of the user
|
4177
|
+
|
4178
|
+
https://www.kucoin.com/docs/rest/account/basic-info/get-account-ledgers-spot-margin
|
4179
|
+
https://www.kucoin.com/docs/rest/account/basic-info/get-account-ledgers-trade_hf
|
4180
|
+
https://www.kucoin.com/docs/rest/account/basic-info/get-account-ledgers-margin_hf
|
4181
|
+
|
4182
|
+
:param str [code]: unified currency code, default is None
|
3673
4183
|
:param int [since]: timestamp in ms of the earliest ledger entry, default is None
|
3674
|
-
:param int [limit]: max number of ledger
|
4184
|
+
:param int [limit]: max number of ledger entries to return, default is None
|
3675
4185
|
:param dict [params]: extra parameters specific to the exchange API endpoint
|
3676
4186
|
:param boolean [params.hf]: default False, when True will fetch ledger entries for the high frequency trading account
|
3677
4187
|
:param int [params.until]: the latest time in ms to fetch entries for
|
3678
|
-
:param boolean [params.paginate]: default False, when True will automatically paginate by calling self endpoint multiple times. See in the docs all the [
|
3679
|
-
:returns dict: a `ledger structure <https://docs.ccxt.com/#/?id=ledger
|
4188
|
+
:param boolean [params.paginate]: default False, when True will automatically paginate by calling self endpoint multiple times. See in the docs all the [available parameters](https://github.com/ccxt/ccxt/wiki/Manual#pagination-params)
|
4189
|
+
:returns dict: a `ledger structure <https://docs.ccxt.com/#/?id=ledger>`
|
3680
4190
|
"""
|
3681
4191
|
self.load_markets()
|
3682
4192
|
self.load_accounts()
|
3683
4193
|
paginate = False
|
3684
4194
|
paginate, params = self.handle_option_and_params(params, 'fetchLedger', 'paginate')
|
3685
|
-
|
3686
|
-
params = self.
|
4195
|
+
hf = None
|
4196
|
+
hf, params = self.handle_hf_and_params(params)
|
3687
4197
|
if paginate:
|
3688
4198
|
return self.fetch_paginated_call_dynamic('fetchLedger', code, since, limit, params)
|
3689
|
-
request = {
|
4199
|
+
request: dict = {
|
3690
4200
|
# 'currency': currency['id'], # can choose up to 10, if not provided returns for all currencies by default
|
3691
4201
|
# 'direction': 'in', # 'out'
|
3692
4202
|
# 'bizType': 'DEPOSIT', # DEPOSIT, WITHDRAW, TRANSFER, SUB_TRANSFER,TRADE_EXCHANGE, MARGIN_EXCHANGE, KUCOIN_BONUS(optional)
|
@@ -3704,7 +4214,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
3704
4214
|
marginMode = None
|
3705
4215
|
marginMode, params = self.handle_margin_mode_and_params('fetchLedger', params)
|
3706
4216
|
response = None
|
3707
|
-
if
|
4217
|
+
if hf:
|
3708
4218
|
if marginMode is not None:
|
3709
4219
|
response = self.privateGetHfMarginAccountLedgers(self.extend(request, params))
|
3710
4220
|
else:
|
@@ -3769,15 +4279,6 @@ class kucoin(Exchange, ImplicitAPI):
|
|
3769
4279
|
return config['v1']
|
3770
4280
|
return self.safe_value(config, 'cost', 1)
|
3771
4281
|
|
3772
|
-
def parse_borrow_rate_history(self, response, code, since, limit):
|
3773
|
-
result = []
|
3774
|
-
for i in range(0, len(response)):
|
3775
|
-
item = response[i]
|
3776
|
-
borrowRate = self.parse_borrow_rate(item)
|
3777
|
-
result.append(borrowRate)
|
3778
|
-
sorted = self.sort_by(result, 'timestamp')
|
3779
|
-
return self.filter_by_currency_since_limit(sorted, code, since, limit)
|
3780
|
-
|
3781
4282
|
def parse_borrow_rate(self, info, currency: Currency = None):
|
3782
4283
|
#
|
3783
4284
|
# {
|
@@ -3808,13 +4309,15 @@ class kucoin(Exchange, ImplicitAPI):
|
|
3808
4309
|
'info': info,
|
3809
4310
|
}
|
3810
4311
|
|
3811
|
-
def fetch_borrow_interest(self, code: Str = None, symbol: Str = None, since: Int = None, limit: Int = None, params={}):
|
4312
|
+
def fetch_borrow_interest(self, code: Str = None, symbol: Str = None, since: Int = None, limit: Int = None, params={}) -> List[BorrowInterest]:
|
3812
4313
|
"""
|
3813
4314
|
fetch the interest owed by the user for borrowing currency for margin trading
|
3814
|
-
|
3815
|
-
|
3816
|
-
|
3817
|
-
|
4315
|
+
|
4316
|
+
https://docs.kucoin.com/#get-repay-record
|
4317
|
+
https://docs.kucoin.com/#query-isolated-margin-account-info
|
4318
|
+
|
4319
|
+
:param str [code]: unified currency code
|
4320
|
+
:param str [symbol]: unified market symbol, required for isolated margin
|
3818
4321
|
:param int [since]: the earliest time in ms to fetch borrrow interest for
|
3819
4322
|
:param int [limit]: the maximum number of structures to retrieve
|
3820
4323
|
:param dict [params]: extra parameters specific to the exchange API endpoint
|
@@ -3823,14 +4326,19 @@ class kucoin(Exchange, ImplicitAPI):
|
|
3823
4326
|
"""
|
3824
4327
|
self.load_markets()
|
3825
4328
|
marginMode = None
|
3826
|
-
marginMode, params = self.handle_margin_mode_and_params('fetchBorrowInterest', params)
|
3827
|
-
|
3828
|
-
|
3829
|
-
request = {}
|
3830
|
-
response = None
|
4329
|
+
marginMode, params = self.handle_margin_mode_and_params('fetchBorrowInterest', params, 'cross')
|
4330
|
+
request: dict = {}
|
4331
|
+
currency = None
|
3831
4332
|
if code is not None:
|
3832
4333
|
currency = self.currency(code)
|
3833
|
-
|
4334
|
+
if marginMode == 'isolated':
|
4335
|
+
request['balanceCurrency'] = currency['id']
|
4336
|
+
else:
|
4337
|
+
request['quoteCurrency'] = currency['id']
|
4338
|
+
market = None
|
4339
|
+
if symbol is not None:
|
4340
|
+
market = self.market(symbol)
|
4341
|
+
response = None
|
3834
4342
|
if marginMode == 'isolated':
|
3835
4343
|
response = self.privateGetIsolatedAccounts(self.extend(request, params))
|
3836
4344
|
else:
|
@@ -3901,9 +4409,11 @@ class kucoin(Exchange, ImplicitAPI):
|
|
3901
4409
|
#
|
3902
4410
|
data = self.safe_dict(response, 'data', {})
|
3903
4411
|
assets = self.safe_list(data, 'assets', []) if (marginMode == 'isolated') else self.safe_list(data, 'accounts', [])
|
3904
|
-
|
4412
|
+
interest = self.parse_borrow_interests(assets, market)
|
4413
|
+
filteredByCurrency = self.filter_by_currency_since_limit(interest, code, since, limit)
|
4414
|
+
return self.filter_by_symbol_since_limit(filteredByCurrency, symbol, since, limit)
|
3905
4415
|
|
3906
|
-
def parse_borrow_interest(self, info, market: Market = None):
|
4416
|
+
def parse_borrow_interest(self, info: dict, market: Market = None) -> BorrowInterest:
|
3907
4417
|
#
|
3908
4418
|
# Cross
|
3909
4419
|
#
|
@@ -3966,21 +4476,23 @@ class kucoin(Exchange, ImplicitAPI):
|
|
3966
4476
|
interest = self.safe_number(info, 'accruedInterest')
|
3967
4477
|
currencyId = self.safe_string(info, 'currency')
|
3968
4478
|
return {
|
4479
|
+
'info': info,
|
3969
4480
|
'symbol': symbol,
|
3970
|
-
'marginMode': marginMode,
|
3971
4481
|
'currency': self.safe_currency_code(currencyId),
|
3972
4482
|
'interest': interest,
|
3973
4483
|
'interestRate': self.safe_number(info, 'dailyIntRate'),
|
3974
4484
|
'amountBorrowed': amountBorrowed,
|
4485
|
+
'marginMode': marginMode,
|
3975
4486
|
'timestamp': timestamp, # create time
|
3976
4487
|
'datetime': self.iso8601(timestamp),
|
3977
|
-
'info': info,
|
3978
4488
|
}
|
3979
4489
|
|
3980
4490
|
def fetch_borrow_rate_histories(self, codes=None, since: Int = None, limit: Int = None, params={}):
|
3981
4491
|
"""
|
3982
4492
|
retrieves a history of a multiple currencies borrow interest rate at specific time slots, returns all currencies if no symbols passed, default is None
|
3983
|
-
|
4493
|
+
|
4494
|
+
https://www.kucoin.com/docs/rest/margin-trading/margin-trading-v3-/get-cross-isolated-margin-interest-records
|
4495
|
+
|
3984
4496
|
:param str[]|None codes: list of unified currency codes, default is None
|
3985
4497
|
:param int [since]: timestamp in ms of the earliest borrowRate, default is None
|
3986
4498
|
:param int [limit]: max number of borrow rate prices to return, default is None
|
@@ -3993,7 +4505,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
3993
4505
|
marginResult = self.handle_margin_mode_and_params('fetchBorrowRateHistories', params)
|
3994
4506
|
marginMode = self.safe_string(marginResult, 0, 'cross')
|
3995
4507
|
isIsolated = (marginMode == 'isolated') # True-isolated, False-cross
|
3996
|
-
request = {
|
4508
|
+
request: dict = {
|
3997
4509
|
'isIsolated': isIsolated,
|
3998
4510
|
}
|
3999
4511
|
if since is not None:
|
@@ -4023,13 +4535,15 @@ class kucoin(Exchange, ImplicitAPI):
|
|
4023
4535
|
# }
|
4024
4536
|
#
|
4025
4537
|
data = self.safe_dict(response, 'data')
|
4026
|
-
rows = self.safe_list(data, 'items')
|
4538
|
+
rows = self.safe_list(data, 'items', [])
|
4027
4539
|
return self.parse_borrow_rate_histories(rows, codes, since, limit)
|
4028
4540
|
|
4029
4541
|
def fetch_borrow_rate_history(self, code: str, since: Int = None, limit: Int = None, params={}):
|
4030
4542
|
"""
|
4031
4543
|
retrieves a history of a currencies borrow interest rate at specific time slots
|
4032
|
-
|
4544
|
+
|
4545
|
+
https://www.kucoin.com/docs/rest/margin-trading/margin-trading-v3-/get-cross-isolated-margin-interest-records
|
4546
|
+
|
4033
4547
|
:param str code: unified currency code
|
4034
4548
|
:param int [since]: timestamp for the earliest borrow rate
|
4035
4549
|
:param int [limit]: the maximum number of `borrow rate structures <https://docs.ccxt.com/#/?id=borrow-rate-structure>` to retrieve
|
@@ -4043,7 +4557,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
4043
4557
|
marginMode = self.safe_string(marginResult, 0, 'cross')
|
4044
4558
|
isIsolated = (marginMode == 'isolated') # True-isolated, False-cross
|
4045
4559
|
currency = self.currency(code)
|
4046
|
-
request = {
|
4560
|
+
request: dict = {
|
4047
4561
|
'isIsolated': isIsolated,
|
4048
4562
|
'currency': currency['id'],
|
4049
4563
|
}
|
@@ -4074,7 +4588,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
4074
4588
|
# }
|
4075
4589
|
#
|
4076
4590
|
data = self.safe_dict(response, 'data')
|
4077
|
-
rows = self.safe_list(data, 'items')
|
4591
|
+
rows = self.safe_list(data, 'items', [])
|
4078
4592
|
return self.parse_borrow_rate_history(rows, code, since, limit)
|
4079
4593
|
|
4080
4594
|
def parse_borrow_rate_histories(self, response, codes, since, limit):
|
@@ -4088,7 +4602,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
4088
4602
|
# }
|
4089
4603
|
# ]
|
4090
4604
|
#
|
4091
|
-
borrowRateHistories = {}
|
4605
|
+
borrowRateHistories: dict = {}
|
4092
4606
|
for i in range(0, len(response)):
|
4093
4607
|
item = response[i]
|
4094
4608
|
code = self.safe_currency_code(self.safe_string(item, 'currency'))
|
@@ -4106,7 +4620,9 @@ class kucoin(Exchange, ImplicitAPI):
|
|
4106
4620
|
def borrow_cross_margin(self, code: str, amount: float, params={}):
|
4107
4621
|
"""
|
4108
4622
|
create a loan to borrow margin
|
4109
|
-
|
4623
|
+
|
4624
|
+
https://docs.kucoin.com/#1-margin-borrowing
|
4625
|
+
|
4110
4626
|
:param str code: unified currency code of the currency to borrow
|
4111
4627
|
:param float amount: the amount to borrow
|
4112
4628
|
:param dict [params]: extra parameters specific to the exchange API endpoints
|
@@ -4115,7 +4631,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
4115
4631
|
"""
|
4116
4632
|
self.load_markets()
|
4117
4633
|
currency = self.currency(code)
|
4118
|
-
request = {
|
4634
|
+
request: dict = {
|
4119
4635
|
'currency': currency['id'],
|
4120
4636
|
'size': self.currency_to_precision(code, amount),
|
4121
4637
|
'timeInForce': 'FOK',
|
@@ -4139,7 +4655,9 @@ class kucoin(Exchange, ImplicitAPI):
|
|
4139
4655
|
def borrow_isolated_margin(self, symbol: str, code: str, amount: float, params={}):
|
4140
4656
|
"""
|
4141
4657
|
create a loan to borrow margin
|
4142
|
-
|
4658
|
+
|
4659
|
+
https://docs.kucoin.com/#1-margin-borrowing
|
4660
|
+
|
4143
4661
|
:param str symbol: unified market symbol, required for isolated margin
|
4144
4662
|
:param str code: unified currency code of the currency to borrow
|
4145
4663
|
:param float amount: the amount to borrow
|
@@ -4150,7 +4668,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
4150
4668
|
self.load_markets()
|
4151
4669
|
market = self.market(symbol)
|
4152
4670
|
currency = self.currency(code)
|
4153
|
-
request = {
|
4671
|
+
request: dict = {
|
4154
4672
|
'currency': currency['id'],
|
4155
4673
|
'size': self.currency_to_precision(code, amount),
|
4156
4674
|
'symbol': market['id'],
|
@@ -4176,7 +4694,9 @@ class kucoin(Exchange, ImplicitAPI):
|
|
4176
4694
|
def repay_cross_margin(self, code: str, amount, params={}):
|
4177
4695
|
"""
|
4178
4696
|
repay borrowed margin and interest
|
4179
|
-
|
4697
|
+
|
4698
|
+
https://docs.kucoin.com/#2-repayment
|
4699
|
+
|
4180
4700
|
:param str code: unified currency code of the currency to repay
|
4181
4701
|
:param float amount: the amount to repay
|
4182
4702
|
:param dict [params]: extra parameters specific to the exchange API endpoints
|
@@ -4184,7 +4704,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
4184
4704
|
"""
|
4185
4705
|
self.load_markets()
|
4186
4706
|
currency = self.currency(code)
|
4187
|
-
request = {
|
4707
|
+
request: dict = {
|
4188
4708
|
'currency': currency['id'],
|
4189
4709
|
'size': self.currency_to_precision(code, amount),
|
4190
4710
|
}
|
@@ -4207,7 +4727,9 @@ class kucoin(Exchange, ImplicitAPI):
|
|
4207
4727
|
def repay_isolated_margin(self, symbol: str, code: str, amount, params={}):
|
4208
4728
|
"""
|
4209
4729
|
repay borrowed margin and interest
|
4210
|
-
|
4730
|
+
|
4731
|
+
https://docs.kucoin.com/#2-repayment
|
4732
|
+
|
4211
4733
|
:param str symbol: unified market symbol
|
4212
4734
|
:param str code: unified currency code of the currency to repay
|
4213
4735
|
:param float amount: the amount to repay
|
@@ -4217,7 +4739,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
4217
4739
|
self.load_markets()
|
4218
4740
|
market = self.market(symbol)
|
4219
4741
|
currency = self.currency(code)
|
4220
|
-
request = {
|
4742
|
+
request: dict = {
|
4221
4743
|
'currency': currency['id'],
|
4222
4744
|
'size': self.currency_to_precision(code, amount),
|
4223
4745
|
'symbol': market['id'],
|
@@ -4261,7 +4783,9 @@ class kucoin(Exchange, ImplicitAPI):
|
|
4261
4783
|
def fetch_deposit_withdraw_fees(self, codes: Strings = None, params={}):
|
4262
4784
|
"""
|
4263
4785
|
fetch deposit and withdraw fees - *IMPORTANT* use fetchDepositWithdrawFee to get more in-depth info
|
4264
|
-
|
4786
|
+
|
4787
|
+
https://docs.kucoin.com/#get-currencies
|
4788
|
+
|
4265
4789
|
:param str[]|None codes: list of unified currency codes
|
4266
4790
|
:param dict [params]: extra parameters specific to the exchange API endpoint
|
4267
4791
|
:returns dict: a list of `fee structures <https://docs.ccxt.com/#/?id=fee-structure>`
|
@@ -4289,6 +4813,38 @@ class kucoin(Exchange, ImplicitAPI):
|
|
4289
4813
|
data = self.safe_list(response, 'data', [])
|
4290
4814
|
return self.parse_deposit_withdraw_fees(data, codes, 'currency')
|
4291
4815
|
|
4816
|
+
def set_leverage(self, leverage: Int, symbol: Str = None, params={}):
|
4817
|
+
"""
|
4818
|
+
set the level of leverage for a market
|
4819
|
+
|
4820
|
+
https://www.kucoin.com/docs/rest/margin-trading/margin-trading-v3-/modify-leverage-multiplier
|
4821
|
+
|
4822
|
+
:param int [leverage]: New leverage multiplier. Must be greater than 1 and up to two decimal places, and cannot be less than the user's current debt leverage or greater than the system's maximum leverage
|
4823
|
+
:param str [symbol]: unified market symbol
|
4824
|
+
:param dict [params]: extra parameters specific to the exchange API endpoint
|
4825
|
+
:returns dict: response from the exchange
|
4826
|
+
"""
|
4827
|
+
self.load_markets()
|
4828
|
+
market = None
|
4829
|
+
marketType: Str = None
|
4830
|
+
marketType, params = self.handle_market_type_and_params('setLeverage', None, params)
|
4831
|
+
if (symbol is not None) or marketType != 'spot':
|
4832
|
+
market = self.market(symbol)
|
4833
|
+
if market['contract']:
|
4834
|
+
raise NotSupported(self.id + ' setLeverage currently supports only spot margin')
|
4835
|
+
marginMode: Str = None
|
4836
|
+
marginMode, params = self.handle_margin_mode_and_params('setLeverage', params)
|
4837
|
+
if marginMode is None:
|
4838
|
+
raise ArgumentsRequired(self.id + ' setLeverage requires a marginMode parameter')
|
4839
|
+
request: dict = {}
|
4840
|
+
if marginMode == 'isolated' and symbol is None:
|
4841
|
+
raise ArgumentsRequired(self.id + ' setLeverage requires a symbol parameter for isolated margin')
|
4842
|
+
if symbol is not None:
|
4843
|
+
request['symbol'] = market['id']
|
4844
|
+
request['leverage'] = str(leverage)
|
4845
|
+
request['isIsolated'] = (marginMode == 'isolated')
|
4846
|
+
return self.privatePostPositionUpdateUserLeverage(self.extend(request, params))
|
4847
|
+
|
4292
4848
|
def sign(self, path, api='public', method='GET', params={}, headers=None, body=None):
|
4293
4849
|
#
|
4294
4850
|
# the v2 URL is https://openapi-v2.kucoin.com/api/v1/endpoint
|
@@ -4304,12 +4860,14 @@ class kucoin(Exchange, ImplicitAPI):
|
|
4304
4860
|
endpoint = '/api/' + version + '/' + self.implode_params(path, params)
|
4305
4861
|
if api == 'webExchange':
|
4306
4862
|
endpoint = '/' + self.implode_params(path, params)
|
4863
|
+
if api == 'earn':
|
4864
|
+
endpoint = '/api/v1/' + self.implode_params(path, params)
|
4307
4865
|
query = self.omit(params, self.extract_params(path))
|
4308
4866
|
endpart = ''
|
4309
4867
|
headers = headers if (headers is not None) else {}
|
4310
4868
|
url = self.urls['api'][api]
|
4311
4869
|
if not self.is_empty(query):
|
4312
|
-
if (method == 'GET') or (method == 'DELETE'):
|
4870
|
+
if ((method == 'GET') or (method == 'DELETE')) and (path != 'orders/multi-cancel'):
|
4313
4871
|
endpoint += '?' + self.rawencode(query)
|
4314
4872
|
else:
|
4315
4873
|
body = self.json(query)
|
@@ -4319,7 +4877,8 @@ class kucoin(Exchange, ImplicitAPI):
|
|
4319
4877
|
isFuturePrivate = (api == 'futuresPrivate')
|
4320
4878
|
isPrivate = (api == 'private')
|
4321
4879
|
isBroker = (api == 'broker')
|
4322
|
-
|
4880
|
+
isEarn = (api == 'earn')
|
4881
|
+
if isPrivate or isFuturePrivate or isBroker or isEarn:
|
4323
4882
|
self.check_required_credentials()
|
4324
4883
|
timestamp = str(self.nonce())
|
4325
4884
|
headers = self.extend({
|
@@ -4345,13 +4904,14 @@ class kucoin(Exchange, ImplicitAPI):
|
|
4345
4904
|
partnerSignature = self.hmac(self.encode(partnerPayload), self.encode(partnerSecret), hashlib.sha256, 'base64')
|
4346
4905
|
headers['KC-API-PARTNER-SIGN'] = partnerSignature
|
4347
4906
|
headers['KC-API-PARTNER'] = partnerId
|
4907
|
+
headers['KC-API-PARTNER-VERIFY'] = 'true'
|
4348
4908
|
if isBroker:
|
4349
4909
|
brokerName = self.safe_string(partner, 'name')
|
4350
4910
|
if brokerName is not None:
|
4351
4911
|
headers['KC-BROKER-NAME'] = brokerName
|
4352
4912
|
return {'url': url, 'method': method, 'body': body, 'headers': headers}
|
4353
4913
|
|
4354
|
-
def handle_errors(self, code, reason, url, method, headers, body, response, requestHeaders, requestBody):
|
4914
|
+
def handle_errors(self, code: int, reason: str, url: str, method: str, headers: dict, body: str, response, requestHeaders, requestBody):
|
4355
4915
|
if not response:
|
4356
4916
|
self.throw_broadly_matched_exception(self.exceptions['broad'], body, body)
|
4357
4917
|
return None
|
@@ -4363,7 +4923,7 @@ class kucoin(Exchange, ImplicitAPI):
|
|
4363
4923
|
#
|
4364
4924
|
errorCode = self.safe_string(response, 'code')
|
4365
4925
|
message = self.safe_string_2(response, 'msg', 'data', '')
|
4366
|
-
feedback = self.id + ' ' +
|
4926
|
+
feedback = self.id + ' ' + body
|
4367
4927
|
self.throw_exactly_matched_exception(self.exceptions['exact'], message, feedback)
|
4368
4928
|
self.throw_exactly_matched_exception(self.exceptions['exact'], errorCode, feedback)
|
4369
4929
|
self.throw_broadly_matched_exception(self.exceptions['broad'], body, feedback)
|