aria-code 0.167.0__py3-none-win_amd64.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 (601) hide show
  1. aria_bots/__init__.py +7 -0
  2. aria_bots/channels/README.md +97 -0
  3. aria_bots/channels/__init__.py +1 -0
  4. aria_bots/channels/approvals.py +263 -0
  5. aria_bots/channels/conversation.py +280 -0
  6. aria_bots/channels/digest.py +186 -0
  7. aria_bots/channels/registry.py +95 -0
  8. aria_bots/engine.py +144 -0
  9. aria_bots/feishu_bot.py +1385 -0
  10. aria_bots/logistics/__init__.py +1 -0
  11. aria_bots/logistics/carriers.py +253 -0
  12. aria_bots/logistics/freight.py +154 -0
  13. aria_bots/logistics/inventory.py +242 -0
  14. aria_bots/logistics/mcp_server.py +156 -0
  15. aria_bots/logistics/records.py +119 -0
  16. aria_bots/logistics/tenancy.py +152 -0
  17. aria_bots/market.py +91 -0
  18. aria_bots/relay_client.py +326 -0
  19. aria_bots/telegram_bot.py +299 -0
  20. aria_code/__init__.py +111 -0
  21. aria_code/_bin/aria-native.exe +0 -0
  22. aria_code/_bin/aria-runtime.exe +0 -0
  23. aria_code/_version.py +20 -0
  24. aria_code/account_memory.py +296 -0
  25. aria_code/account_session.py +166 -0
  26. aria_code/adk_apps/__init__.py +1 -0
  27. aria_code/adk_apps/aria_code_review/__init__.py +1 -0
  28. aria_code/adk_apps/aria_code_review/agent.py +32 -0
  29. aria_code/adk_apps/aria_research/__init__.py +1 -0
  30. aria_code/adk_apps/aria_research/agent.py +31 -0
  31. aria_code/agents/__init__.py +49 -0
  32. aria_code/agents/base.py +329 -0
  33. aria_code/agents/code_review.py +200 -0
  34. aria_code/agents/deep/__init__.py +37 -0
  35. aria_code/agents/deep/calibration_loop.py +144 -0
  36. aria_code/agents/deep/critic.py +125 -0
  37. aria_code/agents/deep/deepen.py +193 -0
  38. aria_code/agents/deep/models.py +149 -0
  39. aria_code/agents/deep/pipeline.py +164 -0
  40. aria_code/agents/deep/quant_fusion.py +192 -0
  41. aria_code/agents/deep/themes.py +95 -0
  42. aria_code/agents/deep/tiers.py +106 -0
  43. aria_code/agents/engineering/__init__.py +14 -0
  44. aria_code/agents/engineering/coder.py +222 -0
  45. aria_code/agents/engineering/tester.py +145 -0
  46. aria_code/agents/financial/__init__.py +21 -0
  47. aria_code/agents/financial/cashflow_burn.py +119 -0
  48. aria_code/agents/financial/catalyst.py +279 -0
  49. aria_code/agents/financial/corporate_finance.py +175 -0
  50. aria_code/agents/financial/debate.py +224 -0
  51. aria_code/agents/financial/earnings.py +315 -0
  52. aria_code/agents/financial/fundamental.py +178 -0
  53. aria_code/agents/financial/macro.py +111 -0
  54. aria_code/agents/financial/news.py +231 -0
  55. aria_code/agents/financial/risk.py +146 -0
  56. aria_code/agents/financial/sector.py +279 -0
  57. aria_code/agents/financial/strategist.py +121 -0
  58. aria_code/agents/financial/stripe_revenue.py +127 -0
  59. aria_code/agents/financial/synthesis.py +274 -0
  60. aria_code/agents/financial/technical.py +277 -0
  61. aria_code/agents/orchestrator.py +44 -0
  62. aria_code/agents/portfolio_agent.py +392 -0
  63. aria_code/agents/realty/__init__.py +62 -0
  64. aria_code/agents/realty/asset_diagnosis.py +152 -0
  65. aria_code/agents/realty/business_match.py +166 -0
  66. aria_code/agents/realty/cashflow_verify.py +209 -0
  67. aria_code/agents/realty/contract_rules.py +210 -0
  68. aria_code/agents/realty/energy_anomaly.py +189 -0
  69. aria_code/agents/realty/exit_settlement.py +208 -0
  70. aria_code/agents/realty/fulfillment_risk.py +206 -0
  71. aria_code/agents/realty/ops_optimize.py +160 -0
  72. aria_code/agents/realty/revenue_share.py +215 -0
  73. aria_code/agents/registry.py +168 -0
  74. aria_code/agents/signal_scheme.py +111 -0
  75. aria_code/agents/sports/__init__.py +0 -0
  76. aria_code/agents/sports/football_agent.py +197 -0
  77. aria_code/agents/supervisor.py +113 -0
  78. aria_code/agents/team.py +500 -0
  79. aria_code/agents/video/__init__.py +16 -0
  80. aria_code/agents/video/director.py +376 -0
  81. aria_code/agents/video/qa_agent.py +143 -0
  82. aria_code/agents/video/script_doctor.py +112 -0
  83. aria_code/agents/warehouse/__init__.py +25 -0
  84. aria_code/agents/warehouse/contracts.py +26 -0
  85. aria_code/agents/warehouse/dashboard.py +155 -0
  86. aria_code/agents/warehouse/fulfillment_leadtime.py +95 -0
  87. aria_code/agents/warehouse/inbound_exceptions.py +25 -0
  88. aria_code/agents/warehouse/inventory_health.py +24 -0
  89. aria_code/agents/warehouse/local_run.py +71 -0
  90. aria_code/agents/warehouse/local_snapshot.py +132 -0
  91. aria_code/agents/warehouse/logistics_cost.py +84 -0
  92. aria_code/agents/warehouse/logistics_sync.py +21 -0
  93. aria_code/agents/warehouse/navigation.schema.json +110 -0
  94. aria_code/agents/warehouse/task_agent.py +172 -0
  95. aria_code/agents/warehouse/workflow.py +31 -0
  96. aria_code/aliyun_data_client.py +4 -0
  97. aria_code/apps/README.md +12 -0
  98. aria_code/apps/__init__.py +2 -0
  99. aria_code/apps/channels/README.md +9 -0
  100. aria_code/apps/channels/__init__.py +17 -0
  101. aria_code/apps/channels/approvals.py +11 -0
  102. aria_code/apps/channels/conversation.py +11 -0
  103. aria_code/apps/channels/digest.py +11 -0
  104. aria_code/apps/channels/intake.py +92 -0
  105. aria_code/apps/channels/registry.py +11 -0
  106. aria_code/apps/channels/tradingview.py +94 -0
  107. aria_code/apps/cli/README.md +13 -0
  108. aria_code/apps/cli/__init__.py +2 -0
  109. aria_code/apps/cli/_optional.py +120 -0
  110. aria_code/apps/cli/app_server.py +656 -0
  111. aria_code/apps/cli/auto_update.py +125 -0
  112. aria_code/apps/cli/bootstrap.py +206 -0
  113. aria_code/apps/cli/broker_render.py +206 -0
  114. aria_code/apps/cli/chat_turn.py +1327 -0
  115. aria_code/apps/cli/cloud_models.py +231 -0
  116. aria_code/apps/cli/codegen_paths.py +29 -0
  117. aria_code/apps/cli/commands/__init__.py +34 -0
  118. aria_code/apps/cli/commands/_business_render.py +78 -0
  119. aria_code/apps/cli/commands/_ui.py +71 -0
  120. aria_code/apps/cli/commands/analysis_cmds.py +378 -0
  121. aria_code/apps/cli/commands/ashare_prediction_cmds.py +327 -0
  122. aria_code/apps/cli/commands/auth_cmds.py +215 -0
  123. aria_code/apps/cli/commands/backtest_cmds.py +2518 -0
  124. aria_code/apps/cli/commands/broker_cmds.py +1236 -0
  125. aria_code/apps/cli/commands/business_workflow_cmds.py +379 -0
  126. aria_code/apps/cli/commands/canvas_cmds.py +77 -0
  127. aria_code/apps/cli/commands/catalog.py +189 -0
  128. aria_code/apps/cli/commands/core_cmds.py +2748 -0
  129. aria_code/apps/cli/commands/data_cmds.py +521 -0
  130. aria_code/apps/cli/commands/diagnostic_cmds.py +285 -0
  131. aria_code/apps/cli/commands/diagnostic_ops_cmds.py +813 -0
  132. aria_code/apps/cli/commands/engineering_cmds.py +399 -0
  133. aria_code/apps/cli/commands/file_cmds.py +312 -0
  134. aria_code/apps/cli/commands/finance_service_cmds.py +60 -0
  135. aria_code/apps/cli/commands/fx_commodity_cmds.py +123 -0
  136. aria_code/apps/cli/commands/market.py +544 -0
  137. aria_code/apps/cli/commands/market_cmds.py +1419 -0
  138. aria_code/apps/cli/commands/market_context.py +432 -0
  139. aria_code/apps/cli/commands/market_render.py +7 -0
  140. aria_code/apps/cli/commands/model_cmds.py +2374 -0
  141. aria_code/apps/cli/commands/ops_cmds.py +721 -0
  142. aria_code/apps/cli/commands/orchestrator_cmds.py +181 -0
  143. aria_code/apps/cli/commands/pdf_export_cmds.py +125 -0
  144. aria_code/apps/cli/commands/portfolio_cmds.py +1316 -0
  145. aria_code/apps/cli/commands/report.py +476 -0
  146. aria_code/apps/cli/commands/scaffold_templates.py +617 -0
  147. aria_code/apps/cli/commands/session_cmds.py +236 -0
  148. aria_code/apps/cli/commands/session_ux_cmds.py +359 -0
  149. aria_code/apps/cli/commands/team.py +723 -0
  150. aria_code/apps/cli/commands/team_render.py +8 -0
  151. aria_code/apps/cli/commands/ui_cmds.py +401 -0
  152. aria_code/apps/cli/commands/warehouse_cmds.py +297 -0
  153. aria_code/apps/cli/commands/workflow_cmds.py +629 -0
  154. aria_code/apps/cli/commands/workspace_cmds.py +1543 -0
  155. aria_code/apps/cli/config_paths.py +73 -0
  156. aria_code/apps/cli/config_store.py +158 -0
  157. aria_code/apps/cli/constants.py +88 -0
  158. aria_code/apps/cli/context.py +34 -0
  159. aria_code/apps/cli/conversation_policy.py +53 -0
  160. aria_code/apps/cli/deterministic.py +200 -0
  161. aria_code/apps/cli/direct.py +48 -0
  162. aria_code/apps/cli/earnings_view.py +172 -0
  163. aria_code/apps/cli/endpoint_migration.py +64 -0
  164. aria_code/apps/cli/exec_events.py +255 -0
  165. aria_code/apps/cli/file_references.py +155 -0
  166. aria_code/apps/cli/finance_service_catalog.py +111 -0
  167. aria_code/apps/cli/football_reports.py +231 -0
  168. aria_code/apps/cli/github_app_auth.py +135 -0
  169. aria_code/apps/cli/google_login.py +239 -0
  170. aria_code/apps/cli/handlers/__init__.py +11 -0
  171. aria_code/apps/cli/handlers/broker_handlers.py +122 -0
  172. aria_code/apps/cli/handlers/chart_handlers.py +1314 -0
  173. aria_code/apps/cli/handlers/market_handlers.py +2570 -0
  174. aria_code/apps/cli/handlers/realty_handlers.py +114 -0
  175. aria_code/apps/cli/handlers/sports_handlers.py +22 -0
  176. aria_code/apps/cli/handlers/strategy_advice.py +82 -0
  177. aria_code/apps/cli/headless.py +352 -0
  178. aria_code/apps/cli/helpers.py +326 -0
  179. aria_code/apps/cli/hooks.py +180 -0
  180. aria_code/apps/cli/i18n.py +310 -0
  181. aria_code/apps/cli/intent.py +136 -0
  182. aria_code/apps/cli/intent_router.py +305 -0
  183. aria_code/apps/cli/intent_shadow.py +72 -0
  184. aria_code/apps/cli/intent_signals.py +347 -0
  185. aria_code/apps/cli/lifecycle_hooks.py +48 -0
  186. aria_code/apps/cli/local_tool_schemas.py +550 -0
  187. aria_code/apps/cli/main.py +39 -0
  188. aria_code/apps/cli/market_hours.py +100 -0
  189. aria_code/apps/cli/market_metadata.py +135 -0
  190. aria_code/apps/cli/market_universe.py +487 -0
  191. aria_code/apps/cli/message_processing.py +310 -0
  192. aria_code/apps/cli/mixin_binding.py +32 -0
  193. aria_code/apps/cli/model_catalog.py +652 -0
  194. aria_code/apps/cli/model_probe.py +169 -0
  195. aria_code/apps/cli/model_retirement.py +65 -0
  196. aria_code/apps/cli/native_branding.py +12 -0
  197. aria_code/apps/cli/native_bridge.py +118 -0
  198. aria_code/apps/cli/native_entry.py +58 -0
  199. aria_code/apps/cli/pdf_report.py +977 -0
  200. aria_code/apps/cli/plan_mode.py +139 -0
  201. aria_code/apps/cli/plotly_html.py +15 -0
  202. aria_code/apps/cli/prediction_feedback.py +202 -0
  203. aria_code/apps/cli/preflight.py +502 -0
  204. aria_code/apps/cli/project_aria.py +60 -0
  205. aria_code/apps/cli/prompt_assembly.py +78 -0
  206. aria_code/apps/cli/prompts/__init__.py +0 -0
  207. aria_code/apps/cli/prompts/coding.py +71 -0
  208. aria_code/apps/cli/prompts/select.py +193 -0
  209. aria_code/apps/cli/prompts/system_prompts.py +562 -0
  210. aria_code/apps/cli/prompts/ui.py +436 -0
  211. aria_code/apps/cli/provider_endpoints.py +237 -0
  212. aria_code/apps/cli/provider_keys.py +73 -0
  213. aria_code/apps/cli/providers/__init__.py +1 -0
  214. aria_code/apps/cli/providers/base.py +775 -0
  215. aria_code/apps/cli/providers/chat_routing.py +139 -0
  216. aria_code/apps/cli/providers/collaboration.py +98 -0
  217. aria_code/apps/cli/providers/llm/__init__.py +1 -0
  218. aria_code/apps/cli/providers/llm/offline_responses.py +68 -0
  219. aria_code/apps/cli/providers/llm/ollama_stream.py +1574 -0
  220. aria_code/apps/cli/providers/llm/response_cache.py +60 -0
  221. aria_code/apps/cli/providers/llm/sse_stream.py +298 -0
  222. aria_code/apps/cli/providers/runtime_bridge.py +586 -0
  223. aria_code/apps/cli/providers/vertexai_stream.py +592 -0
  224. aria_code/apps/cli/release_download.py +159 -0
  225. aria_code/apps/cli/review_runner.py +111 -0
  226. aria_code/apps/cli/runtime_consumer.py +769 -0
  227. aria_code/apps/cli/sandbox.py +32 -0
  228. aria_code/apps/cli/session_export.py +120 -0
  229. aria_code/apps/cli/session_jsonl.py +208 -0
  230. aria_code/apps/cli/session_refresh.py +123 -0
  231. aria_code/apps/cli/session_store.py +125 -0
  232. aria_code/apps/cli/skills_catalog.py +273 -0
  233. aria_code/apps/cli/task_isolation.py +211 -0
  234. aria_code/apps/cli/terminal_chrome.py +412 -0
  235. aria_code/apps/cli/todo_tracker.py +190 -0
  236. aria_code/apps/cli/tool_executor.py +932 -0
  237. aria_code/apps/cli/tool_registry.py +34 -0
  238. aria_code/apps/cli/tool_scope.py +113 -0
  239. aria_code/apps/cli/tools/__init__.py +40 -0
  240. aria_code/apps/cli/tools/context.py +46 -0
  241. aria_code/apps/cli/tools/file_tools.py +181 -0
  242. aria_code/apps/cli/tools/market_tools.py +626 -0
  243. aria_code/apps/cli/tools/notebook_tools.py +111 -0
  244. aria_code/apps/cli/tools/system_tools.py +656 -0
  245. aria_code/apps/cli/tools/write_tools.py +961 -0
  246. aria_code/apps/cli/tradingview_bridge.py +529 -0
  247. aria_code/apps/cli/transactions.py +269 -0
  248. aria_code/apps/cli/turn_planning.py +137 -0
  249. aria_code/apps/cli/update_check.py +257 -0
  250. aria_code/apps/cli/updater.py +373 -0
  251. aria_code/apps/cli/utils/__init__.py +0 -0
  252. aria_code/apps/cli/utils/market_detect.py +1663 -0
  253. aria_code/apps/cli/web_login.py +136 -0
  254. aria_code/apps/cli/workflow_runner.py +127 -0
  255. aria_code/apps/cli/workspace_route.py +121 -0
  256. aria_code/apps/daemon/README.md +14 -0
  257. aria_code/apps/vscode/README.md +115 -0
  258. aria_code/apps/vscode/package.json +70 -0
  259. aria_code/aria_cli.py +5244 -0
  260. aria_code/aria_daemon.py +1372 -0
  261. aria_code/aria_feishu_bot.py +16 -0
  262. aria_code/aria_mcp_server.py +61 -0
  263. aria_code/aria_relay_client.py +4 -0
  264. aria_code/aria_telegram_bot.py +11 -0
  265. aria_code/ariarc.py +385 -0
  266. aria_code/artifacts.py +581 -0
  267. aria_code/backtest_engine.py +4 -0
  268. aria_code/backtest_report.py +4 -0
  269. aria_code/brokers/__init__.py +78 -0
  270. aria_code/brokers/automation.py +193 -0
  271. aria_code/brokers/base.py +231 -0
  272. aria_code/brokers/capabilities.py +264 -0
  273. aria_code/brokers/cn/__init__.py +10 -0
  274. aria_code/brokers/cn/easytrader_broker.py +193 -0
  275. aria_code/brokers/cn/futu_broker.py +194 -0
  276. aria_code/brokers/cn/longbridge_broker.py +190 -0
  277. aria_code/brokers/cn/tiger_broker.py +196 -0
  278. aria_code/brokers/cn/xtquant_broker.py +225 -0
  279. aria_code/brokers/config.py +414 -0
  280. aria_code/brokers/intl/__init__.py +5 -0
  281. aria_code/brokers/intl/alpaca_broker.py +183 -0
  282. aria_code/brokers/intl/ibkr_broker.py +215 -0
  283. aria_code/brokers/intl/trading212_broker.py +183 -0
  284. aria_code/brokers/intl/webull_broker.py +156 -0
  285. aria_code/brokers/paper_broker.py +266 -0
  286. aria_code/brokers/planning.py +296 -0
  287. aria_code/brokers/registry.py +213 -0
  288. aria_code/brokers/trading.py +267 -0
  289. aria_code/canva_client.py +4 -0
  290. aria_code/change_store.py +127 -0
  291. aria_code/clients/__init__.py +0 -0
  292. aria_code/clients/aliyun_data_client.py +660 -0
  293. aria_code/clients/aria_relay_client.py +16 -0
  294. aria_code/clients/canva_client.py +284 -0
  295. aria_code/clients/figma_client.py +100 -0
  296. aria_code/clients/football_data_client.py +1671 -0
  297. aria_code/clients/kling_video_client.py +182 -0
  298. aria_code/clients/market_data_client.py +1985 -0
  299. aria_code/clients/openai_image_client.py +242 -0
  300. aria_code/clients/runway_video_client.py +157 -0
  301. aria_code/clients/warehouse_erp_client.py +105 -0
  302. aria_code/cloud_memory.py +190 -0
  303. aria_code/command_safety.py +19 -0
  304. aria_code/computer_use_server.py +276 -0
  305. aria_code/computer_use_tools.py +4 -0
  306. aria_code/dashboard_generator.py +579 -0
  307. aria_code/data_analysis_tools.py +4 -0
  308. aria_code/data_cleaner.py +483 -0
  309. aria_code/data_service.py +513 -0
  310. aria_code/datasources/__init__.py +23 -0
  311. aria_code/datasources/base.py +166 -0
  312. aria_code/datasources/router.py +253 -0
  313. aria_code/datasources/sec_statements.py +217 -0
  314. aria_code/datasources/sources/__init__.py +15 -0
  315. aria_code/datasources/sources/akshare_source.py +269 -0
  316. aria_code/datasources/sources/alpha_vantage_source.py +203 -0
  317. aria_code/datasources/sources/edgar_source.py +219 -0
  318. aria_code/datasources/sources/finnhub_source.py +198 -0
  319. aria_code/datasources/sources/fred_source.py +223 -0
  320. aria_code/datasources/sources/tushare_source.py +143 -0
  321. aria_code/datasources/sources/web_scraper_source.py +278 -0
  322. aria_code/datasources/sources/world_bank_source.py +206 -0
  323. aria_code/datasources/sources/yfinance_source.py +152 -0
  324. aria_code/doctor.py +860 -0
  325. aria_code/domain/__init__.py +0 -0
  326. aria_code/domain/_finance_core/__init__.py +5 -0
  327. aria_code/domain/_finance_core/backtest_engine.py +325 -0
  328. aria_code/domain/_finance_core/performance_stats.py +101 -0
  329. aria_code/domain/backtest_engine.py +75 -0
  330. aria_code/domain/backtest_report.py +488 -0
  331. aria_code/domain/finance_formulas.py +389 -0
  332. aria_code/domain/performance_stats.py +6 -0
  333. aria_code/domain/portfolio_ledger.py +307 -0
  334. aria_code/domain/strategy_vault.py +421 -0
  335. aria_code/evals/__init__.py +37 -0
  336. aria_code/evals/behavior.py +113 -0
  337. aria_code/evals/gap.py +93 -0
  338. aria_code/evals/harness.py +949 -0
  339. aria_code/evals/review_probe.py +132 -0
  340. aria_code/evals/runner.py +425 -0
  341. aria_code/evals/scorecard.py +322 -0
  342. aria_code/evals/summary.py +125 -0
  343. aria_code/external_agent_runner.py +115 -0
  344. aria_code/figma_client.py +4 -0
  345. aria_code/file_analysis_tools.py +4 -0
  346. aria_code/finance_formulas.py +4 -0
  347. aria_code/football_data_client.py +4 -0
  348. aria_code/image_gen_tools.py +4 -0
  349. aria_code/intent_classifier.py +459 -0
  350. aria_code/kling_video_client.py +4 -0
  351. aria_code/licensing.py +151 -0
  352. aria_code/local_finance_tools.py +4 -0
  353. aria_code/local_image_provider.py +4 -0
  354. aria_code/local_llm_provider.py +4 -0
  355. aria_code/macro_tools.py +4 -0
  356. aria_code/markdown_pdf.py +289 -0
  357. aria_code/market_data_client.py +4 -0
  358. aria_code/mcp_client.py +744 -0
  359. aria_code/memory_manager.py +273 -0
  360. aria_code/model_capability.py +512 -0
  361. aria_code/notification_tools.py +4 -0
  362. aria_code/openai_image_client.py +4 -0
  363. aria_code/packages/__init__.py +26 -0
  364. aria_code/packages/adk_bridge/__init__.py +11 -0
  365. aria_code/packages/adk_bridge/code_review_tools.py +49 -0
  366. aria_code/packages/adk_bridge/market_tools.py +125 -0
  367. aria_code/packages/aria_agents/__init__.py +5 -0
  368. aria_code/packages/aria_agents/manifest.py +78 -0
  369. aria_code/packages/aria_core/__init__.py +34 -0
  370. aria_code/packages/aria_core/architecture.py +269 -0
  371. aria_code/packages/aria_core/export.py +147 -0
  372. aria_code/packages/aria_core/manifest.py +65 -0
  373. aria_code/packages/aria_core/paths.py +57 -0
  374. aria_code/packages/aria_core/secure_file.py +68 -0
  375. aria_code/packages/aria_infra/__init__.py +15 -0
  376. aria_code/packages/aria_infra/arthera.py +58 -0
  377. aria_code/packages/aria_infra/doctor.py +246 -0
  378. aria_code/packages/aria_infra/product.py +40 -0
  379. aria_code/packages/aria_mcp/__init__.py +25 -0
  380. aria_code/packages/aria_mcp/bridge.py +232 -0
  381. aria_code/packages/aria_mcp/circuit.py +82 -0
  382. aria_code/packages/aria_mcp/config.py +162 -0
  383. aria_code/packages/aria_mcp/installer.py +95 -0
  384. aria_code/packages/aria_mcp/server.py +1705 -0
  385. aria_code/packages/aria_mcp/tools.py +81 -0
  386. aria_code/packages/aria_sdk/__init__.py +19 -0
  387. aria_code/packages/aria_sdk/client.py +393 -0
  388. aria_code/packages/aria_sdk/providers.py +70 -0
  389. aria_code/packages/aria_sdk/streaming.py +75 -0
  390. aria_code/packages/aria_sdk/types.py +86 -0
  391. aria_code/packages/aria_services/__init__.py +92 -0
  392. aria_code/packages/aria_services/cache.py +60 -0
  393. aria_code/packages/aria_services/context.py +356 -0
  394. aria_code/packages/aria_services/context_checkpoints.py +157 -0
  395. aria_code/packages/aria_services/data.py +11 -0
  396. aria_code/packages/aria_services/provider_health.py +304 -0
  397. aria_code/packages/aria_services/references.py +247 -0
  398. aria_code/packages/aria_services/registry.py +249 -0
  399. aria_code/packages/aria_services/research_protocol.py +137 -0
  400. aria_code/packages/aria_services/research_quality.py +186 -0
  401. aria_code/packages/aria_services/settings.py +160 -0
  402. aria_code/packages/aria_services/usage.py +151 -0
  403. aria_code/packages/aria_skills/__init__.py +46 -0
  404. aria_code/packages/aria_skills/catalog.py +149 -0
  405. aria_code/packages/aria_skills/loader.py +455 -0
  406. aria_code/packages/aria_skills/registry.py +84 -0
  407. aria_code/packages/aria_tools/__init__.py +5 -0
  408. aria_code/packages/aria_tools/financial/__init__.py +5 -0
  409. aria_code/packages/aria_tools/financial/_paths.py +92 -0
  410. aria_code/packages/aria_tools/registry.py +129 -0
  411. aria_code/packages/quant_engine/__init__.py +33 -0
  412. aria_code/packages/quant_engine/_namespace.py +24 -0
  413. aria_code/packages/quant_engine/backtest/__init__.py +10 -0
  414. aria_code/packages/quant_engine/backtest/core.py +53 -0
  415. aria_code/packages/quant_engine/backtest/engine.py +102 -0
  416. aria_code/packages/quant_engine/portfolio/__init__.py +9 -0
  417. aria_code/packages/quant_engine/portfolio/optimizer.py +85 -0
  418. aria_code/packages/quant_engine/sports/__init__.py +76 -0
  419. aria_code/packages/quant_engine/sports/calibrator.py +354 -0
  420. aria_code/packages/quant_engine/sports/dixon_coles.py +234 -0
  421. aria_code/packages/quant_engine/sports/elo.py +300 -0
  422. aria_code/packages/quant_engine/sports/form.py +188 -0
  423. aria_code/packages/quant_engine/sports/h2h.py +195 -0
  424. aria_code/packages/quant_engine/sports/predictor.py +312 -0
  425. aria_code/packages/quant_engine/sports/tracker.py +665 -0
  426. aria_code/packages/quant_engine/stochastic/__init__.py +31 -0
  427. aria_code/packages/quant_engine/stochastic/gbm_enhanced.py +195 -0
  428. aria_code/packages/quant_engine/stochastic/ito_calculus.py +477 -0
  429. aria_code/packages/quant_engine/stochastic/kelly_criterion.py +181 -0
  430. aria_code/packages/quant_engine/stochastic/monte_carlo_advanced.py +95 -0
  431. aria_code/packages/quant_engine/stochastic/options_pricing.py +576 -0
  432. aria_code/packages/quant_engine/stochastic/stochastic_processes.py +90 -0
  433. aria_code/packs/__init__.py +85 -0
  434. aria_code/packs/base.py +168 -0
  435. aria_code/packs/finance/__init__.py +250 -0
  436. aria_code/packs/healthcare/__init__.py +40 -0
  437. aria_code/packs/logistics/__init__.py +171 -0
  438. aria_code/packs/payments/__init__.py +139 -0
  439. aria_code/packs/realty/__init__.py +190 -0
  440. aria_code/packs/registry.py +202 -0
  441. aria_code/packs/rules.py +90 -0
  442. aria_code/plan_utils.py +194 -0
  443. aria_code/plugin_loader.py +328 -0
  444. aria_code/portfolio_ledger.py +4 -0
  445. aria_code/preview_server.py +449 -0
  446. aria_code/privacy/__init__.py +5 -0
  447. aria_code/privacy/feedback.py +123 -0
  448. aria_code/project_review.py +278 -0
  449. aria_code/project_review_api.py +235 -0
  450. aria_code/project_review_server.py +18 -0
  451. aria_code/project_tools.py +4 -0
  452. aria_code/providers/__init__.py +30 -0
  453. aria_code/providers/google_video_provider.py +256 -0
  454. aria_code/providers/llm/__init__.py +19 -0
  455. aria_code/providers/llm/anthropic.py +184 -0
  456. aria_code/providers/llm/arthera_gateway.py +90 -0
  457. aria_code/providers/llm/autoconfig.py +213 -0
  458. aria_code/providers/llm/base.py +139 -0
  459. aria_code/providers/llm/custom.py +158 -0
  460. aria_code/providers/llm/ollama.py +137 -0
  461. aria_code/providers/llm/openai_compat.py +350 -0
  462. aria_code/providers/llm/registry.py +457 -0
  463. aria_code/providers/local_image_provider.py +202 -0
  464. aria_code/providers/local_llm_provider.py +549 -0
  465. aria_code/providers/ollama_models.py +79 -0
  466. aria_code/providers/openai_params.py +32 -0
  467. aria_code/providers/tool_messages.py +100 -0
  468. aria_code/realty_data_tools.py +4 -0
  469. aria_code/report_exporters.py +150 -0
  470. aria_code/report_generator.py +1764 -0
  471. aria_code/review_service.py +497 -0
  472. aria_code/runtime/__init__.py +176 -0
  473. aria_code/runtime/acceptance.py +632 -0
  474. aria_code/runtime/agent_loop.py +1851 -0
  475. aria_code/runtime/agent_profiles.py +75 -0
  476. aria_code/runtime/approval.py +71 -0
  477. aria_code/runtime/baseline.py +219 -0
  478. aria_code/runtime/budget.py +232 -0
  479. aria_code/runtime/checkpoints.py +481 -0
  480. aria_code/runtime/consult.py +65 -0
  481. aria_code/runtime/contract.py +282 -0
  482. aria_code/runtime/delivery.py +432 -0
  483. aria_code/runtime/events.py +113 -0
  484. aria_code/runtime/gateway.py +167 -0
  485. aria_code/runtime/lsp.py +484 -0
  486. aria_code/runtime/native_index.py +153 -0
  487. aria_code/runtime/orchestrator.py +55 -0
  488. aria_code/runtime/processes.py +343 -0
  489. aria_code/runtime/project_graph.py +614 -0
  490. aria_code/runtime/repo_map.py +712 -0
  491. aria_code/runtime/research_bundle.py +105 -0
  492. aria_code/runtime/review.py +269 -0
  493. aria_code/runtime/run_state.py +127 -0
  494. aria_code/runtime/run_store.py +522 -0
  495. aria_code/runtime/scoped_runs.py +113 -0
  496. aria_code/runtime/self_healing.py +422 -0
  497. aria_code/runtime/semantic_diff.py +171 -0
  498. aria_code/runtime/subagent.py +721 -0
  499. aria_code/runtime/symbol_edit.py +117 -0
  500. aria_code/runtime/task_brief.py +46 -0
  501. aria_code/runtime/task_context.py +145 -0
  502. aria_code/runtime/task_ledger.py +108 -0
  503. aria_code/runtime/task_orchestrator.py +90 -0
  504. aria_code/runtime/task_outcome.py +33 -0
  505. aria_code/runtime/task_verification.py +266 -0
  506. aria_code/runtime/task_worktree.py +448 -0
  507. aria_code/runtime/tool_executor.py +329 -0
  508. aria_code/runtime/tool_policy.py +107 -0
  509. aria_code/runtime/transactions.py +216 -0
  510. aria_code/runtime/windows_job.py +115 -0
  511. aria_code/runtime/workflows.py +222 -0
  512. aria_code/runtime/worktrees.py +215 -0
  513. aria_code/runway_video_client.py +4 -0
  514. aria_code/safety/__init__.py +27 -0
  515. aria_code/safety/client_isolation.py +178 -0
  516. aria_code/safety/permissions.py +339 -0
  517. aria_code/safety/risk.py +699 -0
  518. aria_code/safety/sandbox.py +148 -0
  519. aria_code/safety/service.py +102 -0
  520. aria_code/service_endpoints.py +14 -0
  521. aria_code/setup_wizard.py +684 -0
  522. aria_code/spreadsheet_tools.py +4 -0
  523. aria_code/strategy_vault.py +4 -0
  524. aria_code/tools/__init__.py +0 -0
  525. aria_code/tools/artifact_tools.py +252 -0
  526. aria_code/tools/broker_tools.py +92 -0
  527. aria_code/tools/build_quant_engine.py +97 -0
  528. aria_code/tools/code_audit_tools.py +192 -0
  529. aria_code/tools/computer_use_tools.py +509 -0
  530. aria_code/tools/data_analysis_tools.py +831 -0
  531. aria_code/tools/enterprise_finance_tools.py +202 -0
  532. aria_code/tools/extended_tools.py +240 -0
  533. aria_code/tools/file_analysis_tools.py +880 -0
  534. aria_code/tools/image_gen_tools.py +114 -0
  535. aria_code/tools/local_finance_tools.py +3488 -0
  536. aria_code/tools/logistics_carriers.py +11 -0
  537. aria_code/tools/logistics_inventory.py +11 -0
  538. aria_code/tools/logistics_io.py +11 -0
  539. aria_code/tools/logistics_tenancy.py +11 -0
  540. aria_code/tools/logistics_tools.py +11 -0
  541. aria_code/tools/macro_tools.py +412 -0
  542. aria_code/tools/notification_tools.py +249 -0
  543. aria_code/tools/project_tools.py +525 -0
  544. aria_code/tools/realty_data_tools.py +662 -0
  545. aria_code/tools/spreadsheet_tools.py +399 -0
  546. aria_code/tools/stripe_tools.py +115 -0
  547. aria_code/tools/video_tools.py +500 -0
  548. aria_code/training/__init__.py +1 -0
  549. aria_code/training/compare.py +117 -0
  550. aria_code/training/prelude_commands.py +111 -0
  551. aria_code/training/prelude_eval.py +390 -0
  552. aria_code/training/prelude_real.py +183 -0
  553. aria_code/training/prelude_train.py +248 -0
  554. aria_code/training/sft_dataset.py +230 -0
  555. aria_code/training/trajectory_dataset.py +263 -0
  556. aria_code/ui/__init__.py +105 -0
  557. aria_code/ui/banner.py +404 -0
  558. aria_code/ui/completer.py +571 -0
  559. aria_code/ui/console.py +285 -0
  560. aria_code/ui/input_box.py +505 -0
  561. aria_code/ui/mentions.py +206 -0
  562. aria_code/ui/picker.py +248 -0
  563. aria_code/ui/render/__init__.py +11 -0
  564. aria_code/ui/render/actions.py +297 -0
  565. aria_code/ui/render/finance.py +1732 -0
  566. aria_code/ui/render/market.py +253 -0
  567. aria_code/ui/render/output.py +954 -0
  568. aria_code/ui/render/responsive.py +75 -0
  569. aria_code/ui/render/team.py +367 -0
  570. aria_code/ui/robot.py +239 -0
  571. aria_code/ui/startup_dashboard.py +110 -0
  572. aria_code/video_analysis.py +147 -0
  573. aria_code/video_editor.py +518 -0
  574. aria_code/video_workflow/__init__.py +8 -0
  575. aria_code/video_workflow/__main__.py +61 -0
  576. aria_code/video_workflow/engines/__init__.py +18 -0
  577. aria_code/video_workflow/engines/base.py +69 -0
  578. aria_code/video_workflow/engines/custom_model.py +204 -0
  579. aria_code/video_workflow/engines/google_veo.py +94 -0
  580. aria_code/video_workflow/engines/local_engine.py +71 -0
  581. aria_code/video_workflow/engines/registry.py +98 -0
  582. aria_code/video_workflow/google_models.py +278 -0
  583. aria_code/video_workflow/music/__init__.py +5 -0
  584. aria_code/video_workflow/music/foley_service.py +132 -0
  585. aria_code/video_workflow/music/service.py +212 -0
  586. aria_code/video_workflow/pipeline.py +620 -0
  587. aria_code/video_workflow/plan.py +202 -0
  588. aria_code/video_workflow/session.py +297 -0
  589. aria_code/workspace/__init__.py +6 -0
  590. aria_code/workspace/files.py +219 -0
  591. aria_code/workspace/verify.py +167 -0
  592. aria_code/workspace_changes.py +199 -0
  593. aria_code/workspace_service.py +196 -0
  594. aria_code/workspace_tools.py +150 -0
  595. aria_code-0.167.0.dist-info/METADATA +330 -0
  596. aria_code-0.167.0.dist-info/RECORD +601 -0
  597. aria_code-0.167.0.dist-info/WHEEL +5 -0
  598. aria_code-0.167.0.dist-info/entry_points.txt +5 -0
  599. aria_code-0.167.0.dist-info/licenses/LICENSE +201 -0
  600. aria_code-0.167.0.dist-info/licenses/NOTICE +49 -0
  601. aria_code-0.167.0.dist-info/top_level.txt +2 -0
@@ -0,0 +1,512 @@
1
+ """
2
+ model_capability.py — Aria Code model capability registry & tool-call adapter.
3
+
4
+ Responsibilities:
5
+ - Know which local models support native tool calling vs text-based <tool_call>
6
+ - Normalise tool call output across Ollama-native / XML-tag / JSON-fenced formats
7
+ - Inject the correct tool schema format into the Ollama payload
8
+ - Detect capability dynamically when a model is not in the registry
9
+
10
+ Usage::
11
+
12
+ from aria_code.model_capability import get_model_capability, build_ollama_tool_payload
13
+
14
+ caps = get_model_capability("qwen2.5-coder:7b")
15
+ # {"tool_calls": True, "format": "ollama_native", "context_window": 32768, ...}
16
+
17
+ calls = parse_tool_calls_from_response(full_text, native_tool_calls)
18
+ """
19
+
20
+ from __future__ import annotations
21
+
22
+ import json
23
+ import re
24
+ from dataclasses import dataclass, field
25
+ from typing import Any, Dict, List, Optional, Tuple
26
+
27
+ # ---------------------------------------------------------------------------
28
+ # Capability catalogue
29
+ # ---------------------------------------------------------------------------
30
+
31
+ @dataclass
32
+ class ModelCapability:
33
+ # Whether the model reliably produces structured tool calls
34
+ tool_calls: bool = False
35
+ # "ollama_native" → Ollama's message.tool_calls list
36
+ # "xml_tags" → <tool_call>{"name":…,"arguments":{…}}</tool_call>
37
+ # "json_fence" → ```json\n{"tool":…,"arguments":{…}}\n```
38
+ # "anthropic_native" → tool calling via the Anthropic SDK
39
+ # "openai_native" → tool calling via an OpenAI-compatible / Vertex endpoint
40
+ # (OpenAI, Gemini, Grok) — structured `tool_calls` in the
41
+ # response, not parsed out of the text stream
42
+ # "text_only" → no tool calling; prompt must ask for plain-text answers
43
+ # "router_only" → model is only suitable for intent classification / routing;
44
+ # MUST NOT handle coding, analysis, or multi-step tasks
45
+ format: str = "text_only"
46
+ context_window: int = 8192
47
+ thinking: bool = False # extended-reasoning / <think> tokens
48
+ vision: bool = False # supports image / multimodal input
49
+ finance_tuned: bool = False # model has finance-domain fine-tuning
50
+ # Recommended sampling params
51
+ temperature: float = 0.3
52
+ top_p: float = 0.9
53
+ # Maximum simultaneous tool calls per round (safety limit)
54
+ max_parallel_tools: int = 1
55
+ # Minimum model size class: "nano" <1B / "small" 1-4B / "medium" 4-14B / "large" >14B
56
+ size_class: str = "medium"
57
+ # Extra notes shown in /models list
58
+ notes: str = ""
59
+
60
+
61
+ def is_router_only(cap: "ModelCapability") -> bool:
62
+ """Return True if this model must NOT handle complex tasks (coding/analysis)."""
63
+ return cap.format == "router_only"
64
+
65
+
66
+ def can_handle_coding(cap: "ModelCapability") -> bool:
67
+ """Return True if the model is large/capable enough for code generation tasks."""
68
+ return (
69
+ cap.format in ("ollama_native", "xml_tags", "anthropic_native", "openai_native")
70
+ and cap.context_window >= 8192
71
+ and cap.size_class not in ("nano",)
72
+ )
73
+
74
+
75
+ def can_handle_analysis(cap: "ModelCapability") -> bool:
76
+ """Return True if the model can handle multi-step financial analysis."""
77
+ return (
78
+ cap.format not in ("router_only",)
79
+ and cap.context_window >= 4096
80
+ and cap.size_class not in ("nano",)
81
+ )
82
+
83
+
84
+ # Prefix → capability mapping. Longest prefix wins.
85
+ _CAPABILITY_TABLE: Dict[str, ModelCapability] = {
86
+ # ── Qwen family ────────────────────────────────────────────────────────
87
+ "qwen2.5-coder:32b": ModelCapability(tool_calls=True, format="ollama_native", context_window=131072, temperature=0.2, size_class="large", notes="Best local code+finance model"),
88
+ "qwen2.5-coder:14b": ModelCapability(tool_calls=True, format="ollama_native", context_window=131072, temperature=0.2, size_class="large"),
89
+ "qwen2.5-coder:7b": ModelCapability(tool_calls=True, format="ollama_native", context_window=131072, temperature=0.2, size_class="medium"),
90
+ "qwen2.5-coder:3b": ModelCapability(tool_calls=True, format="ollama_native", context_window=32768, temperature=0.3, size_class="small"),
91
+ # 1.5B — too small for reliable tool calls; use text_only to prevent JSON hallucination
92
+ "qwen2.5-coder:1.5b": ModelCapability(tool_calls=False, format="text_only", context_window=8192, temperature=0.4, size_class="small", notes="1.5B — no tools; simple Q&A only"),
93
+ # 0.5B — nano class; only suitable for routing/classification, never complex tasks
94
+ "qwen2.5-coder:0.5b": ModelCapability(tool_calls=False, format="router_only", context_window=4096, temperature=0.5, size_class="nano", notes="0.5B nano — routing/intent only"),
95
+ "qwen2.5-coder": ModelCapability(tool_calls=True, format="ollama_native", context_window=32768, temperature=0.2, size_class="medium"),
96
+ "qwen2.5:72b": ModelCapability(tool_calls=True, format="ollama_native", context_window=131072, temperature=0.2, notes="Strongest Qwen general model"),
97
+ "qwen2.5:32b": ModelCapability(tool_calls=True, format="ollama_native", context_window=131072, temperature=0.2),
98
+ "qwen2.5:14b": ModelCapability(tool_calls=True, format="ollama_native", context_window=131072, temperature=0.2),
99
+ "qwen2.5:7b": ModelCapability(tool_calls=True, format="ollama_native", context_window=131072, temperature=0.3),
100
+ "qwen2.5": ModelCapability(tool_calls=True, format="ollama_native", context_window=32768, temperature=0.3),
101
+ "qwen3": ModelCapability(tool_calls=True, format="ollama_native", context_window=131072, temperature=0.3, thinking=True),
102
+ "qwq": ModelCapability(tool_calls=True, format="ollama_native", context_window=131072, temperature=0.3, thinking=True, notes="Math/reasoning focused"),
103
+ # ── DeepSeek family ────────────────────────────────────────────────────
104
+ "deepseek-r1:671b": ModelCapability(tool_calls=False, format="xml_tags", context_window=131072, temperature=0.3, thinking=True, notes="State-of-the-art reasoning"),
105
+ "deepseek-r1:70b": ModelCapability(tool_calls=False, format="xml_tags", context_window=131072, temperature=0.3, thinking=True),
106
+ "deepseek-r1:32b": ModelCapability(tool_calls=False, format="xml_tags", context_window=32768, temperature=0.3, thinking=True),
107
+ "deepseek-r1:14b": ModelCapability(tool_calls=False, format="xml_tags", context_window=32768, temperature=0.3, thinking=True),
108
+ "deepseek-r1:8b": ModelCapability(tool_calls=False, format="xml_tags", context_window=32768, temperature=0.3, thinking=True),
109
+ "deepseek-r1:7b": ModelCapability(tool_calls=False, format="xml_tags", context_window=32768, temperature=0.3, thinking=True),
110
+ "deepseek-r1": ModelCapability(tool_calls=False, format="xml_tags", context_window=32768, temperature=0.3, thinking=True),
111
+ "deepseek-v3.1": ModelCapability(tool_calls=True, format="ollama_native", context_window=163840, temperature=0.3, thinking=True, notes="DeepSeek V3.1 671B"),
112
+ "deepseek-v3": ModelCapability(tool_calls=True, format="ollama_native", context_window=131072, temperature=0.3),
113
+ "deepseek-v2.5": ModelCapability(tool_calls=True, format="ollama_native", context_window=65536, temperature=0.3),
114
+ "deepseek-coder-v2": ModelCapability(tool_calls=True, format="ollama_native", context_window=65536, temperature=0.2),
115
+ # DeepSeek's own API (api.deepseek.com). Current names are deepseek-flash and
116
+ # deepseek-v4-pro; deepseek-v4-flash is a legacy alias still accepted. Third-party
117
+ # listings give these 1M tokens; the official pages do not state it, so the window
118
+ # here is a conservative 128K (an underestimate only means earlier compaction).
119
+ "deepseek-v4": ModelCapability(tool_calls=True, format="openai_native", context_window=131072, temperature=0.3, size_class="large"),
120
+ "deepseek-flash": ModelCapability(tool_calls=True, format="openai_native", context_window=131072, temperature=0.3, size_class="medium"),
121
+ # ── LLaMA family ───────────────────────────────────────────────────────
122
+ "llama3.3:70b": ModelCapability(tool_calls=True, format="ollama_native", context_window=131072, temperature=0.3, notes="Meta flagship 2024"),
123
+ "llama3.2:90b": ModelCapability(tool_calls=True, format="ollama_native", context_window=131072, temperature=0.3, vision=True, notes="Multimodal, image+text"),
124
+ "llama3.2:11b": ModelCapability(tool_calls=True, format="ollama_native", context_window=131072, temperature=0.3, vision=True, notes="Multimodal, image+text"),
125
+ "llama3.2:3b": ModelCapability(tool_calls=True, format="ollama_native", context_window=131072, temperature=0.3),
126
+ "llama3.2": ModelCapability(tool_calls=True, format="ollama_native", context_window=131072, temperature=0.3),
127
+ "llama3.1:405b": ModelCapability(tool_calls=True, format="ollama_native", context_window=131072, temperature=0.3),
128
+ "llama3.1:70b": ModelCapability(tool_calls=True, format="ollama_native", context_window=131072, temperature=0.3),
129
+ "llama3.1:8b": ModelCapability(tool_calls=True, format="ollama_native", context_window=131072, temperature=0.3),
130
+ "llama3.1": ModelCapability(tool_calls=True, format="ollama_native", context_window=131072, temperature=0.3),
131
+ "llama3": ModelCapability(tool_calls=False, format="text_only", context_window=8192, temperature=0.3),
132
+ # ── Mistral family ─────────────────────────────────────────────────────
133
+ "mistral-nemo": ModelCapability(tool_calls=True, format="ollama_native", context_window=131072, temperature=0.3),
134
+ "mistral-large": ModelCapability(tool_calls=True, format="ollama_native", context_window=131072, temperature=0.3),
135
+ "mistral-small": ModelCapability(tool_calls=True, format="ollama_native", context_window=32768, temperature=0.3),
136
+ "mistral:7b": ModelCapability(tool_calls=True, format="ollama_native", context_window=32768, temperature=0.3),
137
+ "mistral": ModelCapability(tool_calls=True, format="ollama_native", context_window=32768, temperature=0.3),
138
+ "mixtral": ModelCapability(tool_calls=True, format="ollama_native", context_window=32768, temperature=0.3),
139
+ # ── Phi family ─────────────────────────────────────────────────────────
140
+ "phi4:14b": ModelCapability(tool_calls=True, format="ollama_native", context_window=16384, temperature=0.3, notes="Microsoft Phi4, compact+capable"),
141
+ "phi4": ModelCapability(tool_calls=True, format="ollama_native", context_window=16384, temperature=0.3),
142
+ "phi3.5": ModelCapability(tool_calls=True, format="ollama_native", context_window=16384, temperature=0.3),
143
+ "phi3": ModelCapability(tool_calls=False, format="text_only", context_window=8192, temperature=0.3),
144
+ # ── Google Gemma ───────────────────────────────────────────────────────
145
+ "gemma3:27b": ModelCapability(tool_calls=True, format="ollama_native", context_window=131072, temperature=0.3, vision=True),
146
+ "gemma3:12b": ModelCapability(tool_calls=True, format="ollama_native", context_window=131072, temperature=0.3, vision=True),
147
+ "gemma3:4b": ModelCapability(tool_calls=True, format="ollama_native", context_window=131072, temperature=0.3, vision=True),
148
+ "gemma3": ModelCapability(tool_calls=True, format="ollama_native", context_window=131072, temperature=0.3, vision=True),
149
+ "gemma2": ModelCapability(tool_calls=False, format="text_only", context_window=8192, temperature=0.3),
150
+ # ── Vision / multimodal models ─────────────────────────────────────────────
151
+ "llava:34b": ModelCapability(tool_calls=False, format="text_only", context_window=4096, temperature=0.3, vision=True, notes="LLaVA 34B vision-language"),
152
+ "llava:13b": ModelCapability(tool_calls=False, format="text_only", context_window=4096, temperature=0.3, vision=True),
153
+ "llava:7b": ModelCapability(tool_calls=False, format="text_only", context_window=4096, temperature=0.3, vision=True),
154
+ "llava": ModelCapability(tool_calls=False, format="text_only", context_window=4096, temperature=0.3, vision=True),
155
+ "bakllava": ModelCapability(tool_calls=False, format="text_only", context_window=4096, temperature=0.3, vision=True),
156
+ "moondream": ModelCapability(tool_calls=False, format="text_only", context_window=2048, temperature=0.3, vision=True, size_class="small", notes="Tiny vision model"),
157
+ "minicpm-v": ModelCapability(tool_calls=False, format="text_only", context_window=8192, temperature=0.3, vision=True, size_class="small"),
158
+ "qwen2-vl:72b": ModelCapability(tool_calls=True, format="ollama_native", context_window=131072, temperature=0.3, vision=True, notes="Qwen2-VL 72B multimodal"),
159
+ "qwen2-vl:7b": ModelCapability(tool_calls=True, format="ollama_native", context_window=32768, temperature=0.3, vision=True),
160
+ "qwen2-vl": ModelCapability(tool_calls=True, format="ollama_native", context_window=32768, temperature=0.3, vision=True),
161
+ "qwen2.5vl:72b": ModelCapability(tool_calls=True, format="ollama_native", context_window=131072, temperature=0.3, vision=True, notes="Qwen2.5-VL 72B"),
162
+ "qwen2.5vl:7b": ModelCapability(tool_calls=True, format="ollama_native", context_window=32768, temperature=0.3, vision=True),
163
+ "qwen2.5vl": ModelCapability(tool_calls=True, format="ollama_native", context_window=32768, temperature=0.3, vision=True),
164
+ # ── Finance-specific ───────────────────────────────────────────────────
165
+ "finma": ModelCapability(tool_calls=False, format="text_only", context_window=4096, temperature=0.3, finance_tuned=True),
166
+ "fingpt": ModelCapability(tool_calls=False, format="text_only", context_window=4096, temperature=0.3, finance_tuned=True),
167
+ "bloomberggpt": ModelCapability(tool_calls=False, format="text_only", context_window=2048, temperature=0.2, finance_tuned=True),
168
+ # ── Aria own models ────────────────────────────────────────────────────
169
+ # aria-sonata-3b: primary local production model — 3B, good for finance Q&A + tool calls
170
+ "aria-sonata-3b": ModelCapability(tool_calls=False, format="xml_tags", context_window=16384, temperature=0.3, size_class="small", finance_tuned=True, notes="3B local production model"),
171
+ # aria-sonata 1.x/0.5B series — GGUF Ollama models; xml_tags for text-based tool parsing
172
+ "aria-sonata:4.5-thinking": ModelCapability(tool_calls=False, format="xml_tags", context_window=8192, temperature=0.3, size_class="small", thinking=True, finance_tuned=True),
173
+ "aria-sonata:4.5-verbose": ModelCapability(tool_calls=False, format="xml_tags", context_window=8192, temperature=0.3, size_class="small", finance_tuned=True),
174
+ "aria-sonata:4.6-thinking": ModelCapability(tool_calls=False, format="xml_tags", context_window=8192, temperature=0.3, size_class="small", thinking=True, finance_tuned=True),
175
+ "aria-sonata": ModelCapability(tool_calls=False, format="xml_tags", context_window=8192, temperature=0.3, size_class="small", finance_tuned=True),
176
+ # aria-prelude: nano router model — ONLY for intent classification and routing
177
+ "aria-prelude": ModelCapability(tool_calls=False, format="router_only", context_window=4096, temperature=0.2, size_class="nano", finance_tuned=True, notes="Nano router — intent classification only"),
178
+ # ── Anthropic Claude (cloud API via providers/llm/anthropic.py) ───────
179
+ # format="anthropic_native" → tool calling via Anthropic SDK, not Ollama
180
+ # All Claude 3+ models share 200K context and native vision support.
181
+ "claude-opus-4-8": ModelCapability(tool_calls=True, format="anthropic_native", context_window=200000, temperature=0.3, size_class="large", vision=True, thinking=True, notes="Claude Opus 4.8 — most capable"),
182
+ "claude-opus-4": ModelCapability(tool_calls=True, format="anthropic_native", context_window=200000, temperature=0.3, size_class="large", vision=True, thinking=True),
183
+ "claude-sonnet-4-6": ModelCapability(tool_calls=True, format="anthropic_native", context_window=200000, temperature=0.3, size_class="large", vision=True),
184
+ "claude-sonnet-4": ModelCapability(tool_calls=True, format="anthropic_native", context_window=200000, temperature=0.3, size_class="large", vision=True),
185
+ "claude-haiku-4-5": ModelCapability(tool_calls=True, format="anthropic_native", context_window=200000, temperature=0.3, size_class="medium", vision=True, notes="Claude Haiku 4.5 — fast/cheap"),
186
+ "claude-haiku-4": ModelCapability(tool_calls=True, format="anthropic_native", context_window=200000, temperature=0.3, size_class="medium", vision=True),
187
+ # Claude 3.x legacy — still widely used
188
+ "claude-3-7-sonnet": ModelCapability(tool_calls=True, format="anthropic_native", context_window=200000, temperature=0.3, size_class="large", vision=True, thinking=True),
189
+ "claude-3-5-sonnet": ModelCapability(tool_calls=True, format="anthropic_native", context_window=200000, temperature=0.3, size_class="large", vision=True),
190
+ "claude-3-5-haiku": ModelCapability(tool_calls=True, format="anthropic_native", context_window=200000, temperature=0.3, size_class="medium", vision=True),
191
+ "claude-3-opus": ModelCapability(tool_calls=True, format="anthropic_native", context_window=200000, temperature=0.3, size_class="large", vision=True, thinking=True),
192
+ "claude-3-sonnet": ModelCapability(tool_calls=True, format="anthropic_native", context_window=200000, temperature=0.3, size_class="large", vision=True),
193
+ "claude-3-haiku": ModelCapability(tool_calls=True, format="anthropic_native", context_window=200000, temperature=0.3, size_class="medium", vision=True),
194
+ # Generic prefix catch-all for future Claude versions (longest-prefix matching ensures
195
+ # specific entries above still win over this fallback)
196
+ "claude": ModelCapability(tool_calls=True, format="anthropic_native", context_window=200000, temperature=0.3, size_class="large", vision=True),
197
+ # ── Arthera cloud-routed models (large, run via cloud API) ────────────
198
+ "gpt-oss:120b": ModelCapability(tool_calls=True, format="ollama_native", context_window=131072, temperature=0.3, thinking=True, notes="GPT-OSS 120B via Ollama Cloud"),
199
+ "gpt-oss": ModelCapability(tool_calls=True, format="ollama_native", context_window=131072, temperature=0.3, thinking=True, notes="GPT-OSS via Ollama Cloud"),
200
+ "deepseek-v3.1:671b-cloud": ModelCapability(tool_calls=True, format="ollama_native", context_window=163840, temperature=0.3, thinking=True, notes="DeepSeek V3.1 671B via Ollama Cloud"),
201
+ # ── Google Gemini (cloud, via apps/cli/providers/vertexai_stream.py) ──
202
+ # Registered here as well as in the MODELS catalogue: callers such as the
203
+ # tool-routing check in aria_cli use get_model_capability() directly, and a
204
+ # missing entry silently degrades the model to text_only / 4K context.
205
+ "gemini-4-argon": ModelCapability(tool_calls=True, format="openai_native", context_window=1048576, temperature=0.2, size_class="large", vision=True, thinking=True, notes="Gemini 4 Argon — flagship, 2026-10 GA (context per third-party reports)"),
206
+ "gemini-3.6-flash": ModelCapability(tool_calls=True, format="openai_native", context_window=1048576, temperature=0.2, size_class="large", vision=True, thinking=True, notes="Gemini 3.6 Flash — token-efficient"),
207
+ "gemini-3.1-pro-preview": ModelCapability(tool_calls=True, format="openai_native", context_window=1048576, temperature=0.2, size_class="large", vision=True, thinking=True, notes="Gemini 3.1 Pro (preview) — 1M context"),
208
+ "gemini-3.8-flash": ModelCapability(tool_calls=True, format="openai_native", context_window=1048576, temperature=0.2, size_class="large", vision=True, thinking=True, notes="Gemini 3.8 Flash — 1M context (default)"),
209
+ "gemini-3.5-flash-lite": ModelCapability(tool_calls=True, format="openai_native", context_window=1048576, temperature=0.2, size_class="medium", vision=True, notes="Gemini 3.5 Flash-Lite — 1M context"),
210
+ "gemini-3.5-flash": ModelCapability(tool_calls=True, format="openai_native", context_window=1048576, temperature=0.2, size_class="large", vision=True, thinking=True, notes="Gemini 3.5 Flash — 1M context; deprecated by Google 2026-10-08"),
211
+ "gemini-3.1-flash-lite": ModelCapability(tool_calls=True, format="openai_native", context_window=1048576, temperature=0.2, size_class="medium", vision=True, notes="Gemini 3.1 Flash-Lite — 1M context"),
212
+ # Retired by Google (model_retirement.py migrates configs that name them).
213
+ "gemini-2.5-pro": ModelCapability(tool_calls=True, format="openai_native", context_window=1048576, temperature=0.2, size_class="large", vision=True, thinking=True, notes="Gemini 2.5 Pro — 1M context"),
214
+ "gemini-2.5-flash": ModelCapability(tool_calls=True, format="openai_native", context_window=1048576, temperature=0.2, size_class="medium", vision=True, notes="Gemini 2.5 Flash — 1M context"),
215
+ "gemini-2.0-flash": ModelCapability(tool_calls=True, format="openai_native", context_window=1048576, temperature=0.2, size_class="medium", vision=True),
216
+ "gemini-1.5-pro": ModelCapability(tool_calls=True, format="openai_native", context_window=2097152, temperature=0.2, size_class="large", vision=True),
217
+ "gemini-1.5-flash": ModelCapability(tool_calls=True, format="openai_native", context_window=1048576, temperature=0.2, size_class="medium", vision=True),
218
+ "gemini": ModelCapability(tool_calls=True, format="openai_native", context_window=1048576, temperature=0.2, size_class="large", vision=True),
219
+ # Gemma served on Vertex AI (Model Garden, managed): "gemma-4-…-maas",
220
+ # "gemma-3-…". These used to match nothing and fell to the default — no
221
+ # tools, a 4K window — so a coding task on Gemma was refused as a
222
+ # tool-less route. Ollama's "gemma3:27b" ids keep their own entries above.
223
+ "gemma-4": ModelCapability(tool_calls=True, format="openai_native", context_window=131072, temperature=0.2, size_class="medium", vision=True, notes="Gemma 4 on Vertex AI"),
224
+ "gemma-3": ModelCapability(tool_calls=True, format="openai_native", context_window=131072, temperature=0.2, size_class="medium", vision=True, notes="Gemma 3 on Vertex AI"),
225
+ # ── OpenAI (cloud, via providers/llm/openai_compat.py) ────────────────
226
+ "gpt-5": ModelCapability(tool_calls=True, format="openai_native", context_window=400000, temperature=0.2, size_class="large", vision=True, thinking=True),
227
+ "gpt-4.1": ModelCapability(tool_calls=True, format="openai_native", context_window=1047576, temperature=0.2, size_class="large", vision=True),
228
+ "gpt-4o-mini": ModelCapability(tool_calls=True, format="openai_native", context_window=128000, temperature=0.2, size_class="medium", vision=True),
229
+ "gpt-4o": ModelCapability(tool_calls=True, format="openai_native", context_window=128000, temperature=0.2, size_class="large", vision=True),
230
+ "gpt-4-turbo": ModelCapability(tool_calls=True, format="openai_native", context_window=128000, temperature=0.2, size_class="large", vision=True),
231
+ "gpt-4": ModelCapability(tool_calls=True, format="openai_native", context_window=8192, temperature=0.2, size_class="large"),
232
+ "o4-mini": ModelCapability(tool_calls=True, format="openai_native", context_window=200000, temperature=1.0, size_class="medium", thinking=True),
233
+ "o3-mini": ModelCapability(tool_calls=True, format="openai_native", context_window=200000, temperature=1.0, size_class="medium", thinking=True),
234
+ "o3": ModelCapability(tool_calls=True, format="openai_native", context_window=200000, temperature=1.0, size_class="large", thinking=True),
235
+ "o1": ModelCapability(tool_calls=True, format="openai_native", context_window=200000, temperature=1.0, size_class="large", thinking=True),
236
+ # NVIDIA Nemotron 3 Super: https://research.nvidia.com/labs/nemotron/Nemotron-3-Super/
237
+ "nemotron-3-super-120b-a12b": ModelCapability(
238
+ tool_calls=True, format="openai_native", context_window=1048576,
239
+ temperature=0.2, size_class="large", thinking=True,
240
+ notes="NVIDIA Nemotron 3 Super; OpenAI-compatible tools verified on Nebius",
241
+ ),
242
+ # ── xAI Grok (cloud, OpenAI-compatible endpoint) ──────────────────────
243
+ "grok-4": ModelCapability(tool_calls=True, format="openai_native", context_window=256000, temperature=0.3, size_class="large", vision=True),
244
+ "grok": ModelCapability(tool_calls=True, format="openai_native", context_window=131072, temperature=0.3, size_class="large"),
245
+ }
246
+
247
+ # Provider-qualified ids ("google/gemini-2.5-pro", "openai/gpt-4o") are stripped
248
+ # down to the bare model name before prefix matching. The CLI stores the fully
249
+ # qualified id in its config, so without this every cloud model looked unknown.
250
+ _VENDOR_PREFIXES = (
251
+ "google/", "openai/", "anthropic/", "x-ai/", "xai/", "meta-llama/",
252
+ "mistralai/", "deepseek/", "qwen/", "alibaba/", "vertex_ai/", "vertexai/",
253
+ "azure/", "bedrock/", "openrouter/", "together/", "groq/", "nvidia/",
254
+ )
255
+
256
+ # Default fallback when model is unknown. Deliberately conservative: guessing
257
+ # tool support wrong breaks every turn. ``UNKNOWN_MODEL_NOTE`` lets callers
258
+ # detect this case and warn the user instead of degrading in silence.
259
+ UNKNOWN_MODEL_NOTE = "Unknown model — conservative settings applied"
260
+
261
+ _DEFAULT_CAPABILITY = ModelCapability(
262
+ tool_calls=False, format="text_only", context_window=4096, temperature=0.5,
263
+ notes=UNKNOWN_MODEL_NOTE,
264
+ )
265
+
266
+
267
+ def is_unknown_model(cap: "ModelCapability") -> bool:
268
+ """Return True if *cap* is the unregistered-model fallback.
269
+
270
+ A model that is missing from the registry runs without tools and with a 4K
271
+ context budget. For a cloud model that is a severe, invisible downgrade —
272
+ it cannot read files and the context gauge is computed against the wrong
273
+ denominator — so callers should surface it rather than absorb it.
274
+ """
275
+ return cap.notes == UNKNOWN_MODEL_NOTE
276
+
277
+
278
+ def strip_vendor_prefix(model_name: str) -> str:
279
+ """Strip a provider prefix ("google/gemini-2.5-pro" → "gemini-2.5-pro")."""
280
+ name = (model_name or "").strip().lower()
281
+ for prefix in _VENDOR_PREFIXES:
282
+ if name.startswith(prefix):
283
+ return name[len(prefix):]
284
+ return name
285
+
286
+
287
+ def get_model_capability(model_name: str) -> ModelCapability:
288
+ """
289
+ Return capability for *model_name* using longest-prefix matching.
290
+
291
+ Provider-qualified ids are normalised first, so the fully qualified id the
292
+ CLI stores in its config resolves to the same entry as the bare name.
293
+
294
+ Examples::
295
+
296
+ get_model_capability("qwen2.5-coder:7b-instruct-q4_K_M")
297
+ # → same as "qwen2.5-coder:7b" entry
298
+
299
+ get_model_capability("google/gemini-2.5-pro")
300
+ # → same as "gemini-2.5-pro" entry
301
+ """
302
+ name = strip_vendor_prefix(model_name)
303
+ # Strip GGUF quantisation suffixes like :q4_k_m, :f16, etc.
304
+ clean = re.sub(r":[qfQ][0-9].*$", "", name)
305
+ # Also strip common instruct/chat/gguf tags appended after the size
306
+ clean = re.sub(r"-(instruct|chat|gguf|base|it)$", "", clean)
307
+ # Cloud ids carry a dated or "-latest" suffix ("gemini-2.5-pro-preview-06-05",
308
+ # "claude-3-5-sonnet-20241022") that must not defeat prefix matching.
309
+ clean = re.sub(r"-(latest|preview|exp)(-[0-9-]+)?$", "", clean)
310
+
311
+ best_prefix = ""
312
+ best_cap = _DEFAULT_CAPABILITY
313
+ for prefix, cap in _CAPABILITY_TABLE.items():
314
+ if clean.startswith(prefix.lower()) and len(prefix) > len(best_prefix):
315
+ best_prefix = prefix
316
+ best_cap = cap
317
+
318
+ return best_cap
319
+
320
+
321
+ # ---------------------------------------------------------------------------
322
+ # Tool schema injection helpers
323
+ # ---------------------------------------------------------------------------
324
+
325
+ def build_ollama_tool_payload(
326
+ tools_schema: List[Dict],
327
+ model_name: str,
328
+ ) -> Optional[List[Dict]]:
329
+ """
330
+ Return the `tools` field for an Ollama /api/chat request, or None when the
331
+ model does not support native tool calling.
332
+
333
+ When format == "ollama_native" the schema is passed as-is.
334
+ When format == "xml_tags" we skip the field and rely on prompt injection.
335
+ """
336
+ cap = get_model_capability(model_name)
337
+ if not cap.tool_calls or cap.format != "ollama_native":
338
+ return None
339
+ return tools_schema
340
+
341
+
342
+ def build_tool_system_prompt(
343
+ tools_schema: List[Dict],
344
+ model_name: str,
345
+ ) -> str:
346
+ """
347
+ For models that do NOT support native tool calls (xml_tags / text_only),
348
+ return a system-prompt block that instructs the model to emit
349
+ ``<tool_call>{"name":…,"arguments":{…}}</tool_call>`` tags.
350
+ """
351
+ cap = get_model_capability(model_name)
352
+ if cap.tool_calls and cap.format == "ollama_native":
353
+ return "" # handled by native API
354
+
355
+ tool_list = []
356
+ for t in tools_schema:
357
+ fn = t.get("function", t)
358
+ params = fn.get("parameters", {}).get("properties", {})
359
+ required = fn.get("parameters", {}).get("required", [])
360
+ param_str = ", ".join(
361
+ f"{k}: {v.get('type','any')}{'*' if k in required else ''}"
362
+ for k, v in params.items()
363
+ )
364
+ tool_list.append(f" - {fn['name']}({param_str}): {fn.get('description','')}")
365
+
366
+ tools_block = "\n".join(tool_list)
367
+ return (
368
+ "\n\n## Available Tools\n\n"
369
+ "When you need to call a tool, output EXACTLY this format (nothing else on the line):\n\n"
370
+ '<tool_call>{"name": "tool_name", "arguments": {"param": "value"}}</tool_call>\n\n'
371
+ "Tools available:\n"
372
+ f"{tools_block}\n\n"
373
+ "Rules:\n"
374
+ "1. Call ONE tool at a time. Wait for the result before calling the next.\n"
375
+ "2. After receiving a tool result, continue your analysis or call another tool.\n"
376
+ "3. When done with all tools, write your final answer in plain text.\n"
377
+ "4. Never make up tool results — always call the tool.\n"
378
+ )
379
+
380
+
381
+ # ---------------------------------------------------------------------------
382
+ # Tool call parsers
383
+ # ---------------------------------------------------------------------------
384
+
385
+ def parse_tool_calls_from_response(
386
+ text: str,
387
+ native_calls: Optional[List[Dict]] = None,
388
+ model_name: str = "",
389
+ ) -> List[Dict[str, Any]]:
390
+ """
391
+ Unified parser. Returns list of {"tool": str, "params": dict}.
392
+
393
+ Priority:
394
+ 1. native_calls (Ollama tool_calls list) — most reliable
395
+ 2. XML tags <tool_call>…</tool_call>
396
+ 3. JSON code fences ```json … ```
397
+ 4. Raw JSON object containing "name"/"arguments" keys
398
+ """
399
+ # 1. Native Ollama tool calls
400
+ if native_calls:
401
+ result = []
402
+ for tc in native_calls:
403
+ fn = tc.get("function", tc)
404
+ name = fn.get("name", "")
405
+ args = fn.get("arguments", {})
406
+ if isinstance(args, str):
407
+ try:
408
+ args = json.loads(args)
409
+ except json.JSONDecodeError:
410
+ args = {}
411
+ if name:
412
+ result.append({"tool": name, "params": args})
413
+ if result:
414
+ return result
415
+
416
+ if not text:
417
+ return []
418
+
419
+ results: List[Dict[str, Any]] = []
420
+
421
+ # 2. XML tag format: <tool_call>…</tool_call>
422
+ xml_pattern = re.compile(
423
+ r"<tool_call>\s*(.*?)\s*</tool_call>", re.DOTALL | re.IGNORECASE
424
+ )
425
+ for m in xml_pattern.finditer(text):
426
+ tc = _try_parse_json(m.group(1))
427
+ if tc:
428
+ results.append(_normalise_call(tc))
429
+
430
+ if results:
431
+ return results
432
+
433
+ # 3. JSON fence: ```json … ``` or ``` … ```
434
+ fence_pattern = re.compile(
435
+ r"```(?:json)?\s*(\{.*?\})\s*```", re.DOTALL | re.IGNORECASE
436
+ )
437
+ for m in fence_pattern.finditer(text):
438
+ tc = _try_parse_json(m.group(1))
439
+ if tc and ("name" in tc or "tool" in tc):
440
+ results.append(_normalise_call(tc))
441
+
442
+ if results:
443
+ return results
444
+
445
+ # 4. Bare JSON object anywhere in text
446
+ json_pattern = re.compile(r"\{[^{}]*\"(?:name|tool)\"[^{}]*\}", re.DOTALL)
447
+ for m in json_pattern.finditer(text):
448
+ tc = _try_parse_json(m.group(0))
449
+ if tc and ("name" in tc or "tool" in tc):
450
+ results.append(_normalise_call(tc))
451
+
452
+ return results
453
+
454
+
455
+ def _try_parse_json(s: str) -> Optional[Dict]:
456
+ try:
457
+ return json.loads(s.strip())
458
+ except (json.JSONDecodeError, TypeError):
459
+ return None
460
+
461
+
462
+ def _normalise_call(tc: Dict) -> Dict[str, Any]:
463
+ """Normalise various key naming conventions → {"tool": …, "params": …}."""
464
+ name = tc.get("name") or tc.get("tool") or tc.get("function", {}).get("name", "")
465
+ args = (
466
+ tc.get("arguments")
467
+ or tc.get("params")
468
+ or tc.get("parameters")
469
+ or tc.get("function", {}).get("arguments", {})
470
+ or {}
471
+ )
472
+ if isinstance(args, str):
473
+ args = _try_parse_json(args) or {}
474
+ return {"tool": name, "params": args}
475
+
476
+
477
+ # ---------------------------------------------------------------------------
478
+ # Recommended local models for finance work
479
+ # ---------------------------------------------------------------------------
480
+
481
+ RECOMMENDED_FINANCE_MODELS: List[Dict[str, str]] = [
482
+ {
483
+ "model": "qwen2.5-coder:7b",
484
+ "reason": "Best balance of tool calling + code generation for finance scripts",
485
+ "install": "ollama pull qwen2.5-coder:7b",
486
+ "vram_gb": "5",
487
+ },
488
+ {
489
+ "model": "qwen2.5:14b",
490
+ "reason": "Strong quantitative reasoning, multi-turn strategy analysis",
491
+ "install": "ollama pull qwen2.5:14b",
492
+ "vram_gb": "10",
493
+ },
494
+ {
495
+ "model": "deepseek-r1:14b",
496
+ "reason": "Deep reasoning for complex factor models (slow but thorough)",
497
+ "install": "ollama pull deepseek-r1:14b",
498
+ "vram_gb": "10",
499
+ },
500
+ {
501
+ "model": "llama3.2:3b",
502
+ "reason": "Ultra-fast for quick quotes and simple questions",
503
+ "install": "ollama pull llama3.2:3b",
504
+ "vram_gb": "2",
505
+ },
506
+ {
507
+ "model": "phi4:14b",
508
+ "reason": "Math-strong, good for Greeks / derivative pricing",
509
+ "install": "ollama pull phi4",
510
+ "vram_gb": "9",
511
+ },
512
+ ]
@@ -0,0 +1,4 @@
1
+ """Compatibility import for :mod:`tools.notification_tools`."""
2
+ from importlib import import_module as _import_module
3
+ import sys as _sys
4
+ _sys.modules[__name__] = _import_module("tools.notification_tools")
@@ -0,0 +1,4 @@
1
+ """Compatibility import for :mod:`clients.openai_image_client`."""
2
+ from importlib import import_module as _import_module
3
+ import sys as _sys
4
+ _sys.modules[__name__] = _import_module("clients.openai_image_client")
@@ -0,0 +1,26 @@
1
+ """Aria Code package facade layer.
2
+
3
+ This namespace is intentionally thin. It exposes stable package boundaries
4
+ without forcing the existing single-file CLI to move all implementation code at
5
+ once.
6
+ """
7
+
8
+ # Installed modules are authoritative. A legacy private source bridge requires
9
+ # an explicit opt-in; nearby checkouts must never change import resolution.
10
+ import os as _os
11
+ from pathlib import Path as _Path
12
+
13
+ _configured_root = _os.getenv("ARTHERA_ROOT", "").strip()
14
+ if _configured_root:
15
+ _external = _Path(_configured_root).expanduser() / "packages"
16
+ if _external.is_dir() and str(_external) not in __path__:
17
+ __path__.append(str(_external))
18
+
19
+ __all__ = [
20
+ "aria_agents",
21
+ "aria_core",
22
+ "aria_infra",
23
+ "aria_mcp",
24
+ "aria_skills",
25
+ "aria_tools",
26
+ ]
@@ -0,0 +1,11 @@
1
+ """Safe integration points between Aria Code services and Google ADK.
2
+
3
+ The bridge deliberately exports only read-only, bounded market-data tools.
4
+ Trading, broker credentials, shell access, and filesystem mutation stay outside
5
+ the ADK tool surface and continue to be governed by Aria's existing runtime.
6
+ """
7
+
8
+ from .code_review_tools import CodeReviewTools
9
+ from .market_tools import MarketResearchTools
10
+
11
+ __all__ = ["CodeReviewTools", "MarketResearchTools"]
@@ -0,0 +1,49 @@
1
+ """Read-only code-review tool surface for Google ADK."""
2
+
3
+ from __future__ import annotations
4
+
5
+ from pathlib import PurePath
6
+ from typing import Any, Dict
7
+
8
+
9
+ class CodeReviewTools:
10
+ """Review submitted source text without filesystem or shell capabilities."""
11
+
12
+ def review_code(self, source: str, filename: str = "snippet.py", language: str = "python") -> Dict[str, Any]:
13
+ """Return deterministic review findings for caller-provided code only.
14
+
15
+ Args:
16
+ source: Source code pasted by the user. File paths are never read.
17
+ filename: Display name used to infer language; directory components are ignored.
18
+ language: Source language, currently with additional syntax checks for Python.
19
+ """
20
+ # 惰性导入:agents/__init__.py 会连带拉起 registry 和各 financial agent,
21
+ # 122 个模块、numpy 在内,约 260ms。放在模块级会让 packages.adk_bridge 整体
22
+ # 变重,也会让 agents/ 侧的任何导入故障连累 MarketResearchTools——两个工具面
23
+ # 本该互不影响。market_tools.py 对 DataService 用的是同一套惰性做法。
24
+ from agents.code_review import CodeReviewAgent
25
+
26
+ if not isinstance(source, str) or not source.strip():
27
+ return {"success": False, "error": "Non-empty source text is required."}
28
+ if len(source) > CodeReviewAgent.MAX_SOURCE_CHARS:
29
+ return {
30
+ "success": False,
31
+ "error": f"Source exceeds the {CodeReviewAgent.MAX_SOURCE_CHARS}-character review limit; split it by file.",
32
+ }
33
+
34
+ safe_filename = PurePath(str(filename or "snippet.py")).name[:160] or "snippet.py"
35
+ findings = CodeReviewAgent.review_source(source, filename=safe_filename, language=str(language or "python"))
36
+ counts = {severity: 0 for severity in ("critical", "high", "medium", "low")}
37
+ for finding in findings:
38
+ counts[finding.severity] += 1
39
+ return {
40
+ "success": True,
41
+ "filename": safe_filename,
42
+ "language": str(language or "python")[:32],
43
+ "findings": [finding.to_dict() for finding in findings],
44
+ "counts": counts,
45
+ "limitations": [
46
+ "Static checks only; it did not read a file, execute code, run tests, or inspect dependencies.",
47
+ "Review findings are not a security certification.",
48
+ ],
49
+ }