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.
Files changed (546) hide show
  1. ccxt/__init__.py +36 -14
  2. ccxt/abstract/alpaca.py +4 -0
  3. ccxt/abstract/bigone.py +1 -1
  4. ccxt/abstract/binance.py +112 -48
  5. ccxt/abstract/binancecoinm.py +112 -48
  6. ccxt/abstract/binanceus.py +147 -83
  7. ccxt/abstract/binanceusdm.py +112 -48
  8. ccxt/abstract/bingx.py +133 -78
  9. ccxt/abstract/bitbank.py +5 -0
  10. ccxt/abstract/bitfinex.py +136 -65
  11. ccxt/abstract/bitfinex1.py +69 -0
  12. ccxt/abstract/bitflyer.py +1 -0
  13. ccxt/abstract/bitget.py +8 -1
  14. ccxt/abstract/bitmart.py +13 -1
  15. ccxt/abstract/bitopro.py +1 -0
  16. ccxt/abstract/bitpanda.py +0 -12
  17. ccxt/abstract/bitrue.py +3 -3
  18. ccxt/abstract/bitstamp.py +26 -3
  19. ccxt/abstract/blofin.py +24 -0
  20. ccxt/abstract/btcbox.py +1 -0
  21. ccxt/abstract/bybit.py +29 -14
  22. ccxt/abstract/cex.py +28 -29
  23. ccxt/abstract/coinbase.py +6 -0
  24. ccxt/abstract/coinbaseadvanced.py +94 -0
  25. ccxt/abstract/{coinbasepro.py → coinbaseexchange.py} +1 -0
  26. ccxt/abstract/coinbaseinternational.py +1 -1
  27. ccxt/abstract/coincatch.py +94 -0
  28. ccxt/abstract/coinex.py +233 -123
  29. ccxt/abstract/coinmetro.py +1 -0
  30. ccxt/abstract/cryptocom.py +14 -0
  31. ccxt/abstract/defx.py +69 -0
  32. ccxt/abstract/deribit.py +1 -0
  33. ccxt/abstract/digifinex.py +1 -0
  34. ccxt/abstract/ellipx.py +25 -0
  35. ccxt/abstract/gate.py +20 -0
  36. ccxt/abstract/gateio.py +20 -0
  37. ccxt/abstract/gemini.py +1 -0
  38. ccxt/abstract/hashkey.py +67 -0
  39. ccxt/abstract/hyperliquid.py +1 -1
  40. ccxt/abstract/independentreserve.py +6 -0
  41. ccxt/abstract/kraken.py +4 -3
  42. ccxt/abstract/krakenfutures.py +4 -0
  43. ccxt/abstract/kucoin.py +24 -0
  44. ccxt/abstract/kucoinfutures.py +34 -0
  45. ccxt/abstract/luno.py +2 -0
  46. ccxt/abstract/mexc.py +4 -0
  47. ccxt/abstract/myokx.py +340 -0
  48. ccxt/abstract/oceanex.py +5 -0
  49. ccxt/abstract/okx.py +30 -0
  50. ccxt/abstract/onetrading.py +0 -12
  51. ccxt/abstract/oxfun.py +34 -0
  52. ccxt/abstract/paradex.py +40 -0
  53. ccxt/abstract/phemex.py +1 -0
  54. ccxt/abstract/upbit.py +4 -0
  55. ccxt/abstract/vertex.py +19 -0
  56. ccxt/abstract/whitebit.py +31 -1
  57. ccxt/abstract/woo.py +6 -2
  58. ccxt/abstract/woofipro.py +119 -0
  59. ccxt/abstract/xt.py +153 -0
  60. ccxt/abstract/zonda.py +6 -0
  61. ccxt/ace.py +164 -60
  62. ccxt/alpaca.py +727 -63
  63. ccxt/ascendex.py +395 -249
  64. ccxt/async_support/__init__.py +36 -14
  65. ccxt/async_support/ace.py +164 -60
  66. ccxt/async_support/alpaca.py +727 -63
  67. ccxt/async_support/ascendex.py +396 -249
  68. ccxt/async_support/base/exchange.py +531 -155
  69. ccxt/async_support/base/ws/aiohttp_client.py +28 -5
  70. ccxt/async_support/base/ws/cache.py +3 -2
  71. ccxt/async_support/base/ws/client.py +26 -5
  72. ccxt/async_support/base/ws/fast_client.py +4 -3
  73. ccxt/async_support/base/ws/functions.py +1 -1
  74. ccxt/async_support/base/ws/future.py +40 -31
  75. ccxt/async_support/base/ws/order_book_side.py +3 -0
  76. ccxt/async_support/bequant.py +1 -1
  77. ccxt/async_support/bigone.py +329 -202
  78. ccxt/async_support/binance.py +3030 -1087
  79. ccxt/async_support/binancecoinm.py +2 -1
  80. ccxt/async_support/binanceus.py +12 -1
  81. ccxt/async_support/binanceusdm.py +3 -1
  82. ccxt/async_support/bingx.py +3104 -880
  83. ccxt/async_support/bit2c.py +119 -38
  84. ccxt/async_support/bitbank.py +215 -76
  85. ccxt/async_support/bitbns.py +124 -53
  86. ccxt/async_support/bitfinex.py +3236 -1078
  87. ccxt/async_support/bitfinex1.py +1711 -0
  88. ccxt/async_support/bitflyer.py +238 -49
  89. ccxt/async_support/bitget.py +1513 -563
  90. ccxt/async_support/bithumb.py +199 -65
  91. ccxt/async_support/bitmart.py +1320 -435
  92. ccxt/async_support/bitmex.py +308 -111
  93. ccxt/async_support/bitopro.py +256 -96
  94. ccxt/async_support/bitrue.py +365 -233
  95. ccxt/async_support/bitso.py +201 -89
  96. ccxt/async_support/bitstamp.py +438 -269
  97. ccxt/async_support/bitteam.py +179 -73
  98. ccxt/async_support/bitvavo.py +180 -70
  99. ccxt/async_support/bl3p.py +92 -25
  100. ccxt/async_support/blockchaincom.py +193 -79
  101. ccxt/async_support/blofin.py +392 -148
  102. ccxt/async_support/btcalpha.py +161 -55
  103. ccxt/async_support/btcbox.py +250 -34
  104. ccxt/async_support/btcmarkets.py +232 -85
  105. ccxt/async_support/btcturk.py +159 -60
  106. ccxt/async_support/bybit.py +2231 -1193
  107. ccxt/async_support/cex.py +1409 -1329
  108. ccxt/async_support/coinbase.py +1454 -287
  109. ccxt/async_support/coinbaseadvanced.py +17 -0
  110. ccxt/async_support/{coinbasepro.py → coinbaseexchange.py} +233 -99
  111. ccxt/async_support/coinbaseinternational.py +428 -88
  112. ccxt/async_support/coincatch.py +5152 -0
  113. ccxt/async_support/coincheck.py +121 -38
  114. ccxt/async_support/coinex.py +4020 -3339
  115. ccxt/async_support/coinlist.py +273 -116
  116. ccxt/async_support/coinmate.py +204 -97
  117. ccxt/async_support/coinmetro.py +203 -110
  118. ccxt/async_support/coinone.py +142 -68
  119. ccxt/async_support/coinsph.py +206 -89
  120. ccxt/async_support/coinspot.py +137 -62
  121. ccxt/async_support/cryptocom.py +515 -185
  122. ccxt/async_support/currencycom.py +203 -85
  123. ccxt/async_support/defx.py +2066 -0
  124. ccxt/async_support/delta.py +404 -109
  125. ccxt/async_support/deribit.py +557 -323
  126. ccxt/async_support/digifinex.py +340 -223
  127. ccxt/async_support/ellipx.py +1826 -0
  128. ccxt/async_support/exmo.py +259 -128
  129. ccxt/async_support/gate.py +1472 -463
  130. ccxt/async_support/gemini.py +206 -84
  131. ccxt/async_support/hashkey.py +4164 -0
  132. ccxt/async_support/hitbtc.py +334 -178
  133. ccxt/async_support/hollaex.py +134 -83
  134. ccxt/async_support/htx.py +1095 -563
  135. ccxt/async_support/huobijp.py +105 -56
  136. ccxt/async_support/hyperliquid.py +1633 -268
  137. ccxt/async_support/idex.py +148 -95
  138. ccxt/async_support/independentreserve.py +236 -31
  139. ccxt/async_support/indodax.py +165 -62
  140. ccxt/async_support/kraken.py +871 -354
  141. ccxt/async_support/krakenfutures.py +324 -100
  142. ccxt/async_support/kucoin.py +917 -357
  143. ccxt/async_support/kucoinfutures.py +1004 -149
  144. ccxt/async_support/kuna.py +138 -106
  145. ccxt/async_support/latoken.py +135 -79
  146. ccxt/async_support/lbank.py +290 -113
  147. ccxt/async_support/luno.py +112 -62
  148. ccxt/async_support/lykke.py +104 -55
  149. ccxt/async_support/mercado.py +36 -29
  150. ccxt/async_support/mexc.py +995 -429
  151. ccxt/async_support/myokx.py +43 -0
  152. ccxt/async_support/ndax.py +163 -82
  153. ccxt/async_support/novadax.py +121 -75
  154. ccxt/async_support/oceanex.py +175 -59
  155. ccxt/async_support/okcoin.py +222 -163
  156. ccxt/async_support/okx.py +1776 -454
  157. ccxt/async_support/onetrading.py +132 -414
  158. ccxt/async_support/oxfun.py +2832 -0
  159. ccxt/async_support/p2b.py +79 -51
  160. ccxt/async_support/paradex.py +2017 -0
  161. ccxt/async_support/paymium.py +56 -32
  162. ccxt/async_support/phemex.py +572 -196
  163. ccxt/async_support/poloniex.py +218 -95
  164. ccxt/async_support/poloniexfutures.py +260 -92
  165. ccxt/async_support/probit.py +143 -110
  166. ccxt/async_support/timex.py +123 -70
  167. ccxt/async_support/tokocrypto.py +129 -93
  168. ccxt/async_support/tradeogre.py +39 -25
  169. ccxt/async_support/upbit.py +322 -113
  170. ccxt/async_support/vertex.py +2983 -0
  171. ccxt/async_support/wavesexchange.py +227 -173
  172. ccxt/async_support/wazirx.py +145 -65
  173. ccxt/async_support/whitebit.py +533 -138
  174. ccxt/async_support/woo.py +1137 -296
  175. ccxt/async_support/woofipro.py +2716 -0
  176. ccxt/async_support/xt.py +4628 -0
  177. ccxt/async_support/yobit.py +160 -92
  178. ccxt/async_support/zaif.py +80 -33
  179. ccxt/async_support/zonda.py +140 -69
  180. ccxt/base/errors.py +51 -20
  181. ccxt/base/exchange.py +1722 -480
  182. ccxt/base/precise.py +10 -0
  183. ccxt/base/types.py +223 -4
  184. ccxt/bequant.py +1 -1
  185. ccxt/bigone.py +329 -202
  186. ccxt/binance.py +3030 -1087
  187. ccxt/binancecoinm.py +2 -1
  188. ccxt/binanceus.py +12 -1
  189. ccxt/binanceusdm.py +3 -1
  190. ccxt/bingx.py +3104 -880
  191. ccxt/bit2c.py +119 -38
  192. ccxt/bitbank.py +215 -76
  193. ccxt/bitbns.py +124 -53
  194. ccxt/bitfinex.py +3235 -1078
  195. ccxt/bitfinex1.py +1710 -0
  196. ccxt/bitflyer.py +238 -49
  197. ccxt/bitget.py +1513 -563
  198. ccxt/bithumb.py +198 -65
  199. ccxt/bitmart.py +1320 -435
  200. ccxt/bitmex.py +308 -111
  201. ccxt/bitopro.py +256 -96
  202. ccxt/bitrue.py +365 -233
  203. ccxt/bitso.py +201 -89
  204. ccxt/bitstamp.py +438 -269
  205. ccxt/bitteam.py +179 -73
  206. ccxt/bitvavo.py +180 -70
  207. ccxt/bl3p.py +92 -25
  208. ccxt/blockchaincom.py +193 -79
  209. ccxt/blofin.py +392 -148
  210. ccxt/btcalpha.py +161 -55
  211. ccxt/btcbox.py +250 -34
  212. ccxt/btcmarkets.py +232 -85
  213. ccxt/btcturk.py +159 -60
  214. ccxt/bybit.py +2231 -1193
  215. ccxt/cex.py +1408 -1329
  216. ccxt/coinbase.py +1454 -287
  217. ccxt/coinbaseadvanced.py +17 -0
  218. ccxt/{coinbasepro.py → coinbaseexchange.py} +233 -99
  219. ccxt/coinbaseinternational.py +428 -88
  220. ccxt/coincatch.py +5152 -0
  221. ccxt/coincheck.py +121 -38
  222. ccxt/coinex.py +4020 -3339
  223. ccxt/coinlist.py +273 -116
  224. ccxt/coinmate.py +204 -97
  225. ccxt/coinmetro.py +203 -110
  226. ccxt/coinone.py +142 -68
  227. ccxt/coinsph.py +206 -89
  228. ccxt/coinspot.py +137 -62
  229. ccxt/cryptocom.py +515 -185
  230. ccxt/currencycom.py +203 -85
  231. ccxt/defx.py +2065 -0
  232. ccxt/delta.py +404 -109
  233. ccxt/deribit.py +557 -323
  234. ccxt/digifinex.py +340 -223
  235. ccxt/ellipx.py +1826 -0
  236. ccxt/exmo.py +259 -128
  237. ccxt/gate.py +1472 -463
  238. ccxt/gemini.py +206 -84
  239. ccxt/hashkey.py +4164 -0
  240. ccxt/hitbtc.py +334 -178
  241. ccxt/hollaex.py +134 -83
  242. ccxt/htx.py +1095 -563
  243. ccxt/huobijp.py +105 -56
  244. ccxt/hyperliquid.py +1632 -268
  245. ccxt/idex.py +148 -95
  246. ccxt/independentreserve.py +235 -31
  247. ccxt/indodax.py +165 -62
  248. ccxt/kraken.py +871 -354
  249. ccxt/krakenfutures.py +324 -100
  250. ccxt/kucoin.py +917 -357
  251. ccxt/kucoinfutures.py +1004 -149
  252. ccxt/kuna.py +138 -106
  253. ccxt/latoken.py +135 -79
  254. ccxt/lbank.py +290 -113
  255. ccxt/luno.py +112 -62
  256. ccxt/lykke.py +104 -55
  257. ccxt/mercado.py +36 -29
  258. ccxt/mexc.py +994 -429
  259. ccxt/myokx.py +43 -0
  260. ccxt/ndax.py +163 -82
  261. ccxt/novadax.py +121 -75
  262. ccxt/oceanex.py +175 -59
  263. ccxt/okcoin.py +222 -163
  264. ccxt/okx.py +1776 -454
  265. ccxt/onetrading.py +132 -414
  266. ccxt/oxfun.py +2831 -0
  267. ccxt/p2b.py +79 -51
  268. ccxt/paradex.py +2017 -0
  269. ccxt/paymium.py +56 -32
  270. ccxt/phemex.py +572 -196
  271. ccxt/poloniex.py +218 -95
  272. ccxt/poloniexfutures.py +260 -92
  273. ccxt/pro/__init__.py +29 -5
  274. ccxt/pro/alpaca.py +32 -17
  275. ccxt/pro/ascendex.py +62 -14
  276. ccxt/pro/bequant.py +4 -0
  277. ccxt/pro/binance.py +1596 -329
  278. ccxt/pro/binancecoinm.py +1 -0
  279. ccxt/pro/binanceus.py +2 -9
  280. ccxt/pro/binanceusdm.py +2 -0
  281. ccxt/pro/bingx.py +527 -134
  282. ccxt/pro/bitcoincom.py +4 -1
  283. ccxt/pro/bitfinex.py +731 -266
  284. ccxt/pro/bitfinex1.py +635 -0
  285. ccxt/pro/bitget.py +726 -357
  286. ccxt/pro/bithumb.py +380 -0
  287. ccxt/pro/bitmart.py +138 -39
  288. ccxt/pro/bitmex.py +199 -40
  289. ccxt/pro/bitopro.py +25 -13
  290. ccxt/pro/bitrue.py +31 -32
  291. ccxt/pro/bitstamp.py +7 -6
  292. ccxt/pro/bitvavo.py +203 -81
  293. ccxt/pro/blockchaincom.py +30 -17
  294. ccxt/pro/blofin.py +692 -0
  295. ccxt/pro/bybit.py +791 -82
  296. ccxt/pro/cex.py +99 -51
  297. ccxt/pro/coinbase.py +220 -30
  298. ccxt/{async_support/hitbtc3.py → pro/coinbaseadvanced.py} +5 -5
  299. ccxt/pro/{coinbasepro.py → coinbaseexchange.py} +19 -19
  300. ccxt/pro/coinbaseinternational.py +193 -30
  301. ccxt/pro/coincatch.py +1464 -0
  302. ccxt/pro/coincheck.py +11 -6
  303. ccxt/pro/coinex.py +965 -665
  304. ccxt/pro/coinone.py +17 -10
  305. ccxt/pro/cryptocom.py +446 -66
  306. ccxt/pro/currencycom.py +11 -10
  307. ccxt/pro/defx.py +832 -0
  308. ccxt/pro/deribit.py +167 -31
  309. ccxt/pro/exmo.py +252 -20
  310. ccxt/pro/gate.py +729 -64
  311. ccxt/pro/gemini.py +44 -26
  312. ccxt/pro/hashkey.py +802 -0
  313. ccxt/pro/hitbtc.py +208 -103
  314. ccxt/pro/hollaex.py +25 -9
  315. ccxt/pro/htx.py +83 -39
  316. ccxt/pro/huobijp.py +17 -16
  317. ccxt/pro/hyperliquid.py +502 -31
  318. ccxt/pro/idex.py +28 -13
  319. ccxt/pro/independentreserve.py +21 -16
  320. ccxt/pro/kraken.py +298 -51
  321. ccxt/pro/krakenfutures.py +166 -75
  322. ccxt/pro/kucoin.py +395 -77
  323. ccxt/pro/kucoinfutures.py +400 -99
  324. ccxt/pro/lbank.py +52 -31
  325. ccxt/pro/luno.py +12 -10
  326. ccxt/pro/mexc.py +400 -50
  327. ccxt/pro/myokx.py +28 -0
  328. ccxt/pro/ndax.py +25 -12
  329. ccxt/pro/okcoin.py +28 -9
  330. ccxt/pro/okx.py +935 -124
  331. ccxt/pro/onetrading.py +41 -24
  332. ccxt/pro/oxfun.py +1054 -0
  333. ccxt/pro/p2b.py +100 -24
  334. ccxt/pro/paradex.py +352 -0
  335. ccxt/pro/phemex.py +92 -33
  336. ccxt/pro/poloniex.py +128 -49
  337. ccxt/pro/poloniexfutures.py +53 -32
  338. ccxt/pro/probit.py +92 -85
  339. ccxt/pro/upbit.py +401 -8
  340. ccxt/pro/vertex.py +943 -0
  341. ccxt/pro/wazirx.py +46 -28
  342. ccxt/pro/whitebit.py +65 -12
  343. ccxt/pro/woo.py +437 -65
  344. ccxt/pro/woofipro.py +1271 -0
  345. ccxt/pro/xt.py +1067 -0
  346. ccxt/probit.py +143 -110
  347. ccxt/static_dependencies/__init__.py +1 -1
  348. ccxt/static_dependencies/lark/__init__.py +38 -0
  349. ccxt/static_dependencies/lark/__pyinstaller/__init__.py +6 -0
  350. ccxt/static_dependencies/lark/__pyinstaller/hook-lark.py +14 -0
  351. ccxt/static_dependencies/lark/ast_utils.py +59 -0
  352. ccxt/static_dependencies/lark/common.py +86 -0
  353. ccxt/static_dependencies/lark/exceptions.py +292 -0
  354. ccxt/static_dependencies/lark/grammar.py +130 -0
  355. ccxt/static_dependencies/lark/grammars/__init__.py +0 -0
  356. ccxt/static_dependencies/lark/indenter.py +143 -0
  357. ccxt/static_dependencies/lark/lark.py +658 -0
  358. ccxt/static_dependencies/lark/lexer.py +678 -0
  359. ccxt/static_dependencies/lark/load_grammar.py +1428 -0
  360. ccxt/static_dependencies/lark/parse_tree_builder.py +391 -0
  361. ccxt/static_dependencies/lark/parser_frontends.py +257 -0
  362. ccxt/static_dependencies/lark/parsers/__init__.py +0 -0
  363. ccxt/static_dependencies/lark/parsers/cyk.py +340 -0
  364. ccxt/static_dependencies/lark/parsers/earley.py +314 -0
  365. ccxt/static_dependencies/lark/parsers/earley_common.py +42 -0
  366. ccxt/static_dependencies/lark/parsers/earley_forest.py +801 -0
  367. ccxt/static_dependencies/lark/parsers/grammar_analysis.py +203 -0
  368. ccxt/static_dependencies/lark/parsers/lalr_analysis.py +332 -0
  369. ccxt/static_dependencies/lark/parsers/lalr_interactive_parser.py +158 -0
  370. ccxt/static_dependencies/lark/parsers/lalr_parser.py +122 -0
  371. ccxt/static_dependencies/lark/parsers/lalr_parser_state.py +110 -0
  372. ccxt/static_dependencies/lark/parsers/xearley.py +165 -0
  373. ccxt/static_dependencies/lark/py.typed +0 -0
  374. ccxt/static_dependencies/lark/reconstruct.py +107 -0
  375. ccxt/static_dependencies/lark/tools/__init__.py +70 -0
  376. ccxt/static_dependencies/lark/tools/nearley.py +202 -0
  377. ccxt/static_dependencies/lark/tools/serialize.py +32 -0
  378. ccxt/static_dependencies/lark/tools/standalone.py +196 -0
  379. ccxt/static_dependencies/lark/tree.py +267 -0
  380. ccxt/static_dependencies/lark/tree_matcher.py +186 -0
  381. ccxt/static_dependencies/lark/tree_templates.py +180 -0
  382. ccxt/static_dependencies/lark/utils.py +343 -0
  383. ccxt/static_dependencies/lark/visitors.py +596 -0
  384. ccxt/static_dependencies/marshmallow/__init__.py +81 -0
  385. ccxt/static_dependencies/marshmallow/base.py +65 -0
  386. ccxt/static_dependencies/marshmallow/class_registry.py +94 -0
  387. ccxt/static_dependencies/marshmallow/decorators.py +231 -0
  388. ccxt/static_dependencies/marshmallow/error_store.py +60 -0
  389. ccxt/static_dependencies/marshmallow/exceptions.py +71 -0
  390. ccxt/static_dependencies/marshmallow/fields.py +2114 -0
  391. ccxt/static_dependencies/marshmallow/orderedset.py +89 -0
  392. ccxt/static_dependencies/marshmallow/py.typed +0 -0
  393. ccxt/static_dependencies/marshmallow/schema.py +1228 -0
  394. ccxt/static_dependencies/marshmallow/types.py +12 -0
  395. ccxt/static_dependencies/marshmallow/utils.py +378 -0
  396. ccxt/static_dependencies/marshmallow/validate.py +678 -0
  397. ccxt/static_dependencies/marshmallow/warnings.py +2 -0
  398. ccxt/static_dependencies/marshmallow_dataclass/__init__.py +1047 -0
  399. ccxt/static_dependencies/marshmallow_dataclass/collection_field.py +51 -0
  400. ccxt/static_dependencies/marshmallow_dataclass/lazy_class_attribute.py +45 -0
  401. ccxt/static_dependencies/marshmallow_dataclass/mypy.py +71 -0
  402. ccxt/static_dependencies/marshmallow_dataclass/py.typed +0 -0
  403. ccxt/static_dependencies/marshmallow_dataclass/typing.py +14 -0
  404. ccxt/static_dependencies/marshmallow_dataclass/union_field.py +82 -0
  405. ccxt/static_dependencies/marshmallow_oneofschema/__init__.py +1 -0
  406. ccxt/static_dependencies/marshmallow_oneofschema/one_of_schema.py +193 -0
  407. ccxt/static_dependencies/marshmallow_oneofschema/py.typed +0 -0
  408. ccxt/static_dependencies/starknet/__init__.py +0 -0
  409. ccxt/static_dependencies/starknet/cairo/__init__.py +0 -0
  410. ccxt/static_dependencies/starknet/cairo/data_types.py +123 -0
  411. ccxt/static_dependencies/starknet/cairo/deprecated_parse/__init__.py +0 -0
  412. ccxt/static_dependencies/starknet/cairo/deprecated_parse/cairo_types.py +77 -0
  413. ccxt/static_dependencies/starknet/cairo/deprecated_parse/parser.py +46 -0
  414. ccxt/static_dependencies/starknet/cairo/deprecated_parse/parser_transformer.py +138 -0
  415. ccxt/static_dependencies/starknet/cairo/felt.py +64 -0
  416. ccxt/static_dependencies/starknet/cairo/type_parser.py +121 -0
  417. ccxt/static_dependencies/starknet/cairo/v1/__init__.py +0 -0
  418. ccxt/static_dependencies/starknet/cairo/v1/type_parser.py +59 -0
  419. ccxt/static_dependencies/starknet/cairo/v2/__init__.py +0 -0
  420. ccxt/static_dependencies/starknet/cairo/v2/type_parser.py +77 -0
  421. ccxt/static_dependencies/starknet/ccxt_utils.py +7 -0
  422. ccxt/static_dependencies/starknet/common.py +15 -0
  423. ccxt/static_dependencies/starknet/constants.py +39 -0
  424. ccxt/static_dependencies/starknet/hash/__init__.py +0 -0
  425. ccxt/static_dependencies/starknet/hash/address.py +79 -0
  426. ccxt/static_dependencies/starknet/hash/compiled_class_hash_objects.py +111 -0
  427. ccxt/static_dependencies/starknet/hash/selector.py +16 -0
  428. ccxt/static_dependencies/starknet/hash/storage.py +12 -0
  429. ccxt/static_dependencies/starknet/hash/utils.py +78 -0
  430. ccxt/static_dependencies/starknet/models/__init__.py +0 -0
  431. ccxt/static_dependencies/starknet/models/typed_data.py +45 -0
  432. ccxt/static_dependencies/starknet/serialization/__init__.py +24 -0
  433. ccxt/static_dependencies/starknet/serialization/_calldata_reader.py +40 -0
  434. ccxt/static_dependencies/starknet/serialization/_context.py +142 -0
  435. ccxt/static_dependencies/starknet/serialization/data_serializers/__init__.py +10 -0
  436. ccxt/static_dependencies/starknet/serialization/data_serializers/_common.py +82 -0
  437. ccxt/static_dependencies/starknet/serialization/data_serializers/array_serializer.py +43 -0
  438. ccxt/static_dependencies/starknet/serialization/data_serializers/bool_serializer.py +37 -0
  439. ccxt/static_dependencies/starknet/serialization/data_serializers/byte_array_serializer.py +66 -0
  440. ccxt/static_dependencies/starknet/serialization/data_serializers/cairo_data_serializer.py +71 -0
  441. ccxt/static_dependencies/starknet/serialization/data_serializers/enum_serializer.py +71 -0
  442. ccxt/static_dependencies/starknet/serialization/data_serializers/felt_serializer.py +50 -0
  443. ccxt/static_dependencies/starknet/serialization/data_serializers/named_tuple_serializer.py +58 -0
  444. ccxt/static_dependencies/starknet/serialization/data_serializers/option_serializer.py +43 -0
  445. ccxt/static_dependencies/starknet/serialization/data_serializers/output_serializer.py +40 -0
  446. ccxt/static_dependencies/starknet/serialization/data_serializers/payload_serializer.py +72 -0
  447. ccxt/static_dependencies/starknet/serialization/data_serializers/struct_serializer.py +36 -0
  448. ccxt/static_dependencies/starknet/serialization/data_serializers/tuple_serializer.py +36 -0
  449. ccxt/static_dependencies/starknet/serialization/data_serializers/uint256_serializer.py +76 -0
  450. ccxt/static_dependencies/starknet/serialization/data_serializers/uint_serializer.py +100 -0
  451. ccxt/static_dependencies/starknet/serialization/data_serializers/unit_serializer.py +32 -0
  452. ccxt/static_dependencies/starknet/serialization/errors.py +10 -0
  453. ccxt/static_dependencies/starknet/serialization/factory.py +229 -0
  454. ccxt/static_dependencies/starknet/serialization/function_serialization_adapter.py +110 -0
  455. ccxt/static_dependencies/starknet/serialization/tuple_dataclass.py +59 -0
  456. ccxt/static_dependencies/starknet/utils/__init__.py +0 -0
  457. ccxt/static_dependencies/starknet/utils/constructor_args_translator.py +86 -0
  458. ccxt/static_dependencies/starknet/utils/iterable.py +13 -0
  459. ccxt/static_dependencies/starknet/utils/schema.py +13 -0
  460. ccxt/static_dependencies/starknet/utils/typed_data.py +182 -0
  461. ccxt/static_dependencies/starkware/__init__.py +0 -0
  462. ccxt/static_dependencies/starkware/crypto/__init__.py +0 -0
  463. ccxt/static_dependencies/starkware/crypto/fast_pedersen_hash.py +50 -0
  464. ccxt/static_dependencies/starkware/crypto/math_utils.py +78 -0
  465. ccxt/static_dependencies/starkware/crypto/signature.py +2344 -0
  466. ccxt/static_dependencies/starkware/crypto/utils.py +63 -0
  467. ccxt/static_dependencies/sympy/__init__.py +0 -0
  468. ccxt/static_dependencies/sympy/core/__init__.py +0 -0
  469. ccxt/static_dependencies/sympy/core/intfunc.py +35 -0
  470. ccxt/static_dependencies/sympy/external/__init__.py +0 -0
  471. ccxt/static_dependencies/sympy/external/gmpy.py +345 -0
  472. ccxt/static_dependencies/sympy/external/importtools.py +187 -0
  473. ccxt/static_dependencies/sympy/external/ntheory.py +637 -0
  474. ccxt/static_dependencies/sympy/external/pythonmpq.py +341 -0
  475. ccxt/static_dependencies/typing_inspect/__init__.py +0 -0
  476. ccxt/static_dependencies/typing_inspect/typing_inspect.py +851 -0
  477. ccxt/test/{test_async.py → tests_async.py} +456 -391
  478. ccxt/test/tests_helpers.py +285 -0
  479. ccxt/test/tests_init.py +39 -0
  480. ccxt/test/{test_sync.py → tests_sync.py} +456 -393
  481. ccxt/timex.py +123 -70
  482. ccxt/tokocrypto.py +129 -93
  483. ccxt/tradeogre.py +39 -25
  484. ccxt/upbit.py +322 -113
  485. ccxt/vertex.py +2983 -0
  486. ccxt/wavesexchange.py +227 -173
  487. ccxt/wazirx.py +145 -65
  488. ccxt/whitebit.py +533 -138
  489. ccxt/woo.py +1137 -296
  490. ccxt/woofipro.py +2716 -0
  491. ccxt/xt.py +4627 -0
  492. ccxt/yobit.py +159 -92
  493. ccxt/zaif.py +80 -33
  494. ccxt/zonda.py +140 -69
  495. ccxt-4.4.48.dist-info/LICENSE.txt +21 -0
  496. ccxt-4.4.48.dist-info/METADATA +646 -0
  497. ccxt-4.4.48.dist-info/RECORD +669 -0
  498. {ccxt-4.2.77.dist-info → ccxt-4.4.48.dist-info}/WHEEL +1 -1
  499. ccxt/abstract/bitbay.py +0 -47
  500. ccxt/abstract/bitfinex2.py +0 -139
  501. ccxt/abstract/hitbtc3.py +0 -115
  502. ccxt/async_support/bitbay.py +0 -17
  503. ccxt/async_support/bitfinex2.py +0 -3496
  504. ccxt/async_support/flowbtc.py +0 -34
  505. ccxt/bitbay.py +0 -17
  506. ccxt/bitfinex2.py +0 -3496
  507. ccxt/flowbtc.py +0 -34
  508. ccxt/hitbtc3.py +0 -16
  509. ccxt/pro/bitfinex2.py +0 -1081
  510. ccxt/test/base/__init__.py +0 -28
  511. ccxt/test/base/test_account.py +0 -26
  512. ccxt/test/base/test_balance.py +0 -56
  513. ccxt/test/base/test_borrow_interest.py +0 -35
  514. ccxt/test/base/test_borrow_rate.py +0 -32
  515. ccxt/test/base/test_calculate_fee.py +0 -51
  516. ccxt/test/base/test_crypto.py +0 -127
  517. ccxt/test/base/test_currency.py +0 -76
  518. ccxt/test/base/test_datetime.py +0 -103
  519. ccxt/test/base/test_decimal_to_precision.py +0 -392
  520. ccxt/test/base/test_deep_extend.py +0 -68
  521. ccxt/test/base/test_deposit_withdrawal.py +0 -50
  522. ccxt/test/base/test_exchange_datetime_functions.py +0 -76
  523. ccxt/test/base/test_funding_rate_history.py +0 -29
  524. ccxt/test/base/test_last_price.py +0 -32
  525. ccxt/test/base/test_ledger_entry.py +0 -45
  526. ccxt/test/base/test_ledger_item.py +0 -48
  527. ccxt/test/base/test_leverage_tier.py +0 -33
  528. ccxt/test/base/test_margin_mode.py +0 -24
  529. ccxt/test/base/test_margin_modification.py +0 -35
  530. ccxt/test/base/test_market.py +0 -190
  531. ccxt/test/base/test_number.py +0 -411
  532. ccxt/test/base/test_ohlcv.py +0 -32
  533. ccxt/test/base/test_open_interest.py +0 -32
  534. ccxt/test/base/test_order.py +0 -64
  535. ccxt/test/base/test_order_book.py +0 -63
  536. ccxt/test/base/test_position.py +0 -60
  537. ccxt/test/base/test_shared_methods.py +0 -345
  538. ccxt/test/base/test_status.py +0 -24
  539. ccxt/test/base/test_throttle.py +0 -126
  540. ccxt/test/base/test_ticker.py +0 -86
  541. ccxt/test/base/test_trade.py +0 -47
  542. ccxt/test/base/test_trading_fee.py +0 -26
  543. ccxt/test/base/test_transaction.py +0 -39
  544. ccxt-4.2.77.dist-info/METADATA +0 -626
  545. ccxt-4.2.77.dist-info/RECORD +0 -534
  546. {ccxt-4.2.77.dist-info → ccxt-4.4.48.dist-info}/top_level.txt +0 -0
ccxt/bitget.py CHANGED
@@ -7,9 +7,10 @@ from ccxt.base.exchange import Exchange
7
7
  from ccxt.abstract.bitget import ImplicitAPI
8
8
  import hashlib
9
9
  import json
10
- from ccxt.base.types import Balances, Currency, FundingHistory, Int, Leverage, Liquidation, MarginMode, Market, Num, Order, OrderBook, OrderRequest, OrderSide, OrderType, Position, Str, Strings, Ticker, Tickers, Trade, Transaction, TransferEntry
10
+ from ccxt.base.types import Balances, BorrowInterest, Conversion, CrossBorrowRate, Currencies, Currency, DepositAddress, FundingHistory, Int, IsolatedBorrowRate, LedgerEntry, Leverage, LeverageTier, Liquidation, LongShortRatio, MarginMode, MarginModification, Market, Num, Order, OrderBook, OrderRequest, OrderSide, OrderType, Position, Str, Strings, Ticker, Tickers, FundingRate, FundingRates, Trade, TradingFeeInterface, TradingFees, Transaction, TransferEntry
11
11
  from typing import List
12
12
  from ccxt.base.errors import ExchangeError
13
+ from ccxt.base.errors import AuthenticationError
13
14
  from ccxt.base.errors import PermissionDenied
14
15
  from ccxt.base.errors import AccountSuspended
15
16
  from ccxt.base.errors import ArgumentsRequired
@@ -19,7 +20,6 @@ from ccxt.base.errors import InsufficientFunds
19
20
  from ccxt.base.errors import InvalidAddress
20
21
  from ccxt.base.errors import InvalidOrder
21
22
  from ccxt.base.errors import OrderNotFound
22
- from ccxt.base.errors import CancelPending
23
23
  from ccxt.base.errors import NotSupported
24
24
  from ccxt.base.errors import DDoSProtection
25
25
  from ccxt.base.errors import RateLimitExceeded
@@ -27,7 +27,7 @@ from ccxt.base.errors import ExchangeNotAvailable
27
27
  from ccxt.base.errors import OnMaintenance
28
28
  from ccxt.base.errors import InvalidNonce
29
29
  from ccxt.base.errors import RequestTimeout
30
- from ccxt.base.errors import AuthenticationError
30
+ from ccxt.base.errors import CancelPending
31
31
  from ccxt.base.decimal_to_precision import TICK_SIZE
32
32
  from ccxt.base.precise import Precise
33
33
 
@@ -58,6 +58,7 @@ class bitget(Exchange, ImplicitAPI):
58
58
  'cancelOrders': True,
59
59
  'closeAllPositions': True,
60
60
  'closePosition': True,
61
+ 'createConvertTrade': True,
61
62
  'createDepositAddress': False,
62
63
  'createMarketBuyOrderWithCost': True,
63
64
  'createMarketOrderWithCost': False,
@@ -84,20 +85,27 @@ class bitget(Exchange, ImplicitAPI):
84
85
  'fetchCanceledAndClosedOrders': True,
85
86
  'fetchCanceledOrders': True,
86
87
  'fetchClosedOrders': True,
88
+ 'fetchConvertCurrencies': True,
89
+ 'fetchConvertQuote': True,
90
+ 'fetchConvertTrade': False,
91
+ 'fetchConvertTradeHistory': True,
87
92
  'fetchCrossBorrowRate': True,
88
93
  'fetchCrossBorrowRates': False,
89
94
  'fetchCurrencies': True,
90
95
  'fetchDeposit': False,
91
96
  'fetchDepositAddress': True,
92
97
  'fetchDepositAddresses': False,
98
+ 'fetchDepositAddressesByNetwork': False,
93
99
  'fetchDeposits': True,
94
100
  'fetchDepositsWithdrawals': False,
95
101
  'fetchDepositWithdrawFee': 'emulated',
96
102
  'fetchDepositWithdrawFees': True,
97
103
  'fetchFundingHistory': True,
104
+ 'fetchFundingInterval': True,
105
+ 'fetchFundingIntervals': False,
98
106
  'fetchFundingRate': True,
99
107
  'fetchFundingRateHistory': True,
100
- 'fetchFundingRates': False,
108
+ 'fetchFundingRates': True,
101
109
  'fetchIndexOHLCV': True,
102
110
  'fetchIsolatedBorrowRate': True,
103
111
  'fetchIsolatedBorrowRates': False,
@@ -105,10 +113,14 @@ class bitget(Exchange, ImplicitAPI):
105
113
  'fetchLeverage': True,
106
114
  'fetchLeverageTiers': False,
107
115
  'fetchLiquidations': False,
116
+ 'fetchLongShortRatio': False,
117
+ 'fetchLongShortRatioHistory': True,
118
+ 'fetchMarginAdjustmentHistory': False,
108
119
  'fetchMarginMode': True,
109
120
  'fetchMarketLeverageTiers': True,
110
121
  'fetchMarkets': True,
111
122
  'fetchMarkOHLCV': True,
123
+ 'fetchMarkPrice': True,
112
124
  'fetchMyLiquidations': True,
113
125
  'fetchMyTrades': True,
114
126
  'fetchOHLCV': True,
@@ -121,8 +133,10 @@ class bitget(Exchange, ImplicitAPI):
121
133
  'fetchOrders': False,
122
134
  'fetchOrderTrades': False,
123
135
  'fetchPosition': True,
136
+ 'fetchPositionHistory': 'emulated',
124
137
  'fetchPositionMode': False,
125
138
  'fetchPositions': True,
139
+ 'fetchPositionsHistory': True,
126
140
  'fetchPositionsRisk': False,
127
141
  'fetchPremiumIndexOHLCV': False,
128
142
  'fetchStatus': False,
@@ -167,7 +181,7 @@ class bitget(Exchange, ImplicitAPI):
167
181
  },
168
182
  'hostname': 'bitget.com',
169
183
  'urls': {
170
- 'logo': 'https://user-images.githubusercontent.com/1294454/195989417-4253ddb0-afbe-4a1c-9dea-9dbcd121fa5d.jpg',
184
+ 'logo': 'https://github.com/user-attachments/assets/fbaa10cc-a277-441d-a5b7-997dd9a87658',
171
185
  'api': {
172
186
  'spot': 'https://api.{hostname}',
173
187
  'mix': 'https://api.{hostname}',
@@ -276,6 +290,7 @@ class bitget(Exchange, ImplicitAPI):
276
290
  'v2/mix/market/current-fund-rate': 1,
277
291
  'v2/mix/market/contracts': 1,
278
292
  'v2/mix/market/query-position-lever': 2,
293
+ 'v2/mix/market/account-long-short': 20,
279
294
  },
280
295
  },
281
296
  'margin': {
@@ -286,6 +301,7 @@ class bitget(Exchange, ImplicitAPI):
286
301
  'margin/v1/isolated/public/tierData': 2, # 10 times/1s(IP) => 20/10 = 2
287
302
  'margin/v1/public/currencies': 1, # 20 times/1s(IP) => 20/20 = 1
288
303
  'v2/margin/currencies': 2,
304
+ 'v2/margin/market/long-short-ratio': 20,
289
305
  },
290
306
  },
291
307
  'earn': {
@@ -323,6 +339,9 @@ class bitget(Exchange, ImplicitAPI):
323
339
  'v2/spot/account/subaccount-assets': 2,
324
340
  'v2/spot/account/bills': 2,
325
341
  'v2/spot/account/transferRecords': 1,
342
+ 'v2/account/funding-assets': 2,
343
+ 'v2/account/bot-assets': 2,
344
+ 'v2/account/all-account-balance': 20,
326
345
  'v2/spot/wallet/deposit-address': 2,
327
346
  'v2/spot/wallet/deposit-records': 2,
328
347
  'v2/spot/wallet/withdrawal-records': 2,
@@ -445,6 +464,7 @@ class bitget(Exchange, ImplicitAPI):
445
464
  'v2/mix/order/orders-history': 2,
446
465
  'v2/mix/order/orders-plan-pending': 2,
447
466
  'v2/mix/order/orders-plan-history': 2,
467
+ 'v2/mix/market/position-long-short': 20,
448
468
  },
449
469
  'post': {
450
470
  'mix/v1/account/sub-account-contract-assets': 200, # 0.1 times/1s(UID) => 20/0.1 = 200
@@ -493,7 +513,7 @@ class bitget(Exchange, ImplicitAPI):
493
513
  'v2/mix/account/set-margin': 4,
494
514
  'v2/mix/account/set-margin-mode': 4,
495
515
  'v2/mix/account/set-position-mode': 4,
496
- 'v2/mix/order/place-order': 20,
516
+ 'v2/mix/order/place-order': 2,
497
517
  'v2/mix/order/click-backhand': 20,
498
518
  'v2/mix/order/batch-place-order': 20,
499
519
  'v2/mix/order/modify-order': 2,
@@ -767,6 +787,7 @@ class bitget(Exchange, ImplicitAPI):
767
787
  'v2/earn/loan/borrow-history': 2,
768
788
  'v2/earn/loan/debts': 2,
769
789
  'v2/earn/loan/reduces': 2,
790
+ 'v2/earn/account/assets': 2,
770
791
  },
771
792
  'post': {
772
793
  'v2/earn/savings/subscribe': 2,
@@ -1237,9 +1258,14 @@ class bitget(Exchange, ImplicitAPI):
1237
1258
  '40712': InsufficientFunds, # Insufficient margin
1238
1259
  '40713': ExchangeError, # Cannot exceed the maximum transferable margin amount
1239
1260
  '40714': ExchangeError, # No direct margin call is allowed
1240
- '40768': OrderNotFound, # Order does not exist"
1261
+ '40762': InsufficientFunds, # {"code":"40762","msg":"The order amount exceeds the balance","requestTime":1716572156622,"data":null}
1262
+ '40768': OrderNotFound, # Order does not exist
1263
+ '40808': InvalidOrder, # {"code":"40808","msg":"Parameter verification exception size checkBDScale error value=2293.577 checkScale=2","requestTime":1725638500052,"data":null}
1264
+ '41103': InvalidOrder, # {"code":"41103","msg":"param price scale error error","requestTime":1725635883561,"data":null}
1241
1265
  '41114': OnMaintenance, # {"code":"41114","msg":"The current trading pair is under maintenance, please refer to the official announcement for the opening time","requestTime":1679196062544,"data":null}
1242
1266
  '43011': InvalidOrder, # The parameter does not meet the specification executePrice <= 0
1267
+ '43001': OrderNotFound,
1268
+ '43012': InsufficientFunds, # {"code":"43012","msg":"Insufficient balance","requestTime":1711648951774,"data":null}
1243
1269
  '43025': InvalidOrder, # Plan order does not exist
1244
1270
  '43115': OnMaintenance, # {"code":"43115","msg":"The current trading pair is opening soon, please refer to the official announcement for the opening time","requestTime":1688907202434,"data":null}
1245
1271
  '45110': InvalidOrder, # {"code":"45110","msg":"less than the minimum amount 5 USDT","requestTime":1669911118932,"data":null}
@@ -1313,9 +1339,15 @@ class bitget(Exchange, ImplicitAPI):
1313
1339
  },
1314
1340
  'precisionMode': TICK_SIZE,
1315
1341
  'commonCurrencies': {
1342
+ 'APX': 'AstroPepeX',
1343
+ 'DEGEN': 'DegenReborn',
1316
1344
  'JADE': 'Jade Protocol',
1345
+ 'OMNI': 'omni', # conflict with Omni Network
1346
+ 'TONCOIN': 'TON',
1317
1347
  },
1318
1348
  'options': {
1349
+ 'timeDifference': 0, # the difference between system clock and Binance clock
1350
+ 'adjustForTimeDifference': False, # controls the adjustment logic upon instantiation
1319
1351
  'timeframes': {
1320
1352
  'spot': {
1321
1353
  '1m': '1min',
@@ -1412,19 +1444,243 @@ class bitget(Exchange, ImplicitAPI):
1412
1444
  },
1413
1445
  'sandboxMode': False,
1414
1446
  'networks': {
1415
- 'TRX': 'TRC20',
1416
- 'ETH': 'ERC20',
1447
+ # 'TRX': 'TRX', # different code for mainnet
1448
+ 'TRC20': 'TRC20',
1449
+ # 'ETH': 'ETH', # different code for mainnet
1450
+ 'ERC20': 'ERC20',
1451
+ 'BEP20': 'BSC',
1452
+ # 'BEP20': 'BEP20', # different for BEP20
1417
1453
  'BSC': 'BEP20',
1454
+ 'ATOM': 'ATOM',
1455
+ 'ACA': 'AcalaToken',
1456
+ 'APT': 'Aptos',
1457
+ 'ARBONE': 'ArbitrumOne',
1458
+ 'ARBNOVA': 'ArbitrumNova',
1459
+ 'AVAXC': 'C-Chain',
1460
+ 'AVAXX': 'X-Chain',
1461
+ 'AR': 'Arweave',
1462
+ 'BCH': 'BCH',
1463
+ 'BCHA': 'BCHA',
1464
+ 'BITCI': 'BITCI',
1465
+ 'BTC': 'BTC',
1466
+ 'CELO': 'CELO',
1467
+ 'CSPR': 'CSPR',
1468
+ 'ADA': 'Cardano',
1469
+ 'CHZ': 'ChilizChain',
1470
+ 'CRC20': 'CronosChain',
1471
+ 'DOGE': 'DOGE',
1472
+ 'DOT': 'DOT',
1473
+ 'EOS': 'EOS',
1474
+ 'ETHF': 'ETHFAIR',
1475
+ 'ETHW': 'ETHW',
1476
+ 'ETC': 'ETC',
1477
+ 'EGLD': 'Elrond',
1478
+ 'FIL': 'FIL',
1479
+ 'FIO': 'FIO',
1480
+ 'FTM': 'Fantom',
1481
+ 'HRC20': 'HECO',
1482
+ 'ONE': 'Harmony',
1483
+ 'HNT': 'Helium',
1484
+ 'ICP': 'ICP',
1485
+ 'IOTX': 'IoTeX',
1486
+ 'KARDIA': 'KAI',
1487
+ 'KAVA': 'KAVA',
1488
+ 'KDA': 'KDA',
1489
+ 'KLAY': 'Klaytn',
1490
+ 'KSM': 'Kusama',
1491
+ 'LAT': 'LAT',
1492
+ 'LTC': 'LTC',
1493
+ 'MINA': 'MINA',
1494
+ 'MOVR': 'MOVR',
1495
+ 'METIS': 'MetisToken',
1496
+ 'GLMR': 'Moonbeam',
1497
+ 'NEAR': 'NEARProtocol',
1498
+ 'NULS': 'NULS',
1499
+ 'OASYS': 'OASYS',
1500
+ 'OASIS': 'ROSE',
1501
+ 'OMNI': 'OMNI',
1502
+ 'ONT': 'Ontology',
1503
+ 'OPTIMISM': 'Optimism',
1504
+ 'OSMO': 'Osmosis',
1505
+ 'POKT': 'PocketNetwork',
1506
+ 'MATIC': 'Polygon',
1507
+ 'QTUM': 'QTUM',
1508
+ 'REEF': 'REEF',
1509
+ 'SOL': 'SOL',
1510
+ 'SYS': 'SYS', # SyscoinNEVM is different
1511
+ 'SXP': 'Solar',
1512
+ 'XYM': 'Symbol',
1513
+ 'TON': 'TON',
1514
+ 'TT': 'TT',
1515
+ 'TLOS': 'Telos',
1516
+ 'THETA': 'ThetaToken',
1517
+ 'VITE': 'VITE',
1518
+ 'WAVES': 'WAVES',
1519
+ 'WAX': 'WAXP',
1520
+ 'WEMIX': 'WEMIXMainnet',
1521
+ 'XDC': 'XDCNetworkXDC',
1522
+ 'XRP': 'XRP',
1523
+ 'FET': 'FETCH',
1524
+ 'NEM': 'NEM',
1525
+ 'REI': 'REINetwork',
1526
+ 'ZIL': 'ZIL',
1527
+ 'ABBC': 'ABBCCoin',
1528
+ 'RSK': 'RSK',
1529
+ 'AZERO': 'AZERO',
1530
+ 'TRC10': 'TRC10',
1531
+ 'JUNO': 'JUNO',
1532
+ # undetected: USDSP, more info at https://www.bitget.com/v1/spot/public/coinChainList
1533
+ # todo: uncomment below after unification
1534
+ # 'TERRACLASSIC': 'Terra', # tbd, that network id is also assigned to TERRANEW network
1535
+ # 'CUBENETWORK': 'CUBE',
1536
+ # 'CADUCEUS': 'CMP',
1537
+ # 'CONFLUX': 'CFX', # CFXeSpace is different
1538
+ # 'CERE': 'CERE',
1539
+ # 'CANTO': 'CANTO',
1540
+ 'ZKSYNC': 'zkSyncEra',
1541
+ 'STARKNET': 'Starknet',
1542
+ 'VIC': 'VICTION',
1418
1543
  },
1419
1544
  'networksById': {
1420
- 'TRC20': 'TRX',
1421
- 'BSC': 'BEP20',
1422
1545
  },
1423
1546
  'fetchPositions': {
1424
1547
  'method': 'privateMixGetV2MixPositionAllPosition', # or privateMixGetV2MixPositionHistoryPosition
1425
1548
  },
1426
1549
  'defaultTimeInForce': 'GTC', # 'GTC' = Good To Cancel(default), 'IOC' = Immediate Or Cancel
1427
1550
  },
1551
+ 'features': {
1552
+ 'spot': {
1553
+ 'sandbox': True,
1554
+ 'createOrder': {
1555
+ 'marginMode': True,
1556
+ 'triggerPrice': True,
1557
+ 'triggerPriceType': {
1558
+ 'last': True,
1559
+ 'mark': True,
1560
+ 'index': False, # not on spot
1561
+ },
1562
+ 'triggerDirection': False,
1563
+ 'stopLossPrice': True, # todo: not yet implemented in spot
1564
+ 'takeProfitPrice': True, # todo: not yet implemented in spot
1565
+ 'attachedStopLossTakeProfit': {
1566
+ 'triggerPriceType': {
1567
+ 'last': False,
1568
+ 'mark': False,
1569
+ 'index': False,
1570
+ },
1571
+ 'price': True,
1572
+ },
1573
+ 'timeInForce': {
1574
+ 'IOC': True,
1575
+ 'FOK': True,
1576
+ 'PO': True,
1577
+ 'GTD': False,
1578
+ },
1579
+ 'hedged': False,
1580
+ 'trailing': False,
1581
+ 'marketBuyRequiresPrice': True,
1582
+ 'marketBuyByCost': True,
1583
+ # exchange-supported features
1584
+ # 'selfTradePrevention': True,
1585
+ # 'twap': False,
1586
+ # 'iceberg': False,
1587
+ # 'oco': False,
1588
+ },
1589
+ 'createOrders': {
1590
+ 'max': 50,
1591
+ },
1592
+ 'fetchMyTrades': {
1593
+ 'marginMode': True,
1594
+ 'limit': 100,
1595
+ 'daysBack': None,
1596
+ 'untilDays': 90,
1597
+ },
1598
+ 'fetchOrder': {
1599
+ 'marginMode': False,
1600
+ 'trigger': False,
1601
+ 'trailing': False,
1602
+ },
1603
+ 'fetchOpenOrders': {
1604
+ 'marginMode': True,
1605
+ 'limit': 100,
1606
+ 'trigger': True,
1607
+ 'trailing': False,
1608
+ },
1609
+ 'fetchOrders': None,
1610
+ 'fetchClosedOrders': {
1611
+ 'marginMode': True,
1612
+ 'limit': 100,
1613
+ 'daysBack': None,
1614
+ 'daysBackCanceled': None,
1615
+ 'untilDays': 90,
1616
+ 'trigger': True,
1617
+ 'trailing': False,
1618
+ },
1619
+ 'fetchOHLCV': {
1620
+ 'limit': 1000, # variable timespans for recent endpoint, 200 for historical
1621
+ },
1622
+ },
1623
+ 'forPerps': {
1624
+ 'extends': 'spot',
1625
+ 'createOrder': {
1626
+ 'triggerPrice': True,
1627
+ 'triggerPriceType': {
1628
+ 'last': True,
1629
+ 'mark': True,
1630
+ 'index': False, # not on spot
1631
+ },
1632
+ 'triggerDirection': False,
1633
+ 'stopLossPrice': True,
1634
+ 'takeProfitPrice': True,
1635
+ 'attachedStopLossTakeProfit': {
1636
+ 'triggerPriceType': {
1637
+ 'last': True,
1638
+ 'mark': True,
1639
+ 'index': True,
1640
+ },
1641
+ 'price': False,
1642
+ },
1643
+ 'timeInForce': {
1644
+ 'IOC': True,
1645
+ 'FOK': True,
1646
+ 'PO': True,
1647
+ 'GTD': False,
1648
+ },
1649
+ 'hedged': True,
1650
+ 'trailing': True,
1651
+ 'marketBuyRequiresPrice': False,
1652
+ 'marketBuyByCost': False,
1653
+ # exchange-supported features
1654
+ # 'selfTradePrevention': True,
1655
+ # 'trailing': True,
1656
+ # 'twap': False,
1657
+ # 'iceberg': False,
1658
+ # 'oco': False,
1659
+ },
1660
+ 'fetchMyTrades': {
1661
+ 'untilDays': 7,
1662
+ },
1663
+ 'fetchClosedOrders': {
1664
+ 'trailing': True,
1665
+ },
1666
+ },
1667
+ 'swap': {
1668
+ 'linear': {
1669
+ 'extends': 'forPerps',
1670
+ },
1671
+ 'inverse': {
1672
+ 'extends': 'forPerps',
1673
+ },
1674
+ },
1675
+ 'future': {
1676
+ 'linear': {
1677
+ 'extends': 'forPerps',
1678
+ },
1679
+ 'inverse': {
1680
+ 'extends': 'forPerps',
1681
+ },
1682
+ },
1683
+ },
1428
1684
  })
1429
1685
 
1430
1686
  def set_sandbox_mode(self, enabled):
@@ -1491,7 +1747,9 @@ class bitget(Exchange, ImplicitAPI):
1491
1747
  def fetch_time(self, params={}):
1492
1748
  """
1493
1749
  fetches the current integer timestamp in milliseconds from the exchange server
1494
- :see: https://www.bitget.com/api-doc/common/public/Get-Server-Time
1750
+
1751
+ https://www.bitget.com/api-doc/common/public/Get-Server-Time
1752
+
1495
1753
  :param dict [params]: extra parameters specific to the exchange API endpoint
1496
1754
  :returns int: the current integer timestamp in milliseconds from the exchange server
1497
1755
  """
@@ -1509,22 +1767,28 @@ class bitget(Exchange, ImplicitAPI):
1509
1767
  data = self.safe_value(response, 'data', {})
1510
1768
  return self.safe_integer(data, 'serverTime')
1511
1769
 
1512
- def fetch_markets(self, params={}):
1770
+ def fetch_markets(self, params={}) -> List[Market]:
1513
1771
  """
1514
1772
  retrieves data on all markets for bitget
1515
- :see: https://www.bitget.com/api-doc/spot/market/Get-Symbols
1516
- :see: https://www.bitget.com/api-doc/contract/market/Get-All-Symbols-Contracts
1773
+
1774
+ https://www.bitget.com/api-doc/spot/market/Get-Symbols
1775
+ https://www.bitget.com/api-doc/contract/market/Get-All-Symbols-Contracts
1776
+ https://www.bitget.com/api-doc/margin/common/support-currencies
1777
+
1517
1778
  :param dict [params]: extra parameters specific to the exchange API endpoint
1518
1779
  :returns dict[]: an array of objects representing market data
1519
1780
  """
1781
+ if self.options['adjustForTimeDifference']:
1782
+ self.load_time_difference()
1520
1783
  sandboxMode = self.safe_bool(self.options, 'sandboxMode', False)
1521
1784
  types = self.safe_value(self.options, 'fetchMarkets', ['spot', 'swap'])
1522
1785
  if sandboxMode:
1523
1786
  types = ['swap']
1524
1787
  promises = []
1788
+ fetchMargins = False
1525
1789
  for i in range(0, len(types)):
1526
1790
  type = types[i]
1527
- if type == 'swap':
1791
+ if (type == 'swap') or (type == 'future'):
1528
1792
  subTypes = None
1529
1793
  if sandboxMode:
1530
1794
  # the following are simulated trading markets ['SUSDT-FUTURES', 'SCOIN-FUTURES', 'SUSDC-FUTURES']
@@ -1532,18 +1796,36 @@ class bitget(Exchange, ImplicitAPI):
1532
1796
  else:
1533
1797
  subTypes = ['USDT-FUTURES', 'COIN-FUTURES', 'USDC-FUTURES']
1534
1798
  for j in range(0, len(subTypes)):
1535
- promises.append(self.fetch_markets_by_type(type, self.extend(params, {
1799
+ promises.append(self.publicMixGetV2MixMarketContracts(self.extend(params, {
1536
1800
  'productType': subTypes[j],
1537
1801
  })))
1802
+ elif type == 'spot':
1803
+ promises.append(self.publicSpotGetV2SpotPublicSymbols(params))
1804
+ fetchMargins = True
1805
+ promises.append(self.publicMarginGetV2MarginCurrencies(params))
1538
1806
  else:
1539
- promises.append(self.fetch_markets_by_type(types[i], params))
1540
- promises = promises
1541
- result = promises[0]
1542
- for i in range(1, len(promises)):
1543
- result = self.array_concat(result, promises[i])
1807
+ raise NotSupported(self.id + ' does not support ' + type + ' market')
1808
+ results = promises
1809
+ markets = []
1810
+ self.options['crossMarginPairsData'] = []
1811
+ self.options['isolatedMarginPairsData'] = []
1812
+ for i in range(0, len(results)):
1813
+ res = self.safe_dict(results, i)
1814
+ data = self.safe_list(res, 'data', [])
1815
+ firstData = self.safe_dict(data, 0, {})
1816
+ isBorrowable = self.safe_string(firstData, 'isBorrowable')
1817
+ if fetchMargins and isBorrowable is not None:
1818
+ keysList = list(self.index_by(data, 'symbol').keys())
1819
+ self.options['crossMarginPairsData'] = keysList
1820
+ self.options['isolatedMarginPairsData'] = keysList
1821
+ else:
1822
+ markets = self.array_concat(markets, data)
1823
+ result = []
1824
+ for i in range(0, len(markets)):
1825
+ result.append(self.parse_market(markets[i]))
1544
1826
  return result
1545
1827
 
1546
- def parse_market(self, market) -> Market:
1828
+ def parse_market(self, market: dict) -> Market:
1547
1829
  #
1548
1830
  # spot
1549
1831
  #
@@ -1628,11 +1910,20 @@ class bitget(Exchange, ImplicitAPI):
1628
1910
  expiry = None
1629
1911
  expiryDatetime = None
1630
1912
  symbolType = self.safe_string(market, 'symbolType')
1913
+ marginModes = None
1914
+ isMarginTradingAllowed = False
1631
1915
  if symbolType is None:
1632
1916
  type = 'spot'
1633
1917
  spot = True
1634
1918
  pricePrecision = self.parse_number(self.parse_precision(self.safe_string(market, 'pricePrecision')))
1635
1919
  amountPrecision = self.parse_number(self.parse_precision(self.safe_string(market, 'quantityPrecision')))
1920
+ hasCrossMargin = self.in_array(marketId, self.options['crossMarginPairsData'])
1921
+ hasIsolatedMargin = self.in_array(marketId, self.options['isolatedMarginPairsData'])
1922
+ marginModes = {
1923
+ 'cross': hasCrossMargin,
1924
+ 'isolated': hasIsolatedMargin,
1925
+ }
1926
+ isMarginTradingAllowed = hasCrossMargin or hasCrossMargin
1636
1927
  else:
1637
1928
  if symbolType == 'perpetual':
1638
1929
  type = 'swap'
@@ -1668,6 +1959,10 @@ class bitget(Exchange, ImplicitAPI):
1668
1959
  preciseAmount.reduce()
1669
1960
  amountString = str(preciseAmount)
1670
1961
  amountPrecision = self.parse_number(amountString)
1962
+ marginModes = {
1963
+ 'cross': True,
1964
+ 'isolated': True,
1965
+ }
1671
1966
  status = self.safe_string_2(market, 'status', 'symbolStatus')
1672
1967
  active = None
1673
1968
  if status is not None:
@@ -1687,7 +1982,8 @@ class bitget(Exchange, ImplicitAPI):
1687
1982
  'settleId': settleId,
1688
1983
  'type': type,
1689
1984
  'spot': spot,
1690
- 'margin': None,
1985
+ 'margin': spot and isMarginTradingAllowed,
1986
+ 'marginModes': marginModes,
1691
1987
  'swap': swap,
1692
1988
  'future': future,
1693
1989
  'option': False,
@@ -1728,92 +2024,12 @@ class bitget(Exchange, ImplicitAPI):
1728
2024
  'info': market,
1729
2025
  }
1730
2026
 
1731
- def fetch_markets_by_type(self, type, params={}):
1732
- response = None
1733
- if type == 'spot':
1734
- response = self.publicSpotGetV2SpotPublicSymbols(params)
1735
- elif (type == 'swap') or (type == 'future'):
1736
- response = self.publicMixGetV2MixMarketContracts(params)
1737
- else:
1738
- raise NotSupported(self.id + ' does not support ' + type + ' market')
1739
- #
1740
- # spot
1741
- #
1742
- # {
1743
- # "code": "00000",
1744
- # "msg": "success",
1745
- # "requestTime": 1700102364653,
1746
- # "data": [
1747
- # {
1748
- # "symbol": "TRXUSDT",
1749
- # "baseCoin": "TRX",
1750
- # "quoteCoin": "USDT",
1751
- # "minTradeAmount": "0",
1752
- # "maxTradeAmount": "10000000000",
1753
- # "takerFeeRate": "0.002",
1754
- # "makerFeeRate": "0.002",
1755
- # "pricePrecision": "6",
1756
- # "quantityPrecision": "4",
1757
- # "quotePrecision": "6",
1758
- # "status": "online",
1759
- # "minTradeUSDT": "5",
1760
- # "buyLimitPriceRatio": "0.05",
1761
- # "sellLimitPriceRatio": "0.05"
1762
- # },
1763
- # ]
1764
- # }
1765
- #
1766
- # swap and future
1767
- #
1768
- # {
1769
- # "code": "00000",
1770
- # "msg": "success",
1771
- # "requestTime": 1700102364709,
1772
- # "data": [
1773
- # {
1774
- # "symbol": "BTCUSDT",
1775
- # "baseCoin": "BTC",
1776
- # "quoteCoin": "USDT",
1777
- # "buyLimitPriceRatio": "0.01",
1778
- # "sellLimitPriceRatio": "0.01",
1779
- # "feeRateUpRatio": "0.005",
1780
- # "makerFeeRate": "0.0002",
1781
- # "takerFeeRate": "0.0006",
1782
- # "openCostUpRatio": "0.01",
1783
- # "supportMarginCoins": ["USDT"],
1784
- # "minTradeNum": "0.001",
1785
- # "priceEndStep": "1",
1786
- # "volumePlace": "3",
1787
- # "pricePlace": "1",
1788
- # "sizeMultiplier": "0.001",
1789
- # "symbolType": "perpetual",
1790
- # "minTradeUSDT": "5",
1791
- # "maxSymbolOrderNum": "200",
1792
- # "maxProductOrderNum": "400",
1793
- # "maxPositionNum": "150",
1794
- # "symbolStatus": "normal",
1795
- # "offTime": "-1",
1796
- # "limitOpenTime": "-1",
1797
- # "deliveryTime": "",
1798
- # "deliveryStartTime": "",
1799
- # "deliveryPeriod": "",
1800
- # "launchTime": "",
1801
- # "fundInterval": "8",
1802
- # "minLever": "1",
1803
- # "maxLever": "125",
1804
- # "posLimit": "0.05",
1805
- # "maintainTime": ""
1806
- # },
1807
- # ]
1808
- # }
1809
- #
1810
- data = self.safe_value(response, 'data', [])
1811
- return self.parse_markets(data)
1812
-
1813
- def fetch_currencies(self, params={}):
2027
+ def fetch_currencies(self, params={}) -> Currencies:
1814
2028
  """
1815
2029
  fetches all available currencies on an exchange
1816
- :see: https://www.bitget.com/api-doc/spot/market/Get-Coin-List
2030
+
2031
+ https://www.bitget.com/api-doc/spot/market/Get-Coin-List
2032
+
1817
2033
  :param dict [params]: extra parameters specific to the exchange API endpoint
1818
2034
  :returns dict: an associative dictionary of currencies
1819
2035
  """
@@ -1847,14 +2063,14 @@ class bitget(Exchange, ImplicitAPI):
1847
2063
  # "requestTime": "1700120731773"
1848
2064
  # }
1849
2065
  #
1850
- result = {}
2066
+ result: dict = {}
1851
2067
  data = self.safe_value(response, 'data', [])
1852
2068
  for i in range(0, len(data)):
1853
2069
  entry = data[i]
1854
- id = self.safe_string(entry, 'coinId')
1855
- code = self.safe_currency_code(self.safe_string(entry, 'coin'))
2070
+ id = self.safe_string(entry, 'coin') # we don't use 'coinId' has no use. it is 'coin' field that needs to be used in currency related endpoints(deposit, withdraw, etc..)
2071
+ code = self.safe_currency_code(id)
1856
2072
  chains = self.safe_value(entry, 'chains', [])
1857
- networks = {}
2073
+ networks: dict = {}
1858
2074
  deposit = False
1859
2075
  withdraw = False
1860
2076
  minWithdrawString = None
@@ -1863,7 +2079,9 @@ class bitget(Exchange, ImplicitAPI):
1863
2079
  for j in range(0, len(chains)):
1864
2080
  chain = chains[j]
1865
2081
  networkId = self.safe_string(chain, 'chain')
1866
- network = self.safe_currency_code(networkId)
2082
+ network = self.network_id_to_code(networkId, code)
2083
+ if network is not None:
2084
+ network = network.upper()
1867
2085
  withdrawEnabled = self.safe_string(chain, 'withdrawable')
1868
2086
  canWithdraw = withdrawEnabled == 'true'
1869
2087
  withdraw = canWithdraw if (canWithdraw) else withdraw
@@ -1929,12 +2147,14 @@ class bitget(Exchange, ImplicitAPI):
1929
2147
  }
1930
2148
  return result
1931
2149
 
1932
- def fetch_market_leverage_tiers(self, symbol: str, params={}):
2150
+ def fetch_market_leverage_tiers(self, symbol: str, params={}) -> List[LeverageTier]:
1933
2151
  """
1934
2152
  retrieve information on the maximum leverage, and maintenance margin for trades of varying trade sizes for a single market
1935
- :see: https://www.bitget.com/api-doc/contract/position/Get-Query-Position-Lever
1936
- :see: https://www.bitget.com/api-doc/margin/cross/account/Cross-Tier-Data
1937
- :see: https://www.bitget.com/api-doc/margin/isolated/account/Isolated-Tier-Data
2153
+
2154
+ https://www.bitget.com/api-doc/contract/position/Get-Query-Position-Lever
2155
+ https://www.bitget.com/api-doc/margin/cross/account/Cross-Tier-Data
2156
+ https://www.bitget.com/api-doc/margin/isolated/account/Isolated-Tier-Data
2157
+
1938
2158
  :param str symbol: unified market symbol
1939
2159
  :param dict [params]: extra parameters specific to the exchange API endpoint
1940
2160
  :param str [params.marginMode]: for spot margin 'cross' or 'isolated', default is 'isolated'
@@ -1950,7 +2170,7 @@ class bitget(Exchange, ImplicitAPI):
1950
2170
  market = self.market(sandboxSymbol)
1951
2171
  else:
1952
2172
  market = self.market(symbol)
1953
- request = {}
2173
+ request: dict = {}
1954
2174
  response = None
1955
2175
  marginMode = None
1956
2176
  marginMode, params = self.handle_margin_mode_and_params('fetchMarketLeverageTiers', params, 'isolated')
@@ -1969,7 +2189,7 @@ class bitget(Exchange, ImplicitAPI):
1969
2189
  raise ArgumentsRequired(self.id + ' fetchMarketLeverageTiers() requires a code argument')
1970
2190
  params = self.omit(params, 'code')
1971
2191
  currency = self.currency(code)
1972
- request['coin'] = currency['code']
2192
+ request['coin'] = currency['id']
1973
2193
  response = self.privateMarginGetV2MarginCrossedTierData(self.extend(request, params))
1974
2194
  else:
1975
2195
  raise BadRequest(self.id + ' fetchMarketLeverageTiers() symbol does not support market ' + market['symbol'])
@@ -2033,7 +2253,7 @@ class bitget(Exchange, ImplicitAPI):
2033
2253
  result = self.safe_value(response, 'data', [])
2034
2254
  return self.parse_market_leverage_tiers(result, market)
2035
2255
 
2036
- def parse_market_leverage_tiers(self, info, market: Market = None):
2256
+ def parse_market_leverage_tiers(self, info, market: Market = None) -> List[LeverageTier]:
2037
2257
  #
2038
2258
  # swap and future
2039
2259
  #
@@ -2080,8 +2300,10 @@ class bitget(Exchange, ImplicitAPI):
2080
2300
  maxNotional = self.safe_number_n(item, ['endUnit', 'maxBorrowableAmount', 'baseMaxBorrowableAmount'])
2081
2301
  marginCurrency = self.safe_string_2(item, 'coin', 'baseCoin')
2082
2302
  currencyId = marginCurrency if (marginCurrency is not None) else market['base']
2303
+ marketId = self.safe_string(item, 'symbol')
2083
2304
  tiers.append({
2084
2305
  'tier': self.safe_integer_2(item, 'level', 'tier'),
2306
+ 'symbol': self.safe_symbol(marketId, market),
2085
2307
  'currency': self.safe_currency_code(currencyId),
2086
2308
  'minNotional': minNotional,
2087
2309
  'maxNotional': maxNotional,
@@ -2095,7 +2317,9 @@ class bitget(Exchange, ImplicitAPI):
2095
2317
  def fetch_deposits(self, code: Str = None, since: Int = None, limit: Int = None, params={}) -> List[Transaction]:
2096
2318
  """
2097
2319
  fetch all deposits made to an account
2098
- :see: https://www.bitget.com/api-doc/spot/account/Get-Deposit-Record
2320
+
2321
+ https://www.bitget.com/api-doc/spot/account/Get-Deposit-Record
2322
+
2099
2323
  :param str code: unified currency code
2100
2324
  :param int [since]: the earliest time in ms to fetch deposits for
2101
2325
  :param int [limit]: the maximum number of deposits structures to retrieve
@@ -2115,8 +2339,8 @@ class bitget(Exchange, ImplicitAPI):
2115
2339
  currency = self.currency(code)
2116
2340
  if since is None:
2117
2341
  since = self.milliseconds() - 7776000000 # 90 days
2118
- request = {
2119
- 'coin': currency['code'],
2342
+ request: dict = {
2343
+ 'coin': currency['id'],
2120
2344
  'startTime': since,
2121
2345
  'endTime': self.milliseconds(),
2122
2346
  }
@@ -2147,13 +2371,15 @@ class bitget(Exchange, ImplicitAPI):
2147
2371
  # ]
2148
2372
  # }
2149
2373
  #
2150
- rawTransactions = self.safe_value(response, 'data', [])
2374
+ rawTransactions = self.safe_list(response, 'data', [])
2151
2375
  return self.parse_transactions(rawTransactions, currency, since, limit)
2152
2376
 
2153
- def withdraw(self, code: str, amount: float, address, tag=None, params={}):
2377
+ def withdraw(self, code: str, amount: float, address: str, tag=None, params={}) -> Transaction:
2154
2378
  """
2155
2379
  make a withdrawal
2156
- :see: https://www.bitget.com/api-doc/spot/account/Wallet-Withdrawal
2380
+
2381
+ https://www.bitget.com/api-doc/spot/account/Wallet-Withdrawal
2382
+
2157
2383
  :param str code: unified currency code
2158
2384
  :param float amount: the amount to withdraw
2159
2385
  :param str address: the address to withdraw to
@@ -2163,15 +2389,15 @@ class bitget(Exchange, ImplicitAPI):
2163
2389
  :returns dict: a `transaction structure <https://docs.ccxt.com/#/?id=transaction-structure>`
2164
2390
  """
2165
2391
  self.check_address(address)
2166
- chain = self.safe_string_2(params, 'chain', 'network')
2167
- params = self.omit(params, 'network')
2168
- if chain is None:
2169
- raise ArgumentsRequired(self.id + ' withdraw() requires a chain parameter or a network parameter')
2392
+ networkCode = None
2393
+ networkCode, params = self.handle_network_code_and_params(params)
2394
+ if networkCode is None:
2395
+ raise ArgumentsRequired(self.id + ' withdraw() requires a "network" parameter')
2170
2396
  self.load_markets()
2171
2397
  currency = self.currency(code)
2172
- networkId = self.network_code_to_id(chain)
2173
- request = {
2174
- 'coin': currency['code'],
2398
+ networkId = self.network_code_to_id(networkCode)
2399
+ request: dict = {
2400
+ 'coin': currency['id'],
2175
2401
  'address': address,
2176
2402
  'chain': networkId,
2177
2403
  'size': amount,
@@ -2192,27 +2418,8 @@ class bitget(Exchange, ImplicitAPI):
2192
2418
  # }
2193
2419
  #
2194
2420
  data = self.safe_value(response, 'data', {})
2195
- result = {
2196
- 'id': self.safe_string(data, 'orderId'),
2197
- 'info': response,
2198
- 'txid': None,
2199
- 'timestamp': None,
2200
- 'datetime': None,
2201
- 'network': None,
2202
- 'addressFrom': None,
2203
- 'address': None,
2204
- 'addressTo': None,
2205
- 'amount': None,
2206
- 'type': 'withdrawal',
2207
- 'currency': None,
2208
- 'status': None,
2209
- 'updated': None,
2210
- 'tagFrom': None,
2211
- 'tag': None,
2212
- 'tagTo': None,
2213
- 'comment': None,
2214
- 'fee': None,
2215
- }
2421
+ result = self.parse_transaction(data, currency)
2422
+ result['type'] = 'withdrawal'
2216
2423
  withdrawOptions = self.safe_value(self.options, 'withdraw', {})
2217
2424
  fillResponseFromRequest = self.safe_bool(withdrawOptions, 'fillResponseFromRequest', True)
2218
2425
  if fillResponseFromRequest:
@@ -2223,13 +2430,15 @@ class bitget(Exchange, ImplicitAPI):
2223
2430
  result['tag'] = tag
2224
2431
  result['address'] = address
2225
2432
  result['addressTo'] = address
2226
- result['network'] = chain
2433
+ result['network'] = networkCode
2227
2434
  return result
2228
2435
 
2229
2436
  def fetch_withdrawals(self, code: Str = None, since: Int = None, limit: Int = None, params={}) -> List[Transaction]:
2230
2437
  """
2231
2438
  fetch all withdrawals made from an account
2232
- :see: https://www.bitget.com/api-doc/spot/account/Get-Withdraw-Record
2439
+
2440
+ https://www.bitget.com/api-doc/spot/account/Get-Withdraw-Record
2441
+
2233
2442
  :param str code: unified currency code
2234
2443
  :param int [since]: the earliest time in ms to fetch withdrawals for
2235
2444
  :param int [limit]: the maximum number of withdrawals structures to retrieve
@@ -2249,8 +2458,8 @@ class bitget(Exchange, ImplicitAPI):
2249
2458
  currency = self.currency(code)
2250
2459
  if since is None:
2251
2460
  since = self.milliseconds() - 7776000000 # 90 days
2252
- request = {
2253
- 'coin': currency['code'],
2461
+ request: dict = {
2462
+ 'coin': currency['id'],
2254
2463
  'startTime': since,
2255
2464
  'endTime': self.milliseconds(),
2256
2465
  }
@@ -2284,10 +2493,10 @@ class bitget(Exchange, ImplicitAPI):
2284
2493
  # ]
2285
2494
  # }
2286
2495
  #
2287
- rawTransactions = self.safe_value(response, 'data', [])
2496
+ rawTransactions = self.safe_list(response, 'data', [])
2288
2497
  return self.parse_transactions(rawTransactions, currency, since, limit)
2289
2498
 
2290
- def parse_transaction(self, transaction, currency: Currency = None) -> Transaction:
2499
+ def parse_transaction(self, transaction: dict, currency: Currency = None) -> Transaction:
2291
2500
  #
2292
2501
  # fetchDeposits
2293
2502
  #
@@ -2362,8 +2571,8 @@ class bitget(Exchange, ImplicitAPI):
2362
2571
  'fee': fee,
2363
2572
  }
2364
2573
 
2365
- def parse_transaction_status(self, status):
2366
- statuses = {
2574
+ def parse_transaction_status(self, status: Str):
2575
+ statuses: dict = {
2367
2576
  'success': 'ok',
2368
2577
  'Pending': 'pending',
2369
2578
  'pending_review': 'pending',
@@ -2372,26 +2581,25 @@ class bitget(Exchange, ImplicitAPI):
2372
2581
  }
2373
2582
  return self.safe_string(statuses, status, status)
2374
2583
 
2375
- def fetch_deposit_address(self, code: str, params={}):
2584
+ def fetch_deposit_address(self, code: str, params={}) -> DepositAddress:
2376
2585
  """
2377
2586
  fetch the deposit address for a currency associated with self account
2378
- :see: https://www.bitget.com/api-doc/spot/account/Get-Deposit-Address
2587
+
2588
+ https://www.bitget.com/api-doc/spot/account/Get-Deposit-Address
2589
+
2379
2590
  :param str code: unified currency code
2380
2591
  :param dict [params]: extra parameters specific to the exchange API endpoint
2381
2592
  :returns dict: an `address structure <https://docs.ccxt.com/#/?id=address-structure>`
2382
2593
  """
2383
2594
  self.load_markets()
2384
- networkCode = self.safe_string_2(params, 'chain', 'network')
2385
- params = self.omit(params, 'network')
2386
- networkId = None
2387
- if networkCode is not None:
2388
- networkId = self.network_code_to_id(networkCode, code)
2595
+ networkCode = None
2596
+ networkCode, params = self.handle_network_code_and_params(params)
2389
2597
  currency = self.currency(code)
2390
- request = {
2391
- 'coin': currency['code'],
2598
+ request: dict = {
2599
+ 'coin': currency['id'],
2392
2600
  }
2393
- if networkId is not None:
2394
- request['chain'] = networkId
2601
+ if networkCode is not None:
2602
+ request['chain'] = self.network_code_to_id(networkCode, code)
2395
2603
  response = self.privateSpotGetV2SpotWalletDepositAddress(self.extend(request, params))
2396
2604
  #
2397
2605
  # {
@@ -2407,10 +2615,10 @@ class bitget(Exchange, ImplicitAPI):
2407
2615
  # }
2408
2616
  # }
2409
2617
  #
2410
- data = self.safe_value(response, 'data', {})
2618
+ data = self.safe_dict(response, 'data', {})
2411
2619
  return self.parse_deposit_address(data, currency)
2412
2620
 
2413
- def parse_deposit_address(self, depositAddress, currency: Currency = None):
2621
+ def parse_deposit_address(self, depositAddress, currency: Currency = None) -> DepositAddress:
2414
2622
  #
2415
2623
  # {
2416
2624
  # "coin": "BTC",
@@ -2427,18 +2635,20 @@ class bitget(Exchange, ImplicitAPI):
2427
2635
  if networkId is not None:
2428
2636
  network = self.network_id_to_code(networkId, parsedCurrency)
2429
2637
  return {
2638
+ 'info': depositAddress,
2430
2639
  'currency': parsedCurrency,
2640
+ 'network': network,
2431
2641
  'address': self.safe_string(depositAddress, 'address'),
2432
2642
  'tag': self.safe_string(depositAddress, 'tag'),
2433
- 'network': network,
2434
- 'info': depositAddress,
2435
2643
  }
2436
2644
 
2437
2645
  def fetch_order_book(self, symbol: str, limit: Int = None, params={}) -> OrderBook:
2438
2646
  """
2439
2647
  fetches information on open orders with bid(buy) and ask(sell) prices, volumes and other data
2440
- :see: https://www.bitget.com/api-doc/spot/market/Get-Orderbook
2441
- :see: https://www.bitget.com/api-doc/contract/market/Get-Merge-Depth
2648
+
2649
+ https://www.bitget.com/api-doc/spot/market/Get-Orderbook
2650
+ https://www.bitget.com/api-doc/contract/market/Get-Merge-Depth
2651
+
2442
2652
  :param str symbol: unified symbol of the market to fetch the order book for
2443
2653
  :param int [limit]: the maximum amount of order book entries to return
2444
2654
  :param dict [params]: extra parameters specific to the exchange API endpoint
@@ -2452,7 +2662,7 @@ class bitget(Exchange, ImplicitAPI):
2452
2662
  market = self.market(sandboxSymbol)
2453
2663
  else:
2454
2664
  market = self.market(symbol)
2455
- request = {
2665
+ request: dict = {
2456
2666
  'symbol': market['id'],
2457
2667
  }
2458
2668
  if limit is not None:
@@ -2481,7 +2691,15 @@ class bitget(Exchange, ImplicitAPI):
2481
2691
  timestamp = self.safe_integer(data, 'ts')
2482
2692
  return self.parse_order_book(data, market['symbol'], timestamp)
2483
2693
 
2484
- def parse_ticker(self, ticker, market: Market = None) -> Ticker:
2694
+ def parse_ticker(self, ticker: dict, market: Market = None) -> Ticker:
2695
+ #
2696
+ # {
2697
+ # "symbol": "BTCUSDT",
2698
+ # "price": "26242",
2699
+ # "indexPrice": "34867",
2700
+ # "markPrice": "25555",
2701
+ # "ts": "1695793390482"
2702
+ # }
2485
2703
  #
2486
2704
  # spot: fetchTicker, fetchTickers
2487
2705
  #
@@ -2554,7 +2772,7 @@ class bitget(Exchange, ImplicitAPI):
2554
2772
  #
2555
2773
  marketId = self.safe_string(ticker, 'symbol')
2556
2774
  close = self.safe_string(ticker, 'lastPr')
2557
- timestamp = self.safe_integer(ticker, 'ts')
2775
+ timestamp = self.safe_integer_omit_zero(ticker, 'ts') # exchange bitget provided 0
2558
2776
  change = self.safe_string(ticker, 'change24h')
2559
2777
  open24 = self.safe_string(ticker, 'open24')
2560
2778
  open = self.safe_string(ticker, 'open')
@@ -2586,14 +2804,18 @@ class bitget(Exchange, ImplicitAPI):
2586
2804
  'average': None,
2587
2805
  'baseVolume': self.safe_string(ticker, 'baseVolume'),
2588
2806
  'quoteVolume': self.safe_string(ticker, 'quoteVolume'),
2807
+ 'indexPrice': self.safe_string(ticker, 'indexPrice'),
2808
+ 'markPrice': self.safe_string(ticker, 'markPrice'),
2589
2809
  'info': ticker,
2590
2810
  }, market)
2591
2811
 
2592
2812
  def fetch_ticker(self, symbol: str, params={}) -> Ticker:
2593
2813
  """
2594
2814
  fetches a price ticker, a statistical calculation with the information calculated over the past 24 hours for a specific market
2595
- :see: https://www.bitget.com/api-doc/spot/market/Get-Tickers
2596
- :see: https://www.bitget.com/api-doc/contract/market/Get-Ticker
2815
+
2816
+ https://www.bitget.com/api-doc/spot/market/Get-Tickers
2817
+ https://www.bitget.com/api-doc/contract/market/Get-Ticker
2818
+
2597
2819
  :param str symbol: unified symbol of the market to fetch the ticker for
2598
2820
  :param dict [params]: extra parameters specific to the exchange API endpoint
2599
2821
  :returns dict: a `ticker structure <https://docs.ccxt.com/#/?id=ticker-structure>`
@@ -2606,7 +2828,7 @@ class bitget(Exchange, ImplicitAPI):
2606
2828
  market = self.market(sandboxSymbol)
2607
2829
  else:
2608
2830
  market = self.market(symbol)
2609
- request = {
2831
+ request: dict = {
2610
2832
  'symbol': market['id'],
2611
2833
  }
2612
2834
  response = None
@@ -2680,16 +2902,51 @@ class bitget(Exchange, ImplicitAPI):
2680
2902
  # ]
2681
2903
  # }
2682
2904
  #
2683
- data = self.safe_value(response, 'data', [])
2905
+ data = self.safe_list(response, 'data', [])
2906
+ return self.parse_ticker(data[0], market)
2907
+
2908
+ def fetch_mark_price(self, symbol: str, params={}) -> Ticker:
2909
+ """
2910
+ fetches the mark price for a specific market
2911
+
2912
+ https://www.bitget.com/api-doc/contract/market/Get-Symbol-Price
2913
+
2914
+ :param str symbol: unified symbol of the market to fetch the ticker for
2915
+ :param dict [params]: extra parameters specific to the exchange API endpoint
2916
+ :returns dict: a `ticker structure <https://docs.ccxt.com/#/?id=ticker-structure>`
2917
+ """
2918
+ self.load_markets()
2919
+ sandboxMode = self.safe_bool(self.options, 'sandboxMode', False)
2920
+ market = None
2921
+ if sandboxMode:
2922
+ sandboxSymbol = self.convert_symbol_for_sandbox(symbol)
2923
+ market = self.market(sandboxSymbol)
2924
+ else:
2925
+ market = self.market(symbol)
2926
+ request: dict = {
2927
+ 'symbol': market['id'],
2928
+ }
2929
+ response = None
2930
+ if market['spot']:
2931
+ raise NotSupported(self.id + ' fetchMarkPrice() is not supported for spot markets')
2932
+ else:
2933
+ productType = None
2934
+ productType, params = self.handle_product_type_and_params(market, params)
2935
+ request['productType'] = productType
2936
+ response = self.publicMixGetV2MixMarketSymbolPrice(self.extend(request, params))
2937
+ data = self.safe_list(response, 'data', [])
2684
2938
  return self.parse_ticker(data[0], market)
2685
2939
 
2686
2940
  def fetch_tickers(self, symbols: Strings = None, params={}) -> Tickers:
2687
2941
  """
2688
2942
  fetches price tickers for multiple markets, statistical information calculated over the past 24 hours for each market
2689
- :see: https://www.bitget.com/api-doc/spot/market/Get-Tickers
2690
- :see: https://www.bitget.com/api-doc/contract/market/Get-All-Symbol-Ticker
2943
+
2944
+ https://www.bitget.com/api-doc/spot/market/Get-Tickers
2945
+ https://www.bitget.com/api-doc/contract/market/Get-All-Symbol-Ticker
2946
+
2691
2947
  :param str[]|None symbols: unified symbols of the markets to fetch the ticker for, all market tickers are returned if not assigned
2692
2948
  :param dict [params]: extra parameters specific to the exchange API endpoint
2949
+ :param str [params.subType]: *contract only* 'linear', 'inverse'
2693
2950
  :param str [params.productType]: *contract only* 'USDT-FUTURES', 'USDC-FUTURES', 'COIN-FUTURES', 'SUSDT-FUTURES', 'SUSDC-FUTURES' or 'SCOIN-FUTURES'
2694
2951
  :returns dict: a dictionary of `ticker structures <https://docs.ccxt.com/#/?id=ticker-structure>`
2695
2952
  """
@@ -2703,15 +2960,20 @@ class bitget(Exchange, ImplicitAPI):
2703
2960
  market = self.market(sandboxSymbol)
2704
2961
  else:
2705
2962
  market = self.market(symbol)
2706
- request = {}
2963
+ response = None
2964
+ request: dict = {}
2707
2965
  type = None
2708
2966
  type, params = self.handle_market_type_and_params('fetchTickers', market, params)
2709
- response = None
2710
- if type == 'spot':
2967
+ # Calls like `.fetchTickers(None, {subType:'inverse'})` should be supported for self exchange, so
2968
+ # as "options.defaultSubType" is also set in exchange options, we should consider `params.subType`
2969
+ # with higher priority and only default to spot, if `subType` is not set in params
2970
+ passedSubType = self.safe_string(params, 'subType')
2971
+ productType = None
2972
+ productType, params = self.handle_product_type_and_params(market, params)
2973
+ # only if passedSubType and productType is None, then use spot
2974
+ if type == 'spot' and passedSubType is None:
2711
2975
  response = self.publicSpotGetV2SpotMarketTickers(self.extend(request, params))
2712
2976
  else:
2713
- productType = None
2714
- productType, params = self.handle_product_type_and_params(market, params)
2715
2977
  request['productType'] = productType
2716
2978
  response = self.publicMixGetV2MixMarketTickers(self.extend(request, params))
2717
2979
  #
@@ -2771,10 +3033,10 @@ class bitget(Exchange, ImplicitAPI):
2771
3033
  # ]
2772
3034
  # }
2773
3035
  #
2774
- data = self.safe_value(response, 'data', [])
3036
+ data = self.safe_list(response, 'data', [])
2775
3037
  return self.parse_tickers(data, symbols)
2776
3038
 
2777
- def parse_trade(self, trade, market: Market = None) -> Trade:
3039
+ def parse_trade(self, trade: dict, market: Market = None) -> Trade:
2778
3040
  #
2779
3041
  # spot, swap and future: fetchTrades
2780
3042
  #
@@ -2894,10 +3156,12 @@ class bitget(Exchange, ImplicitAPI):
2894
3156
  def fetch_trades(self, symbol: str, since: Int = None, limit: Int = None, params={}) -> List[Trade]:
2895
3157
  """
2896
3158
  get the list of most recent trades for a particular symbol
2897
- :see: https://www.bitget.com/api-doc/spot/market/Get-Recent-Trades
2898
- :see: https://www.bitget.com/api-doc/spot/market/Get-Market-Trades
2899
- :see: https://www.bitget.com/api-doc/contract/market/Get-Recent-Fills
2900
- :see: https://www.bitget.com/api-doc/contract/market/Get-Fills-History
3159
+
3160
+ https://www.bitget.com/api-doc/spot/market/Get-Recent-Trades
3161
+ https://www.bitget.com/api-doc/spot/market/Get-Market-Trades
3162
+ https://www.bitget.com/api-doc/contract/market/Get-Recent-Fills
3163
+ https://www.bitget.com/api-doc/contract/market/Get-Fills-History
3164
+
2901
3165
  :param str symbol: unified symbol of the market to fetch trades for
2902
3166
  :param int [since]: timestamp in ms of the earliest trade to fetch
2903
3167
  :param int [limit]: the maximum amount of trades to fetch
@@ -2918,7 +3182,7 @@ class bitget(Exchange, ImplicitAPI):
2918
3182
  market = self.market(sandboxSymbol)
2919
3183
  else:
2920
3184
  market = self.market(symbol)
2921
- request = {
3185
+ request: dict = {
2922
3186
  'symbol': market['id'],
2923
3187
  }
2924
3188
  if limit is not None:
@@ -2992,13 +3256,15 @@ class bitget(Exchange, ImplicitAPI):
2992
3256
  # ]
2993
3257
  # }
2994
3258
  #
2995
- data = self.safe_value(response, 'data', [])
3259
+ data = self.safe_list(response, 'data', [])
2996
3260
  return self.parse_trades(data, market, since, limit)
2997
3261
 
2998
- def fetch_trading_fee(self, symbol: str, params={}):
3262
+ def fetch_trading_fee(self, symbol: str, params={}) -> TradingFeeInterface:
2999
3263
  """
3000
3264
  fetch the trading fees for a market
3001
- :see: https://www.bitget.com/api-doc/common/public/Get-Trade-Rate
3265
+
3266
+ https://www.bitget.com/api-doc/common/public/Get-Trade-Rate
3267
+
3002
3268
  :param str symbol: unified market symbol
3003
3269
  :param dict [params]: extra parameters specific to the exchange API endpoint
3004
3270
  :param str [params.marginMode]: 'isolated' or 'cross', for finding the fee rate of spot margin trading pairs
@@ -3006,7 +3272,7 @@ class bitget(Exchange, ImplicitAPI):
3006
3272
  """
3007
3273
  self.load_markets()
3008
3274
  market = self.market(symbol)
3009
- request = {
3275
+ request: dict = {
3010
3276
  'symbol': market['id'],
3011
3277
  }
3012
3278
  marginMode = None
@@ -3033,12 +3299,14 @@ class bitget(Exchange, ImplicitAPI):
3033
3299
  data = self.safe_value(response, 'data', {})
3034
3300
  return self.parse_trading_fee(data, market)
3035
3301
 
3036
- def fetch_trading_fees(self, params={}):
3302
+ def fetch_trading_fees(self, params={}) -> TradingFees:
3037
3303
  """
3038
3304
  fetch the trading fees for multiple markets
3039
- :see: https://www.bitget.com/api-doc/spot/market/Get-Symbols
3040
- :see: https://www.bitget.com/api-doc/contract/market/Get-All-Symbols-Contracts
3041
- :see: https://www.bitget.com/api-doc/margin/common/support-currencies
3305
+
3306
+ https://www.bitget.com/api-doc/spot/market/Get-Symbols
3307
+ https://www.bitget.com/api-doc/contract/market/Get-All-Symbols-Contracts
3308
+ https://www.bitget.com/api-doc/margin/common/support-currencies
3309
+
3042
3310
  :param dict [params]: extra parameters specific to the exchange API endpoint
3043
3311
  :param str [params.productType]: *contract only* 'USDT-FUTURES', 'USDC-FUTURES', 'COIN-FUTURES', 'SUSDT-FUTURES', 'SUSDC-FUTURES' or 'SCOIN-FUTURES'
3044
3312
  :param boolean [params.margin]: set to True for spot margin
@@ -3136,7 +3404,7 @@ class bitget(Exchange, ImplicitAPI):
3136
3404
  # }
3137
3405
  #
3138
3406
  data = self.safe_value(response, 'data', [])
3139
- result = {}
3407
+ result: dict = {}
3140
3408
  for i in range(0, len(data)):
3141
3409
  entry = data[i]
3142
3410
  marketId = self.safe_string(entry, 'symbol')
@@ -3153,6 +3421,8 @@ class bitget(Exchange, ImplicitAPI):
3153
3421
  'symbol': self.safe_symbol(marketId, market),
3154
3422
  'maker': self.safe_number(data, 'makerFeeRate'),
3155
3423
  'taker': self.safe_number(data, 'takerFeeRate'),
3424
+ 'percentage': None,
3425
+ 'tierBased': None,
3156
3426
  }
3157
3427
 
3158
3428
  def parse_ohlcv(self, ohlcv, market: Market = None) -> list:
@@ -3179,12 +3449,14 @@ class bitget(Exchange, ImplicitAPI):
3179
3449
  def fetch_ohlcv(self, symbol: str, timeframe='1m', since: Int = None, limit: Int = None, params={}) -> List[list]:
3180
3450
  """
3181
3451
  fetches historical candlestick data containing the open, high, low, and close price, and the volume of a market
3182
- :see: https://www.bitget.com/api-doc/spot/market/Get-Candle-Data
3183
- :see: https://www.bitget.com/api-doc/spot/market/Get-History-Candle-Data
3184
- :see: https://www.bitget.com/api-doc/contract/market/Get-Candle-Data
3185
- :see: https://www.bitget.com/api-doc/contract/market/Get-History-Candle-Data
3186
- :see: https://www.bitget.com/api-doc/contract/market/Get-History-Index-Candle-Data
3187
- :see: https://www.bitget.com/api-doc/contract/market/Get-History-Mark-Candle-Data
3452
+
3453
+ https://www.bitget.com/api-doc/spot/market/Get-Candle-Data
3454
+ https://www.bitget.com/api-doc/spot/market/Get-History-Candle-Data
3455
+ https://www.bitget.com/api-doc/contract/market/Get-Candle-Data
3456
+ https://www.bitget.com/api-doc/contract/market/Get-History-Candle-Data
3457
+ https://www.bitget.com/api-doc/contract/market/Get-History-Index-Candle-Data
3458
+ https://www.bitget.com/api-doc/contract/market/Get-History-Mark-Candle-Data
3459
+
3188
3460
  :param str symbol: unified symbol of the market to fetch OHLCV data for
3189
3461
  :param str timeframe: the length of time each candle represents
3190
3462
  :param int [since]: timestamp in ms of the earliest candle to fetch
@@ -3214,15 +3486,15 @@ class bitget(Exchange, ImplicitAPI):
3214
3486
  timeframes = self.options['timeframes'][marketType]
3215
3487
  msInDay = 86400000
3216
3488
  duration = self.parse_timeframe(timeframe) * 1000
3217
- request = {
3489
+ request: dict = {
3218
3490
  'symbol': market['id'],
3219
3491
  'granularity': self.safe_string(timeframes, timeframe, timeframe),
3220
3492
  }
3221
- until = self.safe_integer_2(params, 'until', 'till')
3493
+ until = self.safe_integer(params, 'until')
3222
3494
  limitDefined = limit is not None
3223
3495
  sinceDefined = since is not None
3224
3496
  untilDefined = until is not None
3225
- params = self.omit(params, ['until', 'till'])
3497
+ params = self.omit(params, ['until'])
3226
3498
  response = None
3227
3499
  now = self.milliseconds()
3228
3500
  # retrievable periods listed here:
@@ -3299,18 +3571,20 @@ class bitget(Exchange, ImplicitAPI):
3299
3571
  def fetch_balance(self, params={}) -> Balances:
3300
3572
  """
3301
3573
  query for balance and get the amount of funds available for trading or funds locked in orders
3302
- :see: https://www.bitget.com/api-doc/spot/account/Get-Account-Assets
3303
- :see: https://www.bitget.com/api-doc/contract/account/Get-Account-List
3304
- :see: https://www.bitget.com/api-doc/margin/cross/account/Get-Cross-Assets
3305
- :see: https://www.bitget.com/api-doc/margin/isolated/account/Get-Isolated-Assets
3306
- :see: https://bitgetlimited.github.io/apidoc/en/margin/#get-cross-assets
3307
- :see: https://bitgetlimited.github.io/apidoc/en/margin/#get-isolated-assets
3574
+
3575
+ https://www.bitget.com/api-doc/spot/account/Get-Account-Assets
3576
+ https://www.bitget.com/api-doc/contract/account/Get-Account-List
3577
+ https://www.bitget.com/api-doc/margin/cross/account/Get-Cross-Assets
3578
+ https://www.bitget.com/api-doc/margin/isolated/account/Get-Isolated-Assets
3579
+ https://bitgetlimited.github.io/apidoc/en/margin/#get-cross-assets
3580
+ https://bitgetlimited.github.io/apidoc/en/margin/#get-isolated-assets
3581
+
3308
3582
  :param dict [params]: extra parameters specific to the exchange API endpoint
3309
3583
  :param str [params.productType]: *contract only* 'USDT-FUTURES', 'USDC-FUTURES', 'COIN-FUTURES', 'SUSDT-FUTURES', 'SUSDC-FUTURES' or 'SCOIN-FUTURES'
3310
3584
  :returns dict: a `balance structure <https://docs.ccxt.com/#/?id=balance-structure>`
3311
3585
  """
3312
3586
  self.load_markets()
3313
- request = {}
3587
+ request: dict = {}
3314
3588
  marketType = None
3315
3589
  marginMode = None
3316
3590
  response = None
@@ -3420,7 +3694,7 @@ class bitget(Exchange, ImplicitAPI):
3420
3694
  return self.parse_balance(data)
3421
3695
 
3422
3696
  def parse_balance(self, balance) -> Balances:
3423
- result = {'info': balance}
3697
+ result: dict = {'info': balance}
3424
3698
  #
3425
3699
  # spot
3426
3700
  #
@@ -3507,8 +3781,8 @@ class bitget(Exchange, ImplicitAPI):
3507
3781
  result[code] = account
3508
3782
  return self.safe_balance(result)
3509
3783
 
3510
- def parse_order_status(self, status):
3511
- statuses = {
3784
+ def parse_order_status(self, status: Str):
3785
+ statuses: dict = {
3512
3786
  'new': 'open',
3513
3787
  'init': 'open',
3514
3788
  'not_trigger': 'open',
@@ -3528,7 +3802,7 @@ class bitget(Exchange, ImplicitAPI):
3528
3802
  }
3529
3803
  return self.safe_string(statuses, status, status)
3530
3804
 
3531
- def parse_order(self, order, market: Market = None) -> Order:
3805
+ def parse_order(self, order: dict, market: Market = None) -> Order:
3532
3806
  #
3533
3807
  # createOrder, editOrder, closePosition
3534
3808
  #
@@ -3821,7 +4095,7 @@ class bitget(Exchange, ImplicitAPI):
3821
4095
  if feeCostString is not None:
3822
4096
  # swap
3823
4097
  fee = {
3824
- 'cost': self.parse_number(Precise.string_abs(feeCostString)),
4098
+ 'cost': self.parse_number(Precise.string_neg(feeCostString)),
3825
4099
  'currency': market['settle'],
3826
4100
  }
3827
4101
  feeDetail = self.safe_value(order, 'feeDetail')
@@ -3835,7 +4109,7 @@ class bitget(Exchange, ImplicitAPI):
3835
4109
  feeObject = feeValue
3836
4110
  break
3837
4111
  fee = {
3838
- 'cost': self.parse_number(Precise.string_abs(self.safe_string(feeObject, 'totalFee'))),
4112
+ 'cost': self.parse_number(Precise.string_neg(self.safe_string(feeObject, 'totalFee'))),
3839
4113
  'currency': self.safe_currency_code(self.safe_string(feeObject, 'feeCoinCode')),
3840
4114
  }
3841
4115
  postOnly = None
@@ -3893,7 +4167,6 @@ class bitget(Exchange, ImplicitAPI):
3893
4167
  'timeInForce': timeInForce,
3894
4168
  'postOnly': postOnly,
3895
4169
  'reduceOnly': reduceOnly,
3896
- 'stopPrice': self.safe_number(order, 'triggerPrice'),
3897
4170
  'triggerPrice': self.safe_number(order, 'triggerPrice'),
3898
4171
  'takeProfitPrice': self.safe_number_2(order, 'presetStopSurplusPrice', 'stopSurplusTriggerPrice'),
3899
4172
  'stopLossPrice': self.safe_number_2(order, 'presetStopLossPrice', 'stopLossTriggerPrice'),
@@ -3905,9 +4178,11 @@ class bitget(Exchange, ImplicitAPI):
3905
4178
  def create_market_buy_order_with_cost(self, symbol: str, cost: float, params={}):
3906
4179
  """
3907
4180
  create a market buy order by providing the symbol and cost
3908
- :see: https://www.bitget.com/api-doc/spot/trade/Place-Order
3909
- :see: https://www.bitget.com/api-doc/margin/cross/trade/Cross-Place-Order
3910
- :see: https://www.bitget.com/api-doc/margin/isolated/trade/Isolated-Place-Order
4181
+
4182
+ https://www.bitget.com/api-doc/spot/trade/Place-Order
4183
+ https://www.bitget.com/api-doc/margin/cross/trade/Cross-Place-Order
4184
+ https://www.bitget.com/api-doc/margin/isolated/trade/Isolated-Place-Order
4185
+
3911
4186
  :param str symbol: unified symbol of the market to create an order in
3912
4187
  :param float cost: how much you want to trade in units of the quote currency
3913
4188
  :param dict [params]: extra parameters specific to the exchange API endpoint
@@ -3917,24 +4192,28 @@ class bitget(Exchange, ImplicitAPI):
3917
4192
  market = self.market(symbol)
3918
4193
  if not market['spot']:
3919
4194
  raise NotSupported(self.id + ' createMarketBuyOrderWithCost() supports spot orders only')
3920
- params['createMarketBuyOrderRequiresPrice'] = False
3921
- return self.create_order(symbol, 'market', 'buy', cost, None, params)
4195
+ req = {
4196
+ 'createMarketBuyOrderRequiresPrice': False,
4197
+ }
4198
+ return self.create_order(symbol, 'market', 'buy', cost, None, self.extend(req, params))
3922
4199
 
3923
4200
  def create_order(self, symbol: str, type: OrderType, side: OrderSide, amount: float, price: Num = None, params={}):
3924
4201
  """
3925
4202
  create a trade order
3926
- :see: https://www.bitget.com/api-doc/spot/trade/Place-Order
3927
- :see: https://www.bitget.com/api-doc/spot/plan/Place-Plan-Order
3928
- :see: https://www.bitget.com/api-doc/contract/trade/Place-Order
3929
- :see: https://www.bitget.com/api-doc/contract/plan/Place-Tpsl-Order
3930
- :see: https://www.bitget.com/api-doc/contract/plan/Place-Plan-Order
3931
- :see: https://www.bitget.com/api-doc/margin/cross/trade/Cross-Place-Order
3932
- :see: https://www.bitget.com/api-doc/margin/isolated/trade/Isolated-Place-Order
4203
+
4204
+ https://www.bitget.com/api-doc/spot/trade/Place-Order
4205
+ https://www.bitget.com/api-doc/spot/plan/Place-Plan-Order
4206
+ https://www.bitget.com/api-doc/contract/trade/Place-Order
4207
+ https://www.bitget.com/api-doc/contract/plan/Place-Tpsl-Order
4208
+ https://www.bitget.com/api-doc/contract/plan/Place-Plan-Order
4209
+ https://www.bitget.com/api-doc/margin/cross/trade/Cross-Place-Order
4210
+ https://www.bitget.com/api-doc/margin/isolated/trade/Isolated-Place-Order
4211
+
3933
4212
  :param str symbol: unified symbol of the market to create an order in
3934
4213
  :param str type: 'market' or 'limit'
3935
4214
  :param str side: 'buy' or 'sell'
3936
4215
  :param float amount: how much you want to trade in units of the base currency
3937
- :param float [price]: the price at which the order is to be fullfilled, in units of the quote currency, ignored in market orders
4216
+ :param float [price]: the price at which the order is to be fulfilled, in units of the quote currency, ignored in market orders
3938
4217
  :param dict [params]: extra parameters specific to the exchange API endpoint
3939
4218
  :param float [params.cost]: *spot only* how much you want to trade in units of the quote currency, for market buy orders only
3940
4219
  :param float [params.triggerPrice]: *swap only* The price at which a trigger order is triggered at
@@ -3956,6 +4235,8 @@ class bitget(Exchange, ImplicitAPI):
3956
4235
  :param str [params.trailingTriggerPrice]: *swap and future only* the price to trigger a trailing stop order, default uses the price argument
3957
4236
  :param str [params.triggerType]: *swap and future only* 'fill_price', 'mark_price' or 'index_price'
3958
4237
  :param boolean [params.oneWayMode]: *swap and future only* required to set self to True in one_way_mode and you can leave self in hedge_mode, can adjust the mode using the setPositionMode() method
4238
+ :param bool [params.hedged]: *swap and future only* True for hedged mode, False for one way mode, default is False
4239
+ :param bool [params.reduceOnly]: True or False whether the order is reduce-only
3959
4240
  :returns dict: an `order structure <https://docs.ccxt.com/#/?id=order-structure>`
3960
4241
  """
3961
4242
  self.load_markets()
@@ -4000,7 +4281,7 @@ class bitget(Exchange, ImplicitAPI):
4000
4281
  # }
4001
4282
  # }
4002
4283
  #
4003
- data = self.safe_value(response, 'data', {})
4284
+ data = self.safe_dict(response, 'data', {})
4004
4285
  return self.parse_order(data, market)
4005
4286
 
4006
4287
  def create_order_request(self, symbol: str, type: OrderType, side: OrderSide, amount: float, price: Num = None, params={}):
@@ -4015,7 +4296,7 @@ class bitget(Exchange, ImplicitAPI):
4015
4296
  marginMode = None
4016
4297
  marketType, params = self.handle_market_type_and_params('createOrder', market, params)
4017
4298
  marginMode, params = self.handle_margin_mode_and_params('createOrder', params)
4018
- request = {
4299
+ request: dict = {
4019
4300
  'symbol': market['id'],
4020
4301
  'orderType': type,
4021
4302
  }
@@ -4039,7 +4320,7 @@ class bitget(Exchange, ImplicitAPI):
4039
4320
  raise ExchangeError(self.id + ' createOrder() params can only contain one of triggerPrice, stopLossPrice, takeProfitPrice, trailingPercent')
4040
4321
  if type == 'limit':
4041
4322
  request['price'] = self.price_to_precision(symbol, price)
4042
- triggerType = self.safe_string(params, 'triggerType', 'mark_price')
4323
+ triggerPriceType = self.safe_string_2(params, 'triggerPriceType', 'triggerType', 'mark_price')
4043
4324
  reduceOnly = self.safe_bool(params, 'reduceOnly', False)
4044
4325
  clientOrderId = self.safe_string_2(params, 'clientOid', 'clientOrderId')
4045
4326
  exchangeSpecificTifParam = self.safe_string_2(params, 'force', 'timeInForce')
@@ -4065,7 +4346,7 @@ class bitget(Exchange, ImplicitAPI):
4065
4346
  if clientOrderId is not None:
4066
4347
  request['clientOid'] = clientOrderId
4067
4348
  if isTriggerOrder or isStopLossOrTakeProfitTrigger or isTrailingPercentOrder:
4068
- request['triggerType'] = triggerType
4349
+ request['triggerType'] = triggerPriceType
4069
4350
  if isTrailingPercentOrder:
4070
4351
  if not isMarketOrder:
4071
4352
  raise BadRequest(self.id + ' createOrder() bitget trailing orders must be market orders')
@@ -4115,18 +4396,23 @@ class bitget(Exchange, ImplicitAPI):
4115
4396
  marginMode = 'cross'
4116
4397
  marginModeRequest = 'crossed' if (marginMode == 'cross') else 'isolated'
4117
4398
  request['marginMode'] = marginModeRequest
4118
- oneWayMode = self.safe_bool(params, 'oneWayMode', False)
4119
- params = self.omit(params, 'oneWayMode')
4399
+ hedged = None
4400
+ hedged, params = self.handle_param_bool(params, 'hedged', False)
4401
+ # backward compatibility for `oneWayMode`
4402
+ oneWayMode = None
4403
+ oneWayMode, params = self.handle_param_bool(params, 'oneWayMode')
4404
+ if oneWayMode is not None:
4405
+ hedged = not oneWayMode
4120
4406
  requestSide = side
4121
4407
  if reduceOnly:
4122
- if oneWayMode:
4408
+ if not hedged:
4123
4409
  request['reduceOnly'] = 'YES'
4124
4410
  else:
4125
4411
  # on bitget hedge mode if the position is long the side is always buy, and if the position is short the side is always sell
4126
4412
  requestSide = 'sell' if (side == 'buy') else 'buy'
4127
4413
  request['tradeSide'] = 'Close'
4128
4414
  else:
4129
- if not oneWayMode:
4415
+ if hedged:
4130
4416
  request['tradeSide'] = 'Open'
4131
4417
  request['side'] = requestSide
4132
4418
  elif marketType == 'spot':
@@ -4160,7 +4446,7 @@ class bitget(Exchange, ImplicitAPI):
4160
4446
  request['clientOid'] = clientOrderId
4161
4447
  if marginMode is not None:
4162
4448
  request['loanType'] = 'normal'
4163
- if createMarketBuyOrderRequiresPrice and isMarketOrder and (side == 'buy'):
4449
+ if isMarketOrder and (side == 'buy'):
4164
4450
  request['quoteSize'] = quantity
4165
4451
  else:
4166
4452
  request['baseSize'] = quantity
@@ -4169,7 +4455,7 @@ class bitget(Exchange, ImplicitAPI):
4169
4455
  request['size'] = quantity
4170
4456
  if triggerPrice is not None:
4171
4457
  request['planType'] = planType
4172
- request['triggerType'] = triggerType
4458
+ request['triggerType'] = triggerPriceType
4173
4459
  request['triggerPrice'] = self.price_to_precision(symbol, triggerPrice)
4174
4460
  if price is not None:
4175
4461
  request['executePrice'] = self.price_to_precision(symbol, price)
@@ -4180,10 +4466,12 @@ class bitget(Exchange, ImplicitAPI):
4180
4466
  def create_orders(self, orders: List[OrderRequest], params={}):
4181
4467
  """
4182
4468
  create a list of trade orders(all orders should be of the same symbol)
4183
- :see: https://www.bitget.com/api-doc/spot/trade/Batch-Place-Orders
4184
- :see: https://www.bitget.com/api-doc/contract/trade/Batch-Order
4185
- :see: https://www.bitget.com/api-doc/margin/isolated/trade/Isolated-Batch-Order
4186
- :see: https://www.bitget.com/api-doc/margin/cross/trade/Cross-Batch-Order
4469
+
4470
+ https://www.bitget.com/api-doc/spot/trade/Batch-Place-Orders
4471
+ https://www.bitget.com/api-doc/contract/trade/Batch-Order
4472
+ https://www.bitget.com/api-doc/margin/isolated/trade/Isolated-Batch-Order
4473
+ https://www.bitget.com/api-doc/margin/cross/trade/Cross-Batch-Order
4474
+
4187
4475
  :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
4188
4476
  :param dict [params]: extra parameters specific to the api endpoint
4189
4477
  :returns dict: an `order structure <https://docs.ccxt.com/#/?id=order-structure>`
@@ -4222,7 +4510,7 @@ class bitget(Exchange, ImplicitAPI):
4222
4510
  market = self.market(sandboxSymbol)
4223
4511
  else:
4224
4512
  market = self.market(symbol)
4225
- request = {
4513
+ request: dict = {
4226
4514
  'symbol': market['id'],
4227
4515
  'orderList': ordersRequests,
4228
4516
  }
@@ -4275,16 +4563,18 @@ class bitget(Exchange, ImplicitAPI):
4275
4563
  def edit_order(self, id: str, symbol: str, type: OrderType, side: OrderSide, amount: Num = None, price: Num = None, params={}):
4276
4564
  """
4277
4565
  edit a trade order
4278
- :see: https://www.bitget.com/api-doc/spot/plan/Modify-Plan-Order
4279
- :see: https://www.bitget.com/api-doc/contract/trade/Modify-Order
4280
- :see: https://www.bitget.com/api-doc/contract/plan/Modify-Tpsl-Order
4281
- :see: https://www.bitget.com/api-doc/contract/plan/Modify-Plan-Order
4566
+
4567
+ https://www.bitget.com/api-doc/spot/plan/Modify-Plan-Order
4568
+ https://www.bitget.com/api-doc/contract/trade/Modify-Order
4569
+ https://www.bitget.com/api-doc/contract/plan/Modify-Tpsl-Order
4570
+ https://www.bitget.com/api-doc/contract/plan/Modify-Plan-Order
4571
+
4282
4572
  :param str id: cancel order id
4283
4573
  :param str symbol: unified symbol of the market to create an order in
4284
4574
  :param str type: 'market' or 'limit'
4285
4575
  :param str side: 'buy' or 'sell'
4286
4576
  :param float amount: how much you want to trade in units of the base currency
4287
- :param float [price]: the price at which the order is to be fullfilled, in units of the base currency, ignored in market orders
4577
+ :param float [price]: the price at which the order is to be fulfilled, in units of the quote currency, ignored in market orders
4288
4578
  :param dict [params]: extra parameters specific to the exchange API endpoint
4289
4579
  :param float [params.triggerPrice]: the price that a trigger order is triggered at
4290
4580
  :param float [params.stopLossPrice]: *swap only* The price at which a stop loss order is triggered at
@@ -4310,7 +4600,7 @@ class bitget(Exchange, ImplicitAPI):
4310
4600
  market = self.market(sandboxSymbol)
4311
4601
  else:
4312
4602
  market = self.market(symbol)
4313
- request = {
4603
+ request: dict = {
4314
4604
  'orderId': id,
4315
4605
  }
4316
4606
  isMarketOrder = type == 'market'
@@ -4335,6 +4625,8 @@ class bitget(Exchange, ImplicitAPI):
4335
4625
  params = self.omit(params, ['stopPrice', 'triggerType', 'stopLossPrice', 'takeProfitPrice', 'stopLoss', 'takeProfit', 'clientOrderId', 'trailingTriggerPrice', 'trailingPercent'])
4336
4626
  response = None
4337
4627
  if market['spot']:
4628
+ if triggerPrice is None:
4629
+ raise NotSupported(self.id + 'editOrder() only supports plan/trigger spot orders')
4338
4630
  editMarketBuyOrderRequiresPrice = self.safe_bool(self.options, 'editMarketBuyOrderRequiresPrice', True)
4339
4631
  if editMarketBuyOrderRequiresPrice and isMarketOrder and (side == 'buy'):
4340
4632
  if price is None:
@@ -4417,23 +4709,25 @@ class bitget(Exchange, ImplicitAPI):
4417
4709
  # }
4418
4710
  # }
4419
4711
  #
4420
- data = self.safe_value(response, 'data', {})
4712
+ data = self.safe_dict(response, 'data', {})
4421
4713
  return self.parse_order(data, market)
4422
4714
 
4423
4715
  def cancel_order(self, id: str, symbol: Str = None, params={}):
4424
4716
  """
4425
4717
  cancels an open order
4426
- :see: https://www.bitget.com/api-doc/spot/trade/Cancel-Order
4427
- :see: https://www.bitget.com/api-doc/spot/plan/Cancel-Plan-Order
4428
- :see: https://www.bitget.com/api-doc/contract/trade/Cancel-Order
4429
- :see: https://www.bitget.com/api-doc/contract/plan/Cancel-Plan-Order
4430
- :see: https://www.bitget.com/api-doc/margin/cross/trade/Cross-Cancel-Order
4431
- :see: https://www.bitget.com/api-doc/margin/isolated/trade/Isolated-Cancel-Order
4718
+
4719
+ https://www.bitget.com/api-doc/spot/trade/Cancel-Order
4720
+ https://www.bitget.com/api-doc/spot/plan/Cancel-Plan-Order
4721
+ https://www.bitget.com/api-doc/contract/trade/Cancel-Order
4722
+ https://www.bitget.com/api-doc/contract/plan/Cancel-Plan-Order
4723
+ https://www.bitget.com/api-doc/margin/cross/trade/Cross-Cancel-Order
4724
+ https://www.bitget.com/api-doc/margin/isolated/trade/Isolated-Cancel-Order
4725
+
4432
4726
  :param str id: order id
4433
4727
  :param str symbol: unified symbol of the market the order was made in
4434
4728
  :param dict [params]: extra parameters specific to the exchange API endpoint
4435
4729
  :param str [params.marginMode]: 'isolated' or 'cross' for spot margin trading
4436
- :param boolean [params.stop]: set to True for canceling trigger orders
4730
+ :param boolean [params.trigger]: set to True for canceling trigger orders
4437
4731
  :param str [params.planType]: *swap only* either profit_plan, loss_plan, normal_plan, pos_profit, pos_loss, moving_plan or track_plan
4438
4732
  :param boolean [params.trailing]: set to True if you want to cancel a trailing order
4439
4733
  :returns dict: An `order structure <https://docs.ccxt.com/#/?id=order-structure>`
@@ -4451,21 +4745,21 @@ class bitget(Exchange, ImplicitAPI):
4451
4745
  marginMode = None
4452
4746
  response = None
4453
4747
  marginMode, params = self.handle_margin_mode_and_params('cancelOrder', params)
4454
- request = {}
4748
+ request: dict = {}
4455
4749
  trailing = self.safe_value(params, 'trailing')
4456
- stop = self.safe_value_2(params, 'stop', 'trigger')
4750
+ trigger = self.safe_value_2(params, 'stop', 'trigger')
4457
4751
  params = self.omit(params, ['stop', 'trigger', 'trailing'])
4458
- if not (market['spot'] and stop):
4752
+ if not (market['spot'] and trigger):
4459
4753
  request['symbol'] = market['id']
4460
- if not ((market['swap'] or market['future']) and stop):
4754
+ if not ((market['swap'] or market['future']) and trigger):
4461
4755
  request['orderId'] = id
4462
4756
  if (market['swap']) or (market['future']):
4463
4757
  productType = None
4464
4758
  productType, params = self.handle_product_type_and_params(market, params)
4465
4759
  request['productType'] = productType
4466
- if stop or trailing:
4760
+ if trigger or trailing:
4467
4761
  orderIdList = []
4468
- orderId = {
4762
+ orderId: dict = {
4469
4763
  'orderId': id,
4470
4764
  }
4471
4765
  orderIdList.append(orderId)
@@ -4474,7 +4768,7 @@ class bitget(Exchange, ImplicitAPI):
4474
4768
  planType = self.safe_string(params, 'planType', 'track_plan')
4475
4769
  request['planType'] = planType
4476
4770
  response = self.privateMixPostV2MixOrderCancelPlanOrder(self.extend(request, params))
4477
- elif stop:
4771
+ elif trigger:
4478
4772
  response = self.privateMixPostV2MixOrderCancelPlanOrder(self.extend(request, params))
4479
4773
  else:
4480
4774
  response = self.privateMixPostV2MixOrderCancelOrder(self.extend(request, params))
@@ -4485,7 +4779,7 @@ class bitget(Exchange, ImplicitAPI):
4485
4779
  elif marginMode == 'cross':
4486
4780
  response = self.privateMarginPostV2MarginCrossedCancelOrder(self.extend(request, params))
4487
4781
  else:
4488
- if stop:
4782
+ if trigger:
4489
4783
  response = self.privateSpotPostV2SpotTradeCancelPlanOrder(self.extend(request, params))
4490
4784
  else:
4491
4785
  response = self.privateSpotPostV2SpotTradeCancelOrder(self.extend(request, params))
@@ -4534,7 +4828,7 @@ class bitget(Exchange, ImplicitAPI):
4534
4828
  #
4535
4829
  data = self.safe_value(response, 'data', {})
4536
4830
  order = None
4537
- if (market['swap'] or market['future']) and stop:
4831
+ if (market['swap'] or market['future']) and trigger:
4538
4832
  orderInfo = self.safe_value(data, 'successList', [])
4539
4833
  order = orderInfo[0]
4540
4834
  else:
@@ -4544,16 +4838,18 @@ class bitget(Exchange, ImplicitAPI):
4544
4838
  def cancel_orders(self, ids, symbol: Str = None, params={}):
4545
4839
  """
4546
4840
  cancel multiple orders
4547
- :see: https://www.bitget.com/api-doc/spot/trade/Batch-Cancel-Orders
4548
- :see: https://www.bitget.com/api-doc/contract/trade/Batch-Cancel-Orders
4549
- :see: https://www.bitget.com/api-doc/contract/plan/Cancel-Plan-Order
4550
- :see: https://www.bitget.com/api-doc/margin/cross/trade/Cross-Batch-Cancel-Order
4551
- :see: https://www.bitget.com/api-doc/margin/isolated/trade/Isolated-Batch-Cancel-Orders
4841
+
4842
+ https://www.bitget.com/api-doc/spot/trade/Batch-Cancel-Orders
4843
+ https://www.bitget.com/api-doc/contract/trade/Batch-Cancel-Orders
4844
+ https://www.bitget.com/api-doc/contract/plan/Cancel-Plan-Order
4845
+ https://www.bitget.com/api-doc/margin/cross/trade/Cross-Batch-Cancel-Order
4846
+ https://www.bitget.com/api-doc/margin/isolated/trade/Isolated-Batch-Cancel-Orders
4847
+
4552
4848
  :param str[] ids: order ids
4553
4849
  :param str symbol: unified market symbol, default is None
4554
4850
  :param dict [params]: extra parameters specific to the exchange API endpoint
4555
4851
  :param str [params.marginMode]: 'isolated' or 'cross' for spot margin trading
4556
- :param boolean [params.stop]: *contract only* set to True for canceling trigger orders
4852
+ :param boolean [params.trigger]: *contract only* set to True for canceling trigger orders
4557
4853
  :returns dict: an array of `order structures <https://docs.ccxt.com/#/?id=order-structure>`
4558
4854
  """
4559
4855
  if symbol is None:
@@ -4568,16 +4864,16 @@ class bitget(Exchange, ImplicitAPI):
4568
4864
  market = self.market(symbol)
4569
4865
  marginMode = None
4570
4866
  marginMode, params = self.handle_margin_mode_and_params('cancelOrders', params)
4571
- stop = self.safe_value_2(params, 'stop', 'trigger')
4867
+ trigger = self.safe_value_2(params, 'stop', 'trigger')
4572
4868
  params = self.omit(params, ['stop', 'trigger'])
4573
4869
  orderIdList = []
4574
4870
  for i in range(0, len(ids)):
4575
4871
  individualId = ids[i]
4576
- orderId = {
4872
+ orderId: dict = {
4577
4873
  'orderId': individualId,
4578
4874
  }
4579
4875
  orderIdList.append(orderId)
4580
- request = {
4876
+ request: dict = {
4581
4877
  'symbol': market['id'],
4582
4878
  }
4583
4879
  if market['spot'] and (marginMode is None):
@@ -4597,7 +4893,7 @@ class bitget(Exchange, ImplicitAPI):
4597
4893
  productType = None
4598
4894
  productType, params = self.handle_product_type_and_params(market, params)
4599
4895
  request['productType'] = productType
4600
- if stop:
4896
+ if trigger:
4601
4897
  response = self.privateMixPostV2MixOrderCancelPlanOrder(self.extend(request, params))
4602
4898
  else:
4603
4899
  response = self.privateMixPostV2MixOrderBatchCancelOrders(self.extend(request, params))
@@ -4618,21 +4914,23 @@ class bitget(Exchange, ImplicitAPI):
4618
4914
  # }
4619
4915
  #
4620
4916
  data = self.safe_value(response, 'data', {})
4621
- orders = self.safe_value(data, 'successList', [])
4917
+ orders = self.safe_list(data, 'successList', [])
4622
4918
  return self.parse_orders(orders, market)
4623
4919
 
4624
4920
  def cancel_all_orders(self, symbol: Str = None, params={}):
4625
4921
  """
4626
4922
  cancel all open orders
4627
- :see: https://www.bitget.com/api-doc/spot/trade/Cancel-Symbol-Orders
4628
- :see: https://www.bitget.com/api-doc/spot/plan/Batch-Cancel-Plan-Order
4629
- :see: https://www.bitget.com/api-doc/contract/trade/Batch-Cancel-Orders
4630
- :see: https://bitgetlimited.github.io/apidoc/en/margin/#isolated-batch-cancel-orders
4631
- :see: https://bitgetlimited.github.io/apidoc/en/margin/#cross-batch-cancel-order
4923
+
4924
+ https://www.bitget.com/api-doc/spot/trade/Cancel-Symbol-Orders
4925
+ https://www.bitget.com/api-doc/spot/plan/Batch-Cancel-Plan-Order
4926
+ https://www.bitget.com/api-doc/contract/trade/Batch-Cancel-Orders
4927
+ https://bitgetlimited.github.io/apidoc/en/margin/#isolated-batch-cancel-orders
4928
+ https://bitgetlimited.github.io/apidoc/en/margin/#cross-batch-cancel-order
4929
+
4632
4930
  :param str symbol: unified market symbol
4633
4931
  :param dict [params]: extra parameters specific to the exchange API endpoint
4634
4932
  :param str [params.marginMode]: 'isolated' or 'cross' for spot margin trading
4635
- :param boolean [params.stop]: *contract only* set to True for canceling trigger orders
4933
+ :param boolean [params.trigger]: *contract only* set to True for canceling trigger orders
4636
4934
  :returns dict[]: a list of `order structures <https://docs.ccxt.com/#/?id=order-structure>`
4637
4935
  """
4638
4936
  if symbol is None:
@@ -4647,10 +4945,10 @@ class bitget(Exchange, ImplicitAPI):
4647
4945
  market = self.market(symbol)
4648
4946
  marginMode = None
4649
4947
  marginMode, params = self.handle_margin_mode_and_params('cancelAllOrders', params)
4650
- request = {
4948
+ request: dict = {
4651
4949
  'symbol': market['id'],
4652
4950
  }
4653
- stop = self.safe_bool_2(params, 'stop', 'trigger')
4951
+ trigger = self.safe_bool_2(params, 'stop', 'trigger')
4654
4952
  params = self.omit(params, ['stop', 'trigger'])
4655
4953
  response = None
4656
4954
  if market['spot']:
@@ -4659,103 +4957,115 @@ class bitget(Exchange, ImplicitAPI):
4659
4957
  response = self.privateMarginPostMarginV1CrossOrderBatchCancelOrder(self.extend(request, params))
4660
4958
  else:
4661
4959
  response = self.privateMarginPostMarginV1IsolatedOrderBatchCancelOrder(self.extend(request, params))
4960
+ #
4961
+ # {
4962
+ # "code": "00000",
4963
+ # "msg": "success",
4964
+ # "requestTime": 1700717155622,
4965
+ # "data": {
4966
+ # "resultList": [
4967
+ # {
4968
+ # "orderId": "1111453253721796609",
4969
+ # "clientOid": "2ae7fc8a4ff949b6b60d770ca3950e2d"
4970
+ # },
4971
+ # ],
4972
+ # "failure": []
4973
+ # }
4974
+ # }
4975
+ #
4662
4976
  else:
4663
- if stop:
4664
- stopRequest = {
4977
+ if trigger:
4978
+ stopRequest: dict = {
4665
4979
  'symbolList': [market['id']],
4666
4980
  }
4667
4981
  response = self.privateSpotPostV2SpotTradeBatchCancelPlanOrder(self.extend(stopRequest, params))
4668
4982
  else:
4669
4983
  response = self.privateSpotPostV2SpotTradeCancelSymbolOrder(self.extend(request, params))
4984
+ #
4985
+ # {
4986
+ # "code": "00000",
4987
+ # "msg": "success",
4988
+ # "requestTime": 1700716953996,
4989
+ # "data": {
4990
+ # "symbol": "BTCUSDT"
4991
+ # }
4992
+ # }
4993
+ #
4994
+ timestamp = self.safe_integer(response, 'requestTime')
4995
+ responseData = self.safe_dict(response, 'data')
4996
+ marketId = self.safe_string(responseData, 'symbol')
4997
+ return [
4998
+ self.safe_order({
4999
+ 'info': response,
5000
+ 'symbol': self.safe_symbol(marketId, None, None, 'spot'),
5001
+ 'timestamp': timestamp,
5002
+ 'datetime': self.iso8601(timestamp),
5003
+ }),
5004
+ ]
4670
5005
  else:
4671
5006
  productType = None
4672
5007
  productType, params = self.handle_product_type_and_params(market, params)
4673
5008
  request['productType'] = productType
4674
- if stop:
5009
+ if trigger:
4675
5010
  response = self.privateMixPostV2MixOrderCancelPlanOrder(self.extend(request, params))
4676
5011
  else:
4677
5012
  response = self.privateMixPostV2MixOrderBatchCancelOrders(self.extend(request, params))
4678
- #
4679
- # spot
4680
- #
4681
- # {
4682
- # "code": "00000",
4683
- # "msg": "success",
4684
- # "requestTime": 1700716953996,
4685
- # "data": {
4686
- # "symbol": "BTCUSDT"
4687
- # }
4688
- # }
4689
- #
4690
- # swap
4691
- #
4692
- # {
4693
- # "code": "00000",
4694
- # "msg": "success",
4695
- # "requestTime": "1680008815965",
4696
- # "data": {
4697
- # "successList": [
4698
- # {
4699
- # "orderId": "1024598257429823488",
4700
- # "clientOid": "876493ce-c287-4bfc-9f4a-8b1905881313"
4701
- # },
4702
- # ],
4703
- # "failureList": []
4704
- # }
4705
- # }
4706
- #
4707
- # spot margin
4708
- #
4709
- # {
4710
- # "code": "00000",
4711
- # "msg": "success",
4712
- # "requestTime": 1700717155622,
4713
- # "data": {
4714
- # "resultList": [
4715
- # {
4716
- # "orderId": "1111453253721796609",
4717
- # "clientOid": "2ae7fc8a4ff949b6b60d770ca3950e2d"
4718
- # },
4719
- # ],
4720
- # "failure": []
4721
- # }
4722
- # }
4723
- #
4724
- return response
4725
-
4726
- def fetch_order(self, id: str, symbol: Str = None, params={}):
4727
- """
4728
- fetches information on an order made by the user
4729
- :see: https://www.bitget.com/api-doc/spot/trade/Get-Order-Info
4730
- :see: https://www.bitget.com/api-doc/contract/trade/Get-Order-Details
4731
- :param str symbol: unified symbol of the market the order was made in
4732
- :param dict [params]: extra parameters specific to the exchange API endpoint
4733
- :returns dict: An `order structure <https://docs.ccxt.com/#/?id=order-structure>`
4734
- """
4735
- if symbol is None:
4736
- raise ArgumentsRequired(self.id + ' fetchOrder() requires a symbol argument')
4737
- self.load_markets()
4738
- sandboxMode = self.safe_bool(self.options, 'sandboxMode', False)
4739
- market = None
4740
- if sandboxMode:
4741
- sandboxSymbol = self.convert_symbol_for_sandbox(symbol)
4742
- market = self.market(sandboxSymbol)
4743
- else:
4744
- market = self.market(symbol)
4745
- request = {
4746
- 'orderId': id,
4747
- }
4748
- response = None
4749
- if market['spot']:
4750
- response = self.privateSpotGetV2SpotTradeOrderInfo(self.extend(request, params))
4751
- elif market['swap'] or market['future']:
4752
- request['symbol'] = market['id']
4753
- productType = None
4754
- productType, params = self.handle_product_type_and_params(market, params)
4755
- request['productType'] = productType
4756
- response = self.privateMixGetV2MixOrderDetail(self.extend(request, params))
4757
- else:
4758
- raise NotSupported(self.id + ' fetchOrder() does not support ' + market['type'] + ' orders')
5013
+ # {
5014
+ # "code": "00000",
5015
+ # "msg": "success",
5016
+ # "requestTime": "1680008815965",
5017
+ # "data": {
5018
+ # "successList": [
5019
+ # {
5020
+ # "orderId": "1024598257429823488",
5021
+ # "clientOid": "876493ce-c287-4bfc-9f4a-8b1905881313"
5022
+ # },
5023
+ # ],
5024
+ # "failureList": []
5025
+ # }
5026
+ # }
5027
+ data = self.safe_dict(response, 'data')
5028
+ resultList = self.safe_list_2(data, 'resultList', 'successList')
5029
+ failureList = self.safe_list_2(data, 'failure', 'failureList')
5030
+ responseList = self.array_concat(resultList, failureList)
5031
+ return self.parse_orders(responseList)
5032
+
5033
+ def fetch_order(self, id: str, symbol: Str = None, params={}):
5034
+ """
5035
+ fetches information on an order made by the user
5036
+
5037
+ https://www.bitget.com/api-doc/spot/trade/Get-Order-Info
5038
+ https://www.bitget.com/api-doc/contract/trade/Get-Order-Details
5039
+
5040
+ :param str id: the order id
5041
+ :param str symbol: unified symbol of the market the order was made in
5042
+ :param dict [params]: extra parameters specific to the exchange API endpoint
5043
+ :returns dict: An `order structure <https://docs.ccxt.com/#/?id=order-structure>`
5044
+ """
5045
+ if symbol is None:
5046
+ raise ArgumentsRequired(self.id + ' fetchOrder() requires a symbol argument')
5047
+ self.load_markets()
5048
+ sandboxMode = self.safe_bool(self.options, 'sandboxMode', False)
5049
+ market = None
5050
+ if sandboxMode:
5051
+ sandboxSymbol = self.convert_symbol_for_sandbox(symbol)
5052
+ market = self.market(sandboxSymbol)
5053
+ else:
5054
+ market = self.market(symbol)
5055
+ request: dict = {
5056
+ 'orderId': id,
5057
+ }
5058
+ response = None
5059
+ if market['spot']:
5060
+ response = self.privateSpotGetV2SpotTradeOrderInfo(self.extend(request, params))
5061
+ elif market['swap'] or market['future']:
5062
+ request['symbol'] = market['id']
5063
+ productType = None
5064
+ productType, params = self.handle_product_type_and_params(market, params)
5065
+ request['productType'] = productType
5066
+ response = self.privateMixGetV2MixOrderDetail(self.extend(request, params))
5067
+ else:
5068
+ raise NotSupported(self.id + ' fetchOrder() does not support ' + market['type'] + ' orders')
4759
5069
  #
4760
5070
  # spot
4761
5071
  #
@@ -4825,26 +5135,34 @@ class bitget(Exchange, ImplicitAPI):
4825
5135
  #
4826
5136
  if isinstance(response, str):
4827
5137
  response = json.loads(response)
4828
- data = self.safe_value(response, 'data')
4829
- first = self.safe_value(data, 0, data)
5138
+ data = self.safe_dict(response, 'data')
5139
+ if (data is not None):
5140
+ if not isinstance(data, list):
5141
+ return self.parse_order(data, market)
5142
+ dataList = self.safe_list(response, 'data', [])
5143
+ first = self.safe_dict(dataList, 0, {})
4830
5144
  return self.parse_order(first, market)
5145
+ # first = self.safe_dict(data, 0, data)
5146
+ # return self.parse_order(first, market)
4831
5147
 
4832
5148
  def fetch_open_orders(self, symbol: Str = None, since: Int = None, limit: Int = None, params={}) -> List[Order]:
4833
5149
  """
4834
5150
  fetch all unfilled currently open orders
4835
- :see: https://www.bitget.com/api-doc/spot/trade/Get-Unfilled-Orders
4836
- :see: https://www.bitget.com/api-doc/spot/plan/Get-Current-Plan-Order
4837
- :see: https://www.bitget.com/api-doc/contract/trade/Get-Orders-Pending
4838
- :see: https://www.bitget.com/api-doc/contract/plan/get-orders-plan-pending
4839
- :see: https://www.bitget.com/api-doc/margin/cross/trade/Get-Cross-Open-Orders
4840
- :see: https://www.bitget.com/api-doc/margin/isolated/trade/Isolated-Open-Orders
5151
+
5152
+ https://www.bitget.com/api-doc/spot/trade/Get-Unfilled-Orders
5153
+ https://www.bitget.com/api-doc/spot/plan/Get-Current-Plan-Order
5154
+ https://www.bitget.com/api-doc/contract/trade/Get-Orders-Pending
5155
+ https://www.bitget.com/api-doc/contract/plan/get-orders-plan-pending
5156
+ https://www.bitget.com/api-doc/margin/cross/trade/Get-Cross-Open-Orders
5157
+ https://www.bitget.com/api-doc/margin/isolated/trade/Isolated-Open-Orders
5158
+
4841
5159
  :param str symbol: unified market symbol
4842
5160
  :param int [since]: the earliest time in ms to fetch open orders for
4843
5161
  :param int [limit]: the maximum number of open order structures to retrieve
4844
5162
  :param dict [params]: extra parameters specific to the exchange API endpoint
4845
5163
  :param int [params.until]: the latest time in ms to fetch orders for
4846
5164
  :param str [params.planType]: *contract stop only* 'normal_plan': average trigger order, 'profit_loss': opened tp/sl orders, 'track_plan': trailing stop order, default is 'normal_plan'
4847
- :param boolean [params.stop]: set to True for fetching trigger orders
5165
+ :param boolean [params.trigger]: set to True for fetching trigger orders
4848
5166
  :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)
4849
5167
  :param str [params.isPlan]: *swap only* 'plan' for stop orders and 'profit_loss' for tp/sl orders, default is 'plan'
4850
5168
  :param boolean [params.trailing]: set to True if you want to fetch trailing orders
@@ -4854,7 +5172,7 @@ class bitget(Exchange, ImplicitAPI):
4854
5172
  sandboxMode = self.safe_bool(self.options, 'sandboxMode', False)
4855
5173
  market = None
4856
5174
  type = None
4857
- request = {}
5175
+ request: dict = {}
4858
5176
  marginMode = None
4859
5177
  marginMode, params = self.handle_margin_mode_and_params('fetchOpenOrders', params)
4860
5178
  if symbol is not None:
@@ -4882,9 +5200,9 @@ class bitget(Exchange, ImplicitAPI):
4882
5200
  return self.fetch_paginated_call_cursor('fetchOpenOrders', symbol, since, limit, params, cursorReceived, 'idLessThan')
4883
5201
  response = None
4884
5202
  trailing = self.safe_bool(params, 'trailing')
4885
- stop = self.safe_bool_2(params, 'stop', 'trigger')
5203
+ trigger = self.safe_bool_2(params, 'stop', 'trigger')
4886
5204
  planTypeDefined = self.safe_string(params, 'planType') is not None
4887
- isStop = (stop or planTypeDefined)
5205
+ isTrigger = (trigger or planTypeDefined)
4888
5206
  params = self.omit(params, ['stop', 'trigger', 'trailing'])
4889
5207
  request, params = self.handle_until_option('endTime', request, params)
4890
5208
  if since is not None:
@@ -4908,7 +5226,7 @@ class bitget(Exchange, ImplicitAPI):
4908
5226
  elif marginMode == 'cross':
4909
5227
  response = self.privateMarginGetV2MarginCrossedOpenOrders(self.extend(request, query))
4910
5228
  else:
4911
- if stop:
5229
+ if trigger:
4912
5230
  response = self.privateSpotGetV2SpotTradeCurrentPlanOrder(self.extend(request, query))
4913
5231
  else:
4914
5232
  response = self.privateSpotGetV2SpotTradeUnfilledOrders(self.extend(request, query))
@@ -4920,7 +5238,7 @@ class bitget(Exchange, ImplicitAPI):
4920
5238
  planType = self.safe_string(params, 'planType', 'track_plan')
4921
5239
  request['planType'] = planType
4922
5240
  response = self.privateMixGetV2MixOrderOrdersPlanPending(self.extend(request, query))
4923
- elif isStop:
5241
+ elif isTrigger:
4924
5242
  planType = self.safe_string(query, 'planType', 'normal_plan')
4925
5243
  request['planType'] = planType
4926
5244
  response = self.privateMixGetV2MixOrderOrdersPlanPending(self.extend(request, query))
@@ -5103,23 +5421,25 @@ class bitget(Exchange, ImplicitAPI):
5103
5421
  #
5104
5422
  data = self.safe_value(response, 'data')
5105
5423
  if type == 'spot':
5106
- if (marginMode is not None) or stop:
5107
- resultList = self.safe_value(data, 'orderList', [])
5424
+ if (marginMode is not None) or trigger:
5425
+ resultList = self.safe_list(data, 'orderList', [])
5108
5426
  return self.parse_orders(resultList, market, since, limit)
5109
5427
  else:
5110
- result = self.safe_value(data, 'entrustedList', [])
5428
+ result = self.safe_list(data, 'entrustedList', [])
5111
5429
  return self.parse_orders(result, market, since, limit)
5112
5430
  return self.parse_orders(data, market, since, limit)
5113
5431
 
5114
5432
  def fetch_closed_orders(self, symbol: Str = None, since: Int = None, limit: Int = None, params={}) -> List[Order]:
5115
5433
  """
5116
5434
  fetches information on multiple closed orders made by the user
5117
- :see: https://www.bitget.com/api-doc/spot/trade/Get-History-Orders
5118
- :see: https://www.bitget.com/api-doc/spot/plan/Get-History-Plan-Order
5119
- :see: https://www.bitget.com/api-doc/contract/trade/Get-Orders-History
5120
- :see: https://www.bitget.com/api-doc/contract/plan/orders-plan-history
5121
- :see: https://www.bitget.com/api-doc/margin/cross/trade/Get-Cross-Order-History
5122
- :see: https://www.bitget.com/api-doc/margin/isolated/trade/Get-Isolated-Order-History
5435
+
5436
+ https://www.bitget.com/api-doc/spot/trade/Get-History-Orders
5437
+ https://www.bitget.com/api-doc/spot/plan/Get-History-Plan-Order
5438
+ https://www.bitget.com/api-doc/contract/trade/Get-Orders-History
5439
+ https://www.bitget.com/api-doc/contract/plan/orders-plan-history
5440
+ https://www.bitget.com/api-doc/margin/cross/trade/Get-Cross-Order-History
5441
+ https://www.bitget.com/api-doc/margin/isolated/trade/Get-Isolated-Order-History
5442
+
5123
5443
  :param str symbol: unified market symbol of the closed orders
5124
5444
  :param int [since]: timestamp in ms of the earliest order
5125
5445
  :param int [limit]: the max number of closed orders to return
@@ -5138,12 +5458,14 @@ class bitget(Exchange, ImplicitAPI):
5138
5458
  def fetch_canceled_orders(self, symbol: Str = None, since: Int = None, limit: Int = None, params={}):
5139
5459
  """
5140
5460
  fetches information on multiple canceled orders made by the user
5141
- :see: https://www.bitget.com/api-doc/spot/trade/Get-History-Orders
5142
- :see: https://www.bitget.com/api-doc/spot/plan/Get-History-Plan-Order
5143
- :see: https://www.bitget.com/api-doc/contract/trade/Get-Orders-History
5144
- :see: https://www.bitget.com/api-doc/contract/plan/orders-plan-history
5145
- :see: https://www.bitget.com/api-doc/margin/cross/trade/Get-Cross-Order-History
5146
- :see: https://www.bitget.com/api-doc/margin/isolated/trade/Get-Isolated-Order-History
5461
+
5462
+ https://www.bitget.com/api-doc/spot/trade/Get-History-Orders
5463
+ https://www.bitget.com/api-doc/spot/plan/Get-History-Plan-Order
5464
+ https://www.bitget.com/api-doc/contract/trade/Get-Orders-History
5465
+ https://www.bitget.com/api-doc/contract/plan/orders-plan-history
5466
+ https://www.bitget.com/api-doc/margin/cross/trade/Get-Cross-Order-History
5467
+ https://www.bitget.com/api-doc/margin/isolated/trade/Get-Isolated-Order-History
5468
+
5147
5469
  :param str symbol: unified market symbol of the canceled orders
5148
5470
  :param int [since]: timestamp in ms of the earliest order
5149
5471
  :param int [limit]: the max number of canceled orders to return
@@ -5161,12 +5483,14 @@ class bitget(Exchange, ImplicitAPI):
5161
5483
 
5162
5484
  def fetch_canceled_and_closed_orders(self, symbol: Str = None, since: Int = None, limit: Int = None, params={}):
5163
5485
  """
5164
- :see: https://www.bitget.com/api-doc/spot/trade/Get-History-Orders
5165
- :see: https://www.bitget.com/api-doc/spot/plan/Get-History-Plan-Order
5166
- :see: https://www.bitget.com/api-doc/contract/trade/Get-Orders-History
5167
- :see: https://www.bitget.com/api-doc/contract/plan/orders-plan-history
5168
- :see: https://www.bitget.com/api-doc/margin/cross/trade/Get-Cross-Order-History
5169
- :see: https://www.bitget.com/api-doc/margin/isolated/trade/Get-Isolated-Order-History
5486
+
5487
+ https://www.bitget.com/api-doc/spot/trade/Get-History-Orders
5488
+ https://www.bitget.com/api-doc/spot/plan/Get-History-Plan-Order
5489
+ https://www.bitget.com/api-doc/contract/trade/Get-Orders-History
5490
+ https://www.bitget.com/api-doc/contract/plan/orders-plan-history
5491
+ https://www.bitget.com/api-doc/margin/cross/trade/Get-Cross-Order-History
5492
+ https://www.bitget.com/api-doc/margin/isolated/trade/Get-Isolated-Order-History
5493
+
5170
5494
  fetches information on multiple canceled and closed orders made by the user
5171
5495
  :param str symbol: unified market symbol of the market orders were made in
5172
5496
  :param int [since]: the earliest time in ms to fetch orders for
@@ -5181,7 +5505,7 @@ class bitget(Exchange, ImplicitAPI):
5181
5505
  if symbol is not None:
5182
5506
  sandboxSymbol = self.convert_symbol_for_sandbox(symbol)
5183
5507
  symbol = sandboxSymbol
5184
- request = {}
5508
+ request: dict = {}
5185
5509
  if symbol is not None:
5186
5510
  market = self.market(symbol)
5187
5511
  request['symbol'] = market['id']
@@ -5201,7 +5525,7 @@ class bitget(Exchange, ImplicitAPI):
5201
5525
  return self.fetch_paginated_call_cursor('fetchCanceledAndClosedOrders', symbol, since, limit, params, cursorReceived, 'idLessThan')
5202
5526
  response = None
5203
5527
  trailing = self.safe_value(params, 'trailing')
5204
- stop = self.safe_bool_2(params, 'stop', 'trigger')
5528
+ trigger = self.safe_bool_2(params, 'stop', 'trigger')
5205
5529
  params = self.omit(params, ['stop', 'trigger', 'trailing'])
5206
5530
  request, params = self.handle_until_option('endTime', request, params)
5207
5531
  if since is not None:
@@ -5223,20 +5547,19 @@ class bitget(Exchange, ImplicitAPI):
5223
5547
  response = self.privateMarginGetV2MarginIsolatedHistoryOrders(self.extend(request, params))
5224
5548
  elif marginMode == 'cross':
5225
5549
  response = self.privateMarginGetV2MarginCrossedHistoryOrders(self.extend(request, params))
5550
+ elif trigger:
5551
+ if symbol is None:
5552
+ raise ArgumentsRequired(self.id + ' fetchCanceledAndClosedOrders() requires a symbol argument')
5553
+ endTime = self.safe_integer_n(params, ['endTime', 'until'])
5554
+ params = self.omit(params, ['until'])
5555
+ if since is None:
5556
+ since = now - 7776000000
5557
+ request['startTime'] = since
5558
+ if endTime is None:
5559
+ request['endTime'] = now
5560
+ response = self.privateSpotGetV2SpotTradeHistoryPlanOrder(self.extend(request, params))
5226
5561
  else:
5227
- if stop:
5228
- if symbol is None:
5229
- raise ArgumentsRequired(self.id + ' fetchCanceledAndClosedOrders() requires a symbol argument')
5230
- endTime = self.safe_integer_n(params, ['endTime', 'until', 'till'])
5231
- params = self.omit(params, ['until', 'till'])
5232
- if since is None:
5233
- since = now - 7776000000
5234
- request['startTime'] = since
5235
- if endTime is None:
5236
- request['endTime'] = now
5237
- response = self.privateSpotGetV2SpotTradeHistoryPlanOrder(self.extend(request, params))
5238
- else:
5239
- response = self.privateSpotGetV2SpotTradeHistoryOrders(self.extend(request, params))
5562
+ response = self.privateSpotGetV2SpotTradeHistoryOrders(self.extend(request, params))
5240
5563
  else:
5241
5564
  productType = None
5242
5565
  productType, params = self.handle_product_type_and_params(market, params)
@@ -5245,7 +5568,7 @@ class bitget(Exchange, ImplicitAPI):
5245
5568
  planType = self.safe_string(params, 'planType', 'track_plan')
5246
5569
  request['planType'] = planType
5247
5570
  response = self.privateMixGetV2MixOrderOrdersPlanHistory(self.extend(request, params))
5248
- elif stop:
5571
+ elif trigger:
5249
5572
  planType = self.safe_string(params, 'planType', 'normal_plan')
5250
5573
  request['planType'] = planType
5251
5574
  response = self.privateMixGetV2MixOrderOrdersPlanHistory(self.extend(request, params))
@@ -5431,29 +5754,31 @@ class bitget(Exchange, ImplicitAPI):
5431
5754
  #
5432
5755
  data = self.safe_value(response, 'data', {})
5433
5756
  if marketType == 'spot':
5434
- if (marginMode is not None) or stop:
5757
+ if (marginMode is not None) or trigger:
5435
5758
  return self.parse_orders(self.safe_value(data, 'orderList', []), market, since, limit)
5436
5759
  else:
5437
5760
  return self.parse_orders(self.safe_value(data, 'entrustedList', []), market, since, limit)
5438
5761
  if isinstance(response, str):
5439
5762
  response = json.loads(response)
5440
- orders = self.safe_value(response, 'data', [])
5763
+ orders = self.safe_list(response, 'data', [])
5441
5764
  return self.parse_orders(orders, market, since, limit)
5442
5765
 
5443
- def fetch_ledger(self, code: Str = None, since: Int = None, limit: Int = None, params={}):
5766
+ def fetch_ledger(self, code: Str = None, since: Int = None, limit: Int = None, params={}) -> List[LedgerEntry]:
5444
5767
  """
5445
- :see: https://www.bitget.com/api-doc/spot/account/Get-Account-Bills
5446
- :see: https://www.bitget.com/api-doc/contract/account/Get-Account-Bill
5447
- fetch the history of changes, actions done by the user or operations that altered balance of the user
5448
- :param str code: unified currency code, default is None
5768
+ fetch the history of changes, actions done by the user or operations that altered the balance of the user
5769
+
5770
+ https://www.bitget.com/api-doc/spot/account/Get-Account-Bills
5771
+ https://www.bitget.com/api-doc/contract/account/Get-Account-Bill
5772
+
5773
+ :param str [code]: unified currency code, default is None
5449
5774
  :param int [since]: timestamp in ms of the earliest ledger entry, default is None
5450
- :param int [limit]: max number of ledger entrys to return, default is None
5775
+ :param int [limit]: max number of ledger entries to return, default is None
5451
5776
  :param dict [params]: extra parameters specific to the exchange API endpoint
5452
5777
  :param int [params.until]: end time in ms
5453
5778
  :param str [params.symbol]: *contract only* unified market symbol
5454
5779
  :param str [params.productType]: *contract only* 'USDT-FUTURES', 'USDC-FUTURES', 'COIN-FUTURES', 'SUSDT-FUTURES', 'SUSDC-FUTURES' or 'SCOIN-FUTURES'
5455
5780
  :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)
5456
- :returns dict: a `ledger structure <https://docs.ccxt.com/#/?id=ledger-structure>`
5781
+ :returns dict: a `ledger structure <https://docs.ccxt.com/#/?id=ledger>`
5457
5782
  """
5458
5783
  self.load_markets()
5459
5784
  symbol = self.safe_string(params, 'symbol')
@@ -5476,10 +5801,10 @@ class bitget(Exchange, ImplicitAPI):
5476
5801
  cursorReceived = 'endId'
5477
5802
  return self.fetch_paginated_call_cursor('fetchLedger', symbol, since, limit, params, cursorReceived, 'idLessThan')
5478
5803
  currency = None
5479
- request = {}
5804
+ request: dict = {}
5480
5805
  if code is not None:
5481
5806
  currency = self.currency(code)
5482
- request['coin'] = currency['code']
5807
+ request['coin'] = currency['id']
5483
5808
  request, params = self.handle_until_option('endTime', request, params)
5484
5809
  if since is not None:
5485
5810
  request['startTime'] = since
@@ -5545,7 +5870,7 @@ class bitget(Exchange, ImplicitAPI):
5545
5870
  return self.parse_ledger(bills, currency, since, limit)
5546
5871
  return self.parse_ledger(data, currency, since, limit)
5547
5872
 
5548
- def parse_ledger_entry(self, item, currency: Currency = None):
5873
+ def parse_ledger_entry(self, item: dict, currency: Currency = None) -> LedgerEntry:
5549
5874
  #
5550
5875
  # spot
5551
5876
  #
@@ -5575,6 +5900,7 @@ class bitget(Exchange, ImplicitAPI):
5575
5900
  #
5576
5901
  currencyId = self.safe_string(item, 'coin')
5577
5902
  code = self.safe_currency_code(currencyId, currency)
5903
+ currency = self.safe_currency(currencyId, currency)
5578
5904
  timestamp = self.safe_integer(item, 'cTime')
5579
5905
  after = self.safe_number(item, 'balance')
5580
5906
  fee = self.safe_number_2(item, 'fees', 'fee')
@@ -5583,7 +5909,7 @@ class bitget(Exchange, ImplicitAPI):
5583
5909
  direction = 'in'
5584
5910
  if amountRaw.find('-') >= 0:
5585
5911
  direction = 'out'
5586
- return {
5912
+ return self.safe_ledger_entry({
5587
5913
  'info': item,
5588
5914
  'id': self.safe_string(item, 'billId'),
5589
5915
  'timestamp': timestamp,
@@ -5598,11 +5924,14 @@ class bitget(Exchange, ImplicitAPI):
5598
5924
  'before': None,
5599
5925
  'after': after,
5600
5926
  'status': None,
5601
- 'fee': fee,
5602
- }
5927
+ 'fee': {
5928
+ 'currency': code,
5929
+ 'cost': fee,
5930
+ },
5931
+ }, currency)
5603
5932
 
5604
5933
  def parse_ledger_type(self, type):
5605
- types = {
5934
+ types: dict = {
5606
5935
  'trans_to_cross': 'transfer',
5607
5936
  'trans_from_cross': 'transfer',
5608
5937
  'trans_to_exchange': 'transfer',
@@ -5649,10 +5978,12 @@ class bitget(Exchange, ImplicitAPI):
5649
5978
  def fetch_my_trades(self, symbol: Str = None, since: Int = None, limit: Int = None, params={}) -> List[Trade]:
5650
5979
  """
5651
5980
  fetch all trades made by the user
5652
- :see: https://www.bitget.com/api-doc/spot/trade/Get-Fills
5653
- :see: https://www.bitget.com/api-doc/contract/trade/Get-Order-Fills
5654
- :see: https://www.bitget.com/api-doc/margin/cross/trade/Get-Cross-Order-Fills
5655
- :see: https://www.bitget.com/api-doc/margin/isolated/trade/Get-Isolated-Transaction-Details
5981
+
5982
+ https://www.bitget.com/api-doc/spot/trade/Get-Fills
5983
+ https://www.bitget.com/api-doc/contract/trade/Get-Order-Fills
5984
+ https://www.bitget.com/api-doc/margin/cross/trade/Get-Cross-Order-Fills
5985
+ https://www.bitget.com/api-doc/margin/isolated/trade/Get-Isolated-Transaction-Details
5986
+
5656
5987
  :param str symbol: unified market symbol
5657
5988
  :param int [since]: the earliest time in ms to fetch trades for
5658
5989
  :param int [limit]: the maximum number of trades structures to retrieve
@@ -5684,7 +6015,7 @@ class bitget(Exchange, ImplicitAPI):
5684
6015
  cursorReceived = 'endId'
5685
6016
  return self.fetch_paginated_call_cursor('fetchMyTrades', symbol, since, limit, params, cursorReceived, 'idLessThan')
5686
6017
  response = None
5687
- request = {
6018
+ request: dict = {
5688
6019
  'symbol': market['id'],
5689
6020
  }
5690
6021
  request, params = self.handle_until_option('endTime', request, params)
@@ -5808,17 +6139,19 @@ class bitget(Exchange, ImplicitAPI):
5808
6139
  #
5809
6140
  data = self.safe_value(response, 'data')
5810
6141
  if (market['swap']) or (market['future']):
5811
- fillList = self.safe_value(data, 'fillList', [])
6142
+ fillList = self.safe_list(data, 'fillList', [])
5812
6143
  return self.parse_trades(fillList, market, since, limit)
5813
6144
  elif marginMode is not None:
5814
- fills = self.safe_value(data, 'fills', [])
6145
+ fills = self.safe_list(data, 'fills', [])
5815
6146
  return self.parse_trades(fills, market, since, limit)
5816
6147
  return self.parse_trades(data, market, since, limit)
5817
6148
 
5818
6149
  def fetch_position(self, symbol: str, params={}):
5819
6150
  """
5820
6151
  fetch data on a single open contract trade position
5821
- :see: https://www.bitget.com/api-doc/contract/position/get-single-position
6152
+
6153
+ https://www.bitget.com/api-doc/contract/position/get-single-position
6154
+
5822
6155
  :param str symbol: unified market symbol of the market the position is held in
5823
6156
  :param dict [params]: extra parameters specific to the exchange API endpoint
5824
6157
  :returns dict: a `position structure <https://docs.ccxt.com/#/?id=position-structure>`
@@ -5833,7 +6166,7 @@ class bitget(Exchange, ImplicitAPI):
5833
6166
  market = self.market(symbol)
5834
6167
  productType = None
5835
6168
  productType, params = self.handle_product_type_and_params(market, params)
5836
- request = {
6169
+ request: dict = {
5837
6170
  'symbol': market['id'],
5838
6171
  'marginCoin': market['settleId'],
5839
6172
  'productType': productType,
@@ -5869,15 +6202,17 @@ class bitget(Exchange, ImplicitAPI):
5869
6202
  # ]
5870
6203
  # }
5871
6204
  #
5872
- data = self.safe_value(response, 'data', [])
5873
- first = self.safe_value(data, 0, {})
6205
+ data = self.safe_list(response, 'data', [])
6206
+ first = self.safe_dict(data, 0, {})
5874
6207
  return self.parse_position(first, market)
5875
6208
 
5876
6209
  def fetch_positions(self, symbols: Strings = None, params={}) -> List[Position]:
5877
6210
  """
5878
6211
  fetch all open positions
5879
- :see: https://www.bitget.com/api-doc/contract/position/get-all-position
5880
- :see: https://www.bitget.com/api-doc/contract/position/Get-History-Position
6212
+
6213
+ https://www.bitget.com/api-doc/contract/position/get-all-position
6214
+ https://www.bitget.com/api-doc/contract/position/Get-History-Position
6215
+
5881
6216
  :param str[] [symbols]: list of unified market symbols
5882
6217
  :param dict [params]: extra parameters specific to the exchange API endpoint
5883
6218
  :param str [params.marginCoin]: the settle currency of the positions, needs to match the productType
@@ -5909,7 +6244,7 @@ class bitget(Exchange, ImplicitAPI):
5909
6244
  market = self.market(first)
5910
6245
  productType = None
5911
6246
  productType, params = self.handle_product_type_and_params(market, params)
5912
- request = {
6247
+ request: dict = {
5913
6248
  'productType': productType,
5914
6249
  }
5915
6250
  response = None
@@ -6010,7 +6345,7 @@ class bitget(Exchange, ImplicitAPI):
6010
6345
  symbols = self.market_symbols(symbols)
6011
6346
  return self.filter_by_array_positions(result, 'symbol', symbols, False)
6012
6347
 
6013
- def parse_position(self, position, market: Market = None):
6348
+ def parse_position(self, position: dict, market: Market = None):
6014
6349
  #
6015
6350
  # fetchPosition
6016
6351
  #
@@ -6060,7 +6395,7 @@ class bitget(Exchange, ImplicitAPI):
6060
6395
  # "cTime": "1700807507275"
6061
6396
  # }
6062
6397
  #
6063
- # fetchPositions: privateMixGetV2MixPositionHistoryPosition
6398
+ # fetchPositionsHistory: privateMixGetV2MixPositionHistoryPosition
6064
6399
  #
6065
6400
  # {
6066
6401
  # "symbol": "BTCUSDT",
@@ -6176,7 +6511,9 @@ class bitget(Exchange, ImplicitAPI):
6176
6511
  def fetch_funding_rate_history(self, symbol: Str = None, since: Int = None, limit: Int = None, params={}):
6177
6512
  """
6178
6513
  fetches historical funding rate prices
6179
- :see: https://www.bitget.com/api-doc/contract/market/Get-History-Funding-Rate
6514
+
6515
+ https://www.bitget.com/api-doc/contract/market/Get-History-Funding-Rate
6516
+
6180
6517
  :param str symbol: unified symbol of the market to fetch the funding rate history for
6181
6518
  :param int [since]: timestamp in ms of the earliest funding rate to fetch
6182
6519
  :param int [limit]: the maximum amount of funding rate structures to fetch
@@ -6200,7 +6537,7 @@ class bitget(Exchange, ImplicitAPI):
6200
6537
  market = self.market(symbol)
6201
6538
  productType = None
6202
6539
  productType, params = self.handle_product_type_and_params(market, params)
6203
- request = {
6540
+ request: dict = {
6204
6541
  'symbol': market['id'],
6205
6542
  'productType': productType,
6206
6543
  # 'pageSize': limit, # default 20
@@ -6240,10 +6577,12 @@ class bitget(Exchange, ImplicitAPI):
6240
6577
  sorted = self.sort_by(rates, 'timestamp')
6241
6578
  return self.filter_by_symbol_since_limit(sorted, market['symbol'], since, limit)
6242
6579
 
6243
- def fetch_funding_rate(self, symbol: str, params={}):
6580
+ def fetch_funding_rate(self, symbol: str, params={}) -> FundingRate:
6244
6581
  """
6245
6582
  fetch the current funding rate
6246
- :see: https://www.bitget.com/api-doc/contract/market/Get-Current-Funding-Rate
6583
+
6584
+ https://www.bitget.com/api-doc/contract/market/Get-Current-Funding-Rate
6585
+
6247
6586
  :param str symbol: unified market symbol
6248
6587
  :param dict [params]: extra parameters specific to the exchange API endpoint
6249
6588
  :returns dict: a `funding rate structure <https://docs.ccxt.com/#/?id=funding-rate-structure>`
@@ -6260,7 +6599,7 @@ class bitget(Exchange, ImplicitAPI):
6260
6599
  raise BadSymbol(self.id + ' fetchFundingRate() supports swap contracts only')
6261
6600
  productType = None
6262
6601
  productType, params = self.handle_product_type_and_params(market, params)
6263
- request = {
6602
+ request: dict = {
6264
6603
  'symbol': market['id'],
6265
6604
  'productType': productType,
6266
6605
  }
@@ -6281,39 +6620,148 @@ class bitget(Exchange, ImplicitAPI):
6281
6620
  data = self.safe_value(response, 'data', [])
6282
6621
  return self.parse_funding_rate(data[0], market)
6283
6622
 
6284
- def parse_funding_rate(self, contract, market: Market = None):
6623
+ def fetch_funding_rates(self, symbols: Strings = None, params={}) -> FundingRates:
6624
+ """
6625
+ fetch the current funding rates for all markets
6626
+
6627
+ https://www.bitget.com/api-doc/contract/market/Get-All-Symbol-Ticker
6628
+
6629
+ :param str[] [symbols]: list of unified market symbols
6630
+ :param dict [params]: extra parameters specific to the exchange API endpoint
6631
+ :param str [params.subType]: *contract only* 'linear', 'inverse'
6632
+ :param str [params.productType]: *contract only* 'USDT-FUTURES', 'USDC-FUTURES', 'COIN-FUTURES', 'SUSDT-FUTURES', 'SUSDC-FUTURES' or 'SCOIN-FUTURES'
6633
+ :returns dict: a dictionary of `funding rate structures <https://docs.ccxt.com/#/?id=funding-rates-structure>`, indexed by market symbols
6634
+ """
6635
+ self.load_markets()
6636
+ market = None
6637
+ if symbols is not None:
6638
+ symbol = self.safe_value(symbols, 0)
6639
+ sandboxMode = self.safe_bool(self.options, 'sandboxMode', False)
6640
+ if sandboxMode:
6641
+ sandboxSymbol = self.convert_symbol_for_sandbox(symbol)
6642
+ market = self.market(sandboxSymbol)
6643
+ else:
6644
+ market = self.market(symbol)
6645
+ request: dict = {}
6646
+ productType = None
6647
+ productType, params = self.handle_product_type_and_params(market, params)
6648
+ request['productType'] = productType
6649
+ response = self.publicMixGetV2MixMarketTickers(self.extend(request, params))
6650
+ # {
6651
+ # "code": "00000",
6652
+ # "msg": "success",
6653
+ # "requestTime": 1700533773477,
6654
+ # "data": [
6655
+ # {
6656
+ # "symbol": "BTCUSD",
6657
+ # "lastPr": "29904.5",
6658
+ # "askPr": "29904.5",
6659
+ # "bidPr": "29903.5",
6660
+ # "bidSz": "0.5091",
6661
+ # "askSz": "2.2694",
6662
+ # "high24h": "0",
6663
+ # "low24h": "0",
6664
+ # "ts": "1695794271400",
6665
+ # "change24h": "0",
6666
+ # "baseVolume": "0",
6667
+ # "quoteVolume": "0",
6668
+ # "usdtVolume": "0",
6669
+ # "openUtc": "0",
6670
+ # "changeUtc24h": "0",
6671
+ # "indexPrice": "29132.353333",
6672
+ # "fundingRate": "-0.0007",
6673
+ # "holdingAmount": "125.6844",
6674
+ # "deliveryStartTime": null,
6675
+ # "deliveryTime": null,
6676
+ # "deliveryStatus": "delivery_normal",
6677
+ # "open24h": "0",
6678
+ # "markPrice": "12345"
6679
+ # },
6680
+ # ]
6681
+ # }
6682
+ symbols = self.market_symbols(symbols)
6683
+ data = self.safe_list(response, 'data', [])
6684
+ return self.parse_funding_rates(data, symbols)
6685
+
6686
+ def parse_funding_rate(self, contract, market: Market = None) -> FundingRate:
6687
+ #
6688
+ # fetchFundingRate
6285
6689
  #
6286
6690
  # {
6287
6691
  # "symbol": "BTCUSDT",
6288
6692
  # "fundingRate": "-0.000182"
6289
6693
  # }
6290
6694
  #
6695
+ # fetchFundingInterval
6696
+ #
6697
+ # {
6698
+ # "symbol": "BTCUSDT",
6699
+ # "nextFundingTime": "1727942400000",
6700
+ # "ratePeriod": "8"
6701
+ # }
6702
+ # fetchFundingRates
6703
+ # {
6704
+ # "symbol": "BTCUSD",
6705
+ # "lastPr": "29904.5",
6706
+ # "askPr": "29904.5",
6707
+ # "bidPr": "29903.5",
6708
+ # "bidSz": "0.5091",
6709
+ # "askSz": "2.2694",
6710
+ # "high24h": "0",
6711
+ # "low24h": "0",
6712
+ # "ts": "1695794271400",
6713
+ # "change24h": "0",
6714
+ # "baseVolume": "0",
6715
+ # "quoteVolume": "0",
6716
+ # "usdtVolume": "0",
6717
+ # "openUtc": "0",
6718
+ # "changeUtc24h": "0",
6719
+ # "indexPrice": "29132.353333",
6720
+ # "fundingRate": "-0.0007",
6721
+ # "holdingAmount": "125.6844",
6722
+ # "deliveryStartTime": null,
6723
+ # "deliveryTime": null,
6724
+ # "deliveryStatus": "delivery_normal",
6725
+ # "open24h": "0",
6726
+ # "markPrice": "12345"
6727
+ # }
6291
6728
  marketId = self.safe_string(contract, 'symbol')
6292
6729
  symbol = self.safe_symbol(marketId, market, None, 'swap')
6730
+ fundingTimestamp = self.safe_integer(contract, 'nextFundingTime')
6731
+ interval = self.safe_string(contract, 'ratePeriod')
6732
+ timestamp = self.safe_integer(contract, 'ts')
6733
+ markPrice = self.safe_number(contract, 'markPrice')
6734
+ indexPrice = self.safe_number(contract, 'indexPrice')
6735
+ intervalString = None
6736
+ if interval is not None:
6737
+ intervalString = interval + 'h'
6293
6738
  return {
6294
6739
  'info': contract,
6295
6740
  'symbol': symbol,
6296
- 'markPrice': None,
6297
- 'indexPrice': None,
6741
+ 'markPrice': markPrice,
6742
+ 'indexPrice': indexPrice,
6298
6743
  'interestRate': None,
6299
6744
  'estimatedSettlePrice': None,
6300
- 'timestamp': None,
6301
- 'datetime': None,
6745
+ 'timestamp': timestamp,
6746
+ 'datetime': self.iso8601(timestamp),
6302
6747
  'fundingRate': self.safe_number(contract, 'fundingRate'),
6303
- 'fundingTimestamp': None,
6304
- 'fundingDatetime': None,
6748
+ 'fundingTimestamp': fundingTimestamp,
6749
+ 'fundingDatetime': self.iso8601(fundingTimestamp),
6305
6750
  'nextFundingRate': None,
6306
6751
  'nextFundingTimestamp': None,
6307
6752
  'nextFundingDatetime': None,
6308
6753
  'previousFundingRate': None,
6309
6754
  'previousFundingTimestamp': None,
6310
6755
  'previousFundingDatetime': None,
6756
+ 'interval': intervalString,
6311
6757
  }
6312
6758
 
6313
6759
  def fetch_funding_history(self, symbol: Str = None, since: Int = None, limit: Int = None, params={}) -> List[FundingHistory]:
6314
6760
  """
6315
6761
  fetch the funding history
6316
- :see: https://www.bitget.com/api-doc/contract/account/Get-Account-Bill
6762
+
6763
+ https://www.bitget.com/api-doc/contract/account/Get-Account-Bill
6764
+
6317
6765
  :param str symbol: unified market symbol
6318
6766
  :param int [since]: the starting timestamp in milliseconds
6319
6767
  :param int [limit]: the number of entries to return
@@ -6340,7 +6788,7 @@ class bitget(Exchange, ImplicitAPI):
6340
6788
  raise BadSymbol(self.id + ' fetchFundingHistory() supports swap contracts only')
6341
6789
  productType = None
6342
6790
  productType, params = self.handle_product_type_and_params(market, params)
6343
- request = {
6791
+ request: dict = {
6344
6792
  'symbol': market['id'],
6345
6793
  'marginCoin': market['settleId'],
6346
6794
  'businessType': 'contract_settle_fee',
@@ -6415,7 +6863,7 @@ class bitget(Exchange, ImplicitAPI):
6415
6863
  sorted = self.sort_by(result, 'timestamp')
6416
6864
  return self.filter_by_since_limit(sorted, since, limit)
6417
6865
 
6418
- def modify_margin_helper(self, symbol: str, amount, type, params={}):
6866
+ def modify_margin_helper(self, symbol: str, amount, type, params={}) -> MarginModification:
6419
6867
  self.load_markets()
6420
6868
  holdSide = self.safe_string(params, 'holdSide')
6421
6869
  sandboxMode = self.safe_bool(self.options, 'sandboxMode', False)
@@ -6427,7 +6875,7 @@ class bitget(Exchange, ImplicitAPI):
6427
6875
  market = self.market(symbol)
6428
6876
  productType = None
6429
6877
  productType, params = self.handle_product_type_and_params(market, params)
6430
- request = {
6878
+ request: dict = {
6431
6879
  'symbol': market['id'],
6432
6880
  'marginCoin': market['settleId'],
6433
6881
  'amount': self.amount_to_precision(symbol, amount), # positive value for adding margin, negative for reducing
@@ -6449,22 +6897,38 @@ class bitget(Exchange, ImplicitAPI):
6449
6897
  'type': type,
6450
6898
  })
6451
6899
 
6452
- def parse_margin_modification(self, data, market: Market = None):
6900
+ def parse_margin_modification(self, data: dict, market: Market = None) -> MarginModification:
6901
+ #
6902
+ # addMargin/reduceMargin
6903
+ #
6904
+ # {
6905
+ # "code": "00000",
6906
+ # "msg": "success",
6907
+ # "requestTime": 1700813444618,
6908
+ # "data": ""
6909
+ # }
6910
+ #
6453
6911
  errorCode = self.safe_string(data, 'code')
6454
6912
  status = 'ok' if (errorCode == '00000') else 'failed'
6455
6913
  return {
6456
6914
  'info': data,
6915
+ 'symbol': market['symbol'],
6457
6916
  'type': None,
6917
+ 'marginMode': 'isolated',
6458
6918
  'amount': None,
6919
+ 'total': None,
6459
6920
  'code': market['settle'],
6460
- 'symbol': market['symbol'],
6461
6921
  'status': status,
6922
+ 'timestamp': None,
6923
+ 'datetime': None,
6462
6924
  }
6463
6925
 
6464
- def reduce_margin(self, symbol: str, amount, params={}):
6926
+ def reduce_margin(self, symbol: str, amount: float, params={}) -> MarginModification:
6465
6927
  """
6466
6928
  remove margin from a position
6467
- :see: https://www.bitget.com/api-doc/contract/account/Change-Margin
6929
+
6930
+ https://www.bitget.com/api-doc/contract/account/Change-Margin
6931
+
6468
6932
  :param str symbol: unified market symbol
6469
6933
  :param float amount: the amount of margin to remove
6470
6934
  :param dict [params]: extra parameters specific to the exchange API endpoint
@@ -6477,10 +6941,12 @@ class bitget(Exchange, ImplicitAPI):
6477
6941
  raise ArgumentsRequired(self.id + ' reduceMargin() requires a holdSide parameter, either long or short')
6478
6942
  return self.modify_margin_helper(symbol, amount, 'reduce', params)
6479
6943
 
6480
- def add_margin(self, symbol: str, amount, params={}):
6944
+ def add_margin(self, symbol: str, amount: float, params={}) -> MarginModification:
6481
6945
  """
6482
6946
  add margin
6483
- :see: https://www.bitget.com/api-doc/contract/account/Change-Margin
6947
+
6948
+ https://www.bitget.com/api-doc/contract/account/Change-Margin
6949
+
6484
6950
  :param str symbol: unified market symbol
6485
6951
  :param float amount: the amount of margin to add
6486
6952
  :param dict [params]: extra parameters specific to the exchange API endpoint
@@ -6494,7 +6960,9 @@ class bitget(Exchange, ImplicitAPI):
6494
6960
  def fetch_leverage(self, symbol: str, params={}) -> Leverage:
6495
6961
  """
6496
6962
  fetch the set leverage for a market
6497
- :see: https://www.bitget.com/api-doc/contract/account/Get-Single-Account
6963
+
6964
+ https://www.bitget.com/api-doc/contract/account/Get-Single-Account
6965
+
6498
6966
  :param str symbol: unified market symbol
6499
6967
  :param dict [params]: extra parameters specific to the exchange API endpoint
6500
6968
  :returns dict: a `leverage structure <https://docs.ccxt.com/#/?id=leverage-structure>`
@@ -6509,7 +6977,7 @@ class bitget(Exchange, ImplicitAPI):
6509
6977
  market = self.market(symbol)
6510
6978
  productType = None
6511
6979
  productType, params = self.handle_product_type_and_params(market, params)
6512
- request = {
6980
+ request: dict = {
6513
6981
  'symbol': market['id'],
6514
6982
  'marginCoin': market['settleId'],
6515
6983
  'productType': productType,
@@ -6546,7 +7014,7 @@ class bitget(Exchange, ImplicitAPI):
6546
7014
  data = self.safe_dict(response, 'data', {})
6547
7015
  return self.parse_leverage(data, market)
6548
7016
 
6549
- def parse_leverage(self, leverage, market=None) -> Leverage:
7017
+ def parse_leverage(self, leverage: dict, market: Market = None) -> Leverage:
6550
7018
  return {
6551
7019
  'info': leverage,
6552
7020
  'symbol': market['symbol'],
@@ -6558,7 +7026,9 @@ class bitget(Exchange, ImplicitAPI):
6558
7026
  def set_leverage(self, leverage: Int, symbol: Str = None, params={}):
6559
7027
  """
6560
7028
  set the level of leverage for a market
6561
- :see: https://www.bitget.com/api-doc/contract/account/Change-Leverage
7029
+
7030
+ https://www.bitget.com/api-doc/contract/account/Change-Leverage
7031
+
6562
7032
  :param int leverage: the rate of leverage
6563
7033
  :param str symbol: unified market symbol
6564
7034
  :param dict [params]: extra parameters specific to the exchange API endpoint
@@ -6577,7 +7047,7 @@ class bitget(Exchange, ImplicitAPI):
6577
7047
  market = self.market(symbol)
6578
7048
  productType = None
6579
7049
  productType, params = self.handle_product_type_and_params(market, params)
6580
- request = {
7050
+ request: dict = {
6581
7051
  'symbol': market['id'],
6582
7052
  'marginCoin': market['settleId'],
6583
7053
  'leverage': self.number_to_string(leverage),
@@ -6605,7 +7075,9 @@ class bitget(Exchange, ImplicitAPI):
6605
7075
  def set_margin_mode(self, marginMode: str, symbol: Str = None, params={}):
6606
7076
  """
6607
7077
  set margin mode to 'cross' or 'isolated'
6608
- :see: https://www.bitget.com/api-doc/contract/account/Change-Margin-Mode
7078
+
7079
+ https://www.bitget.com/api-doc/contract/account/Change-Margin-Mode
7080
+
6609
7081
  :param str marginMode: 'cross' or 'isolated'
6610
7082
  :param str symbol: unified market symbol
6611
7083
  :param dict [params]: extra parameters specific to the exchange API endpoint
@@ -6628,7 +7100,7 @@ class bitget(Exchange, ImplicitAPI):
6628
7100
  market = self.market(symbol)
6629
7101
  productType = None
6630
7102
  productType, params = self.handle_product_type_and_params(market, params)
6631
- request = {
7103
+ request: dict = {
6632
7104
  'symbol': market['id'],
6633
7105
  'marginCoin': market['settleId'],
6634
7106
  'marginMode': marginMode,
@@ -6654,7 +7126,9 @@ class bitget(Exchange, ImplicitAPI):
6654
7126
  def set_position_mode(self, hedged: bool, symbol: Str = None, params={}):
6655
7127
  """
6656
7128
  set hedged to True or False for a market
6657
- :see: https://www.bitget.com/api-doc/contract/account/Change-Hold-Mode
7129
+
7130
+ https://www.bitget.com/api-doc/contract/account/Change-Hold-Mode
7131
+
6658
7132
  :param bool hedged: set to True to use dualSidePosition
6659
7133
  :param str symbol: not used by bitget setPositionMode()
6660
7134
  :param dict [params]: extra parameters specific to the exchange API endpoint
@@ -6673,7 +7147,7 @@ class bitget(Exchange, ImplicitAPI):
6673
7147
  market = self.market(symbol)
6674
7148
  productType = None
6675
7149
  productType, params = self.handle_product_type_and_params(market, params)
6676
- request = {
7150
+ request: dict = {
6677
7151
  'posMode': posMode,
6678
7152
  'productType': productType,
6679
7153
  }
@@ -6693,7 +7167,9 @@ class bitget(Exchange, ImplicitAPI):
6693
7167
  def fetch_open_interest(self, symbol: str, params={}):
6694
7168
  """
6695
7169
  retrieves the open interest of a contract trading pair
6696
- :see: https://www.bitget.com/api-doc/contract/market/Get-Open-Interest
7170
+
7171
+ https://www.bitget.com/api-doc/contract/market/Get-Open-Interest
7172
+
6697
7173
  :param str symbol: unified CCXT market symbol
6698
7174
  :param dict [params]: exchange specific parameters
6699
7175
  :returns dict} an open interest structure{@link https://docs.ccxt.com/#/?id=open-interest-structure:
@@ -6710,7 +7186,7 @@ class bitget(Exchange, ImplicitAPI):
6710
7186
  raise BadRequest(self.id + ' fetchOpenInterest() supports contract markets only')
6711
7187
  productType = None
6712
7188
  productType, params = self.handle_product_type_and_params(market, params)
6713
- request = {
7189
+ request: dict = {
6714
7190
  'symbol': market['id'],
6715
7191
  'productType': productType,
6716
7192
  }
@@ -6731,7 +7207,7 @@ class bitget(Exchange, ImplicitAPI):
6731
7207
  # }
6732
7208
  # }
6733
7209
  #
6734
- data = self.safe_value(response, 'data', {})
7210
+ data = self.safe_dict(response, 'data', {})
6735
7211
  return self.parse_open_interest(data, market)
6736
7212
 
6737
7213
  def parse_open_interest(self, interest, market: Market = None):
@@ -6758,10 +7234,12 @@ class bitget(Exchange, ImplicitAPI):
6758
7234
  'info': interest,
6759
7235
  }, market)
6760
7236
 
6761
- def fetch_transfers(self, code: Str = None, since: Int = None, limit: Int = None, params={}):
7237
+ def fetch_transfers(self, code: Str = None, since: Int = None, limit: Int = None, params={}) -> List[TransferEntry]:
6762
7238
  """
6763
7239
  fetch a history of internal transfers made on an account
6764
- :see: https://www.bitget.com/api-doc/spot/account/Get-Account-TransferRecords
7240
+
7241
+ https://www.bitget.com/api-doc/spot/account/Get-Account-TransferRecords
7242
+
6765
7243
  :param str code: unified currency code of the currency transferred
6766
7244
  :param int [since]: the earliest time in ms to fetch transfers for
6767
7245
  :param int [limit]: the maximum number of transfers structures to retrieve
@@ -6779,8 +7257,8 @@ class bitget(Exchange, ImplicitAPI):
6779
7257
  accountsByType = self.safe_value(self.options, 'accountsByType', {})
6780
7258
  type = self.safe_string(accountsByType, fromAccount)
6781
7259
  currency = self.currency(code)
6782
- request = {
6783
- 'coin': currency['code'],
7260
+ request: dict = {
7261
+ 'coin': currency['id'],
6784
7262
  'fromType': type,
6785
7263
  }
6786
7264
  if since is not None:
@@ -6810,13 +7288,15 @@ class bitget(Exchange, ImplicitAPI):
6810
7288
  # ]
6811
7289
  # }
6812
7290
  #
6813
- data = self.safe_value(response, 'data', [])
7291
+ data = self.safe_list(response, 'data', [])
6814
7292
  return self.parse_transfers(data, currency, since, limit)
6815
7293
 
6816
7294
  def transfer(self, code: str, amount: float, fromAccount: str, toAccount: str, params={}) -> TransferEntry:
6817
7295
  """
6818
7296
  transfer currency internally between wallets on the same account
6819
- :see: https://www.bitget.com/api-doc/spot/account/Wallet-Transfer
7297
+
7298
+ https://www.bitget.com/api-doc/spot/account/Wallet-Transfer
7299
+
6820
7300
  :param str code: unified currency code
6821
7301
  :param float amount: amount to transfer
6822
7302
  :param str fromAccount: account to transfer from
@@ -6831,11 +7311,11 @@ class bitget(Exchange, ImplicitAPI):
6831
7311
  accountsByType = self.safe_value(self.options, 'accountsByType', {})
6832
7312
  fromType = self.safe_string(accountsByType, fromAccount)
6833
7313
  toType = self.safe_string(accountsByType, toAccount)
6834
- request = {
7314
+ request: dict = {
6835
7315
  'fromType': fromType,
6836
7316
  'toType': toType,
6837
7317
  'amount': amount,
6838
- 'coin': currency['code'],
7318
+ 'coin': currency['id'],
6839
7319
  }
6840
7320
  symbol = self.safe_string(params, 'symbol')
6841
7321
  params = self.omit(params, 'symbol')
@@ -6859,7 +7339,7 @@ class bitget(Exchange, ImplicitAPI):
6859
7339
  data['ts'] = self.safe_integer(response, 'requestTime')
6860
7340
  return self.parse_transfer(data, currency)
6861
7341
 
6862
- def parse_transfer(self, transfer, currency: Currency = None):
7342
+ def parse_transfer(self, transfer: dict, currency: Currency = None) -> TransferEntry:
6863
7343
  #
6864
7344
  # transfer
6865
7345
  #
@@ -6904,8 +7384,8 @@ class bitget(Exchange, ImplicitAPI):
6904
7384
  'status': self.parse_transfer_status(status),
6905
7385
  }
6906
7386
 
6907
- def parse_transfer_status(self, status):
6908
- statuses = {
7387
+ def parse_transfer_status(self, status: Str) -> Str:
7388
+ statuses: dict = {
6909
7389
  'successful': 'ok',
6910
7390
  }
6911
7391
  return self.safe_string(statuses, status, status)
@@ -6935,7 +7415,7 @@ class bitget(Exchange, ImplicitAPI):
6935
7415
  #
6936
7416
  chains = self.safe_value(fee, 'chains', [])
6937
7417
  chainsLength = len(chains)
6938
- result = {
7418
+ result: dict = {
6939
7419
  'info': fee,
6940
7420
  'withdraw': {
6941
7421
  'fee': None,
@@ -6964,7 +7444,9 @@ class bitget(Exchange, ImplicitAPI):
6964
7444
  def fetch_deposit_withdraw_fees(self, codes: Strings = None, params={}):
6965
7445
  """
6966
7446
  fetch deposit and withdraw fees
6967
- :see: https://www.bitget.com/api-doc/spot/market/Get-Coin-List
7447
+
7448
+ https://www.bitget.com/api-doc/spot/market/Get-Coin-List
7449
+
6968
7450
  :param str[]|None codes: list of unified currency codes
6969
7451
  :param dict [params]: extra parameters specific to the exchange API endpoint
6970
7452
  :returns dict: a list of `fee structures <https://docs.ccxt.com/#/?id=fee-structure>`
@@ -7000,13 +7482,15 @@ class bitget(Exchange, ImplicitAPI):
7000
7482
  # "requestTime": "1700120731773"
7001
7483
  # }
7002
7484
  #
7003
- data = self.safe_value(response, 'data', [])
7485
+ data = self.safe_list(response, 'data', [])
7004
7486
  return self.parse_deposit_withdraw_fees(data, codes, 'coin')
7005
7487
 
7006
7488
  def borrow_cross_margin(self, code: str, amount: float, params={}):
7007
7489
  """
7008
7490
  create a loan to borrow margin
7009
- :see: https://www.bitget.com/api-doc/margin/cross/account/Cross-Borrow
7491
+
7492
+ https://www.bitget.com/api-doc/margin/cross/account/Cross-Borrow
7493
+
7010
7494
  :param str code: unified currency code of the currency to borrow
7011
7495
  :param str amount: the amount to borrow
7012
7496
  :param dict [params]: extra parameters specific to the exchange API endpoint
@@ -7014,8 +7498,8 @@ class bitget(Exchange, ImplicitAPI):
7014
7498
  """
7015
7499
  self.load_markets()
7016
7500
  currency = self.currency(code)
7017
- request = {
7018
- 'coin': currency['code'],
7501
+ request: dict = {
7502
+ 'coin': currency['id'],
7019
7503
  'borrowAmount': self.currency_to_precision(code, amount),
7020
7504
  }
7021
7505
  response = self.privateMarginPostV2MarginCrossedAccountBorrow(self.extend(request, params))
@@ -7037,7 +7521,9 @@ class bitget(Exchange, ImplicitAPI):
7037
7521
  def borrow_isolated_margin(self, symbol: str, code: str, amount: float, params={}):
7038
7522
  """
7039
7523
  create a loan to borrow margin
7040
- :see: https://www.bitget.com/api-doc/margin/isolated/account/Isolated-Borrow
7524
+
7525
+ https://www.bitget.com/api-doc/margin/isolated/account/Isolated-Borrow
7526
+
7041
7527
  :param str symbol: unified market symbol
7042
7528
  :param str code: unified currency code of the currency to borrow
7043
7529
  :param str amount: the amount to borrow
@@ -7047,8 +7533,8 @@ class bitget(Exchange, ImplicitAPI):
7047
7533
  self.load_markets()
7048
7534
  currency = self.currency(code)
7049
7535
  market = self.market(symbol)
7050
- request = {
7051
- 'coin': currency['code'],
7536
+ request: dict = {
7537
+ 'coin': currency['id'],
7052
7538
  'borrowAmount': self.currency_to_precision(code, amount),
7053
7539
  'symbol': market['id'],
7054
7540
  }
@@ -7072,7 +7558,9 @@ class bitget(Exchange, ImplicitAPI):
7072
7558
  def repay_isolated_margin(self, symbol: str, code: str, amount, params={}):
7073
7559
  """
7074
7560
  repay borrowed margin and interest
7075
- :see: https://www.bitget.com/api-doc/margin/isolated/account/Isolated-Repay
7561
+
7562
+ https://www.bitget.com/api-doc/margin/isolated/account/Isolated-Repay
7563
+
7076
7564
  :param str symbol: unified market symbol
7077
7565
  :param str code: unified currency code of the currency to repay
7078
7566
  :param str amount: the amount to repay
@@ -7082,8 +7570,8 @@ class bitget(Exchange, ImplicitAPI):
7082
7570
  self.load_markets()
7083
7571
  currency = self.currency(code)
7084
7572
  market = self.market(symbol)
7085
- request = {
7086
- 'coin': currency['code'],
7573
+ request: dict = {
7574
+ 'coin': currency['id'],
7087
7575
  'repayAmount': self.currency_to_precision(code, amount),
7088
7576
  'symbol': market['id'],
7089
7577
  }
@@ -7108,7 +7596,9 @@ class bitget(Exchange, ImplicitAPI):
7108
7596
  def repay_cross_margin(self, code: str, amount, params={}):
7109
7597
  """
7110
7598
  repay borrowed margin and interest
7111
- :see: https://www.bitget.com/api-doc/margin/cross/account/Cross-Repay
7599
+
7600
+ https://www.bitget.com/api-doc/margin/cross/account/Cross-Repay
7601
+
7112
7602
  :param str code: unified currency code of the currency to repay
7113
7603
  :param str amount: the amount to repay
7114
7604
  :param dict [params]: extra parameters specific to the exchange API endpoint
@@ -7116,8 +7606,8 @@ class bitget(Exchange, ImplicitAPI):
7116
7606
  """
7117
7607
  self.load_markets()
7118
7608
  currency = self.currency(code)
7119
- request = {
7120
- 'coin': currency['code'],
7609
+ request: dict = {
7610
+ 'coin': currency['id'],
7121
7611
  'repayAmount': self.currency_to_precision(code, amount),
7122
7612
  }
7123
7613
  response = self.privateMarginPostV2MarginCrossedAccountRepay(self.extend(request, params))
@@ -7193,8 +7683,10 @@ class bitget(Exchange, ImplicitAPI):
7193
7683
  def fetch_my_liquidations(self, symbol: Str = None, since: Int = None, limit: Int = None, params={}) -> List[Liquidation]:
7194
7684
  """
7195
7685
  retrieves the users liquidated positions
7196
- :see: https://www.bitget.com/api-doc/margin/cross/record/Get-Cross-Liquidation-Records
7197
- :see: https://www.bitget.com/api-doc/margin/isolated/record/Get-Isolated-Liquidation-Records
7686
+
7687
+ https://www.bitget.com/api-doc/margin/cross/record/Get-Cross-Liquidation-Records
7688
+ https://www.bitget.com/api-doc/margin/isolated/record/Get-Isolated-Liquidation-Records
7689
+
7198
7690
  :param str [symbol]: unified CCXT market symbol
7199
7691
  :param int [since]: the earliest time in ms to fetch liquidations for
7200
7692
  :param int [limit]: the maximum number of liquidation structures to retrieve
@@ -7216,7 +7708,7 @@ class bitget(Exchange, ImplicitAPI):
7216
7708
  type, params = self.handle_market_type_and_params('fetchMyLiquidations', market, params)
7217
7709
  if type != 'spot':
7218
7710
  raise NotSupported(self.id + ' fetchMyLiquidations() supports spot margin markets only')
7219
- request = {}
7711
+ request: dict = {}
7220
7712
  request, params = self.handle_until_option('endTime', request, params)
7221
7713
  if since is not None:
7222
7714
  request['startTime'] = since
@@ -7287,7 +7779,7 @@ class bitget(Exchange, ImplicitAPI):
7287
7779
  # }
7288
7780
  #
7289
7781
  data = self.safe_value(response, 'data', {})
7290
- liquidations = self.safe_value(data, 'resultList', [])
7782
+ liquidations = self.safe_list(data, 'resultList', [])
7291
7783
  return self.parse_liquidations(liquidations, market, since, limit)
7292
7784
 
7293
7785
  def parse_liquidation(self, liquidation, market: Market = None):
@@ -7338,17 +7830,19 @@ class bitget(Exchange, ImplicitAPI):
7338
7830
  'datetime': self.iso8601(timestamp),
7339
7831
  })
7340
7832
 
7341
- def fetch_isolated_borrow_rate(self, symbol: str, params={}):
7833
+ def fetch_isolated_borrow_rate(self, symbol: str, params={}) -> IsolatedBorrowRate:
7342
7834
  """
7343
7835
  fetch the rate of interest to borrow a currency for margin trading
7344
- :see: https://www.bitget.com/api-doc/margin/isolated/account/Isolated-Margin-Interest-Rate-And-Max-Borrowable-Amount
7836
+
7837
+ https://www.bitget.com/api-doc/margin/isolated/account/Isolated-Margin-Interest-Rate-And-Max-Borrowable-Amount
7838
+
7345
7839
  :param str symbol: unified market symbol
7346
7840
  :param dict [params]: extra parameters specific to the exchange API endpoint
7347
7841
  :returns dict: an `isolated borrow rate structure <https://docs.ccxt.com/#/?id=isolated-borrow-rate-structure>`
7348
7842
  """
7349
7843
  self.load_markets()
7350
7844
  market = self.market(symbol)
7351
- request = {
7845
+ request: dict = {
7352
7846
  'symbol': market['id'],
7353
7847
  }
7354
7848
  response = self.privateMarginGetV2MarginIsolatedInterestRateAndLimit(self.extend(request, params))
@@ -7399,7 +7893,7 @@ class bitget(Exchange, ImplicitAPI):
7399
7893
  first['timestamp'] = timestamp
7400
7894
  return self.parse_isolated_borrow_rate(first, market)
7401
7895
 
7402
- def parse_isolated_borrow_rate(self, info, market: Market = None):
7896
+ def parse_isolated_borrow_rate(self, info: dict, market: Market = None) -> IsolatedBorrowRate:
7403
7897
  #
7404
7898
  # {
7405
7899
  # "symbol": "BTCUSDT",
@@ -7451,10 +7945,12 @@ class bitget(Exchange, ImplicitAPI):
7451
7945
  'info': info,
7452
7946
  }
7453
7947
 
7454
- def fetch_cross_borrow_rate(self, code: str, params={}):
7948
+ def fetch_cross_borrow_rate(self, code: str, params={}) -> CrossBorrowRate:
7455
7949
  """
7456
7950
  fetch the rate of interest to borrow a currency for margin trading
7457
- :see: https://www.bitget.com/api-doc/margin/cross/account/Get-Cross-Margin-Interest-Rate-And-Borrowable
7951
+
7952
+ https://www.bitget.com/api-doc/margin/cross/account/Get-Cross-Margin-Interest-Rate-And-Borrowable
7953
+
7458
7954
  :param str code: unified currency code
7459
7955
  :param dict [params]: extra parameters specific to the exchange API endpoint
7460
7956
  :param str [params.symbol]: required for isolated margin
@@ -7462,8 +7958,8 @@ class bitget(Exchange, ImplicitAPI):
7462
7958
  """
7463
7959
  self.load_markets()
7464
7960
  currency = self.currency(code)
7465
- request = {
7466
- 'coin': currency['code'],
7961
+ request: dict = {
7962
+ 'coin': currency['id'],
7467
7963
  }
7468
7964
  response = self.privateMarginGetV2MarginCrossedInterestRateAndLimit(self.extend(request, params))
7469
7965
  #
@@ -7529,11 +8025,13 @@ class bitget(Exchange, ImplicitAPI):
7529
8025
  'info': info,
7530
8026
  }
7531
8027
 
7532
- def fetch_borrow_interest(self, code: Str = None, symbol: Str = None, since: Int = None, limit: Int = None, params={}):
8028
+ def fetch_borrow_interest(self, code: Str = None, symbol: Str = None, since: Int = None, limit: Int = None, params={}) -> List[BorrowInterest]:
7533
8029
  """
7534
8030
  fetch the interest owed by the user for borrowing currency for margin trading
7535
- :see: https://www.bitget.com/api-doc/margin/cross/record/Get-Cross-Interest-Records
7536
- :see: https://www.bitget.com/api-doc/margin/isolated/record/Get-Isolated-Interest-Records
8031
+
8032
+ https://www.bitget.com/api-doc/margin/cross/record/Get-Cross-Interest-Records
8033
+ https://www.bitget.com/api-doc/margin/isolated/record/Get-Isolated-Interest-Records
8034
+
7537
8035
  :param str [code]: unified currency code
7538
8036
  :param str [symbol]: unified market symbol when fetching interest in isolated markets
7539
8037
  :param int [since]: the earliest time in ms to fetch borrow interest for
@@ -7550,11 +8048,11 @@ class bitget(Exchange, ImplicitAPI):
7550
8048
  market = None
7551
8049
  if symbol is not None:
7552
8050
  market = self.market(symbol)
7553
- request = {}
8051
+ request: dict = {}
7554
8052
  currency = None
7555
8053
  if code is not None:
7556
8054
  currency = self.currency(code)
7557
- request['coin'] = currency['code']
8055
+ request['coin'] = currency['id']
7558
8056
  if since is not None:
7559
8057
  request['startTime'] = since
7560
8058
  else:
@@ -7626,7 +8124,7 @@ class bitget(Exchange, ImplicitAPI):
7626
8124
  interest = self.parse_borrow_interests(rows, market)
7627
8125
  return self.filter_by_currency_since_limit(interest, code, since, limit)
7628
8126
 
7629
- def parse_borrow_interest(self, info, market: Market = None):
8127
+ def parse_borrow_interest(self, info: dict, market: Market = None) -> BorrowInterest:
7630
8128
  #
7631
8129
  # isolated
7632
8130
  #
@@ -7660,21 +8158,23 @@ class bitget(Exchange, ImplicitAPI):
7660
8158
  marginMode = 'isolated' if (marketId is not None) else 'cross'
7661
8159
  timestamp = self.safe_integer(info, 'cTime')
7662
8160
  return {
8161
+ 'info': info,
7663
8162
  'symbol': self.safe_string(market, 'symbol'),
7664
- 'marginMode': marginMode,
7665
8163
  'currency': self.safe_currency_code(self.safe_string(info, 'interestCoin')),
7666
8164
  'interest': self.safe_number(info, 'interestAmount'),
7667
8165
  'interestRate': self.safe_number(info, 'dailyInterestRate'),
7668
8166
  'amountBorrowed': None,
8167
+ 'marginMode': marginMode,
7669
8168
  'timestamp': timestamp,
7670
8169
  'datetime': self.iso8601(timestamp),
7671
- 'info': info,
7672
8170
  }
7673
8171
 
7674
8172
  def close_position(self, symbol: str, side: OrderSide = None, params={}) -> Order:
7675
8173
  """
7676
8174
  closes an open position for a market
7677
- :see: https://www.bitget.com/api-doc/contract/trade/Flash-Close-Position
8175
+
8176
+ https://www.bitget.com/api-doc/contract/trade/Flash-Close-Position
8177
+
7678
8178
  :param str symbol: unified CCXT market symbol
7679
8179
  :param str [side]: one-way mode: 'buy' or 'sell', hedge-mode: 'long' or 'short'
7680
8180
  :param dict [params]: extra parameters specific to the exchange API endpoint
@@ -7690,7 +8190,7 @@ class bitget(Exchange, ImplicitAPI):
7690
8190
  market = self.market(symbol)
7691
8191
  productType = None
7692
8192
  productType, params = self.handle_product_type_and_params(market, params)
7693
- request = {
8193
+ request: dict = {
7694
8194
  'symbol': market['id'],
7695
8195
  'productType': productType,
7696
8196
  }
@@ -7715,13 +8215,15 @@ class bitget(Exchange, ImplicitAPI):
7715
8215
  # }
7716
8216
  #
7717
8217
  data = self.safe_value(response, 'data', {})
7718
- order = self.safe_value(data, 'successList', [])
8218
+ order = self.safe_list(data, 'successList', [])
7719
8219
  return self.parse_order(order[0], market)
7720
8220
 
7721
8221
  def close_all_positions(self, params={}) -> List[Position]:
7722
8222
  """
7723
8223
  closes all open positions for a market type
7724
- :see: https://www.bitget.com/api-doc/contract/trade/Flash-Close-Position
8224
+
8225
+ https://www.bitget.com/api-doc/contract/trade/Flash-Close-Position
8226
+
7725
8227
  :param dict [params]: extra parameters specific to the exchange API endpoint
7726
8228
  :param str [params.productType]: 'USDT-FUTURES', 'USDC-FUTURES', 'COIN-FUTURES', 'SUSDT-FUTURES', 'SUSDC-FUTURES' or 'SCOIN-FUTURES'
7727
8229
  :returns dict[]: A list of `position structures <https://docs.ccxt.com/#/?id=position-structure>`
@@ -7729,7 +8231,7 @@ class bitget(Exchange, ImplicitAPI):
7729
8231
  self.load_markets()
7730
8232
  productType = None
7731
8233
  productType, params = self.handle_product_type_and_params(None, params)
7732
- request = {
8234
+ request: dict = {
7733
8235
  'productType': productType,
7734
8236
  }
7735
8237
  response = self.privateMixPostV2MixOrderClosePositions(self.extend(request, params))
@@ -7751,13 +8253,15 @@ class bitget(Exchange, ImplicitAPI):
7751
8253
  # }
7752
8254
  #
7753
8255
  data = self.safe_value(response, 'data', {})
7754
- orderInfo = self.safe_value(data, 'successList', [])
8256
+ orderInfo = self.safe_list(data, 'successList', [])
7755
8257
  return self.parse_positions(orderInfo, None, params)
7756
8258
 
7757
8259
  def fetch_margin_mode(self, symbol: str, params={}) -> MarginMode:
7758
8260
  """
7759
8261
  fetches the margin mode of a trading pair
7760
- :see: https://www.bitget.com/api-doc/contract/account/Get-Single-Account
8262
+
8263
+ https://www.bitget.com/api-doc/contract/account/Get-Single-Account
8264
+
7761
8265
  :param str symbol: unified symbol of the market to fetch the margin mode for
7762
8266
  :param dict [params]: extra parameters specific to the exchange API endpoint
7763
8267
  :returns dict: a `margin mode structure <https://docs.ccxt.com/#/?id=margin-mode-structure>`
@@ -7772,7 +8276,7 @@ class bitget(Exchange, ImplicitAPI):
7772
8276
  market = self.market(symbol)
7773
8277
  productType = None
7774
8278
  productType, params = self.handle_product_type_and_params(market, params)
7775
- request = {
8279
+ request: dict = {
7776
8280
  'symbol': market['id'],
7777
8281
  'marginCoin': market['settleId'],
7778
8282
  'productType': productType,
@@ -7809,7 +8313,7 @@ class bitget(Exchange, ImplicitAPI):
7809
8313
  data = self.safe_dict(response, 'data', {})
7810
8314
  return self.parse_margin_mode(data, market)
7811
8315
 
7812
- def parse_margin_mode(self, marginMode, market=None) -> MarginMode:
8316
+ def parse_margin_mode(self, marginMode: dict, market=None) -> MarginMode:
7813
8317
  marginType = self.safe_string(marginMode, 'marginMode')
7814
8318
  marginType = 'cross' if (marginType == 'crossed') else marginType
7815
8319
  return {
@@ -7818,12 +8322,455 @@ class bitget(Exchange, ImplicitAPI):
7818
8322
  'marginMode': marginType,
7819
8323
  }
7820
8324
 
7821
- def handle_errors(self, code, reason, url, method, headers, body, response, requestHeaders, requestBody):
8325
+ def fetch_positions_history(self, symbols: Strings = None, since: Int = None, limit: Int = None, params={}) -> List[Position]:
8326
+ """
8327
+ fetches historical positions
8328
+
8329
+ https://www.bitget.com/api-doc/contract/position/Get-History-Position
8330
+
8331
+ :param str[] [symbols]: unified contract symbols
8332
+ :param int [since]: timestamp in ms of the earliest position to fetch, default=3 months ago, max range for params["until"] - since is 3 months
8333
+ :param int [limit]: the maximum amount of records to fetch, default=20, max=100
8334
+ :param dict params: extra parameters specific to the exchange api endpoint
8335
+ :param int [params.until]: timestamp in ms of the latest position to fetch, max range for params["until"] - since is 3 months
8336
+
8337
+ EXCHANGE SPECIFIC PARAMETERS
8338
+ :param str [params.productType]: USDT-FUTURES(default), COIN-FUTURES, USDC-FUTURES, SUSDT-FUTURES, SCOIN-FUTURES, or SUSDC-FUTURES
8339
+ :returns dict[]: a list of `position structures <https://docs.ccxt.com/#/?id=position-structure>`
8340
+ """
8341
+ self.load_markets()
8342
+ until = self.safe_integer(params, 'until')
8343
+ params = self.omit(params, 'until')
8344
+ request: dict = {}
8345
+ if symbols is not None:
8346
+ symbolsLength = len(symbols)
8347
+ if symbolsLength > 0:
8348
+ market = self.market(symbols[0])
8349
+ request['symbol'] = market['id']
8350
+ if since is not None:
8351
+ request['startTime'] = since
8352
+ if limit is not None:
8353
+ request['limit'] = limit
8354
+ if until is not None:
8355
+ request['endTime'] = until
8356
+ response = self.privateMixGetV2MixPositionHistoryPosition(self.extend(request, params))
8357
+ #
8358
+ # {
8359
+ # code: '00000',
8360
+ # msg: 'success',
8361
+ # requestTime: '1712794148791',
8362
+ # data: {
8363
+ # list: [
8364
+ # {
8365
+ # symbol: 'XRPUSDT',
8366
+ # marginCoin: 'USDT',
8367
+ # holdSide: 'long',
8368
+ # openAvgPrice: '0.64967',
8369
+ # closeAvgPrice: '0.58799',
8370
+ # marginMode: 'isolated',
8371
+ # openTotalPos: '10',
8372
+ # closeTotalPos: '10',
8373
+ # pnl: '-0.62976205',
8374
+ # netProfit: '-0.65356802',
8375
+ # totalFunding: '-0.01638',
8376
+ # openFee: '-0.00389802',
8377
+ # closeFee: '-0.00352794',
8378
+ # ctime: '1709590322199',
8379
+ # utime: '1709667583395'
8380
+ # },
8381
+ # ...
8382
+ # ]
8383
+ # }
8384
+ # }
8385
+ #
8386
+ data = self.safe_dict(response, 'data')
8387
+ responseList = self.safe_list(data, 'list')
8388
+ positions = self.parse_positions(responseList, symbols, params)
8389
+ return self.filter_by_since_limit(positions, since, limit)
8390
+
8391
+ def fetch_convert_quote(self, fromCode: str, toCode: str, amount: Num = None, params={}) -> Conversion:
8392
+ """
8393
+ fetch a quote for converting from one currency to another
8394
+
8395
+ https://www.bitget.com/api-doc/common/convert/Get-Quoted-Price
8396
+
8397
+ :param str fromCode: the currency that you want to sell and convert from
8398
+ :param str toCode: the currency that you want to buy and convert into
8399
+ :param float [amount]: how much you want to trade in units of the from currency
8400
+ :param dict [params]: extra parameters specific to the exchange API endpoint
8401
+ :returns dict: a `conversion structure <https://docs.ccxt.com/#/?id=conversion-structure>`
8402
+ """
8403
+ self.load_markets()
8404
+ request: dict = {
8405
+ 'fromCoin': fromCode,
8406
+ 'toCoin': toCode,
8407
+ 'fromCoinSize': self.number_to_string(amount),
8408
+ }
8409
+ response = self.privateConvertGetV2ConvertQuotedPrice(self.extend(request, params))
8410
+ #
8411
+ # {
8412
+ # "code": "00000",
8413
+ # "msg": "success",
8414
+ # "requestTime": 1712121940158,
8415
+ # "data": {
8416
+ # "fromCoin": "USDT",
8417
+ # "fromCoinSize": "5",
8418
+ # "cnvtPrice": "0.9993007892377704",
8419
+ # "toCoin": "USDC",
8420
+ # "toCoinSize": "4.99650394",
8421
+ # "traceId": "1159288930228187140",
8422
+ # "fee": "0"
8423
+ # }
8424
+ # }
8425
+ #
8426
+ data = self.safe_dict(response, 'data', {})
8427
+ fromCurrencyId = self.safe_string(data, 'fromCoin', fromCode)
8428
+ fromCurrency = self.currency(fromCurrencyId)
8429
+ toCurrencyId = self.safe_string(data, 'toCoin', toCode)
8430
+ toCurrency = self.currency(toCurrencyId)
8431
+ return self.parse_conversion(data, fromCurrency, toCurrency)
8432
+
8433
+ def create_convert_trade(self, id: str, fromCode: str, toCode: str, amount: Num = None, params={}) -> Conversion:
8434
+ """
8435
+ convert from one currency to another
8436
+
8437
+ https://www.bitget.com/api-doc/common/convert/Trade
8438
+
8439
+ :param str id: the id of the trade that you want to make
8440
+ :param str fromCode: the currency that you want to sell and convert from
8441
+ :param str toCode: the currency that you want to buy and convert into
8442
+ :param float amount: how much you want to trade in units of the from currency
8443
+ :param dict [params]: extra parameters specific to the exchange API endpoint
8444
+ :param str params['price']: the price of the conversion, obtained from fetchConvertQuote()
8445
+ :param str params['toAmount']: the amount you want to trade in units of the toCurrency, obtained from fetchConvertQuote()
8446
+ :returns dict: a `conversion structure <https://docs.ccxt.com/#/?id=conversion-structure>`
8447
+ """
8448
+ self.load_markets()
8449
+ price = self.safe_string_2(params, 'price', 'cnvtPrice')
8450
+ if price is None:
8451
+ raise ArgumentsRequired(self.id + ' createConvertTrade() requires a price parameter')
8452
+ toAmount = self.safe_string_2(params, 'toAmount', 'toCoinSize')
8453
+ if toAmount is None:
8454
+ raise ArgumentsRequired(self.id + ' createConvertTrade() requires a toAmount parameter')
8455
+ params = self.omit(params, ['price', 'toAmount'])
8456
+ request: dict = {
8457
+ 'traceId': id,
8458
+ 'fromCoin': fromCode,
8459
+ 'toCoin': toCode,
8460
+ 'fromCoinSize': self.number_to_string(amount),
8461
+ 'toCoinSize': toAmount,
8462
+ 'cnvtPrice': price,
8463
+ }
8464
+ response = self.privateConvertPostV2ConvertTrade(self.extend(request, params))
8465
+ #
8466
+ # {
8467
+ # "code": "00000",
8468
+ # "msg": "success",
8469
+ # "requestTime": 1712123746203,
8470
+ # "data": {
8471
+ # "cnvtPrice": "0.99940076",
8472
+ # "toCoin": "USDC",
8473
+ # "toCoinSize": "4.99700379",
8474
+ # "ts": "1712123746217"
8475
+ # }
8476
+ # }
8477
+ #
8478
+ data = self.safe_dict(response, 'data', {})
8479
+ toCurrencyId = self.safe_string(data, 'toCoin', toCode)
8480
+ toCurrency = self.currency(toCurrencyId)
8481
+ return self.parse_conversion(data, None, toCurrency)
8482
+
8483
+ def fetch_convert_trade_history(self, code: Str = None, since: Int = None, limit: Int = None, params={}) -> List[Conversion]:
8484
+ """
8485
+ fetch the users history of conversion trades
8486
+
8487
+ https://www.bitget.com/api-doc/common/convert/Get-Convert-Record
8488
+
8489
+ :param str [code]: the unified currency code
8490
+ :param int [since]: the earliest time in ms to fetch conversions for
8491
+ :param int [limit]: the maximum number of conversion structures to retrieve
8492
+ :param dict [params]: extra parameters specific to the exchange API endpoint
8493
+ :returns dict[]: a list of `conversion structures <https://docs.ccxt.com/#/?id=conversion-structure>`
8494
+ """
8495
+ self.load_markets()
8496
+ request: dict = {}
8497
+ msInDay = 86400000
8498
+ now = self.milliseconds()
8499
+ if since is not None:
8500
+ request['startTime'] = since
8501
+ else:
8502
+ request['startTime'] = now - msInDay
8503
+ endTime = self.safe_string_2(params, 'endTime', 'until')
8504
+ if endTime is not None:
8505
+ request['endTime'] = endTime
8506
+ else:
8507
+ request['endTime'] = now
8508
+ if limit is not None:
8509
+ request['limit'] = limit
8510
+ params = self.omit(params, 'until')
8511
+ response = self.privateConvertGetV2ConvertConvertRecord(self.extend(request, params))
8512
+ #
8513
+ # {
8514
+ # "code": "00000",
8515
+ # "msg": "success",
8516
+ # "requestTime": 1712124371799,
8517
+ # "data": {
8518
+ # "dataList": [
8519
+ # {
8520
+ # "id": "1159296505255219205",
8521
+ # "fromCoin": "USDT",
8522
+ # "fromCoinSize": "5",
8523
+ # "cnvtPrice": "0.99940076",
8524
+ # "toCoin": "USDC",
8525
+ # "toCoinSize": "4.99700379",
8526
+ # "ts": "1712123746217",
8527
+ # "fee": "0"
8528
+ # }
8529
+ # ],
8530
+ # "endId": "1159296505255219205"
8531
+ # }
8532
+ # }
8533
+ #
8534
+ data = self.safe_dict(response, 'data', {})
8535
+ dataList = self.safe_list(data, 'dataList', [])
8536
+ return self.parse_conversions(dataList, code, 'fromCoin', 'toCoin', since, limit)
8537
+
8538
+ def parse_conversion(self, conversion: dict, fromCurrency: Currency = None, toCurrency: Currency = None) -> Conversion:
8539
+ #
8540
+ # fetchConvertQuote
8541
+ #
8542
+ # {
8543
+ # "fromCoin": "USDT",
8544
+ # "fromCoinSize": "5",
8545
+ # "cnvtPrice": "0.9993007892377704",
8546
+ # "toCoin": "USDC",
8547
+ # "toCoinSize": "4.99650394",
8548
+ # "traceId": "1159288930228187140",
8549
+ # "fee": "0"
8550
+ # }
8551
+ #
8552
+ # createConvertTrade
8553
+ #
8554
+ # {
8555
+ # "cnvtPrice": "0.99940076",
8556
+ # "toCoin": "USDC",
8557
+ # "toCoinSize": "4.99700379",
8558
+ # "ts": "1712123746217"
8559
+ # }
8560
+ #
8561
+ # fetchConvertTradeHistory
8562
+ #
8563
+ # {
8564
+ # "id": "1159296505255219205",
8565
+ # "fromCoin": "USDT",
8566
+ # "fromCoinSize": "5",
8567
+ # "cnvtPrice": "0.99940076",
8568
+ # "toCoin": "USDC",
8569
+ # "toCoinSize": "4.99700379",
8570
+ # "ts": "1712123746217",
8571
+ # "fee": "0"
8572
+ # }
8573
+ #
8574
+ timestamp = self.safe_integer(conversion, 'ts')
8575
+ fromCoin = self.safe_string(conversion, 'fromCoin')
8576
+ fromCode = self.safe_currency_code(fromCoin, fromCurrency)
8577
+ to = self.safe_string(conversion, 'toCoin')
8578
+ toCode = self.safe_currency_code(to, toCurrency)
8579
+ return {
8580
+ 'info': conversion,
8581
+ 'timestamp': timestamp,
8582
+ 'datetime': self.iso8601(timestamp),
8583
+ 'id': self.safe_string_2(conversion, 'id', 'traceId'),
8584
+ 'fromCurrency': fromCode,
8585
+ 'fromAmount': self.safe_number(conversion, 'fromCoinSize'),
8586
+ 'toCurrency': toCode,
8587
+ 'toAmount': self.safe_number(conversion, 'toCoinSize'),
8588
+ 'price': self.safe_number(conversion, 'cnvtPrice'),
8589
+ 'fee': self.safe_number(conversion, 'fee'),
8590
+ }
8591
+
8592
+ def fetch_convert_currencies(self, params={}) -> Currencies:
8593
+ """
8594
+ fetches all available currencies that can be converted
8595
+
8596
+ https://www.bitget.com/api-doc/common/convert/Get-Convert-Currencies
8597
+
8598
+ :param dict [params]: extra parameters specific to the exchange API endpoint
8599
+ :returns dict: an associative dictionary of currencies
8600
+ """
8601
+ self.load_markets()
8602
+ response = self.privateConvertGetV2ConvertCurrencies(params)
8603
+ #
8604
+ # {
8605
+ # "code": "00000",
8606
+ # "msg": "success",
8607
+ # "requestTime": 1712121755897,
8608
+ # "data": [
8609
+ # {
8610
+ # "coin": "BTC",
8611
+ # "available": "0.00009850",
8612
+ # "maxAmount": "0.756266",
8613
+ # "minAmount": "0.00001"
8614
+ # },
8615
+ # ]
8616
+ # }
8617
+ #
8618
+ result: dict = {}
8619
+ data = self.safe_list(response, 'data', [])
8620
+ for i in range(0, len(data)):
8621
+ entry = data[i]
8622
+ id = self.safe_string(entry, 'coin')
8623
+ code = self.safe_currency_code(id)
8624
+ result[code] = {
8625
+ 'info': entry,
8626
+ 'id': id,
8627
+ 'code': code,
8628
+ 'networks': None,
8629
+ 'type': None,
8630
+ 'name': None,
8631
+ 'active': None,
8632
+ 'deposit': None,
8633
+ 'withdraw': self.safe_number(entry, 'available'),
8634
+ 'fee': None,
8635
+ 'precision': None,
8636
+ 'limits': {
8637
+ 'amount': {
8638
+ 'min': self.safe_number(entry, 'minAmount'),
8639
+ 'max': self.safe_number(entry, 'maxAmount'),
8640
+ },
8641
+ 'withdraw': {
8642
+ 'min': None,
8643
+ 'max': None,
8644
+ },
8645
+ 'deposit': {
8646
+ 'min': None,
8647
+ 'max': None,
8648
+ },
8649
+ },
8650
+ 'created': None,
8651
+ }
8652
+ return result
8653
+
8654
+ def fetch_funding_interval(self, symbol: str, params={}) -> FundingRate:
8655
+ """
8656
+ fetch the current funding rate interval
8657
+
8658
+ https://www.bitget.com/api-doc/contract/market/Get-Symbol-Next-Funding-Time
8659
+
8660
+ :param str symbol: unified market symbol
8661
+ :param dict [params]: extra parameters specific to the exchange API endpoint
8662
+ :returns dict: a `funding rate structure <https://docs.ccxt.com/#/?id=funding-rate-structure>`
8663
+ """
8664
+ self.load_markets()
8665
+ sandboxMode = self.safe_bool(self.options, 'sandboxMode', False)
8666
+ market = None
8667
+ if sandboxMode:
8668
+ sandboxSymbol = self.convert_symbol_for_sandbox(symbol)
8669
+ market = self.market(sandboxSymbol)
8670
+ else:
8671
+ market = self.market(symbol)
8672
+ productType = None
8673
+ productType, params = self.handle_product_type_and_params(market, params)
8674
+ request: dict = {
8675
+ 'symbol': market['id'],
8676
+ 'productType': productType,
8677
+ }
8678
+ response = self.publicMixGetV2MixMarketFundingTime(self.extend(request, params))
8679
+ #
8680
+ # {
8681
+ # "code": "00000",
8682
+ # "msg": "success",
8683
+ # "requestTime": 1727930153888,
8684
+ # "data": [
8685
+ # {
8686
+ # "symbol": "BTCUSDT",
8687
+ # "nextFundingTime": "1727942400000",
8688
+ # "ratePeriod": "8"
8689
+ # }
8690
+ # ]
8691
+ # }
8692
+ #
8693
+ data = self.safe_list(response, 'data', [])
8694
+ first = self.safe_dict(data, 0, {})
8695
+ return self.parse_funding_rate(first, market)
8696
+
8697
+ def fetch_long_short_ratio_history(self, symbol: Str = None, timeframe: Str = None, since: Int = None, limit: Int = None, params={}) -> List[LongShortRatio]:
8698
+ """
8699
+ fetches the long short ratio history for a unified market symbol
8700
+
8701
+ https://www.bitget.com/api-doc/common/apidata/Margin-Ls-Ratio
8702
+ https://www.bitget.com/api-doc/common/apidata/Account-Long-Short
8703
+
8704
+ :param str symbol: unified symbol of the market to fetch the long short ratio for
8705
+ :param str [timeframe]: the period for the ratio
8706
+ :param int [since]: the earliest time in ms to fetch ratios for
8707
+ :param int [limit]: the maximum number of long short ratio structures to retrieve
8708
+ :param dict [params]: extra parameters specific to the exchange API endpoint
8709
+ :returns dict[]: an array of `long short ratio structures <https://docs.ccxt.com/#/?id=long-short-ratio-structure>`
8710
+ """
8711
+ self.load_markets()
8712
+ market = self.market(symbol)
8713
+ request: dict = {
8714
+ 'symbol': market['id'],
8715
+ }
8716
+ if timeframe is not None:
8717
+ request['period'] = timeframe
8718
+ response = None
8719
+ if market['swap'] or market['future']:
8720
+ response = self.publicMixGetV2MixMarketAccountLongShort(self.extend(request, params))
8721
+ #
8722
+ # {
8723
+ # "code": "00000",
8724
+ # "msg": "success",
8725
+ # "requestTime": 1729321233281,
8726
+ # "data": [
8727
+ # {
8728
+ # "longAccountRatio": "0.58",
8729
+ # "shortAccountRatio": "0.42",
8730
+ # "longShortAccountRatio": "0.0138",
8731
+ # "ts": "1729312200000"
8732
+ # },
8733
+ # ]
8734
+ # }
8735
+ #
8736
+ else:
8737
+ response = self.publicMarginGetV2MarginMarketLongShortRatio(self.extend(request, params))
8738
+ #
8739
+ # {
8740
+ # "code": "00000",
8741
+ # "msg": "success",
8742
+ # "requestTime": 1729306974712,
8743
+ # "data": [
8744
+ # {
8745
+ # "longShortRatio": "40.66",
8746
+ # "ts": "1729306800000"
8747
+ # },
8748
+ # ]
8749
+ # }
8750
+ #
8751
+ data = self.safe_list(response, 'data', [])
8752
+ return self.parse_long_short_ratio_history(data, market)
8753
+
8754
+ def parse_long_short_ratio(self, info: dict, market: Market = None) -> LongShortRatio:
8755
+ marketId = self.safe_string(info, 'symbol')
8756
+ timestamp = self.safe_integer_omit_zero(info, 'ts')
8757
+ return {
8758
+ 'info': info,
8759
+ 'symbol': self.safe_symbol(marketId, market, None, 'contract'),
8760
+ 'timestamp': timestamp,
8761
+ 'datetime': self.iso8601(timestamp),
8762
+ 'timeframe': None,
8763
+ 'longShortRatio': self.safe_number_2(info, 'longShortRatio', 'longShortAccountRatio'),
8764
+ }
8765
+
8766
+ def handle_errors(self, code: int, reason: str, url: str, method: str, headers: dict, body: str, response, requestHeaders, requestBody):
7822
8767
  if not response:
7823
8768
  return None # fallback to default error handler
7824
8769
  #
7825
8770
  # spot
7826
8771
  #
8772
+ # {"code":"00000","msg":"success","requestTime":1713294492511,"data":[...]}"
8773
+ #
7827
8774
  # {"status":"fail","err_code":"01001","err_msg":"系统异常,请稍后重试"}
7828
8775
  # {"status":"error","ts":1595594160149,"err_code":"invalid-parameter","err_msg":"invalid size, valid range: [1,2000]"}
7829
8776
  # {"status":"error","ts":1595684716042,"err_code":"invalid-parameter","err_msg":"illegal sign invalid"}
@@ -7845,13 +8792,13 @@ class bitget(Exchange, ImplicitAPI):
7845
8792
  # {"code":"40108","msg":"","requestTime":1595885064600,"data":null}
7846
8793
  # {"order_id":"513468410013679613","client_oid":null,"symbol":"ethusd","result":false,"err_code":"order_no_exist_error","err_msg":"订单不存在!"}
7847
8794
  #
7848
- message = self.safe_string(response, 'err_msg')
7849
- errorCode = self.safe_string_2(response, 'code', 'err_code')
8795
+ message = self.safe_string_2(response, 'err_msg', 'msg')
7850
8796
  feedback = self.id + ' ' + body
7851
- nonEmptyMessage = ((message is not None) and (message != ''))
8797
+ nonEmptyMessage = ((message is not None) and (message != '') and (message != 'success'))
7852
8798
  if nonEmptyMessage:
7853
8799
  self.throw_exactly_matched_exception(self.exceptions['exact'], message, feedback)
7854
8800
  self.throw_broadly_matched_exception(self.exceptions['broad'], message, feedback)
8801
+ errorCode = self.safe_string_2(response, 'code', 'err_code')
7855
8802
  nonZeroErrorCode = (errorCode is not None) and (errorCode != '00000')
7856
8803
  if nonZeroErrorCode:
7857
8804
  self.throw_exactly_matched_exception(self.exceptions['exact'], errorCode, feedback)
@@ -7859,6 +8806,9 @@ class bitget(Exchange, ImplicitAPI):
7859
8806
  raise ExchangeError(feedback) # unknown message
7860
8807
  return None
7861
8808
 
8809
+ def nonce(self):
8810
+ return self.milliseconds() - self.options['timeDifference']
8811
+
7862
8812
  def sign(self, path, api=[], method='GET', params={}, headers=None, body=None):
7863
8813
  signed = api[0] == 'private'
7864
8814
  endpoint = api[1]
@@ -7874,7 +8824,7 @@ class bitget(Exchange, ImplicitAPI):
7874
8824
  url = url + '?' + self.urlencode(query)
7875
8825
  if signed:
7876
8826
  self.check_required_credentials()
7877
- timestamp = str(self.milliseconds())
8827
+ timestamp = str(self.nonce())
7878
8828
  auth = timestamp + method + payload
7879
8829
  if method == 'POST':
7880
8830
  body = self.json(params)