iatoolkit 2.45.0__tar.gz → 2.45.2__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 (253) hide show
  1. {iatoolkit-2.45.0/src/iatoolkit.egg-info → iatoolkit-2.45.2}/PKG-INFO +1 -1
  2. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/__init__.py +1 -1
  3. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/infra/llm_providers/openai_compatible_chat_adapter.py +69 -7
  4. iatoolkit-2.45.2/src/iatoolkit/infra/llm_providers/openrouter_adapter.py +155 -0
  5. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/infra/llm_response.py +4 -0
  6. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/llm_client_service.py +55 -3
  7. {iatoolkit-2.45.0 → iatoolkit-2.45.2/src/iatoolkit.egg-info}/PKG-INFO +1 -1
  8. iatoolkit-2.45.0/src/iatoolkit/infra/llm_providers/openrouter_adapter.py +0 -100
  9. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/LICENSE +0 -0
  10. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/LICENSE_COMMUNITY.md +0 -0
  11. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/pyproject.toml +0 -0
  12. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/readme.md +0 -0
  13. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/requirements.txt +0 -0
  14. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/setup.cfg +0 -0
  15. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/base_company.py +0 -0
  16. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/cli_commands.py +0 -0
  17. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/common/__init__.py +0 -0
  18. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/common/bridge_validation.py +0 -0
  19. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/common/exceptions.py +0 -0
  20. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/common/interfaces/__init__.py +0 -0
  21. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/common/interfaces/asset_storage.py +0 -0
  22. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/common/interfaces/database_provider.py +0 -0
  23. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/common/interfaces/memory_compilation_trigger.py +0 -0
  24. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/common/interfaces/memory_lint_trigger.py +0 -0
  25. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/common/interfaces/secret_provider.py +0 -0
  26. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/common/interfaces/signup_policy_resolver.py +0 -0
  27. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/common/interfaces/web_search_provider.py +0 -0
  28. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/common/model_registry.py +0 -0
  29. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/common/routes.py +0 -0
  30. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/common/secret_resolver.py +0 -0
  31. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/common/session_manager.py +0 -0
  32. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/common/util.py +0 -0
  33. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/company_registry.py +0 -0
  34. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/config/__init__.py +0 -0
  35. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/config/llm_capabilities.yaml +0 -0
  36. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/config/system_prompts/channel_business_identity.prompt +0 -0
  37. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/config/system_prompts/channel_conversation_continuity.prompt +0 -0
  38. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/config/system_prompts/channel_response_style.prompt +0 -0
  39. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/config/system_prompts/chat_state_rules.prompt +0 -0
  40. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/config/system_prompts/chat_user_profile.prompt +0 -0
  41. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/config/system_prompts/core_identity.prompt +0 -0
  42. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/config/system_prompts/email_output.prompt +0 -0
  43. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/config/system_prompts/file_download_output.prompt +0 -0
  44. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/config/system_prompts/format_styles.prompt +0 -0
  45. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/config/system_prompts/html_structures.prompt +0 -0
  46. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/config/system_prompts/links_documents.prompt +0 -0
  47. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/config/system_prompts/memory_usage.prompt +0 -0
  48. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/config/system_prompts/multimodal_basics.prompt +0 -0
  49. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/config/system_prompts/output_basics.prompt +0 -0
  50. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/config/system_prompts/presentation_formatting.prompt +0 -0
  51. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/config/system_prompts/query_main.prompt +0 -0
  52. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/config/system_prompts/sql_aggregation_scope.prompt +0 -0
  53. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/config/system_prompts/sql_casting.prompt +0 -0
  54. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/config/system_prompts/sql_core.prompt +0 -0
  55. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/config/system_prompts/sql_jsonb.prompt +0 -0
  56. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/config/system_prompts/sql_mysql_casting.prompt +0 -0
  57. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/config/system_prompts/sql_mysql_json.prompt +0 -0
  58. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/config/system_prompts/sql_redshift_basics.prompt +0 -0
  59. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/config/system_prompts/sql_redshift_types.prompt +0 -0
  60. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/config/system_prompts/sql_rules.prompt +0 -0
  61. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/config/system_prompts/tool_html_passthrough.prompt +0 -0
  62. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/config/system_prompts_pack.yaml +0 -0
  63. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/config/system_tools_pack.yaml +0 -0
  64. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/core.py +0 -0
  65. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/infra/__init__.py +0 -0
  66. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/infra/brevo_mail_app.py +0 -0
  67. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/infra/call_service.py +0 -0
  68. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/infra/connectors/__init__.py +0 -0
  69. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/infra/connectors/file_connector.py +0 -0
  70. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/infra/connectors/file_connector_factory.py +0 -0
  71. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/infra/connectors/google_cloud_storage_connector.py +0 -0
  72. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/infra/connectors/google_drive_connector.py +0 -0
  73. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/infra/connectors/local_file_connector.py +0 -0
  74. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/infra/connectors/s3_connector.py +0 -0
  75. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/infra/google_auth_client.py +0 -0
  76. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/infra/google_chat_app.py +0 -0
  77. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/infra/inference_embeddings_client.py +0 -0
  78. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/infra/inference_handler.py +0 -0
  79. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/infra/jina_embeddings_client.py +0 -0
  80. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/infra/llm_gateway_resolver.py +0 -0
  81. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/infra/llm_providers/__init__.py +0 -0
  82. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/infra/llm_providers/anthropic_adapter.py +0 -0
  83. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/infra/llm_providers/deepseek_adapter.py +0 -0
  84. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/infra/llm_providers/gemini_adapter.py +0 -0
  85. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/infra/llm_providers/openai_adapter.py +0 -0
  86. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/infra/llm_proxy.py +0 -0
  87. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/infra/redis_session_manager.py +0 -0
  88. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/locales/en.yaml +0 -0
  89. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/locales/es.yaml +0 -0
  90. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/repositories/__init__.py +0 -0
  91. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/repositories/api_key_repo.py +0 -0
  92. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/repositories/bridge_repo.py +0 -0
  93. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/repositories/database_manager.py +0 -0
  94. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/repositories/document_repo.py +0 -0
  95. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/repositories/env_secret_provider.py +0 -0
  96. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/repositories/filesystem_asset_repository.py +0 -0
  97. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/repositories/knowledge_wiki_repo.py +0 -0
  98. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/repositories/llm_query_repo.py +0 -0
  99. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/repositories/mcp_token_repo.py +0 -0
  100. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/repositories/memory_repo.py +0 -0
  101. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/repositories/models.py +0 -0
  102. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/repositories/profile_repo.py +0 -0
  103. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/repositories/prompt_resource_repo.py +0 -0
  104. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/repositories/sql_dataset_repo.py +0 -0
  105. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/repositories/sql_source_repo.py +0 -0
  106. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/repositories/vs_repo.py +0 -0
  107. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/runtime_logging.py +0 -0
  108. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/__init__.py +0 -0
  109. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/api_key_service.py +0 -0
  110. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/attachment_policy_service.py +0 -0
  111. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/auth_service.py +0 -0
  112. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/benchmark_service.py +0 -0
  113. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/branding_service.py +0 -0
  114. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/company_context_service.py +0 -0
  115. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/configuration_service.py +0 -0
  116. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/context_builder_service.py +0 -0
  117. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/dispatcher_service.py +0 -0
  118. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/embedding_service.py +0 -0
  119. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/excel_service.py +0 -0
  120. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/file_processor_service.py +0 -0
  121. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/history_manager_service.py +0 -0
  122. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/http_tool_service.py +0 -0
  123. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/i18n_service.py +0 -0
  124. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/inference_service.py +0 -0
  125. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/jwt_service.py +0 -0
  126. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/knowledge_base_service.py +0 -0
  127. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/language_service.py +0 -0
  128. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/license_service.py +0 -0
  129. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/mail_service.py +0 -0
  130. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/markdown_wiki_service.py +0 -0
  131. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/mcp_token_service.py +0 -0
  132. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/memory_compiler_service.py +0 -0
  133. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/memory_lint_service.py +0 -0
  134. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/memory_lookup_policy_service.py +0 -0
  135. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/memory_service.py +0 -0
  136. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/memory_wiki_service.py +0 -0
  137. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/noop_memory_compilation_trigger.py +0 -0
  138. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/noop_memory_lint_trigger.py +0 -0
  139. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/operator_identity_service.py +0 -0
  140. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/parsers/__init__.py +0 -0
  141. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/parsers/contracts.py +0 -0
  142. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/parsers/image_normalizer.py +0 -0
  143. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/parsers/parsing_service.py +0 -0
  144. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/parsers/pdf_ocr_detection.py +0 -0
  145. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/parsers/provider_factory.py +0 -0
  146. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/parsers/provider_resolver.py +0 -0
  147. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/parsers/providers/__init__.py +0 -0
  148. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/parsers/providers/basic_provider.py +0 -0
  149. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/parsers/providers/docling_provider.py +0 -0
  150. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/parsers/validator.py +0 -0
  151. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/pdf_service.py +0 -0
  152. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/profile_service.py +0 -0
  153. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/prompt_resource_service.py +0 -0
  154. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/prompt_service.py +0 -0
  155. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/query_service.py +0 -0
  156. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/signup_policy_resolver.py +0 -0
  157. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/sql_dataset_service.py +0 -0
  158. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/sql_service.py +0 -0
  159. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/sql_source_service.py +0 -0
  160. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/storage_service.py +0 -0
  161. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/structured_output_service.py +0 -0
  162. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/system_prompt_catalog.py +0 -0
  163. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/system_tools.py +0 -0
  164. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/telemetry_service.py +0 -0
  165. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/tenant_wiki_service.py +0 -0
  166. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/tool_output_contract.py +0 -0
  167. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/tool_service.py +0 -0
  168. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/user_feedback_service.py +0 -0
  169. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/user_session_context_service.py +0 -0
  170. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/visual_kb_service.py +0 -0
  171. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/visual_tool_service.py +0 -0
  172. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/warmup_service.py +0 -0
  173. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/web_search/__init__.py +0 -0
  174. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/web_search/provider_factory.py +0 -0
  175. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/web_search/providers/__init__.py +0 -0
  176. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/web_search/providers/brave_provider.py +0 -0
  177. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/services/web_search_service.py +0 -0
  178. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/static/images/fernando.jpeg +0 -0
  179. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/static/images/iatoolkit_core.png +0 -0
  180. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/static/images/iatoolkit_logo.png +0 -0
  181. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/static/js/chat_feedback_button.js +0 -0
  182. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/static/js/chat_filepond.js +0 -0
  183. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/static/js/chat_help_content.js +0 -0
  184. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/static/js/chat_history_button.js +0 -0
  185. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/static/js/chat_logout_button.js +0 -0
  186. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/static/js/chat_main.js +0 -0
  187. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/static/js/chat_memory_button.js +0 -0
  188. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/static/js/chat_model_selector.js +0 -0
  189. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/static/js/chat_onboarding_button.js +0 -0
  190. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/static/js/chat_prompt_manager.js +0 -0
  191. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/static/js/chat_reload_button.js +0 -0
  192. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/static/styles/chat_iatoolkit.css +0 -0
  193. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/static/styles/chat_modal.css +0 -0
  194. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/static/styles/chat_public.css +0 -0
  195. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/static/styles/documents.css +0 -0
  196. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/static/styles/landing_page.css +0 -0
  197. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/static/styles/llm_output.css +0 -0
  198. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/static/styles/onboarding.css +0 -0
  199. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/templates/_company_header.html +0 -0
  200. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/templates/_login_widget.html +0 -0
  201. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/templates/account.html +0 -0
  202. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/templates/base.html +0 -0
  203. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/templates/change_password.html +0 -0
  204. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/templates/chat.html +0 -0
  205. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/templates/chat_memory_modal.html +0 -0
  206. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/templates/chat_modals.html +0 -0
  207. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/templates/error.html +0 -0
  208. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/templates/forgot_password.html +0 -0
  209. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/templates/home_hosted_default.html +0 -0
  210. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/templates/memory/wiki_schema.md +0 -0
  211. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/templates/onboarding_shell.html +0 -0
  212. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/templates/pdf/base.html +0 -0
  213. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/templates/pdf/letter.html +0 -0
  214. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/templates/pdf/report.html +0 -0
  215. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/templates/pdf/simple.html +0 -0
  216. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/templates/signup.html +0 -0
  217. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/views/__init__.py +0 -0
  218. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/views/account_view.py +0 -0
  219. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/views/api_key_api_view.py +0 -0
  220. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/views/base_login_view.py +0 -0
  221. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/views/categories_api_view.py +0 -0
  222. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/views/change_password_view.py +0 -0
  223. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/views/chat_context_preview_api_view.py +0 -0
  224. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/views/chat_view.py +0 -0
  225. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/views/configuration_api_view.py +0 -0
  226. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/views/connectors_api_view.py +0 -0
  227. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/views/embedding_api_view.py +0 -0
  228. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/views/forgot_password_view.py +0 -0
  229. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/views/help_content_api_view.py +0 -0
  230. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/views/history_api_view.py +0 -0
  231. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/views/home_view.py +0 -0
  232. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/views/init_context_api_view.py +0 -0
  233. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/views/llmquery_api_view.py +0 -0
  234. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/views/load_document_api_view.py +0 -0
  235. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/views/login_view.py +0 -0
  236. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/views/logout_api_view.py +0 -0
  237. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/views/memory_api_view.py +0 -0
  238. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/views/profile_api_view.py +0 -0
  239. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/views/prompt_api_view.py +0 -0
  240. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/views/prompt_context_preview_api_view.py +0 -0
  241. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/views/prompt_resource_api_view.py +0 -0
  242. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/views/rag_api_view.py +0 -0
  243. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/views/root_redirect_view.py +0 -0
  244. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/views/signup_view.py +0 -0
  245. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/views/static_page_view.py +0 -0
  246. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/views/tool_api_view.py +0 -0
  247. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/views/user_feedback_api_view.py +0 -0
  248. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/views/users_api_view.py +0 -0
  249. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit/views/verify_user_view.py +0 -0
  250. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit.egg-info/SOURCES.txt +0 -0
  251. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit.egg-info/dependency_links.txt +0 -0
  252. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit.egg-info/requires.txt +0 -0
  253. {iatoolkit-2.45.0 → iatoolkit-2.45.2}/src/iatoolkit.egg-info/top_level.txt +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: iatoolkit
3
- Version: 2.45.0
3
+ Version: 2.45.2
4
4
  Summary: IAToolkit
5
5
  Author: Fernando Libedinsky
6
6
  License-Expression: MIT
@@ -3,7 +3,7 @@
3
3
  #
4
4
  # IAToolkit is open source software.
5
5
 
6
- __version__ = "2.45.0"
6
+ __version__ = "2.45.2"
7
7
 
8
8
  # Expose main classes and functions at the top level of the package
9
9
 
@@ -43,6 +43,8 @@ class OpenAICompatibleChatAdapter:
43
43
  #: what DeepseekAdapter does.
44
44
  supports_reasoning_effort = False
45
45
  supports_reasoning_content_messages = False
46
+ supports_reasoning_details_messages = False
47
+ reasoning_content_message_field = "reasoning_content"
46
48
  supports_metadata = False
47
49
  supports_parallel_tool_calls = False
48
50
  supports_thinking = False
@@ -375,10 +377,11 @@ class OpenAICompatibleChatAdapter:
375
377
  message["tool_calls"] = tool_calls
376
378
  seen_tool_call_ids.update(self._extract_tool_call_ids(tool_calls))
377
379
 
378
- if self.supports_reasoning_content_messages:
379
- reasoning_content = str(item.get("reasoning_content") or "").strip()
380
- if reasoning_content:
381
- message["reasoning_content"] = reasoning_content
380
+ self._attach_reasoning_to_message(
381
+ message,
382
+ reasoning_content=item.get("reasoning_content"),
383
+ reasoning_details=item.get("reasoning_details"),
384
+ )
382
385
 
383
386
  tool_call_id = str(item.get("tool_call_id") or "").strip()
384
387
  if role == "tool" and tool_call_id:
@@ -677,7 +680,7 @@ class OpenAICompatibleChatAdapter:
677
680
  total_tokens=getattr(getattr(response, "usage", None), "total_tokens", 0) or 0,
678
681
  )
679
682
 
680
- reasoning_content = getattr(message, "reasoning_content", "") or ""
683
+ reasoning_content, reasoning_details = self._extract_reasoning_from_message(message)
681
684
 
682
685
  tool_calls_out: List[ToolCall] = []
683
686
  content_parts: List[Dict] = []
@@ -701,6 +704,7 @@ class OpenAICompatibleChatAdapter:
701
704
  message=message,
702
705
  normalized_tool_calls=normalized_tool_calls,
703
706
  reasoning_content=reasoning_content,
707
+ reasoning_details=reasoning_details,
704
708
  )
705
709
 
706
710
  for tc in tool_calls:
@@ -738,7 +742,9 @@ class OpenAICompatibleChatAdapter:
738
742
  output=tool_calls_out,
739
743
  usage=usage,
740
744
  reasoning_content=reasoning_content,
745
+ reasoning_details=reasoning_details,
741
746
  content_parts=content_parts,
747
+ provider_metadata=self._extract_provider_metadata(response),
742
748
  )
743
749
 
744
750
  # Backward-compatible alias retained while the old DeepSeek-specific name
@@ -752,6 +758,7 @@ class OpenAICompatibleChatAdapter:
752
758
  message: Any,
753
759
  normalized_tool_calls: List[Dict[str, Any]],
754
760
  reasoning_content: str,
761
+ reasoning_details: Any = None,
755
762
  ) -> None:
756
763
  if not normalized_tool_calls:
757
764
  return
@@ -761,8 +768,11 @@ class OpenAICompatibleChatAdapter:
761
768
  "content": getattr(message, "content", "") or "",
762
769
  "tool_calls": normalized_tool_calls,
763
770
  }
764
- if self.supports_reasoning_content_messages and reasoning_content:
765
- assistant_message["reasoning_content"] = reasoning_content
771
+ self._attach_reasoning_to_message(
772
+ assistant_message,
773
+ reasoning_content=reasoning_content,
774
+ reasoning_details=reasoning_details,
775
+ )
766
776
 
767
777
  group_id = str(getattr(response, "id", "") or normalized_tool_calls[0]["id"]).strip()
768
778
  pending_entry = {
@@ -774,3 +784,55 @@ class OpenAICompatibleChatAdapter:
774
784
  with self._pending_assistant_tool_messages_lock:
775
785
  for tool_call in normalized_tool_calls:
776
786
  self._pending_assistant_tool_messages[tool_call["id"]] = pending_entry
787
+
788
+ def _extract_reasoning_from_message(self, message: Any) -> tuple[str, Any]:
789
+ reasoning_content = self._coerce_optional_text(
790
+ self._get_message_value(message, "reasoning_content")
791
+ )
792
+ reasoning_details = self._get_message_value(message, "reasoning_details")
793
+
794
+ if not reasoning_content:
795
+ reasoning_content = self._coerce_optional_text(
796
+ self._get_message_value(message, "reasoning")
797
+ )
798
+
799
+ return reasoning_content, reasoning_details
800
+
801
+ def _attach_reasoning_to_message(
802
+ self,
803
+ message: Dict[str, Any],
804
+ reasoning_content: Any = None,
805
+ reasoning_details: Any = None,
806
+ ) -> None:
807
+ if self.supports_reasoning_details_messages and reasoning_details:
808
+ message["reasoning_details"] = reasoning_details
809
+ return
810
+
811
+ if not self.supports_reasoning_content_messages:
812
+ return
813
+
814
+ normalized_reasoning = self._coerce_optional_text(reasoning_content)
815
+ if normalized_reasoning:
816
+ message[self.reasoning_content_message_field] = normalized_reasoning
817
+
818
+ @staticmethod
819
+ def _get_message_value(message: Any, key: str) -> Any:
820
+ if isinstance(message, dict):
821
+ return message.get(key)
822
+
823
+ value = getattr(message, key, None)
824
+ if type(value).__module__.startswith("unittest.mock"):
825
+ return None
826
+ return value
827
+
828
+ @staticmethod
829
+ def _coerce_optional_text(value: Any) -> str:
830
+ if value is None:
831
+ return ""
832
+ if type(value).__module__.startswith("unittest.mock"):
833
+ return ""
834
+ return str(value or "").strip()
835
+
836
+ def _extract_provider_metadata(self, response: Any) -> Dict[str, Any]:
837
+ _ = response
838
+ return {}
@@ -0,0 +1,155 @@
1
+ # Copyright (c) 2024 Fernando Libedinsky
2
+ # Product: IAToolkit
3
+ #
4
+ # IAToolkit is open source software.
5
+
6
+ from typing import Any, Dict
7
+
8
+ from iatoolkit.infra.llm_providers.openai_compatible_chat_adapter import OpenAICompatibleChatAdapter
9
+
10
+
11
+ class OpenRouterAdapter(OpenAICompatibleChatAdapter):
12
+ """OpenRouter-specific adapter built on top of the shared chat.completions core."""
13
+
14
+ supports_multimodal = True
15
+ supports_reasoning = False
16
+ supports_reasoning_content_messages = True
17
+ supports_reasoning_details_messages = True
18
+ reasoning_content_message_field = "reasoning"
19
+ supports_metadata = True
20
+ supports_parallel_tool_calls = True
21
+
22
+ def __init__(self, openrouter_client):
23
+ super().__init__(openai_compatible_client=openrouter_client, provider_label="OpenRouter")
24
+
25
+ def _extend_call_kwargs(self, call_kwargs: Dict[str, Any], kwargs: Dict[str, Any]) -> None:
26
+ text = kwargs.get("text") or {}
27
+ verbosity = text.get("verbosity") if isinstance(text, dict) else None
28
+ if verbosity:
29
+ call_kwargs["verbosity"] = verbosity
30
+
31
+ passthrough_keys = (
32
+ "service_tier",
33
+ "temperature",
34
+ "top_p",
35
+ "max_tokens",
36
+ "max_completion_tokens",
37
+ "seed",
38
+ "stop",
39
+ "stream",
40
+ "stream_options",
41
+ "modalities",
42
+ "user",
43
+ )
44
+ for key in passthrough_keys:
45
+ if kwargs.get(key) is not None:
46
+ call_kwargs[key] = kwargs.get(key)
47
+
48
+ extra_body = dict(call_kwargs.get("extra_body") or {})
49
+
50
+ reasoning_payload = self._build_reasoning_payload(kwargs.get("reasoning"), kwargs)
51
+ if reasoning_payload:
52
+ extra_body["reasoning"] = reasoning_payload
53
+
54
+ vendor_specific_keys = (
55
+ "models",
56
+ "provider",
57
+ "plugins",
58
+ "session_id",
59
+ )
60
+ for key in vendor_specific_keys:
61
+ if kwargs.get(key) is not None:
62
+ extra_body[key] = kwargs.get(key)
63
+
64
+ if extra_body:
65
+ call_kwargs["extra_body"] = extra_body
66
+
67
+ def _extract_provider_metadata(self, response: Any) -> Dict[str, Any]:
68
+ raw_metadata = self._get_message_value(response, "openrouter_metadata")
69
+ metadata = self._normalize_metadata_object(raw_metadata)
70
+
71
+ provider_name = self._extract_provider_name(metadata)
72
+ if not provider_name:
73
+ provider_name = self._coerce_optional_text(
74
+ self._get_message_value(response, "provider_name")
75
+ )
76
+
77
+ provider_metadata: Dict[str, Any] = {"provider": "openrouter"}
78
+ if provider_name:
79
+ provider_metadata["provider_name"] = provider_name
80
+ if metadata:
81
+ provider_metadata["openrouter"] = metadata
82
+
83
+ return provider_metadata
84
+
85
+ @classmethod
86
+ def _extract_provider_name(cls, metadata: Dict[str, Any]) -> str:
87
+ for key in ("provider_name", "provider", "upstream_provider", "selected_provider"):
88
+ value = metadata.get(key)
89
+ if isinstance(value, dict):
90
+ nested = cls._extract_provider_name(value)
91
+ if nested:
92
+ return nested
93
+ normalized = cls._coerce_optional_text(value)
94
+ if normalized:
95
+ return normalized
96
+
97
+ for value in metadata.values():
98
+ if isinstance(value, dict):
99
+ nested = cls._extract_provider_name(value)
100
+ if nested:
101
+ return nested
102
+
103
+ return ""
104
+
105
+ @classmethod
106
+ def _normalize_metadata_object(cls, value: Any) -> Dict[str, Any]:
107
+ if value is None or type(value).__module__.startswith("unittest.mock"):
108
+ return {}
109
+
110
+ if isinstance(value, dict):
111
+ return cls._sanitize_metadata_dict(value)
112
+
113
+ model_dump = getattr(value, "model_dump", None)
114
+ if callable(model_dump):
115
+ try:
116
+ dumped = model_dump()
117
+ if isinstance(dumped, dict):
118
+ return cls._sanitize_metadata_dict(dumped)
119
+ except Exception:
120
+ return {}
121
+
122
+ raw_dict = getattr(value, "__dict__", None)
123
+ if isinstance(raw_dict, dict):
124
+ return cls._sanitize_metadata_dict({
125
+ key: item
126
+ for key, item in raw_dict.items()
127
+ if not key.startswith("_") and not callable(item)
128
+ })
129
+
130
+ return {}
131
+
132
+ @classmethod
133
+ def _sanitize_metadata_dict(cls, metadata: Dict[str, Any]) -> Dict[str, Any]:
134
+ sanitized: Dict[str, Any] = {}
135
+ for key, value in dict(metadata or {}).items():
136
+ normalized_key = cls._coerce_optional_text(key)
137
+ if not normalized_key:
138
+ continue
139
+
140
+ if isinstance(value, dict):
141
+ sanitized_value = cls._sanitize_metadata_dict(value)
142
+ elif isinstance(value, list):
143
+ sanitized_value = [
144
+ cls._sanitize_metadata_dict(item) if isinstance(item, dict) else item
145
+ for item in value
146
+ if not type(item).__module__.startswith("unittest.mock")
147
+ ]
148
+ elif type(value).__module__.startswith("unittest.mock"):
149
+ continue
150
+ else:
151
+ sanitized_value = value
152
+
153
+ sanitized[normalized_key] = sanitized_value
154
+
155
+ return sanitized
@@ -33,10 +33,12 @@ class LLMResponse:
33
33
  output: List[ToolCall] # lista de tool calls
34
34
  usage: Usage
35
35
  reasoning_content: str = None # campo opcional para Chain of Thought
36
+ reasoning_details: Any = None # provider-native reasoning blocks, when available
36
37
 
37
38
  # ordered list of content blocks (text and image mixed)
38
39
  # Example: [{"type": "text", "text": "..."}, {"type": "image", "source": {"type": "base64", "data": "..."}}]
39
40
  content_parts: List[Dict] = None
41
+ provider_metadata: Dict[str, Any] = None
40
42
 
41
43
  def __post_init__(self):
42
44
  """Asegura que output sea una lista"""
@@ -56,3 +58,5 @@ class LLMResponse:
56
58
  "text": self.output_text
57
59
  })
58
60
 
61
+ if self.provider_metadata is None:
62
+ self.provider_metadata = {}
@@ -758,7 +758,16 @@ class llmClient:
758
758
  if reasoning_content:
759
759
  assistant_message["reasoning_content"] = reasoning_content
760
760
 
761
- has_assistant_payload = bool(assistant_message.get("content")) or bool(tool_calls) or bool(reasoning_content)
761
+ reasoning_details = getattr(response, "reasoning_details", None)
762
+ if reasoning_details:
763
+ assistant_message["reasoning_details"] = reasoning_details
764
+
765
+ has_assistant_payload = (
766
+ bool(assistant_message.get("content"))
767
+ or bool(tool_calls)
768
+ or bool(reasoning_content)
769
+ or bool(reasoning_details)
770
+ )
762
771
  if not has_assistant_payload:
763
772
  return []
764
773
 
@@ -1246,15 +1255,58 @@ class llmClient:
1246
1255
  "output_tokens": response.usage.output_tokens,
1247
1256
  "total_tokens": response.usage.total_tokens
1248
1257
  }
1258
+ provider_stats = self._build_provider_stats(getattr(response, "provider_metadata", None))
1259
+ if provider_stats:
1260
+ stats_dict.update(provider_stats)
1249
1261
  return stats_dict
1250
1262
 
1251
- def add_stats(self, stats1: dict, stats2: dict) -> dict:
1263
+ @staticmethod
1264
+ def _build_provider_stats(provider_metadata: dict | None) -> dict:
1265
+ if not isinstance(provider_metadata, dict) or not provider_metadata:
1266
+ return {}
1267
+
1268
+ provider = str(provider_metadata.get("provider") or "").strip()
1269
+ routed_provider = str(provider_metadata.get("provider_name") or "").strip()
1270
+
1271
+ stats: dict = {}
1272
+ if provider:
1273
+ stats["provider"] = provider
1274
+ if routed_provider:
1275
+ stats["routed_provider"] = routed_provider
1276
+
1277
+ openrouter_metadata = provider_metadata.get("openrouter")
1278
+ if isinstance(openrouter_metadata, dict) and openrouter_metadata:
1279
+ stats["openrouter"] = openrouter_metadata
1280
+
1281
+ provider_call = {}
1282
+ if provider:
1283
+ provider_call["provider"] = provider
1284
+ if routed_provider:
1285
+ provider_call["routed_provider"] = routed_provider
1286
+ if provider_call:
1287
+ stats["provider_calls"] = [provider_call]
1288
+
1289
+ return stats
1290
+
1291
+ @staticmethod
1292
+ def add_stats(stats1: dict, stats2: dict) -> dict:
1293
+ stats1 = dict(stats1 or {})
1294
+ stats2 = dict(stats2 or {})
1252
1295
  stats_dict = {
1253
- "model": stats1.get('model', ''),
1296
+ **stats1,
1297
+ **stats2,
1298
+ "model": stats2.get('model') or stats1.get('model', ''),
1254
1299
  "input_tokens": (stats1.get('input_tokens') or 0) + (stats2.get('input_tokens') or 0),
1255
1300
  "output_tokens": (stats1.get('output_tokens') or 0) + (stats2.get('output_tokens') or 0),
1256
1301
  "total_tokens": (stats1.get('total_tokens') or 0) + (stats2.get('total_tokens') or 0),
1257
1302
  }
1303
+ provider_calls = []
1304
+ for stats in (stats1, stats2):
1305
+ for provider_call in stats.get("provider_calls") or []:
1306
+ if isinstance(provider_call, dict) and provider_call not in provider_calls:
1307
+ provider_calls.append(provider_call)
1308
+ if provider_calls:
1309
+ stats_dict["provider_calls"] = provider_calls
1258
1310
  return stats_dict
1259
1311
 
1260
1312
 
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: iatoolkit
3
- Version: 2.45.0
3
+ Version: 2.45.2
4
4
  Summary: IAToolkit
5
5
  Author: Fernando Libedinsky
6
6
  License-Expression: MIT
@@ -1,100 +0,0 @@
1
- # Copyright (c) 2024 Fernando Libedinsky
2
- # Product: IAToolkit
3
- #
4
- # IAToolkit is open source software.
5
-
6
- from typing import Any, Dict
7
-
8
- from iatoolkit.infra.llm_providers.openai_compatible_chat_adapter import OpenAICompatibleChatAdapter
9
-
10
-
11
- class OpenRouterAdapter(OpenAICompatibleChatAdapter):
12
- """OpenRouter-specific adapter built on top of the shared chat.completions core."""
13
-
14
- supports_multimodal = True
15
- supports_reasoning = False
16
- supports_metadata = True
17
- supports_parallel_tool_calls = True
18
-
19
- # Fixed at "native" by policy: a PDF attachment must reach the routed model
20
- # as-is, for it to read with its own vision/multimodal capability - never
21
- # silently rewritten into extracted text by OpenRouter's OCR/parsing
22
- # pipeline. This only applies when nothing else already requested a plugin
23
- # (see _extend_call_kwargs below); an explicit `plugins` kwarg always wins.
24
- _PDF_FILE_PARSER_PLUGIN = [{"id": "file-parser", "pdf": {"engine": "native"}}]
25
-
26
- # Providers observed returning HTTP 400 on `type: "file"` content parts
27
- # even when routed to a model whose aggregate catalog entry lists "file"
28
- # as a supported input modality (OpenRouter's per-endpoint support lags
29
- # the model-level declaration). Excluded via `provider.ignore` whenever
30
- # we send a native file attachment, so routing skips them instead of
31
- # failing the request.
32
- _FILE_UNSUPPORTED_PROVIDERS = ("parasail", "akashml", "alibaba", "chutes", "reka")
33
-
34
- def __init__(self, openrouter_client):
35
- super().__init__(openai_compatible_client=openrouter_client, provider_label="OpenRouter")
36
-
37
- def _extend_call_kwargs(self, call_kwargs: Dict[str, Any], kwargs: Dict[str, Any]) -> None:
38
- text = kwargs.get("text") or {}
39
- verbosity = text.get("verbosity") if isinstance(text, dict) else None
40
- if verbosity:
41
- call_kwargs["verbosity"] = verbosity
42
-
43
- passthrough_keys = (
44
- "service_tier",
45
- "temperature",
46
- "top_p",
47
- "max_tokens",
48
- "max_completion_tokens",
49
- "seed",
50
- "stop",
51
- "stream",
52
- "stream_options",
53
- "modalities",
54
- "user",
55
- )
56
- for key in passthrough_keys:
57
- if kwargs.get(key) is not None:
58
- call_kwargs[key] = kwargs.get(key)
59
-
60
- extra_body = dict(call_kwargs.get("extra_body") or {})
61
-
62
- reasoning_payload = self._build_reasoning_payload(kwargs.get("reasoning"), kwargs)
63
- if reasoning_payload:
64
- extra_body["reasoning"] = reasoning_payload
65
-
66
- vendor_specific_keys = (
67
- "models",
68
- "provider",
69
- "plugins",
70
- "session_id",
71
- )
72
- for key in vendor_specific_keys:
73
- if kwargs.get(key) is not None:
74
- extra_body[key] = kwargs.get(key)
75
-
76
- if self._has_pdf_attachment(kwargs.get("attachments")):
77
- if "plugins" not in extra_body:
78
- extra_body["plugins"] = self._PDF_FILE_PARSER_PLUGIN
79
-
80
- provider_opts = dict(extra_body.get("provider") or {})
81
- ignore = list(provider_opts.get("ignore") or [])
82
- for provider_slug in self._FILE_UNSUPPORTED_PROVIDERS:
83
- if provider_slug not in ignore:
84
- ignore.append(provider_slug)
85
- provider_opts["ignore"] = ignore
86
- extra_body["provider"] = provider_opts
87
-
88
- if extra_body:
89
- call_kwargs["extra_body"] = extra_body
90
-
91
- @staticmethod
92
- def _has_pdf_attachment(attachments: Any) -> bool:
93
- for attachment in attachments or []:
94
- if not isinstance(attachment, dict):
95
- continue
96
- mime_type = str(attachment.get("mime_type") or attachment.get("type") or "").strip().lower()
97
- filename = str(attachment.get("name") or attachment.get("filename") or "").strip().lower()
98
- if mime_type == "application/pdf" or filename.endswith(".pdf"):
99
- return True
100
- return False
File without changes
File without changes
File without changes
File without changes
File without changes