ccxt 4.2.77__py2.py3-none-any.whl → 4.4.49__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 +3205 -937
  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 +1525 -573
  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 +223 -97
  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 +639 -323
  126. ccxt/async_support/digifinex.py +465 -233
  127. ccxt/async_support/ellipx.py +1887 -0
  128. ccxt/async_support/exmo.py +317 -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 +433 -178
  133. ccxt/async_support/hollaex.py +207 -83
  134. ccxt/async_support/htx.py +1095 -563
  135. ccxt/async_support/huobijp.py +178 -56
  136. ccxt/async_support/hyperliquid.py +1678 -292
  137. ccxt/async_support/idex.py +219 -95
  138. ccxt/async_support/independentreserve.py +300 -31
  139. ccxt/async_support/indodax.py +226 -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 +198 -107
  145. ccxt/async_support/latoken.py +199 -79
  146. ccxt/async_support/lbank.py +360 -113
  147. ccxt/async_support/luno.py +185 -62
  148. ccxt/async_support/lykke.py +168 -55
  149. ccxt/async_support/mercado.py +101 -29
  150. ccxt/async_support/mexc.py +995 -429
  151. ccxt/async_support/myokx.py +53 -0
  152. ccxt/async_support/ndax.py +234 -82
  153. ccxt/async_support/novadax.py +195 -75
  154. ccxt/async_support/oceanex.py +244 -59
  155. ccxt/async_support/okcoin.py +301 -165
  156. ccxt/async_support/okx.py +1776 -454
  157. ccxt/async_support/onetrading.py +198 -414
  158. ccxt/async_support/oxfun.py +2898 -0
  159. ccxt/async_support/p2b.py +142 -52
  160. ccxt/async_support/paradex.py +2085 -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 +3205 -937
  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 +1525 -573
  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 +223 -97
  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 +639 -323
  234. ccxt/digifinex.py +465 -233
  235. ccxt/ellipx.py +1887 -0
  236. ccxt/exmo.py +317 -128
  237. ccxt/gate.py +1472 -463
  238. ccxt/gemini.py +206 -84
  239. ccxt/hashkey.py +4164 -0
  240. ccxt/hitbtc.py +433 -178
  241. ccxt/hollaex.py +207 -83
  242. ccxt/htx.py +1095 -563
  243. ccxt/huobijp.py +178 -56
  244. ccxt/hyperliquid.py +1677 -292
  245. ccxt/idex.py +219 -95
  246. ccxt/independentreserve.py +299 -31
  247. ccxt/indodax.py +226 -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 +198 -107
  253. ccxt/latoken.py +199 -79
  254. ccxt/lbank.py +360 -113
  255. ccxt/luno.py +185 -62
  256. ccxt/lykke.py +168 -55
  257. ccxt/mercado.py +101 -29
  258. ccxt/mexc.py +994 -429
  259. ccxt/myokx.py +53 -0
  260. ccxt/ndax.py +234 -82
  261. ccxt/novadax.py +195 -75
  262. ccxt/oceanex.py +244 -59
  263. ccxt/okcoin.py +301 -165
  264. ccxt/okx.py +1776 -454
  265. ccxt/onetrading.py +198 -414
  266. ccxt/oxfun.py +2897 -0
  267. ccxt/p2b.py +142 -52
  268. ccxt/paradex.py +2085 -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 +143 -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.49.dist-info/LICENSE.txt +21 -0
  496. ccxt-4.4.49.dist-info/METADATA +646 -0
  497. ccxt-4.4.49.dist-info/RECORD +669 -0
  498. {ccxt-4.2.77.dist-info → ccxt-4.4.49.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.49.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',
@@ -1370,18 +1402,18 @@ class bitget(Exchange, ImplicitAPI):
1370
1402
  '1m': 30,
1371
1403
  '3m': 30,
1372
1404
  '5m': 30,
1373
- '10m': 52,
1405
+ '10m': 30,
1374
1406
  '15m': 52,
1375
- '30m': 52,
1407
+ '30m': 62,
1376
1408
  '1h': 83,
1377
1409
  '2h': 120,
1378
1410
  '4h': 240,
1379
1411
  '6h': 360,
1380
1412
  '12h': 360,
1381
- '1d': 360,
1382
- '3d': 1000,
1383
- '1w': 1000,
1384
- '1M': 1000,
1413
+ '1d': 300,
1414
+ '3d': 300,
1415
+ '1w': 300,
1416
+ '1M': 300,
1385
1417
  },
1386
1418
  },
1387
1419
  'fetchTrades': {
@@ -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,18 +3449,21 @@ 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
3191
3463
  :param int [limit]: the maximum amount of candles to fetch
3192
3464
  :param dict [params]: extra parameters specific to the exchange API endpoint
3193
3465
  :param int [params.until]: timestamp in ms of the latest candle to fetch
3466
+ :param boolean [params.useHistoryEndpoint]: whether to force to use historical endpoint(it has max limit of 200)
3194
3467
  :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)
3195
3468
  :param str [params.price]: *swap only* "mark"(to fetch mark price candles) or "index"(to fetch index price candles)
3196
3469
  :returns int[][]: A list of candles ordered, open, high, low, close, volume
@@ -3202,8 +3475,9 @@ class bitget(Exchange, ImplicitAPI):
3202
3475
  paginate = False
3203
3476
  paginate, params = self.handle_option_and_params(params, 'fetchOHLCV', 'paginate')
3204
3477
  if paginate:
3205
- return self.fetch_paginated_call_deterministic('fetchOHLCV', symbol, since, limit, timeframe, params, maxLimitForHistoryEndpoint)
3478
+ return self.fetch_paginated_call_deterministic('fetchOHLCV', symbol, since, limit, timeframe, params, maxLimitForRecentEndpoint)
3206
3479
  sandboxMode = self.safe_bool(self.options, 'sandboxMode', False)
3480
+ useHistoryEndpoint = self.safe_bool(params, 'useHistoryEndpoint', False)
3207
3481
  market = None
3208
3482
  if sandboxMode:
3209
3483
  sandboxSymbol = self.convert_symbol_for_sandbox(symbol)
@@ -3214,15 +3488,15 @@ class bitget(Exchange, ImplicitAPI):
3214
3488
  timeframes = self.options['timeframes'][marketType]
3215
3489
  msInDay = 86400000
3216
3490
  duration = self.parse_timeframe(timeframe) * 1000
3217
- request = {
3491
+ request: dict = {
3218
3492
  'symbol': market['id'],
3219
3493
  'granularity': self.safe_string(timeframes, timeframe, timeframe),
3220
3494
  }
3221
- until = self.safe_integer_2(params, 'until', 'till')
3495
+ until = self.safe_integer(params, 'until')
3222
3496
  limitDefined = limit is not None
3223
3497
  sinceDefined = since is not None
3224
3498
  untilDefined = until is not None
3225
- params = self.omit(params, ['until', 'till'])
3499
+ params = self.omit(params, ['until'])
3226
3500
  response = None
3227
3501
  now = self.milliseconds()
3228
3502
  # retrievable periods listed here:
@@ -3231,7 +3505,7 @@ class bitget(Exchange, ImplicitAPI):
3231
3505
  ohlcOptions = self.safe_dict(self.options, 'fetchOHLCV', {})
3232
3506
  retrievableDaysMap = self.safe_dict(ohlcOptions, 'maxDaysPerTimeframe', {})
3233
3507
  maxRetrievableDaysForRecent = self.safe_integer(retrievableDaysMap, timeframe, 30) # default to safe minimum
3234
- endpointTsBoundary = now - maxRetrievableDaysForRecent * msInDay
3508
+ endpointTsBoundary = now - (maxRetrievableDaysForRecent - 1) * msInDay
3235
3509
  if limitDefined:
3236
3510
  limit = min(limit, maxLimitForRecentEndpoint)
3237
3511
  request['limit'] = limit
@@ -3262,7 +3536,7 @@ class bitget(Exchange, ImplicitAPI):
3262
3536
  # make request
3263
3537
  if market['spot']:
3264
3538
  # checks if we need history endpoint
3265
- if historicalEndpointNeeded:
3539
+ if historicalEndpointNeeded or useHistoryEndpoint:
3266
3540
  response = self.publicSpotGetV2SpotMarketHistoryCandles(self.extend(request, params))
3267
3541
  else:
3268
3542
  response = self.publicSpotGetV2SpotMarketCandles(self.extend(request, params))
@@ -3286,7 +3560,7 @@ class bitget(Exchange, ImplicitAPI):
3286
3560
  elif priceType == 'index':
3287
3561
  response = self.publicMixGetV2MixMarketHistoryIndexCandles(extended)
3288
3562
  else:
3289
- if historicalEndpointNeeded:
3563
+ if historicalEndpointNeeded or useHistoryEndpoint:
3290
3564
  response = self.publicMixGetV2MixMarketHistoryCandles(extended)
3291
3565
  else:
3292
3566
  response = self.publicMixGetV2MixMarketCandles(extended)
@@ -3299,18 +3573,20 @@ class bitget(Exchange, ImplicitAPI):
3299
3573
  def fetch_balance(self, params={}) -> Balances:
3300
3574
  """
3301
3575
  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
3576
+
3577
+ https://www.bitget.com/api-doc/spot/account/Get-Account-Assets
3578
+ https://www.bitget.com/api-doc/contract/account/Get-Account-List
3579
+ https://www.bitget.com/api-doc/margin/cross/account/Get-Cross-Assets
3580
+ https://www.bitget.com/api-doc/margin/isolated/account/Get-Isolated-Assets
3581
+ https://bitgetlimited.github.io/apidoc/en/margin/#get-cross-assets
3582
+ https://bitgetlimited.github.io/apidoc/en/margin/#get-isolated-assets
3583
+
3308
3584
  :param dict [params]: extra parameters specific to the exchange API endpoint
3309
3585
  :param str [params.productType]: *contract only* 'USDT-FUTURES', 'USDC-FUTURES', 'COIN-FUTURES', 'SUSDT-FUTURES', 'SUSDC-FUTURES' or 'SCOIN-FUTURES'
3310
3586
  :returns dict: a `balance structure <https://docs.ccxt.com/#/?id=balance-structure>`
3311
3587
  """
3312
3588
  self.load_markets()
3313
- request = {}
3589
+ request: dict = {}
3314
3590
  marketType = None
3315
3591
  marginMode = None
3316
3592
  response = None
@@ -3420,7 +3696,7 @@ class bitget(Exchange, ImplicitAPI):
3420
3696
  return self.parse_balance(data)
3421
3697
 
3422
3698
  def parse_balance(self, balance) -> Balances:
3423
- result = {'info': balance}
3699
+ result: dict = {'info': balance}
3424
3700
  #
3425
3701
  # spot
3426
3702
  #
@@ -3507,8 +3783,8 @@ class bitget(Exchange, ImplicitAPI):
3507
3783
  result[code] = account
3508
3784
  return self.safe_balance(result)
3509
3785
 
3510
- def parse_order_status(self, status):
3511
- statuses = {
3786
+ def parse_order_status(self, status: Str):
3787
+ statuses: dict = {
3512
3788
  'new': 'open',
3513
3789
  'init': 'open',
3514
3790
  'not_trigger': 'open',
@@ -3528,7 +3804,7 @@ class bitget(Exchange, ImplicitAPI):
3528
3804
  }
3529
3805
  return self.safe_string(statuses, status, status)
3530
3806
 
3531
- def parse_order(self, order, market: Market = None) -> Order:
3807
+ def parse_order(self, order: dict, market: Market = None) -> Order:
3532
3808
  #
3533
3809
  # createOrder, editOrder, closePosition
3534
3810
  #
@@ -3821,7 +4097,7 @@ class bitget(Exchange, ImplicitAPI):
3821
4097
  if feeCostString is not None:
3822
4098
  # swap
3823
4099
  fee = {
3824
- 'cost': self.parse_number(Precise.string_abs(feeCostString)),
4100
+ 'cost': self.parse_number(Precise.string_neg(feeCostString)),
3825
4101
  'currency': market['settle'],
3826
4102
  }
3827
4103
  feeDetail = self.safe_value(order, 'feeDetail')
@@ -3835,7 +4111,7 @@ class bitget(Exchange, ImplicitAPI):
3835
4111
  feeObject = feeValue
3836
4112
  break
3837
4113
  fee = {
3838
- 'cost': self.parse_number(Precise.string_abs(self.safe_string(feeObject, 'totalFee'))),
4114
+ 'cost': self.parse_number(Precise.string_neg(self.safe_string(feeObject, 'totalFee'))),
3839
4115
  'currency': self.safe_currency_code(self.safe_string(feeObject, 'feeCoinCode')),
3840
4116
  }
3841
4117
  postOnly = None
@@ -3893,7 +4169,6 @@ class bitget(Exchange, ImplicitAPI):
3893
4169
  'timeInForce': timeInForce,
3894
4170
  'postOnly': postOnly,
3895
4171
  'reduceOnly': reduceOnly,
3896
- 'stopPrice': self.safe_number(order, 'triggerPrice'),
3897
4172
  'triggerPrice': self.safe_number(order, 'triggerPrice'),
3898
4173
  'takeProfitPrice': self.safe_number_2(order, 'presetStopSurplusPrice', 'stopSurplusTriggerPrice'),
3899
4174
  'stopLossPrice': self.safe_number_2(order, 'presetStopLossPrice', 'stopLossTriggerPrice'),
@@ -3905,9 +4180,11 @@ class bitget(Exchange, ImplicitAPI):
3905
4180
  def create_market_buy_order_with_cost(self, symbol: str, cost: float, params={}):
3906
4181
  """
3907
4182
  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
4183
+
4184
+ https://www.bitget.com/api-doc/spot/trade/Place-Order
4185
+ https://www.bitget.com/api-doc/margin/cross/trade/Cross-Place-Order
4186
+ https://www.bitget.com/api-doc/margin/isolated/trade/Isolated-Place-Order
4187
+
3911
4188
  :param str symbol: unified symbol of the market to create an order in
3912
4189
  :param float cost: how much you want to trade in units of the quote currency
3913
4190
  :param dict [params]: extra parameters specific to the exchange API endpoint
@@ -3917,24 +4194,28 @@ class bitget(Exchange, ImplicitAPI):
3917
4194
  market = self.market(symbol)
3918
4195
  if not market['spot']:
3919
4196
  raise NotSupported(self.id + ' createMarketBuyOrderWithCost() supports spot orders only')
3920
- params['createMarketBuyOrderRequiresPrice'] = False
3921
- return self.create_order(symbol, 'market', 'buy', cost, None, params)
4197
+ req = {
4198
+ 'createMarketBuyOrderRequiresPrice': False,
4199
+ }
4200
+ return self.create_order(symbol, 'market', 'buy', cost, None, self.extend(req, params))
3922
4201
 
3923
4202
  def create_order(self, symbol: str, type: OrderType, side: OrderSide, amount: float, price: Num = None, params={}):
3924
4203
  """
3925
4204
  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
4205
+
4206
+ https://www.bitget.com/api-doc/spot/trade/Place-Order
4207
+ https://www.bitget.com/api-doc/spot/plan/Place-Plan-Order
4208
+ https://www.bitget.com/api-doc/contract/trade/Place-Order
4209
+ https://www.bitget.com/api-doc/contract/plan/Place-Tpsl-Order
4210
+ https://www.bitget.com/api-doc/contract/plan/Place-Plan-Order
4211
+ https://www.bitget.com/api-doc/margin/cross/trade/Cross-Place-Order
4212
+ https://www.bitget.com/api-doc/margin/isolated/trade/Isolated-Place-Order
4213
+
3933
4214
  :param str symbol: unified symbol of the market to create an order in
3934
4215
  :param str type: 'market' or 'limit'
3935
4216
  :param str side: 'buy' or 'sell'
3936
4217
  :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
4218
+ :param float [price]: the price at which the order is to be fulfilled, in units of the quote currency, ignored in market orders
3938
4219
  :param dict [params]: extra parameters specific to the exchange API endpoint
3939
4220
  :param float [params.cost]: *spot only* how much you want to trade in units of the quote currency, for market buy orders only
3940
4221
  :param float [params.triggerPrice]: *swap only* The price at which a trigger order is triggered at
@@ -3956,6 +4237,8 @@ class bitget(Exchange, ImplicitAPI):
3956
4237
  :param str [params.trailingTriggerPrice]: *swap and future only* the price to trigger a trailing stop order, default uses the price argument
3957
4238
  :param str [params.triggerType]: *swap and future only* 'fill_price', 'mark_price' or 'index_price'
3958
4239
  :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
4240
+ :param bool [params.hedged]: *swap and future only* True for hedged mode, False for one way mode, default is False
4241
+ :param bool [params.reduceOnly]: True or False whether the order is reduce-only
3959
4242
  :returns dict: an `order structure <https://docs.ccxt.com/#/?id=order-structure>`
3960
4243
  """
3961
4244
  self.load_markets()
@@ -4000,7 +4283,7 @@ class bitget(Exchange, ImplicitAPI):
4000
4283
  # }
4001
4284
  # }
4002
4285
  #
4003
- data = self.safe_value(response, 'data', {})
4286
+ data = self.safe_dict(response, 'data', {})
4004
4287
  return self.parse_order(data, market)
4005
4288
 
4006
4289
  def create_order_request(self, symbol: str, type: OrderType, side: OrderSide, amount: float, price: Num = None, params={}):
@@ -4015,7 +4298,7 @@ class bitget(Exchange, ImplicitAPI):
4015
4298
  marginMode = None
4016
4299
  marketType, params = self.handle_market_type_and_params('createOrder', market, params)
4017
4300
  marginMode, params = self.handle_margin_mode_and_params('createOrder', params)
4018
- request = {
4301
+ request: dict = {
4019
4302
  'symbol': market['id'],
4020
4303
  'orderType': type,
4021
4304
  }
@@ -4039,7 +4322,7 @@ class bitget(Exchange, ImplicitAPI):
4039
4322
  raise ExchangeError(self.id + ' createOrder() params can only contain one of triggerPrice, stopLossPrice, takeProfitPrice, trailingPercent')
4040
4323
  if type == 'limit':
4041
4324
  request['price'] = self.price_to_precision(symbol, price)
4042
- triggerType = self.safe_string(params, 'triggerType', 'mark_price')
4325
+ triggerPriceType = self.safe_string_2(params, 'triggerPriceType', 'triggerType', 'mark_price')
4043
4326
  reduceOnly = self.safe_bool(params, 'reduceOnly', False)
4044
4327
  clientOrderId = self.safe_string_2(params, 'clientOid', 'clientOrderId')
4045
4328
  exchangeSpecificTifParam = self.safe_string_2(params, 'force', 'timeInForce')
@@ -4065,7 +4348,7 @@ class bitget(Exchange, ImplicitAPI):
4065
4348
  if clientOrderId is not None:
4066
4349
  request['clientOid'] = clientOrderId
4067
4350
  if isTriggerOrder or isStopLossOrTakeProfitTrigger or isTrailingPercentOrder:
4068
- request['triggerType'] = triggerType
4351
+ request['triggerType'] = triggerPriceType
4069
4352
  if isTrailingPercentOrder:
4070
4353
  if not isMarketOrder:
4071
4354
  raise BadRequest(self.id + ' createOrder() bitget trailing orders must be market orders')
@@ -4115,18 +4398,23 @@ class bitget(Exchange, ImplicitAPI):
4115
4398
  marginMode = 'cross'
4116
4399
  marginModeRequest = 'crossed' if (marginMode == 'cross') else 'isolated'
4117
4400
  request['marginMode'] = marginModeRequest
4118
- oneWayMode = self.safe_bool(params, 'oneWayMode', False)
4119
- params = self.omit(params, 'oneWayMode')
4401
+ hedged = None
4402
+ hedged, params = self.handle_param_bool(params, 'hedged', False)
4403
+ # backward compatibility for `oneWayMode`
4404
+ oneWayMode = None
4405
+ oneWayMode, params = self.handle_param_bool(params, 'oneWayMode')
4406
+ if oneWayMode is not None:
4407
+ hedged = not oneWayMode
4120
4408
  requestSide = side
4121
4409
  if reduceOnly:
4122
- if oneWayMode:
4410
+ if not hedged:
4123
4411
  request['reduceOnly'] = 'YES'
4124
4412
  else:
4125
4413
  # 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
4414
  requestSide = 'sell' if (side == 'buy') else 'buy'
4127
4415
  request['tradeSide'] = 'Close'
4128
4416
  else:
4129
- if not oneWayMode:
4417
+ if hedged:
4130
4418
  request['tradeSide'] = 'Open'
4131
4419
  request['side'] = requestSide
4132
4420
  elif marketType == 'spot':
@@ -4160,7 +4448,7 @@ class bitget(Exchange, ImplicitAPI):
4160
4448
  request['clientOid'] = clientOrderId
4161
4449
  if marginMode is not None:
4162
4450
  request['loanType'] = 'normal'
4163
- if createMarketBuyOrderRequiresPrice and isMarketOrder and (side == 'buy'):
4451
+ if isMarketOrder and (side == 'buy'):
4164
4452
  request['quoteSize'] = quantity
4165
4453
  else:
4166
4454
  request['baseSize'] = quantity
@@ -4169,7 +4457,7 @@ class bitget(Exchange, ImplicitAPI):
4169
4457
  request['size'] = quantity
4170
4458
  if triggerPrice is not None:
4171
4459
  request['planType'] = planType
4172
- request['triggerType'] = triggerType
4460
+ request['triggerType'] = triggerPriceType
4173
4461
  request['triggerPrice'] = self.price_to_precision(symbol, triggerPrice)
4174
4462
  if price is not None:
4175
4463
  request['executePrice'] = self.price_to_precision(symbol, price)
@@ -4180,10 +4468,12 @@ class bitget(Exchange, ImplicitAPI):
4180
4468
  def create_orders(self, orders: List[OrderRequest], params={}):
4181
4469
  """
4182
4470
  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
4471
+
4472
+ https://www.bitget.com/api-doc/spot/trade/Batch-Place-Orders
4473
+ https://www.bitget.com/api-doc/contract/trade/Batch-Order
4474
+ https://www.bitget.com/api-doc/margin/isolated/trade/Isolated-Batch-Order
4475
+ https://www.bitget.com/api-doc/margin/cross/trade/Cross-Batch-Order
4476
+
4187
4477
  :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
4478
  :param dict [params]: extra parameters specific to the api endpoint
4189
4479
  :returns dict: an `order structure <https://docs.ccxt.com/#/?id=order-structure>`
@@ -4222,7 +4512,7 @@ class bitget(Exchange, ImplicitAPI):
4222
4512
  market = self.market(sandboxSymbol)
4223
4513
  else:
4224
4514
  market = self.market(symbol)
4225
- request = {
4515
+ request: dict = {
4226
4516
  'symbol': market['id'],
4227
4517
  'orderList': ordersRequests,
4228
4518
  }
@@ -4275,16 +4565,18 @@ class bitget(Exchange, ImplicitAPI):
4275
4565
  def edit_order(self, id: str, symbol: str, type: OrderType, side: OrderSide, amount: Num = None, price: Num = None, params={}):
4276
4566
  """
4277
4567
  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
4568
+
4569
+ https://www.bitget.com/api-doc/spot/plan/Modify-Plan-Order
4570
+ https://www.bitget.com/api-doc/contract/trade/Modify-Order
4571
+ https://www.bitget.com/api-doc/contract/plan/Modify-Tpsl-Order
4572
+ https://www.bitget.com/api-doc/contract/plan/Modify-Plan-Order
4573
+
4282
4574
  :param str id: cancel order id
4283
4575
  :param str symbol: unified symbol of the market to create an order in
4284
4576
  :param str type: 'market' or 'limit'
4285
4577
  :param str side: 'buy' or 'sell'
4286
4578
  :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
4579
+ :param float [price]: the price at which the order is to be fulfilled, in units of the quote currency, ignored in market orders
4288
4580
  :param dict [params]: extra parameters specific to the exchange API endpoint
4289
4581
  :param float [params.triggerPrice]: the price that a trigger order is triggered at
4290
4582
  :param float [params.stopLossPrice]: *swap only* The price at which a stop loss order is triggered at
@@ -4310,7 +4602,7 @@ class bitget(Exchange, ImplicitAPI):
4310
4602
  market = self.market(sandboxSymbol)
4311
4603
  else:
4312
4604
  market = self.market(symbol)
4313
- request = {
4605
+ request: dict = {
4314
4606
  'orderId': id,
4315
4607
  }
4316
4608
  isMarketOrder = type == 'market'
@@ -4335,6 +4627,8 @@ class bitget(Exchange, ImplicitAPI):
4335
4627
  params = self.omit(params, ['stopPrice', 'triggerType', 'stopLossPrice', 'takeProfitPrice', 'stopLoss', 'takeProfit', 'clientOrderId', 'trailingTriggerPrice', 'trailingPercent'])
4336
4628
  response = None
4337
4629
  if market['spot']:
4630
+ if triggerPrice is None:
4631
+ raise NotSupported(self.id + 'editOrder() only supports plan/trigger spot orders')
4338
4632
  editMarketBuyOrderRequiresPrice = self.safe_bool(self.options, 'editMarketBuyOrderRequiresPrice', True)
4339
4633
  if editMarketBuyOrderRequiresPrice and isMarketOrder and (side == 'buy'):
4340
4634
  if price is None:
@@ -4417,23 +4711,25 @@ class bitget(Exchange, ImplicitAPI):
4417
4711
  # }
4418
4712
  # }
4419
4713
  #
4420
- data = self.safe_value(response, 'data', {})
4714
+ data = self.safe_dict(response, 'data', {})
4421
4715
  return self.parse_order(data, market)
4422
4716
 
4423
4717
  def cancel_order(self, id: str, symbol: Str = None, params={}):
4424
4718
  """
4425
4719
  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
4720
+
4721
+ https://www.bitget.com/api-doc/spot/trade/Cancel-Order
4722
+ https://www.bitget.com/api-doc/spot/plan/Cancel-Plan-Order
4723
+ https://www.bitget.com/api-doc/contract/trade/Cancel-Order
4724
+ https://www.bitget.com/api-doc/contract/plan/Cancel-Plan-Order
4725
+ https://www.bitget.com/api-doc/margin/cross/trade/Cross-Cancel-Order
4726
+ https://www.bitget.com/api-doc/margin/isolated/trade/Isolated-Cancel-Order
4727
+
4432
4728
  :param str id: order id
4433
4729
  :param str symbol: unified symbol of the market the order was made in
4434
4730
  :param dict [params]: extra parameters specific to the exchange API endpoint
4435
4731
  :param str [params.marginMode]: 'isolated' or 'cross' for spot margin trading
4436
- :param boolean [params.stop]: set to True for canceling trigger orders
4732
+ :param boolean [params.trigger]: set to True for canceling trigger orders
4437
4733
  :param str [params.planType]: *swap only* either profit_plan, loss_plan, normal_plan, pos_profit, pos_loss, moving_plan or track_plan
4438
4734
  :param boolean [params.trailing]: set to True if you want to cancel a trailing order
4439
4735
  :returns dict: An `order structure <https://docs.ccxt.com/#/?id=order-structure>`
@@ -4451,21 +4747,21 @@ class bitget(Exchange, ImplicitAPI):
4451
4747
  marginMode = None
4452
4748
  response = None
4453
4749
  marginMode, params = self.handle_margin_mode_and_params('cancelOrder', params)
4454
- request = {}
4750
+ request: dict = {}
4455
4751
  trailing = self.safe_value(params, 'trailing')
4456
- stop = self.safe_value_2(params, 'stop', 'trigger')
4752
+ trigger = self.safe_value_2(params, 'stop', 'trigger')
4457
4753
  params = self.omit(params, ['stop', 'trigger', 'trailing'])
4458
- if not (market['spot'] and stop):
4754
+ if not (market['spot'] and trigger):
4459
4755
  request['symbol'] = market['id']
4460
- if not ((market['swap'] or market['future']) and stop):
4756
+ if not ((market['swap'] or market['future']) and trigger):
4461
4757
  request['orderId'] = id
4462
4758
  if (market['swap']) or (market['future']):
4463
4759
  productType = None
4464
4760
  productType, params = self.handle_product_type_and_params(market, params)
4465
4761
  request['productType'] = productType
4466
- if stop or trailing:
4762
+ if trigger or trailing:
4467
4763
  orderIdList = []
4468
- orderId = {
4764
+ orderId: dict = {
4469
4765
  'orderId': id,
4470
4766
  }
4471
4767
  orderIdList.append(orderId)
@@ -4474,7 +4770,7 @@ class bitget(Exchange, ImplicitAPI):
4474
4770
  planType = self.safe_string(params, 'planType', 'track_plan')
4475
4771
  request['planType'] = planType
4476
4772
  response = self.privateMixPostV2MixOrderCancelPlanOrder(self.extend(request, params))
4477
- elif stop:
4773
+ elif trigger:
4478
4774
  response = self.privateMixPostV2MixOrderCancelPlanOrder(self.extend(request, params))
4479
4775
  else:
4480
4776
  response = self.privateMixPostV2MixOrderCancelOrder(self.extend(request, params))
@@ -4485,7 +4781,7 @@ class bitget(Exchange, ImplicitAPI):
4485
4781
  elif marginMode == 'cross':
4486
4782
  response = self.privateMarginPostV2MarginCrossedCancelOrder(self.extend(request, params))
4487
4783
  else:
4488
- if stop:
4784
+ if trigger:
4489
4785
  response = self.privateSpotPostV2SpotTradeCancelPlanOrder(self.extend(request, params))
4490
4786
  else:
4491
4787
  response = self.privateSpotPostV2SpotTradeCancelOrder(self.extend(request, params))
@@ -4534,7 +4830,7 @@ class bitget(Exchange, ImplicitAPI):
4534
4830
  #
4535
4831
  data = self.safe_value(response, 'data', {})
4536
4832
  order = None
4537
- if (market['swap'] or market['future']) and stop:
4833
+ if (market['swap'] or market['future']) and trigger:
4538
4834
  orderInfo = self.safe_value(data, 'successList', [])
4539
4835
  order = orderInfo[0]
4540
4836
  else:
@@ -4544,16 +4840,18 @@ class bitget(Exchange, ImplicitAPI):
4544
4840
  def cancel_orders(self, ids, symbol: Str = None, params={}):
4545
4841
  """
4546
4842
  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
4843
+
4844
+ https://www.bitget.com/api-doc/spot/trade/Batch-Cancel-Orders
4845
+ https://www.bitget.com/api-doc/contract/trade/Batch-Cancel-Orders
4846
+ https://www.bitget.com/api-doc/contract/plan/Cancel-Plan-Order
4847
+ https://www.bitget.com/api-doc/margin/cross/trade/Cross-Batch-Cancel-Order
4848
+ https://www.bitget.com/api-doc/margin/isolated/trade/Isolated-Batch-Cancel-Orders
4849
+
4552
4850
  :param str[] ids: order ids
4553
4851
  :param str symbol: unified market symbol, default is None
4554
4852
  :param dict [params]: extra parameters specific to the exchange API endpoint
4555
4853
  :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
4854
+ :param boolean [params.trigger]: *contract only* set to True for canceling trigger orders
4557
4855
  :returns dict: an array of `order structures <https://docs.ccxt.com/#/?id=order-structure>`
4558
4856
  """
4559
4857
  if symbol is None:
@@ -4568,16 +4866,16 @@ class bitget(Exchange, ImplicitAPI):
4568
4866
  market = self.market(symbol)
4569
4867
  marginMode = None
4570
4868
  marginMode, params = self.handle_margin_mode_and_params('cancelOrders', params)
4571
- stop = self.safe_value_2(params, 'stop', 'trigger')
4869
+ trigger = self.safe_value_2(params, 'stop', 'trigger')
4572
4870
  params = self.omit(params, ['stop', 'trigger'])
4573
4871
  orderIdList = []
4574
4872
  for i in range(0, len(ids)):
4575
4873
  individualId = ids[i]
4576
- orderId = {
4874
+ orderId: dict = {
4577
4875
  'orderId': individualId,
4578
4876
  }
4579
4877
  orderIdList.append(orderId)
4580
- request = {
4878
+ request: dict = {
4581
4879
  'symbol': market['id'],
4582
4880
  }
4583
4881
  if market['spot'] and (marginMode is None):
@@ -4597,7 +4895,7 @@ class bitget(Exchange, ImplicitAPI):
4597
4895
  productType = None
4598
4896
  productType, params = self.handle_product_type_and_params(market, params)
4599
4897
  request['productType'] = productType
4600
- if stop:
4898
+ if trigger:
4601
4899
  response = self.privateMixPostV2MixOrderCancelPlanOrder(self.extend(request, params))
4602
4900
  else:
4603
4901
  response = self.privateMixPostV2MixOrderBatchCancelOrders(self.extend(request, params))
@@ -4618,21 +4916,23 @@ class bitget(Exchange, ImplicitAPI):
4618
4916
  # }
4619
4917
  #
4620
4918
  data = self.safe_value(response, 'data', {})
4621
- orders = self.safe_value(data, 'successList', [])
4919
+ orders = self.safe_list(data, 'successList', [])
4622
4920
  return self.parse_orders(orders, market)
4623
4921
 
4624
4922
  def cancel_all_orders(self, symbol: Str = None, params={}):
4625
4923
  """
4626
4924
  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
4925
+
4926
+ https://www.bitget.com/api-doc/spot/trade/Cancel-Symbol-Orders
4927
+ https://www.bitget.com/api-doc/spot/plan/Batch-Cancel-Plan-Order
4928
+ https://www.bitget.com/api-doc/contract/trade/Batch-Cancel-Orders
4929
+ https://bitgetlimited.github.io/apidoc/en/margin/#isolated-batch-cancel-orders
4930
+ https://bitgetlimited.github.io/apidoc/en/margin/#cross-batch-cancel-order
4931
+
4632
4932
  :param str symbol: unified market symbol
4633
4933
  :param dict [params]: extra parameters specific to the exchange API endpoint
4634
4934
  :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
4935
+ :param boolean [params.trigger]: *contract only* set to True for canceling trigger orders
4636
4936
  :returns dict[]: a list of `order structures <https://docs.ccxt.com/#/?id=order-structure>`
4637
4937
  """
4638
4938
  if symbol is None:
@@ -4647,10 +4947,10 @@ class bitget(Exchange, ImplicitAPI):
4647
4947
  market = self.market(symbol)
4648
4948
  marginMode = None
4649
4949
  marginMode, params = self.handle_margin_mode_and_params('cancelAllOrders', params)
4650
- request = {
4950
+ request: dict = {
4651
4951
  'symbol': market['id'],
4652
4952
  }
4653
- stop = self.safe_bool_2(params, 'stop', 'trigger')
4953
+ trigger = self.safe_bool_2(params, 'stop', 'trigger')
4654
4954
  params = self.omit(params, ['stop', 'trigger'])
4655
4955
  response = None
4656
4956
  if market['spot']:
@@ -4659,103 +4959,115 @@ class bitget(Exchange, ImplicitAPI):
4659
4959
  response = self.privateMarginPostMarginV1CrossOrderBatchCancelOrder(self.extend(request, params))
4660
4960
  else:
4661
4961
  response = self.privateMarginPostMarginV1IsolatedOrderBatchCancelOrder(self.extend(request, params))
4962
+ #
4963
+ # {
4964
+ # "code": "00000",
4965
+ # "msg": "success",
4966
+ # "requestTime": 1700717155622,
4967
+ # "data": {
4968
+ # "resultList": [
4969
+ # {
4970
+ # "orderId": "1111453253721796609",
4971
+ # "clientOid": "2ae7fc8a4ff949b6b60d770ca3950e2d"
4972
+ # },
4973
+ # ],
4974
+ # "failure": []
4975
+ # }
4976
+ # }
4977
+ #
4662
4978
  else:
4663
- if stop:
4664
- stopRequest = {
4979
+ if trigger:
4980
+ stopRequest: dict = {
4665
4981
  'symbolList': [market['id']],
4666
4982
  }
4667
4983
  response = self.privateSpotPostV2SpotTradeBatchCancelPlanOrder(self.extend(stopRequest, params))
4668
4984
  else:
4669
4985
  response = self.privateSpotPostV2SpotTradeCancelSymbolOrder(self.extend(request, params))
4986
+ #
4987
+ # {
4988
+ # "code": "00000",
4989
+ # "msg": "success",
4990
+ # "requestTime": 1700716953996,
4991
+ # "data": {
4992
+ # "symbol": "BTCUSDT"
4993
+ # }
4994
+ # }
4995
+ #
4996
+ timestamp = self.safe_integer(response, 'requestTime')
4997
+ responseData = self.safe_dict(response, 'data')
4998
+ marketId = self.safe_string(responseData, 'symbol')
4999
+ return [
5000
+ self.safe_order({
5001
+ 'info': response,
5002
+ 'symbol': self.safe_symbol(marketId, None, None, 'spot'),
5003
+ 'timestamp': timestamp,
5004
+ 'datetime': self.iso8601(timestamp),
5005
+ }),
5006
+ ]
4670
5007
  else:
4671
5008
  productType = None
4672
5009
  productType, params = self.handle_product_type_and_params(market, params)
4673
5010
  request['productType'] = productType
4674
- if stop:
5011
+ if trigger:
4675
5012
  response = self.privateMixPostV2MixOrderCancelPlanOrder(self.extend(request, params))
4676
5013
  else:
4677
5014
  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')
5015
+ # {
5016
+ # "code": "00000",
5017
+ # "msg": "success",
5018
+ # "requestTime": "1680008815965",
5019
+ # "data": {
5020
+ # "successList": [
5021
+ # {
5022
+ # "orderId": "1024598257429823488",
5023
+ # "clientOid": "876493ce-c287-4bfc-9f4a-8b1905881313"
5024
+ # },
5025
+ # ],
5026
+ # "failureList": []
5027
+ # }
5028
+ # }
5029
+ data = self.safe_dict(response, 'data')
5030
+ resultList = self.safe_list_2(data, 'resultList', 'successList')
5031
+ failureList = self.safe_list_2(data, 'failure', 'failureList')
5032
+ responseList = self.array_concat(resultList, failureList)
5033
+ return self.parse_orders(responseList)
5034
+
5035
+ def fetch_order(self, id: str, symbol: Str = None, params={}):
5036
+ """
5037
+ fetches information on an order made by the user
5038
+
5039
+ https://www.bitget.com/api-doc/spot/trade/Get-Order-Info
5040
+ https://www.bitget.com/api-doc/contract/trade/Get-Order-Details
5041
+
5042
+ :param str id: the order id
5043
+ :param str symbol: unified symbol of the market the order was made in
5044
+ :param dict [params]: extra parameters specific to the exchange API endpoint
5045
+ :returns dict: An `order structure <https://docs.ccxt.com/#/?id=order-structure>`
5046
+ """
5047
+ if symbol is None:
5048
+ raise ArgumentsRequired(self.id + ' fetchOrder() requires a symbol argument')
5049
+ self.load_markets()
5050
+ sandboxMode = self.safe_bool(self.options, 'sandboxMode', False)
5051
+ market = None
5052
+ if sandboxMode:
5053
+ sandboxSymbol = self.convert_symbol_for_sandbox(symbol)
5054
+ market = self.market(sandboxSymbol)
5055
+ else:
5056
+ market = self.market(symbol)
5057
+ request: dict = {
5058
+ 'orderId': id,
5059
+ }
5060
+ response = None
5061
+ if market['spot']:
5062
+ response = self.privateSpotGetV2SpotTradeOrderInfo(self.extend(request, params))
5063
+ elif market['swap'] or market['future']:
5064
+ request['symbol'] = market['id']
5065
+ productType = None
5066
+ productType, params = self.handle_product_type_and_params(market, params)
5067
+ request['productType'] = productType
5068
+ response = self.privateMixGetV2MixOrderDetail(self.extend(request, params))
5069
+ else:
5070
+ raise NotSupported(self.id + ' fetchOrder() does not support ' + market['type'] + ' orders')
4759
5071
  #
4760
5072
  # spot
4761
5073
  #
@@ -4825,26 +5137,34 @@ class bitget(Exchange, ImplicitAPI):
4825
5137
  #
4826
5138
  if isinstance(response, str):
4827
5139
  response = json.loads(response)
4828
- data = self.safe_value(response, 'data')
4829
- first = self.safe_value(data, 0, data)
5140
+ data = self.safe_dict(response, 'data')
5141
+ if (data is not None):
5142
+ if not isinstance(data, list):
5143
+ return self.parse_order(data, market)
5144
+ dataList = self.safe_list(response, 'data', [])
5145
+ first = self.safe_dict(dataList, 0, {})
4830
5146
  return self.parse_order(first, market)
5147
+ # first = self.safe_dict(data, 0, data)
5148
+ # return self.parse_order(first, market)
4831
5149
 
4832
5150
  def fetch_open_orders(self, symbol: Str = None, since: Int = None, limit: Int = None, params={}) -> List[Order]:
4833
5151
  """
4834
5152
  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
5153
+
5154
+ https://www.bitget.com/api-doc/spot/trade/Get-Unfilled-Orders
5155
+ https://www.bitget.com/api-doc/spot/plan/Get-Current-Plan-Order
5156
+ https://www.bitget.com/api-doc/contract/trade/Get-Orders-Pending
5157
+ https://www.bitget.com/api-doc/contract/plan/get-orders-plan-pending
5158
+ https://www.bitget.com/api-doc/margin/cross/trade/Get-Cross-Open-Orders
5159
+ https://www.bitget.com/api-doc/margin/isolated/trade/Isolated-Open-Orders
5160
+
4841
5161
  :param str symbol: unified market symbol
4842
5162
  :param int [since]: the earliest time in ms to fetch open orders for
4843
5163
  :param int [limit]: the maximum number of open order structures to retrieve
4844
5164
  :param dict [params]: extra parameters specific to the exchange API endpoint
4845
5165
  :param int [params.until]: the latest time in ms to fetch orders for
4846
5166
  :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
5167
+ :param boolean [params.trigger]: set to True for fetching trigger orders
4848
5168
  :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
5169
  :param str [params.isPlan]: *swap only* 'plan' for stop orders and 'profit_loss' for tp/sl orders, default is 'plan'
4850
5170
  :param boolean [params.trailing]: set to True if you want to fetch trailing orders
@@ -4854,7 +5174,7 @@ class bitget(Exchange, ImplicitAPI):
4854
5174
  sandboxMode = self.safe_bool(self.options, 'sandboxMode', False)
4855
5175
  market = None
4856
5176
  type = None
4857
- request = {}
5177
+ request: dict = {}
4858
5178
  marginMode = None
4859
5179
  marginMode, params = self.handle_margin_mode_and_params('fetchOpenOrders', params)
4860
5180
  if symbol is not None:
@@ -4882,9 +5202,9 @@ class bitget(Exchange, ImplicitAPI):
4882
5202
  return self.fetch_paginated_call_cursor('fetchOpenOrders', symbol, since, limit, params, cursorReceived, 'idLessThan')
4883
5203
  response = None
4884
5204
  trailing = self.safe_bool(params, 'trailing')
4885
- stop = self.safe_bool_2(params, 'stop', 'trigger')
5205
+ trigger = self.safe_bool_2(params, 'stop', 'trigger')
4886
5206
  planTypeDefined = self.safe_string(params, 'planType') is not None
4887
- isStop = (stop or planTypeDefined)
5207
+ isTrigger = (trigger or planTypeDefined)
4888
5208
  params = self.omit(params, ['stop', 'trigger', 'trailing'])
4889
5209
  request, params = self.handle_until_option('endTime', request, params)
4890
5210
  if since is not None:
@@ -4908,7 +5228,7 @@ class bitget(Exchange, ImplicitAPI):
4908
5228
  elif marginMode == 'cross':
4909
5229
  response = self.privateMarginGetV2MarginCrossedOpenOrders(self.extend(request, query))
4910
5230
  else:
4911
- if stop:
5231
+ if trigger:
4912
5232
  response = self.privateSpotGetV2SpotTradeCurrentPlanOrder(self.extend(request, query))
4913
5233
  else:
4914
5234
  response = self.privateSpotGetV2SpotTradeUnfilledOrders(self.extend(request, query))
@@ -4920,7 +5240,7 @@ class bitget(Exchange, ImplicitAPI):
4920
5240
  planType = self.safe_string(params, 'planType', 'track_plan')
4921
5241
  request['planType'] = planType
4922
5242
  response = self.privateMixGetV2MixOrderOrdersPlanPending(self.extend(request, query))
4923
- elif isStop:
5243
+ elif isTrigger:
4924
5244
  planType = self.safe_string(query, 'planType', 'normal_plan')
4925
5245
  request['planType'] = planType
4926
5246
  response = self.privateMixGetV2MixOrderOrdersPlanPending(self.extend(request, query))
@@ -5103,23 +5423,25 @@ class bitget(Exchange, ImplicitAPI):
5103
5423
  #
5104
5424
  data = self.safe_value(response, 'data')
5105
5425
  if type == 'spot':
5106
- if (marginMode is not None) or stop:
5107
- resultList = self.safe_value(data, 'orderList', [])
5426
+ if (marginMode is not None) or trigger:
5427
+ resultList = self.safe_list(data, 'orderList', [])
5108
5428
  return self.parse_orders(resultList, market, since, limit)
5109
5429
  else:
5110
- result = self.safe_value(data, 'entrustedList', [])
5430
+ result = self.safe_list(data, 'entrustedList', [])
5111
5431
  return self.parse_orders(result, market, since, limit)
5112
5432
  return self.parse_orders(data, market, since, limit)
5113
5433
 
5114
5434
  def fetch_closed_orders(self, symbol: Str = None, since: Int = None, limit: Int = None, params={}) -> List[Order]:
5115
5435
  """
5116
5436
  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
5437
+
5438
+ https://www.bitget.com/api-doc/spot/trade/Get-History-Orders
5439
+ https://www.bitget.com/api-doc/spot/plan/Get-History-Plan-Order
5440
+ https://www.bitget.com/api-doc/contract/trade/Get-Orders-History
5441
+ https://www.bitget.com/api-doc/contract/plan/orders-plan-history
5442
+ https://www.bitget.com/api-doc/margin/cross/trade/Get-Cross-Order-History
5443
+ https://www.bitget.com/api-doc/margin/isolated/trade/Get-Isolated-Order-History
5444
+
5123
5445
  :param str symbol: unified market symbol of the closed orders
5124
5446
  :param int [since]: timestamp in ms of the earliest order
5125
5447
  :param int [limit]: the max number of closed orders to return
@@ -5138,12 +5460,14 @@ class bitget(Exchange, ImplicitAPI):
5138
5460
  def fetch_canceled_orders(self, symbol: Str = None, since: Int = None, limit: Int = None, params={}):
5139
5461
  """
5140
5462
  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
5463
+
5464
+ https://www.bitget.com/api-doc/spot/trade/Get-History-Orders
5465
+ https://www.bitget.com/api-doc/spot/plan/Get-History-Plan-Order
5466
+ https://www.bitget.com/api-doc/contract/trade/Get-Orders-History
5467
+ https://www.bitget.com/api-doc/contract/plan/orders-plan-history
5468
+ https://www.bitget.com/api-doc/margin/cross/trade/Get-Cross-Order-History
5469
+ https://www.bitget.com/api-doc/margin/isolated/trade/Get-Isolated-Order-History
5470
+
5147
5471
  :param str symbol: unified market symbol of the canceled orders
5148
5472
  :param int [since]: timestamp in ms of the earliest order
5149
5473
  :param int [limit]: the max number of canceled orders to return
@@ -5161,12 +5485,14 @@ class bitget(Exchange, ImplicitAPI):
5161
5485
 
5162
5486
  def fetch_canceled_and_closed_orders(self, symbol: Str = None, since: Int = None, limit: Int = None, params={}):
5163
5487
  """
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
5488
+
5489
+ https://www.bitget.com/api-doc/spot/trade/Get-History-Orders
5490
+ https://www.bitget.com/api-doc/spot/plan/Get-History-Plan-Order
5491
+ https://www.bitget.com/api-doc/contract/trade/Get-Orders-History
5492
+ https://www.bitget.com/api-doc/contract/plan/orders-plan-history
5493
+ https://www.bitget.com/api-doc/margin/cross/trade/Get-Cross-Order-History
5494
+ https://www.bitget.com/api-doc/margin/isolated/trade/Get-Isolated-Order-History
5495
+
5170
5496
  fetches information on multiple canceled and closed orders made by the user
5171
5497
  :param str symbol: unified market symbol of the market orders were made in
5172
5498
  :param int [since]: the earliest time in ms to fetch orders for
@@ -5181,7 +5507,7 @@ class bitget(Exchange, ImplicitAPI):
5181
5507
  if symbol is not None:
5182
5508
  sandboxSymbol = self.convert_symbol_for_sandbox(symbol)
5183
5509
  symbol = sandboxSymbol
5184
- request = {}
5510
+ request: dict = {}
5185
5511
  if symbol is not None:
5186
5512
  market = self.market(symbol)
5187
5513
  request['symbol'] = market['id']
@@ -5201,7 +5527,7 @@ class bitget(Exchange, ImplicitAPI):
5201
5527
  return self.fetch_paginated_call_cursor('fetchCanceledAndClosedOrders', symbol, since, limit, params, cursorReceived, 'idLessThan')
5202
5528
  response = None
5203
5529
  trailing = self.safe_value(params, 'trailing')
5204
- stop = self.safe_bool_2(params, 'stop', 'trigger')
5530
+ trigger = self.safe_bool_2(params, 'stop', 'trigger')
5205
5531
  params = self.omit(params, ['stop', 'trigger', 'trailing'])
5206
5532
  request, params = self.handle_until_option('endTime', request, params)
5207
5533
  if since is not None:
@@ -5223,20 +5549,19 @@ class bitget(Exchange, ImplicitAPI):
5223
5549
  response = self.privateMarginGetV2MarginIsolatedHistoryOrders(self.extend(request, params))
5224
5550
  elif marginMode == 'cross':
5225
5551
  response = self.privateMarginGetV2MarginCrossedHistoryOrders(self.extend(request, params))
5552
+ elif trigger:
5553
+ if symbol is None:
5554
+ raise ArgumentsRequired(self.id + ' fetchCanceledAndClosedOrders() requires a symbol argument')
5555
+ endTime = self.safe_integer_n(params, ['endTime', 'until'])
5556
+ params = self.omit(params, ['until'])
5557
+ if since is None:
5558
+ since = now - 7776000000
5559
+ request['startTime'] = since
5560
+ if endTime is None:
5561
+ request['endTime'] = now
5562
+ response = self.privateSpotGetV2SpotTradeHistoryPlanOrder(self.extend(request, params))
5226
5563
  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))
5564
+ response = self.privateSpotGetV2SpotTradeHistoryOrders(self.extend(request, params))
5240
5565
  else:
5241
5566
  productType = None
5242
5567
  productType, params = self.handle_product_type_and_params(market, params)
@@ -5245,7 +5570,7 @@ class bitget(Exchange, ImplicitAPI):
5245
5570
  planType = self.safe_string(params, 'planType', 'track_plan')
5246
5571
  request['planType'] = planType
5247
5572
  response = self.privateMixGetV2MixOrderOrdersPlanHistory(self.extend(request, params))
5248
- elif stop:
5573
+ elif trigger:
5249
5574
  planType = self.safe_string(params, 'planType', 'normal_plan')
5250
5575
  request['planType'] = planType
5251
5576
  response = self.privateMixGetV2MixOrderOrdersPlanHistory(self.extend(request, params))
@@ -5431,29 +5756,31 @@ class bitget(Exchange, ImplicitAPI):
5431
5756
  #
5432
5757
  data = self.safe_value(response, 'data', {})
5433
5758
  if marketType == 'spot':
5434
- if (marginMode is not None) or stop:
5759
+ if (marginMode is not None) or trigger:
5435
5760
  return self.parse_orders(self.safe_value(data, 'orderList', []), market, since, limit)
5436
5761
  else:
5437
5762
  return self.parse_orders(self.safe_value(data, 'entrustedList', []), market, since, limit)
5438
5763
  if isinstance(response, str):
5439
5764
  response = json.loads(response)
5440
- orders = self.safe_value(response, 'data', [])
5765
+ orders = self.safe_list(response, 'data', [])
5441
5766
  return self.parse_orders(orders, market, since, limit)
5442
5767
 
5443
- def fetch_ledger(self, code: Str = None, since: Int = None, limit: Int = None, params={}):
5768
+ def fetch_ledger(self, code: Str = None, since: Int = None, limit: Int = None, params={}) -> List[LedgerEntry]:
5444
5769
  """
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
5770
+ fetch the history of changes, actions done by the user or operations that altered the balance of the user
5771
+
5772
+ https://www.bitget.com/api-doc/spot/account/Get-Account-Bills
5773
+ https://www.bitget.com/api-doc/contract/account/Get-Account-Bill
5774
+
5775
+ :param str [code]: unified currency code, default is None
5449
5776
  :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
5777
+ :param int [limit]: max number of ledger entries to return, default is None
5451
5778
  :param dict [params]: extra parameters specific to the exchange API endpoint
5452
5779
  :param int [params.until]: end time in ms
5453
5780
  :param str [params.symbol]: *contract only* unified market symbol
5454
5781
  :param str [params.productType]: *contract only* 'USDT-FUTURES', 'USDC-FUTURES', 'COIN-FUTURES', 'SUSDT-FUTURES', 'SUSDC-FUTURES' or 'SCOIN-FUTURES'
5455
5782
  :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>`
5783
+ :returns dict: a `ledger structure <https://docs.ccxt.com/#/?id=ledger>`
5457
5784
  """
5458
5785
  self.load_markets()
5459
5786
  symbol = self.safe_string(params, 'symbol')
@@ -5476,10 +5803,10 @@ class bitget(Exchange, ImplicitAPI):
5476
5803
  cursorReceived = 'endId'
5477
5804
  return self.fetch_paginated_call_cursor('fetchLedger', symbol, since, limit, params, cursorReceived, 'idLessThan')
5478
5805
  currency = None
5479
- request = {}
5806
+ request: dict = {}
5480
5807
  if code is not None:
5481
5808
  currency = self.currency(code)
5482
- request['coin'] = currency['code']
5809
+ request['coin'] = currency['id']
5483
5810
  request, params = self.handle_until_option('endTime', request, params)
5484
5811
  if since is not None:
5485
5812
  request['startTime'] = since
@@ -5545,7 +5872,7 @@ class bitget(Exchange, ImplicitAPI):
5545
5872
  return self.parse_ledger(bills, currency, since, limit)
5546
5873
  return self.parse_ledger(data, currency, since, limit)
5547
5874
 
5548
- def parse_ledger_entry(self, item, currency: Currency = None):
5875
+ def parse_ledger_entry(self, item: dict, currency: Currency = None) -> LedgerEntry:
5549
5876
  #
5550
5877
  # spot
5551
5878
  #
@@ -5575,6 +5902,7 @@ class bitget(Exchange, ImplicitAPI):
5575
5902
  #
5576
5903
  currencyId = self.safe_string(item, 'coin')
5577
5904
  code = self.safe_currency_code(currencyId, currency)
5905
+ currency = self.safe_currency(currencyId, currency)
5578
5906
  timestamp = self.safe_integer(item, 'cTime')
5579
5907
  after = self.safe_number(item, 'balance')
5580
5908
  fee = self.safe_number_2(item, 'fees', 'fee')
@@ -5583,7 +5911,7 @@ class bitget(Exchange, ImplicitAPI):
5583
5911
  direction = 'in'
5584
5912
  if amountRaw.find('-') >= 0:
5585
5913
  direction = 'out'
5586
- return {
5914
+ return self.safe_ledger_entry({
5587
5915
  'info': item,
5588
5916
  'id': self.safe_string(item, 'billId'),
5589
5917
  'timestamp': timestamp,
@@ -5598,11 +5926,14 @@ class bitget(Exchange, ImplicitAPI):
5598
5926
  'before': None,
5599
5927
  'after': after,
5600
5928
  'status': None,
5601
- 'fee': fee,
5602
- }
5929
+ 'fee': {
5930
+ 'currency': code,
5931
+ 'cost': fee,
5932
+ },
5933
+ }, currency)
5603
5934
 
5604
5935
  def parse_ledger_type(self, type):
5605
- types = {
5936
+ types: dict = {
5606
5937
  'trans_to_cross': 'transfer',
5607
5938
  'trans_from_cross': 'transfer',
5608
5939
  'trans_to_exchange': 'transfer',
@@ -5649,10 +5980,12 @@ class bitget(Exchange, ImplicitAPI):
5649
5980
  def fetch_my_trades(self, symbol: Str = None, since: Int = None, limit: Int = None, params={}) -> List[Trade]:
5650
5981
  """
5651
5982
  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
5983
+
5984
+ https://www.bitget.com/api-doc/spot/trade/Get-Fills
5985
+ https://www.bitget.com/api-doc/contract/trade/Get-Order-Fills
5986
+ https://www.bitget.com/api-doc/margin/cross/trade/Get-Cross-Order-Fills
5987
+ https://www.bitget.com/api-doc/margin/isolated/trade/Get-Isolated-Transaction-Details
5988
+
5656
5989
  :param str symbol: unified market symbol
5657
5990
  :param int [since]: the earliest time in ms to fetch trades for
5658
5991
  :param int [limit]: the maximum number of trades structures to retrieve
@@ -5684,7 +6017,7 @@ class bitget(Exchange, ImplicitAPI):
5684
6017
  cursorReceived = 'endId'
5685
6018
  return self.fetch_paginated_call_cursor('fetchMyTrades', symbol, since, limit, params, cursorReceived, 'idLessThan')
5686
6019
  response = None
5687
- request = {
6020
+ request: dict = {
5688
6021
  'symbol': market['id'],
5689
6022
  }
5690
6023
  request, params = self.handle_until_option('endTime', request, params)
@@ -5808,17 +6141,19 @@ class bitget(Exchange, ImplicitAPI):
5808
6141
  #
5809
6142
  data = self.safe_value(response, 'data')
5810
6143
  if (market['swap']) or (market['future']):
5811
- fillList = self.safe_value(data, 'fillList', [])
6144
+ fillList = self.safe_list(data, 'fillList', [])
5812
6145
  return self.parse_trades(fillList, market, since, limit)
5813
6146
  elif marginMode is not None:
5814
- fills = self.safe_value(data, 'fills', [])
6147
+ fills = self.safe_list(data, 'fills', [])
5815
6148
  return self.parse_trades(fills, market, since, limit)
5816
6149
  return self.parse_trades(data, market, since, limit)
5817
6150
 
5818
6151
  def fetch_position(self, symbol: str, params={}):
5819
6152
  """
5820
6153
  fetch data on a single open contract trade position
5821
- :see: https://www.bitget.com/api-doc/contract/position/get-single-position
6154
+
6155
+ https://www.bitget.com/api-doc/contract/position/get-single-position
6156
+
5822
6157
  :param str symbol: unified market symbol of the market the position is held in
5823
6158
  :param dict [params]: extra parameters specific to the exchange API endpoint
5824
6159
  :returns dict: a `position structure <https://docs.ccxt.com/#/?id=position-structure>`
@@ -5833,7 +6168,7 @@ class bitget(Exchange, ImplicitAPI):
5833
6168
  market = self.market(symbol)
5834
6169
  productType = None
5835
6170
  productType, params = self.handle_product_type_and_params(market, params)
5836
- request = {
6171
+ request: dict = {
5837
6172
  'symbol': market['id'],
5838
6173
  'marginCoin': market['settleId'],
5839
6174
  'productType': productType,
@@ -5869,15 +6204,17 @@ class bitget(Exchange, ImplicitAPI):
5869
6204
  # ]
5870
6205
  # }
5871
6206
  #
5872
- data = self.safe_value(response, 'data', [])
5873
- first = self.safe_value(data, 0, {})
6207
+ data = self.safe_list(response, 'data', [])
6208
+ first = self.safe_dict(data, 0, {})
5874
6209
  return self.parse_position(first, market)
5875
6210
 
5876
6211
  def fetch_positions(self, symbols: Strings = None, params={}) -> List[Position]:
5877
6212
  """
5878
6213
  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
6214
+
6215
+ https://www.bitget.com/api-doc/contract/position/get-all-position
6216
+ https://www.bitget.com/api-doc/contract/position/Get-History-Position
6217
+
5881
6218
  :param str[] [symbols]: list of unified market symbols
5882
6219
  :param dict [params]: extra parameters specific to the exchange API endpoint
5883
6220
  :param str [params.marginCoin]: the settle currency of the positions, needs to match the productType
@@ -5909,7 +6246,7 @@ class bitget(Exchange, ImplicitAPI):
5909
6246
  market = self.market(first)
5910
6247
  productType = None
5911
6248
  productType, params = self.handle_product_type_and_params(market, params)
5912
- request = {
6249
+ request: dict = {
5913
6250
  'productType': productType,
5914
6251
  }
5915
6252
  response = None
@@ -6010,7 +6347,7 @@ class bitget(Exchange, ImplicitAPI):
6010
6347
  symbols = self.market_symbols(symbols)
6011
6348
  return self.filter_by_array_positions(result, 'symbol', symbols, False)
6012
6349
 
6013
- def parse_position(self, position, market: Market = None):
6350
+ def parse_position(self, position: dict, market: Market = None):
6014
6351
  #
6015
6352
  # fetchPosition
6016
6353
  #
@@ -6060,7 +6397,7 @@ class bitget(Exchange, ImplicitAPI):
6060
6397
  # "cTime": "1700807507275"
6061
6398
  # }
6062
6399
  #
6063
- # fetchPositions: privateMixGetV2MixPositionHistoryPosition
6400
+ # fetchPositionsHistory: privateMixGetV2MixPositionHistoryPosition
6064
6401
  #
6065
6402
  # {
6066
6403
  # "symbol": "BTCUSDT",
@@ -6176,7 +6513,9 @@ class bitget(Exchange, ImplicitAPI):
6176
6513
  def fetch_funding_rate_history(self, symbol: Str = None, since: Int = None, limit: Int = None, params={}):
6177
6514
  """
6178
6515
  fetches historical funding rate prices
6179
- :see: https://www.bitget.com/api-doc/contract/market/Get-History-Funding-Rate
6516
+
6517
+ https://www.bitget.com/api-doc/contract/market/Get-History-Funding-Rate
6518
+
6180
6519
  :param str symbol: unified symbol of the market to fetch the funding rate history for
6181
6520
  :param int [since]: timestamp in ms of the earliest funding rate to fetch
6182
6521
  :param int [limit]: the maximum amount of funding rate structures to fetch
@@ -6200,7 +6539,7 @@ class bitget(Exchange, ImplicitAPI):
6200
6539
  market = self.market(symbol)
6201
6540
  productType = None
6202
6541
  productType, params = self.handle_product_type_and_params(market, params)
6203
- request = {
6542
+ request: dict = {
6204
6543
  'symbol': market['id'],
6205
6544
  'productType': productType,
6206
6545
  # 'pageSize': limit, # default 20
@@ -6240,10 +6579,12 @@ class bitget(Exchange, ImplicitAPI):
6240
6579
  sorted = self.sort_by(rates, 'timestamp')
6241
6580
  return self.filter_by_symbol_since_limit(sorted, market['symbol'], since, limit)
6242
6581
 
6243
- def fetch_funding_rate(self, symbol: str, params={}):
6582
+ def fetch_funding_rate(self, symbol: str, params={}) -> FundingRate:
6244
6583
  """
6245
6584
  fetch the current funding rate
6246
- :see: https://www.bitget.com/api-doc/contract/market/Get-Current-Funding-Rate
6585
+
6586
+ https://www.bitget.com/api-doc/contract/market/Get-Current-Funding-Rate
6587
+
6247
6588
  :param str symbol: unified market symbol
6248
6589
  :param dict [params]: extra parameters specific to the exchange API endpoint
6249
6590
  :returns dict: a `funding rate structure <https://docs.ccxt.com/#/?id=funding-rate-structure>`
@@ -6260,7 +6601,7 @@ class bitget(Exchange, ImplicitAPI):
6260
6601
  raise BadSymbol(self.id + ' fetchFundingRate() supports swap contracts only')
6261
6602
  productType = None
6262
6603
  productType, params = self.handle_product_type_and_params(market, params)
6263
- request = {
6604
+ request: dict = {
6264
6605
  'symbol': market['id'],
6265
6606
  'productType': productType,
6266
6607
  }
@@ -6281,39 +6622,148 @@ class bitget(Exchange, ImplicitAPI):
6281
6622
  data = self.safe_value(response, 'data', [])
6282
6623
  return self.parse_funding_rate(data[0], market)
6283
6624
 
6284
- def parse_funding_rate(self, contract, market: Market = None):
6625
+ def fetch_funding_rates(self, symbols: Strings = None, params={}) -> FundingRates:
6626
+ """
6627
+ fetch the current funding rates for all markets
6628
+
6629
+ https://www.bitget.com/api-doc/contract/market/Get-All-Symbol-Ticker
6630
+
6631
+ :param str[] [symbols]: list of unified market symbols
6632
+ :param dict [params]: extra parameters specific to the exchange API endpoint
6633
+ :param str [params.subType]: *contract only* 'linear', 'inverse'
6634
+ :param str [params.productType]: *contract only* 'USDT-FUTURES', 'USDC-FUTURES', 'COIN-FUTURES', 'SUSDT-FUTURES', 'SUSDC-FUTURES' or 'SCOIN-FUTURES'
6635
+ :returns dict: a dictionary of `funding rate structures <https://docs.ccxt.com/#/?id=funding-rates-structure>`, indexed by market symbols
6636
+ """
6637
+ self.load_markets()
6638
+ market = None
6639
+ if symbols is not None:
6640
+ symbol = self.safe_value(symbols, 0)
6641
+ sandboxMode = self.safe_bool(self.options, 'sandboxMode', False)
6642
+ if sandboxMode:
6643
+ sandboxSymbol = self.convert_symbol_for_sandbox(symbol)
6644
+ market = self.market(sandboxSymbol)
6645
+ else:
6646
+ market = self.market(symbol)
6647
+ request: dict = {}
6648
+ productType = None
6649
+ productType, params = self.handle_product_type_and_params(market, params)
6650
+ request['productType'] = productType
6651
+ response = self.publicMixGetV2MixMarketTickers(self.extend(request, params))
6652
+ # {
6653
+ # "code": "00000",
6654
+ # "msg": "success",
6655
+ # "requestTime": 1700533773477,
6656
+ # "data": [
6657
+ # {
6658
+ # "symbol": "BTCUSD",
6659
+ # "lastPr": "29904.5",
6660
+ # "askPr": "29904.5",
6661
+ # "bidPr": "29903.5",
6662
+ # "bidSz": "0.5091",
6663
+ # "askSz": "2.2694",
6664
+ # "high24h": "0",
6665
+ # "low24h": "0",
6666
+ # "ts": "1695794271400",
6667
+ # "change24h": "0",
6668
+ # "baseVolume": "0",
6669
+ # "quoteVolume": "0",
6670
+ # "usdtVolume": "0",
6671
+ # "openUtc": "0",
6672
+ # "changeUtc24h": "0",
6673
+ # "indexPrice": "29132.353333",
6674
+ # "fundingRate": "-0.0007",
6675
+ # "holdingAmount": "125.6844",
6676
+ # "deliveryStartTime": null,
6677
+ # "deliveryTime": null,
6678
+ # "deliveryStatus": "delivery_normal",
6679
+ # "open24h": "0",
6680
+ # "markPrice": "12345"
6681
+ # },
6682
+ # ]
6683
+ # }
6684
+ symbols = self.market_symbols(symbols)
6685
+ data = self.safe_list(response, 'data', [])
6686
+ return self.parse_funding_rates(data, symbols)
6687
+
6688
+ def parse_funding_rate(self, contract, market: Market = None) -> FundingRate:
6689
+ #
6690
+ # fetchFundingRate
6285
6691
  #
6286
6692
  # {
6287
6693
  # "symbol": "BTCUSDT",
6288
6694
  # "fundingRate": "-0.000182"
6289
6695
  # }
6290
6696
  #
6697
+ # fetchFundingInterval
6698
+ #
6699
+ # {
6700
+ # "symbol": "BTCUSDT",
6701
+ # "nextFundingTime": "1727942400000",
6702
+ # "ratePeriod": "8"
6703
+ # }
6704
+ # fetchFundingRates
6705
+ # {
6706
+ # "symbol": "BTCUSD",
6707
+ # "lastPr": "29904.5",
6708
+ # "askPr": "29904.5",
6709
+ # "bidPr": "29903.5",
6710
+ # "bidSz": "0.5091",
6711
+ # "askSz": "2.2694",
6712
+ # "high24h": "0",
6713
+ # "low24h": "0",
6714
+ # "ts": "1695794271400",
6715
+ # "change24h": "0",
6716
+ # "baseVolume": "0",
6717
+ # "quoteVolume": "0",
6718
+ # "usdtVolume": "0",
6719
+ # "openUtc": "0",
6720
+ # "changeUtc24h": "0",
6721
+ # "indexPrice": "29132.353333",
6722
+ # "fundingRate": "-0.0007",
6723
+ # "holdingAmount": "125.6844",
6724
+ # "deliveryStartTime": null,
6725
+ # "deliveryTime": null,
6726
+ # "deliveryStatus": "delivery_normal",
6727
+ # "open24h": "0",
6728
+ # "markPrice": "12345"
6729
+ # }
6291
6730
  marketId = self.safe_string(contract, 'symbol')
6292
6731
  symbol = self.safe_symbol(marketId, market, None, 'swap')
6732
+ fundingTimestamp = self.safe_integer(contract, 'nextFundingTime')
6733
+ interval = self.safe_string(contract, 'ratePeriod')
6734
+ timestamp = self.safe_integer(contract, 'ts')
6735
+ markPrice = self.safe_number(contract, 'markPrice')
6736
+ indexPrice = self.safe_number(contract, 'indexPrice')
6737
+ intervalString = None
6738
+ if interval is not None:
6739
+ intervalString = interval + 'h'
6293
6740
  return {
6294
6741
  'info': contract,
6295
6742
  'symbol': symbol,
6296
- 'markPrice': None,
6297
- 'indexPrice': None,
6743
+ 'markPrice': markPrice,
6744
+ 'indexPrice': indexPrice,
6298
6745
  'interestRate': None,
6299
6746
  'estimatedSettlePrice': None,
6300
- 'timestamp': None,
6301
- 'datetime': None,
6747
+ 'timestamp': timestamp,
6748
+ 'datetime': self.iso8601(timestamp),
6302
6749
  'fundingRate': self.safe_number(contract, 'fundingRate'),
6303
- 'fundingTimestamp': None,
6304
- 'fundingDatetime': None,
6750
+ 'fundingTimestamp': fundingTimestamp,
6751
+ 'fundingDatetime': self.iso8601(fundingTimestamp),
6305
6752
  'nextFundingRate': None,
6306
6753
  'nextFundingTimestamp': None,
6307
6754
  'nextFundingDatetime': None,
6308
6755
  'previousFundingRate': None,
6309
6756
  'previousFundingTimestamp': None,
6310
6757
  'previousFundingDatetime': None,
6758
+ 'interval': intervalString,
6311
6759
  }
6312
6760
 
6313
6761
  def fetch_funding_history(self, symbol: Str = None, since: Int = None, limit: Int = None, params={}) -> List[FundingHistory]:
6314
6762
  """
6315
6763
  fetch the funding history
6316
- :see: https://www.bitget.com/api-doc/contract/account/Get-Account-Bill
6764
+
6765
+ https://www.bitget.com/api-doc/contract/account/Get-Account-Bill
6766
+
6317
6767
  :param str symbol: unified market symbol
6318
6768
  :param int [since]: the starting timestamp in milliseconds
6319
6769
  :param int [limit]: the number of entries to return
@@ -6340,7 +6790,7 @@ class bitget(Exchange, ImplicitAPI):
6340
6790
  raise BadSymbol(self.id + ' fetchFundingHistory() supports swap contracts only')
6341
6791
  productType = None
6342
6792
  productType, params = self.handle_product_type_and_params(market, params)
6343
- request = {
6793
+ request: dict = {
6344
6794
  'symbol': market['id'],
6345
6795
  'marginCoin': market['settleId'],
6346
6796
  'businessType': 'contract_settle_fee',
@@ -6415,7 +6865,7 @@ class bitget(Exchange, ImplicitAPI):
6415
6865
  sorted = self.sort_by(result, 'timestamp')
6416
6866
  return self.filter_by_since_limit(sorted, since, limit)
6417
6867
 
6418
- def modify_margin_helper(self, symbol: str, amount, type, params={}):
6868
+ def modify_margin_helper(self, symbol: str, amount, type, params={}) -> MarginModification:
6419
6869
  self.load_markets()
6420
6870
  holdSide = self.safe_string(params, 'holdSide')
6421
6871
  sandboxMode = self.safe_bool(self.options, 'sandboxMode', False)
@@ -6427,7 +6877,7 @@ class bitget(Exchange, ImplicitAPI):
6427
6877
  market = self.market(symbol)
6428
6878
  productType = None
6429
6879
  productType, params = self.handle_product_type_and_params(market, params)
6430
- request = {
6880
+ request: dict = {
6431
6881
  'symbol': market['id'],
6432
6882
  'marginCoin': market['settleId'],
6433
6883
  'amount': self.amount_to_precision(symbol, amount), # positive value for adding margin, negative for reducing
@@ -6449,22 +6899,38 @@ class bitget(Exchange, ImplicitAPI):
6449
6899
  'type': type,
6450
6900
  })
6451
6901
 
6452
- def parse_margin_modification(self, data, market: Market = None):
6902
+ def parse_margin_modification(self, data: dict, market: Market = None) -> MarginModification:
6903
+ #
6904
+ # addMargin/reduceMargin
6905
+ #
6906
+ # {
6907
+ # "code": "00000",
6908
+ # "msg": "success",
6909
+ # "requestTime": 1700813444618,
6910
+ # "data": ""
6911
+ # }
6912
+ #
6453
6913
  errorCode = self.safe_string(data, 'code')
6454
6914
  status = 'ok' if (errorCode == '00000') else 'failed'
6455
6915
  return {
6456
6916
  'info': data,
6917
+ 'symbol': market['symbol'],
6457
6918
  'type': None,
6919
+ 'marginMode': 'isolated',
6458
6920
  'amount': None,
6921
+ 'total': None,
6459
6922
  'code': market['settle'],
6460
- 'symbol': market['symbol'],
6461
6923
  'status': status,
6924
+ 'timestamp': None,
6925
+ 'datetime': None,
6462
6926
  }
6463
6927
 
6464
- def reduce_margin(self, symbol: str, amount, params={}):
6928
+ def reduce_margin(self, symbol: str, amount: float, params={}) -> MarginModification:
6465
6929
  """
6466
6930
  remove margin from a position
6467
- :see: https://www.bitget.com/api-doc/contract/account/Change-Margin
6931
+
6932
+ https://www.bitget.com/api-doc/contract/account/Change-Margin
6933
+
6468
6934
  :param str symbol: unified market symbol
6469
6935
  :param float amount: the amount of margin to remove
6470
6936
  :param dict [params]: extra parameters specific to the exchange API endpoint
@@ -6477,10 +6943,12 @@ class bitget(Exchange, ImplicitAPI):
6477
6943
  raise ArgumentsRequired(self.id + ' reduceMargin() requires a holdSide parameter, either long or short')
6478
6944
  return self.modify_margin_helper(symbol, amount, 'reduce', params)
6479
6945
 
6480
- def add_margin(self, symbol: str, amount, params={}):
6946
+ def add_margin(self, symbol: str, amount: float, params={}) -> MarginModification:
6481
6947
  """
6482
6948
  add margin
6483
- :see: https://www.bitget.com/api-doc/contract/account/Change-Margin
6949
+
6950
+ https://www.bitget.com/api-doc/contract/account/Change-Margin
6951
+
6484
6952
  :param str symbol: unified market symbol
6485
6953
  :param float amount: the amount of margin to add
6486
6954
  :param dict [params]: extra parameters specific to the exchange API endpoint
@@ -6494,7 +6962,9 @@ class bitget(Exchange, ImplicitAPI):
6494
6962
  def fetch_leverage(self, symbol: str, params={}) -> Leverage:
6495
6963
  """
6496
6964
  fetch the set leverage for a market
6497
- :see: https://www.bitget.com/api-doc/contract/account/Get-Single-Account
6965
+
6966
+ https://www.bitget.com/api-doc/contract/account/Get-Single-Account
6967
+
6498
6968
  :param str symbol: unified market symbol
6499
6969
  :param dict [params]: extra parameters specific to the exchange API endpoint
6500
6970
  :returns dict: a `leverage structure <https://docs.ccxt.com/#/?id=leverage-structure>`
@@ -6509,7 +6979,7 @@ class bitget(Exchange, ImplicitAPI):
6509
6979
  market = self.market(symbol)
6510
6980
  productType = None
6511
6981
  productType, params = self.handle_product_type_and_params(market, params)
6512
- request = {
6982
+ request: dict = {
6513
6983
  'symbol': market['id'],
6514
6984
  'marginCoin': market['settleId'],
6515
6985
  'productType': productType,
@@ -6546,7 +7016,7 @@ class bitget(Exchange, ImplicitAPI):
6546
7016
  data = self.safe_dict(response, 'data', {})
6547
7017
  return self.parse_leverage(data, market)
6548
7018
 
6549
- def parse_leverage(self, leverage, market=None) -> Leverage:
7019
+ def parse_leverage(self, leverage: dict, market: Market = None) -> Leverage:
6550
7020
  return {
6551
7021
  'info': leverage,
6552
7022
  'symbol': market['symbol'],
@@ -6558,7 +7028,9 @@ class bitget(Exchange, ImplicitAPI):
6558
7028
  def set_leverage(self, leverage: Int, symbol: Str = None, params={}):
6559
7029
  """
6560
7030
  set the level of leverage for a market
6561
- :see: https://www.bitget.com/api-doc/contract/account/Change-Leverage
7031
+
7032
+ https://www.bitget.com/api-doc/contract/account/Change-Leverage
7033
+
6562
7034
  :param int leverage: the rate of leverage
6563
7035
  :param str symbol: unified market symbol
6564
7036
  :param dict [params]: extra parameters specific to the exchange API endpoint
@@ -6577,7 +7049,7 @@ class bitget(Exchange, ImplicitAPI):
6577
7049
  market = self.market(symbol)
6578
7050
  productType = None
6579
7051
  productType, params = self.handle_product_type_and_params(market, params)
6580
- request = {
7052
+ request: dict = {
6581
7053
  'symbol': market['id'],
6582
7054
  'marginCoin': market['settleId'],
6583
7055
  'leverage': self.number_to_string(leverage),
@@ -6605,7 +7077,9 @@ class bitget(Exchange, ImplicitAPI):
6605
7077
  def set_margin_mode(self, marginMode: str, symbol: Str = None, params={}):
6606
7078
  """
6607
7079
  set margin mode to 'cross' or 'isolated'
6608
- :see: https://www.bitget.com/api-doc/contract/account/Change-Margin-Mode
7080
+
7081
+ https://www.bitget.com/api-doc/contract/account/Change-Margin-Mode
7082
+
6609
7083
  :param str marginMode: 'cross' or 'isolated'
6610
7084
  :param str symbol: unified market symbol
6611
7085
  :param dict [params]: extra parameters specific to the exchange API endpoint
@@ -6628,7 +7102,7 @@ class bitget(Exchange, ImplicitAPI):
6628
7102
  market = self.market(symbol)
6629
7103
  productType = None
6630
7104
  productType, params = self.handle_product_type_and_params(market, params)
6631
- request = {
7105
+ request: dict = {
6632
7106
  'symbol': market['id'],
6633
7107
  'marginCoin': market['settleId'],
6634
7108
  'marginMode': marginMode,
@@ -6654,7 +7128,9 @@ class bitget(Exchange, ImplicitAPI):
6654
7128
  def set_position_mode(self, hedged: bool, symbol: Str = None, params={}):
6655
7129
  """
6656
7130
  set hedged to True or False for a market
6657
- :see: https://www.bitget.com/api-doc/contract/account/Change-Hold-Mode
7131
+
7132
+ https://www.bitget.com/api-doc/contract/account/Change-Hold-Mode
7133
+
6658
7134
  :param bool hedged: set to True to use dualSidePosition
6659
7135
  :param str symbol: not used by bitget setPositionMode()
6660
7136
  :param dict [params]: extra parameters specific to the exchange API endpoint
@@ -6673,7 +7149,7 @@ class bitget(Exchange, ImplicitAPI):
6673
7149
  market = self.market(symbol)
6674
7150
  productType = None
6675
7151
  productType, params = self.handle_product_type_and_params(market, params)
6676
- request = {
7152
+ request: dict = {
6677
7153
  'posMode': posMode,
6678
7154
  'productType': productType,
6679
7155
  }
@@ -6693,7 +7169,9 @@ class bitget(Exchange, ImplicitAPI):
6693
7169
  def fetch_open_interest(self, symbol: str, params={}):
6694
7170
  """
6695
7171
  retrieves the open interest of a contract trading pair
6696
- :see: https://www.bitget.com/api-doc/contract/market/Get-Open-Interest
7172
+
7173
+ https://www.bitget.com/api-doc/contract/market/Get-Open-Interest
7174
+
6697
7175
  :param str symbol: unified CCXT market symbol
6698
7176
  :param dict [params]: exchange specific parameters
6699
7177
  :returns dict} an open interest structure{@link https://docs.ccxt.com/#/?id=open-interest-structure:
@@ -6710,7 +7188,7 @@ class bitget(Exchange, ImplicitAPI):
6710
7188
  raise BadRequest(self.id + ' fetchOpenInterest() supports contract markets only')
6711
7189
  productType = None
6712
7190
  productType, params = self.handle_product_type_and_params(market, params)
6713
- request = {
7191
+ request: dict = {
6714
7192
  'symbol': market['id'],
6715
7193
  'productType': productType,
6716
7194
  }
@@ -6731,7 +7209,7 @@ class bitget(Exchange, ImplicitAPI):
6731
7209
  # }
6732
7210
  # }
6733
7211
  #
6734
- data = self.safe_value(response, 'data', {})
7212
+ data = self.safe_dict(response, 'data', {})
6735
7213
  return self.parse_open_interest(data, market)
6736
7214
 
6737
7215
  def parse_open_interest(self, interest, market: Market = None):
@@ -6758,10 +7236,12 @@ class bitget(Exchange, ImplicitAPI):
6758
7236
  'info': interest,
6759
7237
  }, market)
6760
7238
 
6761
- def fetch_transfers(self, code: Str = None, since: Int = None, limit: Int = None, params={}):
7239
+ def fetch_transfers(self, code: Str = None, since: Int = None, limit: Int = None, params={}) -> List[TransferEntry]:
6762
7240
  """
6763
7241
  fetch a history of internal transfers made on an account
6764
- :see: https://www.bitget.com/api-doc/spot/account/Get-Account-TransferRecords
7242
+
7243
+ https://www.bitget.com/api-doc/spot/account/Get-Account-TransferRecords
7244
+
6765
7245
  :param str code: unified currency code of the currency transferred
6766
7246
  :param int [since]: the earliest time in ms to fetch transfers for
6767
7247
  :param int [limit]: the maximum number of transfers structures to retrieve
@@ -6779,8 +7259,8 @@ class bitget(Exchange, ImplicitAPI):
6779
7259
  accountsByType = self.safe_value(self.options, 'accountsByType', {})
6780
7260
  type = self.safe_string(accountsByType, fromAccount)
6781
7261
  currency = self.currency(code)
6782
- request = {
6783
- 'coin': currency['code'],
7262
+ request: dict = {
7263
+ 'coin': currency['id'],
6784
7264
  'fromType': type,
6785
7265
  }
6786
7266
  if since is not None:
@@ -6810,13 +7290,15 @@ class bitget(Exchange, ImplicitAPI):
6810
7290
  # ]
6811
7291
  # }
6812
7292
  #
6813
- data = self.safe_value(response, 'data', [])
7293
+ data = self.safe_list(response, 'data', [])
6814
7294
  return self.parse_transfers(data, currency, since, limit)
6815
7295
 
6816
7296
  def transfer(self, code: str, amount: float, fromAccount: str, toAccount: str, params={}) -> TransferEntry:
6817
7297
  """
6818
7298
  transfer currency internally between wallets on the same account
6819
- :see: https://www.bitget.com/api-doc/spot/account/Wallet-Transfer
7299
+
7300
+ https://www.bitget.com/api-doc/spot/account/Wallet-Transfer
7301
+
6820
7302
  :param str code: unified currency code
6821
7303
  :param float amount: amount to transfer
6822
7304
  :param str fromAccount: account to transfer from
@@ -6831,11 +7313,11 @@ class bitget(Exchange, ImplicitAPI):
6831
7313
  accountsByType = self.safe_value(self.options, 'accountsByType', {})
6832
7314
  fromType = self.safe_string(accountsByType, fromAccount)
6833
7315
  toType = self.safe_string(accountsByType, toAccount)
6834
- request = {
7316
+ request: dict = {
6835
7317
  'fromType': fromType,
6836
7318
  'toType': toType,
6837
7319
  'amount': amount,
6838
- 'coin': currency['code'],
7320
+ 'coin': currency['id'],
6839
7321
  }
6840
7322
  symbol = self.safe_string(params, 'symbol')
6841
7323
  params = self.omit(params, 'symbol')
@@ -6859,7 +7341,7 @@ class bitget(Exchange, ImplicitAPI):
6859
7341
  data['ts'] = self.safe_integer(response, 'requestTime')
6860
7342
  return self.parse_transfer(data, currency)
6861
7343
 
6862
- def parse_transfer(self, transfer, currency: Currency = None):
7344
+ def parse_transfer(self, transfer: dict, currency: Currency = None) -> TransferEntry:
6863
7345
  #
6864
7346
  # transfer
6865
7347
  #
@@ -6904,8 +7386,8 @@ class bitget(Exchange, ImplicitAPI):
6904
7386
  'status': self.parse_transfer_status(status),
6905
7387
  }
6906
7388
 
6907
- def parse_transfer_status(self, status):
6908
- statuses = {
7389
+ def parse_transfer_status(self, status: Str) -> Str:
7390
+ statuses: dict = {
6909
7391
  'successful': 'ok',
6910
7392
  }
6911
7393
  return self.safe_string(statuses, status, status)
@@ -6935,7 +7417,7 @@ class bitget(Exchange, ImplicitAPI):
6935
7417
  #
6936
7418
  chains = self.safe_value(fee, 'chains', [])
6937
7419
  chainsLength = len(chains)
6938
- result = {
7420
+ result: dict = {
6939
7421
  'info': fee,
6940
7422
  'withdraw': {
6941
7423
  'fee': None,
@@ -6964,7 +7446,9 @@ class bitget(Exchange, ImplicitAPI):
6964
7446
  def fetch_deposit_withdraw_fees(self, codes: Strings = None, params={}):
6965
7447
  """
6966
7448
  fetch deposit and withdraw fees
6967
- :see: https://www.bitget.com/api-doc/spot/market/Get-Coin-List
7449
+
7450
+ https://www.bitget.com/api-doc/spot/market/Get-Coin-List
7451
+
6968
7452
  :param str[]|None codes: list of unified currency codes
6969
7453
  :param dict [params]: extra parameters specific to the exchange API endpoint
6970
7454
  :returns dict: a list of `fee structures <https://docs.ccxt.com/#/?id=fee-structure>`
@@ -7000,13 +7484,15 @@ class bitget(Exchange, ImplicitAPI):
7000
7484
  # "requestTime": "1700120731773"
7001
7485
  # }
7002
7486
  #
7003
- data = self.safe_value(response, 'data', [])
7487
+ data = self.safe_list(response, 'data', [])
7004
7488
  return self.parse_deposit_withdraw_fees(data, codes, 'coin')
7005
7489
 
7006
7490
  def borrow_cross_margin(self, code: str, amount: float, params={}):
7007
7491
  """
7008
7492
  create a loan to borrow margin
7009
- :see: https://www.bitget.com/api-doc/margin/cross/account/Cross-Borrow
7493
+
7494
+ https://www.bitget.com/api-doc/margin/cross/account/Cross-Borrow
7495
+
7010
7496
  :param str code: unified currency code of the currency to borrow
7011
7497
  :param str amount: the amount to borrow
7012
7498
  :param dict [params]: extra parameters specific to the exchange API endpoint
@@ -7014,8 +7500,8 @@ class bitget(Exchange, ImplicitAPI):
7014
7500
  """
7015
7501
  self.load_markets()
7016
7502
  currency = self.currency(code)
7017
- request = {
7018
- 'coin': currency['code'],
7503
+ request: dict = {
7504
+ 'coin': currency['id'],
7019
7505
  'borrowAmount': self.currency_to_precision(code, amount),
7020
7506
  }
7021
7507
  response = self.privateMarginPostV2MarginCrossedAccountBorrow(self.extend(request, params))
@@ -7037,7 +7523,9 @@ class bitget(Exchange, ImplicitAPI):
7037
7523
  def borrow_isolated_margin(self, symbol: str, code: str, amount: float, params={}):
7038
7524
  """
7039
7525
  create a loan to borrow margin
7040
- :see: https://www.bitget.com/api-doc/margin/isolated/account/Isolated-Borrow
7526
+
7527
+ https://www.bitget.com/api-doc/margin/isolated/account/Isolated-Borrow
7528
+
7041
7529
  :param str symbol: unified market symbol
7042
7530
  :param str code: unified currency code of the currency to borrow
7043
7531
  :param str amount: the amount to borrow
@@ -7047,8 +7535,8 @@ class bitget(Exchange, ImplicitAPI):
7047
7535
  self.load_markets()
7048
7536
  currency = self.currency(code)
7049
7537
  market = self.market(symbol)
7050
- request = {
7051
- 'coin': currency['code'],
7538
+ request: dict = {
7539
+ 'coin': currency['id'],
7052
7540
  'borrowAmount': self.currency_to_precision(code, amount),
7053
7541
  'symbol': market['id'],
7054
7542
  }
@@ -7072,7 +7560,9 @@ class bitget(Exchange, ImplicitAPI):
7072
7560
  def repay_isolated_margin(self, symbol: str, code: str, amount, params={}):
7073
7561
  """
7074
7562
  repay borrowed margin and interest
7075
- :see: https://www.bitget.com/api-doc/margin/isolated/account/Isolated-Repay
7563
+
7564
+ https://www.bitget.com/api-doc/margin/isolated/account/Isolated-Repay
7565
+
7076
7566
  :param str symbol: unified market symbol
7077
7567
  :param str code: unified currency code of the currency to repay
7078
7568
  :param str amount: the amount to repay
@@ -7082,8 +7572,8 @@ class bitget(Exchange, ImplicitAPI):
7082
7572
  self.load_markets()
7083
7573
  currency = self.currency(code)
7084
7574
  market = self.market(symbol)
7085
- request = {
7086
- 'coin': currency['code'],
7575
+ request: dict = {
7576
+ 'coin': currency['id'],
7087
7577
  'repayAmount': self.currency_to_precision(code, amount),
7088
7578
  'symbol': market['id'],
7089
7579
  }
@@ -7108,7 +7598,9 @@ class bitget(Exchange, ImplicitAPI):
7108
7598
  def repay_cross_margin(self, code: str, amount, params={}):
7109
7599
  """
7110
7600
  repay borrowed margin and interest
7111
- :see: https://www.bitget.com/api-doc/margin/cross/account/Cross-Repay
7601
+
7602
+ https://www.bitget.com/api-doc/margin/cross/account/Cross-Repay
7603
+
7112
7604
  :param str code: unified currency code of the currency to repay
7113
7605
  :param str amount: the amount to repay
7114
7606
  :param dict [params]: extra parameters specific to the exchange API endpoint
@@ -7116,8 +7608,8 @@ class bitget(Exchange, ImplicitAPI):
7116
7608
  """
7117
7609
  self.load_markets()
7118
7610
  currency = self.currency(code)
7119
- request = {
7120
- 'coin': currency['code'],
7611
+ request: dict = {
7612
+ 'coin': currency['id'],
7121
7613
  'repayAmount': self.currency_to_precision(code, amount),
7122
7614
  }
7123
7615
  response = self.privateMarginPostV2MarginCrossedAccountRepay(self.extend(request, params))
@@ -7193,8 +7685,10 @@ class bitget(Exchange, ImplicitAPI):
7193
7685
  def fetch_my_liquidations(self, symbol: Str = None, since: Int = None, limit: Int = None, params={}) -> List[Liquidation]:
7194
7686
  """
7195
7687
  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
7688
+
7689
+ https://www.bitget.com/api-doc/margin/cross/record/Get-Cross-Liquidation-Records
7690
+ https://www.bitget.com/api-doc/margin/isolated/record/Get-Isolated-Liquidation-Records
7691
+
7198
7692
  :param str [symbol]: unified CCXT market symbol
7199
7693
  :param int [since]: the earliest time in ms to fetch liquidations for
7200
7694
  :param int [limit]: the maximum number of liquidation structures to retrieve
@@ -7216,7 +7710,7 @@ class bitget(Exchange, ImplicitAPI):
7216
7710
  type, params = self.handle_market_type_and_params('fetchMyLiquidations', market, params)
7217
7711
  if type != 'spot':
7218
7712
  raise NotSupported(self.id + ' fetchMyLiquidations() supports spot margin markets only')
7219
- request = {}
7713
+ request: dict = {}
7220
7714
  request, params = self.handle_until_option('endTime', request, params)
7221
7715
  if since is not None:
7222
7716
  request['startTime'] = since
@@ -7287,7 +7781,7 @@ class bitget(Exchange, ImplicitAPI):
7287
7781
  # }
7288
7782
  #
7289
7783
  data = self.safe_value(response, 'data', {})
7290
- liquidations = self.safe_value(data, 'resultList', [])
7784
+ liquidations = self.safe_list(data, 'resultList', [])
7291
7785
  return self.parse_liquidations(liquidations, market, since, limit)
7292
7786
 
7293
7787
  def parse_liquidation(self, liquidation, market: Market = None):
@@ -7338,17 +7832,19 @@ class bitget(Exchange, ImplicitAPI):
7338
7832
  'datetime': self.iso8601(timestamp),
7339
7833
  })
7340
7834
 
7341
- def fetch_isolated_borrow_rate(self, symbol: str, params={}):
7835
+ def fetch_isolated_borrow_rate(self, symbol: str, params={}) -> IsolatedBorrowRate:
7342
7836
  """
7343
7837
  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
7838
+
7839
+ https://www.bitget.com/api-doc/margin/isolated/account/Isolated-Margin-Interest-Rate-And-Max-Borrowable-Amount
7840
+
7345
7841
  :param str symbol: unified market symbol
7346
7842
  :param dict [params]: extra parameters specific to the exchange API endpoint
7347
7843
  :returns dict: an `isolated borrow rate structure <https://docs.ccxt.com/#/?id=isolated-borrow-rate-structure>`
7348
7844
  """
7349
7845
  self.load_markets()
7350
7846
  market = self.market(symbol)
7351
- request = {
7847
+ request: dict = {
7352
7848
  'symbol': market['id'],
7353
7849
  }
7354
7850
  response = self.privateMarginGetV2MarginIsolatedInterestRateAndLimit(self.extend(request, params))
@@ -7399,7 +7895,7 @@ class bitget(Exchange, ImplicitAPI):
7399
7895
  first['timestamp'] = timestamp
7400
7896
  return self.parse_isolated_borrow_rate(first, market)
7401
7897
 
7402
- def parse_isolated_borrow_rate(self, info, market: Market = None):
7898
+ def parse_isolated_borrow_rate(self, info: dict, market: Market = None) -> IsolatedBorrowRate:
7403
7899
  #
7404
7900
  # {
7405
7901
  # "symbol": "BTCUSDT",
@@ -7451,10 +7947,12 @@ class bitget(Exchange, ImplicitAPI):
7451
7947
  'info': info,
7452
7948
  }
7453
7949
 
7454
- def fetch_cross_borrow_rate(self, code: str, params={}):
7950
+ def fetch_cross_borrow_rate(self, code: str, params={}) -> CrossBorrowRate:
7455
7951
  """
7456
7952
  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
7953
+
7954
+ https://www.bitget.com/api-doc/margin/cross/account/Get-Cross-Margin-Interest-Rate-And-Borrowable
7955
+
7458
7956
  :param str code: unified currency code
7459
7957
  :param dict [params]: extra parameters specific to the exchange API endpoint
7460
7958
  :param str [params.symbol]: required for isolated margin
@@ -7462,8 +7960,8 @@ class bitget(Exchange, ImplicitAPI):
7462
7960
  """
7463
7961
  self.load_markets()
7464
7962
  currency = self.currency(code)
7465
- request = {
7466
- 'coin': currency['code'],
7963
+ request: dict = {
7964
+ 'coin': currency['id'],
7467
7965
  }
7468
7966
  response = self.privateMarginGetV2MarginCrossedInterestRateAndLimit(self.extend(request, params))
7469
7967
  #
@@ -7529,11 +8027,13 @@ class bitget(Exchange, ImplicitAPI):
7529
8027
  'info': info,
7530
8028
  }
7531
8029
 
7532
- def fetch_borrow_interest(self, code: Str = None, symbol: Str = None, since: Int = None, limit: Int = None, params={}):
8030
+ def fetch_borrow_interest(self, code: Str = None, symbol: Str = None, since: Int = None, limit: Int = None, params={}) -> List[BorrowInterest]:
7533
8031
  """
7534
8032
  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
8033
+
8034
+ https://www.bitget.com/api-doc/margin/cross/record/Get-Cross-Interest-Records
8035
+ https://www.bitget.com/api-doc/margin/isolated/record/Get-Isolated-Interest-Records
8036
+
7537
8037
  :param str [code]: unified currency code
7538
8038
  :param str [symbol]: unified market symbol when fetching interest in isolated markets
7539
8039
  :param int [since]: the earliest time in ms to fetch borrow interest for
@@ -7550,11 +8050,11 @@ class bitget(Exchange, ImplicitAPI):
7550
8050
  market = None
7551
8051
  if symbol is not None:
7552
8052
  market = self.market(symbol)
7553
- request = {}
8053
+ request: dict = {}
7554
8054
  currency = None
7555
8055
  if code is not None:
7556
8056
  currency = self.currency(code)
7557
- request['coin'] = currency['code']
8057
+ request['coin'] = currency['id']
7558
8058
  if since is not None:
7559
8059
  request['startTime'] = since
7560
8060
  else:
@@ -7626,7 +8126,7 @@ class bitget(Exchange, ImplicitAPI):
7626
8126
  interest = self.parse_borrow_interests(rows, market)
7627
8127
  return self.filter_by_currency_since_limit(interest, code, since, limit)
7628
8128
 
7629
- def parse_borrow_interest(self, info, market: Market = None):
8129
+ def parse_borrow_interest(self, info: dict, market: Market = None) -> BorrowInterest:
7630
8130
  #
7631
8131
  # isolated
7632
8132
  #
@@ -7660,21 +8160,23 @@ class bitget(Exchange, ImplicitAPI):
7660
8160
  marginMode = 'isolated' if (marketId is not None) else 'cross'
7661
8161
  timestamp = self.safe_integer(info, 'cTime')
7662
8162
  return {
8163
+ 'info': info,
7663
8164
  'symbol': self.safe_string(market, 'symbol'),
7664
- 'marginMode': marginMode,
7665
8165
  'currency': self.safe_currency_code(self.safe_string(info, 'interestCoin')),
7666
8166
  'interest': self.safe_number(info, 'interestAmount'),
7667
8167
  'interestRate': self.safe_number(info, 'dailyInterestRate'),
7668
8168
  'amountBorrowed': None,
8169
+ 'marginMode': marginMode,
7669
8170
  'timestamp': timestamp,
7670
8171
  'datetime': self.iso8601(timestamp),
7671
- 'info': info,
7672
8172
  }
7673
8173
 
7674
8174
  def close_position(self, symbol: str, side: OrderSide = None, params={}) -> Order:
7675
8175
  """
7676
8176
  closes an open position for a market
7677
- :see: https://www.bitget.com/api-doc/contract/trade/Flash-Close-Position
8177
+
8178
+ https://www.bitget.com/api-doc/contract/trade/Flash-Close-Position
8179
+
7678
8180
  :param str symbol: unified CCXT market symbol
7679
8181
  :param str [side]: one-way mode: 'buy' or 'sell', hedge-mode: 'long' or 'short'
7680
8182
  :param dict [params]: extra parameters specific to the exchange API endpoint
@@ -7690,7 +8192,7 @@ class bitget(Exchange, ImplicitAPI):
7690
8192
  market = self.market(symbol)
7691
8193
  productType = None
7692
8194
  productType, params = self.handle_product_type_and_params(market, params)
7693
- request = {
8195
+ request: dict = {
7694
8196
  'symbol': market['id'],
7695
8197
  'productType': productType,
7696
8198
  }
@@ -7715,13 +8217,15 @@ class bitget(Exchange, ImplicitAPI):
7715
8217
  # }
7716
8218
  #
7717
8219
  data = self.safe_value(response, 'data', {})
7718
- order = self.safe_value(data, 'successList', [])
8220
+ order = self.safe_list(data, 'successList', [])
7719
8221
  return self.parse_order(order[0], market)
7720
8222
 
7721
8223
  def close_all_positions(self, params={}) -> List[Position]:
7722
8224
  """
7723
8225
  closes all open positions for a market type
7724
- :see: https://www.bitget.com/api-doc/contract/trade/Flash-Close-Position
8226
+
8227
+ https://www.bitget.com/api-doc/contract/trade/Flash-Close-Position
8228
+
7725
8229
  :param dict [params]: extra parameters specific to the exchange API endpoint
7726
8230
  :param str [params.productType]: 'USDT-FUTURES', 'USDC-FUTURES', 'COIN-FUTURES', 'SUSDT-FUTURES', 'SUSDC-FUTURES' or 'SCOIN-FUTURES'
7727
8231
  :returns dict[]: A list of `position structures <https://docs.ccxt.com/#/?id=position-structure>`
@@ -7729,7 +8233,7 @@ class bitget(Exchange, ImplicitAPI):
7729
8233
  self.load_markets()
7730
8234
  productType = None
7731
8235
  productType, params = self.handle_product_type_and_params(None, params)
7732
- request = {
8236
+ request: dict = {
7733
8237
  'productType': productType,
7734
8238
  }
7735
8239
  response = self.privateMixPostV2MixOrderClosePositions(self.extend(request, params))
@@ -7751,13 +8255,15 @@ class bitget(Exchange, ImplicitAPI):
7751
8255
  # }
7752
8256
  #
7753
8257
  data = self.safe_value(response, 'data', {})
7754
- orderInfo = self.safe_value(data, 'successList', [])
8258
+ orderInfo = self.safe_list(data, 'successList', [])
7755
8259
  return self.parse_positions(orderInfo, None, params)
7756
8260
 
7757
8261
  def fetch_margin_mode(self, symbol: str, params={}) -> MarginMode:
7758
8262
  """
7759
8263
  fetches the margin mode of a trading pair
7760
- :see: https://www.bitget.com/api-doc/contract/account/Get-Single-Account
8264
+
8265
+ https://www.bitget.com/api-doc/contract/account/Get-Single-Account
8266
+
7761
8267
  :param str symbol: unified symbol of the market to fetch the margin mode for
7762
8268
  :param dict [params]: extra parameters specific to the exchange API endpoint
7763
8269
  :returns dict: a `margin mode structure <https://docs.ccxt.com/#/?id=margin-mode-structure>`
@@ -7772,7 +8278,7 @@ class bitget(Exchange, ImplicitAPI):
7772
8278
  market = self.market(symbol)
7773
8279
  productType = None
7774
8280
  productType, params = self.handle_product_type_and_params(market, params)
7775
- request = {
8281
+ request: dict = {
7776
8282
  'symbol': market['id'],
7777
8283
  'marginCoin': market['settleId'],
7778
8284
  'productType': productType,
@@ -7809,7 +8315,7 @@ class bitget(Exchange, ImplicitAPI):
7809
8315
  data = self.safe_dict(response, 'data', {})
7810
8316
  return self.parse_margin_mode(data, market)
7811
8317
 
7812
- def parse_margin_mode(self, marginMode, market=None) -> MarginMode:
8318
+ def parse_margin_mode(self, marginMode: dict, market=None) -> MarginMode:
7813
8319
  marginType = self.safe_string(marginMode, 'marginMode')
7814
8320
  marginType = 'cross' if (marginType == 'crossed') else marginType
7815
8321
  return {
@@ -7818,12 +8324,455 @@ class bitget(Exchange, ImplicitAPI):
7818
8324
  'marginMode': marginType,
7819
8325
  }
7820
8326
 
7821
- def handle_errors(self, code, reason, url, method, headers, body, response, requestHeaders, requestBody):
8327
+ def fetch_positions_history(self, symbols: Strings = None, since: Int = None, limit: Int = None, params={}) -> List[Position]:
8328
+ """
8329
+ fetches historical positions
8330
+
8331
+ https://www.bitget.com/api-doc/contract/position/Get-History-Position
8332
+
8333
+ :param str[] [symbols]: unified contract symbols
8334
+ :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
8335
+ :param int [limit]: the maximum amount of records to fetch, default=20, max=100
8336
+ :param dict params: extra parameters specific to the exchange api endpoint
8337
+ :param int [params.until]: timestamp in ms of the latest position to fetch, max range for params["until"] - since is 3 months
8338
+
8339
+ EXCHANGE SPECIFIC PARAMETERS
8340
+ :param str [params.productType]: USDT-FUTURES(default), COIN-FUTURES, USDC-FUTURES, SUSDT-FUTURES, SCOIN-FUTURES, or SUSDC-FUTURES
8341
+ :returns dict[]: a list of `position structures <https://docs.ccxt.com/#/?id=position-structure>`
8342
+ """
8343
+ self.load_markets()
8344
+ until = self.safe_integer(params, 'until')
8345
+ params = self.omit(params, 'until')
8346
+ request: dict = {}
8347
+ if symbols is not None:
8348
+ symbolsLength = len(symbols)
8349
+ if symbolsLength > 0:
8350
+ market = self.market(symbols[0])
8351
+ request['symbol'] = market['id']
8352
+ if since is not None:
8353
+ request['startTime'] = since
8354
+ if limit is not None:
8355
+ request['limit'] = limit
8356
+ if until is not None:
8357
+ request['endTime'] = until
8358
+ response = self.privateMixGetV2MixPositionHistoryPosition(self.extend(request, params))
8359
+ #
8360
+ # {
8361
+ # code: '00000',
8362
+ # msg: 'success',
8363
+ # requestTime: '1712794148791',
8364
+ # data: {
8365
+ # list: [
8366
+ # {
8367
+ # symbol: 'XRPUSDT',
8368
+ # marginCoin: 'USDT',
8369
+ # holdSide: 'long',
8370
+ # openAvgPrice: '0.64967',
8371
+ # closeAvgPrice: '0.58799',
8372
+ # marginMode: 'isolated',
8373
+ # openTotalPos: '10',
8374
+ # closeTotalPos: '10',
8375
+ # pnl: '-0.62976205',
8376
+ # netProfit: '-0.65356802',
8377
+ # totalFunding: '-0.01638',
8378
+ # openFee: '-0.00389802',
8379
+ # closeFee: '-0.00352794',
8380
+ # ctime: '1709590322199',
8381
+ # utime: '1709667583395'
8382
+ # },
8383
+ # ...
8384
+ # ]
8385
+ # }
8386
+ # }
8387
+ #
8388
+ data = self.safe_dict(response, 'data')
8389
+ responseList = self.safe_list(data, 'list')
8390
+ positions = self.parse_positions(responseList, symbols, params)
8391
+ return self.filter_by_since_limit(positions, since, limit)
8392
+
8393
+ def fetch_convert_quote(self, fromCode: str, toCode: str, amount: Num = None, params={}) -> Conversion:
8394
+ """
8395
+ fetch a quote for converting from one currency to another
8396
+
8397
+ https://www.bitget.com/api-doc/common/convert/Get-Quoted-Price
8398
+
8399
+ :param str fromCode: the currency that you want to sell and convert from
8400
+ :param str toCode: the currency that you want to buy and convert into
8401
+ :param float [amount]: how much you want to trade in units of the from currency
8402
+ :param dict [params]: extra parameters specific to the exchange API endpoint
8403
+ :returns dict: a `conversion structure <https://docs.ccxt.com/#/?id=conversion-structure>`
8404
+ """
8405
+ self.load_markets()
8406
+ request: dict = {
8407
+ 'fromCoin': fromCode,
8408
+ 'toCoin': toCode,
8409
+ 'fromCoinSize': self.number_to_string(amount),
8410
+ }
8411
+ response = self.privateConvertGetV2ConvertQuotedPrice(self.extend(request, params))
8412
+ #
8413
+ # {
8414
+ # "code": "00000",
8415
+ # "msg": "success",
8416
+ # "requestTime": 1712121940158,
8417
+ # "data": {
8418
+ # "fromCoin": "USDT",
8419
+ # "fromCoinSize": "5",
8420
+ # "cnvtPrice": "0.9993007892377704",
8421
+ # "toCoin": "USDC",
8422
+ # "toCoinSize": "4.99650394",
8423
+ # "traceId": "1159288930228187140",
8424
+ # "fee": "0"
8425
+ # }
8426
+ # }
8427
+ #
8428
+ data = self.safe_dict(response, 'data', {})
8429
+ fromCurrencyId = self.safe_string(data, 'fromCoin', fromCode)
8430
+ fromCurrency = self.currency(fromCurrencyId)
8431
+ toCurrencyId = self.safe_string(data, 'toCoin', toCode)
8432
+ toCurrency = self.currency(toCurrencyId)
8433
+ return self.parse_conversion(data, fromCurrency, toCurrency)
8434
+
8435
+ def create_convert_trade(self, id: str, fromCode: str, toCode: str, amount: Num = None, params={}) -> Conversion:
8436
+ """
8437
+ convert from one currency to another
8438
+
8439
+ https://www.bitget.com/api-doc/common/convert/Trade
8440
+
8441
+ :param str id: the id of the trade that you want to make
8442
+ :param str fromCode: the currency that you want to sell and convert from
8443
+ :param str toCode: the currency that you want to buy and convert into
8444
+ :param float amount: how much you want to trade in units of the from currency
8445
+ :param dict [params]: extra parameters specific to the exchange API endpoint
8446
+ :param str params['price']: the price of the conversion, obtained from fetchConvertQuote()
8447
+ :param str params['toAmount']: the amount you want to trade in units of the toCurrency, obtained from fetchConvertQuote()
8448
+ :returns dict: a `conversion structure <https://docs.ccxt.com/#/?id=conversion-structure>`
8449
+ """
8450
+ self.load_markets()
8451
+ price = self.safe_string_2(params, 'price', 'cnvtPrice')
8452
+ if price is None:
8453
+ raise ArgumentsRequired(self.id + ' createConvertTrade() requires a price parameter')
8454
+ toAmount = self.safe_string_2(params, 'toAmount', 'toCoinSize')
8455
+ if toAmount is None:
8456
+ raise ArgumentsRequired(self.id + ' createConvertTrade() requires a toAmount parameter')
8457
+ params = self.omit(params, ['price', 'toAmount'])
8458
+ request: dict = {
8459
+ 'traceId': id,
8460
+ 'fromCoin': fromCode,
8461
+ 'toCoin': toCode,
8462
+ 'fromCoinSize': self.number_to_string(amount),
8463
+ 'toCoinSize': toAmount,
8464
+ 'cnvtPrice': price,
8465
+ }
8466
+ response = self.privateConvertPostV2ConvertTrade(self.extend(request, params))
8467
+ #
8468
+ # {
8469
+ # "code": "00000",
8470
+ # "msg": "success",
8471
+ # "requestTime": 1712123746203,
8472
+ # "data": {
8473
+ # "cnvtPrice": "0.99940076",
8474
+ # "toCoin": "USDC",
8475
+ # "toCoinSize": "4.99700379",
8476
+ # "ts": "1712123746217"
8477
+ # }
8478
+ # }
8479
+ #
8480
+ data = self.safe_dict(response, 'data', {})
8481
+ toCurrencyId = self.safe_string(data, 'toCoin', toCode)
8482
+ toCurrency = self.currency(toCurrencyId)
8483
+ return self.parse_conversion(data, None, toCurrency)
8484
+
8485
+ def fetch_convert_trade_history(self, code: Str = None, since: Int = None, limit: Int = None, params={}) -> List[Conversion]:
8486
+ """
8487
+ fetch the users history of conversion trades
8488
+
8489
+ https://www.bitget.com/api-doc/common/convert/Get-Convert-Record
8490
+
8491
+ :param str [code]: the unified currency code
8492
+ :param int [since]: the earliest time in ms to fetch conversions for
8493
+ :param int [limit]: the maximum number of conversion structures to retrieve
8494
+ :param dict [params]: extra parameters specific to the exchange API endpoint
8495
+ :returns dict[]: a list of `conversion structures <https://docs.ccxt.com/#/?id=conversion-structure>`
8496
+ """
8497
+ self.load_markets()
8498
+ request: dict = {}
8499
+ msInDay = 86400000
8500
+ now = self.milliseconds()
8501
+ if since is not None:
8502
+ request['startTime'] = since
8503
+ else:
8504
+ request['startTime'] = now - msInDay
8505
+ endTime = self.safe_string_2(params, 'endTime', 'until')
8506
+ if endTime is not None:
8507
+ request['endTime'] = endTime
8508
+ else:
8509
+ request['endTime'] = now
8510
+ if limit is not None:
8511
+ request['limit'] = limit
8512
+ params = self.omit(params, 'until')
8513
+ response = self.privateConvertGetV2ConvertConvertRecord(self.extend(request, params))
8514
+ #
8515
+ # {
8516
+ # "code": "00000",
8517
+ # "msg": "success",
8518
+ # "requestTime": 1712124371799,
8519
+ # "data": {
8520
+ # "dataList": [
8521
+ # {
8522
+ # "id": "1159296505255219205",
8523
+ # "fromCoin": "USDT",
8524
+ # "fromCoinSize": "5",
8525
+ # "cnvtPrice": "0.99940076",
8526
+ # "toCoin": "USDC",
8527
+ # "toCoinSize": "4.99700379",
8528
+ # "ts": "1712123746217",
8529
+ # "fee": "0"
8530
+ # }
8531
+ # ],
8532
+ # "endId": "1159296505255219205"
8533
+ # }
8534
+ # }
8535
+ #
8536
+ data = self.safe_dict(response, 'data', {})
8537
+ dataList = self.safe_list(data, 'dataList', [])
8538
+ return self.parse_conversions(dataList, code, 'fromCoin', 'toCoin', since, limit)
8539
+
8540
+ def parse_conversion(self, conversion: dict, fromCurrency: Currency = None, toCurrency: Currency = None) -> Conversion:
8541
+ #
8542
+ # fetchConvertQuote
8543
+ #
8544
+ # {
8545
+ # "fromCoin": "USDT",
8546
+ # "fromCoinSize": "5",
8547
+ # "cnvtPrice": "0.9993007892377704",
8548
+ # "toCoin": "USDC",
8549
+ # "toCoinSize": "4.99650394",
8550
+ # "traceId": "1159288930228187140",
8551
+ # "fee": "0"
8552
+ # }
8553
+ #
8554
+ # createConvertTrade
8555
+ #
8556
+ # {
8557
+ # "cnvtPrice": "0.99940076",
8558
+ # "toCoin": "USDC",
8559
+ # "toCoinSize": "4.99700379",
8560
+ # "ts": "1712123746217"
8561
+ # }
8562
+ #
8563
+ # fetchConvertTradeHistory
8564
+ #
8565
+ # {
8566
+ # "id": "1159296505255219205",
8567
+ # "fromCoin": "USDT",
8568
+ # "fromCoinSize": "5",
8569
+ # "cnvtPrice": "0.99940076",
8570
+ # "toCoin": "USDC",
8571
+ # "toCoinSize": "4.99700379",
8572
+ # "ts": "1712123746217",
8573
+ # "fee": "0"
8574
+ # }
8575
+ #
8576
+ timestamp = self.safe_integer(conversion, 'ts')
8577
+ fromCoin = self.safe_string(conversion, 'fromCoin')
8578
+ fromCode = self.safe_currency_code(fromCoin, fromCurrency)
8579
+ to = self.safe_string(conversion, 'toCoin')
8580
+ toCode = self.safe_currency_code(to, toCurrency)
8581
+ return {
8582
+ 'info': conversion,
8583
+ 'timestamp': timestamp,
8584
+ 'datetime': self.iso8601(timestamp),
8585
+ 'id': self.safe_string_2(conversion, 'id', 'traceId'),
8586
+ 'fromCurrency': fromCode,
8587
+ 'fromAmount': self.safe_number(conversion, 'fromCoinSize'),
8588
+ 'toCurrency': toCode,
8589
+ 'toAmount': self.safe_number(conversion, 'toCoinSize'),
8590
+ 'price': self.safe_number(conversion, 'cnvtPrice'),
8591
+ 'fee': self.safe_number(conversion, 'fee'),
8592
+ }
8593
+
8594
+ def fetch_convert_currencies(self, params={}) -> Currencies:
8595
+ """
8596
+ fetches all available currencies that can be converted
8597
+
8598
+ https://www.bitget.com/api-doc/common/convert/Get-Convert-Currencies
8599
+
8600
+ :param dict [params]: extra parameters specific to the exchange API endpoint
8601
+ :returns dict: an associative dictionary of currencies
8602
+ """
8603
+ self.load_markets()
8604
+ response = self.privateConvertGetV2ConvertCurrencies(params)
8605
+ #
8606
+ # {
8607
+ # "code": "00000",
8608
+ # "msg": "success",
8609
+ # "requestTime": 1712121755897,
8610
+ # "data": [
8611
+ # {
8612
+ # "coin": "BTC",
8613
+ # "available": "0.00009850",
8614
+ # "maxAmount": "0.756266",
8615
+ # "minAmount": "0.00001"
8616
+ # },
8617
+ # ]
8618
+ # }
8619
+ #
8620
+ result: dict = {}
8621
+ data = self.safe_list(response, 'data', [])
8622
+ for i in range(0, len(data)):
8623
+ entry = data[i]
8624
+ id = self.safe_string(entry, 'coin')
8625
+ code = self.safe_currency_code(id)
8626
+ result[code] = {
8627
+ 'info': entry,
8628
+ 'id': id,
8629
+ 'code': code,
8630
+ 'networks': None,
8631
+ 'type': None,
8632
+ 'name': None,
8633
+ 'active': None,
8634
+ 'deposit': None,
8635
+ 'withdraw': self.safe_number(entry, 'available'),
8636
+ 'fee': None,
8637
+ 'precision': None,
8638
+ 'limits': {
8639
+ 'amount': {
8640
+ 'min': self.safe_number(entry, 'minAmount'),
8641
+ 'max': self.safe_number(entry, 'maxAmount'),
8642
+ },
8643
+ 'withdraw': {
8644
+ 'min': None,
8645
+ 'max': None,
8646
+ },
8647
+ 'deposit': {
8648
+ 'min': None,
8649
+ 'max': None,
8650
+ },
8651
+ },
8652
+ 'created': None,
8653
+ }
8654
+ return result
8655
+
8656
+ def fetch_funding_interval(self, symbol: str, params={}) -> FundingRate:
8657
+ """
8658
+ fetch the current funding rate interval
8659
+
8660
+ https://www.bitget.com/api-doc/contract/market/Get-Symbol-Next-Funding-Time
8661
+
8662
+ :param str symbol: unified market symbol
8663
+ :param dict [params]: extra parameters specific to the exchange API endpoint
8664
+ :returns dict: a `funding rate structure <https://docs.ccxt.com/#/?id=funding-rate-structure>`
8665
+ """
8666
+ self.load_markets()
8667
+ sandboxMode = self.safe_bool(self.options, 'sandboxMode', False)
8668
+ market = None
8669
+ if sandboxMode:
8670
+ sandboxSymbol = self.convert_symbol_for_sandbox(symbol)
8671
+ market = self.market(sandboxSymbol)
8672
+ else:
8673
+ market = self.market(symbol)
8674
+ productType = None
8675
+ productType, params = self.handle_product_type_and_params(market, params)
8676
+ request: dict = {
8677
+ 'symbol': market['id'],
8678
+ 'productType': productType,
8679
+ }
8680
+ response = self.publicMixGetV2MixMarketFundingTime(self.extend(request, params))
8681
+ #
8682
+ # {
8683
+ # "code": "00000",
8684
+ # "msg": "success",
8685
+ # "requestTime": 1727930153888,
8686
+ # "data": [
8687
+ # {
8688
+ # "symbol": "BTCUSDT",
8689
+ # "nextFundingTime": "1727942400000",
8690
+ # "ratePeriod": "8"
8691
+ # }
8692
+ # ]
8693
+ # }
8694
+ #
8695
+ data = self.safe_list(response, 'data', [])
8696
+ first = self.safe_dict(data, 0, {})
8697
+ return self.parse_funding_rate(first, market)
8698
+
8699
+ def fetch_long_short_ratio_history(self, symbol: Str = None, timeframe: Str = None, since: Int = None, limit: Int = None, params={}) -> List[LongShortRatio]:
8700
+ """
8701
+ fetches the long short ratio history for a unified market symbol
8702
+
8703
+ https://www.bitget.com/api-doc/common/apidata/Margin-Ls-Ratio
8704
+ https://www.bitget.com/api-doc/common/apidata/Account-Long-Short
8705
+
8706
+ :param str symbol: unified symbol of the market to fetch the long short ratio for
8707
+ :param str [timeframe]: the period for the ratio
8708
+ :param int [since]: the earliest time in ms to fetch ratios for
8709
+ :param int [limit]: the maximum number of long short ratio structures to retrieve
8710
+ :param dict [params]: extra parameters specific to the exchange API endpoint
8711
+ :returns dict[]: an array of `long short ratio structures <https://docs.ccxt.com/#/?id=long-short-ratio-structure>`
8712
+ """
8713
+ self.load_markets()
8714
+ market = self.market(symbol)
8715
+ request: dict = {
8716
+ 'symbol': market['id'],
8717
+ }
8718
+ if timeframe is not None:
8719
+ request['period'] = timeframe
8720
+ response = None
8721
+ if market['swap'] or market['future']:
8722
+ response = self.publicMixGetV2MixMarketAccountLongShort(self.extend(request, params))
8723
+ #
8724
+ # {
8725
+ # "code": "00000",
8726
+ # "msg": "success",
8727
+ # "requestTime": 1729321233281,
8728
+ # "data": [
8729
+ # {
8730
+ # "longAccountRatio": "0.58",
8731
+ # "shortAccountRatio": "0.42",
8732
+ # "longShortAccountRatio": "0.0138",
8733
+ # "ts": "1729312200000"
8734
+ # },
8735
+ # ]
8736
+ # }
8737
+ #
8738
+ else:
8739
+ response = self.publicMarginGetV2MarginMarketLongShortRatio(self.extend(request, params))
8740
+ #
8741
+ # {
8742
+ # "code": "00000",
8743
+ # "msg": "success",
8744
+ # "requestTime": 1729306974712,
8745
+ # "data": [
8746
+ # {
8747
+ # "longShortRatio": "40.66",
8748
+ # "ts": "1729306800000"
8749
+ # },
8750
+ # ]
8751
+ # }
8752
+ #
8753
+ data = self.safe_list(response, 'data', [])
8754
+ return self.parse_long_short_ratio_history(data, market)
8755
+
8756
+ def parse_long_short_ratio(self, info: dict, market: Market = None) -> LongShortRatio:
8757
+ marketId = self.safe_string(info, 'symbol')
8758
+ timestamp = self.safe_integer_omit_zero(info, 'ts')
8759
+ return {
8760
+ 'info': info,
8761
+ 'symbol': self.safe_symbol(marketId, market, None, 'contract'),
8762
+ 'timestamp': timestamp,
8763
+ 'datetime': self.iso8601(timestamp),
8764
+ 'timeframe': None,
8765
+ 'longShortRatio': self.safe_number_2(info, 'longShortRatio', 'longShortAccountRatio'),
8766
+ }
8767
+
8768
+ def handle_errors(self, code: int, reason: str, url: str, method: str, headers: dict, body: str, response, requestHeaders, requestBody):
7822
8769
  if not response:
7823
8770
  return None # fallback to default error handler
7824
8771
  #
7825
8772
  # spot
7826
8773
  #
8774
+ # {"code":"00000","msg":"success","requestTime":1713294492511,"data":[...]}"
8775
+ #
7827
8776
  # {"status":"fail","err_code":"01001","err_msg":"系统异常,请稍后重试"}
7828
8777
  # {"status":"error","ts":1595594160149,"err_code":"invalid-parameter","err_msg":"invalid size, valid range: [1,2000]"}
7829
8778
  # {"status":"error","ts":1595684716042,"err_code":"invalid-parameter","err_msg":"illegal sign invalid"}
@@ -7845,13 +8794,13 @@ class bitget(Exchange, ImplicitAPI):
7845
8794
  # {"code":"40108","msg":"","requestTime":1595885064600,"data":null}
7846
8795
  # {"order_id":"513468410013679613","client_oid":null,"symbol":"ethusd","result":false,"err_code":"order_no_exist_error","err_msg":"订单不存在!"}
7847
8796
  #
7848
- message = self.safe_string(response, 'err_msg')
7849
- errorCode = self.safe_string_2(response, 'code', 'err_code')
8797
+ message = self.safe_string_2(response, 'err_msg', 'msg')
7850
8798
  feedback = self.id + ' ' + body
7851
- nonEmptyMessage = ((message is not None) and (message != ''))
8799
+ nonEmptyMessage = ((message is not None) and (message != '') and (message != 'success'))
7852
8800
  if nonEmptyMessage:
7853
8801
  self.throw_exactly_matched_exception(self.exceptions['exact'], message, feedback)
7854
8802
  self.throw_broadly_matched_exception(self.exceptions['broad'], message, feedback)
8803
+ errorCode = self.safe_string_2(response, 'code', 'err_code')
7855
8804
  nonZeroErrorCode = (errorCode is not None) and (errorCode != '00000')
7856
8805
  if nonZeroErrorCode:
7857
8806
  self.throw_exactly_matched_exception(self.exceptions['exact'], errorCode, feedback)
@@ -7859,6 +8808,9 @@ class bitget(Exchange, ImplicitAPI):
7859
8808
  raise ExchangeError(feedback) # unknown message
7860
8809
  return None
7861
8810
 
8811
+ def nonce(self):
8812
+ return self.milliseconds() - self.options['timeDifference']
8813
+
7862
8814
  def sign(self, path, api=[], method='GET', params={}, headers=None, body=None):
7863
8815
  signed = api[0] == 'private'
7864
8816
  endpoint = api[1]
@@ -7874,7 +8826,7 @@ class bitget(Exchange, ImplicitAPI):
7874
8826
  url = url + '?' + self.urlencode(query)
7875
8827
  if signed:
7876
8828
  self.check_required_credentials()
7877
- timestamp = str(self.milliseconds())
8829
+ timestamp = str(self.nonce())
7878
8830
  auth = timestamp + method + payload
7879
8831
  if method == 'POST':
7880
8832
  body = self.json(params)