akquant 0.3.2__tar.gz → 0.3.4__tar.gz

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 (585) hide show
  1. {akquant-0.3.2 → akquant-0.3.4}/Cargo.lock +1 -1
  2. {akquant-0.3.2 → akquant-0.3.4}/Cargo.toml +1 -1
  3. {akquant-0.3.2 → akquant-0.3.4}/PKG-INFO +1 -1
  4. {akquant-0.3.2 → akquant-0.3.4}/docs/en/guide/analysis.md +1 -1
  5. {akquant-0.3.2 → akquant-0.3.4}/docs/en/start/quickstart.md +1 -1
  6. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/guide/analysis.md +1 -1
  7. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/start/quickstart.md +1 -1
  8. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/textbook/01_foundations.md +1 -1
  9. {akquant-0.3.2 → akquant-0.3.4}/pyproject.toml +1 -1
  10. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/__init__.py +1 -1
  11. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/akquant.pyi +3 -0
  12. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/backtest/engine.py +31 -8
  13. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/config.py +9 -0
  14. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/execution/base.py +3 -0
  15. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/execution/sim.py +4 -0
  16. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/gateway/broker_execution.py +4 -0
  17. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/strategy.py +8 -0
  18. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/strategy_trading_api.py +11 -0
  19. {akquant-0.3.2 → akquant-0.3.4}/src/analysis/python.rs +3 -1
  20. {akquant-0.3.2 → akquant-0.3.4}/src/context.rs +52 -0
  21. {akquant-0.3.2 → akquant-0.3.4}/src/engine/core.rs +3 -0
  22. {akquant-0.3.2 → akquant-0.3.4}/src/engine/mod.rs +1 -0
  23. {akquant-0.3.2 → akquant-0.3.4}/src/execution/simulated.rs +45 -15
  24. {akquant-0.3.2 → akquant-0.3.4}/src/execution/stock.rs +1 -0
  25. {akquant-0.3.2 → akquant-0.3.4}/src/market/china.rs +22 -50
  26. {akquant-0.3.2 → akquant-0.3.4}/src/market/fund.rs +3 -3
  27. {akquant-0.3.2 → akquant-0.3.4}/src/market/stock.rs +7 -7
  28. {akquant-0.3.2 → akquant-0.3.4}/src/model/instrument.rs +26 -1
  29. {akquant-0.3.2 → akquant-0.3.4}/src/pipeline/stages/channel.rs +25 -0
  30. {akquant-0.3.2 → akquant-0.3.4}/src/pipeline/stages/mod.rs +1 -0
  31. {akquant-0.3.2 → akquant-0.3.4}/src/portfolio.rs +1 -0
  32. {akquant-0.3.2 → akquant-0.3.4}/src/risk/common.rs +11 -3
  33. {akquant-0.3.2 → akquant-0.3.4}/src/risk/mod.rs +1 -0
  34. {akquant-0.3.2 → akquant-0.3.4}/src/risk/portfolio.rs +1 -0
  35. {akquant-0.3.2 → akquant-0.3.4}/src/risk/stock.rs +3 -0
  36. {akquant-0.3.2 → akquant-0.3.4}/src/settlement/expiry.rs +1 -0
  37. {akquant-0.3.2 → akquant-0.3.4}/src/settlement/manager.rs +1 -0
  38. {akquant-0.3.2/tests/golden/current → akquant-0.3.4/tests/golden/baselines}/futures_margin/metrics.json +2 -2
  39. {akquant-0.3.2/tests/golden/current → akquant-0.3.4/tests/golden/baselines}/futures_margin/orders.parquet +0 -0
  40. {akquant-0.3.2 → akquant-0.3.4}/tests/golden/baselines/option_basic/metrics.json +2 -2
  41. {akquant-0.3.2/tests/golden/current → akquant-0.3.4/tests/golden/baselines}/option_basic/orders.parquet +0 -0
  42. {akquant-0.3.2/tests/golden/current → akquant-0.3.4/tests/golden/baselines}/stock_t1/metrics.json +2 -2
  43. {akquant-0.3.2/tests/golden/current → akquant-0.3.4/tests/golden/baselines}/stock_t1/orders.parquet +0 -0
  44. {akquant-0.3.2/tests/golden/baselines → akquant-0.3.4/tests/golden/current}/futures_margin/equity_curve.parquet +0 -0
  45. {akquant-0.3.2/tests/golden/baselines → akquant-0.3.4/tests/golden/current}/futures_margin/metrics.json +2 -2
  46. akquant-0.3.4/tests/golden/current/futures_margin/orders.parquet +0 -0
  47. {akquant-0.3.2/tests/golden/baselines → akquant-0.3.4/tests/golden/current}/option_basic/equity_curve.parquet +0 -0
  48. {akquant-0.3.2 → akquant-0.3.4}/tests/golden/current/option_basic/metrics.json +2 -2
  49. akquant-0.3.4/tests/golden/current/option_basic/orders.parquet +0 -0
  50. {akquant-0.3.2/tests/golden/baselines → akquant-0.3.4/tests/golden/current}/stock_t1/equity_curve.parquet +0 -0
  51. {akquant-0.3.2/tests/golden/baselines → akquant-0.3.4/tests/golden/current}/stock_t1/metrics.json +2 -2
  52. akquant-0.3.4/tests/golden/current/stock_t1/orders.parquet +0 -0
  53. {akquant-0.3.2/tests/golden/baselines → akquant-0.3.4/tests/golden/current}/stock_t1/trades.parquet +0 -0
  54. {akquant-0.3.2 → akquant-0.3.4}/tests/test_engine.py +275 -0
  55. akquant-0.3.2/tests/golden/baselines/futures_margin/orders.parquet +0 -0
  56. akquant-0.3.2/tests/golden/baselines/option_basic/orders.parquet +0 -0
  57. akquant-0.3.2/tests/golden/baselines/stock_t1/orders.parquet +0 -0
  58. {akquant-0.3.2 → akquant-0.3.4}/.github/ISSUE_TEMPLATE/bug_report.yml +0 -0
  59. {akquant-0.3.2 → akquant-0.3.4}/.github/ISSUE_TEMPLATE/config.yml +0 -0
  60. {akquant-0.3.2 → akquant-0.3.4}/.github/ISSUE_TEMPLATE/feature_request.yml +0 -0
  61. {akquant-0.3.2 → akquant-0.3.4}/.github/workflows/deploy-docs.yml +0 -0
  62. {akquant-0.3.2 → akquant-0.3.4}/.github/workflows/docs-quality.yml +0 -0
  63. {akquant-0.3.2 → akquant-0.3.4}/.github/workflows/release.yml +0 -0
  64. {akquant-0.3.2 → akquant-0.3.4}/.gitignore +0 -0
  65. {akquant-0.3.2 → akquant-0.3.4}/.pre-commit-config.yaml +0 -0
  66. {akquant-0.3.2 → akquant-0.3.4}/CHANGELOG.md +0 -0
  67. {akquant-0.3.2 → akquant-0.3.4}/CODE_OF_CONDUCT.md +0 -0
  68. {akquant-0.3.2 → akquant-0.3.4}/CONTRIBUTING.md +0 -0
  69. {akquant-0.3.2 → akquant-0.3.4}/LICENSE +0 -0
  70. {akquant-0.3.2 → akquant-0.3.4}/README.md +0 -0
  71. {akquant-0.3.2 → akquant-0.3.4}/assets/dashboard_preview.png +0 -0
  72. {akquant-0.3.2 → akquant-0.3.4}/assets/logo.svg +0 -0
  73. {akquant-0.3.2 → akquant-0.3.4}/assets/social_preview.png +0 -0
  74. {akquant-0.3.2 → akquant-0.3.4}/docs/CNAME +0 -0
  75. {akquant-0.3.2 → akquant-0.3.4}/docs/assets/akquant-icon.svg +0 -0
  76. {akquant-0.3.2 → akquant-0.3.4}/docs/assets/akquant-logo.svg +0 -0
  77. {akquant-0.3.2 → akquant-0.3.4}/docs/assets/reports/akquant_report.html +0 -0
  78. {akquant-0.3.2 → akquant-0.3.4}/docs/en/advanced/analyzer_plugin_spec.md +0 -0
  79. {akquant-0.3.2 → akquant-0.3.4}/docs/en/advanced/broker_capability_matrix.md +0 -0
  80. {akquant-0.3.2 → akquant-0.3.4}/docs/en/advanced/custom_broker_production_checklist.md +0 -0
  81. {akquant-0.3.2 → akquant-0.3.4}/docs/en/advanced/custom_broker_registry.md +0 -0
  82. {akquant-0.3.2 → akquant-0.3.4}/docs/en/advanced/data_feed_adapter_spec.md +0 -0
  83. {akquant-0.3.2 → akquant-0.3.4}/docs/en/advanced/live_functional_quickstart.md +0 -0
  84. {akquant-0.3.2 → akquant-0.3.4}/docs/en/advanced/llm.md +0 -0
  85. {akquant-0.3.2 → akquant-0.3.4}/docs/en/advanced/ml.md +0 -0
  86. {akquant-0.3.2 → akquant-0.3.4}/docs/en/advanced/multi_strategy_guide.md +0 -0
  87. {akquant-0.3.2 → akquant-0.3.4}/docs/en/advanced/multi_timeframe_feed_api.md +0 -0
  88. {akquant-0.3.2 → akquant-0.3.4}/docs/en/advanced/runtime_config.md +0 -0
  89. {akquant-0.3.2 → akquant-0.3.4}/docs/en/advanced/strategy_style_decision.md +0 -0
  90. {akquant-0.3.2 → akquant-0.3.4}/docs/en/advanced/timezone.md +0 -0
  91. {akquant-0.3.2 → akquant-0.3.4}/docs/en/advanced/warm_start.md +0 -0
  92. {akquant-0.3.2 → akquant-0.3.4}/docs/en/guide/cross_section_checklist.md +0 -0
  93. {akquant-0.3.2 → akquant-0.3.4}/docs/en/guide/custom_indicator.md +0 -0
  94. {akquant-0.3.2 → akquant-0.3.4}/docs/en/guide/data.md +0 -0
  95. {akquant-0.3.2 → akquant-0.3.4}/docs/en/guide/examples.md +0 -0
  96. {akquant-0.3.2 → akquant-0.3.4}/docs/en/guide/factor.md +0 -0
  97. {akquant-0.3.2 → akquant-0.3.4}/docs/en/guide/indicator_scenario_quickref.md +0 -0
  98. {akquant-0.3.2 → akquant-0.3.4}/docs/en/guide/optimization.md +0 -0
  99. {akquant-0.3.2 → akquant-0.3.4}/docs/en/guide/python_basics.md +0 -0
  100. {akquant-0.3.2 → akquant-0.3.4}/docs/en/guide/quant_basics.md +0 -0
  101. {akquant-0.3.2 → akquant-0.3.4}/docs/en/guide/rust_indicator_reference.md +0 -0
  102. {akquant-0.3.2 → akquant-0.3.4}/docs/en/guide/strategy.md +0 -0
  103. {akquant-0.3.2 → akquant-0.3.4}/docs/en/guide/talib_indicator_playbook.md +0 -0
  104. {akquant-0.3.2 → akquant-0.3.4}/docs/en/guide/testing.md +0 -0
  105. {akquant-0.3.2 → akquant-0.3.4}/docs/en/guide/visualization.md +0 -0
  106. {akquant-0.3.2 → akquant-0.3.4}/docs/en/index.md +0 -0
  107. {akquant-0.3.2 → akquant-0.3.4}/docs/en/meta/architecture.md +0 -0
  108. {akquant-0.3.2 → akquant-0.3.4}/docs/en/meta/internals.md +0 -0
  109. {akquant-0.3.2 → akquant-0.3.4}/docs/en/reference/api.md +0 -0
  110. {akquant-0.3.2 → akquant-0.3.4}/docs/en/start/first_strategy.md +0 -0
  111. {akquant-0.3.2 → akquant-0.3.4}/docs/en/start/installation.md +0 -0
  112. {akquant-0.3.2 → akquant-0.3.4}/docs/en/start/setup_guide.md +0 -0
  113. {akquant-0.3.2 → akquant-0.3.4}/docs/en/textbook/01_foundations.md +0 -0
  114. {akquant-0.3.2 → akquant-0.3.4}/docs/en/textbook/02_programming.md +0 -0
  115. {akquant-0.3.2 → akquant-0.3.4}/docs/en/textbook/03_data.md +0 -0
  116. {akquant-0.3.2 → akquant-0.3.4}/docs/en/textbook/04_backtest_engine.md +0 -0
  117. {akquant-0.3.2 → akquant-0.3.4}/docs/en/textbook/05_strategy.md +0 -0
  118. {akquant-0.3.2 → akquant-0.3.4}/docs/en/textbook/06_stock_a.md +0 -0
  119. {akquant-0.3.2 → akquant-0.3.4}/docs/en/textbook/07_futures.md +0 -0
  120. {akquant-0.3.2 → akquant-0.3.4}/docs/en/textbook/08_options.md +0 -0
  121. {akquant-0.3.2 → akquant-0.3.4}/docs/en/textbook/09_funds.md +0 -0
  122. {akquant-0.3.2 → akquant-0.3.4}/docs/en/textbook/10_analysis.md +0 -0
  123. {akquant-0.3.2 → akquant-0.3.4}/docs/en/textbook/11_optimization.md +0 -0
  124. {akquant-0.3.2 → akquant-0.3.4}/docs/en/textbook/12_ml.md +0 -0
  125. {akquant-0.3.2 → akquant-0.3.4}/docs/en/textbook/13_visualization.md +0 -0
  126. {akquant-0.3.2 → akquant-0.3.4}/docs/en/textbook/14_factor.md +0 -0
  127. {akquant-0.3.2 → akquant-0.3.4}/docs/en/textbook/15_live_trading.md +0 -0
  128. {akquant-0.3.2 → akquant-0.3.4}/docs/en/textbook/16_rust_indicators.md +0 -0
  129. {akquant-0.3.2 → akquant-0.3.4}/docs/en/textbook/index.md +0 -0
  130. {akquant-0.3.2 → akquant-0.3.4}/docs/javascripts/mathjax.js +0 -0
  131. {akquant-0.3.2 → akquant-0.3.4}/docs/javascripts/search-lang-filter.js +0 -0
  132. {akquant-0.3.2 → akquant-0.3.4}/docs/robots.txt +0 -0
  133. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/advanced/adding_a_broker.md +0 -0
  134. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/advanced/analyzer_plugin_spec.md +0 -0
  135. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/advanced/broker_capability_matrix.md +0 -0
  136. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/advanced/custom_broker_production_checklist.md +0 -0
  137. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/advanced/custom_broker_registry.md +0 -0
  138. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/advanced/data_feed_adapter_spec.md +0 -0
  139. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/advanced/live_functional_quickstart.md +0 -0
  140. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/advanced/llm.md +0 -0
  141. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/advanced/ml.md +0 -0
  142. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/advanced/multi_strategy_guide.md +0 -0
  143. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/advanced/multi_timeframe_feed_api.md +0 -0
  144. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/advanced/runtime_config.md +0 -0
  145. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/advanced/strategy_style_decision.md +0 -0
  146. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/advanced/timezone.md +0 -0
  147. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/advanced/warm_start.md +0 -0
  148. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/guide/cross_section_checklist.md +0 -0
  149. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/guide/custom_indicator.md +0 -0
  150. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/guide/data.md +0 -0
  151. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/guide/examples.md +0 -0
  152. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/guide/factor.md +0 -0
  153. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/guide/indicator_scenario_quickref.md +0 -0
  154. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/guide/optimization.md +0 -0
  155. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/guide/python_basics.md +0 -0
  156. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/guide/quant_basics.md +0 -0
  157. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/guide/rust_indicator_reference.md +0 -0
  158. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/guide/strategy.md +0 -0
  159. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/guide/talib_indicator_playbook.md +0 -0
  160. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/guide/testing.md +0 -0
  161. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/guide/visualization.md +0 -0
  162. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/index.md +0 -0
  163. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/meta/architecture.md +0 -0
  164. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/meta/internals.md +0 -0
  165. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/reference/api.md +0 -0
  166. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/start/first_strategy.md +0 -0
  167. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/start/installation.md +0 -0
  168. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/start/setup_guide.md +0 -0
  169. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/textbook/00_glossary.md +0 -0
  170. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/textbook/02_programming.md +0 -0
  171. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/textbook/03_data.md +0 -0
  172. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/textbook/04_backtest_engine.md +0 -0
  173. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/textbook/05_strategy.md +0 -0
  174. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/textbook/06_stock_a.md +0 -0
  175. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/textbook/07_futures.md +0 -0
  176. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/textbook/08_options.md +0 -0
  177. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/textbook/09_funds.md +0 -0
  178. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/textbook/10_analysis.md +0 -0
  179. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/textbook/11_optimization.md +0 -0
  180. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/textbook/12_ml.md +0 -0
  181. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/textbook/13_visualization.md +0 -0
  182. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/textbook/14_factor.md +0 -0
  183. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/textbook/15_live_trading.md +0 -0
  184. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/textbook/16_rust_indicators.md +0 -0
  185. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/textbook/ROADMAP.md +0 -0
  186. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/textbook/appendix_cite.md +0 -0
  187. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/textbook/appendix_pitfalls.md +0 -0
  188. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/textbook/appendix_setup.md +0 -0
  189. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/textbook/capstone.md +0 -0
  190. {akquant-0.3.2 → akquant-0.3.4}/docs/zh/textbook/index.md +0 -0
  191. {akquant-0.3.2 → akquant-0.3.4}/examples/01_quickstart.py +0 -0
  192. {akquant-0.3.2 → akquant-0.3.4}/examples/02_parameter_optimization.py +0 -0
  193. {akquant-0.3.2 → akquant-0.3.4}/examples/03_parameter_optimization_advanced.py +0 -0
  194. {akquant-0.3.2 → akquant-0.3.4}/examples/04_mixed_assets.py +0 -0
  195. {akquant-0.3.2 → akquant-0.3.4}/examples/05_live_trading_ctp.py +0 -0
  196. {akquant-0.3.2 → akquant-0.3.4}/examples/06_complex_orders.py +0 -0
  197. {akquant-0.3.2 → akquant-0.3.4}/examples/07_option_test.py +0 -0
  198. {akquant-0.3.2 → akquant-0.3.4}/examples/08_event_callbacks.py +0 -0
  199. {akquant-0.3.2 → akquant-0.3.4}/examples/09_ml_framework.py +0 -0
  200. {akquant-0.3.2 → akquant-0.3.4}/examples/10_ml_walk_forward.py +0 -0
  201. {akquant-0.3.2 → akquant-0.3.4}/examples/11_plot_visualization.py +0 -0
  202. {akquant-0.3.2 → akquant-0.3.4}/examples/12_wfo_integrated.py +0 -0
  203. {akquant-0.3.2 → akquant-0.3.4}/examples/13_quantstats_report.py +0 -0
  204. {akquant-0.3.2 → akquant-0.3.4}/examples/14_multi_frequency.py +0 -0
  205. {akquant-0.3.2 → akquant-0.3.4}/examples/15_plot_intraday.py +0 -0
  206. {akquant-0.3.2 → akquant-0.3.4}/examples/16_adj_returns_signal.py +0 -0
  207. {akquant-0.3.2 → akquant-0.3.4}/examples/17_readme_demo.py +0 -0
  208. {akquant-0.3.2 → akquant-0.3.4}/examples/18_benchmark_multisymbol.py +0 -0
  209. {akquant-0.3.2 → akquant-0.3.4}/examples/19_factor_expression.py +0 -0
  210. {akquant-0.3.2 → akquant-0.3.4}/examples/20_risk_management_demo.py +0 -0
  211. {akquant-0.3.2 → akquant-0.3.4}/examples/21_warm_start_demo.py +0 -0
  212. {akquant-0.3.2 → akquant-0.3.4}/examples/22_strategy_runtime_config_demo.py +0 -0
  213. {akquant-0.3.2 → akquant-0.3.4}/examples/23_functional_callbacks_demo.py +0 -0
  214. {akquant-0.3.2 → akquant-0.3.4}/examples/24_functional_tick_simulation_demo.py +0 -0
  215. {akquant-0.3.2 → akquant-0.3.4}/examples/25_streaming_backtest_demo.py +0 -0
  216. {akquant-0.3.2 → akquant-0.3.4}/examples/26_streaming_quickstart.py +0 -0
  217. {akquant-0.3.2 → akquant-0.3.4}/examples/27_streaming_monitoring_console.py +0 -0
  218. {akquant-0.3.2 → akquant-0.3.4}/examples/28_streaming_alerts_and_persist.py +0 -0
  219. {akquant-0.3.2 → akquant-0.3.4}/examples/29_streaming_event_report.py +0 -0
  220. {akquant-0.3.2 → akquant-0.3.4}/examples/30_streaming_report_oneclick.py +0 -0
  221. {akquant-0.3.2 → akquant-0.3.4}/examples/31_streaming_live_console.py +0 -0
  222. {akquant-0.3.2 → akquant-0.3.4}/examples/32_streaming_live_web.py +0 -0
  223. {akquant-0.3.2 → akquant-0.3.4}/examples/33_report_and_analysis_outputs.py +0 -0
  224. {akquant-0.3.2 → akquant-0.3.4}/examples/34_multi_strategy_demo.py +0 -0
  225. {akquant-0.3.2 → akquant-0.3.4}/examples/35_custom_broker_registry_demo.py +0 -0
  226. {akquant-0.3.2 → akquant-0.3.4}/examples/36_trailing_orders.py +0 -0
  227. {akquant-0.3.2 → akquant-0.3.4}/examples/37_feed_replay_alignment_demo.py +0 -0
  228. {akquant-0.3.2 → akquant-0.3.4}/examples/38_live_functional_strategy_demo.py +0 -0
  229. {akquant-0.3.2 → akquant-0.3.4}/examples/39_live_broker_submit_order_demo.py +0 -0
  230. {akquant-0.3.2 → akquant-0.3.4}/examples/40_functional_multi_slot_risk_demo.py +0 -0
  231. {akquant-0.3.2 → akquant-0.3.4}/examples/41_live_multi_slot_orchestration_demo.py +0 -0
  232. {akquant-0.3.2 → akquant-0.3.4}/examples/42_live_broker_event_audit_demo.py +0 -0
  233. {akquant-0.3.2 → akquant-0.3.4}/examples/43_target_weights_rebalance.py +0 -0
  234. {akquant-0.3.2 → akquant-0.3.4}/examples/44_strategy_source_loader_demo.py +0 -0
  235. {akquant-0.3.2 → akquant-0.3.4}/examples/45_talib_indicator_playbook_demo.py +0 -0
  236. {akquant-0.3.2 → akquant-0.3.4}/examples/46_broker_profile_demo.py +0 -0
  237. {akquant-0.3.2 → akquant-0.3.4}/examples/47_margin_liquidation_audit_demo.py +0 -0
  238. {akquant-0.3.2 → akquant-0.3.4}/examples/48_margin_liquidation_priority_compare.py +0 -0
  239. {akquant-0.3.2 → akquant-0.3.4}/examples/49_on_expiry_demo.py +0 -0
  240. {akquant-0.3.2 → akquant-0.3.4}/examples/50_framework_hooks_demo.py +0 -0
  241. {akquant-0.3.2 → akquant-0.3.4}/examples/51_class_tick_callbacks_demo.py +0 -0
  242. {akquant-0.3.2 → akquant-0.3.4}/examples/52_pre_open_demo.py +0 -0
  243. {akquant-0.3.2 → akquant-0.3.4}/examples/53_timer_to_pre_open_demo.py +0 -0
  244. {akquant-0.3.2 → akquant-0.3.4}/examples/54_functional_pre_open_demo.py +0 -0
  245. {akquant-0.3.2 → akquant-0.3.4}/examples/55_functional_ml_walk_forward.py +0 -0
  246. {akquant-0.3.2 → akquant-0.3.4}/examples/56_functional_warm_start_demo.py +0 -0
  247. {akquant-0.3.2 → akquant-0.3.4}/examples/57_functional_multi_slot_warm_start_demo.py +0 -0
  248. {akquant-0.3.2 → akquant-0.3.4}/examples/58_incremental_bootstrap_demo.py +0 -0
  249. {akquant-0.3.2 → akquant-0.3.4}/examples/59_akshare_etf_rotation.py +0 -0
  250. {akquant-0.3.2 → akquant-0.3.4}/examples/60_custom_indicator_demo.py +0 -0
  251. {akquant-0.3.2 → akquant-0.3.4}/examples/61_indicator_visualization_export_demo.py +0 -0
  252. {akquant-0.3.2 → akquant-0.3.4}/examples/62_indicator_streaming_demo.py +0 -0
  253. {akquant-0.3.2 → akquant-0.3.4}/examples/63_indicator_ws_bridge_demo.py +0 -0
  254. {akquant-0.3.2 → akquant-0.3.4}/examples/64_indicator_live_web.py +0 -0
  255. {akquant-0.3.2 → akquant-0.3.4}/examples/65_bar_generator.py +0 -0
  256. {akquant-0.3.2 → akquant-0.3.4}/examples/README.md +0 -0
  257. {akquant-0.3.2 → akquant-0.3.4}/examples/benchmark_utils.py +0 -0
  258. {akquant-0.3.2 → akquant-0.3.4}/examples/pb_mock.py +0 -0
  259. {akquant-0.3.2 → akquant-0.3.4}/examples/strategies/01_stock_dual_moving_average.py +0 -0
  260. {akquant-0.3.2 → akquant-0.3.4}/examples/strategies/02_stock_grid_trading.py +0 -0
  261. {akquant-0.3.2 → akquant-0.3.4}/examples/strategies/03_stock_atr_breakout.py +0 -0
  262. {akquant-0.3.2 → akquant-0.3.4}/examples/strategies/04_stock_momentum_rotation.py +0 -0
  263. {akquant-0.3.2 → akquant-0.3.4}/examples/strategies/05_stock_momentum_rotation_timer.py +0 -0
  264. {akquant-0.3.2 → akquant-0.3.4}/examples/strategies/06_stock_momentum_rotation_bucket.py +0 -0
  265. {akquant-0.3.2 → akquant-0.3.4}/examples/strategies/07_stock_momentum_rotation_on_timer.py +0 -0
  266. {akquant-0.3.2 → akquant-0.3.4}/examples/strategies/08_target_positions_long_short.py +0 -0
  267. {akquant-0.3.2 → akquant-0.3.4}/examples/strategies/09_stock_momentum_rotation_after_bar.py +0 -0
  268. {akquant-0.3.2 → akquant-0.3.4}/examples/strategies/README.md +0 -0
  269. {akquant-0.3.2 → akquant-0.3.4}/examples/textbook/ch01_quickstart.py +0 -0
  270. {akquant-0.3.2 → akquant-0.3.4}/examples/textbook/ch02_programming.py +0 -0
  271. {akquant-0.3.2 → akquant-0.3.4}/examples/textbook/ch03_data.py +0 -0
  272. {akquant-0.3.2 → akquant-0.3.4}/examples/textbook/ch04_comparison.py +0 -0
  273. {akquant-0.3.2 → akquant-0.3.4}/examples/textbook/ch05_strategy.py +0 -0
  274. {akquant-0.3.2 → akquant-0.3.4}/examples/textbook/ch06_stock_a.py +0 -0
  275. {akquant-0.3.2 → akquant-0.3.4}/examples/textbook/ch07_futures.py +0 -0
  276. {akquant-0.3.2 → akquant-0.3.4}/examples/textbook/ch08_options.py +0 -0
  277. {akquant-0.3.2 → akquant-0.3.4}/examples/textbook/ch09_funds.py +0 -0
  278. {akquant-0.3.2 → akquant-0.3.4}/examples/textbook/ch09_portfolio.py +0 -0
  279. {akquant-0.3.2 → akquant-0.3.4}/examples/textbook/ch10_analysis.py +0 -0
  280. {akquant-0.3.2 → akquant-0.3.4}/examples/textbook/ch11_optimization.py +0 -0
  281. {akquant-0.3.2 → akquant-0.3.4}/examples/textbook/ch12_ml.py +0 -0
  282. {akquant-0.3.2 → akquant-0.3.4}/examples/textbook/ch13_visualization.py +0 -0
  283. {akquant-0.3.2 → akquant-0.3.4}/examples/textbook/ch14_factor.py +0 -0
  284. {akquant-0.3.2 → akquant-0.3.4}/examples/textbook/ch15_live_trading.py +0 -0
  285. {akquant-0.3.2 → akquant-0.3.4}/examples/textbook/ch15_strategy_loader.py +0 -0
  286. {akquant-0.3.2 → akquant-0.3.4}/examples/textbook/ch16_indicators.py +0 -0
  287. {akquant-0.3.2 → akquant-0.3.4}/mkdocs.yml +0 -0
  288. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/analysis/__init__.py +0 -0
  289. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/analysis/benchmark.py +0 -0
  290. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/analyzer_plugin.py +0 -0
  291. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/backtest/__init__.py +0 -0
  292. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/backtest/__init__.pyi +0 -0
  293. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/backtest/result.py +0 -0
  294. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/bar_generator.py +0 -0
  295. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/checkpoint.py +0 -0
  296. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/data.py +0 -0
  297. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/execution/__init__.py +0 -0
  298. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/factor/__init__.py +0 -0
  299. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/factor/engine.py +0 -0
  300. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/factor/ops.py +0 -0
  301. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/factor/parser.py +0 -0
  302. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/feed_adapter.py +0 -0
  303. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/fund/__init__.py +0 -0
  304. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/futures/__init__.py +0 -0
  305. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/gateway/__init__.py +0 -0
  306. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/gateway/base.py +0 -0
  307. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/gateway/broker_event_adapter.py +0 -0
  308. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/gateway/broker_event_bridge.py +0 -0
  309. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/gateway/broker_event_mapper.py +0 -0
  310. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/gateway/broker_models.py +0 -0
  311. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/gateway/broker_recovery.py +0 -0
  312. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/gateway/broker_runtime.py +0 -0
  313. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/gateway/broker_state_cache.py +0 -0
  314. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/gateway/broker_strategy_api.py +0 -0
  315. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/gateway/brokers/__init__.py +0 -0
  316. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/gateway/brokers/builtins.py +0 -0
  317. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/gateway/brokers/ctp/__init__.py +0 -0
  318. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/gateway/brokers/ctp/adapter.py +0 -0
  319. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/gateway/brokers/ctp/native.py +0 -0
  320. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/gateway/brokers/miniqmt/__init__.py +0 -0
  321. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/gateway/brokers/miniqmt/stub.py +0 -0
  322. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/gateway/brokers/plugins.py +0 -0
  323. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/gateway/brokers/ptrade/__init__.py +0 -0
  324. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/gateway/brokers/ptrade/stub.py +0 -0
  325. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/gateway/ctp_adapter.py +0 -0
  326. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/gateway/ctp_native.py +0 -0
  327. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/gateway/factory.py +0 -0
  328. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/gateway/local_stop_book.py +0 -0
  329. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/gateway/mapper.py +0 -0
  330. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/gateway/miniqmt.py +0 -0
  331. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/gateway/models.py +0 -0
  332. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/gateway/order_receipt.py +0 -0
  333. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/gateway/order_submitter.py +0 -0
  334. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/gateway/protocols.py +0 -0
  335. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/gateway/ptrade.py +0 -0
  336. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/gateway/registry.py +0 -0
  337. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/gateway/trader_base.py +0 -0
  338. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/indicator.py +0 -0
  339. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/indicator_recording.py +0 -0
  340. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/indicator_stream.py +0 -0
  341. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/live.py +0 -0
  342. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/log.py +0 -0
  343. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/ml/__init__.py +0 -0
  344. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/ml/model.py +0 -0
  345. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/optimize.py +0 -0
  346. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/option/__init__.py +0 -0
  347. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/params.py +0 -0
  348. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/params_adapter.py +0 -0
  349. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/plot/__init__.py +0 -0
  350. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/plot/analysis.py +0 -0
  351. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/plot/dashboard.py +0 -0
  352. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/plot/indicator.py +0 -0
  353. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/plot/report.py +0 -0
  354. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/plot/strategy.py +0 -0
  355. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/plot/utils.py +0 -0
  356. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/py.typed +0 -0
  357. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/risk.py +0 -0
  358. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/sizer.py +0 -0
  359. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/stock/__init__.py +0 -0
  360. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/strategy_events.py +0 -0
  361. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/strategy_framework_hooks.py +0 -0
  362. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/strategy_history.py +0 -0
  363. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/strategy_loader.py +0 -0
  364. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/strategy_logging.py +0 -0
  365. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/strategy_ml.py +0 -0
  366. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/strategy_order_events.py +0 -0
  367. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/strategy_position.py +0 -0
  368. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/strategy_scheduler.py +0 -0
  369. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/strategy_time.py +0 -0
  370. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/talib/__init__.py +0 -0
  371. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/talib/backend.py +0 -0
  372. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/talib/core.py +0 -0
  373. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/talib/funcs.py +0 -0
  374. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/utils/__init__.py +0 -0
  375. {akquant-0.3.2 → akquant-0.3.4}/python/akquant/utils/inspector.py +0 -0
  376. {akquant-0.3.2 → akquant-0.3.4}/requirements-dev.txt +0 -0
  377. {akquant-0.3.2 → akquant-0.3.4}/scripts/cargo-test.sh +0 -0
  378. {akquant-0.3.2 → akquant-0.3.4}/scripts/check_docs_api_examples.py +0 -0
  379. {akquant-0.3.2 → akquant-0.3.4}/scripts/check_docs_links.py +0 -0
  380. {akquant-0.3.2 → akquant-0.3.4}/scripts/dev-check.sh +0 -0
  381. {akquant-0.3.2 → akquant-0.3.4}/scripts/find_legacy_execution_policy_calls.py +0 -0
  382. {akquant-0.3.2 → akquant-0.3.4}/scripts/golden_baseline_report.py +0 -0
  383. {akquant-0.3.2 → akquant-0.3.4}/src/account.rs +0 -0
  384. {akquant-0.3.2 → akquant-0.3.4}/src/analysis/mod.rs +0 -0
  385. {akquant-0.3.2 → akquant-0.3.4}/src/analysis/result.rs +0 -0
  386. {akquant-0.3.2 → akquant-0.3.4}/src/analysis/tests.rs +0 -0
  387. {akquant-0.3.2 → akquant-0.3.4}/src/analysis/tracker.rs +0 -0
  388. {akquant-0.3.2 → akquant-0.3.4}/src/analysis/types.rs +0 -0
  389. {akquant-0.3.2 → akquant-0.3.4}/src/bin/stub_gen.rs +0 -0
  390. {akquant-0.3.2 → akquant-0.3.4}/src/clock.rs +0 -0
  391. {akquant-0.3.2 → akquant-0.3.4}/src/data/aggregator.rs +0 -0
  392. {akquant-0.3.2 → akquant-0.3.4}/src/data/batch.rs +0 -0
  393. {akquant-0.3.2 → akquant-0.3.4}/src/data/client.rs +0 -0
  394. {akquant-0.3.2 → akquant-0.3.4}/src/data/feed.rs +0 -0
  395. {akquant-0.3.2 → akquant-0.3.4}/src/data/mod.rs +0 -0
  396. {akquant-0.3.2 → akquant-0.3.4}/src/engine/python.rs +0 -0
  397. {akquant-0.3.2 → akquant-0.3.4}/src/engine/state.rs +0 -0
  398. {akquant-0.3.2 → akquant-0.3.4}/src/error.rs +0 -0
  399. {akquant-0.3.2 → akquant-0.3.4}/src/event.rs +0 -0
  400. {akquant-0.3.2 → akquant-0.3.4}/src/event_manager.rs +0 -0
  401. {akquant-0.3.2 → akquant-0.3.4}/src/execution/common.rs +0 -0
  402. {akquant-0.3.2 → akquant-0.3.4}/src/execution/crypto.rs +0 -0
  403. {akquant-0.3.2 → akquant-0.3.4}/src/execution/forex.rs +0 -0
  404. {akquant-0.3.2 → akquant-0.3.4}/src/execution/futures.rs +0 -0
  405. {akquant-0.3.2 → akquant-0.3.4}/src/execution/matcher.rs +0 -0
  406. {akquant-0.3.2 → akquant-0.3.4}/src/execution/mod.rs +0 -0
  407. {akquant-0.3.2 → akquant-0.3.4}/src/execution/option.rs +0 -0
  408. {akquant-0.3.2 → akquant-0.3.4}/src/execution/python.rs +0 -0
  409. {akquant-0.3.2 → akquant-0.3.4}/src/execution/realtime.rs +0 -0
  410. {akquant-0.3.2 → akquant-0.3.4}/src/execution/slippage.rs +0 -0
  411. {akquant-0.3.2 → akquant-0.3.4}/src/history.rs +0 -0
  412. {akquant-0.3.2 → akquant-0.3.4}/src/indicators/momentum.rs +0 -0
  413. {akquant-0.3.2 → akquant-0.3.4}/src/indicators/momentum_oscillators.rs +0 -0
  414. {akquant-0.3.2 → akquant-0.3.4}/src/indicators/momentum_rates.rs +0 -0
  415. {akquant-0.3.2 → akquant-0.3.4}/src/indicators/moving_average.rs +0 -0
  416. {akquant-0.3.2 → akquant-0.3.4}/src/indicators/moving_average_compound.rs +0 -0
  417. {akquant-0.3.2 → akquant-0.3.4}/src/indicators/moving_average_core.rs +0 -0
  418. {akquant-0.3.2 → akquant-0.3.4}/src/indicators/moving_average_transforms.rs +0 -0
  419. {akquant-0.3.2 → akquant-0.3.4}/src/indicators/moving_average_windowed.rs +0 -0
  420. {akquant-0.3.2 → akquant-0.3.4}/src/indicators/trend.rs +0 -0
  421. {akquant-0.3.2 → akquant-0.3.4}/src/indicators/trend_directional.rs +0 -0
  422. {akquant-0.3.2 → akquant-0.3.4}/src/indicators/trend_oscillators.rs +0 -0
  423. {akquant-0.3.2 → akquant-0.3.4}/src/indicators/trend_regression.rs +0 -0
  424. {akquant-0.3.2 → akquant-0.3.4}/src/indicators/volatility.rs +0 -0
  425. {akquant-0.3.2 → akquant-0.3.4}/src/indicators/volatility_price.rs +0 -0
  426. {akquant-0.3.2 → akquant-0.3.4}/src/indicators/volatility_stats.rs +0 -0
  427. {akquant-0.3.2 → akquant-0.3.4}/src/indicators/volume.rs +0 -0
  428. {akquant-0.3.2 → akquant-0.3.4}/src/indicators.rs +0 -0
  429. {akquant-0.3.2 → akquant-0.3.4}/src/lib.rs +0 -0
  430. {akquant-0.3.2 → akquant-0.3.4}/src/log_context.rs +0 -0
  431. {akquant-0.3.2 → akquant-0.3.4}/src/margin/calculator.rs +0 -0
  432. {akquant-0.3.2 → akquant-0.3.4}/src/margin/engine.rs +0 -0
  433. {akquant-0.3.2 → akquant-0.3.4}/src/margin/mod.rs +0 -0
  434. {akquant-0.3.2 → akquant-0.3.4}/src/market/core.rs +0 -0
  435. {akquant-0.3.2 → akquant-0.3.4}/src/market/corporate_action.rs +0 -0
  436. {akquant-0.3.2 → akquant-0.3.4}/src/market/futures.rs +0 -0
  437. {akquant-0.3.2 → akquant-0.3.4}/src/market/manager.rs +0 -0
  438. {akquant-0.3.2 → akquant-0.3.4}/src/market/mod.rs +0 -0
  439. {akquant-0.3.2 → akquant-0.3.4}/src/market/option.rs +0 -0
  440. {akquant-0.3.2 → akquant-0.3.4}/src/market/simple.rs +0 -0
  441. {akquant-0.3.2 → akquant-0.3.4}/src/model/corporate_action.rs +0 -0
  442. {akquant-0.3.2 → akquant-0.3.4}/src/model/market_data.rs +0 -0
  443. {akquant-0.3.2 → akquant-0.3.4}/src/model/mod.rs +0 -0
  444. {akquant-0.3.2 → akquant-0.3.4}/src/model/order.rs +0 -0
  445. {akquant-0.3.2 → akquant-0.3.4}/src/model/timer.rs +0 -0
  446. {akquant-0.3.2 → akquant-0.3.4}/src/model/types.rs +0 -0
  447. {akquant-0.3.2 → akquant-0.3.4}/src/order_manager.rs +0 -0
  448. {akquant-0.3.2 → akquant-0.3.4}/src/pipeline/mod.rs +0 -0
  449. {akquant-0.3.2 → akquant-0.3.4}/src/pipeline/processor.rs +0 -0
  450. {akquant-0.3.2 → akquant-0.3.4}/src/pipeline/runner.rs +0 -0
  451. {akquant-0.3.2 → akquant-0.3.4}/src/pipeline/stages/cleanup.rs +0 -0
  452. {akquant-0.3.2 → akquant-0.3.4}/src/pipeline/stages/data.rs +0 -0
  453. {akquant-0.3.2 → akquant-0.3.4}/src/pipeline/stages/execution.rs +0 -0
  454. {akquant-0.3.2 → akquant-0.3.4}/src/pipeline/stages/shared.rs +0 -0
  455. {akquant-0.3.2 → akquant-0.3.4}/src/pipeline/stages/statistics.rs +0 -0
  456. {akquant-0.3.2 → akquant-0.3.4}/src/pipeline/stages/strategy.rs +0 -0
  457. {akquant-0.3.2 → akquant-0.3.4}/src/risk/config.rs +0 -0
  458. {akquant-0.3.2 → akquant-0.3.4}/src/risk/futures.rs +0 -0
  459. {akquant-0.3.2 → akquant-0.3.4}/src/risk/manager.rs +0 -0
  460. {akquant-0.3.2 → akquant-0.3.4}/src/risk/option.rs +0 -0
  461. {akquant-0.3.2 → akquant-0.3.4}/src/risk/rule.rs +0 -0
  462. {akquant-0.3.2 → akquant-0.3.4}/src/settlement/handler.rs +0 -0
  463. {akquant-0.3.2 → akquant-0.3.4}/src/settlement/mod.rs +0 -0
  464. {akquant-0.3.2 → akquant-0.3.4}/src/settlement/option.rs +0 -0
  465. {akquant-0.3.2 → akquant-0.3.4}/src/statistics/mod.rs +0 -0
  466. {akquant-0.3.2 → akquant-0.3.4}/tests/gateway_contract/test_event_bridge_contract.py +0 -0
  467. {akquant-0.3.2 → akquant-0.3.4}/tests/gateway_contract/test_recovery_contract.py +0 -0
  468. {akquant-0.3.2 → akquant-0.3.4}/tests/gateway_contract/test_submitter_contract.py +0 -0
  469. {akquant-0.3.2 → akquant-0.3.4}/tests/golden/BASELINE_REPORT.md +0 -0
  470. {akquant-0.3.2 → akquant-0.3.4}/tests/golden/LEGACY_EXECUTION_CALLS.md +0 -0
  471. {akquant-0.3.2/tests/golden/current → akquant-0.3.4/tests/golden/baselines}/futures_margin/equity_curve.parquet +0 -0
  472. {akquant-0.3.2/tests/golden/current → akquant-0.3.4/tests/golden/baselines}/option_basic/equity_curve.parquet +0 -0
  473. {akquant-0.3.2/tests/golden/current → akquant-0.3.4/tests/golden/baselines}/stock_t1/equity_curve.parquet +0 -0
  474. {akquant-0.3.2/tests/golden/current → akquant-0.3.4/tests/golden/baselines}/stock_t1/trades.parquet +0 -0
  475. {akquant-0.3.2 → akquant-0.3.4}/tests/golden/data/future_margin.parquet +0 -0
  476. {akquant-0.3.2 → akquant-0.3.4}/tests/golden/data/future_margin.parquet.sha256 +0 -0
  477. {akquant-0.3.2 → akquant-0.3.4}/tests/golden/data/option_basic.parquet +0 -0
  478. {akquant-0.3.2 → akquant-0.3.4}/tests/golden/data/option_basic.parquet.sha256 +0 -0
  479. {akquant-0.3.2 → akquant-0.3.4}/tests/golden/data/stock_t1.parquet +0 -0
  480. {akquant-0.3.2 → akquant-0.3.4}/tests/golden/data/stock_t1.parquet.sha256 +0 -0
  481. {akquant-0.3.2 → akquant-0.3.4}/tests/golden/gen_data.py +0 -0
  482. {akquant-0.3.2 → akquant-0.3.4}/tests/golden/runner.py +0 -0
  483. {akquant-0.3.2 → akquant-0.3.4}/tests/golden/strategies/futures_margin.py +0 -0
  484. {akquant-0.3.2 → akquant-0.3.4}/tests/golden/strategies/option_basic.py +0 -0
  485. {akquant-0.3.2 → akquant-0.3.4}/tests/golden/strategies/stock_t1.py +0 -0
  486. {akquant-0.3.2 → akquant-0.3.4}/tests/golden/test_golden.py +0 -0
  487. {akquant-0.3.2 → akquant-0.3.4}/tests/test_account_risk_rules.py +0 -0
  488. {akquant-0.3.2 → akquant-0.3.4}/tests/test_api_rename_cash.py +0 -0
  489. {akquant-0.3.2 → akquant-0.3.4}/tests/test_api_rename_composites.py +0 -0
  490. {akquant-0.3.2 → akquant-0.3.4}/tests/test_api_rename_equity.py +0 -0
  491. {akquant-0.3.2 → akquant-0.3.4}/tests/test_api_rename_holding_bars.py +0 -0
  492. {akquant-0.3.2 → akquant-0.3.4}/tests/test_api_rename_positions.py +0 -0
  493. {akquant-0.3.2 → akquant-0.3.4}/tests/test_api_rename_rebalance.py +0 -0
  494. {akquant-0.3.2 → akquant-0.3.4}/tests/test_bar_generator.py +0 -0
  495. {akquant-0.3.2 → akquant-0.3.4}/tests/test_broker_bridge_adapts_events.py +0 -0
  496. {akquant-0.3.2 → akquant-0.3.4}/tests/test_broker_bridge_drives_order_groups.py +0 -0
  497. {akquant-0.3.2 → akquant-0.3.4}/tests/test_broker_event_adapter.py +0 -0
  498. {akquant-0.3.2 → akquant-0.3.4}/tests/test_broker_event_adapter_local_id.py +0 -0
  499. {akquant-0.3.2 → akquant-0.3.4}/tests/test_broker_execution_local_stops.py +0 -0
  500. {akquant-0.3.2 → akquant-0.3.4}/tests/test_broker_execution_read_path_parity.py +0 -0
  501. {akquant-0.3.2 → akquant-0.3.4}/tests/test_broker_execution_stop_requeue.py +0 -0
  502. {akquant-0.3.2 → akquant-0.3.4}/tests/test_broker_plugins.py +0 -0
  503. {akquant-0.3.2 → akquant-0.3.4}/tests/test_broker_position_sync.py +0 -0
  504. {akquant-0.3.2 → akquant-0.3.4}/tests/test_broker_seed_baseline.py +0 -0
  505. {akquant-0.3.2 → akquant-0.3.4}/tests/test_broker_trade_redelivery_dedup.py +0 -0
  506. {akquant-0.3.2 → akquant-0.3.4}/tests/test_close_position_delegate.py +0 -0
  507. {akquant-0.3.2 → akquant-0.3.4}/tests/test_composed_ctx_not_ready.py +0 -0
  508. {akquant-0.3.2 → akquant-0.3.4}/tests/test_cost_config_consolidation.py +0 -0
  509. {akquant-0.3.2 → akquant-0.3.4}/tests/test_custom_matcher.py +0 -0
  510. {akquant-0.3.2 → akquant-0.3.4}/tests/test_data_catalog.py +0 -0
  511. {akquant-0.3.2 → akquant-0.3.4}/tests/test_docs_api_examples.py +0 -0
  512. {akquant-0.3.2 → akquant-0.3.4}/tests/test_docs_links.py +0 -0
  513. {akquant-0.3.2 → akquant-0.3.4}/tests/test_event_model_parity.py +0 -0
  514. {akquant-0.3.2 → akquant-0.3.4}/tests/test_examples_regression.py +0 -0
  515. {akquant-0.3.2 → akquant-0.3.4}/tests/test_execution_binding.py +0 -0
  516. {akquant-0.3.2 → akquant-0.3.4}/tests/test_execution_broker.py +0 -0
  517. {akquant-0.3.2 → akquant-0.3.4}/tests/test_execution_broker_reads_routed.py +0 -0
  518. {akquant-0.3.2 → akquant-0.3.4}/tests/test_execution_composed_parity.py +0 -0
  519. {akquant-0.3.2 → akquant-0.3.4}/tests/test_execution_read_delegation.py +0 -0
  520. {akquant-0.3.2 → akquant-0.3.4}/tests/test_execution_sim.py +0 -0
  521. {akquant-0.3.2 → akquant-0.3.4}/tests/test_execution_write_delegation.py +0 -0
  522. {akquant-0.3.2 → akquant-0.3.4}/tests/test_factor_engine.py +0 -0
  523. {akquant-0.3.2 → akquant-0.3.4}/tests/test_factor_ops.py +0 -0
  524. {akquant-0.3.2 → akquant-0.3.4}/tests/test_feed_adapter.py +0 -0
  525. {akquant-0.3.2 → akquant-0.3.4}/tests/test_gateway_broker_live_cancel.py +0 -0
  526. {akquant-0.3.2 → akquant-0.3.4}/tests/test_gateway_broker_live_reads.py +0 -0
  527. {akquant-0.3.2 → akquant-0.3.4}/tests/test_gateway_broker_models_ext.py +0 -0
  528. {akquant-0.3.2 → akquant-0.3.4}/tests/test_gateway_broker_state_cache.py +0 -0
  529. {akquant-0.3.2 → akquant-0.3.4}/tests/test_gateway_broker_state_invalidation.py +0 -0
  530. {akquant-0.3.2 → akquant-0.3.4}/tests/test_gateway_broker_submitter_readiness.py +0 -0
  531. {akquant-0.3.2 → akquant-0.3.4}/tests/test_gateway_broker_submitter_signature.py +0 -0
  532. {akquant-0.3.2 → akquant-0.3.4}/tests/test_gateway_brokers_paths.py +0 -0
  533. {akquant-0.3.2 → akquant-0.3.4}/tests/test_gateway_builtins_registry.py +0 -0
  534. {akquant-0.3.2 → akquant-0.3.4}/tests/test_gateway_callbacks.py +0 -0
  535. {akquant-0.3.2 → akquant-0.3.4}/tests/test_gateway_ctp_adapter.py +0 -0
  536. {akquant-0.3.2 → akquant-0.3.4}/tests/test_gateway_ctp_native.py +0 -0
  537. {akquant-0.3.2 → akquant-0.3.4}/tests/test_gateway_factory.py +0 -0
  538. {akquant-0.3.2 → akquant-0.3.4}/tests/test_gateway_mapper.py +0 -0
  539. {akquant-0.3.2 → akquant-0.3.4}/tests/test_gateway_optional_market.py +0 -0
  540. {akquant-0.3.2 → akquant-0.3.4}/tests/test_gateway_order_submitter_extra.py +0 -0
  541. {akquant-0.3.2 → akquant-0.3.4}/tests/test_gateway_registry.py +0 -0
  542. {akquant-0.3.2 → akquant-0.3.4}/tests/test_gateway_sim_submit_guard.py +0 -0
  543. {akquant-0.3.2 → akquant-0.3.4}/tests/test_gateway_tif_mapping.py +0 -0
  544. {akquant-0.3.2 → akquant-0.3.4}/tests/test_gateway_trader_base.py +0 -0
  545. {akquant-0.3.2 → akquant-0.3.4}/tests/test_indicator_live_web_example.py +0 -0
  546. {akquant-0.3.2 → akquant-0.3.4}/tests/test_indicator_recording.py +0 -0
  547. {akquant-0.3.2 → akquant-0.3.4}/tests/test_inspector.py +0 -0
  548. {akquant-0.3.2 → akquant-0.3.4}/tests/test_live_runner.py +0 -0
  549. {akquant-0.3.2 → akquant-0.3.4}/tests/test_live_runner_broker_bridge.py +0 -0
  550. {akquant-0.3.2 → akquant-0.3.4}/tests/test_live_runner_broker_readiness.py +0 -0
  551. {akquant-0.3.2 → akquant-0.3.4}/tests/test_live_runner_broker_recovery.py +0 -0
  552. {akquant-0.3.2 → akquant-0.3.4}/tests/test_live_runner_broker_submitter.py +0 -0
  553. {akquant-0.3.2 → akquant-0.3.4}/tests/test_live_runner_order_request_cache.py +0 -0
  554. {akquant-0.3.2 → akquant-0.3.4}/tests/test_live_runner_stop_remap.py +0 -0
  555. {akquant-0.3.2 → akquant-0.3.4}/tests/test_local_stop_book.py +0 -0
  556. {akquant-0.3.2 → akquant-0.3.4}/tests/test_local_stop_book_threadsafe.py +0 -0
  557. {akquant-0.3.2 → akquant-0.3.4}/tests/test_local_stop_scenario.py +0 -0
  558. {akquant-0.3.2 → akquant-0.3.4}/tests/test_multisymbol_cross_section_consistency.py +0 -0
  559. {akquant-0.3.2 → akquant-0.3.4}/tests/test_oco_bracket_broker_live_scenario.py +0 -0
  560. {akquant-0.3.2 → akquant-0.3.4}/tests/test_on_execution_report_noop.py +0 -0
  561. {akquant-0.3.2 → akquant-0.3.4}/tests/test_order_receipt.py +0 -0
  562. {akquant-0.3.2 → akquant-0.3.4}/tests/test_order_receipt_backtest.py +0 -0
  563. {akquant-0.3.2 → akquant-0.3.4}/tests/test_orders_df.py +0 -0
  564. {akquant-0.3.2 → akquant-0.3.4}/tests/test_params_adapter.py +0 -0
  565. {akquant-0.3.2 → akquant-0.3.4}/tests/test_partial_filled_status.py +0 -0
  566. {akquant-0.3.2 → akquant-0.3.4}/tests/test_portfolio.py +0 -0
  567. {akquant-0.3.2 → akquant-0.3.4}/tests/test_quickstart_stream_consistency.py +0 -0
  568. {akquant-0.3.2 → akquant-0.3.4}/tests/test_removed_wrappers.py +0 -0
  569. {akquant-0.3.2 → akquant-0.3.4}/tests/test_report_helpers.py +0 -0
  570. {akquant-0.3.2 → akquant-0.3.4}/tests/test_report_plot_extensions.py +0 -0
  571. {akquant-0.3.2 → akquant-0.3.4}/tests/test_result_analysis_extensions.py +0 -0
  572. {akquant-0.3.2 → akquant-0.3.4}/tests/test_review_minors_cleanup.py +0 -0
  573. {akquant-0.3.2 → akquant-0.3.4}/tests/test_stop_id_remap_scenario.py +0 -0
  574. {akquant-0.3.2 → akquant-0.3.4}/tests/test_stop_orders.py +0 -0
  575. {akquant-0.3.2 → akquant-0.3.4}/tests/test_strategy_events_stop_hook.py +0 -0
  576. {akquant-0.3.2 → akquant-0.3.4}/tests/test_strategy_extras.py +0 -0
  577. {akquant-0.3.2 → akquant-0.3.4}/tests/test_strategy_order_group_lock.py +0 -0
  578. {akquant-0.3.2 → akquant-0.3.4}/tests/test_strategy_sizing_broker_live_guard.py +0 -0
  579. {akquant-0.3.2 → akquant-0.3.4}/tests/test_strategy_timers_indicators.py +0 -0
  580. {akquant-0.3.2 → akquant-0.3.4}/tests/test_t_plus_one.py +0 -0
  581. {akquant-0.3.2 → akquant-0.3.4}/tests/test_talib_backend.py +0 -0
  582. {akquant-0.3.2 → akquant-0.3.4}/tests/test_talib_compat.py +0 -0
  583. {akquant-0.3.2 → akquant-0.3.4}/tests/test_target_orders_core.py +0 -0
  584. {akquant-0.3.2 → akquant-0.3.4}/tests/test_trades_df.py +0 -0
  585. {akquant-0.3.2 → akquant-0.3.4}/tests/test_version.py +0 -0
@@ -30,7 +30,7 @@ dependencies = [
30
30
 
31
31
  [[package]]
32
32
  name = "akquant"
33
- version = "0.3.2"
33
+ version = "0.3.4"
34
34
  dependencies = [
35
35
  "anyhow",
36
36
  "chrono",
@@ -1,6 +1,6 @@
1
1
  [package]
2
2
  name = "akquant"
3
- version = "0.3.2"
3
+ version = "0.3.4"
4
4
  edition = "2024"
5
5
  description = "High-performance quantitative trading framework based on Rust and Python"
6
6
  license = "MIT"
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: akquant
3
- Version: 0.3.2
3
+ Version: 0.3.4
4
4
  Classifier: Programming Language :: Rust
5
5
  Classifier: Programming Language :: Python :: Implementation :: CPython
6
6
  Classifier: Programming Language :: Python :: Implementation :: PyPy
@@ -116,7 +116,7 @@ aqp.plot_pnl_vs_duration(result.trades_df)
116
116
  | `open_position_count` | Open Position Count | Int | Number of symbols still carrying open positions at the end of the backtest. |
117
117
  | `initial_market_value` | Initial Market Value | Float | Initial capital (usually Cash). |
118
118
  | `end_market_value` | End Market Value | Float | Total asset value at the end (Cash + Position Value). |
119
- | `total_pnl` | Total PnL | Float | `end_market_value - initial_market_value`. |
119
+ | `total_pnl` | Total PnL | Float | `end_market_value - initial_market_value` (portfolio-level: realized net PnL + unrealized floating PnL). Note it is NOT equal to `total_profit + total_loss` (which is the trade-level realized gross PnL, before commission and excluding floating PnL); for the trade-level realized gross PnL use `result.trade_metrics.gross_pnl`. |
120
120
  | `unrealized_pnl` | Unrealized PnL | Float | Floating PnL of open positions at the end. |
121
121
  | `total_return_pct` | Total Return | **%** | `(End MV - Initial MV) / Initial MV * 100`. |
122
122
  | `annualized_return` | Annualized Return | Ratio | `(1 + Total Return)^(1/Years) - 1`. |
@@ -95,7 +95,7 @@ execution_count 134.0
95
95
  open_position_count 0.0
96
96
  initial_market_value 100000.0
97
97
  end_market_value 99100.68204
98
- total_pnl -188.0
98
+ total_pnl -899.31796
99
99
  unrealized_pnl 0.0
100
100
  total_return_pct -0.899318
101
101
  annualized_return -0.008109
@@ -15,7 +15,7 @@
15
15
  | `open_position_count` | 未平仓标的数 | Int | 回测结束时仍有持仓的标的数量。 |
16
16
  | `initial_market_value` | 初始市值 | Float | 初始资金 (通常为 Cash)。 |
17
17
  | `end_market_value` | 结束市值 | Float | 回测结束时的总资产 (Cash + 持仓市值)。 |
18
- | `total_pnl` | 总盈亏 | Float | `end_market_value - initial_market_value`。 |
18
+ | `total_pnl` | 总盈亏 | Float | `end_market_value - initial_market_value`(组合层:已实现净盈亏 + 未实现浮动盈亏)。注意它不等于 `total_profit + total_loss`(后者是逐笔已实现毛盈亏,未扣佣金、不含浮动盈亏);若需逐笔已实现毛盈亏请用 `result.trade_metrics.gross_pnl`。 |
19
19
  | `unrealized_pnl` | 未实现盈亏 | Float | 结束时持仓的浮动盈亏。 |
20
20
  | `total_return_pct` | 总收益率 | **% (百分比)** | `(结束市值 - 初始市值) / 初始市值 * 100`。 |
21
21
  | `annualized_return` | 年化收益率 | Ratio (小数) | `(1 + 总收益率)^(1/年数) - 1`。注意这里是小数,如 0.2 表示 20%。 |
@@ -95,7 +95,7 @@ execution_count 134.0
95
95
  open_position_count 0.0
96
96
  initial_market_value 100000.0
97
97
  end_market_value 99100.68204
98
- total_pnl -188.0
98
+ total_pnl -899.31796
99
99
  unrealized_pnl 0.0
100
100
  total_return_pct -0.899318
101
101
  annualized_return -0.008109
@@ -272,7 +272,7 @@ execution_count 66.0
272
272
  open_position_count 0.0
273
273
  initial_market_value 100000.0
274
274
  end_market_value 70668.3408
275
- total_pnl -25232.0
275
+ total_pnl -29331.6592
276
276
  unrealized_pnl 0.0
277
277
  total_return_pct -29.331659
278
278
  annualized_return -0.083297
@@ -4,7 +4,7 @@ build-backend = "maturin"
4
4
 
5
5
  [project]
6
6
  name = "akquant"
7
- version = "0.3.2"
7
+ version = "0.3.4"
8
8
  description = "High-performance quantitative trading framework based on Rust and Python"
9
9
  readme = "README.md"
10
10
  license = {text = "MIT License"}
@@ -8,7 +8,7 @@ try:
8
8
  except metadata.PackageNotFoundError:
9
9
  __version__ = "0.0.0+unknown"
10
10
 
11
- __engine_rule_version__ = "1.1.0" # Increment on behavior-changing updates
11
+ __engine_rule_version__ = "1.3.0" # Increment on behavior-changing updates
12
12
 
13
13
  from . import akquant as _akquant
14
14
  from . import log as _log
@@ -948,6 +948,7 @@ class Instrument:
948
948
  option_margin_model: typing.Optional[akquant.OptionMarginModel]
949
949
  implied_volatility: typing.Optional[float]
950
950
  reference_volatility: typing.Optional[float]
951
+ sellable_after_days: int
951
952
  def __new__(
952
953
  cls,
953
954
  symbol: str,
@@ -965,6 +966,7 @@ class Instrument:
965
966
  option_margin_model: typing.Optional[OptionMarginModel] = ...,
966
967
  implied_volatility: typing.Optional[float] = ...,
967
968
  reference_volatility: typing.Optional[float] = ...,
969
+ sellable_after_days: typing.Optional[int] = ...,
968
970
  ) -> "Instrument": ...
969
971
 
970
972
  class MACD:
@@ -2585,6 +2587,7 @@ class StrategyContext:
2585
2587
  last_closed_trade: typing.Optional[ClosedTrade]
2586
2588
  closed_trades: list[ClosedTrade]
2587
2589
  cash: float
2590
+ buying_power: float
2588
2591
  positions: dict[str, float]
2589
2592
  available_positions: dict[str, float]
2590
2593
  def __new__(
@@ -2838,8 +2838,8 @@ def run_backtest(
2838
2838
  option_margin_model=_option_margin_model_to_upper_name(
2839
2839
  getattr(prebuilt, "option_margin_model", None)
2840
2840
  ),
2841
- tick_size=float(getattr(prebuilt, "tick_size", 0.01)),
2842
- lot_size=float(getattr(prebuilt, "lot_size", 1.0)),
2841
+ tick_size=float(getattr(prebuilt, "tick_size", 0.01) or 0.01),
2842
+ lot_size=float(getattr(prebuilt, "lot_size", 1.0) or 1.0),
2843
2843
  implied_volatility=(
2844
2844
  float(getattr(prebuilt, "implied_volatility"))
2845
2845
  if getattr(prebuilt, "implied_volatility", None) is not None
@@ -3661,6 +3661,15 @@ def run_backtest(
3661
3661
  ):
3662
3662
  has_futures_instruments = True
3663
3663
 
3664
+ # Any explicit per-instrument T+1 (sellable_after_days>=1) needs ChinaMarket so
3665
+ # on_day_close releases the lock; otherwise a T+1 instrument under t_plus_one=False
3666
+ # (SimpleMarket) would silently never become sellable.
3667
+ any_t_plus_one_instrument = any(
3668
+ getattr(ic, "sellable_after_days", None) is not None
3669
+ and getattr(ic, "sellable_after_days", 0) >= 1
3670
+ for ic in (kwargs.get("instruments") or [])
3671
+ )
3672
+
3664
3673
  if china_futures_config and has_futures_instruments:
3665
3674
  if (
3666
3675
  not china_futures_config.use_china_futures_market
@@ -3683,9 +3692,10 @@ def run_backtest(
3683
3692
  engine.use_simple_market(commission_rate)
3684
3693
  if t_plus_one:
3685
3694
  engine.set_t_plus_one(True)
3686
- elif t_plus_one:
3695
+ elif t_plus_one or any_t_plus_one_instrument:
3687
3696
  engine.use_china_market()
3688
- engine.set_t_plus_one(True)
3697
+ if t_plus_one:
3698
+ engine.set_t_plus_one(True)
3689
3699
  else:
3690
3700
  if hasattr(engine, "use_simple_market_policy"):
3691
3701
  cast(Any, engine).use_simple_market_policy(
@@ -4097,8 +4107,8 @@ def run_backtest(
4097
4107
  option_margin_model=_option_margin_model_to_upper_name(
4098
4108
  getattr(prebuilt, "option_margin_model", None)
4099
4109
  ),
4100
- tick_size=float(getattr(prebuilt, "tick_size", 0.01)),
4101
- lot_size=float(getattr(prebuilt, "lot_size", 1.0)),
4110
+ tick_size=float(getattr(prebuilt, "tick_size", 0.01) or 0.01),
4111
+ lot_size=float(getattr(prebuilt, "lot_size", 1.0) or 1.0),
4102
4112
  implied_volatility=(
4103
4113
  float(getattr(prebuilt, "implied_volatility"))
4104
4114
  if getattr(prebuilt, "implied_volatility", None) is not None
@@ -4170,6 +4180,11 @@ def run_backtest(
4170
4180
  i_conf.settlement_type
4171
4181
  )
4172
4182
  p_settlement_price = i_conf.settlement_price
4183
+ p_sellable_after_days = (
4184
+ i_conf.sellable_after_days
4185
+ if i_conf.sellable_after_days is not None
4186
+ else (1 if t_plus_one else 0)
4187
+ )
4173
4188
  static_attrs = getattr(i_conf, "static_attrs", {})
4174
4189
  if static_attrs is None:
4175
4190
  static_attrs = {}
@@ -4222,6 +4237,7 @@ def run_backtest(
4222
4237
  default_settlement_type
4223
4238
  )
4224
4239
  p_settlement_price = default_settlement_price
4240
+ p_sellable_after_days = 1 if t_plus_one else 0
4225
4241
  static_attrs = {}
4226
4242
 
4227
4243
  if p_asset_type != AssetType.Futures:
@@ -4265,6 +4281,7 @@ def run_backtest(
4265
4281
  p_option_margin_model,
4266
4282
  p_implied_volatility,
4267
4283
  p_reference_volatility,
4284
+ p_sellable_after_days,
4268
4285
  )
4269
4286
  engine.add_instrument(instr)
4270
4287
  instrument_snapshots[sym] = InstrumentSnapshot(
@@ -5305,8 +5322,8 @@ def run_warm_start(
5305
5322
  option_margin_model=_option_margin_model_to_upper_name(
5306
5323
  getattr(prebuilt, "option_margin_model", None)
5307
5324
  ),
5308
- tick_size=float(getattr(prebuilt, "tick_size", 0.01)),
5309
- lot_size=float(getattr(prebuilt, "lot_size", 1.0)),
5325
+ tick_size=float(getattr(prebuilt, "tick_size", 0.01) or 0.01),
5326
+ lot_size=float(getattr(prebuilt, "lot_size", 1.0) or 1.0),
5310
5327
  option_type=_option_type_to_upper_name(
5311
5328
  getattr(prebuilt, "option_type", None)
5312
5329
  ),
@@ -5418,6 +5435,11 @@ def run_warm_start(
5418
5435
  p_implied_volatility = None
5419
5436
  p_reference_volatility = None
5420
5437
 
5438
+ p_sellable_after_days = (
5439
+ conf.sellable_after_days
5440
+ if conf is not None and conf.sellable_after_days is not None
5441
+ else None
5442
+ )
5421
5443
  instr = Instrument(
5422
5444
  symbol=sym,
5423
5445
  asset_type=p_asset_type,
@@ -5434,6 +5456,7 @@ def run_warm_start(
5434
5456
  option_margin_model=p_option_margin_model,
5435
5457
  implied_volatility=p_implied_volatility,
5436
5458
  reference_volatility=p_reference_volatility,
5459
+ sellable_after_days=p_sellable_after_days,
5437
5460
  )
5438
5461
  engine.add_instrument(instr)
5439
5462
  warm_start_instrument_snapshots[sym] = InstrumentSnapshot(
@@ -185,6 +185,7 @@ class InstrumentConfig:
185
185
  reference_volatility: Optional[float] = None
186
186
  settlement_type: Optional[InstrumentSettlementTypeInput] = None
187
187
  settlement_price: Optional[float] = None
188
+ sellable_after_days: Optional[int] = None
188
189
  static_attrs: Dict[str, Union[str, int, float, bool]] = field(default_factory=dict)
189
190
 
190
191
  def __post_init__(self) -> None:
@@ -241,6 +242,14 @@ class InstrumentConfig:
241
242
  raise ValueError("lot_size must be > 0")
242
243
  if self.reference_volatility is not None and self.reference_volatility <= 0:
243
244
  raise ValueError("reference_volatility must be > 0")
245
+ if self.sellable_after_days is not None and self.sellable_after_days not in (
246
+ 0,
247
+ 1,
248
+ ):
249
+ raise ValueError(
250
+ "InstrumentConfig.sellable_after_days must be 0 (T+0) or 1 (T+1); "
251
+ f"got {self.sellable_after_days} (T+2+ not yet supported)"
252
+ )
244
253
 
245
254
 
246
255
  @dataclass
@@ -36,6 +36,9 @@ class ExecutionBackend(Protocol):
36
36
  def get_cash(self) -> float:
37
37
  """获取现金."""
38
38
 
39
+ def get_buying_power(self) -> float:
40
+ """获取可用买入力."""
41
+
39
42
  def submit_order(self, **kwargs: Any) -> str:
40
43
  """提交订单,返回订单号."""
41
44
 
@@ -51,6 +51,10 @@ class SimExecution:
51
51
  """获取现金."""
52
52
  return api._sim_get_cash(self._s)
53
53
 
54
+ def get_buying_power(self) -> float:
55
+ """获取可用买入力."""
56
+ return api._sim_get_buying_power(self._s)
57
+
54
58
  def submit_order(self, **kwargs: Any) -> OrderReceipt:
55
59
  """提交订单,返回 OrderReceipt(携带回测拆腿产生的全部订单 id)."""
56
60
  return api._sim_submit_order(self._s, **kwargs)
@@ -129,6 +129,10 @@ class BrokerExecution:
129
129
  """获取现金."""
130
130
  return float(getattr(self._cache.account(), "cash", 0.0) or 0.0)
131
131
 
132
+ def get_buying_power(self) -> float:
133
+ """获取可用买入力(实盘暂以可用现金近似)."""
134
+ return self.get_cash()
135
+
132
136
  def submit_order(self, **kwargs: Any) -> OrderReceipt:
133
137
  """提交订单,返回下单回执(OrderReceipt,含全部腿 id).
134
138
 
@@ -112,6 +112,9 @@ from .strategy_trading_api import (
112
112
  from .strategy_trading_api import (
113
113
  get_available_position as _get_available_position_impl,
114
114
  )
115
+ from .strategy_trading_api import (
116
+ get_buying_power as _get_buying_power_impl,
117
+ )
115
118
  from .strategy_trading_api import (
116
119
  get_cash as _get_cash_impl,
117
120
  )
@@ -2228,6 +2231,11 @@ class Strategy:
2228
2231
  """当前可用现金(等同旧 get_cash())."""
2229
2232
  return _get_cash_impl(self)
2230
2233
 
2234
+ @property
2235
+ def buying_power(self) -> float:
2236
+ """可用买入力(含本回调已提交卖单的预期回笼;用于卖出后为买单定量)."""
2237
+ return _get_buying_power_impl(self)
2238
+
2231
2239
  @property
2232
2240
  def equity(self) -> float:
2233
2241
  """当前账户总权益(现金 + 持仓市值,权威只读;等同旧 get_portfolio_value())."""
@@ -1527,6 +1527,11 @@ def get_cash(strategy: Any) -> float:
1527
1527
  return float(strategy.execution.get_cash())
1528
1528
 
1529
1529
 
1530
+ def get_buying_power(strategy: Any) -> float:
1531
+ """获取可用买入力(经执行后端)."""
1532
+ return float(strategy.execution.get_buying_power())
1533
+
1534
+
1530
1535
  # --- SimExecution 后端原语(Task 1 引入;Task 3/4 让公共函数 delegate 到 execution)---
1531
1536
  def _sim_get_position(strategy: Any, symbol: Optional[str] = None) -> float:
1532
1537
  if strategy.ctx is None:
@@ -1558,6 +1563,12 @@ def _sim_get_cash(strategy: Any) -> float:
1558
1563
  return float(strategy.ctx.cash)
1559
1564
 
1560
1565
 
1566
+ def _sim_get_buying_power(strategy: Any) -> float:
1567
+ if strategy.ctx is None:
1568
+ return 0.0
1569
+ return float(strategy.ctx.buying_power)
1570
+
1571
+
1561
1572
  def _sim_get_open_orders(strategy: Any, symbol: Optional[str] = None) -> List[Any]:
1562
1573
  """获取当前未完成的订单(_sim_ 原语,复制自 get_open_orders,逻辑一字不改)."""
1563
1574
  if strategy.ctx is None:
@@ -567,7 +567,9 @@ impl BacktestResult {
567
567
  push_f64(open_position_count);
568
568
  push_f64(metrics.initial_market_value);
569
569
  push_f64(metrics.end_market_value);
570
- push_f64(t_metrics.gross_pnl);
570
+ // total_pnl 为组合层总盈亏,与文档一致 = end_market_value - initial_market_value
571
+ // (即已实现净盈亏 + 未实现浮动盈亏)。逐笔已实现毛盈亏请用 trade_metrics.gross_pnl。
572
+ push_f64(metrics.end_market_value - metrics.initial_market_value);
571
573
  push_f64(t_metrics.unrealized_pnl);
572
574
  push_f64(metrics.total_return_pct);
573
575
  push_f64(metrics.annualized_return);
@@ -71,6 +71,8 @@ pub struct ContextInit {
71
71
  pub previous_account_maintenance_ratio: f64,
72
72
  pub margin_accrued_interest: f64,
73
73
  pub margin_daily_interest: f64,
74
+ pub instruments: Arc<HashMap<String, Instrument>>,
75
+ pub last_prices: Arc<HashMap<String, Decimal>>,
74
76
  }
75
77
 
76
78
  pub struct ContextUpdate {
@@ -102,6 +104,7 @@ pub struct ContextUpdate {
102
104
  pub previous_account_maintenance_ratio: f64,
103
105
  pub margin_accrued_interest: f64,
104
106
  pub margin_daily_interest: f64,
107
+ pub last_prices: Arc<HashMap<String, Decimal>>,
105
108
  }
106
109
 
107
110
  #[gen_stub_pyclass]
@@ -294,6 +297,7 @@ impl StrategyContext {
294
297
  self.positions = update.positions;
295
298
  self.available_positions = update.available_positions;
296
299
  self.position_entry_prices = update.position_entry_prices;
300
+ self.last_prices = update.last_prices;
297
301
  self.session = update.session;
298
302
  self.current_time = update.current_time;
299
303
  self.active_orders_arc = update.active_orders.clone();
@@ -380,6 +384,10 @@ pub struct StrategyContext {
380
384
  pub active_orders_arc: Arc<Vec<Order>>,
381
385
  pub timers_arc: Arc<RwLock<Vec<Timer>>>,
382
386
 
387
+ // Snapshots for buying-power computation (set at construction / each bar).
388
+ pub instruments: Arc<HashMap<String, Instrument>>,
389
+ pub last_prices: Arc<HashMap<String, Decimal>>,
390
+
383
391
  pub cash: Decimal,
384
392
  pub previous_cash: Decimal,
385
393
  pub positions: Arc<HashMap<String, Decimal>>,
@@ -484,6 +492,8 @@ impl StrategyContext {
484
492
  previous_account_maintenance_ratio: init.previous_account_maintenance_ratio,
485
493
  margin_accrued_interest: init.margin_accrued_interest,
486
494
  margin_daily_interest: init.margin_daily_interest,
495
+ instruments: init.instruments,
496
+ last_prices: init.last_prices,
487
497
  }
488
498
  }
489
499
  }
@@ -589,6 +599,8 @@ impl StrategyContext {
589
599
  previous_account_maintenance_ratio: previous_account_maintenance_ratio.unwrap_or(0.0),
590
600
  margin_accrued_interest: margin_accrued_interest.unwrap_or(0.0),
591
601
  margin_daily_interest: margin_daily_interest.unwrap_or(0.0),
602
+ instruments: Arc::new(HashMap::new()),
603
+ last_prices: Arc::new(HashMap::new()),
592
604
  })
593
605
  }
594
606
 
@@ -676,6 +688,46 @@ impl StrategyContext {
676
688
  self.cash.to_f64().unwrap_or_default()
677
689
  }
678
690
 
691
+ /// 可用买入力:现金 + 本回调及既有挂单的净预期回笼,投影后按风控口径
692
+ /// 计算 free_margin × (1 - safety_margin)。用于在同一 on_bar 内、卖出后
693
+ /// 为买单定量(卖出资金当日可复用)。
694
+ #[getter]
695
+ fn get_buying_power(&self) -> f64 {
696
+ let portfolio = crate::portfolio::Portfolio {
697
+ cash: self.cash,
698
+ positions: self.positions.clone(),
699
+ available_positions: self.available_positions.clone(),
700
+ };
701
+ let mut pending: Vec<Order> =
702
+ Vec::with_capacity(self.active_orders.len() + self.orders.len());
703
+ pending.extend(self.active_orders.iter().cloned());
704
+ pending.extend(self.orders.iter().cloned());
705
+ let projected = crate::risk::common::project_active_orders_into(
706
+ &portfolio,
707
+ &pending,
708
+ &self.last_prices,
709
+ &self.instruments,
710
+ );
711
+ let stock_ratio_override = if self.risk_config.is_margin_account() {
712
+ Some(self.risk_config.stock_initial_margin_ratio())
713
+ } else {
714
+ None
715
+ };
716
+ let free_margin = projected.calculate_free_margin_with_stock_ratio(
717
+ &self.last_prices,
718
+ &self.instruments,
719
+ stock_ratio_override,
720
+ );
721
+ let safety = Decimal::from_f64(self.risk_config.safety_margin).unwrap_or(Decimal::ZERO);
722
+ let factor = (Decimal::ONE - safety).max(Decimal::ZERO);
723
+ free_margin
724
+ .checked_mul(factor)
725
+ .unwrap_or(Decimal::ZERO)
726
+ .max(Decimal::ZERO)
727
+ .to_f64()
728
+ .unwrap_or_default()
729
+ }
730
+
679
731
  #[getter]
680
732
  fn get_previous_cash(&self) -> f64 {
681
733
  self.previous_cash.to_f64().unwrap_or_default()
@@ -765,6 +765,7 @@ impl Engine {
765
765
  .margin_daily_interest
766
766
  .to_f64()
767
767
  .unwrap_or_default(),
768
+ last_prices: Arc::new(self.last_prices.clone()),
768
769
  });
769
770
  }
770
771
  Ok::<_, PyErr>(py_ctx)
@@ -1148,6 +1149,8 @@ impl Engine {
1148
1149
  .unwrap_or_default(),
1149
1150
  margin_accrued_interest: self.margin_accrued_interest.to_f64().unwrap_or_default(),
1150
1151
  margin_daily_interest: self.margin_daily_interest.to_f64().unwrap_or_default(),
1152
+ instruments: Arc::new(self.instruments.clone()),
1153
+ last_prices: Arc::new(self.last_prices.clone()),
1151
1154
  })
1152
1155
  }
1153
1156
 
@@ -49,6 +49,7 @@ mod tests {
49
49
  lot_size: Decimal::from(100),
50
50
  tick_size: Decimal::new(1, 2),
51
51
  expiry_date: None,
52
+ sellable_after_days: 1,
52
53
  }),
53
54
  };
54
55
  engine.add_instrument(instr);
@@ -194,19 +194,31 @@ impl SimulatedExecutionClient {
194
194
  Self::is_same_cycle_close_policy(Self::effective_policy(order, ctx))
195
195
  }
196
196
 
197
- fn has_cross_symbol_reduce_pending(
197
+ /// Whether the order is scheduled to attempt its fill during the current
198
+ /// timestamp. Same-cycle-close orders fill at the close of their creation
199
+ /// bar (created_at == now); next-open orders fill at the open of the first
200
+ /// bar after submission (created_at < now while still active).
201
+ fn fills_current_cycle(&self, order: &Order, ctx: &crate::context::EngineContext) -> bool {
202
+ let policy = Self::effective_policy(order, ctx);
203
+ if Self::is_same_cycle_close_policy(policy) {
204
+ order.created_at == ctx.current_time
205
+ } else {
206
+ order.created_at < ctx.current_time
207
+ }
208
+ }
209
+
210
+ /// A co-submitted (same created_at) cross-symbol reduce/close order that
211
+ /// also fills this cycle — its proceeds should fund `order` before it fills.
212
+ fn has_cosubmitted_cross_symbol_reduce_pending(
198
213
  &self,
199
- event: &Event,
214
+ order: &Order,
200
215
  ctx: &crate::context::EngineContext,
201
216
  ) -> bool {
202
- let Some(event_symbol) = Self::event_symbol(event) else {
203
- return false;
204
- };
205
217
  self.orders.values().any(|candidate| {
206
218
  Self::is_order_active(candidate)
207
- && candidate.created_at == ctx.current_time
208
- && candidate.symbol != event_symbol
209
- && self.is_same_cycle_close_order(candidate, ctx)
219
+ && candidate.symbol != order.symbol
220
+ && candidate.created_at == order.created_at
221
+ && self.fills_current_cycle(candidate, ctx)
210
222
  && crate::model::is_reduce_first_order(candidate.side, candidate.position_effect)
211
223
  })
212
224
  }
@@ -217,7 +229,7 @@ impl SimulatedExecutionClient {
217
229
  event: &Event,
218
230
  ctx: &crate::context::EngineContext,
219
231
  ) -> bool {
220
- if order.created_at != ctx.current_time || !self.is_same_cycle_close_order(order, ctx) {
232
+ if !self.fills_current_cycle(order, ctx) {
221
233
  return false;
222
234
  }
223
235
  if crate::model::is_reduce_first_order(order.side, order.position_effect) {
@@ -226,15 +238,15 @@ impl SimulatedExecutionClient {
226
238
  Self::event_symbol(event)
227
239
  .map(|symbol| order.symbol == symbol)
228
240
  .unwrap_or(false)
229
- && self.has_cross_symbol_reduce_pending(event, ctx)
241
+ && self.has_cosubmitted_cross_symbol_reduce_pending(order, ctx)
230
242
  }
231
243
 
232
244
  fn should_finalize_order(&self, order: &Order, ctx: &crate::context::EngineContext) -> bool {
233
- order.created_at == ctx.current_time
234
- && Self::is_order_active(order)
235
- && self.is_same_cycle_close_order(order, ctx)
236
- && (!self.attempted_same_cycle_order_ids.contains(&order.id)
237
- || self.deferred_same_cycle_order_ids.contains(&order.id))
245
+ Self::is_order_active(order)
246
+ && (self.deferred_same_cycle_order_ids.contains(&order.id)
247
+ || (order.created_at == ctx.current_time
248
+ && self.is_same_cycle_close_order(order, ctx)
249
+ && !self.attempted_same_cycle_order_ids.contains(&order.id)))
238
250
  }
239
251
 
240
252
  fn sorted_queue(&self) -> Vec<String> {
@@ -313,6 +325,21 @@ impl SimulatedExecutionClient {
313
325
  continue;
314
326
  }
315
327
 
328
+ // A next-open (bar_offset>=1) order must not fill on any event at or
329
+ // before its submission timestamp — including a same-timestamp bar of a
330
+ // different symbol processed after the order was queued (e.g. a strategy
331
+ // that submits a cross-symbol order inside another symbol's bar callback).
332
+ // Without this, such an order fills on its own creation-timestamp bar
333
+ // instead of the next one, skewing cross-symbol switch timing (#307).
334
+ let order_policy = Self::effective_policy(&order_snapshot, ctx);
335
+ if order_policy.bar_offset >= 1
336
+ && Self::event_timestamp(event)
337
+ .map(|ts| ts <= order_snapshot.created_at)
338
+ .unwrap_or(false)
339
+ {
340
+ continue;
341
+ }
342
+
316
343
  let defer_current = defer_cross_symbol_increase
317
344
  && self.should_defer_order_on_current_event(&order_snapshot, event, ctx);
318
345
  let mark_attempted = order_snapshot.created_at == ctx.current_time
@@ -794,6 +821,7 @@ mod tests {
794
821
  lot_size: Decimal::from(100),
795
822
  tick_size: Decimal::new(1, 2),
796
823
  expiry_date: None,
824
+ sellable_after_days: 1,
797
825
  }),
798
826
  };
799
827
  map.insert("AAPL".to_string(), aapl);
@@ -1261,6 +1289,7 @@ mod tests {
1261
1289
  lot_size: Decimal::from(100),
1262
1290
  tick_size: Decimal::new(1, 2),
1263
1291
  expiry_date: None,
1292
+ sellable_after_days: 1,
1264
1293
  }),
1265
1294
  },
1266
1295
  );
@@ -1372,6 +1401,7 @@ mod tests {
1372
1401
  lot_size: Decimal::from(100),
1373
1402
  tick_size: Decimal::new(1, 2),
1374
1403
  expiry_date: None,
1404
+ sellable_after_days: 1,
1375
1405
  }),
1376
1406
  },
1377
1407
  );
@@ -46,6 +46,7 @@ mod tests {
46
46
  lot_size: dec!(100),
47
47
  tick_size: dec!(0.01),
48
48
  expiry_date: None,
49
+ sellable_after_days: 1,
49
50
  }),
50
51
  }
51
52
  }