ciris-agent 1.7.7__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.
- ciris_adapters/README.md +113 -0
- ciris_adapters/__init__.py +30 -0
- ciris_adapters/ciris_covenant_metrics/README.md +144 -0
- ciris_adapters/ciris_covenant_metrics/__init__.py +36 -0
- ciris_adapters/ciris_covenant_metrics/adapter.py +249 -0
- ciris_adapters/ciris_covenant_metrics/manifest.json +152 -0
- ciris_adapters/ciris_covenant_metrics/services.py +403 -0
- ciris_adapters/ciris_hosted_tools/__init__.py +24 -0
- ciris_adapters/ciris_hosted_tools/adapter.py +169 -0
- ciris_adapters/ciris_hosted_tools/manifest.json +94 -0
- ciris_adapters/ciris_hosted_tools/services.py +744 -0
- ciris_adapters/external_data_sql/README.md +559 -0
- ciris_adapters/external_data_sql/__init__.py +43 -0
- ciris_adapters/external_data_sql/adapter.py +144 -0
- ciris_adapters/external_data_sql/configurable.py +315 -0
- ciris_adapters/external_data_sql/dialects/__init__.py +37 -0
- ciris_adapters/external_data_sql/dialects/base.py +133 -0
- ciris_adapters/external_data_sql/dialects/mysql.py +63 -0
- ciris_adapters/external_data_sql/dialects/postgresql.py +59 -0
- ciris_adapters/external_data_sql/dialects/sqlite.py +62 -0
- ciris_adapters/external_data_sql/example_config.json +88 -0
- ciris_adapters/external_data_sql/example_privacy_schema.yaml +127 -0
- ciris_adapters/external_data_sql/manifest.json +195 -0
- ciris_adapters/external_data_sql/privacy_schema_loader.py +189 -0
- ciris_adapters/external_data_sql/protocol.py +101 -0
- ciris_adapters/external_data_sql/schemas.py +146 -0
- ciris_adapters/external_data_sql/service.py +1547 -0
- ciris_adapters/external_data_sql/service_old.py +492 -0
- ciris_adapters/home_assistant/__init__.py +63 -0
- ciris_adapters/home_assistant/adapter.py +201 -0
- ciris_adapters/home_assistant/communication_service.py +347 -0
- ciris_adapters/home_assistant/configurable.py +667 -0
- ciris_adapters/home_assistant/manifest.json +203 -0
- ciris_adapters/home_assistant/schemas.py +129 -0
- ciris_adapters/home_assistant/service.py +751 -0
- ciris_adapters/home_assistant/tool_service.py +441 -0
- ciris_adapters/mcp_client/__init__.py +82 -0
- ciris_adapters/mcp_client/adapter.py +847 -0
- ciris_adapters/mcp_client/config.py +280 -0
- ciris_adapters/mcp_client/configurable.py +422 -0
- ciris_adapters/mcp_client/manifest.json +185 -0
- ciris_adapters/mcp_client/mcp_communication_service.py +393 -0
- ciris_adapters/mcp_client/mcp_tool_service.py +463 -0
- ciris_adapters/mcp_client/mcp_wise_service.py +394 -0
- ciris_adapters/mcp_client/schemas.py +149 -0
- ciris_adapters/mcp_client/security.py +592 -0
- ciris_adapters/mcp_common/__init__.py +44 -0
- ciris_adapters/mcp_common/manifest.json +25 -0
- ciris_adapters/mcp_common/protocol.py +315 -0
- ciris_adapters/mcp_common/schemas.py +225 -0
- ciris_adapters/mcp_server/__init__.py +47 -0
- ciris_adapters/mcp_server/adapter.py +581 -0
- ciris_adapters/mcp_server/config.py +260 -0
- ciris_adapters/mcp_server/configurable.py +393 -0
- ciris_adapters/mcp_server/handlers.py +663 -0
- ciris_adapters/mcp_server/manifest.json +211 -0
- ciris_adapters/mcp_server/security.py +500 -0
- ciris_adapters/mock_llm/README.md +117 -0
- ciris_adapters/mock_llm/__init__.py +21 -0
- ciris_adapters/mock_llm/adapter.py +131 -0
- ciris_adapters/mock_llm/configurable.py +237 -0
- ciris_adapters/mock_llm/manifest.json +106 -0
- ciris_adapters/mock_llm/protocol.py +37 -0
- ciris_adapters/mock_llm/responses.py +520 -0
- ciris_adapters/mock_llm/responses_action_selection.py +1041 -0
- ciris_adapters/mock_llm/responses_epistemic.py +17 -0
- ciris_adapters/mock_llm/responses_feedback.py +27 -0
- ciris_adapters/mock_llm/schemas.py +35 -0
- ciris_adapters/mock_llm/service.py +294 -0
- ciris_adapters/navigation/__init__.py +21 -0
- ciris_adapters/navigation/adapter.py +129 -0
- ciris_adapters/navigation/configurable.py +239 -0
- ciris_adapters/navigation/manifest.json +104 -0
- ciris_adapters/navigation/service.py +487 -0
- ciris_adapters/reddit/README.md +132 -0
- ciris_adapters/reddit/REDDIT_ADAPTER_ANALYSIS.md +715 -0
- ciris_adapters/reddit/REDDIT_ADAPTER_SUMMARY.txt +278 -0
- ciris_adapters/reddit/REDDIT_ANALYSIS_INDEX.md +307 -0
- ciris_adapters/reddit/REDDIT_PRODUCTION_READINESS_PLAN.md +518 -0
- ciris_adapters/reddit/__init__.py +15 -0
- ciris_adapters/reddit/adapter.py +189 -0
- ciris_adapters/reddit/configurable.py +274 -0
- ciris_adapters/reddit/error_handler.py +307 -0
- ciris_adapters/reddit/manifest.json +218 -0
- ciris_adapters/reddit/observer.py +532 -0
- ciris_adapters/reddit/protocol.py +34 -0
- ciris_adapters/reddit/schemas.py +433 -0
- ciris_adapters/reddit/service.py +1471 -0
- ciris_adapters/sample_adapter/README.md +474 -0
- ciris_adapters/sample_adapter/__init__.py +45 -0
- ciris_adapters/sample_adapter/adapter.py +208 -0
- ciris_adapters/sample_adapter/configurable.py +469 -0
- ciris_adapters/sample_adapter/manifest.json +247 -0
- ciris_adapters/sample_adapter/services.py +486 -0
- ciris_adapters/weather/__init__.py +16 -0
- ciris_adapters/weather/adapter.py +130 -0
- ciris_adapters/weather/configurable.py +240 -0
- ciris_adapters/weather/manifest.json +156 -0
- ciris_adapters/weather/service.py +600 -0
- ciris_agent-1.7.7.dist-info/METADATA +284 -0
- ciris_agent-1.7.7.dist-info/RECORD +986 -0
- ciris_agent-1.7.7.dist-info/WHEEL +5 -0
- ciris_agent-1.7.7.dist-info/entry_points.txt +15 -0
- ciris_agent-1.7.7.dist-info/licenses/LICENSE +205 -0
- ciris_agent-1.7.7.dist-info/licenses/NOTICE +82 -0
- ciris_agent-1.7.7.dist-info/top_level.txt +4 -0
- ciris_engine/__init__.py +15 -0
- ciris_engine/ciris_templates/ally.yaml +632 -0
- ciris_engine/ciris_templates/default.yaml +411 -0
- ciris_engine/ciris_templates/echo-core.yaml +629 -0
- ciris_engine/ciris_templates/echo-speculative.yaml +764 -0
- ciris_engine/ciris_templates/echo.yaml +647 -0
- ciris_engine/ciris_templates/sage.yaml +332 -0
- ciris_engine/ciris_templates/scout.yaml +338 -0
- ciris_engine/ciris_templates/test.yaml +168 -0
- ciris_engine/cli.py +42 -0
- ciris_engine/config/CIRIS_SERVICES.json +19 -0
- ciris_engine/config/MODEL_CAPABILITIES.json +419 -0
- ciris_engine/config/PRICING_DATA.json +179 -0
- ciris_engine/config/__init__.py +50 -0
- ciris_engine/config/ciris_services.py +113 -0
- ciris_engine/config/model_capabilities.py +388 -0
- ciris_engine/config/pricing_models.py +276 -0
- ciris_engine/constants.py +35 -0
- ciris_engine/data/__init__.py +1 -0
- ciris_engine/data/covenant_1.0b.txt +978 -0
- ciris_engine/gui_static/11steps.svg +107 -0
- ciris_engine/gui_static/2x-schematics.png +0 -0
- ciris_engine/gui_static/404/index.html +1 -0
- ciris_engine/gui_static/404.html +1 -0
- ciris_engine/gui_static/_next/static/0edhkwDxd5UccTsCmtaBi/_buildManifest.js +1 -0
- ciris_engine/gui_static/_next/static/0edhkwDxd5UccTsCmtaBi/_ssgManifest.js +1 -0
- ciris_engine/gui_static/_next/static/U-3xTQao7hc2wnAi-Uekm/_buildManifest.js +1 -0
- ciris_engine/gui_static/_next/static/U-3xTQao7hc2wnAi-Uekm/_ssgManifest.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/3297-60e86ba0f8a7b040.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/3835-2aad4b7f5f8e4643.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/4499-99a0bc47de0b8975.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/4534-af88cd4ba6e99bff.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/4541-84b455f9e0dc4cfe.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/4789-61412711484754bb.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/6539-c6398bc9d7018430.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/704-8e827b26cc8c2d32.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/704-fb45d630f3192c6f.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/8072-de4952a2e6d2b33f.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/8315-b91d03a3949db0af.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/8386-f93a83ccbd789bd9.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/87c73c54-781a7f35148d5433.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/8903-fefea3339a02d41b.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/9090-e66485adf8d9d990.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/_not-found/page-a67d9808462c23b1.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/account/api-keys/page-2d7ee1583bbbd02e.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/account/api-keys/page-6a3c2bae6fe92b7b.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/account/consent/page-2ed3a035136bc4e8.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/account/consent/page-b2f5c91844a32422.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/account/page-25b90f89af3ea58c.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/account/page-b65d16c94ecaf69c.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/account/privacy/page-675b6d05c8f9184f.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/account/privacy/page-cbee2e1c8ab52145.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/account/settings/page-0f44da06697cf9f0.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/account/settings/page-563420253577edbf.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/adapters/page-1854631018bc32be.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/agents/page-8353752c176a7c70.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/agents/page-f61a529f110a6040.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/api-demo/page-7f19b9d20d39be28.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/api-demo/page-d1063938f249b8bd.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/audit/page-321b6728b8fff0bb.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/audit/page-ebac35ca961a1277.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/billing/page-6f3dc3bd02924f8e.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/billing/page-fa4a469f814c821a.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/comms/page-0d4f734269addd8f.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/comms/page-79227d426050089c.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/config/page-018d21d683b6e5bc.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/config/page-2aa5a5363ca2a371.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/consent/page-198373205fd316e2.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/consent/page-f2ca39e7713b13f8.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/dashboard/page-1dd5a196f643c60d.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/dashboard/page-530a04d3abbb8cda.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/docs/page-3193b06d094ab654.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/docs/page-330e996dedb87aba.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/layout-0a70f5fc460298b1.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/layout-21f2f99dd5b336e9.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/login/page-33240e6c6034a49d.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/login/page-68ffab6d54a7fdcd.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/logs/page-8a6167aecc4a475c.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/memory/page-9ca8c5d0056de3ff.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/memory/page-e961226941c18f81.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/page-6fdb065a787a4974.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/page-89f87d431be6064a.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/runtime/page-2e728b9c43aa164d.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/runtime/page-c7dd033dc40a72f0.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/services/page-ae9f0bdf11d01a95.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/services/page-b10feb79ca5d75e5.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/sessions/page-13ebe7ef1c16ae11.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/sessions/page-e6c82b16d617f785.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/setup/page-0beb5f5b5a5c20fc.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/setup/page-2595e729eae30c0e.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/status-dashboard/page-1037c987aecc3653.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/status-dashboard/page-2ffd147f6d3162ff.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/system/page-2c5798d58cafcd91.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/system/page-505b1ba4eceb01c3.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/test-auth/page-b0cad31d5cb1b2fa.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/test-auth/page-f3ecd7a8012df230.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/test-login/page-f35117fdc4105801.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/test-login/page-fb583a7924114906.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/test-sdk/page-50f116fd76935563.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/test-sdk/page-c37d8aa5ba623a44.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/tools/page-429aec7a707777ef.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/tools/page-5f705aad60e0c04e.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/users/page-13476b8b0f3808cc.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/users/page-7e500d154ed5bba4.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/wa/page-cc4a9d8a5cb44d08.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/app/wa/page-ec3e429efbc79230.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/framework-9d29490f5ba089ba.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/main-1f554952e47a82c4.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/main-app-26fa8aed029082e5.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/main-app-97b0486ef6bcef25.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/pages/_app-6ce685456e616eb2.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/pages/_error-d4bce98d93fe21e7.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/polyfills-42372ed130431b0a.js +1 -0
- ciris_engine/gui_static/_next/static/chunks/webpack-fcebd240b7f8477d.js +1 -0
- ciris_engine/gui_static/_next/static/css/16b94b1fe0cc6e37.css +3 -0
- ciris_engine/gui_static/_next/static/css/77a24ceaae86deff.css +3 -0
- ciris_engine/gui_static/_next/static/media/4cf2300e9c8272f7-s.p.woff2 +0 -0
- ciris_engine/gui_static/_next/static/media/747892c23ea88013-s.woff2 +0 -0
- ciris_engine/gui_static/_next/static/media/8d697b304b401681-s.woff2 +0 -0
- ciris_engine/gui_static/_next/static/media/93f479601ee12b01-s.p.woff2 +0 -0
- ciris_engine/gui_static/_next/static/media/9610d9e46709d722-s.woff2 +0 -0
- ciris_engine/gui_static/_next/static/media/ba015fad6dcf6784-s.woff2 +0 -0
- ciris_engine/gui_static/_next/static/media/d8298875641ec7d4-s.p.woff2 +0 -0
- ciris_engine/gui_static/account/api-keys/index.html +1 -0
- ciris_engine/gui_static/account/api-keys/index.txt +27 -0
- ciris_engine/gui_static/account/consent/index.html +1 -0
- ciris_engine/gui_static/account/consent/index.txt +27 -0
- ciris_engine/gui_static/account/index.html +1 -0
- ciris_engine/gui_static/account/index.txt +27 -0
- ciris_engine/gui_static/account/privacy/index.html +1 -0
- ciris_engine/gui_static/account/privacy/index.txt +27 -0
- ciris_engine/gui_static/account/settings/index.html +1 -0
- ciris_engine/gui_static/account/settings/index.txt +27 -0
- ciris_engine/gui_static/adapters/index.html +1 -0
- ciris_engine/gui_static/adapters/index.txt +27 -0
- ciris_engine/gui_static/agents/index.html +1 -0
- ciris_engine/gui_static/agents/index.txt +27 -0
- ciris_engine/gui_static/andrew-roberts-euBRXcx57T4-unsplash.jpg +0 -0
- ciris_engine/gui_static/api-demo/index.html +1 -0
- ciris_engine/gui_static/api-demo/index.txt +27 -0
- ciris_engine/gui_static/audit/index.html +1 -0
- ciris_engine/gui_static/audit/index.txt +27 -0
- ciris_engine/gui_static/billing/index.html +1 -0
- ciris_engine/gui_static/billing/index.txt +27 -0
- ciris_engine/gui_static/blurryinfo.png +0 -0
- ciris_engine/gui_static/chip-vincent-PkQDwfl9Flc-unsplash.jpg +0 -0
- ciris_engine/gui_static/ciris-architecture.svg +338 -0
- ciris_engine/gui_static/comms/index.html +1 -0
- ciris_engine/gui_static/comms/index.txt +27 -0
- ciris_engine/gui_static/config/index.html +1 -0
- ciris_engine/gui_static/config/index.txt +27 -0
- ciris_engine/gui_static/consent/index.html +1 -0
- ciris_engine/gui_static/consent/index.txt +27 -0
- ciris_engine/gui_static/dashboard/index.html +1 -0
- ciris_engine/gui_static/dashboard/index.txt +27 -0
- ciris_engine/gui_static/docs/index.html +1 -0
- ciris_engine/gui_static/docs/index.txt +27 -0
- ciris_engine/gui_static/eric.png +0 -0
- ciris_engine/gui_static/file.svg +1 -0
- ciris_engine/gui_static/globe.svg +1 -0
- ciris_engine/gui_static/index.html +1 -0
- ciris_engine/gui_static/index.txt +27 -0
- ciris_engine/gui_static/infogfx-1@2x.png +0 -0
- ciris_engine/gui_static/infogfx-2.png +0 -0
- ciris_engine/gui_static/infogfx-dark-1.png +0 -0
- ciris_engine/gui_static/kelly-vohs-soSTXmIxTDU-unsplash.jpg +0 -0
- ciris_engine/gui_static/login/index.html +1 -0
- ciris_engine/gui_static/login/index.txt +27 -0
- ciris_engine/gui_static/logs/index.html +1 -0
- ciris_engine/gui_static/logs/index.txt +27 -0
- ciris_engine/gui_static/memory/index.html +1 -0
- ciris_engine/gui_static/memory/index.txt +27 -0
- ciris_engine/gui_static/nathan-farrish-ArcTfEoBgzs-unsplash.jpg +0 -0
- ciris_engine/gui_static/next.svg +1 -0
- ciris_engine/gui_static/overview.svg +512 -0
- ciris_engine/gui_static/overview1.svg +407 -0
- ciris_engine/gui_static/overview2.svg +370 -0
- ciris_engine/gui_static/pipeline-visualization.svg +278 -0
- ciris_engine/gui_static/privacy-policy.html +160 -0
- ciris_engine/gui_static/runtime/index.html +8 -0
- ciris_engine/gui_static/runtime/index.txt +27 -0
- ciris_engine/gui_static/services/index.html +1 -0
- ciris_engine/gui_static/services/index.txt +27 -0
- ciris_engine/gui_static/sessions/index.html +1 -0
- ciris_engine/gui_static/sessions/index.txt +27 -0
- ciris_engine/gui_static/setup/index.html +1 -0
- ciris_engine/gui_static/setup/index.txt +27 -0
- ciris_engine/gui_static/status-dashboard/index.html +1 -0
- ciris_engine/gui_static/status-dashboard/index.txt +27 -0
- ciris_engine/gui_static/system/index.html +1 -0
- ciris_engine/gui_static/system/index.txt +27 -0
- ciris_engine/gui_static/terms-of-service.html +174 -0
- ciris_engine/gui_static/test-auth/index.html +1 -0
- ciris_engine/gui_static/test-auth/index.txt +27 -0
- ciris_engine/gui_static/test-login/index.html +1 -0
- ciris_engine/gui_static/test-login/index.txt +27 -0
- ciris_engine/gui_static/test-sdk/index.html +1 -0
- ciris_engine/gui_static/test-sdk/index.txt +27 -0
- ciris_engine/gui_static/tools/index.html +1 -0
- ciris_engine/gui_static/tools/index.txt +27 -0
- ciris_engine/gui_static/users/index.html +1 -0
- ciris_engine/gui_static/users/index.txt +27 -0
- ciris_engine/gui_static/vercel.svg +1 -0
- ciris_engine/gui_static/videos/video1.mp4 +0 -0
- ciris_engine/gui_static/videos/video3.mp4 +0 -0
- ciris_engine/gui_static/wa/index.html +1 -0
- ciris_engine/gui_static/wa/index.txt +27 -0
- ciris_engine/gui_static/window.svg +1 -0
- ciris_engine/logic/__init__.py +8 -0
- ciris_engine/logic/adapters/__init__.py +74 -0
- ciris_engine/logic/adapters/api/__init__.py +5 -0
- ciris_engine/logic/adapters/api/adapter.py +1037 -0
- ciris_engine/logic/adapters/api/api_communication.py +370 -0
- ciris_engine/logic/adapters/api/api_document.py +330 -0
- ciris_engine/logic/adapters/api/api_observer.py +24 -0
- ciris_engine/logic/adapters/api/api_runtime_control.py +388 -0
- ciris_engine/logic/adapters/api/api_tools.py +299 -0
- ciris_engine/logic/adapters/api/api_vision.py +215 -0
- ciris_engine/logic/adapters/api/app.py +272 -0
- ciris_engine/logic/adapters/api/auth.py +159 -0
- ciris_engine/logic/adapters/api/config.py +101 -0
- ciris_engine/logic/adapters/api/constants.py +55 -0
- ciris_engine/logic/adapters/api/dependencies/__init__.py +1 -0
- ciris_engine/logic/adapters/api/dependencies/auth.py +260 -0
- ciris_engine/logic/adapters/api/endpoints/__init__.py +1 -0
- ciris_engine/logic/adapters/api/endpoints/emergency.py +86 -0
- ciris_engine/logic/adapters/api/middleware/__init__.py +1 -0
- ciris_engine/logic/adapters/api/middleware/rate_limiter.py +302 -0
- ciris_engine/logic/adapters/api/models.py +29 -0
- ciris_engine/logic/adapters/api/routes/__init__.py +52 -0
- ciris_engine/logic/adapters/api/routes/agent.py +1762 -0
- ciris_engine/logic/adapters/api/routes/audit.py +707 -0
- ciris_engine/logic/adapters/api/routes/auth.py +1745 -0
- ciris_engine/logic/adapters/api/routes/billing.py +895 -0
- ciris_engine/logic/adapters/api/routes/config.py +329 -0
- ciris_engine/logic/adapters/api/routes/connectors.py +534 -0
- ciris_engine/logic/adapters/api/routes/consent.py +637 -0
- ciris_engine/logic/adapters/api/routes/dsar.py +637 -0
- ciris_engine/logic/adapters/api/routes/dsar_multi_source.py +484 -0
- ciris_engine/logic/adapters/api/routes/emergency.py +302 -0
- ciris_engine/logic/adapters/api/routes/memory.py +733 -0
- ciris_engine/logic/adapters/api/routes/memory_filters.py +230 -0
- ciris_engine/logic/adapters/api/routes/memory_models.py +112 -0
- ciris_engine/logic/adapters/api/routes/memory_queries.py +236 -0
- ciris_engine/logic/adapters/api/routes/memory_query_helpers.py +394 -0
- ciris_engine/logic/adapters/api/routes/memory_visualization.py +359 -0
- ciris_engine/logic/adapters/api/routes/memory_visualization_helpers.py +110 -0
- ciris_engine/logic/adapters/api/routes/partnership.py +541 -0
- ciris_engine/logic/adapters/api/routes/setup.py +1374 -0
- ciris_engine/logic/adapters/api/routes/system.py +3049 -0
- ciris_engine/logic/adapters/api/routes/system_extensions.py +952 -0
- ciris_engine/logic/adapters/api/routes/telemetry.py +1987 -0
- ciris_engine/logic/adapters/api/routes/telemetry_converters.py +141 -0
- ciris_engine/logic/adapters/api/routes/telemetry_helpers.py +111 -0
- ciris_engine/logic/adapters/api/routes/telemetry_logs_reader.py +280 -0
- ciris_engine/logic/adapters/api/routes/telemetry_metrics.py +131 -0
- ciris_engine/logic/adapters/api/routes/telemetry_models.py +190 -0
- ciris_engine/logic/adapters/api/routes/telemetry_otlp.py +878 -0
- ciris_engine/logic/adapters/api/routes/telemetry_resource_helpers.py +191 -0
- ciris_engine/logic/adapters/api/routes/tickets.py +541 -0
- ciris_engine/logic/adapters/api/routes/tools.py +556 -0
- ciris_engine/logic/adapters/api/routes/transparency.py +281 -0
- ciris_engine/logic/adapters/api/routes/users.py +981 -0
- ciris_engine/logic/adapters/api/routes/verification.py +373 -0
- ciris_engine/logic/adapters/api/routes/wa.py +369 -0
- ciris_engine/logic/adapters/api/service_configuration.py +177 -0
- ciris_engine/logic/adapters/api/services/__init__.py +1 -0
- ciris_engine/logic/adapters/api/services/auth_service.py +1417 -0
- ciris_engine/logic/adapters/api/services/oauth_security.py +68 -0
- ciris_engine/logic/adapters/base.py +141 -0
- ciris_engine/logic/adapters/base_adapter.py +73 -0
- ciris_engine/logic/adapters/base_observer.py +1141 -0
- ciris_engine/logic/adapters/base_vision.py +312 -0
- ciris_engine/logic/adapters/cirisnode_client.py +307 -0
- ciris_engine/logic/adapters/cli/__init__.py +3 -0
- ciris_engine/logic/adapters/cli/adapter.py +207 -0
- ciris_engine/logic/adapters/cli/cli_adapter.py +902 -0
- ciris_engine/logic/adapters/cli/cli_observer.py +268 -0
- ciris_engine/logic/adapters/cli/cli_tools.py +427 -0
- ciris_engine/logic/adapters/cli/cli_wa_service.py +134 -0
- ciris_engine/logic/adapters/cli/config.py +73 -0
- ciris_engine/logic/adapters/discord/__init__.py +3 -0
- ciris_engine/logic/adapters/discord/adapter.py +783 -0
- ciris_engine/logic/adapters/discord/ciris_discord_client.py +159 -0
- ciris_engine/logic/adapters/discord/config.py +177 -0
- ciris_engine/logic/adapters/discord/constants.py +185 -0
- ciris_engine/logic/adapters/discord/discord-stubs.pyi +50 -0
- ciris_engine/logic/adapters/discord/discord_adapter.py +1584 -0
- ciris_engine/logic/adapters/discord/discord_audit.py +150 -0
- ciris_engine/logic/adapters/discord/discord_channel_manager.py +351 -0
- ciris_engine/logic/adapters/discord/discord_connection_manager.py +313 -0
- ciris_engine/logic/adapters/discord/discord_embed_formatter.py +369 -0
- ciris_engine/logic/adapters/discord/discord_error_classifier.py +302 -0
- ciris_engine/logic/adapters/discord/discord_error_handler.py +316 -0
- ciris_engine/logic/adapters/discord/discord_guidance_handler.py +460 -0
- ciris_engine/logic/adapters/discord/discord_message_handler.py +207 -0
- ciris_engine/logic/adapters/discord/discord_observer.py +670 -0
- ciris_engine/logic/adapters/discord/discord_rate_limiter.py +249 -0
- ciris_engine/logic/adapters/discord/discord_reaction_handler.py +278 -0
- ciris_engine/logic/adapters/discord/discord_tool_handler.py +465 -0
- ciris_engine/logic/adapters/discord/discord_tool_service.py +790 -0
- ciris_engine/logic/adapters/discord/discord_tools.py +90 -0
- ciris_engine/logic/adapters/discord/discord_vision_helper.py +148 -0
- ciris_engine/logic/adapters/discord/py.typed +0 -0
- ciris_engine/logic/adapters/document_parser.py +320 -0
- ciris_engine/logic/audit/__init__.py +10 -0
- ciris_engine/logic/audit/hash_chain.py +313 -0
- ciris_engine/logic/audit/signature_manager.py +352 -0
- ciris_engine/logic/audit/verifier.py +408 -0
- ciris_engine/logic/buses/__init__.py +21 -0
- ciris_engine/logic/buses/base_bus.py +178 -0
- ciris_engine/logic/buses/bus_manager.py +121 -0
- ciris_engine/logic/buses/communication_bus.py +387 -0
- ciris_engine/logic/buses/llm_bus.py +722 -0
- ciris_engine/logic/buses/memory_bus.py +577 -0
- ciris_engine/logic/buses/prohibitions.py +502 -0
- ciris_engine/logic/buses/runtime_control_bus.py +539 -0
- ciris_engine/logic/buses/tool_bus.py +482 -0
- ciris_engine/logic/buses/wise_bus.py +684 -0
- ciris_engine/logic/config/__init__.py +25 -0
- ciris_engine/logic/config/bootstrap.py +255 -0
- ciris_engine/logic/config/config_accessor.py +202 -0
- ciris_engine/logic/config/db_paths.py +194 -0
- ciris_engine/logic/config/env_utils.py +39 -0
- ciris_engine/logic/conscience/__init__.py +16 -0
- ciris_engine/logic/conscience/build_deferral_package.py +0 -0
- ciris_engine/logic/conscience/core.py +688 -0
- ciris_engine/logic/conscience/interface.py +33 -0
- ciris_engine/logic/conscience/registry.py +76 -0
- ciris_engine/logic/conscience/thought_depth_guardrail.py +231 -0
- ciris_engine/logic/conscience/updated_status_conscience.py +156 -0
- ciris_engine/logic/context/__init__.py +10 -0
- ciris_engine/logic/context/batch_context.py +550 -0
- ciris_engine/logic/context/builder.py +149 -0
- ciris_engine/logic/context/channel_resolution.py +136 -0
- ciris_engine/logic/context/secrets_snapshot.py +52 -0
- ciris_engine/logic/context/system_snapshot.py +116 -0
- ciris_engine/logic/context/system_snapshot_helpers.py +1651 -0
- ciris_engine/logic/covenant/__init__.py +33 -0
- ciris_engine/logic/covenant/executor.py +303 -0
- ciris_engine/logic/covenant/extractor.py +382 -0
- ciris_engine/logic/covenant/handler.py +241 -0
- ciris_engine/logic/covenant/verifier.py +383 -0
- ciris_engine/logic/dma/__init__.py +15 -0
- ciris_engine/logic/dma/action_selection/__init__.py +11 -0
- ciris_engine/logic/dma/action_selection/action_instruction_generator.py +444 -0
- ciris_engine/logic/dma/action_selection/context_builder.py +508 -0
- ciris_engine/logic/dma/action_selection/faculty_integration.py +193 -0
- ciris_engine/logic/dma/action_selection/special_cases.py +132 -0
- ciris_engine/logic/dma/action_selection_pdma.py +365 -0
- ciris_engine/logic/dma/base_dma.py +335 -0
- ciris_engine/logic/dma/csdma.py +239 -0
- ciris_engine/logic/dma/dma_executor.py +575 -0
- ciris_engine/logic/dma/dsdma_base.py +410 -0
- ciris_engine/logic/dma/exceptions.py +4 -0
- ciris_engine/logic/dma/factory.py +150 -0
- ciris_engine/logic/dma/pdma.py +120 -0
- ciris_engine/logic/dma/prompt_loader.py +189 -0
- ciris_engine/logic/dma/prompts/action_selection_pdma.yml +58 -0
- ciris_engine/logic/dma/prompts/csdma_common_sense.yml +28 -0
- ciris_engine/logic/dma/prompts/dsdma_base.yml +17 -0
- ciris_engine/logic/dma/prompts/pdma_ethical.yml +42 -0
- ciris_engine/logic/formatters/__init__.py +26 -0
- ciris_engine/logic/formatters/crisis_resources.py +80 -0
- ciris_engine/logic/formatters/escalation.py +21 -0
- ciris_engine/logic/formatters/identity.py +224 -0
- ciris_engine/logic/formatters/prompt_blocks.py +64 -0
- ciris_engine/logic/formatters/system_snapshot.py +193 -0
- ciris_engine/logic/formatters/user_profiles.py +108 -0
- ciris_engine/logic/handlers/__init__.py +1 -0
- ciris_engine/logic/handlers/control/__init__.py +1 -0
- ciris_engine/logic/handlers/control/defer_handler.py +195 -0
- ciris_engine/logic/handlers/control/ponder_handler.py +154 -0
- ciris_engine/logic/handlers/control/reject_handler.py +81 -0
- ciris_engine/logic/handlers/external/__init__.py +1 -0
- ciris_engine/logic/handlers/external/observe_handler.py +154 -0
- ciris_engine/logic/handlers/external/speak_handler.py +250 -0
- ciris_engine/logic/handlers/external/tool_handler.py +148 -0
- ciris_engine/logic/handlers/memory/__init__.py +1 -0
- ciris_engine/logic/handlers/memory/forget_handler.py +107 -0
- ciris_engine/logic/handlers/memory/memorize_handler.py +391 -0
- ciris_engine/logic/handlers/memory/recall_handler.py +213 -0
- ciris_engine/logic/handlers/terminal/__init__.py +1 -0
- ciris_engine/logic/handlers/terminal/task_complete_handler.py +299 -0
- ciris_engine/logic/infrastructure/__init__.py +1 -0
- ciris_engine/logic/infrastructure/handlers/__init__.py +8 -0
- ciris_engine/logic/infrastructure/handlers/action_dispatcher.py +382 -0
- ciris_engine/logic/infrastructure/handlers/base_handler.py +450 -0
- ciris_engine/logic/infrastructure/handlers/exceptions.py +2 -0
- ciris_engine/logic/infrastructure/handlers/handler_registry.py +59 -0
- ciris_engine/logic/infrastructure/handlers/helpers.py +55 -0
- ciris_engine/logic/infrastructure/step_streaming.py +149 -0
- ciris_engine/logic/infrastructure/sub_services/__init__.py +1 -0
- ciris_engine/logic/infrastructure/sub_services/identity_variance_monitor.py +1035 -0
- ciris_engine/logic/infrastructure/sub_services/pattern_analysis_loop.py +758 -0
- ciris_engine/logic/infrastructure/sub_services/wa_cli_bootstrap.py +229 -0
- ciris_engine/logic/infrastructure/sub_services/wa_cli_display.py +176 -0
- ciris_engine/logic/infrastructure/sub_services/wa_cli_oauth.py +404 -0
- ciris_engine/logic/infrastructure/sub_services/wa_cli_wizard.py +181 -0
- ciris_engine/logic/persistence/__init__.py +130 -0
- ciris_engine/logic/persistence/analytics.py +97 -0
- ciris_engine/logic/persistence/db/__init__.py +28 -0
- ciris_engine/logic/persistence/db/core.py +520 -0
- ciris_engine/logic/persistence/db/dialect.py +380 -0
- ciris_engine/logic/persistence/db/execution_helpers.py +216 -0
- ciris_engine/logic/persistence/db/migration_runner.py +191 -0
- ciris_engine/logic/persistence/db/operations.py +313 -0
- ciris_engine/logic/persistence/db/query_builder.py +232 -0
- ciris_engine/logic/persistence/db/retry.py +154 -0
- ciris_engine/logic/persistence/db/setup.py +18 -0
- ciris_engine/logic/persistence/migrations/postgres/001_initial_schema.sql +4 -0
- ciris_engine/logic/persistence/migrations/postgres/002_add_retry_status.sql +3 -0
- ciris_engine/logic/persistence/migrations/postgres/003_add_task_update_tracking.sql +8 -0
- ciris_engine/logic/persistence/migrations/postgres/004_add_occurrence_id.sql +54 -0
- ciris_engine/logic/persistence/migrations/postgres/005_add_consolidation_locks.sql +22 -0
- ciris_engine/logic/persistence/migrations/postgres/006_add_correlation_id_unique_index.sql +16 -0
- ciris_engine/logic/persistence/migrations/postgres/007_add_dsar_tickets.sql +39 -0
- ciris_engine/logic/persistence/migrations/postgres/008_rename_to_tickets_add_sop.sql +123 -0
- ciris_engine/logic/persistence/migrations/postgres/009_add_ticket_status_columns.sql +39 -0
- ciris_engine/logic/persistence/migrations/postgres/010_add_images_to_tasks.sql +5 -0
- ciris_engine/logic/persistence/migrations/sqlite/001_initial_schema.sql +357 -0
- ciris_engine/logic/persistence/migrations/sqlite/002_add_retry_status.sql +3 -0
- ciris_engine/logic/persistence/migrations/sqlite/003_add_task_update_tracking.sql +8 -0
- ciris_engine/logic/persistence/migrations/sqlite/004_add_occurrence_id.sql +45 -0
- ciris_engine/logic/persistence/migrations/sqlite/005_add_consolidation_locks.sql +22 -0
- ciris_engine/logic/persistence/migrations/sqlite/006_add_correlation_id_unique_index.sql +16 -0
- ciris_engine/logic/persistence/migrations/sqlite/007_add_dsar_tickets.sql +39 -0
- ciris_engine/logic/persistence/migrations/sqlite/008_rename_to_tickets_add_sop.sql +120 -0
- ciris_engine/logic/persistence/migrations/sqlite/009_add_ticket_status_columns.sql +129 -0
- ciris_engine/logic/persistence/migrations/sqlite/010_add_images_to_tasks.sql +17 -0
- ciris_engine/logic/persistence/models/__init__.py +141 -0
- ciris_engine/logic/persistence/models/correlations.py +881 -0
- ciris_engine/logic/persistence/models/deferral.py +68 -0
- ciris_engine/logic/persistence/models/dsar.py +286 -0
- ciris_engine/logic/persistence/models/graph.py +362 -0
- ciris_engine/logic/persistence/models/identity.py +264 -0
- ciris_engine/logic/persistence/models/queue_status.py +139 -0
- ciris_engine/logic/persistence/models/tasks.py +1043 -0
- ciris_engine/logic/persistence/models/thoughts.py +400 -0
- ciris_engine/logic/persistence/models/tickets.py +518 -0
- ciris_engine/logic/persistence/stores/__init__.py +13 -0
- ciris_engine/logic/persistence/stores/auth_helpers.py +117 -0
- ciris_engine/logic/persistence/stores/authentication_store.py +414 -0
- ciris_engine/logic/persistence/utils.py +212 -0
- ciris_engine/logic/processors/__init__.py +30 -0
- ciris_engine/logic/processors/core/__init__.py +1 -0
- ciris_engine/logic/processors/core/base_processor.py +280 -0
- ciris_engine/logic/processors/core/main_processor.py +1777 -0
- ciris_engine/logic/processors/core/step_decorators.py +1583 -0
- ciris_engine/logic/processors/core/thought_processor/__init__.py +20 -0
- ciris_engine/logic/processors/core/thought_processor/action_execution.py +49 -0
- ciris_engine/logic/processors/core/thought_processor/conscience_execution.py +382 -0
- ciris_engine/logic/processors/core/thought_processor/finalize_action.py +66 -0
- ciris_engine/logic/processors/core/thought_processor/gather_context.py +120 -0
- ciris_engine/logic/processors/core/thought_processor/main.py +920 -0
- ciris_engine/logic/processors/core/thought_processor/perform_aspdma.py +86 -0
- ciris_engine/logic/processors/core/thought_processor/perform_dmas.py +106 -0
- ciris_engine/logic/processors/core/thought_processor/recursive_processing.py +237 -0
- ciris_engine/logic/processors/core/thought_processor/round_complete.py +52 -0
- ciris_engine/logic/processors/core/thought_processor/start_round.py +64 -0
- ciris_engine/logic/processors/exceptions.py +59 -0
- ciris_engine/logic/processors/states/__init__.py +1 -0
- ciris_engine/logic/processors/states/dream_processor.py +1381 -0
- ciris_engine/logic/processors/states/play_processor.py +141 -0
- ciris_engine/logic/processors/states/shutdown_processor.py +623 -0
- ciris_engine/logic/processors/states/solitude_processor.py +305 -0
- ciris_engine/logic/processors/states/wakeup_processor.py +802 -0
- ciris_engine/logic/processors/states/work_processor.py +742 -0
- ciris_engine/logic/processors/support/__init__.py +1 -0
- ciris_engine/logic/processors/support/dma_orchestrator.py +336 -0
- ciris_engine/logic/processors/support/processing_queue.py +133 -0
- ciris_engine/logic/processors/support/shutdown_condition_evaluator.py +294 -0
- ciris_engine/logic/processors/support/state_manager.py +358 -0
- ciris_engine/logic/processors/support/task_manager.py +303 -0
- ciris_engine/logic/processors/support/thought_escalation.py +116 -0
- ciris_engine/logic/processors/support/thought_manager.py +328 -0
- ciris_engine/logic/processors/support/thought_manager_enhanced.py +105 -0
- ciris_engine/logic/registries/__init__.py +34 -0
- ciris_engine/logic/registries/base.py +653 -0
- ciris_engine/logic/registries/circuit_breaker.py +275 -0
- ciris_engine/logic/registries/typed_registries.py +184 -0
- ciris_engine/logic/runtime/__init__.py +7 -0
- ciris_engine/logic/runtime/adapter_loader.py +261 -0
- ciris_engine/logic/runtime/adapter_manager.py +1053 -0
- ciris_engine/logic/runtime/ciris_runtime.py +2342 -0
- ciris_engine/logic/runtime/ciris_runtime_helpers.py +923 -0
- ciris_engine/logic/runtime/component_builder.py +361 -0
- ciris_engine/logic/runtime/identity_manager.py +219 -0
- ciris_engine/logic/runtime/module_loader.py +207 -0
- ciris_engine/logic/runtime/prevent_sideeffects.py +30 -0
- ciris_engine/logic/runtime/runtime_interface.py +23 -0
- ciris_engine/logic/runtime/service_initializer.py +1623 -0
- ciris_engine/logic/secrets/__init__.py +30 -0
- ciris_engine/logic/secrets/encryption.py +175 -0
- ciris_engine/logic/secrets/filter.py +295 -0
- ciris_engine/logic/secrets/service.py +652 -0
- ciris_engine/logic/secrets/store.py +669 -0
- ciris_engine/logic/services/__init__.py +1 -0
- ciris_engine/logic/services/adaptation/__init__.py +3 -0
- ciris_engine/logic/services/base_graph_service.py +142 -0
- ciris_engine/logic/services/base_infrastructure_service.py +69 -0
- ciris_engine/logic/services/base_scheduled_service.py +136 -0
- ciris_engine/logic/services/base_service.py +247 -0
- ciris_engine/logic/services/governance/__init__.py +3 -0
- ciris_engine/logic/services/governance/adaptive_filter/__init__.py +14 -0
- ciris_engine/logic/services/governance/adaptive_filter/service.py +818 -0
- ciris_engine/logic/services/governance/consent/__init__.py +53 -0
- ciris_engine/logic/services/governance/consent/air.py +403 -0
- ciris_engine/logic/services/governance/consent/decay.py +324 -0
- ciris_engine/logic/services/governance/consent/dsar_automation.py +589 -0
- ciris_engine/logic/services/governance/consent/exceptions.py +106 -0
- ciris_engine/logic/services/governance/consent/metrics.py +270 -0
- ciris_engine/logic/services/governance/consent/partnership.py +533 -0
- ciris_engine/logic/services/governance/consent/service.py +1256 -0
- ciris_engine/logic/services/governance/dsar/__init__.py +29 -0
- ciris_engine/logic/services/governance/dsar/orchestrator.py +977 -0
- ciris_engine/logic/services/governance/dsar/schemas.py +141 -0
- ciris_engine/logic/services/governance/dsar/signature_service.py +283 -0
- ciris_engine/logic/services/governance/self_observation/__init__.py +20 -0
- ciris_engine/logic/services/governance/self_observation/service.py +1153 -0
- ciris_engine/logic/services/governance/visibility/__init__.py +17 -0
- ciris_engine/logic/services/governance/visibility/service.py +512 -0
- ciris_engine/logic/services/governance/wise_authority/__init__.py +15 -0
- ciris_engine/logic/services/governance/wise_authority/service.py +827 -0
- ciris_engine/logic/services/graph/__init__.py +5 -0
- ciris_engine/logic/services/graph/audit_service/__init__.py +5 -0
- ciris_engine/logic/services/graph/audit_service/service.py +1675 -0
- ciris_engine/logic/services/graph/base.py +208 -0
- ciris_engine/logic/services/graph/config_service/__init__.py +5 -0
- ciris_engine/logic/services/graph/config_service/service.py +372 -0
- ciris_engine/logic/services/graph/incident_service/__init__.py +5 -0
- ciris_engine/logic/services/graph/incident_service/service.py +803 -0
- ciris_engine/logic/services/graph/memory_service.py +1120 -0
- ciris_engine/logic/services/graph/telemetry_service/__init__.py +5 -0
- ciris_engine/logic/services/graph/telemetry_service/exceptions.py +104 -0
- ciris_engine/logic/services/graph/telemetry_service/helpers.py +1337 -0
- ciris_engine/logic/services/graph/telemetry_service/service.py +2429 -0
- ciris_engine/logic/services/graph/tsdb_consolidation/__init__.py +17 -0
- ciris_engine/logic/services/graph/tsdb_consolidation/aggregation_helpers.py +355 -0
- ciris_engine/logic/services/graph/tsdb_consolidation/cleanup_helpers.py +438 -0
- ciris_engine/logic/services/graph/tsdb_consolidation/compressor.py +260 -0
- ciris_engine/logic/services/graph/tsdb_consolidation/consolidators/__init__.py +27 -0
- ciris_engine/logic/services/graph/tsdb_consolidation/consolidators/audit.py +326 -0
- ciris_engine/logic/services/graph/tsdb_consolidation/consolidators/conversation.py +291 -0
- ciris_engine/logic/services/graph/tsdb_consolidation/consolidators/memory.py +197 -0
- ciris_engine/logic/services/graph/tsdb_consolidation/consolidators/metrics.py +251 -0
- ciris_engine/logic/services/graph/tsdb_consolidation/consolidators/task.py +257 -0
- ciris_engine/logic/services/graph/tsdb_consolidation/consolidators/trace.py +363 -0
- ciris_engine/logic/services/graph/tsdb_consolidation/data_converter.py +545 -0
- ciris_engine/logic/services/graph/tsdb_consolidation/date_calculation_helpers.py +193 -0
- ciris_engine/logic/services/graph/tsdb_consolidation/db_query_helpers.py +296 -0
- ciris_engine/logic/services/graph/tsdb_consolidation/edge_helpers.py +92 -0
- ciris_engine/logic/services/graph/tsdb_consolidation/edge_manager.py +896 -0
- ciris_engine/logic/services/graph/tsdb_consolidation/extensive_helpers.py +322 -0
- ciris_engine/logic/services/graph/tsdb_consolidation/period_manager.py +152 -0
- ciris_engine/logic/services/graph/tsdb_consolidation/profound_helpers.py +277 -0
- ciris_engine/logic/services/graph/tsdb_consolidation/query_manager.py +812 -0
- ciris_engine/logic/services/graph/tsdb_consolidation/service.py +1692 -0
- ciris_engine/logic/services/graph/tsdb_consolidation/sql_builders.py +363 -0
- ciris_engine/logic/services/infrastructure/__init__.py +1 -0
- ciris_engine/logic/services/infrastructure/authentication/__init__.py +5 -0
- ciris_engine/logic/services/infrastructure/authentication/service.py +1634 -0
- ciris_engine/logic/services/infrastructure/database_maintenance/__init__.py +15 -0
- ciris_engine/logic/services/infrastructure/database_maintenance/service.py +764 -0
- ciris_engine/logic/services/infrastructure/resource_monitor/__init__.py +7 -0
- ciris_engine/logic/services/infrastructure/resource_monitor/ciris_billing_provider.py +755 -0
- ciris_engine/logic/services/infrastructure/resource_monitor/service.py +409 -0
- ciris_engine/logic/services/infrastructure/resource_monitor/simple_credit_provider.py +129 -0
- ciris_engine/logic/services/lifecycle/__init__.py +3 -0
- ciris_engine/logic/services/lifecycle/initialization/__init__.py +10 -0
- ciris_engine/logic/services/lifecycle/initialization/service.py +312 -0
- ciris_engine/logic/services/lifecycle/scheduler/__init__.py +5 -0
- ciris_engine/logic/services/lifecycle/scheduler/service.py +607 -0
- ciris_engine/logic/services/lifecycle/shutdown/__init__.py +9 -0
- ciris_engine/logic/services/lifecycle/shutdown/service.py +378 -0
- ciris_engine/logic/services/lifecycle/time/__init__.py +15 -0
- ciris_engine/logic/services/lifecycle/time/service.py +259 -0
- ciris_engine/logic/services/memory_service/__init__.py +8 -0
- ciris_engine/logic/services/mixins/__init__.py +13 -0
- ciris_engine/logic/services/mixins/example_usage.py +200 -0
- ciris_engine/logic/services/mixins/request_metrics.py +179 -0
- ciris_engine/logic/services/runtime/__init__.py +3 -0
- ciris_engine/logic/services/runtime/adapter_configuration/__init__.py +16 -0
- ciris_engine/logic/services/runtime/adapter_configuration/service.py +674 -0
- ciris_engine/logic/services/runtime/adapter_configuration/session.py +67 -0
- ciris_engine/logic/services/runtime/control_service/__init__.py +5 -0
- ciris_engine/logic/services/runtime/control_service/service.py +2269 -0
- ciris_engine/logic/services/runtime/llm_service/__init__.py +14 -0
- ciris_engine/logic/services/runtime/llm_service/pricing_calculator.py +279 -0
- ciris_engine/logic/services/runtime/llm_service/service.py +930 -0
- ciris_engine/logic/services/tools/__init__.py +5 -0
- ciris_engine/logic/services/tools/core_tool_service/__init__.py +8 -0
- ciris_engine/logic/services/tools/core_tool_service/service.py +852 -0
- ciris_engine/logic/setup/__init__.py +1 -0
- ciris_engine/logic/setup/first_run.py +250 -0
- ciris_engine/logic/setup/wizard.py +327 -0
- ciris_engine/logic/telemetry/__init__.py +46 -0
- ciris_engine/logic/telemetry/core.py +239 -0
- ciris_engine/logic/telemetry/hot_cold_config.py +133 -0
- ciris_engine/logic/telemetry/log_collector.py +190 -0
- ciris_engine/logic/telemetry/resource_monitor.py +7 -0
- ciris_engine/logic/telemetry/security.py +79 -0
- ciris_engine/logic/utils/__init__.py +18 -0
- ciris_engine/logic/utils/channel_utils.py +75 -0
- ciris_engine/logic/utils/consent/__init__.py +1 -0
- ciris_engine/logic/utils/consent/partnership_utils.py +172 -0
- ciris_engine/logic/utils/constants.py +92 -0
- ciris_engine/logic/utils/context_utils.py +145 -0
- ciris_engine/logic/utils/directory_setup.py +533 -0
- ciris_engine/logic/utils/graphql_context_provider.py +152 -0
- ciris_engine/logic/utils/identity_resolution.py +843 -0
- ciris_engine/logic/utils/incident_capture_handler.py +303 -0
- ciris_engine/logic/utils/initialization_manager.py +74 -0
- ciris_engine/logic/utils/jsondict_helpers.py +290 -0
- ciris_engine/logic/utils/log_sanitizer.py +97 -0
- ciris_engine/logic/utils/logging_config.py +151 -0
- ciris_engine/logic/utils/observability_decorators.py +544 -0
- ciris_engine/logic/utils/occurrence_utils.py +155 -0
- ciris_engine/logic/utils/path_resolution.py +281 -0
- ciris_engine/logic/utils/platform_detection.py +286 -0
- ciris_engine/logic/utils/privacy.py +266 -0
- ciris_engine/logic/utils/profile_loader.py +124 -0
- ciris_engine/logic/utils/profile_manager.py +16 -0
- ciris_engine/logic/utils/runtime_utils.py +69 -0
- ciris_engine/logic/utils/shutdown_manager.py +107 -0
- ciris_engine/logic/utils/task_formatters.py +60 -0
- ciris_engine/logic/utils/task_thought_factory.py +404 -0
- ciris_engine/logic/utils/thought_utils.py +54 -0
- ciris_engine/logic/utils/user_utils.py +70 -0
- ciris_engine/protocols/__init__.py +0 -0
- ciris_engine/protocols/adapters/__init__.py +35 -0
- ciris_engine/protocols/adapters/base.py +149 -0
- ciris_engine/protocols/adapters/configurable.py +265 -0
- ciris_engine/protocols/adapters/message.py +90 -0
- ciris_engine/protocols/audit/__init__.py +1 -0
- ciris_engine/protocols/buses/__init__.py +1 -0
- ciris_engine/protocols/config/__init__.py +1 -0
- ciris_engine/protocols/conscience/__init__.py +1 -0
- ciris_engine/protocols/consent.py +88 -0
- ciris_engine/protocols/context/__init__.py +1 -0
- ciris_engine/protocols/data/__init__.py +1 -0
- ciris_engine/protocols/dma/__init__.py +1 -0
- ciris_engine/protocols/dma/base.py +107 -0
- ciris_engine/protocols/faculties.py +34 -0
- ciris_engine/protocols/formatters/__init__.py +1 -0
- ciris_engine/protocols/handlers/__init__.py +1 -0
- ciris_engine/protocols/infrastructure/__init__.py +25 -0
- ciris_engine/protocols/infrastructure/base.py +377 -0
- ciris_engine/protocols/persistence/__init__.py +1 -0
- ciris_engine/protocols/pipeline_control.py +609 -0
- ciris_engine/protocols/processors/__init__.py +19 -0
- ciris_engine/protocols/processors/agent.py +299 -0
- ciris_engine/protocols/processors/base.py +130 -0
- ciris_engine/protocols/processors/orchestration.py +62 -0
- ciris_engine/protocols/registries/__init__.py +1 -0
- ciris_engine/protocols/runtime/__init__.py +1 -0
- ciris_engine/protocols/runtime/base.py +163 -0
- ciris_engine/protocols/secrets/__init__.py +1 -0
- ciris_engine/protocols/services/__init__.py +80 -0
- ciris_engine/protocols/services/adaptation/__init__.py +7 -0
- ciris_engine/protocols/services/adaptation/self_observation.py +265 -0
- ciris_engine/protocols/services/governance/__init__.py +20 -0
- ciris_engine/protocols/services/governance/communication.py +58 -0
- ciris_engine/protocols/services/governance/filter.py +56 -0
- ciris_engine/protocols/services/governance/visibility.py +32 -0
- ciris_engine/protocols/services/governance/wa_auth.py +192 -0
- ciris_engine/protocols/services/governance/wise_authority.py +75 -0
- ciris_engine/protocols/services/graph/__init__.py +19 -0
- ciris_engine/protocols/services/graph/audit.py +92 -0
- ciris_engine/protocols/services/graph/config.py +54 -0
- ciris_engine/protocols/services/graph/incident_management.py +103 -0
- ciris_engine/protocols/services/graph/memory.py +110 -0
- ciris_engine/protocols/services/graph/telemetry.py +51 -0
- ciris_engine/protocols/services/graph/tsdb_consolidation.py +87 -0
- ciris_engine/protocols/services/infrastructure/__init__.py +11 -0
- ciris_engine/protocols/services/infrastructure/authentication.py +159 -0
- ciris_engine/protocols/services/infrastructure/credit_gate.py +46 -0
- ciris_engine/protocols/services/infrastructure/database_maintenance.py +25 -0
- ciris_engine/protocols/services/infrastructure/resource_monitor.py +83 -0
- ciris_engine/protocols/services/lifecycle/__init__.py +13 -0
- ciris_engine/protocols/services/lifecycle/initialization.py +41 -0
- ciris_engine/protocols/services/lifecycle/scheduler.py +42 -0
- ciris_engine/protocols/services/lifecycle/shutdown.py +50 -0
- ciris_engine/protocols/services/lifecycle/time.py +31 -0
- ciris_engine/protocols/services/runtime/__init__.py +13 -0
- ciris_engine/protocols/services/runtime/llm.py +50 -0
- ciris_engine/protocols/services/runtime/runtime_control.py +193 -0
- ciris_engine/protocols/services/runtime/secrets.py +100 -0
- ciris_engine/protocols/services/runtime/tool.py +123 -0
- ciris_engine/protocols/telemetry/__init__.py +1 -0
- ciris_engine/protocols/utils/__init__.py +1 -0
- ciris_engine/schemas/__init__.py +112 -0
- ciris_engine/schemas/actions/__init__.py +37 -0
- ciris_engine/schemas/actions/parameters.py +137 -0
- ciris_engine/schemas/adapters/__init__.py +13 -0
- ciris_engine/schemas/adapters/cirisnode.py +135 -0
- ciris_engine/schemas/adapters/cli.py +97 -0
- ciris_engine/schemas/adapters/cli_tools.py +98 -0
- ciris_engine/schemas/adapters/discord.py +125 -0
- ciris_engine/schemas/adapters/graphql_core.py +144 -0
- ciris_engine/schemas/adapters/registration.py +47 -0
- ciris_engine/schemas/adapters/runtime_context.py +48 -0
- ciris_engine/schemas/adapters/tool_execution.py +45 -0
- ciris_engine/schemas/adapters/tools.py +96 -0
- ciris_engine/schemas/api/__init__.py +1 -0
- ciris_engine/schemas/api/agent.py +50 -0
- ciris_engine/schemas/api/audit.py +38 -0
- ciris_engine/schemas/api/auth.py +351 -0
- ciris_engine/schemas/api/config_security.py +242 -0
- ciris_engine/schemas/api/emergency.py +111 -0
- ciris_engine/schemas/api/responses.py +72 -0
- ciris_engine/schemas/api/runtime.py +26 -0
- ciris_engine/schemas/api/telemetry.py +109 -0
- ciris_engine/schemas/api/wa.py +90 -0
- ciris_engine/schemas/audit/__init__.py +13 -0
- ciris_engine/schemas/audit/core.py +139 -0
- ciris_engine/schemas/audit/hash_chain.py +58 -0
- ciris_engine/schemas/audit/verification.py +131 -0
- ciris_engine/schemas/buses/__init__.py +1 -0
- ciris_engine/schemas/config/__init__.py +41 -0
- ciris_engine/schemas/config/agent.py +279 -0
- ciris_engine/schemas/config/cognitive_state_behaviors.py +194 -0
- ciris_engine/schemas/config/default_dsar_sops.py +178 -0
- ciris_engine/schemas/config/essential.py +195 -0
- ciris_engine/schemas/config/tickets.py +86 -0
- ciris_engine/schemas/conscience/__init__.py +25 -0
- ciris_engine/schemas/conscience/context.py +34 -0
- ciris_engine/schemas/conscience/core.py +145 -0
- ciris_engine/schemas/conscience/results.py +24 -0
- ciris_engine/schemas/consent/__init__.py +5 -0
- ciris_engine/schemas/consent/core.py +404 -0
- ciris_engine/schemas/context/__init__.py +1 -0
- ciris_engine/schemas/covenant.py +382 -0
- ciris_engine/schemas/data/__init__.py +1 -0
- ciris_engine/schemas/dma/__init__.py +16 -0
- ciris_engine/schemas/dma/core.py +199 -0
- ciris_engine/schemas/dma/faculty.py +192 -0
- ciris_engine/schemas/dma/prompts.py +172 -0
- ciris_engine/schemas/dma/results.py +103 -0
- ciris_engine/schemas/formatters/__init__.py +1 -0
- ciris_engine/schemas/handlers/__init__.py +10 -0
- ciris_engine/schemas/handlers/context.py +119 -0
- ciris_engine/schemas/handlers/contexts.py +100 -0
- ciris_engine/schemas/handlers/core.py +167 -0
- ciris_engine/schemas/handlers/memory_schemas.py +67 -0
- ciris_engine/schemas/handlers/schemas.py +95 -0
- ciris_engine/schemas/identity.py +149 -0
- ciris_engine/schemas/infrastructure/__init__.py +1 -0
- ciris_engine/schemas/infrastructure/base.py +256 -0
- ciris_engine/schemas/infrastructure/behavioral_patterns.py +129 -0
- ciris_engine/schemas/infrastructure/feedback_loop.py +57 -0
- ciris_engine/schemas/infrastructure/identity_variance.py +141 -0
- ciris_engine/schemas/infrastructure/oauth.py +175 -0
- ciris_engine/schemas/infrastructure/wa_cli_wizard.py +54 -0
- ciris_engine/schemas/persistence/__init__.py +34 -0
- ciris_engine/schemas/persistence/core.py +140 -0
- ciris_engine/schemas/persistence/correlations.py +73 -0
- ciris_engine/schemas/persistence/postgres/__init__.py +1 -0
- ciris_engine/schemas/persistence/postgres/tables.py +280 -0
- ciris_engine/schemas/persistence/sqlite/__init__.py +1 -0
- ciris_engine/schemas/persistence/sqlite/tables.py +281 -0
- ciris_engine/schemas/platform.py +149 -0
- ciris_engine/schemas/processors/__init__.py +26 -0
- ciris_engine/schemas/processors/base.py +130 -0
- ciris_engine/schemas/processors/cognitive.py +77 -0
- ciris_engine/schemas/processors/context.py +35 -0
- ciris_engine/schemas/processors/core.py +152 -0
- ciris_engine/schemas/processors/dma.py +105 -0
- ciris_engine/schemas/processors/error.py +122 -0
- ciris_engine/schemas/processors/main.py +109 -0
- ciris_engine/schemas/processors/phase_results.py +21 -0
- ciris_engine/schemas/processors/results.py +99 -0
- ciris_engine/schemas/processors/solitude.py +79 -0
- ciris_engine/schemas/processors/state.py +202 -0
- ciris_engine/schemas/processors/state_example.py +177 -0
- ciris_engine/schemas/processors/states.py +21 -0
- ciris_engine/schemas/processors/status.py +34 -0
- ciris_engine/schemas/registries/__init__.py +1 -0
- ciris_engine/schemas/registries/base.py +66 -0
- ciris_engine/schemas/resources/__init__.py +15 -0
- ciris_engine/schemas/resources/crisis.py +315 -0
- ciris_engine/schemas/runtime/__init__.py +42 -0
- ciris_engine/schemas/runtime/adapter_management.py +186 -0
- ciris_engine/schemas/runtime/api.py +58 -0
- ciris_engine/schemas/runtime/audit.py +50 -0
- ciris_engine/schemas/runtime/bootstrap.py +33 -0
- ciris_engine/schemas/runtime/contexts.py +61 -0
- ciris_engine/schemas/runtime/core.py +161 -0
- ciris_engine/schemas/runtime/enums.py +167 -0
- ciris_engine/schemas/runtime/extended.py +232 -0
- ciris_engine/schemas/runtime/manifest.py +311 -0
- ciris_engine/schemas/runtime/memory.py +60 -0
- ciris_engine/schemas/runtime/messages.py +108 -0
- ciris_engine/schemas/runtime/models.py +156 -0
- ciris_engine/schemas/runtime/processing_context.py +43 -0
- ciris_engine/schemas/runtime/protocols_core.py +96 -0
- ciris_engine/schemas/runtime/resources.py +33 -0
- ciris_engine/schemas/runtime/system_context.py +417 -0
- ciris_engine/schemas/secrets/__init__.py +1 -0
- ciris_engine/schemas/secrets/core.py +267 -0
- ciris_engine/schemas/secrets/service.py +95 -0
- ciris_engine/schemas/services/__init__.py +33 -0
- ciris_engine/schemas/services/audit_summary_node.py +172 -0
- ciris_engine/schemas/services/authority/__init__.py +39 -0
- ciris_engine/schemas/services/authority/jwt.py +158 -0
- ciris_engine/schemas/services/authority/wa_updates.py +138 -0
- ciris_engine/schemas/services/authority/wise_authority.py +163 -0
- ciris_engine/schemas/services/authority_core.py +370 -0
- ciris_engine/schemas/services/capabilities.py +72 -0
- ciris_engine/schemas/services/community_core.py +95 -0
- ciris_engine/schemas/services/context.py +111 -0
- ciris_engine/schemas/services/conversation_summary_node.py +189 -0
- ciris_engine/schemas/services/core/__init__.py +153 -0
- ciris_engine/schemas/services/core/runtime.py +262 -0
- ciris_engine/schemas/services/core/runtime_config.py +117 -0
- ciris_engine/schemas/services/core/secrets.py +65 -0
- ciris_engine/schemas/services/correlation_node.py +179 -0
- ciris_engine/schemas/services/credit_gate.py +92 -0
- ciris_engine/schemas/services/discord_nodes.py +299 -0
- ciris_engine/schemas/services/feedback_core.py +131 -0
- ciris_engine/schemas/services/filters_core.py +270 -0
- ciris_engine/schemas/services/governance.py +26 -0
- ciris_engine/schemas/services/graph/__init__.py +26 -0
- ciris_engine/schemas/services/graph/attributes.py +254 -0
- ciris_engine/schemas/services/graph/audit.py +98 -0
- ciris_engine/schemas/services/graph/consolidation.py +338 -0
- ciris_engine/schemas/services/graph/edge_types.py +43 -0
- ciris_engine/schemas/services/graph/edges.py +88 -0
- ciris_engine/schemas/services/graph/incident.py +312 -0
- ciris_engine/schemas/services/graph/memory.py +84 -0
- ciris_engine/schemas/services/graph/node_data.py +174 -0
- ciris_engine/schemas/services/graph/query_results.py +82 -0
- ciris_engine/schemas/services/graph/telemetry.py +250 -0
- ciris_engine/schemas/services/graph/tsdb_consolidation.py +27 -0
- ciris_engine/schemas/services/graph/tsdb_models.py +107 -0
- ciris_engine/schemas/services/graph_core.py +196 -0
- ciris_engine/schemas/services/graph_typed_nodes.py +194 -0
- ciris_engine/schemas/services/infrastructure/__init__.py +1 -0
- ciris_engine/schemas/services/infrastructure/resource_monitor.py +20 -0
- ciris_engine/schemas/services/lifecycle/__init__.py +9 -0
- ciris_engine/schemas/services/lifecycle/initialization.py +33 -0
- ciris_engine/schemas/services/lifecycle/time.py +50 -0
- ciris_engine/schemas/services/llm.py +187 -0
- ciris_engine/schemas/services/metadata.py +43 -0
- ciris_engine/schemas/services/nodes.py +704 -0
- ciris_engine/schemas/services/operations.py +126 -0
- ciris_engine/schemas/services/requests.py +128 -0
- ciris_engine/schemas/services/resources_core.py +182 -0
- ciris_engine/schemas/services/runtime_control.py +1010 -0
- ciris_engine/schemas/services/shutdown.py +88 -0
- ciris_engine/schemas/services/special/__init__.py +0 -0
- ciris_engine/schemas/services/special/self_observation.py +396 -0
- ciris_engine/schemas/services/trace_summary_node.py +199 -0
- ciris_engine/schemas/services/visibility.py +98 -0
- ciris_engine/schemas/streaming/__init__.py +10 -0
- ciris_engine/schemas/streaming/reasoning_stream.py +95 -0
- ciris_engine/schemas/telemetry/__init__.py +0 -0
- ciris_engine/schemas/telemetry/collector.py +67 -0
- ciris_engine/schemas/telemetry/core.py +252 -0
- ciris_engine/schemas/telemetry/unified.py +59 -0
- ciris_engine/schemas/tools.py +72 -0
- ciris_engine/schemas/types.py +47 -0
- ciris_engine/schemas/utils/__init__.py +1 -0
- ciris_engine/schemas/utils/config_validator.py +54 -0
- ciris_engine/utils/__init__.py +1 -0
- ciris_engine/utils/serialization.py +35 -0
- ciris_sdk/__init__.py +124 -0
- ciris_sdk/auth_store.py +261 -0
- ciris_sdk/client.py +261 -0
- ciris_sdk/exceptions.py +73 -0
- ciris_sdk/model_types.py +258 -0
- ciris_sdk/models.py +354 -0
- ciris_sdk/pagination.py +214 -0
- ciris_sdk/rate_limiter.py +188 -0
- ciris_sdk/setup.py +17 -0
- ciris_sdk/telemetry_models.py +257 -0
- ciris_sdk/telemetry_responses.py +199 -0
- ciris_sdk/transport.py +177 -0
- ciris_sdk/websocket.py +400 -0
- main.py +766 -0
|
@@ -0,0 +1,764 @@
|
|
|
1
|
+
import logging
|
|
2
|
+
from datetime import timedelta
|
|
3
|
+
from pathlib import Path
|
|
4
|
+
from typing import TYPE_CHECKING, Any, Dict, List, Optional
|
|
5
|
+
|
|
6
|
+
import aiofiles
|
|
7
|
+
|
|
8
|
+
if TYPE_CHECKING:
|
|
9
|
+
from ciris_engine.schemas.services.core import ServiceCapabilities
|
|
10
|
+
|
|
11
|
+
from ciris_engine.constants import UTC_TIMEZONE_SUFFIX
|
|
12
|
+
from ciris_engine.logic.persistence import (
|
|
13
|
+
delete_tasks_by_ids,
|
|
14
|
+
delete_thoughts_by_ids,
|
|
15
|
+
get_all_tasks,
|
|
16
|
+
get_task_by_id,
|
|
17
|
+
get_tasks_by_status,
|
|
18
|
+
get_thoughts_by_status,
|
|
19
|
+
get_thoughts_by_task_id,
|
|
20
|
+
get_thoughts_older_than,
|
|
21
|
+
)
|
|
22
|
+
from ciris_engine.logic.services.base_scheduled_service import BaseScheduledService
|
|
23
|
+
from ciris_engine.protocols.services.infrastructure.database_maintenance import DatabaseMaintenanceServiceProtocol
|
|
24
|
+
from ciris_engine.protocols.services.lifecycle.time import TimeServiceProtocol
|
|
25
|
+
from ciris_engine.schemas.runtime.enums import ServiceType, TaskStatus, ThoughtStatus
|
|
26
|
+
|
|
27
|
+
logger = logging.getLogger(__name__)
|
|
28
|
+
|
|
29
|
+
|
|
30
|
+
class DatabaseMaintenanceService(BaseScheduledService, DatabaseMaintenanceServiceProtocol):
|
|
31
|
+
"""
|
|
32
|
+
Service for performing database maintenance tasks like cleanup and archiving.
|
|
33
|
+
"""
|
|
34
|
+
|
|
35
|
+
def __init__(
|
|
36
|
+
self,
|
|
37
|
+
time_service: TimeServiceProtocol,
|
|
38
|
+
archive_dir_path: str = "data_archive",
|
|
39
|
+
archive_older_than_hours: int = 24,
|
|
40
|
+
config_service: Optional[Any] = None,
|
|
41
|
+
db_path: Optional[str] = None,
|
|
42
|
+
bus_manager: Optional[Any] = None,
|
|
43
|
+
) -> None:
|
|
44
|
+
# Initialize BaseScheduledService with hourly maintenance interval
|
|
45
|
+
super().__init__(time_service=time_service, run_interval_seconds=3600) # Run every hour
|
|
46
|
+
self.time_service = time_service
|
|
47
|
+
self.archive_dir = Path(archive_dir_path)
|
|
48
|
+
self.archive_older_than_hours = archive_older_than_hours
|
|
49
|
+
self.config_service = config_service
|
|
50
|
+
self.db_path = db_path
|
|
51
|
+
self.bus_manager = bus_manager
|
|
52
|
+
|
|
53
|
+
# Tracking variables for metrics
|
|
54
|
+
self._cleanup_runs = 0
|
|
55
|
+
self._records_deleted = 0
|
|
56
|
+
self._vacuum_runs = 0
|
|
57
|
+
self._archive_runs = 0
|
|
58
|
+
self._last_cleanup_duration = 0.0
|
|
59
|
+
self._start_time = time_service.now()
|
|
60
|
+
|
|
61
|
+
async def _run_scheduled_task(self) -> None:
|
|
62
|
+
"""
|
|
63
|
+
Execute scheduled maintenance tasks.
|
|
64
|
+
|
|
65
|
+
This is called periodically by BaseScheduledService.
|
|
66
|
+
"""
|
|
67
|
+
await self._perform_periodic_maintenance()
|
|
68
|
+
|
|
69
|
+
async def _perform_periodic_maintenance(self) -> None:
|
|
70
|
+
"""Run periodic maintenance tasks including stale task cleanup."""
|
|
71
|
+
logger.info("Periodic maintenance tasks starting.")
|
|
72
|
+
# Increment vacuum operations counter for periodic maintenance
|
|
73
|
+
self._vacuum_runs += 1
|
|
74
|
+
|
|
75
|
+
# Clean up stale wakeup/shutdown tasks from dead occurrences
|
|
76
|
+
# This is critical for multi-occurrence deployments where an occurrence
|
|
77
|
+
# may die mid-wakeup, leaving shared tasks in ACTIVE state forever
|
|
78
|
+
await self._cleanup_stale_wakeup_tasks()
|
|
79
|
+
|
|
80
|
+
# Clean up old active tasks that may have been orphaned
|
|
81
|
+
await self._cleanup_old_active_tasks()
|
|
82
|
+
|
|
83
|
+
logger.info("Periodic maintenance tasks completed.")
|
|
84
|
+
|
|
85
|
+
async def _on_stop(self) -> None:
|
|
86
|
+
"""Stop hook for cleanup."""
|
|
87
|
+
await self._final_cleanup()
|
|
88
|
+
|
|
89
|
+
async def _final_cleanup(self) -> None:
|
|
90
|
+
"""Final cleanup before shutdown."""
|
|
91
|
+
logger.info("Final maintenance cleanup executed.")
|
|
92
|
+
|
|
93
|
+
def _get_archive_size_mb(self) -> float:
|
|
94
|
+
"""Calculate archive directory size in MB."""
|
|
95
|
+
if not self.archive_dir.exists():
|
|
96
|
+
return 0.0
|
|
97
|
+
total_size = sum(f.stat().st_size for f in self.archive_dir.rglob("*") if f.is_file())
|
|
98
|
+
return total_size / (1024 * 1024)
|
|
99
|
+
|
|
100
|
+
def _time_until_next_run(self) -> int:
|
|
101
|
+
"""Calculate seconds until next scheduled run."""
|
|
102
|
+
if hasattr(self, "_next_run_time") and self._next_run_time:
|
|
103
|
+
delta = (self._next_run_time - self.time_service.now()).total_seconds()
|
|
104
|
+
return max(0, int(delta))
|
|
105
|
+
return 0
|
|
106
|
+
|
|
107
|
+
async def perform_startup_cleanup(self, time_service: Optional[TimeServiceProtocol] = None) -> None:
|
|
108
|
+
"""
|
|
109
|
+
Performs database cleanup at startup:
|
|
110
|
+
1. Removes orphaned active tasks and thoughts.
|
|
111
|
+
2. Archives tasks and thoughts older than the configured threshold.
|
|
112
|
+
3. Cleans up thoughts with invalid context.
|
|
113
|
+
Logs actions taken.
|
|
114
|
+
"""
|
|
115
|
+
from datetime import datetime, timedelta, timezone
|
|
116
|
+
|
|
117
|
+
# Use provided time_service or fallback to instance time_service
|
|
118
|
+
ts = time_service or self.time_service
|
|
119
|
+
logger.info("Starting database cleanup")
|
|
120
|
+
self.archive_dir.mkdir(parents=True, exist_ok=True)
|
|
121
|
+
|
|
122
|
+
# --- Clean up thoughts with invalid/malformed context ---
|
|
123
|
+
await self._cleanup_invalid_thoughts()
|
|
124
|
+
|
|
125
|
+
# --- Clean up runtime-specific configuration from previous runs ---
|
|
126
|
+
await self._cleanup_runtime_config()
|
|
127
|
+
|
|
128
|
+
# --- Clean up stale wakeup tasks from interrupted startups ---
|
|
129
|
+
await self._cleanup_stale_wakeup_tasks()
|
|
130
|
+
|
|
131
|
+
# --- Clean up old active tasks from previous runs ---
|
|
132
|
+
await self._cleanup_old_active_tasks()
|
|
133
|
+
|
|
134
|
+
# --- Clean up duplicate temporal edges (v1.5.6 PostgreSQL bug) ---
|
|
135
|
+
await self._cleanup_duplicate_temporal_edges()
|
|
136
|
+
|
|
137
|
+
# --- 1. Remove orphaned active tasks and thoughts ---
|
|
138
|
+
orphaned_tasks_deleted_count = 0
|
|
139
|
+
orphaned_thoughts_deleted_count = 0
|
|
140
|
+
|
|
141
|
+
active_tasks = get_tasks_by_status(TaskStatus.ACTIVE, db_path=self.db_path)
|
|
142
|
+
task_ids_to_delete: List[Any] = []
|
|
143
|
+
|
|
144
|
+
for task in active_tasks:
|
|
145
|
+
if not hasattr(task, "task_id"):
|
|
146
|
+
logger.error(f"Item in active_tasks is not a Task object, it's a {type(task)}: {task}")
|
|
147
|
+
continue # Skip this item
|
|
148
|
+
|
|
149
|
+
# CRITICAL: Multi-occurrence race condition protection
|
|
150
|
+
# Skip tasks created within last 2 minutes to prevent deleting tasks
|
|
151
|
+
# created by another occurrence that just started up
|
|
152
|
+
task_created_at = datetime.fromisoformat(task.created_at.replace("Z", "+00:00"))
|
|
153
|
+
task_age = ts.now() - task_created_at
|
|
154
|
+
if task_age < timedelta(minutes=2):
|
|
155
|
+
logger.debug(
|
|
156
|
+
f"Skipping orphan check for recent task {task.task_id} (age: {task_age}). "
|
|
157
|
+
"Will check in next cleanup cycle if still orphaned."
|
|
158
|
+
)
|
|
159
|
+
continue
|
|
160
|
+
|
|
161
|
+
is_orphan = False
|
|
162
|
+
if task.task_id.startswith("shutdown_") and task.parent_task_id is None:
|
|
163
|
+
pass # Shutdown tasks are valid root tasks
|
|
164
|
+
elif task.parent_task_id:
|
|
165
|
+
# CRITICAL: Pass task's own occurrence_id to find parent in same namespace
|
|
166
|
+
# This prevents shared tasks from being marked as orphans in multi-occurrence setups
|
|
167
|
+
parent_task = get_task_by_id(task.parent_task_id, task.agent_occurrence_id, db_path=self.db_path)
|
|
168
|
+
if not parent_task or parent_task.status not in [TaskStatus.ACTIVE, TaskStatus.COMPLETED]:
|
|
169
|
+
is_orphan = True
|
|
170
|
+
elif task.parent_task_id is None:
|
|
171
|
+
# Root tasks without parents are allowed
|
|
172
|
+
pass
|
|
173
|
+
|
|
174
|
+
if is_orphan:
|
|
175
|
+
logger.info(
|
|
176
|
+
f"Orphaned active task found: {task.task_id} ('{task.description}'). Parent missing or not active/completed. Marking for deletion."
|
|
177
|
+
)
|
|
178
|
+
task_ids_to_delete.append(task.task_id)
|
|
179
|
+
|
|
180
|
+
if task_ids_to_delete:
|
|
181
|
+
orphaned_tasks_deleted_count = delete_tasks_by_ids(task_ids_to_delete, db_path=self.db_path)
|
|
182
|
+
logger.info(
|
|
183
|
+
f"Deleted {orphaned_tasks_deleted_count} orphaned active tasks (and their thoughts via cascade)."
|
|
184
|
+
)
|
|
185
|
+
|
|
186
|
+
pending_thoughts = get_thoughts_by_status(ThoughtStatus.PENDING, db_path=self.db_path)
|
|
187
|
+
processing_thoughts = get_thoughts_by_status(ThoughtStatus.PROCESSING, db_path=self.db_path)
|
|
188
|
+
all_potentially_orphaned_thoughts = pending_thoughts + processing_thoughts
|
|
189
|
+
thought_ids_to_delete_orphan: List[Any] = []
|
|
190
|
+
|
|
191
|
+
for thought in all_potentially_orphaned_thoughts:
|
|
192
|
+
# CRITICAL: Pass thought's own occurrence_id to find task in same namespace
|
|
193
|
+
source_task = get_task_by_id(thought.source_task_id, thought.agent_occurrence_id, db_path=self.db_path)
|
|
194
|
+
if not source_task or source_task.status != TaskStatus.ACTIVE:
|
|
195
|
+
logger.info(
|
|
196
|
+
f"Orphaned thought found: {thought.thought_id} (Task: {thought.source_task_id} not found or not active). Marking for deletion."
|
|
197
|
+
)
|
|
198
|
+
thought_ids_to_delete_orphan.append(thought.thought_id)
|
|
199
|
+
|
|
200
|
+
if thought_ids_to_delete_orphan:
|
|
201
|
+
unique_thought_ids_to_delete = list(set(thought_ids_to_delete_orphan))
|
|
202
|
+
count = delete_thoughts_by_ids(unique_thought_ids_to_delete, db_path=self.db_path)
|
|
203
|
+
orphaned_thoughts_deleted_count += count
|
|
204
|
+
logger.info(f"Deleted {count} additional orphaned active/processing thoughts.")
|
|
205
|
+
|
|
206
|
+
logger.info(
|
|
207
|
+
f"Orphan cleanup: {orphaned_tasks_deleted_count} tasks, {orphaned_thoughts_deleted_count} thoughts removed."
|
|
208
|
+
)
|
|
209
|
+
|
|
210
|
+
# Increment cleanup operations counter
|
|
211
|
+
self._cleanup_runs += 1
|
|
212
|
+
|
|
213
|
+
# --- 2. Archive thoughts older than configured hours ---
|
|
214
|
+
# Tasks are now managed by TSDB consolidator, not archived here
|
|
215
|
+
archived_tasks_count = 0
|
|
216
|
+
archived_thoughts_count = 0
|
|
217
|
+
|
|
218
|
+
now = ts.now()
|
|
219
|
+
archive_timestamp_str = now.strftime("%Y%m%d_%H%M%S")
|
|
220
|
+
older_than_timestamp = (now - timedelta(hours=self.archive_older_than_hours)).isoformat()
|
|
221
|
+
|
|
222
|
+
# Skip task archival - handled by TSDB consolidator
|
|
223
|
+
logger.info("Task archival skipped - tasks are now managed by TSDB consolidator")
|
|
224
|
+
task_ids_actually_archived_and_deleted: set[str] = set()
|
|
225
|
+
|
|
226
|
+
thoughts_to_archive = get_thoughts_older_than(older_than_timestamp, db_path=self.db_path)
|
|
227
|
+
if thoughts_to_archive:
|
|
228
|
+
thought_archive_file = self.archive_dir / f"archive_thoughts_{archive_timestamp_str}.jsonl"
|
|
229
|
+
thought_ids_to_delete_for_archive: List[Any] = []
|
|
230
|
+
|
|
231
|
+
async with aiofiles.open(thought_archive_file, "w") as f:
|
|
232
|
+
for thought in thoughts_to_archive:
|
|
233
|
+
# Archive all thoughts older than threshold
|
|
234
|
+
await f.write(thought.model_dump_json() + "\n")
|
|
235
|
+
thought_ids_to_delete_for_archive.append(thought.thought_id)
|
|
236
|
+
|
|
237
|
+
if thought_ids_to_delete_for_archive:
|
|
238
|
+
archived_thoughts_count = delete_thoughts_by_ids(
|
|
239
|
+
thought_ids_to_delete_for_archive, db_path=self.db_path
|
|
240
|
+
)
|
|
241
|
+
logger.info(
|
|
242
|
+
f"Archived and deleted {archived_thoughts_count} thoughts older than {self.archive_older_than_hours} hours to {thought_archive_file}."
|
|
243
|
+
)
|
|
244
|
+
else:
|
|
245
|
+
logger.info(f"No thoughts older than {self.archive_older_than_hours} hours to archive.")
|
|
246
|
+
else:
|
|
247
|
+
logger.info(f"No thoughts older than {self.archive_older_than_hours} hours found for archiving.")
|
|
248
|
+
|
|
249
|
+
logger.info(f"Archival: {archived_tasks_count} tasks, {archived_thoughts_count} thoughts archived and removed.")
|
|
250
|
+
logger.info("Database cleanup completed")
|
|
251
|
+
|
|
252
|
+
async def _cleanup_invalid_thoughts(self) -> None:
|
|
253
|
+
"""Clean up thoughts with invalid or malformed context."""
|
|
254
|
+
from ciris_engine.logic.persistence import get_db_connection
|
|
255
|
+
from ciris_engine.logic.persistence.db.dialect import get_adapter
|
|
256
|
+
|
|
257
|
+
logger.info("Cleaning up thoughts with invalid context...")
|
|
258
|
+
|
|
259
|
+
# Get adapter to detect database type
|
|
260
|
+
adapter = get_adapter()
|
|
261
|
+
|
|
262
|
+
# Different SQL for PostgreSQL (JSONB) vs SQLite (TEXT)
|
|
263
|
+
if adapter.is_postgresql():
|
|
264
|
+
# PostgreSQL: Cast JSONB to text for LIKE operations
|
|
265
|
+
sql = """
|
|
266
|
+
SELECT thought_id, context_json
|
|
267
|
+
FROM thoughts
|
|
268
|
+
WHERE context_json::text = '{}'
|
|
269
|
+
OR context_json IS NULL
|
|
270
|
+
OR context_json::text NOT LIKE '%task_id%'
|
|
271
|
+
OR context_json::text NOT LIKE '%correlation_id%'
|
|
272
|
+
"""
|
|
273
|
+
else:
|
|
274
|
+
# SQLite: context_json is TEXT, use LIKE directly
|
|
275
|
+
sql = """
|
|
276
|
+
SELECT thought_id, context_json
|
|
277
|
+
FROM thoughts
|
|
278
|
+
WHERE context_json = '{}'
|
|
279
|
+
OR context_json IS NULL
|
|
280
|
+
OR context_json NOT LIKE '%task_id%'
|
|
281
|
+
OR context_json NOT LIKE '%correlation_id%'
|
|
282
|
+
"""
|
|
283
|
+
|
|
284
|
+
invalid_thought_ids = []
|
|
285
|
+
|
|
286
|
+
try:
|
|
287
|
+
with get_db_connection(db_path=self.db_path) as conn:
|
|
288
|
+
cursor = conn.cursor()
|
|
289
|
+
cursor.execute(sql)
|
|
290
|
+
rows = cursor.fetchall()
|
|
291
|
+
|
|
292
|
+
for row in rows:
|
|
293
|
+
invalid_thought_ids.append(row["thought_id"])
|
|
294
|
+
|
|
295
|
+
if invalid_thought_ids:
|
|
296
|
+
# Delete these invalid thoughts
|
|
297
|
+
placeholders = ",".join("?" * len(invalid_thought_ids))
|
|
298
|
+
delete_sql = f"DELETE FROM thoughts WHERE thought_id IN ({placeholders})" # nosec B608 - placeholders are '?' strings, not user input
|
|
299
|
+
cursor.execute(delete_sql, invalid_thought_ids)
|
|
300
|
+
conn.commit()
|
|
301
|
+
|
|
302
|
+
logger.info(f"Deleted {len(invalid_thought_ids)} thoughts with invalid context")
|
|
303
|
+
else:
|
|
304
|
+
logger.info("No thoughts with invalid context found")
|
|
305
|
+
|
|
306
|
+
except Exception as e:
|
|
307
|
+
logger.error(f"Failed to clean up invalid thoughts: {e}", exc_info=True)
|
|
308
|
+
|
|
309
|
+
async def _cleanup_runtime_config(self) -> None:
|
|
310
|
+
"""Clean up runtime-specific configuration from previous runs."""
|
|
311
|
+
try:
|
|
312
|
+
# Use injected config service
|
|
313
|
+
if not self.config_service:
|
|
314
|
+
logger.warning("Cannot clean up runtime config - config service not available")
|
|
315
|
+
return
|
|
316
|
+
|
|
317
|
+
# Get all config entries
|
|
318
|
+
all_configs = await self.config_service.list_configs()
|
|
319
|
+
|
|
320
|
+
runtime_config_patterns = [
|
|
321
|
+
"adapter.", # Adapter configurations
|
|
322
|
+
"runtime.", # Runtime-specific settings
|
|
323
|
+
"session.", # Session-specific data
|
|
324
|
+
"temp.", # Temporary configurations
|
|
325
|
+
]
|
|
326
|
+
|
|
327
|
+
deleted_count = 0
|
|
328
|
+
|
|
329
|
+
for key, value in all_configs.items():
|
|
330
|
+
# Check if this is a runtime-specific config
|
|
331
|
+
is_runtime_config = any(key.startswith(pattern) for pattern in runtime_config_patterns)
|
|
332
|
+
|
|
333
|
+
if is_runtime_config:
|
|
334
|
+
# Get the actual config node to check if it should be deleted
|
|
335
|
+
config_node = await self.config_service.get_config(key)
|
|
336
|
+
if config_node:
|
|
337
|
+
# Skip configs created by system_bootstrap (essential configs)
|
|
338
|
+
if config_node.updated_by == "system_bootstrap":
|
|
339
|
+
logger.debug(f"Preserving bootstrap config: {key}")
|
|
340
|
+
continue
|
|
341
|
+
|
|
342
|
+
# Convert to GraphNode and use memory service to forget it
|
|
343
|
+
graph_node = config_node.to_graph_node()
|
|
344
|
+
await self.config_service.graph.forget(graph_node)
|
|
345
|
+
deleted_count += 1
|
|
346
|
+
logger.debug(f"Deleted runtime config node: {key}")
|
|
347
|
+
|
|
348
|
+
if deleted_count > 0:
|
|
349
|
+
logger.info(f"Cleaned up {deleted_count} runtime-specific configuration entries from previous runs")
|
|
350
|
+
else:
|
|
351
|
+
logger.info("No runtime-specific configuration entries to clean up")
|
|
352
|
+
|
|
353
|
+
except Exception as e:
|
|
354
|
+
logger.error(f"Failed to clean up runtime config: {e}", exc_info=True)
|
|
355
|
+
|
|
356
|
+
async def _cleanup_old_active_tasks(self) -> None:
|
|
357
|
+
"""Mark old active tasks from previous runs as completed."""
|
|
358
|
+
try:
|
|
359
|
+
from ciris_engine.logic.persistence import update_task_status
|
|
360
|
+
|
|
361
|
+
logger.info("Checking for old PENDING/ACTIVE tasks from previous runs")
|
|
362
|
+
|
|
363
|
+
# Get current time
|
|
364
|
+
current_time = self.time_service.now()
|
|
365
|
+
|
|
366
|
+
# Get all active tasks from all occurrences by querying the database directly
|
|
367
|
+
# We need to check ALL occurrences for old active tasks
|
|
368
|
+
from ciris_engine.logic.persistence import get_db_connection
|
|
369
|
+
|
|
370
|
+
# Check both PENDING and ACTIVE tasks - PENDING tasks that are old
|
|
371
|
+
# indicate messages that were received but never processed
|
|
372
|
+
stale_tasks = []
|
|
373
|
+
with get_db_connection(db_path=self.db_path) as conn:
|
|
374
|
+
cursor = conn.cursor()
|
|
375
|
+
cursor.execute(
|
|
376
|
+
"SELECT * FROM tasks WHERE status IN (?, ?)",
|
|
377
|
+
(TaskStatus.PENDING.value, TaskStatus.ACTIVE.value),
|
|
378
|
+
)
|
|
379
|
+
rows = cursor.fetchall()
|
|
380
|
+
from ciris_engine.logic.persistence.utils import map_row_to_task
|
|
381
|
+
|
|
382
|
+
for row in rows:
|
|
383
|
+
stale_tasks.append(map_row_to_task(row))
|
|
384
|
+
|
|
385
|
+
old_task_ids = []
|
|
386
|
+
|
|
387
|
+
for task in stale_tasks:
|
|
388
|
+
if not hasattr(task, "task_id"):
|
|
389
|
+
continue
|
|
390
|
+
|
|
391
|
+
# Skip wakeup and shutdown tasks (handled by _cleanup_stale_wakeup_tasks)
|
|
392
|
+
if (
|
|
393
|
+
task.task_id.startswith("WAKEUP_")
|
|
394
|
+
or task.task_id.startswith("VERIFY_IDENTITY_")
|
|
395
|
+
or task.task_id.startswith("VALIDATE_INTEGRITY_")
|
|
396
|
+
or task.task_id.startswith("EVALUATE_RESILIENCE_")
|
|
397
|
+
or task.task_id.startswith("ACCEPT_INCOMPLETENESS_")
|
|
398
|
+
or task.task_id.startswith("EXPRESS_GRATITUDE_")
|
|
399
|
+
or task.task_id.startswith("shutdown_")
|
|
400
|
+
):
|
|
401
|
+
continue
|
|
402
|
+
|
|
403
|
+
# Check task age
|
|
404
|
+
if isinstance(task.created_at, str):
|
|
405
|
+
from datetime import datetime
|
|
406
|
+
|
|
407
|
+
task_created = datetime.fromisoformat(task.created_at.replace("Z", UTC_TIMEZONE_SUFFIX))
|
|
408
|
+
else:
|
|
409
|
+
task_created = task.created_at
|
|
410
|
+
|
|
411
|
+
task_age = current_time - task_created
|
|
412
|
+
# Mark tasks older than 5 minutes as completed
|
|
413
|
+
is_old = task_age.total_seconds() > 300 # 5 minutes
|
|
414
|
+
|
|
415
|
+
if is_old:
|
|
416
|
+
logger.info(
|
|
417
|
+
f"Found old active task from previous run: {task.task_id} (age: {task_age.total_seconds():.0f}s) - marking as completed"
|
|
418
|
+
)
|
|
419
|
+
old_task_ids.append(task.task_id)
|
|
420
|
+
|
|
421
|
+
# Mark old tasks as completed and notify channels
|
|
422
|
+
if old_task_ids:
|
|
423
|
+
for task in stale_tasks:
|
|
424
|
+
if task.task_id in old_task_ids:
|
|
425
|
+
# CRITICAL: Use task's own occurrence_id, not hardcoded "default"
|
|
426
|
+
update_task_status(
|
|
427
|
+
task.task_id,
|
|
428
|
+
TaskStatus.COMPLETED,
|
|
429
|
+
task.agent_occurrence_id,
|
|
430
|
+
self.time_service,
|
|
431
|
+
db_path=self.db_path,
|
|
432
|
+
)
|
|
433
|
+
# Send notification to the channel that the task was auto-completed
|
|
434
|
+
await self._notify_stale_task_completed(task)
|
|
435
|
+
logger.info(f"Marked {len(old_task_ids)} old active tasks as completed")
|
|
436
|
+
else:
|
|
437
|
+
logger.info("No old PENDING/ACTIVE tasks found")
|
|
438
|
+
|
|
439
|
+
except Exception as e:
|
|
440
|
+
logger.error(f"Failed to clean up old active tasks: {e}", exc_info=True)
|
|
441
|
+
|
|
442
|
+
async def _notify_stale_task_completed(self, task: Any) -> None:
|
|
443
|
+
"""Send a notification to the channel that a stale task was auto-completed due to restart."""
|
|
444
|
+
if not self.bus_manager:
|
|
445
|
+
logger.debug("No bus_manager available - skipping stale task notification")
|
|
446
|
+
return
|
|
447
|
+
|
|
448
|
+
channel_id = getattr(task, "channel_id", None)
|
|
449
|
+
if not channel_id:
|
|
450
|
+
logger.debug(f"Task {task.task_id} has no channel_id - skipping notification")
|
|
451
|
+
return
|
|
452
|
+
|
|
453
|
+
# Skip internal/system channels
|
|
454
|
+
if channel_id.startswith("__") or channel_id == "system":
|
|
455
|
+
return
|
|
456
|
+
|
|
457
|
+
try:
|
|
458
|
+
msg = (
|
|
459
|
+
"I was restarted while processing your request. "
|
|
460
|
+
"The previous task was auto-completed. Please resend your message if you still need a response."
|
|
461
|
+
)
|
|
462
|
+
await self.bus_manager.communication.send_message_sync(
|
|
463
|
+
channel_id=channel_id,
|
|
464
|
+
content=msg,
|
|
465
|
+
handler_name="DatabaseMaintenanceService",
|
|
466
|
+
)
|
|
467
|
+
logger.info(f"Sent stale task notification to channel {channel_id}")
|
|
468
|
+
except Exception as e:
|
|
469
|
+
logger.warning(f"Failed to send stale task notification to {channel_id}: {e}")
|
|
470
|
+
|
|
471
|
+
async def _cleanup_stale_wakeup_tasks(self) -> None:
|
|
472
|
+
"""
|
|
473
|
+
Clean up stale wakeup and shutdown thoughts from previous runs while preserving completed tasks for history.
|
|
474
|
+
|
|
475
|
+
This prevents infinite loops where old PENDING/ACTIVE shutdown tasks with completed thoughts
|
|
476
|
+
get reused on restart, causing the shutdown processor to wait forever for an LLM response.
|
|
477
|
+
"""
|
|
478
|
+
try:
|
|
479
|
+
logger.info("Checking for stale wakeup and shutdown tasks from previous runs")
|
|
480
|
+
|
|
481
|
+
# Get current time for comparison
|
|
482
|
+
current_time = self.time_service.now()
|
|
483
|
+
|
|
484
|
+
# Get all wakeup and shutdown related tasks from __shared__ occurrence
|
|
485
|
+
# Wakeup tasks are always in the shared namespace
|
|
486
|
+
all_tasks = get_all_tasks("__shared__", db_path=self.db_path)
|
|
487
|
+
stale_tasks = []
|
|
488
|
+
for task in all_tasks:
|
|
489
|
+
if not hasattr(task, "task_id"):
|
|
490
|
+
continue
|
|
491
|
+
# Check for wakeup and shutdown tasks by ID pattern
|
|
492
|
+
if (
|
|
493
|
+
task.task_id.startswith("WAKEUP_")
|
|
494
|
+
or task.task_id.startswith("VERIFY_IDENTITY_")
|
|
495
|
+
or task.task_id.startswith("VALIDATE_INTEGRITY_")
|
|
496
|
+
or task.task_id.startswith("EVALUATE_RESILIENCE_")
|
|
497
|
+
or task.task_id.startswith("ACCEPT_INCOMPLETENESS_")
|
|
498
|
+
or task.task_id.startswith("EXPRESS_GRATITUDE_")
|
|
499
|
+
or task.task_id.startswith("shutdown_")
|
|
500
|
+
or task.task_id.startswith("SHUTDOWN_") # Also match uppercase SHUTDOWN_ tasks
|
|
501
|
+
):
|
|
502
|
+
stale_tasks.append(task)
|
|
503
|
+
|
|
504
|
+
# Clean up thoughts and interfering tasks from old wakeup runs
|
|
505
|
+
stale_task_ids = [] # For PENDING/ACTIVE tasks that would interfere
|
|
506
|
+
stale_thought_ids = []
|
|
507
|
+
|
|
508
|
+
for task in stale_tasks:
|
|
509
|
+
# Check if this task is from a previous run (more than 5 minutes old)
|
|
510
|
+
# Convert string timestamp to datetime if needed
|
|
511
|
+
if isinstance(task.created_at, str):
|
|
512
|
+
from datetime import datetime
|
|
513
|
+
|
|
514
|
+
task_created = datetime.fromisoformat(task.created_at.replace("Z", UTC_TIMEZONE_SUFFIX))
|
|
515
|
+
else:
|
|
516
|
+
task_created = task.created_at
|
|
517
|
+
|
|
518
|
+
task_age = current_time - task_created
|
|
519
|
+
is_old_task = task_age.total_seconds() > 300 # 5 minutes
|
|
520
|
+
|
|
521
|
+
if is_old_task:
|
|
522
|
+
# For old tasks, clean up any pending/processing thoughts
|
|
523
|
+
# CRITICAL: Pass task's occurrence_id to fetch thoughts in same namespace
|
|
524
|
+
thoughts = get_thoughts_by_task_id(task.task_id, task.agent_occurrence_id, db_path=self.db_path)
|
|
525
|
+
for thought in thoughts:
|
|
526
|
+
if thought.status in [ThoughtStatus.PENDING, ThoughtStatus.PROCESSING]:
|
|
527
|
+
logger.info(
|
|
528
|
+
f"Found stale wakeup thought from old task {task.task_id}: {thought.thought_id} (status: {thought.status})"
|
|
529
|
+
)
|
|
530
|
+
stale_thought_ids.append(thought.thought_id)
|
|
531
|
+
|
|
532
|
+
# Delete old PENDING or ACTIVE tasks as they would interfere
|
|
533
|
+
if task.status in [TaskStatus.PENDING, TaskStatus.ACTIVE]:
|
|
534
|
+
logger.info(f"Found stale {task.status} wakeup task from previous run: {task.task_id}")
|
|
535
|
+
stale_task_ids.append(task.task_id)
|
|
536
|
+
|
|
537
|
+
# Delete stale thoughts first
|
|
538
|
+
if stale_thought_ids:
|
|
539
|
+
deleted_thoughts = delete_thoughts_by_ids(stale_thought_ids, db_path=self.db_path)
|
|
540
|
+
logger.info(f"Deleted {deleted_thoughts} stale wakeup thoughts from previous runs")
|
|
541
|
+
|
|
542
|
+
# Then delete stale active tasks (only ACTIVE ones from interrupted startups)
|
|
543
|
+
if stale_task_ids:
|
|
544
|
+
deleted_tasks = delete_tasks_by_ids(stale_task_ids, db_path=self.db_path)
|
|
545
|
+
logger.info(f"Deleted {deleted_tasks} stale active wakeup tasks from interrupted startups")
|
|
546
|
+
|
|
547
|
+
if not stale_task_ids and not stale_thought_ids:
|
|
548
|
+
logger.info("No stale wakeup tasks or thoughts found")
|
|
549
|
+
|
|
550
|
+
except Exception as e:
|
|
551
|
+
logger.error(f"Failed to clean up stale wakeup tasks: {e}", exc_info=True)
|
|
552
|
+
|
|
553
|
+
async def _cleanup_duplicate_temporal_edges(self) -> None:
|
|
554
|
+
"""
|
|
555
|
+
Clean up duplicate temporal edges created by v1.5.5 PostgreSQL bug.
|
|
556
|
+
|
|
557
|
+
Bug: edge_manager.py used hardcoded ? placeholders instead of adapter.placeholder(),
|
|
558
|
+
causing DELETE and INSERT to fail on PostgreSQL, creating duplicate TEMPORAL_NEXT
|
|
559
|
+
and TEMPORAL_PREV edges.
|
|
560
|
+
|
|
561
|
+
This cleanup:
|
|
562
|
+
1. Finds summaries with multiple TEMPORAL_NEXT/PREV edges
|
|
563
|
+
2. Keeps only the most recent edge for each relationship type
|
|
564
|
+
3. Deletes older duplicates
|
|
565
|
+
|
|
566
|
+
Safe to run multiple times - idempotent.
|
|
567
|
+
"""
|
|
568
|
+
try:
|
|
569
|
+
from ciris_engine.logic.persistence.db.core import get_db_connection
|
|
570
|
+
from ciris_engine.logic.persistence.db.dialect import get_adapter
|
|
571
|
+
|
|
572
|
+
logger.info("Checking for duplicate temporal edges from v1.5.5 PostgreSQL bug")
|
|
573
|
+
|
|
574
|
+
with get_db_connection(db_path=self.db_path) as conn:
|
|
575
|
+
# CRITICAL: Get adapter AFTER opening connection to ensure dialect is initialized
|
|
576
|
+
# for the correct database backend (PostgreSQL vs SQLite)
|
|
577
|
+
adapter = get_adapter()
|
|
578
|
+
ph = adapter.placeholder()
|
|
579
|
+
cursor = conn.cursor()
|
|
580
|
+
|
|
581
|
+
# Find summaries with duplicate temporal edges
|
|
582
|
+
cursor.execute(
|
|
583
|
+
f"""
|
|
584
|
+
SELECT source_node_id, relationship, COUNT(*) as edge_count
|
|
585
|
+
FROM graph_edges
|
|
586
|
+
WHERE relationship IN ('TEMPORAL_NEXT', 'TEMPORAL_PREV')
|
|
587
|
+
GROUP BY source_node_id, relationship
|
|
588
|
+
HAVING COUNT(*) > 1
|
|
589
|
+
ORDER BY edge_count DESC
|
|
590
|
+
"""
|
|
591
|
+
)
|
|
592
|
+
|
|
593
|
+
duplicates = cursor.fetchall()
|
|
594
|
+
|
|
595
|
+
if not duplicates:
|
|
596
|
+
logger.info("No duplicate temporal edges found")
|
|
597
|
+
return
|
|
598
|
+
|
|
599
|
+
total_duplicates_deleted = 0
|
|
600
|
+
logger.info(f"Found {len(duplicates)} summaries with duplicate temporal edges")
|
|
601
|
+
|
|
602
|
+
for row in duplicates:
|
|
603
|
+
if adapter.is_postgresql():
|
|
604
|
+
source_id, relationship, count = row["source_node_id"], row["relationship"], row["edge_count"]
|
|
605
|
+
else:
|
|
606
|
+
source_id, relationship, count = row[0], row[1], row[2]
|
|
607
|
+
|
|
608
|
+
logger.info(f" {source_id} has {count} duplicate {relationship} edges")
|
|
609
|
+
|
|
610
|
+
# Get all edges for this source + relationship, ordered by created_at DESC
|
|
611
|
+
cursor.execute(
|
|
612
|
+
f"""
|
|
613
|
+
SELECT edge_id, created_at
|
|
614
|
+
FROM graph_edges
|
|
615
|
+
WHERE source_node_id = {ph}
|
|
616
|
+
AND relationship = {ph}
|
|
617
|
+
ORDER BY created_at DESC
|
|
618
|
+
""",
|
|
619
|
+
(source_id, relationship),
|
|
620
|
+
)
|
|
621
|
+
|
|
622
|
+
edges = cursor.fetchall()
|
|
623
|
+
|
|
624
|
+
if len(edges) <= 1:
|
|
625
|
+
continue # No duplicates to clean
|
|
626
|
+
|
|
627
|
+
# Keep the first (most recent), delete the rest
|
|
628
|
+
edges_to_delete = []
|
|
629
|
+
for i, edge_row in enumerate(edges):
|
|
630
|
+
if i == 0:
|
|
631
|
+
continue # Keep first edge
|
|
632
|
+
if adapter.is_postgresql():
|
|
633
|
+
edges_to_delete.append(edge_row["edge_id"])
|
|
634
|
+
else:
|
|
635
|
+
edges_to_delete.append(edge_row[0])
|
|
636
|
+
|
|
637
|
+
if edges_to_delete:
|
|
638
|
+
# Delete duplicate edges
|
|
639
|
+
placeholders = ",".join([ph] * len(edges_to_delete))
|
|
640
|
+
cursor.execute(
|
|
641
|
+
f"""
|
|
642
|
+
DELETE FROM graph_edges
|
|
643
|
+
WHERE edge_id IN ({placeholders})
|
|
644
|
+
""",
|
|
645
|
+
edges_to_delete,
|
|
646
|
+
)
|
|
647
|
+
|
|
648
|
+
deleted = cursor.rowcount
|
|
649
|
+
total_duplicates_deleted += deleted
|
|
650
|
+
logger.info(f" Deleted {deleted} duplicate {relationship} edges from {source_id}")
|
|
651
|
+
|
|
652
|
+
conn.commit()
|
|
653
|
+
|
|
654
|
+
if total_duplicates_deleted > 0:
|
|
655
|
+
logger.info(f"✓ Cleaned up {total_duplicates_deleted} duplicate temporal edges from PostgreSQL bug")
|
|
656
|
+
|
|
657
|
+
except Exception as e:
|
|
658
|
+
logger.error(f"Failed to clean up duplicate temporal edges: {e}", exc_info=True)
|
|
659
|
+
|
|
660
|
+
def get_capabilities(self) -> "ServiceCapabilities":
|
|
661
|
+
"""Get service capabilities."""
|
|
662
|
+
from ciris_engine.schemas.services.core import ServiceCapabilities
|
|
663
|
+
|
|
664
|
+
return ServiceCapabilities(
|
|
665
|
+
service_name="DatabaseMaintenanceService",
|
|
666
|
+
actions=["cleanup", "archive", "maintenance"],
|
|
667
|
+
version="1.0.0",
|
|
668
|
+
dependencies=["TimeService"],
|
|
669
|
+
metadata=None,
|
|
670
|
+
)
|
|
671
|
+
|
|
672
|
+
def get_service_type(self) -> ServiceType:
|
|
673
|
+
"""Get the service type enum value."""
|
|
674
|
+
return ServiceType.MAINTENANCE
|
|
675
|
+
|
|
676
|
+
def _get_actions(self) -> List[str]:
|
|
677
|
+
"""Get list of actions this service provides."""
|
|
678
|
+
return ["cleanup", "archive", "maintenance"]
|
|
679
|
+
|
|
680
|
+
def _check_dependencies(self) -> bool:
|
|
681
|
+
"""Check if all required dependencies are available."""
|
|
682
|
+
return self.time_service is not None
|
|
683
|
+
|
|
684
|
+
def _collect_custom_metrics(self) -> Dict[str, float]:
|
|
685
|
+
"""Collect database maintenance metrics."""
|
|
686
|
+
metrics = super()._collect_custom_metrics()
|
|
687
|
+
|
|
688
|
+
# Calculate database size
|
|
689
|
+
db_size_mb = 0.0
|
|
690
|
+
try:
|
|
691
|
+
import os
|
|
692
|
+
|
|
693
|
+
from ciris_engine.logic.persistence import get_sqlite_db_full_path
|
|
694
|
+
|
|
695
|
+
db_path = get_sqlite_db_full_path()
|
|
696
|
+
if os.path.exists(db_path):
|
|
697
|
+
db_size_mb = os.path.getsize(db_path) / (1024 * 1024)
|
|
698
|
+
except (OSError, IOError, ImportError):
|
|
699
|
+
# Ignore file system and import errors when checking database size
|
|
700
|
+
pass
|
|
701
|
+
|
|
702
|
+
metrics.update(
|
|
703
|
+
{
|
|
704
|
+
"cleanup_runs": float(self._cleanup_runs),
|
|
705
|
+
"records_deleted": float(self._records_deleted),
|
|
706
|
+
"vacuum_runs": float(self._vacuum_runs),
|
|
707
|
+
"archive_runs": float(self._archive_runs),
|
|
708
|
+
"database_size_mb": db_size_mb,
|
|
709
|
+
"last_cleanup_duration_s": self._last_cleanup_duration,
|
|
710
|
+
"cleanup_due": 1.0 if self._is_cleanup_due() else 0.0,
|
|
711
|
+
"archive_due": 1.0 if self._is_archive_due() else 0.0,
|
|
712
|
+
}
|
|
713
|
+
)
|
|
714
|
+
|
|
715
|
+
return metrics
|
|
716
|
+
|
|
717
|
+
def _is_cleanup_due(self) -> bool:
|
|
718
|
+
"""Check if cleanup is due."""
|
|
719
|
+
# Placeholder - implement based on schedule
|
|
720
|
+
return False
|
|
721
|
+
|
|
722
|
+
def _is_archive_due(self) -> bool:
|
|
723
|
+
"""Check if archive is due."""
|
|
724
|
+
# Placeholder - implement based on schedule
|
|
725
|
+
return False
|
|
726
|
+
|
|
727
|
+
async def get_metrics(self) -> Dict[str, float]:
|
|
728
|
+
"""
|
|
729
|
+
Get all database maintenance metrics including base, custom, and v1.4.3 specific.
|
|
730
|
+
"""
|
|
731
|
+
# Get all base + custom metrics
|
|
732
|
+
metrics = self._collect_metrics()
|
|
733
|
+
# Calculate database size
|
|
734
|
+
db_size_mb = 0.0
|
|
735
|
+
try:
|
|
736
|
+
import os
|
|
737
|
+
|
|
738
|
+
from ciris_engine.logic.persistence import get_sqlite_db_full_path
|
|
739
|
+
|
|
740
|
+
db_path = get_sqlite_db_full_path()
|
|
741
|
+
if os.path.exists(db_path):
|
|
742
|
+
db_size_mb = os.path.getsize(db_path) / (1024 * 1024)
|
|
743
|
+
except (OSError, IOError, ImportError):
|
|
744
|
+
# Ignore file system and import errors when checking database size
|
|
745
|
+
pass
|
|
746
|
+
|
|
747
|
+
# Calculate uptime in seconds
|
|
748
|
+
uptime_seconds = 0.0
|
|
749
|
+
if hasattr(self, "_start_time") and self._start_time is not None:
|
|
750
|
+
current_time = self.time_service.now()
|
|
751
|
+
uptime_delta = current_time - self._start_time
|
|
752
|
+
uptime_seconds = uptime_delta.total_seconds()
|
|
753
|
+
|
|
754
|
+
# Add v1.4.3 specific metrics
|
|
755
|
+
metrics.update(
|
|
756
|
+
{
|
|
757
|
+
"db_vacuum_operations": float(self._vacuum_runs),
|
|
758
|
+
"db_cleanup_operations": float(self._cleanup_runs),
|
|
759
|
+
"db_size_mb": db_size_mb,
|
|
760
|
+
"db_maintenance_uptime_seconds": uptime_seconds,
|
|
761
|
+
}
|
|
762
|
+
)
|
|
763
|
+
|
|
764
|
+
return metrics
|