solace-agent-mesh 1.6.1__py3-none-any.whl → 1.13.2__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Potentially problematic release.
This version of solace-agent-mesh might be problematic. Click here for more details.
- solace_agent_mesh/agent/adk/alembic/README +74 -0
- solace_agent_mesh/agent/adk/alembic/env.py +77 -0
- solace_agent_mesh/agent/adk/alembic/script.py.mako +28 -0
- solace_agent_mesh/agent/adk/alembic/versions/e2902798564d_adk_session_db_upgrade.py +52 -0
- solace_agent_mesh/agent/adk/alembic.ini +112 -0
- solace_agent_mesh/agent/adk/app_llm_agent.py +26 -0
- solace_agent_mesh/agent/adk/artifacts/filesystem_artifact_service.py +165 -1
- solace_agent_mesh/agent/adk/artifacts/s3_artifact_service.py +163 -0
- solace_agent_mesh/agent/adk/callbacks.py +852 -109
- solace_agent_mesh/agent/adk/embed_resolving_mcp_toolset.py +234 -36
- solace_agent_mesh/agent/adk/intelligent_mcp_callbacks.py +52 -5
- solace_agent_mesh/agent/adk/mcp_content_processor.py +1 -1
- solace_agent_mesh/agent/adk/models/lite_llm.py +77 -21
- solace_agent_mesh/agent/adk/models/oauth2_token_manager.py +24 -137
- solace_agent_mesh/agent/adk/runner.py +85 -20
- solace_agent_mesh/agent/adk/schema_migration.py +88 -0
- solace_agent_mesh/agent/adk/services.py +94 -18
- solace_agent_mesh/agent/adk/setup.py +281 -65
- solace_agent_mesh/agent/adk/stream_parser.py +231 -37
- solace_agent_mesh/agent/adk/tool_wrapper.py +3 -0
- solace_agent_mesh/agent/protocol/event_handlers.py +472 -137
- solace_agent_mesh/agent/proxies/a2a/app.py +3 -2
- solace_agent_mesh/agent/proxies/a2a/component.py +572 -75
- solace_agent_mesh/agent/proxies/a2a/config.py +80 -4
- solace_agent_mesh/agent/proxies/base/app.py +3 -2
- solace_agent_mesh/agent/proxies/base/component.py +188 -22
- solace_agent_mesh/agent/proxies/base/proxy_task_context.py +3 -1
- solace_agent_mesh/agent/sac/app.py +91 -3
- solace_agent_mesh/agent/sac/component.py +591 -157
- solace_agent_mesh/agent/sac/patch_adk.py +8 -16
- solace_agent_mesh/agent/sac/task_execution_context.py +146 -4
- solace_agent_mesh/agent/tools/__init__.py +3 -0
- solace_agent_mesh/agent/tools/audio_tools.py +3 -3
- solace_agent_mesh/agent/tools/builtin_artifact_tools.py +710 -171
- solace_agent_mesh/agent/tools/deep_research_tools.py +2161 -0
- solace_agent_mesh/agent/tools/dynamic_tool.py +2 -0
- solace_agent_mesh/agent/tools/peer_agent_tool.py +82 -15
- solace_agent_mesh/agent/tools/time_tools.py +126 -0
- solace_agent_mesh/agent/tools/tool_config_types.py +57 -2
- solace_agent_mesh/agent/tools/web_search_tools.py +279 -0
- solace_agent_mesh/agent/tools/web_tools.py +125 -17
- solace_agent_mesh/agent/utils/artifact_helpers.py +248 -6
- solace_agent_mesh/agent/utils/context_helpers.py +17 -0
- solace_agent_mesh/assets/docs/404.html +6 -6
- solace_agent_mesh/assets/docs/assets/css/{styles.906a1503.css → styles.8162edfb.css} +1 -1
- solace_agent_mesh/assets/docs/assets/js/05749d90.19ac4f35.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/15ba94aa.e186750d.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/15e40e79.434bb30f.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/17896441.e612dfb4.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/2279.550aa580.js +2 -0
- solace_agent_mesh/assets/docs/assets/js/{17896441.a5e82f9b.js.LICENSE.txt → 2279.550aa580.js.LICENSE.txt} +6 -0
- solace_agent_mesh/assets/docs/assets/js/240a0364.83e37aa8.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/2987107d.a80604f9.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/2e32b5e0.2f0db237.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/3a6c6137.7e61915d.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/3ac1795d.7f7ab1c1.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/3ff0015d.e53c9b78.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/41adc471.0e95b87c.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/4667dc50.bf2ad456.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/49eed117.493d6f99.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/{509e993c.4c7a1a6d.js → 509e993c.a1fbf45a.js} +1 -1
- solace_agent_mesh/assets/docs/assets/js/547e15cc.8e6da617.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/55b7b518.29d6e75d.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/5b8d9c11.d4eb37b8.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/5c2bd65f.1ee87753.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/60702c0e.a8bdd79b.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/631738c7.fa471607.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/64195356.09dbd087.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/66d4869e.30340bd3.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/6a520c9d.b6e3f2ce.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/6aaedf65.7253541d.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/6ad8f0bd.a5b36a60.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/6d84eae0.fd23ba4a.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/71da7b71.374b9d54.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/729898df.7249e9fd.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/7e294c01.7c5f6906.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/8024126c.e3467286.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/81a99df0.7ed65d45.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/82fbfb93.161823a5.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/8b032486.91a91afc.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/924ffdeb.975e428a.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/94e8668d.16083b3f.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/9bb13469.4523ae20.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/a7d42657.a956689d.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/a94703ab.3e5fbcb3.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/ab9708a8.3e563275.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/ad87452a.9d73dad6.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/c93cbaa0.0e0d8baf.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/cab03b5b.6a073091.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/cbe2e9ea.07e170dd.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/da0b5bad.b62f7b08.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/dd817ffc.c37a755e.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/dd81e2b8.b682e9c2.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/de915948.44a432bc.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/e04b235d.06d23db6.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/e1b6eeb4.deb2b62e.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/e3d9abda.1476f570.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/e6f9706b.acc800d3.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/e92d0134.c147a429.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/ee0c2fe7.94d0a351.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/f284c35a.cc97854c.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/ff4d71f2.74710fc1.js +1 -0
- solace_agent_mesh/assets/docs/assets/js/main.d634009f.js +2 -0
- solace_agent_mesh/assets/docs/assets/js/runtime~main.27bb82a7.js +1 -0
- solace_agent_mesh/assets/docs/docs/documentation/components/agents/index.html +68 -68
- solace_agent_mesh/assets/docs/docs/documentation/components/builtin-tools/artifact-management/index.html +50 -50
- solace_agent_mesh/assets/docs/docs/documentation/components/builtin-tools/audio-tools/index.html +42 -42
- solace_agent_mesh/assets/docs/docs/documentation/components/builtin-tools/data-analysis-tools/index.html +55 -55
- solace_agent_mesh/assets/docs/docs/documentation/components/builtin-tools/embeds/index.html +82 -68
- solace_agent_mesh/assets/docs/docs/documentation/components/builtin-tools/image-tools/index.html +81 -0
- solace_agent_mesh/assets/docs/docs/documentation/components/builtin-tools/index.html +67 -50
- solace_agent_mesh/assets/docs/docs/documentation/components/builtin-tools/research-tools/index.html +136 -0
- solace_agent_mesh/assets/docs/docs/documentation/components/cli/index.html +178 -144
- solace_agent_mesh/assets/docs/docs/documentation/components/gateways/index.html +43 -42
- solace_agent_mesh/assets/docs/docs/documentation/components/index.html +20 -18
- solace_agent_mesh/assets/docs/docs/documentation/components/orchestrator/index.html +23 -23
- solace_agent_mesh/assets/docs/docs/documentation/components/platform-service/index.html +33 -0
- solace_agent_mesh/assets/docs/docs/documentation/components/plugins/index.html +45 -45
- solace_agent_mesh/assets/docs/docs/documentation/components/projects/index.html +182 -0
- solace_agent_mesh/assets/docs/docs/documentation/components/prompts/index.html +147 -0
- solace_agent_mesh/assets/docs/docs/documentation/components/proxies/index.html +208 -125
- solace_agent_mesh/assets/docs/docs/documentation/components/speech/index.html +52 -0
- solace_agent_mesh/assets/docs/docs/documentation/deploying/debugging/index.html +28 -49
- solace_agent_mesh/assets/docs/docs/documentation/deploying/deployment-options/index.html +29 -30
- solace_agent_mesh/assets/docs/docs/documentation/deploying/index.html +14 -14
- solace_agent_mesh/assets/docs/docs/documentation/deploying/kubernetes/index.html +47 -0
- solace_agent_mesh/assets/docs/docs/documentation/deploying/kubernetes/kubernetes-deployment-guide/index.html +197 -0
- solace_agent_mesh/assets/docs/docs/documentation/deploying/logging/index.html +90 -0
- solace_agent_mesh/assets/docs/docs/documentation/deploying/observability/index.html +17 -16
- solace_agent_mesh/assets/docs/docs/documentation/deploying/proxy_configuration/index.html +49 -0
- solace_agent_mesh/assets/docs/docs/documentation/developing/create-agents/index.html +38 -38
- solace_agent_mesh/assets/docs/docs/documentation/developing/create-gateways/index.html +162 -171
- solace_agent_mesh/assets/docs/docs/documentation/developing/creating-python-tools/index.html +67 -49
- solace_agent_mesh/assets/docs/docs/documentation/developing/creating-service-providers/index.html +17 -17
- solace_agent_mesh/assets/docs/docs/documentation/developing/evaluations/index.html +51 -51
- solace_agent_mesh/assets/docs/docs/documentation/developing/index.html +22 -22
- solace_agent_mesh/assets/docs/docs/documentation/developing/structure/index.html +27 -27
- solace_agent_mesh/assets/docs/docs/documentation/developing/tutorials/bedrock-agents/index.html +135 -135
- solace_agent_mesh/assets/docs/docs/documentation/developing/tutorials/custom-agent/index.html +66 -66
- solace_agent_mesh/assets/docs/docs/documentation/developing/tutorials/event-mesh-gateway/index.html +51 -51
- solace_agent_mesh/assets/docs/docs/documentation/developing/tutorials/mcp-integration/index.html +50 -38
- solace_agent_mesh/assets/docs/docs/documentation/developing/tutorials/mongodb-integration/index.html +86 -86
- solace_agent_mesh/assets/docs/docs/documentation/developing/tutorials/rag-integration/index.html +51 -51
- solace_agent_mesh/assets/docs/docs/documentation/developing/tutorials/rest-gateway/index.html +24 -24
- solace_agent_mesh/assets/docs/docs/documentation/developing/tutorials/slack-integration/index.html +30 -30
- solace_agent_mesh/assets/docs/docs/documentation/developing/tutorials/sql-database/index.html +44 -44
- solace_agent_mesh/assets/docs/docs/documentation/developing/tutorials/teams-integration/index.html +115 -0
- solace_agent_mesh/assets/docs/docs/documentation/enterprise/agent-builder/index.html +86 -0
- solace_agent_mesh/assets/docs/docs/documentation/enterprise/connectors/index.html +67 -0
- solace_agent_mesh/assets/docs/docs/documentation/enterprise/index.html +23 -19
- solace_agent_mesh/assets/docs/docs/documentation/enterprise/installation/index.html +40 -37
- solace_agent_mesh/assets/docs/docs/documentation/enterprise/openapi-tools/index.html +324 -0
- solace_agent_mesh/assets/docs/docs/documentation/enterprise/rbac-setup-guide/index.html +112 -87
- solace_agent_mesh/assets/docs/docs/documentation/enterprise/secure-user-delegated-access/index.html +440 -0
- solace_agent_mesh/assets/docs/docs/documentation/enterprise/single-sign-on/index.html +87 -64
- solace_agent_mesh/assets/docs/docs/documentation/enterprise/wheel-installation/index.html +62 -0
- solace_agent_mesh/assets/docs/docs/documentation/getting-started/architecture/index.html +44 -44
- solace_agent_mesh/assets/docs/docs/documentation/getting-started/index.html +39 -37
- solace_agent_mesh/assets/docs/docs/documentation/getting-started/introduction/index.html +30 -30
- solace_agent_mesh/assets/docs/docs/documentation/getting-started/try-agent-mesh/index.html +18 -18
- solace_agent_mesh/assets/docs/docs/documentation/getting-started/vibe_coding/index.html +62 -0
- solace_agent_mesh/assets/docs/docs/documentation/installing-and-configuring/artifact-storage/index.html +311 -0
- solace_agent_mesh/assets/docs/docs/documentation/installing-and-configuring/configurations/index.html +39 -42
- solace_agent_mesh/assets/docs/docs/documentation/installing-and-configuring/index.html +14 -14
- solace_agent_mesh/assets/docs/docs/documentation/installing-and-configuring/installation/index.html +27 -25
- solace_agent_mesh/assets/docs/docs/documentation/installing-and-configuring/large_language_models/index.html +69 -69
- solace_agent_mesh/assets/docs/docs/documentation/installing-and-configuring/run-project/index.html +72 -72
- solace_agent_mesh/assets/docs/docs/documentation/installing-and-configuring/session-storage/index.html +251 -0
- solace_agent_mesh/assets/docs/docs/documentation/installing-and-configuring/user-feedback/index.html +88 -0
- solace_agent_mesh/assets/docs/docs/documentation/migrations/a2a-upgrade/a2a-gateway-upgrade-to-0.3.0/index.html +42 -42
- solace_agent_mesh/assets/docs/docs/documentation/migrations/a2a-upgrade/a2a-technical-migration-map/index.html +20 -20
- solace_agent_mesh/assets/docs/docs/documentation/migrations/platform-service-split/index.html +85 -0
- solace_agent_mesh/assets/docs/lunr-index-1768329217460.json +1 -0
- solace_agent_mesh/assets/docs/lunr-index.json +1 -1
- solace_agent_mesh/assets/docs/search-doc-1768329217460.json +1 -0
- solace_agent_mesh/assets/docs/search-doc.json +1 -1
- solace_agent_mesh/assets/docs/sitemap.xml +1 -1
- solace_agent_mesh/cli/__init__.py +1 -1
- solace_agent_mesh/cli/commands/add_cmd/__init__.py +3 -1
- solace_agent_mesh/cli/commands/add_cmd/agent_cmd.py +6 -1
- solace_agent_mesh/cli/commands/add_cmd/proxy_cmd.py +100 -0
- solace_agent_mesh/cli/commands/docs_cmd.py +4 -1
- solace_agent_mesh/cli/commands/eval_cmd.py +1 -1
- solace_agent_mesh/cli/commands/init_cmd/__init__.py +15 -0
- solace_agent_mesh/cli/commands/init_cmd/directory_step.py +1 -1
- solace_agent_mesh/cli/commands/init_cmd/env_step.py +30 -3
- solace_agent_mesh/cli/commands/init_cmd/orchestrator_step.py +3 -4
- solace_agent_mesh/cli/commands/init_cmd/platform_service_step.py +85 -0
- solace_agent_mesh/cli/commands/init_cmd/webui_gateway_step.py +16 -3
- solace_agent_mesh/cli/commands/plugin_cmd/add_cmd.py +2 -1
- solace_agent_mesh/cli/commands/plugin_cmd/catalog_cmd.py +1 -0
- solace_agent_mesh/cli/commands/plugin_cmd/create_cmd.py +3 -3
- solace_agent_mesh/cli/commands/run_cmd.py +64 -49
- solace_agent_mesh/cli/commands/tools_cmd.py +315 -0
- solace_agent_mesh/cli/main.py +15 -0
- solace_agent_mesh/client/webui/frontend/static/assets/{authCallback-BTf6dqwp.js → authCallback-KnKMP_vb.js} +1 -1
- solace_agent_mesh/client/webui/frontend/static/assets/client-DpBL2stg.js +25 -0
- solace_agent_mesh/client/webui/frontend/static/assets/main-Cd498TV2.js +435 -0
- solace_agent_mesh/client/webui/frontend/static/assets/main-rSf8Vu29.css +1 -0
- solace_agent_mesh/client/webui/frontend/static/assets/vendor-CGk8Suyh.js +565 -0
- solace_agent_mesh/client/webui/frontend/static/auth-callback.html +3 -3
- solace_agent_mesh/client/webui/frontend/static/index.html +4 -4
- solace_agent_mesh/client/webui/frontend/static/mockServiceWorker.js +336 -0
- solace_agent_mesh/client/webui/frontend/static/ui-version.json +6 -0
- solace_agent_mesh/common/a2a/events.py +2 -1
- solace_agent_mesh/common/a2a/protocol.py +5 -0
- solace_agent_mesh/common/a2a/types.py +2 -1
- solace_agent_mesh/common/a2a_spec/schemas/artifact_creation_progress.json +23 -6
- solace_agent_mesh/common/a2a_spec/schemas/feedback_event.json +51 -0
- solace_agent_mesh/common/agent_registry.py +38 -11
- solace_agent_mesh/common/data_parts.py +144 -4
- solace_agent_mesh/common/error_handlers.py +83 -0
- solace_agent_mesh/common/exceptions.py +24 -0
- solace_agent_mesh/common/oauth/__init__.py +17 -0
- solace_agent_mesh/common/oauth/oauth_client.py +408 -0
- solace_agent_mesh/common/oauth/utils.py +50 -0
- solace_agent_mesh/common/rag_dto.py +156 -0
- solace_agent_mesh/common/sac/sam_component_base.py +97 -19
- solace_agent_mesh/common/sam_events/event_service.py +2 -2
- solace_agent_mesh/common/services/employee_service.py +1 -1
- solace_agent_mesh/common/utils/embeds/constants.py +1 -0
- solace_agent_mesh/common/utils/embeds/converter.py +1 -8
- solace_agent_mesh/common/utils/embeds/modifiers.py +4 -28
- solace_agent_mesh/common/utils/embeds/resolver.py +152 -31
- solace_agent_mesh/common/utils/embeds/types.py +9 -0
- solace_agent_mesh/common/utils/log_formatters.py +20 -0
- solace_agent_mesh/common/utils/mime_helpers.py +12 -5
- solace_agent_mesh/common/utils/pydantic_utils.py +90 -3
- solace_agent_mesh/common/utils/rbac_utils.py +69 -0
- solace_agent_mesh/common/utils/templates/__init__.py +8 -0
- solace_agent_mesh/common/utils/templates/liquid_renderer.py +210 -0
- solace_agent_mesh/common/utils/templates/template_resolver.py +161 -0
- solace_agent_mesh/config_portal/backend/common.py +12 -0
- solace_agent_mesh/config_portal/frontend/static/client/assets/_index-CljP4_mv.js +103 -0
- solace_agent_mesh/config_portal/frontend/static/client/assets/{components-Rk0n-9cK.js → components-CaC6hG8d.js} +22 -22
- solace_agent_mesh/config_portal/frontend/static/client/assets/{entry.client-mvZjNKiz.js → entry.client-H_TM0YBt.js} +3 -3
- solace_agent_mesh/config_portal/frontend/static/client/assets/{index-DzNKzXrc.js → index-CnFykb2v.js} +16 -16
- solace_agent_mesh/config_portal/frontend/static/client/assets/manifest-f8439d40.js +1 -0
- solace_agent_mesh/config_portal/frontend/static/client/assets/root-BIMqslJB.css +1 -0
- solace_agent_mesh/config_portal/frontend/static/client/assets/root-mJmTIdIk.js +10 -0
- solace_agent_mesh/config_portal/frontend/static/client/index.html +3 -3
- solace_agent_mesh/core_a2a/service.py +3 -2
- solace_agent_mesh/gateway/adapter/__init__.py +1 -0
- solace_agent_mesh/gateway/adapter/base.py +170 -0
- solace_agent_mesh/gateway/adapter/types.py +230 -0
- solace_agent_mesh/gateway/base/app.py +39 -2
- solace_agent_mesh/gateway/base/auth_interface.py +103 -0
- solace_agent_mesh/gateway/base/component.py +1027 -151
- solace_agent_mesh/gateway/generic/__init__.py +1 -0
- solace_agent_mesh/gateway/generic/app.py +50 -0
- solace_agent_mesh/gateway/generic/component.py +894 -0
- solace_agent_mesh/gateway/http_sse/alembic/env.py +0 -7
- solace_agent_mesh/gateway/http_sse/alembic/versions/20251023_add_project_users_table.py +72 -0
- solace_agent_mesh/gateway/http_sse/alembic/versions/20251023_add_soft_delete_and_search.py +109 -0
- solace_agent_mesh/gateway/http_sse/alembic/versions/20251024_add_default_agent_to_projects.py +26 -0
- solace_agent_mesh/gateway/http_sse/alembic/versions/20251024_add_projects_table.py +135 -0
- solace_agent_mesh/gateway/http_sse/alembic/versions/20251108_create_prompt_tables_with_sharing.py +154 -0
- solace_agent_mesh/gateway/http_sse/alembic/versions/20251115_add_parent_task_id.py +32 -0
- solace_agent_mesh/gateway/http_sse/alembic/versions/20251126_add_background_task_fields.py +47 -0
- solace_agent_mesh/gateway/http_sse/alembic/versions/20251202_add_versioned_fields_to_prompts.py +52 -0
- solace_agent_mesh/gateway/http_sse/alembic.ini +0 -36
- solace_agent_mesh/gateway/http_sse/app.py +40 -11
- solace_agent_mesh/gateway/http_sse/component.py +285 -160
- solace_agent_mesh/gateway/http_sse/dependencies.py +149 -114
- solace_agent_mesh/gateway/http_sse/main.py +68 -450
- solace_agent_mesh/gateway/http_sse/repository/__init__.py +19 -1
- solace_agent_mesh/gateway/http_sse/repository/chat_task_repository.py +2 -2
- solace_agent_mesh/gateway/http_sse/repository/entities/project.py +81 -0
- solace_agent_mesh/gateway/http_sse/repository/entities/project_user.py +47 -0
- solace_agent_mesh/gateway/http_sse/repository/entities/session.py +26 -3
- solace_agent_mesh/gateway/http_sse/repository/entities/task.py +7 -0
- solace_agent_mesh/gateway/http_sse/repository/feedback_repository.py +47 -0
- solace_agent_mesh/gateway/http_sse/repository/interfaces.py +114 -6
- solace_agent_mesh/gateway/http_sse/repository/models/__init__.py +13 -0
- solace_agent_mesh/gateway/http_sse/repository/models/project_model.py +51 -0
- solace_agent_mesh/gateway/http_sse/repository/models/project_user_model.py +75 -0
- solace_agent_mesh/gateway/http_sse/repository/models/prompt_model.py +159 -0
- solace_agent_mesh/gateway/http_sse/repository/models/session_model.py +8 -2
- solace_agent_mesh/gateway/http_sse/repository/models/task_model.py +8 -1
- solace_agent_mesh/gateway/http_sse/repository/project_repository.py +172 -0
- solace_agent_mesh/gateway/http_sse/repository/project_user_repository.py +186 -0
- solace_agent_mesh/gateway/http_sse/repository/session_repository.py +177 -11
- solace_agent_mesh/gateway/http_sse/repository/task_repository.py +86 -2
- solace_agent_mesh/gateway/http_sse/routers/agent_cards.py +38 -7
- solace_agent_mesh/gateway/http_sse/routers/artifacts.py +256 -58
- solace_agent_mesh/gateway/http_sse/routers/auth.py +168 -134
- solace_agent_mesh/gateway/http_sse/routers/config.py +302 -8
- solace_agent_mesh/gateway/http_sse/routers/dto/project_dto.py +69 -0
- solace_agent_mesh/gateway/http_sse/routers/dto/prompt_dto.py +255 -0
- solace_agent_mesh/gateway/http_sse/routers/dto/requests/project_requests.py +48 -0
- solace_agent_mesh/gateway/http_sse/routers/dto/requests/session_requests.py +14 -1
- solace_agent_mesh/gateway/http_sse/routers/dto/responses/base_responses.py +1 -1
- solace_agent_mesh/gateway/http_sse/routers/dto/responses/project_responses.py +31 -0
- solace_agent_mesh/gateway/http_sse/routers/dto/responses/session_responses.py +5 -2
- solace_agent_mesh/gateway/http_sse/routers/dto/responses/version_responses.py +31 -0
- solace_agent_mesh/gateway/http_sse/routers/feedback.py +133 -2
- solace_agent_mesh/gateway/http_sse/routers/people.py +2 -2
- solace_agent_mesh/gateway/http_sse/routers/projects.py +768 -0
- solace_agent_mesh/gateway/http_sse/routers/prompts.py +1416 -0
- solace_agent_mesh/gateway/http_sse/routers/sessions.py +167 -7
- solace_agent_mesh/gateway/http_sse/routers/speech.py +355 -0
- solace_agent_mesh/gateway/http_sse/routers/sse.py +131 -8
- solace_agent_mesh/gateway/http_sse/routers/tasks.py +670 -18
- solace_agent_mesh/gateway/http_sse/routers/users.py +1 -1
- solace_agent_mesh/gateway/http_sse/routers/version.py +343 -0
- solace_agent_mesh/gateway/http_sse/routers/visualization.py +92 -9
- solace_agent_mesh/gateway/http_sse/services/audio_service.py +1227 -0
- solace_agent_mesh/gateway/http_sse/services/background_task_monitor.py +186 -0
- solace_agent_mesh/gateway/http_sse/services/data_retention_service.py +1 -1
- solace_agent_mesh/gateway/http_sse/services/feedback_service.py +1 -1
- solace_agent_mesh/gateway/http_sse/services/project_service.py +930 -0
- solace_agent_mesh/gateway/http_sse/services/prompt_builder_assistant.py +303 -0
- solace_agent_mesh/gateway/http_sse/services/session_service.py +361 -12
- solace_agent_mesh/gateway/http_sse/services/task_logger_service.py +354 -4
- solace_agent_mesh/gateway/http_sse/session_manager.py +15 -15
- solace_agent_mesh/gateway/http_sse/sse_manager.py +286 -166
- solace_agent_mesh/gateway/http_sse/utils/artifact_copy_utils.py +370 -0
- solace_agent_mesh/gateway/http_sse/utils/stim_utils.py +41 -1
- solace_agent_mesh/services/__init__.py +0 -0
- solace_agent_mesh/services/platform/__init__.py +29 -0
- solace_agent_mesh/services/platform/alembic/env.py +85 -0
- solace_agent_mesh/services/platform/alembic/script.py.mako +28 -0
- solace_agent_mesh/services/platform/alembic.ini +109 -0
- solace_agent_mesh/services/platform/api/__init__.py +3 -0
- solace_agent_mesh/services/platform/api/dependencies.py +154 -0
- solace_agent_mesh/services/platform/api/main.py +314 -0
- solace_agent_mesh/services/platform/api/middleware.py +51 -0
- solace_agent_mesh/services/platform/api/routers/__init__.py +33 -0
- solace_agent_mesh/services/platform/api/routers/health_router.py +31 -0
- solace_agent_mesh/services/platform/app.py +215 -0
- solace_agent_mesh/services/platform/component.py +777 -0
- solace_agent_mesh/shared/__init__.py +14 -0
- solace_agent_mesh/shared/api/__init__.py +42 -0
- solace_agent_mesh/shared/auth/__init__.py +26 -0
- solace_agent_mesh/shared/auth/dependencies.py +204 -0
- solace_agent_mesh/shared/auth/middleware.py +347 -0
- solace_agent_mesh/shared/database/__init__.py +20 -0
- solace_agent_mesh/{gateway/http_sse/shared → shared/database}/base_repository.py +1 -1
- solace_agent_mesh/{gateway/http_sse/shared → shared/database}/database_exceptions.py +1 -1
- solace_agent_mesh/{gateway/http_sse/shared → shared/database}/database_helpers.py +1 -1
- solace_agent_mesh/shared/exceptions/__init__.py +36 -0
- solace_agent_mesh/{gateway/http_sse/shared → shared/exceptions}/exception_handlers.py +19 -5
- solace_agent_mesh/shared/utils/__init__.py +21 -0
- solace_agent_mesh/templates/logging_config_template.yaml +48 -0
- solace_agent_mesh/templates/main_orchestrator.yaml +12 -1
- solace_agent_mesh/templates/platform.yaml +49 -0
- solace_agent_mesh/templates/plugin_readme_template.md +3 -25
- solace_agent_mesh/templates/plugin_tool_config_template.yaml +109 -0
- solace_agent_mesh/templates/proxy_template.yaml +62 -0
- solace_agent_mesh/templates/webui.yaml +148 -6
- solace_agent_mesh/tools/web_search/__init__.py +18 -0
- solace_agent_mesh/tools/web_search/base.py +84 -0
- solace_agent_mesh/tools/web_search/google_search.py +247 -0
- solace_agent_mesh/tools/web_search/models.py +99 -0
- {solace_agent_mesh-1.6.1.dist-info → solace_agent_mesh-1.13.2.dist-info}/METADATA +31 -12
- solace_agent_mesh-1.13.2.dist-info/RECORD +591 -0
- {solace_agent_mesh-1.6.1.dist-info → solace_agent_mesh-1.13.2.dist-info}/WHEEL +1 -1
- solace_agent_mesh/agent/adk/adk_llm.txt +0 -232
- solace_agent_mesh/agent/adk/adk_llm_detail.txt +0 -566
- solace_agent_mesh/agent/adk/artifacts/artifacts_llm.txt +0 -171
- solace_agent_mesh/agent/adk/models/models_llm.txt +0 -142
- solace_agent_mesh/agent/agent_llm.txt +0 -378
- solace_agent_mesh/agent/agent_llm_detail.txt +0 -1702
- solace_agent_mesh/agent/protocol/protocol_llm.txt +0 -81
- solace_agent_mesh/agent/protocol/protocol_llm_detail.txt +0 -92
- solace_agent_mesh/agent/sac/sac_llm.txt +0 -189
- solace_agent_mesh/agent/sac/sac_llm_detail.txt +0 -200
- solace_agent_mesh/agent/testing/testing_llm.txt +0 -57
- solace_agent_mesh/agent/testing/testing_llm_detail.txt +0 -68
- solace_agent_mesh/agent/tools/tools_llm.txt +0 -263
- solace_agent_mesh/agent/tools/tools_llm_detail.txt +0 -274
- solace_agent_mesh/agent/utils/utils_llm.txt +0 -138
- solace_agent_mesh/agent/utils/utils_llm_detail.txt +0 -149
- solace_agent_mesh/assets/docs/assets/js/15ba94aa.932dd2db.js +0 -1
- solace_agent_mesh/assets/docs/assets/js/17896441.a5e82f9b.js +0 -2
- solace_agent_mesh/assets/docs/assets/js/240a0364.7eac6021.js +0 -1
- solace_agent_mesh/assets/docs/assets/js/2e32b5e0.33f5d75b.js +0 -1
- solace_agent_mesh/assets/docs/assets/js/3a6c6137.f5940cfa.js +0 -1
- solace_agent_mesh/assets/docs/assets/js/3ac1795d.76654dd9.js +0 -1
- solace_agent_mesh/assets/docs/assets/js/3ff0015d.2be20244.js +0 -1
- solace_agent_mesh/assets/docs/assets/js/547e15cc.2cbb060a.js +0 -1
- solace_agent_mesh/assets/docs/assets/js/55b7b518.f2b1d1ba.js +0 -1
- solace_agent_mesh/assets/docs/assets/js/5c2bd65f.eda4bcb2.js +0 -1
- solace_agent_mesh/assets/docs/assets/js/631738c7.a8b1ef8b.js +0 -1
- solace_agent_mesh/assets/docs/assets/js/6a520c9d.ba015d81.js +0 -1
- solace_agent_mesh/assets/docs/assets/js/6ad8f0bd.f4b15f3b.js +0 -1
- solace_agent_mesh/assets/docs/assets/js/6d84eae0.4a5fbf39.js +0 -1
- solace_agent_mesh/assets/docs/assets/js/71da7b71.38583438.js +0 -1
- solace_agent_mesh/assets/docs/assets/js/8024126c.56e59919.js +0 -1
- solace_agent_mesh/assets/docs/assets/js/81a99df0.07034dd9.js +0 -1
- solace_agent_mesh/assets/docs/assets/js/82fbfb93.139a1a1f.js +0 -1
- solace_agent_mesh/assets/docs/assets/js/924ffdeb.8095e148.js +0 -1
- solace_agent_mesh/assets/docs/assets/js/94e8668d.b5ddb7a1.js +0 -1
- solace_agent_mesh/assets/docs/assets/js/9bb13469.dd1c9b54.js +0 -1
- solace_agent_mesh/assets/docs/assets/js/a94703ab.0438dbc2.js +0 -1
- solace_agent_mesh/assets/docs/assets/js/ab9708a8.3e6dd091.js +0 -1
- solace_agent_mesh/assets/docs/assets/js/c93cbaa0.eaff365e.js +0 -1
- solace_agent_mesh/assets/docs/assets/js/da0b5bad.d08a9466.js +0 -1
- solace_agent_mesh/assets/docs/assets/js/dd817ffc.0aa9630a.js +0 -1
- solace_agent_mesh/assets/docs/assets/js/dd81e2b8.d590bc9e.js +0 -1
- solace_agent_mesh/assets/docs/assets/js/de915948.27d6b065.js +0 -1
- solace_agent_mesh/assets/docs/assets/js/e3d9abda.6b9493d0.js +0 -1
- solace_agent_mesh/assets/docs/assets/js/e6f9706b.e74a984d.js +0 -1
- solace_agent_mesh/assets/docs/assets/js/e92d0134.cf6d6522.js +0 -1
- solace_agent_mesh/assets/docs/assets/js/f284c35a.42f59cdd.js +0 -1
- solace_agent_mesh/assets/docs/assets/js/ff4d71f2.15b02f97.js +0 -1
- solace_agent_mesh/assets/docs/assets/js/main.b12eac43.js +0 -2
- solace_agent_mesh/assets/docs/assets/js/runtime~main.e268214e.js +0 -1
- solace_agent_mesh/assets/docs/lunr-index-1761248203150.json +0 -1
- solace_agent_mesh/assets/docs/search-doc-1761248203150.json +0 -1
- solace_agent_mesh/cli/commands/add_cmd/add_cmd_llm.txt +0 -250
- solace_agent_mesh/cli/commands/init_cmd/init_cmd_llm.txt +0 -365
- solace_agent_mesh/cli/commands/plugin_cmd/plugin_cmd_llm.txt +0 -305
- solace_agent_mesh/client/webui/frontend/static/assets/client-CaY59VuC.js +0 -25
- solace_agent_mesh/client/webui/frontend/static/assets/main-B32noGmR.js +0 -342
- solace_agent_mesh/client/webui/frontend/static/assets/main-DHJKSW1S.css +0 -1
- solace_agent_mesh/client/webui/frontend/static/assets/vendor-BEmvJSYz.js +0 -405
- solace_agent_mesh/common/a2a/a2a_llm.txt +0 -182
- solace_agent_mesh/common/a2a/a2a_llm_detail.txt +0 -193
- solace_agent_mesh/common/a2a_spec/a2a_spec_llm.txt +0 -407
- solace_agent_mesh/common/a2a_spec/a2a_spec_llm_detail.txt +0 -736
- solace_agent_mesh/common/a2a_spec/schemas/schemas_llm.txt +0 -313
- solace_agent_mesh/common/common_llm.txt +0 -251
- solace_agent_mesh/common/common_llm_detail.txt +0 -2562
- solace_agent_mesh/common/middleware/middleware_llm.txt +0 -174
- solace_agent_mesh/common/middleware/middleware_llm_detail.txt +0 -185
- solace_agent_mesh/common/sac/sac_llm.txt +0 -71
- solace_agent_mesh/common/sac/sac_llm_detail.txt +0 -82
- solace_agent_mesh/common/sam_events/sam_events_llm.txt +0 -104
- solace_agent_mesh/common/sam_events/sam_events_llm_detail.txt +0 -115
- solace_agent_mesh/common/services/providers/providers_llm.txt +0 -80
- solace_agent_mesh/common/services/services_llm.txt +0 -363
- solace_agent_mesh/common/services/services_llm_detail.txt +0 -459
- solace_agent_mesh/common/utils/embeds/embeds_llm.txt +0 -220
- solace_agent_mesh/common/utils/utils_llm.txt +0 -336
- solace_agent_mesh/common/utils/utils_llm_detail.txt +0 -572
- solace_agent_mesh/config_portal/frontend/static/client/assets/_index-ByU1X1HD.js +0 -98
- solace_agent_mesh/config_portal/frontend/static/client/assets/manifest-61038fc6.js +0 -1
- solace_agent_mesh/config_portal/frontend/static/client/assets/root-BWvk5-gF.js +0 -10
- solace_agent_mesh/config_portal/frontend/static/client/assets/root-DxRwaWiE.css +0 -1
- solace_agent_mesh/core_a2a/core_a2a_llm.txt +0 -90
- solace_agent_mesh/core_a2a/core_a2a_llm_detail.txt +0 -101
- solace_agent_mesh/gateway/base/base_llm.txt +0 -224
- solace_agent_mesh/gateway/base/base_llm_detail.txt +0 -235
- solace_agent_mesh/gateway/gateway_llm.txt +0 -373
- solace_agent_mesh/gateway/gateway_llm_detail.txt +0 -3885
- solace_agent_mesh/gateway/http_sse/alembic/alembic_llm.txt +0 -295
- solace_agent_mesh/gateway/http_sse/alembic/versions/versions_llm.txt +0 -155
- solace_agent_mesh/gateway/http_sse/components/components_llm.txt +0 -105
- solace_agent_mesh/gateway/http_sse/http_sse_llm.txt +0 -299
- solace_agent_mesh/gateway/http_sse/http_sse_llm_detail.txt +0 -3278
- solace_agent_mesh/gateway/http_sse/repository/entities/entities_llm.txt +0 -263
- solace_agent_mesh/gateway/http_sse/repository/models/models_llm.txt +0 -266
- solace_agent_mesh/gateway/http_sse/repository/repository_llm.txt +0 -340
- solace_agent_mesh/gateway/http_sse/routers/dto/dto_llm.txt +0 -346
- solace_agent_mesh/gateway/http_sse/routers/dto/requests/requests_llm.txt +0 -83
- solace_agent_mesh/gateway/http_sse/routers/dto/responses/responses_llm.txt +0 -107
- solace_agent_mesh/gateway/http_sse/routers/routers_llm.txt +0 -314
- solace_agent_mesh/gateway/http_sse/services/services_llm.txt +0 -297
- solace_agent_mesh/gateway/http_sse/shared/__init__.py +0 -146
- solace_agent_mesh/gateway/http_sse/shared/shared_llm.txt +0 -285
- solace_agent_mesh/gateway/http_sse/utils/utils_llm.txt +0 -47
- solace_agent_mesh/llm.txt +0 -228
- solace_agent_mesh/llm_detail.txt +0 -2835
- solace_agent_mesh/solace_agent_mesh_llm.txt +0 -362
- solace_agent_mesh/solace_agent_mesh_llm_detail.txt +0 -8599
- solace_agent_mesh/templates/logging_config_template.ini +0 -45
- solace_agent_mesh/templates/templates_llm.txt +0 -147
- solace_agent_mesh-1.6.1.dist-info/RECORD +0 -525
- /solace_agent_mesh/assets/docs/assets/js/{main.b12eac43.js.LICENSE.txt → main.d634009f.js.LICENSE.txt} +0 -0
- /solace_agent_mesh/{gateway/http_sse/shared → shared/api}/auth_utils.py +0 -0
- /solace_agent_mesh/{gateway/http_sse/shared → shared/api}/pagination.py +0 -0
- /solace_agent_mesh/{gateway/http_sse/shared → shared/api}/response_utils.py +0 -0
- /solace_agent_mesh/{gateway/http_sse/shared → shared/exceptions}/error_dto.py +0 -0
- /solace_agent_mesh/{gateway/http_sse/shared → shared/exceptions}/exceptions.py +0 -0
- /solace_agent_mesh/{gateway/http_sse/shared → shared/utils}/enums.py +0 -0
- /solace_agent_mesh/{gateway/http_sse/shared → shared/utils}/timestamp_utils.py +0 -0
- /solace_agent_mesh/{gateway/http_sse/shared → shared/utils}/types.py +0 -0
- /solace_agent_mesh/{gateway/http_sse/shared → shared/utils}/utils.py +0 -0
- {solace_agent_mesh-1.6.1.dist-info → solace_agent_mesh-1.13.2.dist-info}/entry_points.txt +0 -0
- {solace_agent_mesh-1.6.1.dist-info → solace_agent_mesh-1.13.2.dist-info}/licenses/LICENSE +0 -0
|
@@ -2,9 +2,9 @@
|
|
|
2
2
|
Custom Solace AI Connector Component to host the FastAPI backend for the Web UI.
|
|
3
3
|
"""
|
|
4
4
|
|
|
5
|
-
import logging
|
|
6
5
|
import asyncio
|
|
7
6
|
import json
|
|
7
|
+
import logging
|
|
8
8
|
import queue
|
|
9
9
|
import re
|
|
10
10
|
import threading
|
|
@@ -15,22 +15,20 @@ from typing import Any
|
|
|
15
15
|
import uvicorn
|
|
16
16
|
from fastapi import FastAPI, UploadFile
|
|
17
17
|
from fastapi import Request as FastAPIRequest
|
|
18
|
-
|
|
18
|
+
from solace_ai_connector.common.event import Event, EventType
|
|
19
19
|
from solace_ai_connector.components.inputs_outputs.broker_input import BrokerInput
|
|
20
20
|
from solace_ai_connector.flow.app import App as SACApp
|
|
21
|
-
from solace_ai_connector.common.event import Event, EventType
|
|
22
21
|
|
|
23
22
|
from ...common.agent_registry import AgentRegistry
|
|
24
23
|
from ...core_a2a.service import CoreA2AService
|
|
25
24
|
from ...gateway.base.component import BaseGatewayComponent
|
|
26
25
|
from ...gateway.http_sse.session_manager import SessionManager
|
|
27
26
|
from ...gateway.http_sse.sse_manager import SSEManager
|
|
28
|
-
from .
|
|
27
|
+
from . import dependencies
|
|
29
28
|
from .components import VisualizationForwarderComponent
|
|
30
29
|
from .components.task_logger_forwarder import TaskLoggerForwarderComponent
|
|
31
|
-
from .services.feedback_service import FeedbackService
|
|
32
30
|
from .services.task_logger_service import TaskLoggerService
|
|
33
|
-
from . import
|
|
31
|
+
from .sse_event_buffer import SSEEventBuffer
|
|
34
32
|
|
|
35
33
|
log = logging.getLogger(__name__)
|
|
36
34
|
|
|
@@ -97,7 +95,16 @@ class WebUIBackendComponent(BaseGatewayComponent):
|
|
|
97
95
|
app_config = component_config.get("app_config", {})
|
|
98
96
|
resolve_uris = app_config.get("resolve_artifact_uris_in_gateway", True)
|
|
99
97
|
|
|
100
|
-
|
|
98
|
+
# HTTP SSE gateway configuration:
|
|
99
|
+
# - supports_inline_artifact_resolution=True: Artifacts are converted to FileParts
|
|
100
|
+
# during embed resolution and rendered inline in the web UI
|
|
101
|
+
# - filter_tool_data_parts=False: Web UI displays all parts including tool execution details
|
|
102
|
+
super().__init__(
|
|
103
|
+
resolve_artifact_uris_in_gateway=resolve_uris,
|
|
104
|
+
supports_inline_artifact_resolution=True,
|
|
105
|
+
filter_tool_data_parts=False,
|
|
106
|
+
**kwargs
|
|
107
|
+
)
|
|
101
108
|
log.info("%s Initializing Web UI Backend Component...", self.log_identifier)
|
|
102
109
|
|
|
103
110
|
try:
|
|
@@ -115,6 +122,14 @@ class WebUIBackendComponent(BaseGatewayComponent):
|
|
|
115
122
|
self.ssl_keyfile = self.get_config("ssl_keyfile", "")
|
|
116
123
|
self.ssl_certfile = self.get_config("ssl_certfile", "")
|
|
117
124
|
self.ssl_keyfile_password = self.get_config("ssl_keyfile_password", "")
|
|
125
|
+
self.model_config = self.get_config("model", None)
|
|
126
|
+
|
|
127
|
+
# OAuth2 configuration (enterprise feature - defaults to community mode)
|
|
128
|
+
self.external_auth_service_url = self.get_config("external_auth_service_url", "")
|
|
129
|
+
self.external_auth_provider = self.get_config("external_auth_provider", "generic")
|
|
130
|
+
|
|
131
|
+
# frontend_server_url is optional - empty string means frontend uses relative URLs
|
|
132
|
+
self.frontend_server_url = self.get_config("frontend_server_url", "")
|
|
118
133
|
|
|
119
134
|
log.info(
|
|
120
135
|
"%s WebUI-specific configuration retrieved (Host: %s, Port: %d).",
|
|
@@ -126,16 +141,15 @@ class WebUIBackendComponent(BaseGatewayComponent):
|
|
|
126
141
|
log.error("%s Failed to retrieve configuration: %s", self.log_identifier, e)
|
|
127
142
|
raise ValueError(f"Configuration retrieval error: {e}") from e
|
|
128
143
|
|
|
129
|
-
sse_max_queue_size = self.get_config("sse_max_queue_size", 200)
|
|
144
|
+
self.sse_max_queue_size = self.get_config("sse_max_queue_size", 200)
|
|
130
145
|
sse_buffer_max_age_seconds = self.get_config("sse_buffer_max_age_seconds", 600)
|
|
131
146
|
|
|
132
147
|
self.sse_event_buffer = SSEEventBuffer(
|
|
133
|
-
max_queue_size=sse_max_queue_size,
|
|
148
|
+
max_queue_size=self.sse_max_queue_size,
|
|
134
149
|
max_age_seconds=sse_buffer_max_age_seconds,
|
|
135
150
|
)
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
)
|
|
151
|
+
# SSE manager will be initialized after database setup
|
|
152
|
+
self.sse_manager = None
|
|
139
153
|
|
|
140
154
|
self._sse_cleanup_timer_id = f"sse_cleanup_{self.gateway_id}"
|
|
141
155
|
cleanup_interval_sec = self.get_config(
|
|
@@ -146,11 +160,14 @@ class WebUIBackendComponent(BaseGatewayComponent):
|
|
|
146
160
|
timer_id=self._sse_cleanup_timer_id,
|
|
147
161
|
interval_ms=cleanup_interval_sec * 1000,
|
|
148
162
|
)
|
|
149
|
-
|
|
163
|
+
|
|
150
164
|
# Set up health check timer for agent registry
|
|
151
165
|
from ...common.constants import HEALTH_CHECK_INTERVAL_SECONDS
|
|
166
|
+
|
|
152
167
|
self.health_check_timer_id = f"agent_health_check_{self.gateway_id}"
|
|
153
|
-
health_check_interval_seconds = self.get_config(
|
|
168
|
+
health_check_interval_seconds = self.get_config(
|
|
169
|
+
"agent_health_check_interval_seconds", HEALTH_CHECK_INTERVAL_SECONDS
|
|
170
|
+
)
|
|
154
171
|
if health_check_interval_seconds > 0:
|
|
155
172
|
log.info(
|
|
156
173
|
"%s Scheduling agent health check every %d seconds.",
|
|
@@ -181,8 +198,9 @@ class WebUIBackendComponent(BaseGatewayComponent):
|
|
|
181
198
|
else:
|
|
182
199
|
# Memory storage or no explicit configuration - no persistence service needed
|
|
183
200
|
self.database_url = None
|
|
184
|
-
|
|
185
|
-
|
|
201
|
+
|
|
202
|
+
# Validate that features requiring runtime database persistence are not enabled without database
|
|
203
|
+
if self.database_url is None:
|
|
186
204
|
task_logging_config = self.get_config("task_logging", {})
|
|
187
205
|
if task_logging_config.get("enabled", False):
|
|
188
206
|
raise ValueError(
|
|
@@ -190,15 +208,17 @@ class WebUIBackendComponent(BaseGatewayComponent):
|
|
|
190
208
|
"Either set session_service.type='sql' with a valid database_url, "
|
|
191
209
|
"or disable task_logging.enabled."
|
|
192
210
|
)
|
|
193
|
-
|
|
211
|
+
|
|
194
212
|
feedback_config = self.get_config("feedback_publishing", {})
|
|
195
213
|
if feedback_config.get("enabled", False):
|
|
196
214
|
log.warning(
|
|
197
215
|
"%s Feedback publishing is enabled but database persistence is not configured. "
|
|
198
216
|
"Feedback will only be published to the broker, not stored locally.",
|
|
199
|
-
self.log_identifier
|
|
217
|
+
self.log_identifier,
|
|
200
218
|
)
|
|
201
219
|
|
|
220
|
+
platform_config = self.get_config("platform_service", {})
|
|
221
|
+
self.platform_service_url = platform_config.get("url", "")
|
|
202
222
|
component_config = self.get_config("component_config", {})
|
|
203
223
|
app_config = component_config.get("app_config", {})
|
|
204
224
|
|
|
@@ -226,6 +246,10 @@ class WebUIBackendComponent(BaseGatewayComponent):
|
|
|
226
246
|
self._task_logger_broker_input: BrokerInput | None = None
|
|
227
247
|
self._task_logger_processor_task: asyncio.Task | None = None
|
|
228
248
|
self.task_logger_service: TaskLoggerService | None = None
|
|
249
|
+
|
|
250
|
+
# Background task monitor
|
|
251
|
+
self.background_task_monitor = None
|
|
252
|
+
self._background_task_monitor_timer_id = None
|
|
229
253
|
|
|
230
254
|
# Initialize SAM Events service for system events
|
|
231
255
|
from ...common.sam_events import SamEventService
|
|
@@ -241,27 +265,33 @@ class WebUIBackendComponent(BaseGatewayComponent):
|
|
|
241
265
|
self._data_retention_timer_id = None
|
|
242
266
|
data_retention_config = self.get_config("data_retention", {})
|
|
243
267
|
if data_retention_config.get("enabled", True):
|
|
244
|
-
log.info(
|
|
245
|
-
|
|
268
|
+
log.info(
|
|
269
|
+
"%s Data retention is enabled. Initializing service and timer...",
|
|
270
|
+
self.log_identifier,
|
|
271
|
+
)
|
|
272
|
+
|
|
246
273
|
# Import and initialize the DataRetentionService
|
|
247
274
|
from .services.data_retention_service import DataRetentionService
|
|
248
|
-
|
|
275
|
+
|
|
249
276
|
session_factory = None
|
|
250
277
|
if self.database_url:
|
|
251
278
|
# SessionLocal will be initialized later in setup_dependencies
|
|
252
279
|
# We'll pass a lambda that returns SessionLocal when called
|
|
253
|
-
session_factory = lambda:
|
|
254
|
-
|
|
280
|
+
session_factory = lambda: (
|
|
281
|
+
dependencies.SessionLocal() if dependencies.SessionLocal else None
|
|
282
|
+
)
|
|
283
|
+
|
|
255
284
|
self.data_retention_service = DataRetentionService(
|
|
256
|
-
session_factory=session_factory,
|
|
257
|
-
config=data_retention_config
|
|
285
|
+
session_factory=session_factory, config=data_retention_config
|
|
258
286
|
)
|
|
259
|
-
|
|
287
|
+
|
|
260
288
|
# Create and start the cleanup timer
|
|
261
|
-
cleanup_interval_hours = data_retention_config.get(
|
|
289
|
+
cleanup_interval_hours = data_retention_config.get(
|
|
290
|
+
"cleanup_interval_hours", 24
|
|
291
|
+
)
|
|
262
292
|
cleanup_interval_ms = cleanup_interval_hours * 60 * 60 * 1000
|
|
263
293
|
self._data_retention_timer_id = f"data_retention_cleanup_{self.gateway_id}"
|
|
264
|
-
|
|
294
|
+
|
|
265
295
|
self.add_timer(
|
|
266
296
|
delay_ms=cleanup_interval_ms,
|
|
267
297
|
timer_id=self._data_retention_timer_id,
|
|
@@ -274,14 +304,35 @@ class WebUIBackendComponent(BaseGatewayComponent):
|
|
|
274
304
|
cleanup_interval_hours,
|
|
275
305
|
)
|
|
276
306
|
else:
|
|
277
|
-
log.info(
|
|
307
|
+
log.info(
|
|
308
|
+
"%s Data retention is disabled via configuration.", self.log_identifier
|
|
309
|
+
)
|
|
310
|
+
|
|
311
|
+
if self.database_url:
|
|
312
|
+
log.info("%s Running database migrations...", self.log_identifier)
|
|
313
|
+
self._run_database_migrations()
|
|
314
|
+
log.info("%s Database migrations completed", self.log_identifier)
|
|
278
315
|
|
|
279
316
|
log.info("%s Web UI Backend Component initialized.", self.log_identifier)
|
|
280
317
|
|
|
318
|
+
def _run_database_migrations(self):
|
|
319
|
+
"""Run database migrations synchronously during __init__."""
|
|
320
|
+
try:
|
|
321
|
+
from ...gateway.http_sse.main import _setup_database
|
|
322
|
+
_setup_database(self.database_url)
|
|
323
|
+
except Exception as e:
|
|
324
|
+
log.error(
|
|
325
|
+
"%s Failed to run database migrations: %s",
|
|
326
|
+
self.log_identifier,
|
|
327
|
+
e,
|
|
328
|
+
exc_info=True
|
|
329
|
+
)
|
|
330
|
+
raise RuntimeError(f"Database migration failed during component initialization: {e}") from e
|
|
331
|
+
|
|
281
332
|
def process_event(self, event: Event):
|
|
282
333
|
if event.event_type == EventType.TIMER:
|
|
283
334
|
timer_id = event.data.get("timer_id")
|
|
284
|
-
|
|
335
|
+
|
|
285
336
|
if timer_id == self._sse_cleanup_timer_id:
|
|
286
337
|
log.debug("%s SSE buffer cleanup timer triggered.", self.log_identifier)
|
|
287
338
|
self.sse_event_buffer.cleanup_stale_buffers()
|
|
@@ -290,9 +341,11 @@ class WebUIBackendComponent(BaseGatewayComponent):
|
|
|
290
341
|
log.debug("%s Agent health check timer triggered.", self.log_identifier)
|
|
291
342
|
self._check_agent_health()
|
|
292
343
|
return
|
|
293
|
-
|
|
344
|
+
|
|
294
345
|
if timer_id == self._data_retention_timer_id:
|
|
295
|
-
log.debug(
|
|
346
|
+
log.debug(
|
|
347
|
+
"%s Data retention cleanup timer triggered.", self.log_identifier
|
|
348
|
+
)
|
|
296
349
|
if self.data_retention_service:
|
|
297
350
|
try:
|
|
298
351
|
self.data_retention_service.cleanup_old_data()
|
|
@@ -309,6 +362,27 @@ class WebUIBackendComponent(BaseGatewayComponent):
|
|
|
309
362
|
self.log_identifier,
|
|
310
363
|
)
|
|
311
364
|
return
|
|
365
|
+
|
|
366
|
+
if timer_id == self._background_task_monitor_timer_id:
|
|
367
|
+
log.debug("%s Background task monitor timer triggered.", self.log_identifier)
|
|
368
|
+
if self.background_task_monitor:
|
|
369
|
+
loop = self.get_async_loop()
|
|
370
|
+
if loop and loop.is_running():
|
|
371
|
+
asyncio.run_coroutine_threadsafe(
|
|
372
|
+
self.background_task_monitor.check_timeouts(),
|
|
373
|
+
loop
|
|
374
|
+
)
|
|
375
|
+
else:
|
|
376
|
+
log.warning(
|
|
377
|
+
"%s Async loop not available for background task monitor.",
|
|
378
|
+
self.log_identifier
|
|
379
|
+
)
|
|
380
|
+
else:
|
|
381
|
+
log.warning(
|
|
382
|
+
"%s Background task monitor timer fired but service is not initialized.",
|
|
383
|
+
self.log_identifier,
|
|
384
|
+
)
|
|
385
|
+
return
|
|
312
386
|
|
|
313
387
|
super().process_event(event)
|
|
314
388
|
|
|
@@ -364,7 +438,7 @@ class WebUIBackendComponent(BaseGatewayComponent):
|
|
|
364
438
|
broker_input_cfg = {
|
|
365
439
|
"component_module": "broker_input",
|
|
366
440
|
"component_name": f"{self.gateway_id}_viz_broker_input",
|
|
367
|
-
"broker_queue_name": f"{self.namespace.strip('/')}/q/gdk/viz/{self.gateway_id}
|
|
441
|
+
"broker_queue_name": f"{self.namespace.strip('/')}/q/gdk/viz/{self.gateway_id}",
|
|
368
442
|
"create_queue_on_start": True,
|
|
369
443
|
"component_config": {
|
|
370
444
|
"broker_url": main_broker_config.get("broker_url"),
|
|
@@ -386,7 +460,9 @@ class WebUIBackendComponent(BaseGatewayComponent):
|
|
|
386
460
|
forwarder_cfg = {
|
|
387
461
|
"component_class": VisualizationForwarderComponent,
|
|
388
462
|
"component_name": f"{self.gateway_id}_viz_forwarder",
|
|
389
|
-
"component_config": {
|
|
463
|
+
"component_config": {
|
|
464
|
+
"target_queue_ref": self._visualization_message_queue
|
|
465
|
+
},
|
|
390
466
|
}
|
|
391
467
|
|
|
392
468
|
flow_config = {
|
|
@@ -437,7 +513,7 @@ class WebUIBackendComponent(BaseGatewayComponent):
|
|
|
437
513
|
raise RuntimeError(
|
|
438
514
|
"Visualization flow setup error: BrokerInput not found."
|
|
439
515
|
)
|
|
440
|
-
log.
|
|
516
|
+
log.debug(
|
|
441
517
|
"%s Obtained reference to internal BrokerInput component.",
|
|
442
518
|
log_id_prefix,
|
|
443
519
|
)
|
|
@@ -496,7 +572,7 @@ class WebUIBackendComponent(BaseGatewayComponent):
|
|
|
496
572
|
broker_input_cfg = {
|
|
497
573
|
"component_module": "broker_input",
|
|
498
574
|
"component_name": f"{self.gateway_id}_task_log_broker_input",
|
|
499
|
-
"broker_queue_name": f"{self.namespace.strip('/')}/q/gdk/task_log/{self.gateway_id}
|
|
575
|
+
"broker_queue_name": f"{self.namespace.strip('/')}/q/gdk/task_log/{self.gateway_id}",
|
|
500
576
|
"create_queue_on_start": True,
|
|
501
577
|
"component_config": {
|
|
502
578
|
"broker_url": main_broker_config.get("broker_url"),
|
|
@@ -786,11 +862,34 @@ class WebUIBackendComponent(BaseGatewayComponent):
|
|
|
786
862
|
event_details["direction"],
|
|
787
863
|
)
|
|
788
864
|
except asyncio.QueueFull:
|
|
789
|
-
|
|
790
|
-
|
|
791
|
-
|
|
792
|
-
|
|
793
|
-
|
|
865
|
+
# Check if this is a background task
|
|
866
|
+
is_background = False
|
|
867
|
+
if task_id_for_context and self.database_url:
|
|
868
|
+
try:
|
|
869
|
+
from .repository.task_repository import TaskRepository
|
|
870
|
+
db = dependencies.SessionLocal()
|
|
871
|
+
try:
|
|
872
|
+
repo = TaskRepository()
|
|
873
|
+
task = repo.find_by_id(db, task_id_for_context)
|
|
874
|
+
is_background = task and task.background_execution_enabled
|
|
875
|
+
finally:
|
|
876
|
+
db.close()
|
|
877
|
+
except Exception:
|
|
878
|
+
pass
|
|
879
|
+
|
|
880
|
+
if is_background:
|
|
881
|
+
log.debug(
|
|
882
|
+
"%s SSE queue full for stream %s. Dropping visualization message for background task %s.",
|
|
883
|
+
log_id_prefix,
|
|
884
|
+
stream_id,
|
|
885
|
+
task_id_for_context,
|
|
886
|
+
)
|
|
887
|
+
else:
|
|
888
|
+
log.warning(
|
|
889
|
+
"%s SSE queue full for stream %s. Visualization message dropped.",
|
|
890
|
+
log_id_prefix,
|
|
891
|
+
stream_id,
|
|
892
|
+
)
|
|
794
893
|
except Exception as send_err:
|
|
795
894
|
log.error(
|
|
796
895
|
"%s Error sending formatted message to SSE queue for stream %s: %s",
|
|
@@ -883,7 +982,7 @@ class WebUIBackendComponent(BaseGatewayComponent):
|
|
|
883
982
|
Manages global subscription reference counts.
|
|
884
983
|
"""
|
|
885
984
|
log_id_prefix = f"{self.log_identifier}[AddVizSub:{stream_id}]"
|
|
886
|
-
log.
|
|
985
|
+
log.debug(
|
|
887
986
|
"%s Attempting to add subscription to topic: %s", log_id_prefix, topic_str
|
|
888
987
|
)
|
|
889
988
|
|
|
@@ -1164,7 +1263,12 @@ class WebUIBackendComponent(BaseGatewayComponent):
|
|
|
1164
1263
|
log_id_prefix,
|
|
1165
1264
|
username,
|
|
1166
1265
|
)
|
|
1167
|
-
return {
|
|
1266
|
+
return {
|
|
1267
|
+
"id": username,
|
|
1268
|
+
"name": username,
|
|
1269
|
+
"email": username,
|
|
1270
|
+
"user_info": user_info,
|
|
1271
|
+
}
|
|
1168
1272
|
|
|
1169
1273
|
log.debug(
|
|
1170
1274
|
"%s No authenticated user in request.state, falling back to SessionManager.",
|
|
@@ -1198,19 +1302,79 @@ class WebUIBackendComponent(BaseGatewayComponent):
|
|
|
1198
1302
|
|
|
1199
1303
|
self.fastapi_app = fastapi_app_instance
|
|
1200
1304
|
|
|
1201
|
-
setup_dependencies(self
|
|
1305
|
+
setup_dependencies(self)
|
|
1202
1306
|
|
|
1203
1307
|
# Instantiate services that depend on the database session factory.
|
|
1204
1308
|
# This must be done *after* setup_dependencies has run.
|
|
1205
1309
|
session_factory = dependencies.SessionLocal if self.database_url else None
|
|
1310
|
+
|
|
1311
|
+
# Initialize SSE manager with session factory for background task detection
|
|
1312
|
+
self.sse_manager = SSEManager(
|
|
1313
|
+
max_queue_size=self.sse_max_queue_size,
|
|
1314
|
+
event_buffer=self.sse_event_buffer,
|
|
1315
|
+
session_factory=session_factory
|
|
1316
|
+
)
|
|
1317
|
+
log.debug(
|
|
1318
|
+
"%s SSE manager initialized with database session factory.",
|
|
1319
|
+
self.log_identifier,
|
|
1320
|
+
)
|
|
1206
1321
|
task_logging_config = self.get_config("task_logging", {})
|
|
1207
1322
|
self.task_logger_service = TaskLoggerService(
|
|
1208
1323
|
session_factory=session_factory, config=task_logging_config
|
|
1209
1324
|
)
|
|
1210
|
-
log.
|
|
1325
|
+
log.debug(
|
|
1211
1326
|
"%s Services dependent on database session factory have been initialized.",
|
|
1212
1327
|
self.log_identifier,
|
|
1213
1328
|
)
|
|
1329
|
+
|
|
1330
|
+
# Initialize background task monitor if task logging is enabled
|
|
1331
|
+
if self.database_url and task_logging_config.get("enabled", False):
|
|
1332
|
+
from .services.background_task_monitor import BackgroundTaskMonitor
|
|
1333
|
+
from .services.task_service import TaskService
|
|
1334
|
+
|
|
1335
|
+
# Create task service for cancellation operations
|
|
1336
|
+
task_service = TaskService(
|
|
1337
|
+
core_a2a_service=self.core_a2a_service,
|
|
1338
|
+
publish_func=self.publish_a2a,
|
|
1339
|
+
namespace=self.namespace,
|
|
1340
|
+
gateway_id=self.gateway_id,
|
|
1341
|
+
sse_manager=self.sse_manager,
|
|
1342
|
+
task_context_map=self.task_context_manager._contexts,
|
|
1343
|
+
task_context_lock=self.task_context_manager._lock,
|
|
1344
|
+
app_name=self.name,
|
|
1345
|
+
)
|
|
1346
|
+
|
|
1347
|
+
# Get timeout configuration
|
|
1348
|
+
background_config = self.get_config("background_tasks", {})
|
|
1349
|
+
default_timeout_ms = background_config.get("default_timeout_ms", 3600000) # 1 hour
|
|
1350
|
+
|
|
1351
|
+
self.background_task_monitor = BackgroundTaskMonitor(
|
|
1352
|
+
session_factory=session_factory,
|
|
1353
|
+
task_service=task_service,
|
|
1354
|
+
default_timeout_ms=default_timeout_ms,
|
|
1355
|
+
)
|
|
1356
|
+
|
|
1357
|
+
# Create timer for periodic timeout checks
|
|
1358
|
+
monitor_interval_ms = background_config.get("monitor_interval_ms", 300000) # 5 minutes
|
|
1359
|
+
self._background_task_monitor_timer_id = f"background_task_monitor_{self.gateway_id}"
|
|
1360
|
+
|
|
1361
|
+
self.add_timer(
|
|
1362
|
+
delay_ms=monitor_interval_ms,
|
|
1363
|
+
timer_id=self._background_task_monitor_timer_id,
|
|
1364
|
+
interval_ms=monitor_interval_ms,
|
|
1365
|
+
)
|
|
1366
|
+
|
|
1367
|
+
log.info(
|
|
1368
|
+
"%s Background task monitor initialized with %dms check interval and %dms default timeout",
|
|
1369
|
+
self.log_identifier,
|
|
1370
|
+
monitor_interval_ms,
|
|
1371
|
+
default_timeout_ms
|
|
1372
|
+
)
|
|
1373
|
+
else:
|
|
1374
|
+
log.info(
|
|
1375
|
+
"%s Background task monitor not initialized (task logging disabled or no database)",
|
|
1376
|
+
self.log_identifier
|
|
1377
|
+
)
|
|
1214
1378
|
|
|
1215
1379
|
port = (
|
|
1216
1380
|
self.fastapi_https_port
|
|
@@ -1227,6 +1391,7 @@ class WebUIBackendComponent(BaseGatewayComponent):
|
|
|
1227
1391
|
ssl_keyfile=self.ssl_keyfile,
|
|
1228
1392
|
ssl_certfile=self.ssl_certfile,
|
|
1229
1393
|
ssl_keyfile_password=self.ssl_keyfile_password,
|
|
1394
|
+
log_config=None
|
|
1230
1395
|
)
|
|
1231
1396
|
self.uvicorn_server = uvicorn.Server(config)
|
|
1232
1397
|
|
|
@@ -1238,14 +1403,14 @@ class WebUIBackendComponent(BaseGatewayComponent):
|
|
|
1238
1403
|
)
|
|
1239
1404
|
try:
|
|
1240
1405
|
self.fastapi_event_loop = asyncio.get_running_loop()
|
|
1241
|
-
log.
|
|
1406
|
+
log.debug(
|
|
1242
1407
|
"%s [_start_listener] Captured FastAPI event loop via startup event: %s",
|
|
1243
1408
|
self.log_identifier,
|
|
1244
1409
|
self.fastapi_event_loop,
|
|
1245
1410
|
)
|
|
1246
1411
|
|
|
1247
1412
|
if self.fastapi_event_loop:
|
|
1248
|
-
log.
|
|
1413
|
+
log.debug(
|
|
1249
1414
|
"%s Ensuring visualization flow is running...",
|
|
1250
1415
|
self.log_identifier,
|
|
1251
1416
|
)
|
|
@@ -1255,7 +1420,7 @@ class WebUIBackendComponent(BaseGatewayComponent):
|
|
|
1255
1420
|
self._visualization_processor_task is None
|
|
1256
1421
|
or self._visualization_processor_task.done()
|
|
1257
1422
|
):
|
|
1258
|
-
log.
|
|
1423
|
+
log.debug(
|
|
1259
1424
|
"%s Starting visualization message processor task.",
|
|
1260
1425
|
self.log_identifier,
|
|
1261
1426
|
)
|
|
@@ -1265,7 +1430,7 @@ class WebUIBackendComponent(BaseGatewayComponent):
|
|
|
1265
1430
|
)
|
|
1266
1431
|
)
|
|
1267
1432
|
else:
|
|
1268
|
-
log.
|
|
1433
|
+
log.debug(
|
|
1269
1434
|
"%s Visualization message processor task already running.",
|
|
1270
1435
|
self.log_identifier,
|
|
1271
1436
|
)
|
|
@@ -1297,7 +1462,9 @@ class WebUIBackendComponent(BaseGatewayComponent):
|
|
|
1297
1462
|
self.log_identifier,
|
|
1298
1463
|
)
|
|
1299
1464
|
else:
|
|
1300
|
-
log.info(
|
|
1465
|
+
log.info(
|
|
1466
|
+
"%s Task logging is disabled.", self.log_identifier
|
|
1467
|
+
)
|
|
1301
1468
|
else:
|
|
1302
1469
|
log.error(
|
|
1303
1470
|
"%s FastAPI event loop not captured. Cannot start visualization processor.",
|
|
@@ -1312,27 +1479,6 @@ class WebUIBackendComponent(BaseGatewayComponent):
|
|
|
1312
1479
|
)
|
|
1313
1480
|
self.stop_signal.set()
|
|
1314
1481
|
|
|
1315
|
-
try:
|
|
1316
|
-
from solace_agent_mesh_enterprise.init_enterprise import start_enterprise_background_tasks
|
|
1317
|
-
log.info("%s Starting enterprise background tasks...", self.log_identifier)
|
|
1318
|
-
await start_enterprise_background_tasks(self)
|
|
1319
|
-
log.info("%s Enterprise background tasks started successfully", self.log_identifier)
|
|
1320
|
-
except ImportError:
|
|
1321
|
-
log.debug("%s Enterprise package not available - skipping background tasks", self.log_identifier)
|
|
1322
|
-
except RuntimeError as enterprise_err:
|
|
1323
|
-
log.warning(
|
|
1324
|
-
"%s Enterprise background tasks disabled: %s - Community features will continue normally",
|
|
1325
|
-
self.log_identifier,
|
|
1326
|
-
enterprise_err
|
|
1327
|
-
)
|
|
1328
|
-
except Exception as enterprise_err:
|
|
1329
|
-
log.error(
|
|
1330
|
-
"%s Failed to start enterprise background tasks: %s - Community features will continue normally",
|
|
1331
|
-
self.log_identifier,
|
|
1332
|
-
enterprise_err,
|
|
1333
|
-
exc_info=True
|
|
1334
|
-
)
|
|
1335
|
-
|
|
1336
1482
|
@self.fastapi_app.on_event("shutdown")
|
|
1337
1483
|
async def shutdown_event():
|
|
1338
1484
|
log.info(
|
|
@@ -1340,21 +1486,6 @@ class WebUIBackendComponent(BaseGatewayComponent):
|
|
|
1340
1486
|
self.log_identifier,
|
|
1341
1487
|
)
|
|
1342
1488
|
|
|
1343
|
-
try:
|
|
1344
|
-
from solace_agent_mesh_enterprise.init_enterprise import stop_enterprise_background_tasks
|
|
1345
|
-
log.info("%s Stopping enterprise background tasks...", self.log_identifier)
|
|
1346
|
-
await stop_enterprise_background_tasks()
|
|
1347
|
-
log.info("%s Enterprise background tasks stopped", self.log_identifier)
|
|
1348
|
-
except ImportError:
|
|
1349
|
-
log.debug("%s Enterprise package not available - no background tasks to stop", self.log_identifier)
|
|
1350
|
-
except Exception as enterprise_err:
|
|
1351
|
-
log.error(
|
|
1352
|
-
"%s Failed to stop enterprise background tasks: %s",
|
|
1353
|
-
self.log_identifier,
|
|
1354
|
-
enterprise_err,
|
|
1355
|
-
exc_info=True
|
|
1356
|
-
)
|
|
1357
|
-
|
|
1358
1489
|
self.fastapi_thread = threading.Thread(
|
|
1359
1490
|
target=self.uvicorn_server.run, daemon=True, name="FastAPI_Thread"
|
|
1360
1491
|
)
|
|
@@ -1417,18 +1548,27 @@ class WebUIBackendComponent(BaseGatewayComponent):
|
|
|
1417
1548
|
def cleanup(self):
|
|
1418
1549
|
"""Gracefully shuts down the component and the FastAPI server."""
|
|
1419
1550
|
log.info("%s Cleaning up Web UI Backend Component...", self.log_identifier)
|
|
1420
|
-
|
|
1551
|
+
|
|
1421
1552
|
# Cancel timers
|
|
1422
1553
|
self.cancel_timer(self._sse_cleanup_timer_id)
|
|
1423
1554
|
if self._data_retention_timer_id:
|
|
1424
1555
|
self.cancel_timer(self._data_retention_timer_id)
|
|
1425
1556
|
log.info("%s Cancelled data retention cleanup timer.", self.log_identifier)
|
|
1426
1557
|
|
|
1558
|
+
if self._background_task_monitor_timer_id:
|
|
1559
|
+
self.cancel_timer(self._background_task_monitor_timer_id)
|
|
1560
|
+
log.info("%s Cancelled background task monitor timer.", self.log_identifier)
|
|
1561
|
+
|
|
1427
1562
|
# Clean up data retention service
|
|
1428
1563
|
if self.data_retention_service:
|
|
1429
1564
|
self.data_retention_service = None
|
|
1430
1565
|
log.info("%s Data retention service cleaned up.", self.log_identifier)
|
|
1431
1566
|
|
|
1567
|
+
# Clean up background task monitor
|
|
1568
|
+
if self.background_task_monitor:
|
|
1569
|
+
self.background_task_monitor = None
|
|
1570
|
+
log.info("%s Background task monitor cleaned up.", self.log_identifier)
|
|
1571
|
+
|
|
1432
1572
|
self.cancel_timer(self.health_check_timer_id)
|
|
1433
1573
|
log.info("%s Cleaning up visualization resources...", self.log_identifier)
|
|
1434
1574
|
if self._visualization_message_queue:
|
|
@@ -1445,7 +1585,10 @@ class WebUIBackendComponent(BaseGatewayComponent):
|
|
|
1445
1585
|
)
|
|
1446
1586
|
self._visualization_processor_task.cancel()
|
|
1447
1587
|
|
|
1448
|
-
if
|
|
1588
|
+
if (
|
|
1589
|
+
self._task_logger_processor_task
|
|
1590
|
+
and not self._task_logger_processor_task.done()
|
|
1591
|
+
):
|
|
1449
1592
|
log.info("%s Cancelling task logger processor task...", self.log_identifier)
|
|
1450
1593
|
self._task_logger_processor_task.cancel()
|
|
1451
1594
|
|
|
@@ -1755,70 +1898,88 @@ class WebUIBackendComponent(BaseGatewayComponent):
|
|
|
1755
1898
|
|
|
1756
1899
|
def get_agent_registry(self) -> AgentRegistry:
|
|
1757
1900
|
return self.agent_registry
|
|
1758
|
-
|
|
1901
|
+
|
|
1759
1902
|
def _check_agent_health(self):
|
|
1760
1903
|
"""
|
|
1761
1904
|
Checks the health of peer agents and de-registers unresponsive ones.
|
|
1762
1905
|
This is called periodically by the health check timer.
|
|
1763
1906
|
Uses TTL-based expiration to determine if an agent is unresponsive.
|
|
1764
1907
|
"""
|
|
1765
|
-
|
|
1908
|
+
|
|
1766
1909
|
log.debug("%s Performing agent health check...", self.log_identifier)
|
|
1767
|
-
|
|
1910
|
+
|
|
1768
1911
|
# Get TTL from configuration or use default from constants
|
|
1769
|
-
from ...common.constants import
|
|
1770
|
-
|
|
1771
|
-
|
|
1912
|
+
from ...common.constants import (
|
|
1913
|
+
HEALTH_CHECK_INTERVAL_SECONDS,
|
|
1914
|
+
HEALTH_CHECK_TTL_SECONDS,
|
|
1915
|
+
)
|
|
1916
|
+
|
|
1917
|
+
ttl_seconds = self.get_config(
|
|
1918
|
+
"agent_health_check_ttl_seconds", HEALTH_CHECK_TTL_SECONDS
|
|
1919
|
+
)
|
|
1920
|
+
health_check_interval = self.get_config(
|
|
1921
|
+
"agent_health_check_interval_seconds", HEALTH_CHECK_INTERVAL_SECONDS
|
|
1922
|
+
)
|
|
1772
1923
|
|
|
1773
1924
|
log.debug(
|
|
1774
1925
|
"%s Health check configuration: interval=%d seconds, TTL=%d seconds",
|
|
1775
1926
|
self.log_identifier,
|
|
1776
1927
|
health_check_interval,
|
|
1777
|
-
ttl_seconds
|
|
1928
|
+
ttl_seconds,
|
|
1778
1929
|
)
|
|
1779
|
-
|
|
1930
|
+
|
|
1780
1931
|
# Validate configuration values
|
|
1781
|
-
if
|
|
1932
|
+
if (
|
|
1933
|
+
ttl_seconds <= 0
|
|
1934
|
+
or health_check_interval <= 0
|
|
1935
|
+
or ttl_seconds < health_check_interval
|
|
1936
|
+
):
|
|
1782
1937
|
log.error(
|
|
1783
1938
|
"%s agent_health_check_ttl_seconds (%d) and agent_health_check_interval_seconds (%d) must be positive and TTL must be greater than interval.",
|
|
1784
1939
|
self.log_identifier,
|
|
1785
1940
|
ttl_seconds,
|
|
1786
|
-
health_check_interval
|
|
1941
|
+
health_check_interval,
|
|
1787
1942
|
)
|
|
1788
|
-
raise ValueError(
|
|
1789
|
-
|
|
1943
|
+
raise ValueError(
|
|
1944
|
+
f"Invalid health check configuration. agent_health_check_ttl_seconds ({ttl_seconds}) and agent_health_check_interval_seconds ({health_check_interval}) must be positive and TTL must be greater than interval."
|
|
1945
|
+
)
|
|
1946
|
+
|
|
1790
1947
|
# Get all agent names from the registry
|
|
1791
1948
|
agent_names = self.agent_registry.get_agent_names()
|
|
1792
1949
|
total_agents = len(agent_names)
|
|
1793
1950
|
agents_to_deregister = []
|
|
1794
|
-
|
|
1795
|
-
log.debug(
|
|
1796
|
-
|
|
1951
|
+
|
|
1952
|
+
log.debug(
|
|
1953
|
+
"%s Checking health of %d peer agents", self.log_identifier, total_agents
|
|
1954
|
+
)
|
|
1955
|
+
|
|
1797
1956
|
for agent_name in agent_names:
|
|
1798
1957
|
# Check if the agent's TTL has expired
|
|
1799
|
-
is_expired, time_since_last_seen = self.agent_registry.check_ttl_expired(
|
|
1800
|
-
|
|
1958
|
+
is_expired, time_since_last_seen = self.agent_registry.check_ttl_expired(
|
|
1959
|
+
agent_name, ttl_seconds
|
|
1960
|
+
)
|
|
1961
|
+
|
|
1801
1962
|
if is_expired:
|
|
1802
1963
|
log.warning(
|
|
1803
1964
|
"%s Agent '%s' TTL has expired. De-registering. Time since last seen: %d seconds (TTL: %d seconds)",
|
|
1804
1965
|
self.log_identifier,
|
|
1805
1966
|
agent_name,
|
|
1806
1967
|
time_since_last_seen,
|
|
1807
|
-
ttl_seconds
|
|
1968
|
+
ttl_seconds,
|
|
1808
1969
|
)
|
|
1809
1970
|
agents_to_deregister.append(agent_name)
|
|
1810
|
-
|
|
1971
|
+
|
|
1811
1972
|
# De-register unresponsive agents
|
|
1812
1973
|
for agent_name in agents_to_deregister:
|
|
1813
1974
|
self._deregister_agent(agent_name)
|
|
1814
|
-
|
|
1815
|
-
log.
|
|
1975
|
+
|
|
1976
|
+
log.debug(
|
|
1816
1977
|
"%s Agent health check completed. Total agents: %d, De-registered: %d",
|
|
1817
1978
|
self.log_identifier,
|
|
1818
1979
|
total_agents,
|
|
1819
|
-
len(agents_to_deregister)
|
|
1980
|
+
len(agents_to_deregister),
|
|
1820
1981
|
)
|
|
1821
|
-
|
|
1982
|
+
|
|
1822
1983
|
def _deregister_agent(self, agent_name: str):
|
|
1823
1984
|
"""
|
|
1824
1985
|
De-registers an agent from the registry and publishes a de-registration event.
|
|
@@ -1865,52 +2026,6 @@ class WebUIBackendComponent(BaseGatewayComponent):
|
|
|
1865
2026
|
"""Returns the instance of the ConfigResolver."""
|
|
1866
2027
|
return self._config_resolver
|
|
1867
2028
|
|
|
1868
|
-
async def _resolve_embeds_for_persistence(
|
|
1869
|
-
self, message_content: str, session_id: str, user_id: str, log_identifier: str
|
|
1870
|
-
) -> str:
|
|
1871
|
-
"""
|
|
1872
|
-
Resolves embeds in a message for database storage.
|
|
1873
|
-
Returns the resolved text.
|
|
1874
|
-
|
|
1875
|
-
Args:
|
|
1876
|
-
message_content: The message text that may contain embeds
|
|
1877
|
-
session_id: The A2A session ID
|
|
1878
|
-
user_id: The user ID
|
|
1879
|
-
log_identifier: Logging identifier
|
|
1880
|
-
|
|
1881
|
-
Returns:
|
|
1882
|
-
The message with embeds resolved (or original if resolution fails)
|
|
1883
|
-
"""
|
|
1884
|
-
try:
|
|
1885
|
-
embed_context = {
|
|
1886
|
-
"artifact_service": self.shared_artifact_service,
|
|
1887
|
-
"session_context": {
|
|
1888
|
-
"app_name": self.gateway_id,
|
|
1889
|
-
"user_id": user_id,
|
|
1890
|
-
"session_id": session_id,
|
|
1891
|
-
},
|
|
1892
|
-
"config": self.get_embed_config(),
|
|
1893
|
-
}
|
|
1894
|
-
|
|
1895
|
-
resolved_text, _, _ = await resolve_embeds_in_string(
|
|
1896
|
-
text=message_content,
|
|
1897
|
-
context=embed_context,
|
|
1898
|
-
resolver_func=evaluate_embed,
|
|
1899
|
-
types_to_resolve=EARLY_EMBED_TYPES,
|
|
1900
|
-
log_identifier=log_identifier,
|
|
1901
|
-
config=embed_context["config"],
|
|
1902
|
-
)
|
|
1903
|
-
|
|
1904
|
-
return resolved_text
|
|
1905
|
-
|
|
1906
|
-
except Exception as e:
|
|
1907
|
-
log.warning(
|
|
1908
|
-
"%s Error resolving embeds for storage: %s. Using original message.",
|
|
1909
|
-
log_identifier,
|
|
1910
|
-
e,
|
|
1911
|
-
)
|
|
1912
|
-
return message_content
|
|
1913
|
-
|
|
1914
2029
|
def _start_listener(self) -> None:
|
|
1915
2030
|
"""
|
|
1916
2031
|
GDK Hook: Starts the FastAPI/Uvicorn server.
|
|
@@ -2052,6 +2167,15 @@ class WebUIBackendComponent(BaseGatewayComponent):
|
|
|
2052
2167
|
)
|
|
2053
2168
|
return
|
|
2054
2169
|
|
|
2170
|
+
try:
|
|
2171
|
+
from solace_agent_mesh_enterprise.auth.input_required import (
|
|
2172
|
+
handle_input_required_request,
|
|
2173
|
+
)
|
|
2174
|
+
|
|
2175
|
+
event_data = handle_input_required_request(event_data, sse_task_id, self)
|
|
2176
|
+
except ImportError:
|
|
2177
|
+
pass
|
|
2178
|
+
|
|
2055
2179
|
log.debug(
|
|
2056
2180
|
"%s Sending update for A2A Task ID %s to SSE Task ID %s. Final chunk: %s",
|
|
2057
2181
|
log_id_prefix,
|
|
@@ -2073,7 +2197,7 @@ class WebUIBackendComponent(BaseGatewayComponent):
|
|
|
2073
2197
|
await self.sse_manager.send_event(
|
|
2074
2198
|
task_id=sse_task_id, event_data=sse_payload, event_type=sse_event_type
|
|
2075
2199
|
)
|
|
2076
|
-
log.
|
|
2200
|
+
log.debug(
|
|
2077
2201
|
"%s Successfully sent %s via SSE for A2A Task ID %s.",
|
|
2078
2202
|
log_id_prefix,
|
|
2079
2203
|
sse_event_type,
|
|
@@ -2111,7 +2235,7 @@ class WebUIBackendComponent(BaseGatewayComponent):
|
|
|
2111
2235
|
)
|
|
2112
2236
|
return
|
|
2113
2237
|
|
|
2114
|
-
log.
|
|
2238
|
+
log.info(
|
|
2115
2239
|
"%s Sending final response for A2A Task ID %s to SSE Task ID %s.",
|
|
2116
2240
|
log_id_prefix,
|
|
2117
2241
|
a2a_task_id,
|
|
@@ -2127,7 +2251,7 @@ class WebUIBackendComponent(BaseGatewayComponent):
|
|
|
2127
2251
|
await self.sse_manager.send_event(
|
|
2128
2252
|
task_id=sse_task_id, event_data=sse_payload, event_type="final_response"
|
|
2129
2253
|
)
|
|
2130
|
-
log.
|
|
2254
|
+
log.debug(
|
|
2131
2255
|
"%s Successfully sent final_response via SSE for A2A Task ID %s.",
|
|
2132
2256
|
log_id_prefix,
|
|
2133
2257
|
a2a_task_id,
|
|
@@ -2147,6 +2271,7 @@ class WebUIBackendComponent(BaseGatewayComponent):
|
|
|
2147
2271
|
log_id_prefix,
|
|
2148
2272
|
sse_task_id,
|
|
2149
2273
|
)
|
|
2274
|
+
|
|
2150
2275
|
|
|
2151
2276
|
async def _send_error_to_external(
|
|
2152
2277
|
self, external_request_context: dict[str, Any], error_data: JSONRPCError
|