agentengine-sdk-python 0.8.4__py3-none-any.whl → 0.8.6__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.
- {agentengine_sdk_python-0.8.4.dist-info → agentengine_sdk_python-0.8.6.dist-info}/METADATA +17 -10
- agentengine_sdk_python-0.8.6.dist-info/RECORD +1731 -0
- ksadk/_async_iterators.py +79 -0
- ksadk/_build_provenance.json +1 -1
- ksadk/_model_anthropic.py +49 -0
- ksadk/_model_input.py +86 -0
- ksadk/_model_json.py +40 -0
- ksadk/_model_reasoning.py +17 -0
- ksadk/_model_refusal.py +20 -0
- ksadk/_model_sse.py +163 -0
- ksadk/_process.py +83 -0
- ksadk/_str_enum.py +17 -0
- ksadk/a2a/__init__.py +157 -167
- ksadk/a2a/_invocation_state.py +86 -0
- ksadk/a2a/_space_client_events.py +33 -22
- ksadk/a2a/adk.py +194 -0
- ksadk/a2a/adk_invocation_context.py +242 -0
- ksadk/a2a/adk_runtime.py +126 -0
- ksadk/a2a/adk_tools.py +319 -0
- ksadk/a2a/bootstrap.py +149 -23
- ksadk/a2a/build_validation.py +147 -0
- ksadk/a2a/card.py +23 -15
- ksadk/a2a/codex.py +160 -0
- ksadk/a2a/codex_checkpoint.py +111 -0
- ksadk/a2a/codex_recovery.py +96 -0
- ksadk/a2a/codex_recovery_events.py +123 -0
- ksadk/a2a/codex_runtime.py +198 -0
- ksadk/a2a/codex_session_checkpoint.py +162 -0
- ksadk/a2a/composition.py +88 -0
- ksadk/a2a/context_store.py +118 -19
- ksadk/a2a/control_plane.py +108 -106
- ksadk/a2a/event_adapter.py +92 -193
- ksadk/a2a/executor.py +257 -85
- ksadk/a2a/exposure.py +106 -0
- ksadk/a2a/external_transport.py +3 -4
- ksadk/a2a/identity.py +106 -12
- ksadk/a2a/ids.py +14 -3
- ksadk/a2a/inbound_kernel.py +133 -0
- ksadk/a2a/interaction_wire.py +76 -0
- ksadk/a2a/invocation_checkpoint.py +274 -0
- ksadk/a2a/invocation_policy.py +87 -0
- ksadk/a2a/invocation_publication.py +210 -0
- ksadk/a2a/invocation_service.py +972 -0
- ksadk/a2a/invocation_types.py +459 -0
- ksadk/a2a/kernel_task_adapter.py +259 -0
- ksadk/a2a/langgraph.py +20 -7
- ksadk/a2a/langgraph_invocation_context.py +136 -0
- ksadk/a2a/langgraph_managed.py +150 -0
- ksadk/a2a/langgraph_recovery.py +32 -0
- ksadk/a2a/langgraph_runtime.py +89 -0
- ksadk/a2a/langgraph_tool_runtime.py +132 -0
- ksadk/a2a/langgraph_tools.py +63 -0
- ksadk/a2a/message_digest.py +40 -0
- ksadk/a2a/platform.py +389 -0
- ksadk/a2a/policy_refs.py +13 -0
- ksadk/a2a/presentation.py +402 -0
- ksadk/a2a/product_kernel_facts.py +177 -0
- ksadk/a2a/product_key.py +99 -0
- ksadk/a2a/protocol_errors.py +116 -0
- ksadk/a2a/result_text.py +49 -0
- ksadk/a2a/resume_store.py +93 -3
- ksadk/a2a/routes.py +6 -1
- ksadk/a2a/runtime_approval.py +198 -0
- ksadk/a2a/runtime_input.py +151 -0
- ksadk/a2a/server.py +16 -7
- ksadk/a2a/space_client.py +101 -16
- ksadk/a2a/task_adapter.py +19 -5
- ksadk/a2a/task_event_dispatcher.py +39 -2
- ksadk/a2a/task_event_outbox.py +215 -0
- ksadk/a2a/task_event_outbox_owned.py +130 -0
- ksadk/a2a/task_store.py +37 -0
- ksadk/a2a/tool_activity.py +176 -0
- ksadk/a2a/workload_tokens.py +134 -0
- ksadk/a2ui/core.py +3 -3
- ksadk/api/client.py +38 -79
- ksadk/api/sse_stream.py +96 -0
- ksadk/builders/code_builder.py +121 -118
- ksadk/builders/container_builder.py +11 -29
- ksadk/builders/framework_requirements.py +22 -2
- ksadk/builders/managed_runtime_builder.py +12 -0
- ksadk/builders/source_provenance.py +87 -0
- ksadk/cli/__init__.py +36 -0
- ksadk/cli/cmd_a2a.py +43 -0
- ksadk/cli/cmd_build.py +9 -0
- ksadk/cli/cmd_config.py +4 -4
- ksadk/cli/cmd_create.py +12 -12
- ksadk/cli/cmd_deploy.py +27 -2
- ksadk/cli/cmd_hermes.py +24 -2
- ksadk/cli/cmd_invoke.py +64 -88
- ksadk/cli/cmd_openclaw.py +26 -1
- ksadk/cli/cmd_plugin.py +70 -12
- ksadk/cli/cmd_studio.py +69 -17
- ksadk/cli/cmd_web.py +2 -0
- ksadk/cli/hosted_invoke.py +206 -0
- ksadk/cli/invoke_content.py +60 -0
- ksadk/cli/openclaw_env.py +1 -1
- ksadk/cli/resource_common.py +26 -0
- ksadk/cli/runtime_bootstrap.py +27 -5
- ksadk/codex/_expert_request_reader.py +48 -0
- ksadk/codex/a2a_tools.py +140 -0
- ksadk/codex/async_approval.py +169 -0
- ksadk/codex/async_client.py +938 -0
- ksadk/codex/async_proxy.py +216 -0
- ksadk/codex/base_runtime.py +25 -0
- ksadk/codex/client.py +3 -1047
- ksadk/codex/client_payloads.py +85 -0
- ksadk/codex/rollout_checkpoint.py +264 -0
- ksadk/codex/runtime.py +290 -54
- ksadk/common/auth.py +2 -2
- ksadk/common/cloud_headers.py +36 -0
- ksadk/common/diagnostics.py +34 -0
- ksadk/common/kop_client.py +2 -1
- ksadk/configs/__init__.py +1 -1
- ksadk/configs/env_registry.py +216 -143
- ksadk/configs/env_registry_a2a.py +173 -0
- ksadk/configs/env_registry_studio.py +134 -0
- ksadk/configs/global_config.py +2 -1
- ksadk/configs/settings.py +9 -3
- ksadk/connector/__init__.py +17 -0
- ksadk/connector/channel.py +477 -0
- ksadk/context_engine/assembler.py +9 -0
- ksadk/context_engine/capabilities.py +52 -4
- ksadk/context_engine/contributors.py +80 -17
- ksadk/context_engine/instruction_authority.py +18 -0
- ksadk/conversations/attachment_storage.py +10 -3
- ksadk/conversations/attachments.py +69 -20
- ksadk/conversations/contracts.py +28 -9
- ksadk/conversations/message_projection.py +51 -155
- ksadk/conversations/message_projection_blocks.py +137 -0
- ksadk/conversations/model_context.py +11 -3
- ksadk/conversations/normalize.py +28 -10
- ksadk/conversations/projector.py +63 -0
- ksadk/conversations/runtime_baseline.py +37 -0
- ksadk/conversations/runtime_compaction.py +7 -2
- ksadk/conversations/runtime_input.py +16 -4
- ksadk/conversations/runtime_invocation.py +17 -4
- ksadk/conversations/runtime_observability.py +39 -10
- ksadk/conversations/runtime_payloads.py +12 -0
- ksadk/conversations/runtime_persistence.py +296 -32
- ksadk/conversations/runtime_preparation.py +98 -13
- ksadk/conversations/runtime_projection.py +217 -0
- ksadk/conversations/runtime_resume.py +141 -70
- ksadk/conversations/runtime_stream_events.py +29 -35
- ksadk/conversations/runtime_streaming.py +8 -0
- ksadk/conversations/tool_receipt_resume.py +387 -0
- ksadk/conversations/tool_receipts.py +32 -0
- ksadk/deployment/env_forward.py +5 -0
- ksadk/deployment/manager.py +15 -6
- ksadk/deployment/providers/serverless.py +76 -136
- ksadk/deployment/providers/serverless_payloads.py +122 -0
- ksadk/evaluation/agent_eval_client.py +2 -1
- ksadk/evaluation/contracts.py +78 -3
- ksadk/evaluation/evaluators.py +166 -1
- ksadk/evaluation/evidence.py +271 -4
- ksadk/evaluation/local_adapter.py +76 -12
- ksadk/evaluation/studio_build_adapter.py +73 -9
- ksadk/events/adapters/_a2a_checkpoint.py +151 -0
- ksadk/events/adapters/_a2a_snapshot.py +18 -14
- ksadk/events/adapters/_a2a_support.py +15 -3
- ksadk/events/adapters/_a2a_tool_activity.py +123 -0
- ksadk/events/adapters/_codex_errors.py +49 -0
- ksadk/events/adapters/_codex_items.py +16 -8
- ksadk/events/adapters/_langgraph_support.py +46 -1
- ksadk/events/adapters/a2a.py +54 -26
- ksadk/events/adapters/adk.py +188 -30
- ksadk/events/adapters/codex.py +33 -7
- ksadk/events/adapters/langgraph.py +16 -6
- ksadk/events/canonical.py +5 -0
- ksadk/events/canonical_store.py +200 -4
- ksadk/events/reducer.py +82 -0
- ksadk/events/run_authority.py +176 -0
- ksadk/events/session_event.py +2 -2
- ksadk/harness/__init__.py +18 -0
- ksadk/harness/app.py +11 -0
- ksadk/harness/artifact_adapters/__init__.py +1 -0
- ksadk/harness/artifact_adapters/native_page_budget.py +172 -0
- ksadk/harness/artifact_adapters/native_search.py +249 -0
- ksadk/harness/artifact_adapters/native_search_budget.py +134 -0
- ksadk/harness/artifact_adapters/native_store.py +115 -0
- ksadk/harness/artifact_adapters/native_tool.py +222 -0
- ksadk/harness/artifact_store.py +230 -0
- ksadk/harness/browser_adapters/__init__.py +6 -0
- ksadk/harness/browser_adapters/native_browser_tool.py +92 -0
- ksadk/harness/browser_adapters/native_dom_snapshot.py +187 -0
- ksadk/harness/browser_adapters/native_playwright.py +953 -0
- ksadk/harness/browser_adapters/native_vision.py +295 -0
- ksadk/harness/capabilities.py +115 -0
- ksadk/harness/capability_adapters/__init__.py +1 -0
- ksadk/harness/capability_adapters/native_dsh.py +289 -0
- ksadk/harness/capability_runtime.py +332 -0
- ksadk/harness/closure_contract.py +92 -0
- ksadk/harness/compaction_record.py +153 -0
- ksadk/harness/compiler.py +284 -0
- ksadk/harness/config.py +28 -5
- ksadk/harness/conformance/__init__.py +33 -0
- ksadk/harness/conformance/contract.py +504 -0
- ksadk/harness/conformance/fixtures.py +102 -0
- ksadk/harness/context_engine.py +388 -0
- ksadk/harness/context_maintenance.py +259 -0
- ksadk/harness/context_manifest.py +188 -0
- ksadk/harness/context_sections.py +397 -0
- ksadk/harness/context_tuning.py +168 -0
- ksadk/harness/diagnostic_adapters/__init__.py +1 -0
- ksadk/harness/diagnostic_adapters/contracts.py +70 -0
- ksadk/harness/diagnostic_adapters/lsp_rpc.py +210 -0
- ksadk/harness/diagnostic_adapters/native_lsp.py +286 -0
- ksadk/harness/draft_runtime.py +322 -0
- ksadk/harness/engine/__init__.py +40 -0
- ksadk/harness/engine/base.py +122 -0
- ksadk/harness/engine/budgets.py +108 -0
- ksadk/harness/engine/capability_declarations.py +59 -0
- ksadk/harness/engine/completion_guard.py +57 -0
- ksadk/harness/engine/context_pipeline.py +1351 -0
- ksadk/harness/engine/graph_builder.py +352 -0
- ksadk/harness/engine/hooked_reasoner.py +380 -0
- ksadk/harness/engine/langgraph.py +1049 -0
- ksadk/harness/engine/mcp_disclosure.py +701 -0
- ksadk/harness/engine/phases/__init__.py +6 -0
- ksadk/harness/engine/phases/context.py +48 -0
- ksadk/harness/engine/phases/interaction.py +31 -0
- ksadk/harness/engine/phases/reason.py +552 -0
- ksadk/harness/engine/phases/tools.py +638 -0
- ksadk/harness/engine/policy_runtime.py +81 -0
- ksadk/harness/engine/postgres_checkpointer.py +386 -0
- ksadk/harness/engine/run_control_bridge.py +100 -0
- ksadk/harness/engine/run_types.py +98 -0
- ksadk/harness/engine/skill_disclosure.py +275 -0
- ksadk/harness/engine/spans.py +41 -0
- ksadk/harness/engine/steering.py +177 -0
- ksadk/harness/engine/subagents.py +360 -0
- ksadk/harness/engine/thread_ids.py +112 -0
- ksadk/harness/engine/tool_dispatch.py +249 -0
- ksadk/harness/event_tree.py +212 -0
- ksadk/harness/events.py +498 -0
- ksadk/harness/execution_policy.py +104 -0
- ksadk/harness/hooks.py +259 -0
- ksadk/harness/insights.py +210 -0
- ksadk/harness/lifecycle.py +578 -0
- ksadk/harness/lifecycle_conformance.py +233 -0
- ksadk/harness/lifecycle_local_plane.py +104 -0
- ksadk/harness/loop/__init__.py +44 -0
- ksadk/harness/loop/reason.py +699 -0
- ksadk/harness/loop/tools.py +907 -0
- ksadk/harness/managed_runtime.py +1044 -0
- ksadk/harness/mcp_disclosure_contract.py +85 -0
- ksadk/harness/mcp_matrix.py +474 -0
- ksadk/harness/mcp_result_policy.py +44 -0
- ksadk/harness/mcp_runtime.py +504 -0
- ksadk/harness/memory_consolidation.py +157 -0
- ksadk/harness/memory_loop.py +156 -0
- ksadk/harness/memory_runtime.py +541 -0
- ksadk/harness/metrics.py +90 -0
- ksadk/harness/micro_compact.py +69 -0
- ksadk/harness/model_adapters/__init__.py +1 -0
- ksadk/harness/model_adapters/native_mcp_media.py +100 -0
- ksadk/harness/model_adapters/native_mcp_result.py +36 -0
- ksadk/harness/model_adapters/native_openai.py +703 -0
- ksadk/harness/model_capability.py +468 -0
- ksadk/harness/model_provider.py +430 -0
- ksadk/harness/multimodal.py +57 -0
- ksadk/harness/native/__init__.py +1 -0
- ksadk/harness/native/activation_contract.py +25 -0
- ksadk/harness/native/activation_recovery.py +29 -0
- ksadk/harness/native/adapters.py +291 -0
- ksadk/harness/native/artifact_contract.py +14 -0
- ksadk/harness/native/artifact_partial_read_capacity.py +171 -0
- ksadk/harness/native/artifact_read_capacity.py +182 -0
- ksadk/harness/native/artifact_read_contract.py +27 -0
- ksadk/harness/native/artifact_runtime.py +408 -0
- ksadk/harness/native/artifact_search_capacity.py +206 -0
- ksadk/harness/native/artifact_search_contract.py +40 -0
- ksadk/harness/native/artifact_single_read_capacity.py +170 -0
- ksadk/harness/native/browser_contract.py +229 -0
- ksadk/harness/native/browser_recovery.py +183 -0
- ksadk/harness/native/capabilities.py +204 -0
- ksadk/harness/native/child_approval.py +60 -0
- ksadk/harness/native/child_budget.py +136 -0
- ksadk/harness/native/child_cancellation.py +80 -0
- ksadk/harness/native/child_input.py +98 -0
- ksadk/harness/native/child_input_runtime.py +59 -0
- ksadk/harness/native/child_interruption.py +81 -0
- ksadk/harness/native/child_lifecycle.py +246 -0
- ksadk/harness/native/child_lifecycle_contract.py +91 -0
- ksadk/harness/native/child_notifications.py +75 -0
- ksadk/harness/native/child_promotion.py +66 -0
- ksadk/harness/native/command_runtime.py +99 -0
- ksadk/harness/native/completion.py +302 -0
- ksadk/harness/native/completion_text.py +116 -0
- ksadk/harness/native/context.py +358 -0
- ksadk/harness/native/context_artifact_page.py +75 -0
- ksadk/harness/native/context_compaction_projection.py +131 -0
- ksadk/harness/native/context_contributions.py +320 -0
- ksadk/harness/native/context_contributor_contract.py +133 -0
- ksadk/harness/native/context_driver.py +820 -0
- ksadk/harness/native/context_fresh_tools.py +49 -0
- ksadk/harness/native/context_history.py +272 -0
- ksadk/harness/native/context_microcompact.py +61 -0
- ksadk/harness/native/context_partial_summary.py +58 -0
- ksadk/harness/native/context_partition.py +492 -0
- ksadk/harness/native/context_pruning.py +275 -0
- ksadk/harness/native/context_reduction.py +60 -0
- ksadk/harness/native/context_replay.py +148 -0
- ksadk/harness/native/context_request_projection.py +526 -0
- ksadk/harness/native/context_runtime.py +976 -0
- ksadk/harness/native/context_runtime_contracts.py +409 -0
- ksadk/harness/native/context_search.py +112 -0
- ksadk/harness/native/context_source_fragments.py +188 -0
- ksadk/harness/native/context_source_progress.py +119 -0
- ksadk/harness/native/context_summary_planning.py +788 -0
- ksadk/harness/native/context_summary_recovery.py +105 -0
- ksadk/harness/native/delivery_review.py +331 -0
- ksadk/harness/native/delivery_review_contract.py +54 -0
- ksadk/harness/native/effect_admission.py +82 -0
- ksadk/harness/native/effect_control.py +318 -0
- ksadk/harness/native/effect_receipts.py +729 -0
- ksadk/harness/native/effect_runtime.py +303 -0
- ksadk/harness/native/effective_configuration.py +28 -0
- ksadk/harness/native/engine.py +945 -0
- ksadk/harness/native/final_output.py +34 -0
- ksadk/harness/native/final_submission.py +58 -0
- ksadk/harness/native/finalization_workspace.py +96 -0
- ksadk/harness/native/fork.py +151 -0
- ksadk/harness/native/guidance.py +91 -0
- ksadk/harness/native/history.py +381 -0
- ksadk/harness/native/hook_executor.py +205 -0
- ksadk/harness/native/hook_runtime_contract.py +282 -0
- ksadk/harness/native/interaction_observation.py +117 -0
- ksadk/harness/native/lease.py +103 -0
- ksadk/harness/native/machine.py +974 -0
- ksadk/harness/native/mcp_result_governance.py +156 -0
- ksadk/harness/native/model.py +570 -0
- ksadk/harness/native/model_feedback.py +63 -0
- ksadk/harness/native/model_input.py +30 -0
- ksadk/harness/native/model_recovery_contract.py +35 -0
- ksadk/harness/native/model_replay.py +128 -0
- ksadk/harness/native/model_request.py +133 -0
- ksadk/harness/native/model_runtime.py +196 -0
- ksadk/harness/native/model_takeover.py +419 -0
- ksadk/harness/native/model_tool_batch.py +40 -0
- ksadk/harness/native/observed_progress.py +46 -0
- ksadk/harness/native/operator_guidance.py +201 -0
- ksadk/harness/native/output_contract.py +80 -0
- ksadk/harness/native/output_recovery.py +24 -0
- ksadk/harness/native/ports.py +749 -0
- ksadk/harness/native/precompact_hook_runtime.py +171 -0
- ksadk/harness/native/replay_context.py +149 -0
- ksadk/harness/native/request_media.py +112 -0
- ksadk/harness/native/restore_contract.py +16 -0
- ksadk/harness/native/run_clock.py +120 -0
- ksadk/harness/native/state.py +436 -0
- ksadk/harness/native/steering.py +170 -0
- ksadk/harness/native/stop_hook_runtime.py +151 -0
- ksadk/harness/native/studio_admission.py +29 -0
- ksadk/harness/native/subagents.py +86 -0
- ksadk/harness/native/task_policy.py +99 -0
- ksadk/harness/native/task_progress.py +86 -0
- ksadk/harness/native/terminal_verification.py +43 -0
- ksadk/harness/native/tool_argument_feedback.py +178 -0
- ksadk/harness/native/tool_budget.py +253 -0
- ksadk/harness/native/tool_error_streak.py +89 -0
- ksadk/harness/native/tool_hook_runtime.py +343 -0
- ksadk/harness/native/tool_input_validation.py +58 -0
- ksadk/harness/native/tool_interruption.py +96 -0
- ksadk/harness/native/tool_observation.py +259 -0
- ksadk/harness/native/tool_progress.py +223 -0
- ksadk/harness/native/tool_recovery.py +25 -0
- ksadk/harness/native/tool_scheduling.py +33 -0
- ksadk/harness/native/tool_schema.py +126 -0
- ksadk/harness/native/transitions.py +151 -0
- ksadk/harness/native/turn_control.py +98 -0
- ksadk/harness/native/user_document.py +98 -0
- ksadk/harness/native/user_document_capture.py +49 -0
- ksadk/harness/native/user_input.py +87 -0
- ksadk/harness/native/verification.py +432 -0
- ksadk/harness/native/verification_binding.py +40 -0
- ksadk/harness/native/verification_runtime.py +233 -0
- ksadk/harness/native/verification_workspace.py +67 -0
- ksadk/harness/native_driver_failure.py +123 -0
- ksadk/harness/native_facade.py +977 -0
- ksadk/harness/native_factory.py +244 -0
- ksadk/harness/native_projection.py +503 -0
- ksadk/harness/native_runtime.py +621 -0
- ksadk/harness/native_shadow.py +250 -0
- ksadk/harness/native_shadow_inputs.py +146 -0
- ksadk/harness/observability/__init__.py +29 -0
- ksadk/harness/observability/inspection.py +528 -0
- ksadk/harness/observability/metrics.py +167 -0
- ksadk/harness/observability/otel_exporter.py +218 -0
- ksadk/harness/progress_adapters/__init__.py +5 -0
- ksadk/harness/progress_adapters/native_todo.py +75 -0
- ksadk/harness/prompt_cache.py +132 -0
- ksadk/harness/public_activity.py +213 -0
- ksadk/harness/public_output.py +30 -0
- ksadk/harness/public_summary.py +36 -0
- ksadk/harness/readiness.py +249 -0
- ksadk/harness/reasoner.py +779 -17
- ksadk/harness/release_readiness.py +140 -0
- ksadk/harness/resource_ref.py +69 -0
- ksadk/harness/rpc.py +200 -0
- ksadk/harness/run_control.py +773 -0
- ksadk/harness/runtime.py +157 -113
- ksadk/harness/runtime_capabilities.py +228 -0
- ksadk/harness/runtime_server.py +514 -0
- ksadk/harness/sandbox_adapters.py +739 -0
- ksadk/harness/sandbox_backend.py +733 -0
- ksadk/harness/sandbox_conformance.py +288 -0
- ksadk/harness/sandbox_lease.py +77 -0
- ksadk/harness/sandbox_lease_conformance.py +259 -0
- ksadk/harness/sandbox_matrix.py +170 -0
- ksadk/harness/sandbox_reconciliation.py +140 -0
- ksadk/harness/sandbox_recovery.py +586 -0
- ksadk/harness/sandbox_recovery_conformance.py +246 -0
- ksadk/harness/sdk.py +153 -0
- ksadk/harness/session_store.py +589 -0
- ksadk/harness/skill_adapters/__init__.py +1 -0
- ksadk/harness/skill_adapters/native_bundle.py +148 -0
- ksadk/harness/skill_adapters/native_disclosure.py +306 -0
- ksadk/harness/skill_composition.py +212 -0
- ksadk/harness/skill_feedback.py +123 -0
- ksadk/harness/skill_intent.py +47 -0
- ksadk/harness/skill_matrix.py +233 -0
- ksadk/harness/skill_runtime.py +317 -0
- ksadk/harness/spec.py +342 -0
- ksadk/harness/state.py +155 -0
- ksadk/harness/stores/__init__.py +14 -0
- ksadk/harness/stores/native_command_settlement.py +65 -0
- ksadk/harness/stores/native_contract.py +311 -0
- ksadk/harness/stores/native_memory.py +326 -0
- ksadk/harness/stores/native_memory_archive.py +70 -0
- ksadk/harness/stores/native_migration_cli.py +91 -0
- ksadk/harness/stores/native_outbox.py +56 -0
- ksadk/harness/stores/native_sqlite.py +782 -0
- ksadk/harness/stores/native_sqlite_audit.py +29 -0
- ksadk/harness/stores/native_sqlite_migration.py +252 -0
- ksadk/harness/strategies.py +149 -0
- ksadk/harness/subagent.py +263 -0
- ksadk/harness/subagent_adapters/checkpoint_recovery.py +120 -0
- ksadk/harness/subagent_adapters/native_background_child.py +803 -0
- ksadk/harness/subagent_adapters/native_child.py +819 -0
- ksadk/harness/subagent_adapters/native_child_approval.py +128 -0
- ksadk/harness/subagent_adapters/native_child_continuation.py +51 -0
- ksadk/harness/subagent_adapters/native_child_result.py +392 -0
- ksadk/harness/subagent_adapters/prepared_recovery.py +120 -0
- ksadk/harness/tool_display.py +75 -0
- ksadk/harness/tool_display_contract.py +134 -0
- ksadk/harness/tool_output.py +141 -0
- ksadk/harness/tool_policy.py +134 -0
- ksadk/harness/tool_receipts.py +96 -0
- ksadk/harness/tool_reliability.py +81 -0
- ksadk/harness/tool_result_policy.py +216 -0
- ksadk/harness/tools.py +52 -0
- ksadk/harness/user_errors.py +69 -0
- ksadk/harness/working_context.py +81 -0
- ksadk/harness/working_context_patch.py +99 -0
- ksadk/harness/workspace_adapters/__init__.py +6 -0
- ksadk/harness/workspace_adapters/native_directory.py +180 -0
- ksadk/harness/workspace_adapters/native_git.py +208 -0
- ksadk/harness/workspace_adapters/native_isolation.py +350 -0
- ksadk/identity/resolver.py +18 -0
- ksadk/interaction/__init__.py +1 -1
- ksadk/interaction/ledger.py +1 -1
- ksadk/interaction/provider.py +1 -1
- ksadk/interaction/providers/__init__.py +3 -1
- ksadk/interaction/providers/adk.py +1 -1
- ksadk/interaction/providers/codex.py +1 -1
- ksadk/interaction/providers/harness.py +50 -0
- ksadk/interaction/providers/langgraph.py +9 -2
- ksadk/kernel/__init__.py +10 -0
- ksadk/kernel/approval_presentation.py +91 -0
- ksadk/kernel/authorization.py +1 -1
- ksadk/kernel/bootstrap.py +220 -252
- ksadk/kernel/contract_fingerprints.py +45 -1
- ksadk/kernel/contracts.py +30 -0
- ksadk/kernel/control.py +180 -29
- ksadk/kernel/execution_grants.py +428 -0
- ksadk/kernel/execution_grants_memory.py +252 -0
- ksadk/kernel/execution_grants_postgres.py +395 -0
- ksadk/kernel/execution_grants_sqlite.py +435 -0
- ksadk/kernel/execution_host_ingress.py +1071 -0
- ksadk/kernel/history_projection.py +120 -0
- ksadk/kernel/ingress.py +139 -226
- ksadk/kernel/ingress_bootstrap.py +268 -0
- ksadk/kernel/legacy_history.py +179 -0
- ksadk/kernel/mapping.py +1 -1
- ksadk/kernel/memory_store.py +61 -58
- ksadk/kernel/memory_store_projection.py +63 -0
- ksadk/kernel/postgres_event_log.py +181 -0
- ksadk/kernel/postgres_store.py +230 -231
- ksadk/kernel/readiness.py +125 -0
- ksadk/kernel/recovery.py +166 -16
- ksadk/kernel/recovery_projection.py +124 -0
- ksadk/kernel/runtime_checkpoint.py +34 -0
- ksadk/kernel/sql/001_agent_kernel.sql +28 -0
- ksadk/kernel/sqlite_schema.py +100 -0
- ksadk/kernel/sqlite_store.py +410 -200
- ksadk/kernel/state.py +2 -3
- ksadk/kernel/store.py +104 -5
- ksadk/kernel/teams_artifact_tools.py +392 -0
- ksadk/kernel/teams_effects.py +851 -0
- ksadk/kernel/teams_execution_context.py +408 -0
- ksadk/kernel/teams_host_http.py +237 -0
- ksadk/kernel/teams_material_transport.py +245 -0
- ksadk/kernel/teams_materials.py +318 -0
- ksadk/kernel/teams_runtime_bootstrap.py +604 -0
- ksadk/kernel/teams_tool_runtime.py +273 -0
- ksadk/kernel/teams_workspace.py +259 -0
- ksadk/kernel/worker.py +369 -340
- ksadk/kernel/worker_controls.py +454 -0
- ksadk/kernel/worker_history.py +72 -0
- ksadk/kernel/worker_identity.py +74 -0
- ksadk/kernel/worker_interactions.py +197 -0
- ksadk/knowledge_base/client.py +15 -1
- ksadk/managed_runtime.py +29 -2
- ksadk/memory/adk/backends/http_ltm_backend.py +2 -1
- ksadk/memory/adk/backends/sdk_ltm_backend.py +15 -1
- ksadk/memory/adk/bounded_database_session_service.py +232 -0
- ksadk/memory/adk/resilient_session_service.py +115 -15
- ksadk/memory/adk/short_term_memory.py +8 -9
- ksadk/memory/coordinator.py +22 -6
- ksadk/memory/extraction.py +159 -7
- ksadk/memory/models.py +77 -1
- ksadk/memory/provider_resolver.py +5 -0
- ksadk/memory/providers/local_candidates.py +183 -0
- ksadk/memory/providers/local_postgres.py +200 -0
- ksadk/memory/providers/local_sqlite.py +280 -67
- ksadk/memory/resolved_policy.py +12 -7
- ksadk/memory/retrieval.py +189 -0
- ksadk/memory/store_adapter.py +150 -0
- ksadk/model_gateway/__init__.py +29 -0
- ksadk/model_gateway/client.py +253 -0
- ksadk/model_gateway/events.py +113 -0
- ksadk/model_gateway/matrix.py +297 -0
- ksadk/model_policy.py +2 -2
- ksadk/model_proxy/compat.py +670 -0
- ksadk/model_proxy/detect.py +254 -0
- ksadk/model_proxy/server.py +14 -9
- ksadk/model_proxy/transform.py +72 -6
- ksadk/plugins/__init__.py +1 -1
- ksadk/plugins/bridges/dsh.py +29 -20
- ksadk/plugins/bridges/dsh_profile_manifest.py +36 -0
- ksadk/plugins/builtin_resources.py +199 -0
- ksadk/plugins/builtins.py +417 -185
- ksadk/plugins/companion_artifacts.py +83 -0
- ksadk/plugins/companions.py +368 -0
- ksadk/plugins/context_contributor.py +15 -4
- ksadk/plugins/contracts.py +1 -1
- ksadk/plugins/dsh_channels.py +156 -0
- ksadk/plugins/dsh_dependency_policy.py +41 -0
- ksadk/plugins/dsh_home.py +140 -0
- ksadk/plugins/dsh_teams.py +105 -0
- ksadk/plugins/dsh_toolchain.py +92 -21
- ksadk/plugins/execution_host.py +107 -0
- ksadk/plugins/host.py +73 -5
- ksadk/plugins/kernel_adapter.py +44 -1
- ksadk/plugins/memory_provider.py +180 -0
- ksadk/plugins/providers/_process_group.py +50 -0
- ksadk/plugins/providers/bundles/dsh-channels-client/client.js +19 -0
- ksadk/plugins/providers/bundles/dsh-channels-client/cordis.patch.yml +3 -0
- ksadk/plugins/providers/bundles/dsh-channels-client/index.mjs +7 -0
- ksadk/plugins/providers/bundles/dsh-channels-client/package.json +12 -0
- ksadk/plugins/providers/bundles/dsh-knowledge/index.mjs +24 -2
- ksadk/plugins/providers/bundles/dsh-knowledge/package.json +1 -1
- ksadk/plugins/providers/bundles/dsh-memory/package.json +1 -1
- ksadk/plugins/providers/bundles/dsh-skill-center/package.json +1 -1
- ksadk/plugins/providers/bundles/dsh-teams-client/client.js +29 -0
- ksadk/plugins/providers/bundles/dsh-teams-client/cordis.patch.yml +3 -0
- ksadk/plugins/providers/bundles/dsh-teams-client/index.mjs +11 -0
- ksadk/plugins/providers/bundles/dsh-teams-client/package.json +35 -0
- ksadk/plugins/providers/bundles/dsh-teams-leader-policy/cordis.patch.yml +3 -0
- ksadk/plugins/providers/bundles/dsh-teams-leader-policy/index.mjs +13 -0
- ksadk/plugins/providers/bundles/dsh-teams-leader-policy/package.json +27 -0
- ksadk/plugins/providers/bundles/dsh-teams-profile/cordis.patch.yml +3 -0
- ksadk/plugins/providers/bundles/dsh-teams-profile/index.mjs +12 -0
- ksadk/plugins/providers/bundles/dsh-teams-profile/package.json +26 -0
- ksadk/plugins/providers/bundles/dsh-teams-router/cordis.patch.yml +3 -0
- ksadk/plugins/providers/bundles/dsh-teams-router/index.mjs +16 -0
- ksadk/plugins/providers/bundles/dsh-teams-router/package.json +27 -0
- ksadk/plugins/providers/bundles/dsh-teams-tasks/cordis.patch.yml +3 -0
- ksadk/plugins/providers/bundles/dsh-teams-tasks/index.mjs +16 -0
- ksadk/plugins/providers/bundles/dsh-teams-tasks/package.json +27 -0
- ksadk/plugins/providers/bundles/dsh-teams-tools/cordis.patch.yml +3 -0
- ksadk/plugins/providers/bundles/dsh-teams-tools/index.mjs +25 -0
- ksadk/plugins/providers/bundles/dsh-teams-tools/package.json +29 -0
- ksadk/plugins/providers/bundles/dsh-teams-tools/tools.json +235 -0
- ksadk/plugins/providers/bundles/ksadk-codex/index.mjs +1 -1
- ksadk/plugins/providers/bundles/ksadk-dsh-capability-host/index.mjs +51 -1
- ksadk/plugins/providers/bundles/ksadk-dsh-capability-host/package.json +2 -2
- ksadk/plugins/providers/bundles/ksadk-dsh-companion-host/client.mjs +133 -0
- ksadk/plugins/providers/bundles/ksadk-dsh-companion-host/index.mjs +14 -0
- ksadk/plugins/providers/bundles/ksadk-dsh-studio/client.js +27 -4
- ksadk/plugins/providers/bundles/ksadk-dsh-studio/index.mjs +9 -5
- ksadk/plugins/providers/bundles/ksadk-harness/index.mjs +1 -1
- ksadk/plugins/providers/codex.py +52 -40
- ksadk/plugins/providers/codex_native.py +20 -0
- ksadk/plugins/providers/codex_skills.py +46 -0
- ksadk/plugins/providers/dsh_capabilities.py +49 -143
- ksadk/plugins/providers/dsh_connector_lease.py +225 -0
- ksadk/plugins/providers/dsh_mcp.py +163 -1
- ksadk/plugins/providers/harness.py +413 -52
- ksadk/plugins/providers/harness_context.py +61 -0
- ksadk/plugins/providers/harness_contributions.py +241 -0
- ksadk/plugins/providers/harness_delegation.py +670 -0
- ksadk/plugins/providers/harness_hooks.py +121 -0
- ksadk/plugins/providers/harness_managed.py +550 -0
- ksadk/plugins/providers/harness_tools.py +455 -0
- ksadk/plugins/providers/legacy_catalog.py +1 -1
- ksadk/plugins/providers/mcp_projection.py +100 -3
- ksadk/plugins/providers/platform_resources.py +16 -6
- ksadk/plugins/providers/shipped_dsh.py +4 -1
- ksadk/plugins/subagent_providers/codex.py +28 -6
- ksadk/plugins/teams/__init__.py +5 -0
- ksadk/plugins/teams/api.py +405 -0
- ksadk/plugins/teams/application.py +540 -0
- ksadk/plugins/teams/artifacts.py +60 -0
- ksadk/plugins/teams/build_artifacts.py +460 -0
- ksadk/plugins/teams/cloud_contract_fingerprints.py +22 -0
- ksadk/plugins/teams/cloud_contracts.py +928 -0
- ksadk/plugins/teams/cloud_permits.py +250 -0
- ksadk/plugins/teams/context.py +96 -0
- ksadk/plugins/teams/contracts.py +136 -0
- ksadk/plugins/teams/domain.py +1480 -0
- ksadk/plugins/teams/domain_values.py +24 -0
- ksadk/plugins/teams/effect_contracts.py +255 -0
- ksadk/plugins/teams/errors.py +13 -0
- ksadk/plugins/teams/execution_projection.py +255 -0
- ksadk/plugins/teams/leader_decisions.py +106 -0
- ksadk/plugins/teams/migration.py +311 -0
- ksadk/plugins/teams/migration_cli.py +322 -0
- ksadk/plugins/teams/postgres_store.py +352 -0
- ksadk/plugins/teams/release_contracts.py +60 -0
- ksadk/plugins/teams/runtime.py +853 -0
- ksadk/plugins/teams/source_projection.py +84 -0
- ksadk/plugins/teams/store.py +519 -0
- ksadk/plugins/teams/task_decisions.py +436 -0
- ksadk/plugins/teams/tool_service.py +152 -0
- ksadk/plugins/teams/transport.py +96 -0
- ksadk/plugins/teams/workspaces.py +255 -0
- ksadk/resource_runtime/skill_runtime.py +3 -0
- ksadk/resource_runtime/socket_server.py +11 -0
- ksadk/resource_runtime/worker.py +28 -4
- ksadk/runners/_adk_a2a_stream.py +122 -0
- ksadk/runners/_adk_canonical_stream.py +474 -0
- ksadk/runners/_langgraph_canonical_streams.py +527 -0
- ksadk/runners/_langgraph_runner_streams.py +83 -401
- ksadk/runners/_langgraph_state_reader.py +106 -0
- ksadk/runners/_langgraph_tool_projection.py +86 -0
- ksadk/runners/_langgraph_tools_transformer.py +27 -0
- ksadk/runners/_session_identity.py +285 -0
- ksadk/runners/adk_runner.py +220 -350
- ksadk/runners/base_runner.py +6 -5
- ksadk/runners/langgraph_runner.py +208 -195
- ksadk/runners/patch_langchain.py +47 -0
- ksadk/runners/usage_accumulator.py +11 -3
- ksadk/runners/utils/loader.py +28 -14
- ksadk/runtime/_runner_adapter/a2ui_surface.py +145 -0
- ksadk/runtime/_runner_adapter/gateway_approvals.py +93 -0
- ksadk/runtime/_runner_adapter/stream_mapping.py +134 -129
- ksadk/runtime/adapter.py +40 -3
- ksadk/runtime/conversation_execution.py +29 -3
- ksadk/runtime/executor.py +105 -7
- ksadk/runtime/factory.py +45 -3
- ksadk/runtime/framework_adapters.py +184 -10
- ksadk/runtime/hosted_finalizer.py +4 -6
- ksadk/runtime/launch.py +2 -0
- ksadk/runtime/preprocessing.py +11 -3
- ksadk/runtime/runner_adapter.py +160 -21
- ksadk/runtime/skill_eval_result.py +36 -0
- ksadk/runtime/timing.py +46 -0
- ksadk/runtime/usage.py +49 -18
- ksadk/runtime_context.py +105 -1
- ksadk/sandbox/backends/e2b.py +272 -24
- ksadk/sandbox/backends/local_process.py +73 -39
- ksadk/sandbox/base.py +62 -1
- ksadk/sandbox/diagnostics.py +82 -0
- ksadk/sandbox/e2b_connection.py +9 -1
- ksadk/sandbox/local_controls.py +776 -0
- ksadk/sandbox/local_launcher.py +124 -0
- ksadk/scheduler/dispatcher.py +1 -1
- ksadk/server/factory.py +178 -25
- ksadk/server/history_deadline.py +158 -0
- ksadk/server/history_page_cache.py +129 -0
- ksadk/server/invocation_identity.py +118 -0
- ksadk/server/routes/checkpoint_audit.py +88 -0
- ksadk/server/routes/checkpoint_listing.py +294 -0
- ksadk/server/routes/checkpoint_resolution.py +73 -20
- ksadk/server/routes/common.py +32 -3
- ksadk/server/routes/control.py +112 -9
- ksadk/server/routes/dependencies.py +2 -1
- ksadk/server/routes/display_projection.py +154 -0
- ksadk/server/routes/kernel_ingress.py +26 -3
- ksadk/server/routes/misc.py +331 -33
- ksadk/server/routes/models.py +28 -4
- ksadk/server/routes/openai_compat.py +82 -13
- ksadk/server/routes/projection.py +159 -216
- ksadk/server/routes/run.py +112 -37
- ksadk/server/routes/sessions.py +493 -358
- ksadk/server/routes/streaming.py +68 -15
- ksadk/server/routes/tool_receipt_claim_routes.py +107 -0
- ksadk/server/routes/workspace.py +135 -23
- ksadk/server/static/assets/{ArtifactsPanel-CGbWlMNh.js → ArtifactsPanel-CILaW-fC.js} +1 -1
- ksadk/server/static/assets/{CodeBlock-b4C7upmO.js → CodeBlock-BVrNVtJC.js} +10 -7
- ksadk/server/static/assets/MathMessageMarkdown-Dp7c4wWD.js +8 -0
- ksadk/server/static/assets/{MermaidBlock-BEBN4Ksz.js → MermaidBlock-Dxop8Rd7.js} +9 -9
- ksadk/server/static/assets/{NativeTerminalPanel-zvL-WpAn.js → NativeTerminalPanel-Cjjz8B30.js} +1 -1
- ksadk/server/static/assets/{abnfDiagram-VCTEODGH-BYafW7Za.js → abnfDiagram-VCTEODGH-ckWDmOzw.js} +1 -1
- ksadk/server/static/assets/{arc-bTohInsS.js → arc-DqxJede-.js} +1 -1
- ksadk/server/static/assets/architecture-7GRP2DOG-pn_DuLy6.js +1 -0
- ksadk/server/static/assets/{architectureDiagram-5GKGNRK7-Ch5Lbzsi.js → architectureDiagram-5GKGNRK7-SEQA4bVi.js} +1 -1
- ksadk/server/static/assets/{blockDiagram-NRAW4CY4-kqF4MDOG.js → blockDiagram-NRAW4CY4-pM0B-6NJ.js} +1 -1
- ksadk/server/static/assets/{c4Diagram-UCG6FXSJ-8uSRIODv.js → c4Diagram-UCG6FXSJ-m2tuCNVq.js} +1 -1
- ksadk/server/static/assets/channel-fySsnkft.js +1 -0
- ksadk/server/static/assets/chunk-2Q5K7J3B-BheGxKRQ.js +1 -0
- ksadk/server/static/assets/{chunk-5VM5RSS4-DkhehZDr.js → chunk-5VM5RSS4-GJHDr9Ww.js} +1 -1
- ksadk/server/static/assets/{chunk-F27PBJKO-BdXhtPe9.js → chunk-F27PBJKO-CbAN45AV.js} +1 -1
- ksadk/server/static/assets/{chunk-G27WJ6UU-DPTpvpwi.js → chunk-G27WJ6UU-D5ngbbzF.js} +1 -1
- ksadk/server/static/assets/{chunk-JWPE2WC7-Pqoh38el.js → chunk-JWPE2WC7-Cc5IwuYC.js} +1 -1
- ksadk/server/static/assets/{chunk-LCL6LL3I-DeU00qC-.js → chunk-LCL6LL3I-CprgDDdJ.js} +1 -1
- ksadk/server/static/assets/{chunk-POPQ4Y6H-CzxScFkr.js → chunk-POPQ4Y6H-CDZhSy82.js} +1 -1
- ksadk/server/static/assets/{chunk-RHFEMEQ7-DpqMx-ux.js → chunk-RHFEMEQ7-CZchUNro.js} +1 -1
- ksadk/server/static/assets/{chunk-SVP7TREG-C6t0SypQ.js → chunk-SVP7TREG-BVruqk6T.js} +1 -1
- ksadk/server/static/assets/{chunk-XXDRQBXY-DVaeafZk.js → chunk-XXDRQBXY-4ld9SxPN.js} +1 -1
- ksadk/server/static/assets/classDiagram-DTDB5LWJ-DSfLtNYm.js +1 -0
- ksadk/server/static/assets/classDiagram-v2-JRS7N3AN-DSfLtNYm.js +1 -0
- ksadk/server/static/assets/{cose-bilkent-JH36ORCC-Bf9D3tzJ.js → cose-bilkent-JH36ORCC-Dmyyk_Vp.js} +1 -1
- ksadk/server/static/assets/cynefin-OW5HDTMX-PFWIGtvA.js +1 -0
- ksadk/server/static/assets/{cynefinDiagram-5FMLGOSQ-B9cY3iTz.js → cynefinDiagram-5FMLGOSQ-BIyq3EJb.js} +1 -1
- ksadk/server/static/assets/{dagre-3AP2YEHR-CSwlx3CB.js → dagre-3AP2YEHR-eBw08Qdk.js} +1 -1
- ksadk/server/static/assets/{dagre-UBpgon5q.js → dagre-DfvnEf45.js} +1 -1
- ksadk/server/static/assets/{diagram-S7CK7UJ4-C9akhN9a.js → diagram-S7CK7UJ4-CUSrE3Mg.js} +1 -1
- ksadk/server/static/assets/{diagram-UQ7AKVKN-CgedhTPI.js → diagram-UQ7AKVKN-Dq5Zw2gy.js} +1 -1
- ksadk/server/static/assets/{diagram-VSXAHHWV-Cjucz5BY.js → diagram-VSXAHHWV-DyUHfNwT.js} +1 -1
- ksadk/server/static/assets/{diagram-VX7I27RA-Dd4Vleyn.js → diagram-VX7I27RA-CREmM89O.js} +1 -1
- ksadk/server/static/assets/{diagram-Z3DM3KII-CZ2jGtYW.js → diagram-Z3DM3KII-Dw9zhHUK.js} +1 -1
- ksadk/server/static/assets/{dist-Bj730Ib4.js → dist-0uJ4tdx6.js} +1 -1
- ksadk/server/static/assets/{dist-BnaTiyzN.js → dist-AEv-vXf-.js} +1 -1
- ksadk/server/static/assets/{dist-BgV_owcB.js → dist-B49GzZDb.js} +1 -1
- ksadk/server/static/assets/{dist-D_ctSS2i.js → dist-B8Myiet9.js} +1 -1
- ksadk/server/static/assets/{dist-ufY3F5p6.js → dist-BBsYarrI.js} +2 -2
- ksadk/server/static/assets/{dist-ClYUxfeK.js → dist-BQMrUwdI.js} +1 -1
- ksadk/server/static/assets/{dist-CFzsn6BG.js → dist-BX_-FENW.js} +1 -1
- ksadk/server/static/assets/{dist-B3FR1SKK.js → dist-CD4L6ymH.js} +1 -1
- ksadk/server/static/assets/{dist-Cf125P_m.js → dist-CHpW1BHj.js} +1 -1
- ksadk/server/static/assets/{dist-DVCOWtha.js → dist-CVPau3tn.js} +1 -1
- ksadk/server/static/assets/{dist-DFD6Qa6T.js → dist-C_qdxcSH.js} +1 -1
- ksadk/server/static/assets/{dist-BIr4DSRq.js → dist-Co68Apq4.js} +1 -1
- ksadk/server/static/assets/{dist-DiixqL0J.js → dist-Cp2PaOMY.js} +1 -1
- ksadk/server/static/assets/{dist-fBO2v5Kt.js → dist-CuR5Bgme.js} +1 -1
- ksadk/server/static/assets/{dist-DoVSwoDb.js → dist-DDSyLEOX.js} +1 -1
- ksadk/server/static/assets/{dist-C5_ZAZsG.js → dist-DUxO0R99.js} +1 -1
- ksadk/server/static/assets/{dist-C1NMAY5a.js → dist-QzbGrED_.js} +1 -1
- ksadk/server/static/assets/dist-bupkyEBZ.js +1 -0
- ksadk/server/static/assets/{dist-DvFK7p5S.js → dist-cxTGfdqx.js} +1 -1
- ksadk/server/static/assets/{dist-CB9iJrvg.js → dist-hL5p1til.js} +1 -1
- ksadk/server/static/assets/{dist-btbmmX5O.js → dist-lOy23y43.js} +1 -1
- ksadk/server/static/assets/{dist-QfkEHOlb.js → dist-pq-nD33R.js} +1 -1
- ksadk/server/static/assets/{ebnfDiagram-PWID7BFC-Ci8NqqZu.js → ebnfDiagram-PWID7BFC-BS5LdNoR.js} +1 -1
- ksadk/server/static/assets/{erDiagram-SSCWMZ5O-CCIOhLZG.js → erDiagram-SSCWMZ5O-Bv1QtiY-.js} +1 -1
- ksadk/server/static/assets/eventmodeling-NTZA5JFV-DsM4upQX.js +1 -0
- ksadk/server/static/assets/flowDiagram-A5DVABFB-D5NA16k9.js +1 -0
- ksadk/server/static/assets/{ganttDiagram-EL5Y4UJY-Cp_r9Hb6.js → ganttDiagram-EL5Y4UJY-musi-e0G.js} +1 -1
- ksadk/server/static/assets/gitGraph-4MIJSDKK-DUCVz-ih.js +1 -0
- ksadk/server/static/assets/{gitGraphDiagram-WWUBYQGX-Dlhc8Wr8.js → gitGraphDiagram-WWUBYQGX-DH37EGkG.js} +1 -1
- ksadk/server/static/assets/index-CZdkAvsv.js +244 -0
- ksadk/server/static/assets/index-CvXdHgF3.css +2 -0
- ksadk/server/static/assets/info-A6RAGUB7-rw0ZNHZp.js +1 -0
- ksadk/server/static/assets/{infoDiagram-RXCK75RN-CO0rRTRA.js → infoDiagram-RXCK75RN-C1kEtv2y.js} +1 -1
- ksadk/server/static/assets/{ishikawaDiagram-5VMMS53U-CHiaedSS.js → ishikawaDiagram-5VMMS53U-BCNPyMka.js} +1 -1
- ksadk/server/static/assets/{journeyDiagram-EYS64GPL-CHcCIB09.js → journeyDiagram-EYS64GPL--cDbKnjP.js} +1 -1
- ksadk/server/static/assets/{kanban-definition-3QL26DDD-CJ_ebBZf.js → kanban-definition-3QL26DDD-R1rAVw2f.js} +1 -1
- ksadk/server/static/assets/{katex-B4weu383.js → katex-BT-X-V7U.js} +1 -1
- ksadk/server/static/assets/{linear-V-MgYHW1.js → linear-DTR631iG.js} +1 -1
- ksadk/server/static/assets/{mermaid-parser.core-CBijEX_c.js → mermaid-parser.core-DfFzJhX8.js} +2 -2
- ksadk/server/static/assets/{mindmap-definition-FBJOCRG2-Bc-pQvpp.js → mindmap-definition-FBJOCRG2-D4by_rmk.js} +1 -1
- ksadk/server/static/assets/packet-AYTQ26CC-Ca4Hvki9.js +1 -0
- ksadk/server/static/assets/{pegDiagram-XKGWAZYB-D7genGLl.js → pegDiagram-XKGWAZYB-xWXPEh0c.js} +1 -1
- ksadk/server/static/assets/pie-WAS4IAKB-hwiz6fbw.js +1 -0
- ksadk/server/static/assets/{pieDiagram-E7YTZNPT-Bxj32zwD.js → pieDiagram-E7YTZNPT-BudBDlCI.js} +1 -1
- ksadk/server/static/assets/{quadrantDiagram-AXDQQJYC-BURv2mGh.js → quadrantDiagram-AXDQQJYC-DXZ0PCJF.js} +1 -1
- ksadk/server/static/assets/radar-RG4KPBEZ-BR1oZXLM.js +1 -0
- ksadk/server/static/assets/railroad-74A4TZTK-DfgEISfX.js +1 -0
- ksadk/server/static/assets/railroad-abnf-HS5TGJTU-CWOC3rdk.js +1 -0
- ksadk/server/static/assets/railroad-ebnf-LZEXJU2U-CiRvHCLY.js +1 -0
- ksadk/server/static/assets/railroad-peg-WCYAUIDC-DSDDyJ2f.js +1 -0
- ksadk/server/static/assets/{railroadDiagram-O6MQD6OU-CCsh3avW.js → railroadDiagram-O6MQD6OU-BdAYRYB8.js} +1 -1
- ksadk/server/static/assets/{requirementDiagram-EFPCY7ZU-_FRRBKEd.js → requirementDiagram-EFPCY7ZU-CBBmaL70.js} +1 -1
- ksadk/server/static/assets/{sankeyDiagram-P5KCCOFB-C-gr2o9M.js → sankeyDiagram-P5KCCOFB-Doc3rdwp.js} +1 -1
- ksadk/server/static/assets/{sequenceDiagram-WJ2MYXX4-D97NmfKg.js → sequenceDiagram-WJ2MYXX4-0J8R8hWW.js} +1 -1
- ksadk/server/static/assets/{sizeCapture-X5ZJPWSS-DjrPC5FX.js → sizeCapture-X5ZJPWSS-CfFLlWsK.js} +1 -1
- ksadk/server/static/assets/{stateDiagram-HBIQ2CUA-DzMNg1hh.js → stateDiagram-HBIQ2CUA-jBwkjtTy.js} +1 -1
- ksadk/server/static/assets/stateDiagram-v2-4QOOHH4V-Cw1fPb5w.js +1 -0
- ksadk/server/static/assets/{swimlanes-XN3QIQJK-Cssf_CsU.js → swimlanes-XN3QIQJK-B0WxTQf8.js} +1 -1
- ksadk/server/static/assets/swimlanesDiagram-VK2B7HYN-Cc3JMBAF.js +8 -0
- ksadk/server/static/assets/{timeline-definition-24CTP7MA-BWTHzyS1.js → timeline-definition-24CTP7MA-BfCT_75A.js} +1 -1
- ksadk/server/static/assets/treeView-Q6P3EWNA-C05SJHxo.js +1 -0
- ksadk/server/static/assets/treemap-WGGIJYW6-BqNLAhc3.js +1 -0
- ksadk/server/static/assets/{vennDiagram-4TSXK5OY-BSKgJsmR.js → vennDiagram-4TSXK5OY-9gX1VMDC.js} +1 -1
- ksadk/server/static/assets/wardley-WFR3VGLG-DokNktqB.js +1 -0
- ksadk/server/static/assets/{wardleyDiagram-VM6X3IG4-eflHNoaZ.js → wardleyDiagram-VM6X3IG4-sEs_BP6O.js} +1 -1
- ksadk/server/static/assets/{xychartDiagram-S5SC5T6Z-eYqrQ-v4.js → xychartDiagram-S5SC5T6Z-Ll4jvUN9.js} +1 -1
- ksadk/server/static/index.html +2 -2
- ksadk/server/terminal_sessions.py +34 -2
- ksadk/sessions/__init__.py +8 -1
- ksadk/sessions/_checkpoint_resume_audit.py +44 -0
- ksadk/sessions/_in_memory_query.py +112 -0
- ksadk/sessions/_local_service_sync.py +157 -156
- ksadk/sessions/_local_state_sync.py +152 -0
- ksadk/sessions/_local_tables.py +2 -0
- ksadk/sessions/_postgres_checkpoint_read.py +323 -0
- ksadk/sessions/_postgres_checkpoint_stats.py +330 -0
- ksadk/sessions/_postgres_history_read.py +678 -0
- ksadk/sessions/_postgres_schema.py +44 -2
- ksadk/sessions/_postgres_tables.py +2 -0
- ksadk/sessions/_postgres_tool_receipts.py +169 -0
- ksadk/sessions/_resilient_read.py +630 -0
- ksadk/sessions/_tool_receipt_sync.py +119 -0
- ksadk/sessions/agent_identity.py +16 -0
- ksadk/sessions/base.py +278 -0
- ksadk/sessions/db_budget.py +332 -0
- ksadk/sessions/errors.py +12 -0
- ksadk/sessions/history_budget.py +36 -0
- ksadk/sessions/history_identity.py +27 -0
- ksadk/sessions/in_memory.py +376 -113
- ksadk/sessions/invocation_identity.py +235 -0
- ksadk/sessions/local_service.py +345 -0
- ksadk/sessions/postgres_service.py +515 -549
- ksadk/sessions/resilience.py +21 -14
- ksadk/sessions/resilient.py +611 -504
- ksadk/skills/__init__.py +26 -0
- ksadk/skills/events.py +464 -0
- ksadk/skills/loader.py +44 -2
- ksadk/skills/manifest_cache.py +263 -0
- ksadk/skills/mcp_server/__init__.py +0 -0
- ksadk/skills/mcp_server/_registry.py +33 -0
- ksadk/skills/mcp_server/_routing.py +26 -0
- ksadk/skills/mcp_server/_workspace_files.py +160 -0
- ksadk/skills/mcp_server/register.py +415 -0
- ksadk/skills/mcp_server/server.py +218 -0
- ksadk/skills/models.py +11 -0
- ksadk/skills/observability.py +132 -0
- ksadk/skills/package_store.py +75 -2
- ksadk/skills/runtime/agent.py +38 -5
- ksadk/skills/runtime/artifacts.py +87 -0
- ksadk/skills/runtime/backends/e2b.py +400 -56
- ksadk/skills/runtime/backends/local.py +621 -119
- ksadk/skills/runtime/base.py +78 -7
- ksadk/skills/runtime/executor.py +266 -1
- ksadk/skills/runtime/loader.py +108 -3
- ksadk/skills/runtime/request.py +18 -0
- ksadk/skills/service_client.py +6 -1
- ksadk/skills/tool_defs.py +108 -3
- ksadk/studio/a2a_bindings.py +407 -0
- ksadk/studio/a2a_orchestration.py +178 -0
- ksadk/studio/active_run_output.py +92 -0
- ksadk/studio/activity_records.py +542 -0
- ksadk/studio/agent_configuration.py +173 -0
- ksadk/studio/api.py +784 -419
- ksadk/studio/api_a2a_routes.py +93 -0
- ksadk/studio/api_catalog_routes.py +13 -0
- ksadk/studio/api_cloud_chat_routes.py +382 -0
- ksadk/studio/api_contracts.py +31 -2
- ksadk/studio/api_plugin_routes.py +39 -12
- ksadk/studio/api_resource_connections.py +79 -41
- ksadk/studio/attachment_store.py +14 -2
- ksadk/studio/authoring.py +12 -6
- ksadk/studio/authoring_coordinator.py +4 -2
- ksadk/studio/build_resolution.py +117 -0
- ksadk/studio/build_singleflight.py +37 -0
- ksadk/studio/builder.py +32 -2
- ksadk/studio/capabilities.py +31 -9
- ksadk/studio/channel_connections.py +333 -0
- ksadk/studio/cloud.py +113 -387
- ksadk/studio/cloud_gateways.py +424 -0
- ksadk/studio/cloud_shared_web.py +82 -2
- ksadk/studio/codex_agent_service.py +19 -2
- ksadk/studio/codex_builder.py +1 -1
- ksadk/studio/codex_manifest.py +5 -1
- ksadk/studio/codex_provider_build.py +65 -0
- ksadk/studio/codex_run.py +6 -1
- ksadk/studio/compiler.py +112 -6
- ksadk/studio/configuration.py +182 -0
- ksadk/studio/contract_base.py +19 -0
- ksadk/studio/contracts.py +260 -202
- ksadk/studio/dsh_application.py +183 -27
- ksadk/studio/dsh_capability_service.py +302 -189
- ksadk/studio/dsh_lifecycle.py +58 -0
- ksadk/studio/dsh_mcp_transport.py +191 -0
- ksadk/studio/dsh_provider_registration.py +55 -16
- ksadk/studio/entry.py +53 -0
- ksadk/studio/event_store.py +53 -5
- ksadk/studio/execution_host.py +598 -0
- ksadk/studio/framework_run.py +50 -10
- ksadk/studio/hosted_kernel.py +1 -1
- ksadk/studio/interaction_submission.py +265 -0
- ksadk/studio/kernel_registry.py +429 -0
- ksadk/studio/kernel_sqlite_migration.py +181 -0
- ksadk/studio/lifecycle_status.py +43 -0
- ksadk/studio/model_buffered_wire.py +227 -0
- ksadk/studio/model_chat_tools.py +143 -0
- ksadk/studio/model_client.py +1939 -345
- ksadk/studio/model_content_stream.py +129 -0
- ksadk/studio/model_credentials.py +196 -0
- ksadk/studio/model_profile_service.py +89 -40
- ksadk/studio/model_request_projection.py +284 -0
- ksadk/studio/model_responses_content.py +296 -0
- ksadk/studio/model_usage.py +109 -0
- ksadk/studio/model_wire_failure.py +110 -0
- ksadk/studio/model_wire_identity.py +138 -0
- ksadk/studio/model_wire_snapshot.py +45 -0
- ksadk/studio/model_wire_tools.py +283 -0
- ksadk/studio/native_acceptance.py +68 -0
- ksadk/studio/native_approval.py +111 -0
- ksadk/studio/native_browser_port.py +861 -0
- ksadk/studio/native_child_mcp.py +87 -0
- ksadk/studio/native_child_publication.py +68 -0
- ksadk/studio/native_child_skills.py +72 -0
- ksadk/studio/native_child_workspace.py +176 -0
- ksadk/studio/native_command_policy.py +53 -0
- ksadk/studio/native_context_port.py +326 -0
- ksadk/studio/native_context_registration.py +54 -0
- ksadk/studio/native_document_input.py +88 -0
- ksadk/studio/native_documents.py +172 -0
- ksadk/studio/native_final_shape.py +852 -0
- ksadk/studio/native_gateway_stream.py +69 -0
- ksadk/studio/native_hook_port.py +145 -0
- ksadk/studio/native_hook_registration.py +70 -0
- ksadk/studio/native_inventory_disclosure.py +223 -0
- ksadk/studio/native_kernel_admission.py +84 -0
- ksadk/studio/native_language_diagnostics.py +320 -0
- ksadk/studio/native_mcp_disclosure.py +198 -0
- ksadk/studio/native_mcp_tool_port.py +219 -0
- ksadk/studio/native_memory_acceptance.py +362 -0
- ksadk/studio/native_memory_context.py +266 -0
- ksadk/studio/native_memory_flush.py +174 -0
- ksadk/studio/native_memory_sources.py +80 -0
- ksadk/studio/native_memory_tool_port.py +360 -0
- ksadk/studio/native_memory_turn.py +183 -0
- ksadk/studio/native_model_port.py +765 -0
- ksadk/studio/native_model_recovery.py +126 -0
- ksadk/studio/native_options.py +75 -0
- ksadk/studio/native_output_fields.py +58 -0
- ksadk/studio/native_planning.py +156 -0
- ksadk/studio/native_product.py +988 -0
- ksadk/studio/native_read_budget.py +426 -0
- ksadk/studio/native_recovery.py +171 -0
- ksadk/studio/native_scope.py +35 -0
- ksadk/studio/native_session_context_port.py +141 -0
- ksadk/studio/native_session_engine.py +14 -0
- ksadk/studio/native_skill_source.py +74 -0
- ksadk/studio/native_subagent_port.py +700 -0
- ksadk/studio/native_terminal_recovery.py +95 -0
- ksadk/studio/native_test_action.py +610 -0
- ksadk/studio/native_tool_port.py +477 -0
- ksadk/studio/native_user_input.py +60 -0
- ksadk/studio/native_verification_presentation.py +65 -0
- ksadk/studio/native_workspace_diagnostics.py +183 -0
- ksadk/studio/native_workspace_port.py +43 -0
- ksadk/studio/operations.py +34 -9
- ksadk/studio/plugin_composition.py +39 -12
- ksadk/studio/plugin_kernel_adapter.py +89 -0
- ksadk/studio/plugin_lifecycle.py +80 -0
- ksadk/studio/plugin_native_activation.py +163 -0
- ksadk/studio/plugin_runtime.py +832 -99
- ksadk/studio/plugin_runtime_admission.py +57 -0
- ksadk/studio/presentation.py +92 -0
- ksadk/studio/provider_recovery.py +59 -0
- ksadk/studio/public_output_store.py +69 -0
- ksadk/studio/recovery_page.py +70 -0
- ksadk/studio/resource_authority.py +69 -34
- ksadk/studio/resource_catalog.py +14 -12
- ksadk/studio/run_activity.py +848 -0
- ksadk/studio/run_controls.py +185 -0
- ksadk/studio/run_documents.py +127 -0
- ksadk/studio/run_service.py +1220 -335
- ksadk/studio/run_submission_receipts.py +68 -0
- ksadk/studio/runtime_catalog.py +73 -11
- ksadk/studio/runtime_prewarm.py +22 -0
- ksadk/studio/runtime_source.py +1 -1
- ksadk/studio/scheduler_assistant.py +4 -1
- ksadk/studio/scheduler_runtime.py +32 -289
- ksadk/studio/service.py +615 -246
- ksadk/studio/service_settings.py +229 -0
- ksadk/studio/shared_web.py +518 -181
- ksadk/studio/shared_web_response_events.py +180 -0
- ksadk/studio/shared_web_run_state.py +133 -0
- ksadk/studio/skill_discovery.py +305 -3
- ksadk/studio/static/assets/ChannelsPage-xX5HlMId.js +8 -0
- ksadk/studio/static/assets/CodeBlock-DMIf4h33-CkufcPYo.js +44 -0
- ksadk/studio/static/assets/ExecutionTree-v3HexvPo-Bk8wzGSy.js +1 -0
- ksadk/studio/static/assets/MathMessageMarkdown-BesSeCYl-DYG1Wzbx.js +8 -0
- ksadk/studio/static/assets/MermaidBlock-H_0qzQDf-BdXtxug_.js +11 -0
- ksadk/studio/static/assets/MessageMarkdown-CwMTvgFj-BeyLyQHu.js +59 -0
- ksadk/studio/static/assets/PrismRenderer-5pK6tUdb.js +3 -0
- ksadk/studio/static/assets/TeamsPage-CCaaGaVp.js +3 -0
- ksadk/studio/static/assets/abnfDiagram-VCTEODGH-Bnb1O3tA.js +1 -0
- ksadk/studio/static/assets/architecture-7GRP2DOG-BMOPAkUC.js +1 -0
- ksadk/studio/static/assets/architectureDiagram-5GKGNRK7-5Zn1gqJv.js +36 -0
- ksadk/studio/static/assets/{blockDiagram-I7D4REHJ-CFmPl1de.js → blockDiagram-I7D4REHJ-CLB4L11u.js} +6 -6
- ksadk/studio/static/assets/{c4Diagram-7LVT6UL2-BRrGu8qt.js → c4Diagram-7LVT6UL2-BOma_Z_F.js} +7 -7
- ksadk/studio/static/assets/channel-r8itPEik.js +1 -0
- ksadk/studio/static/assets/chunk-2E4U76K2-BFf_huql.js +2 -0
- ksadk/studio/static/assets/chunk-2ZTRR5NV-C2qZJila.js +2 -0
- ksadk/studio/static/assets/chunk-3Z5EZCMW-DMniOlPd.js +1 -0
- ksadk/studio/static/assets/{chunk-4HAMMTFA-D220vUtq.js → chunk-4HAMMTFA-DVtDP4rm.js} +7 -7
- ksadk/studio/static/assets/chunk-5V3GS4D5-i-ZDOEnP.js +1 -0
- ksadk/studio/static/assets/chunk-6AZGARVD-BB6FqMl-.js +1 -0
- ksadk/studio/static/assets/chunk-6EIED4P4-DdUJkP0f.js +1 -0
- ksadk/studio/static/assets/chunk-6K3QC6MW-CqVsVn-y.js +1 -0
- ksadk/studio/static/assets/chunk-6TQVIW2G-DKlLbNIP.js +1 -0
- ksadk/studio/static/assets/chunk-747NJXEK-BFkZPlab.js +2 -0
- ksadk/studio/static/assets/chunk-75Z2AOVW-BZNhM4vB.js +2 -0
- ksadk/studio/static/assets/chunk-CLGD4ZFX-D-GTtyKs.js +1 -0
- ksadk/studio/static/assets/{chunk-DU6HZSFF-C4DtVpCu.js → chunk-DU6HZSFF-CpEZCUgg.js} +1 -1
- ksadk/studio/static/assets/chunk-F27PBJKO-D7pvKf0C.js +1 -0
- ksadk/studio/static/assets/{chunk-GMAD6QVW-DiQA-u2N.js → chunk-GMAD6QVW-DE_8H717.js} +6 -6
- ksadk/studio/static/assets/chunk-GVQU2GXP-BfEB0lNv.js +1 -0
- ksadk/studio/static/assets/chunk-I5DQTOEV-Hm2LfiYI.js +1 -0
- ksadk/studio/static/assets/chunk-ICYGCRZG-749o-pGJ.js +1 -0
- ksadk/studio/static/assets/chunk-IH6LHLGP-CC6I9F3i.js +1 -0
- ksadk/studio/static/assets/{chunk-IMKFNOWR-BSlbjT_b.js → chunk-IMKFNOWR-D38axYOR.js} +5 -5
- ksadk/studio/static/assets/chunk-KI3K4JFJ-Rma-0k_M.js +1 -0
- ksadk/studio/static/assets/chunk-L3NEJ4N5-Dq5xn7aL.js +1 -0
- ksadk/studio/static/assets/chunk-LNGE3PJU-DWpGwHrW.js +34 -0
- ksadk/studio/static/assets/{chunk-OSK3NFVY-M2m6G3j4.js → chunk-OSK3NFVY-DiCQjx9b.js} +5 -5
- ksadk/studio/static/assets/chunk-OUJLGHUK-D0j2JRSg.js +2 -0
- ksadk/studio/static/assets/{chunk-P2QGCYS3-DezaQxiK.js → chunk-P2QGCYS3-VdhKmfYq.js} +1 -1
- ksadk/studio/static/assets/chunk-POPQ4Y6H-C1_rzO5M.js +1 -0
- ksadk/studio/static/assets/chunk-PWAF6VOD-B45HvflI.js +1 -0
- ksadk/studio/static/assets/{chunk-SHT3W25Y-DAyIVp5H.js → chunk-SHT3W25Y-DsCFnRVE.js} +9 -9
- ksadk/studio/static/assets/{chunk-SVP7TREG-DulomOrS.js → chunk-SVP7TREG-DljApgRX.js} +1 -1
- ksadk/studio/static/assets/{chunk-TICWLB2K-bHJYoflj.js → chunk-TICWLB2K-DWqRtyqa.js} +6 -6
- ksadk/studio/static/assets/chunk-TLUHSLCS-DUeGgnD5.js +2 -0
- ksadk/studio/static/assets/chunk-UY3FDG6J-CnmaAkG5.js +1 -0
- ksadk/studio/static/assets/chunk-XHIXRSVI-BFQ6B8BE.js +1 -0
- ksadk/studio/static/assets/chunk-XXDRQBXY-DqAYeljN.js +1 -0
- ksadk/studio/static/assets/classDiagram-ZZMXUADV-DjeMNJmu.js +1 -0
- ksadk/studio/static/assets/classDiagram-v2-VYDZK3BY-DjeMNJmu.js +1 -0
- ksadk/studio/static/assets/clsx-DB0hHKMi.js +1 -0
- ksadk/studio/static/assets/cose-bilkent-JH36ORCC-om8AY0Mc.js +1 -0
- ksadk/studio/static/assets/createLucideIcon-DR0LGTP5.js +1 -0
- ksadk/studio/static/assets/cynefin-OW5HDTMX-7tP7QfM3.js +1 -0
- ksadk/studio/static/assets/cynefinDiagram-5FMLGOSQ-6BrmK52S.js +62 -0
- ksadk/studio/static/assets/dagre-GXQ25YYZ-buZBRlwz.js +4 -0
- ksadk/studio/static/assets/{diagram-S7CK7UJ4-0BZ98mya.js → diagram-S7CK7UJ4-C6aH78c4.js} +3 -3
- ksadk/studio/static/assets/diagram-UQ7AKVKN-DY_tQ6C_.js +41 -0
- ksadk/studio/static/assets/diagram-VSXAHHWV-DX9p5cQT.js +3 -0
- ksadk/studio/static/assets/diagram-VX7I27RA-DB2WSH8X.js +24 -0
- ksadk/studio/static/assets/diagram-Z3DM3KII-Ce1BJwHE.js +24 -0
- ksadk/studio/static/assets/ebnfDiagram-PWID7BFC-Daukxwqf.js +1 -0
- ksadk/studio/static/assets/{erDiagram-RLTQ6QDP-DLGry2Ap.js → erDiagram-RLTQ6QDP-CGthTMmJ.js} +6 -6
- ksadk/studio/static/assets/eventmodeling-NTZA5JFV-BR2FzK4R.js +1 -0
- ksadk/studio/static/assets/flowDiagram-HODETNUW-CZ1tEenp.js +1 -0
- ksadk/studio/static/assets/ganttDiagram-EL5Y4UJY-BfoAZW9X.js +292 -0
- ksadk/studio/static/assets/gitGraph-4MIJSDKK-DYlXv_yJ.js +1 -0
- ksadk/studio/static/assets/gitGraphDiagram-WWUBYQGX-S985OIJF.js +106 -0
- ksadk/studio/static/assets/iconfont-4HN3C9Pg.woff2 +0 -0
- ksadk/studio/static/assets/index-C7DNDik2.css +2 -0
- ksadk/studio/static/assets/index-Cy68gTlH.js +265 -0
- ksadk/studio/static/assets/index.dom-BQenBtFm.js +1 -0
- ksadk/studio/static/assets/info-A6RAGUB7-BlU-8_xu.js +1 -0
- ksadk/studio/static/assets/infoDiagram-27XIBGKW-CO3W8tFn.js +2 -0
- ksadk/studio/static/assets/{ishikawaDiagram-5VMMS53U-CljI2wyf.js → ishikawaDiagram-5VMMS53U-BUGEl8cO.js} +2 -2
- ksadk/studio/static/assets/{journeyDiagram-3NMN7TZE-D50Fo2sL.js → journeyDiagram-3NMN7TZE-Ch2ZYxvr.js} +6 -6
- ksadk/studio/static/assets/{kanban-definition-UXKFOSKX-DimfOTam.js → kanban-definition-UXKFOSKX-Da-Fp4vC.js} +3 -3
- ksadk/studio/static/assets/kingsoft-cloud-BOcLiQ3e.ico +0 -0
- ksadk/studio/static/assets/{line-CX5BOOUP.js → line-BDaeq300.js} +1 -1
- ksadk/studio/static/assets/linear-DmucvK78.js +1 -0
- ksadk/studio/static/assets/mermaid-parser.core-Cj5mYdBi.js +4 -0
- ksadk/studio/static/assets/{mindmap-definition-YA3MSWOX-Bizzqy5R.js → mindmap-definition-YA3MSWOX-CvlsVQ38.js} +1 -1
- ksadk/studio/static/assets/packet-AYTQ26CC-BSJEH9Lb.js +1 -0
- ksadk/studio/static/assets/pegDiagram-XKGWAZYB-BuHuNgT5.js +1 -0
- ksadk/studio/static/assets/pie-WAS4IAKB-qxv01Y8W.js +1 -0
- ksadk/studio/static/assets/{pieDiagram-E7YTZNPT-B9mrFSDF.js → pieDiagram-E7YTZNPT-DlrWiSOv.js} +1 -1
- ksadk/studio/static/assets/preload-helper-CO68xz6u.js +1 -0
- ksadk/studio/static/assets/presentation-yYw7xK60-BmcZriri.js +1 -0
- ksadk/studio/static/assets/{quadrantDiagram-AXDQQJYC-NzUfCbMR.js → quadrantDiagram-AXDQQJYC-BA3hpUZM.js} +6 -6
- ksadk/studio/static/assets/radar-RG4KPBEZ-B6h6pWOs.js +1 -0
- ksadk/studio/static/assets/railroad-74A4TZTK-CGtTWdGc.js +1 -0
- ksadk/studio/static/assets/railroad-abnf-HS5TGJTU-Cq7y22IA.js +1 -0
- ksadk/studio/static/assets/railroad-ebnf-LZEXJU2U-V0aQVv9m.js +1 -0
- ksadk/studio/static/assets/railroad-peg-WCYAUIDC-BQiIsX_p.js +1 -0
- ksadk/studio/static/assets/railroadDiagram-O6MQD6OU-BxpAazym.js +1 -0
- ksadk/studio/static/assets/{requirementDiagram-BXWQKSXE-BF3d103U.js → requirementDiagram-BXWQKSXE-E-Ge0FcV.js} +1 -1
- ksadk/studio/static/assets/sankeyDiagram-P5KCCOFB-CA6YKhQ3.js +40 -0
- ksadk/studio/static/assets/{sequenceDiagram-WJ2MYXX4-Dh4wZtUm.js → sequenceDiagram-WJ2MYXX4-CcElXGg4.js} +9 -9
- ksadk/studio/static/assets/src-B6xuSHsQ.js +1 -0
- ksadk/studio/static/assets/stateDiagram-D77RDMKH-DdXZOFqY.js +1 -0
- ksadk/studio/static/assets/stateDiagram-v2-MP3YSRHH-CJbOM-QK.js +1 -0
- ksadk/studio/static/assets/swimlanes-42K2YHIH-NtgEEHLY.js +1 -0
- ksadk/studio/static/assets/swimlanesDiagram-VR7AAH4N-D-AVlW8B.js +8 -0
- ksadk/studio/static/assets/{timeline-definition-24CTP7MA-DxmSSjRB.js → timeline-definition-24CTP7MA-CIuYhNy3.js} +7 -7
- ksadk/studio/static/assets/treeView-Q6P3EWNA-BTTYcvrF.js +1 -0
- ksadk/studio/static/assets/treemap-WGGIJYW6-Cg7tyfH8.js +1 -0
- ksadk/studio/static/assets/vennDiagram-4TSXK5OY-7HbApbrv.js +34 -0
- ksadk/studio/static/assets/wardley-WFR3VGLG-C6N1rULY.js +1 -0
- ksadk/studio/static/assets/{wardleyDiagram-VM6X3IG4-Ba1AOWoe.js → wardleyDiagram-VM6X3IG4-CMJiaedy.js} +1 -1
- ksadk/studio/static/assets/{xychartDiagram-S5SC5T6Z-Cr5pt5Y-.js → xychartDiagram-S5SC5T6Z-BdgtMvW2.js} +6 -6
- ksadk/studio/static/index.html +8 -2
- ksadk/studio/teams_catalog.py +166 -0
- ksadk/studio/teams_installation.py +217 -0
- ksadk/studio/teams_node.py +549 -0
- ksadk/studio/teams_node_factory.py +558 -0
- ksadk/studio/teams_node_runner.py +72 -0
- ksadk/studio/teams_node_v1.py +935 -0
- ksadk/studio/teams_remote.py +496 -0
- ksadk/studio/templates.py +41 -19
- ksadk/studio/validator.py +13 -0
- ksadk/studio/workspace.py +19 -4
- ksadk/studio/workspace_plugins.py +138 -0
- ksadk/studio/workspace_registry.py +286 -0
- ksadk/tools/a2a_policy.py +5 -0
- ksadk/tools/artifact_observation.py +53 -0
- ksadk/tools/captured_source_artifact.py +68 -0
- ksadk/tools/schema.py +34 -0
- ksadk/toolsets/__init__.py +93 -88
- ksadk/toolsets/a2a.py +89 -89
- ksadk/toolsets/sandbox.py +377 -6
- ksadk/toolsets/skill_management.py +315 -0
- ksadk/toolsets/skills.py +446 -378
- ksadk/toolsets/tool_selection.py +94 -0
- ksadk/toolsets/workspace.py +344 -326
- ksadk/toolsets/workspace_editing.py +291 -0
- ksadk/toolsets/workspace_identity.py +15 -0
- ksadk/toolsets/workspace_model_observation.py +104 -0
- ksadk/toolsets/workspace_mutation.py +75 -0
- ksadk/toolsets/workspace_read_budget.py +216 -0
- ksadk/toolsets/workspace_search.py +192 -0
- ksadk/toolsets/workspace_search_process.py +129 -0
- ksadk/toolsets/workspace_state.py +6 -0
- ksadk/version.py +1 -1
- ksadk_runtime_common/http_headers.py +18 -0
- ksadk_runtime_common/memory_backend/providers/lancedb.py +56 -2
- ksadk_runtime_common/schemas/memory_backend_manifest.schema.json +148 -148
- ksadk_runtime_common/workspace_files/router.py +28 -14
- agentengine_sdk_python-0.8.4.dist-info/RECORD +0 -1070
- ksadk/server/static/assets/MathMessageMarkdown-DbdW5A4_.js +0 -8
- ksadk/server/static/assets/architecture-7GRP2DOG-BW5UtSnx.js +0 -1
- ksadk/server/static/assets/channel-CF5Up3hQ.js +0 -1
- ksadk/server/static/assets/chunk-2Q5K7J3B-KkXX47WI.js +0 -1
- ksadk/server/static/assets/classDiagram-DTDB5LWJ-Cz81acRQ.js +0 -1
- ksadk/server/static/assets/classDiagram-v2-JRS7N3AN-Cz81acRQ.js +0 -1
- ksadk/server/static/assets/cynefin-OW5HDTMX-DVWs8a2t.js +0 -1
- ksadk/server/static/assets/dist-B2_CVgKv.js +0 -1
- ksadk/server/static/assets/eventmodeling-NTZA5JFV-CQqR2hg3.js +0 -1
- ksadk/server/static/assets/flowDiagram-A5DVABFB-DDRRbGPm.js +0 -1
- ksadk/server/static/assets/gitGraph-4MIJSDKK-fgWEf7UD.js +0 -1
- ksadk/server/static/assets/index-DcTML1Up.css +0 -2
- ksadk/server/static/assets/index-Dh2XHqPK.js +0 -244
- ksadk/server/static/assets/info-A6RAGUB7-BUecLTdt.js +0 -1
- ksadk/server/static/assets/packet-AYTQ26CC-BeW-btFv.js +0 -1
- ksadk/server/static/assets/pie-WAS4IAKB-X0xh4SaT.js +0 -1
- ksadk/server/static/assets/radar-RG4KPBEZ-DzRMSqjd.js +0 -1
- ksadk/server/static/assets/railroad-74A4TZTK-Cc44icX-.js +0 -1
- ksadk/server/static/assets/railroad-abnf-HS5TGJTU-D6S4BdV-.js +0 -1
- ksadk/server/static/assets/railroad-ebnf-LZEXJU2U-vD3aVE2o.js +0 -1
- ksadk/server/static/assets/railroad-peg-WCYAUIDC-CYbW_b4T.js +0 -1
- ksadk/server/static/assets/stateDiagram-v2-4QOOHH4V-BIcjKFhF.js +0 -1
- ksadk/server/static/assets/swimlanesDiagram-VK2B7HYN-tq3K3Ybl.js +0 -8
- ksadk/server/static/assets/treeView-Q6P3EWNA-DBXt3GdU.js +0 -1
- ksadk/server/static/assets/treemap-WGGIJYW6-DrCy4E_l.js +0 -1
- ksadk/server/static/assets/wardley-WFR3VGLG-CefhOliM.js +0 -1
- ksadk/studio/static/assets/CodeBlock-DCUUY0PL-BLjA7kbS.js +0 -41
- ksadk/studio/static/assets/MathMessageMarkdown-CBcDrAw--CUYIXwgI.js +0 -8
- ksadk/studio/static/assets/MermaidBlock-DBFTztfQ-BTYKWEbD.js +0 -44
- ksadk/studio/static/assets/PrismRenderer-wiXRHURw.js +0 -3
- ksadk/studio/static/assets/abnfDiagram-VCTEODGH-CLETGjKq.js +0 -1
- ksadk/studio/static/assets/architecture-7GRP2DOG-hXMiO_AU.js +0 -1
- ksadk/studio/static/assets/architectureDiagram-5GKGNRK7-B5EQysk6.js +0 -36
- ksadk/studio/static/assets/channel-BqO-gtEw.js +0 -1
- ksadk/studio/static/assets/chunk-75Z2AOVW-C8lLv_qc.js +0 -2
- ksadk/studio/static/assets/chunk-F27PBJKO-Cpw14SNG.js +0 -1
- ksadk/studio/static/assets/chunk-GVQU2GXP-DUdNBUCi.js +0 -1
- ksadk/studio/static/assets/chunk-L3NEJ4N5-Db8Ab22W.js +0 -1
- ksadk/studio/static/assets/chunk-POPQ4Y6H-DOpufJ3t.js +0 -1
- ksadk/studio/static/assets/chunk-PWAF6VOD-CfLb1gSc.js +0 -1
- ksadk/studio/static/assets/chunk-XXDRQBXY-7PcdR2B1.js +0 -1
- ksadk/studio/static/assets/classDiagram-ZZMXUADV-D_bW8JjA.js +0 -1
- ksadk/studio/static/assets/classDiagram-v2-VYDZK3BY-D_bW8JjA.js +0 -1
- ksadk/studio/static/assets/cose-bilkent-JH36ORCC-snL88wkX.js +0 -1
- ksadk/studio/static/assets/cynefin-OW5HDTMX-Bd1YhRo1.js +0 -1
- ksadk/studio/static/assets/cynefinDiagram-5FMLGOSQ-BBrIG_mI.js +0 -62
- ksadk/studio/static/assets/dagre-GXQ25YYZ-DtF1nGdY.js +0 -4
- ksadk/studio/static/assets/diagram-UQ7AKVKN-6mLKEo6L.js +0 -41
- ksadk/studio/static/assets/diagram-VSXAHHWV-CJBIaiZ2.js +0 -3
- ksadk/studio/static/assets/diagram-VX7I27RA-BohLEE1C.js +0 -24
- ksadk/studio/static/assets/diagram-Z3DM3KII-D8KIGonG.js +0 -24
- ksadk/studio/static/assets/ebnfDiagram-PWID7BFC-C99HU61t.js +0 -1
- ksadk/studio/static/assets/eventmodeling-NTZA5JFV-B1_5Ac8j.js +0 -1
- ksadk/studio/static/assets/flowDiagram-HODETNUW-DD5hmicn.js +0 -1
- ksadk/studio/static/assets/ganttDiagram-EL5Y4UJY-BPJrVLSG.js +0 -292
- ksadk/studio/static/assets/gitGraph-4MIJSDKK-Cy_ZQBGi.js +0 -1
- ksadk/studio/static/assets/gitGraphDiagram-WWUBYQGX-CZCUz4MT.js +0 -106
- ksadk/studio/static/assets/index-CeHL9ARV.css +0 -2
- ksadk/studio/static/assets/index-D9QEcVpL.js +0 -320
- ksadk/studio/static/assets/info-A6RAGUB7-DBzDQB_I.js +0 -1
- ksadk/studio/static/assets/infoDiagram-27XIBGKW-B-sq07Hi.js +0 -2
- ksadk/studio/static/assets/linear-BCxN9JLv.js +0 -1
- ksadk/studio/static/assets/mermaid-parser.core-BdCz8fkS.js +0 -7
- ksadk/studio/static/assets/packet-AYTQ26CC-gPln-_kG.js +0 -1
- ksadk/studio/static/assets/pegDiagram-XKGWAZYB-Dy3fB-gW.js +0 -1
- ksadk/studio/static/assets/pie-WAS4IAKB-qZdHMr7B.js +0 -1
- ksadk/studio/static/assets/radar-RG4KPBEZ-BZlnaea9.js +0 -1
- ksadk/studio/static/assets/railroad-74A4TZTK-Ce3__H9c.js +0 -1
- ksadk/studio/static/assets/railroad-abnf-HS5TGJTU-DqQn7EzD.js +0 -1
- ksadk/studio/static/assets/railroad-ebnf-LZEXJU2U-B55kCA8F.js +0 -1
- ksadk/studio/static/assets/railroad-peg-WCYAUIDC-DfQnvkHd.js +0 -1
- ksadk/studio/static/assets/railroadDiagram-O6MQD6OU-DnhMjZCk.js +0 -1
- ksadk/studio/static/assets/sankeyDiagram-P5KCCOFB-Bo-JTwt0.js +0 -40
- ksadk/studio/static/assets/src-SFn9St9H.js +0 -1
- ksadk/studio/static/assets/stateDiagram-D77RDMKH-DH774G6d.js +0 -1
- ksadk/studio/static/assets/stateDiagram-v2-MP3YSRHH-DZvVWPBo.js +0 -1
- ksadk/studio/static/assets/swimlanes-42K2YHIH-Bl13OvTX.js +0 -1
- ksadk/studio/static/assets/swimlanesDiagram-VR7AAH4N-BnFOTALJ.js +0 -8
- ksadk/studio/static/assets/treeView-Q6P3EWNA-D5Nn9Swz.js +0 -1
- ksadk/studio/static/assets/treemap-WGGIJYW6-CgHgnQhE.js +0 -1
- ksadk/studio/static/assets/vennDiagram-4TSXK5OY-B9QEXcJq.js +0 -34
- ksadk/studio/static/assets/wardley-WFR3VGLG-DXrK2RRY.js +0 -1
- {agentengine_sdk_python-0.8.4.dist-info → agentengine_sdk_python-0.8.6.dist-info}/WHEEL +0 -0
- {agentengine_sdk_python-0.8.4.dist-info → agentengine_sdk_python-0.8.6.dist-info}/entry_points.txt +0 -0
- {agentengine_sdk_python-0.8.4.dist-info → agentengine_sdk_python-0.8.6.dist-info}/licenses/LICENSE +0 -0
- {agentengine_sdk_python-0.8.4.dist-info → agentengine_sdk_python-0.8.6.dist-info}/top_level.txt +0 -0
- /ksadk/studio/static/assets/{MathMessageMarkdown-CBcDrAw--BEOyPC3w.css → MathMessageMarkdown-BesSeCYl-BEOyPC3w.css} +0 -0
|
@@ -0,0 +1,851 @@
|
|
|
1
|
+
"""Durable, conservative effect boundary for explicitly controlled Teams tools.
|
|
2
|
+
|
|
3
|
+
This is an injectable component, not capability advertisement or Host assembly.
|
|
4
|
+
The caller supplies real per-tool grant/policy validation and an authoritative
|
|
5
|
+
Server prepared ACK. Opaque shell tools are deliberately unsupported. Unknown
|
|
6
|
+
means do not replay; even an expired local claim never grants a second send.
|
|
7
|
+
"""
|
|
8
|
+
|
|
9
|
+
from __future__ import annotations
|
|
10
|
+
|
|
11
|
+
import asyncio
|
|
12
|
+
import json
|
|
13
|
+
import os
|
|
14
|
+
import re
|
|
15
|
+
import sqlite3
|
|
16
|
+
import threading
|
|
17
|
+
from contextlib import asynccontextmanager
|
|
18
|
+
from pathlib import Path
|
|
19
|
+
from typing import Any, Awaitable, Callable, Protocol
|
|
20
|
+
from uuid import uuid4
|
|
21
|
+
|
|
22
|
+
from ksadk.plugins.teams.cloud_contracts import (
|
|
23
|
+
canonical_bytes,
|
|
24
|
+
digest,
|
|
25
|
+
)
|
|
26
|
+
from ksadk.plugins.teams.effect_contracts import (
|
|
27
|
+
EffectOutcome as EffectOutcome,
|
|
28
|
+
)
|
|
29
|
+
from ksadk.plugins.teams.effect_contracts import (
|
|
30
|
+
EffectPreparedReceipt as EffectPreparedReceipt,
|
|
31
|
+
)
|
|
32
|
+
from ksadk.plugins.teams.effect_contracts import (
|
|
33
|
+
EffectRecord as EffectRecord,
|
|
34
|
+
)
|
|
35
|
+
from ksadk.plugins.teams.effect_contracts import (
|
|
36
|
+
EffectReportReceipt as EffectReportReceipt,
|
|
37
|
+
)
|
|
38
|
+
from ksadk.plugins.teams.effect_contracts import (
|
|
39
|
+
EffectRequest as EffectRequest,
|
|
40
|
+
)
|
|
41
|
+
from ksadk.plugins.teams.effect_contracts import (
|
|
42
|
+
effect_payload_digest as effect_payload_digest,
|
|
43
|
+
)
|
|
44
|
+
|
|
45
|
+
|
|
46
|
+
class EffectConflict(RuntimeError):
|
|
47
|
+
"""Safe error code; never includes raw tool arguments or transport errors."""
|
|
48
|
+
|
|
49
|
+
|
|
50
|
+
class EffectUncertain(EffectConflict):
|
|
51
|
+
pass
|
|
52
|
+
|
|
53
|
+
|
|
54
|
+
class EffectJournal(Protocol):
|
|
55
|
+
"""Native PostgreSQL adapters implement this port without SQLite wrapping."""
|
|
56
|
+
|
|
57
|
+
store_incarnation: str
|
|
58
|
+
journal_incarnation: str
|
|
59
|
+
|
|
60
|
+
async def record_invocation(self, request: EffectRequest) -> str: ...
|
|
61
|
+
async def get_invocation(self, request: EffectRequest) -> bool: ...
|
|
62
|
+
async def get(self, request: EffectRequest) -> EffectRecord | None: ...
|
|
63
|
+
async def prepare(self, request: EffectRequest) -> EffectRecord: ...
|
|
64
|
+
async def claim(self, request: EffectRequest, claim_id: str) -> EffectRecord | None: ...
|
|
65
|
+
async def settle(
|
|
66
|
+
self, request: EffectRequest, claim_id: str, outcome: EffectOutcome
|
|
67
|
+
) -> EffectRecord: ...
|
|
68
|
+
async def unresolved(self, *, limit: int = 100, after: str = "") -> list[EffectRecord]: ...
|
|
69
|
+
async def pending_reports(self, *, limit: int = 100) -> list[EffectRecord]: ...
|
|
70
|
+
async def for_execution(
|
|
71
|
+
self, context_ref: str, native_run_id: str, *, limit: int = 100, after: str = ""
|
|
72
|
+
) -> list[EffectRecord]: ...
|
|
73
|
+
async def acknowledge_report(
|
|
74
|
+
self, effect_key: str, revision: int, evidence_digest: str
|
|
75
|
+
) -> None: ...
|
|
76
|
+
|
|
77
|
+
|
|
78
|
+
class SQLiteEffectJournal:
|
|
79
|
+
"""Local Host journal; explicitly create once, fail closed on reopen loss.
|
|
80
|
+
|
|
81
|
+
Place beside the original Kernel's durable store. A separate journal UUID
|
|
82
|
+
prevents recreated/lost journals from matching an earlier Server ACK, even
|
|
83
|
+
if the caller accidentally initializes using the same Kernel incarnation.
|
|
84
|
+
This local adapter does not claim cross-host shared persistence.
|
|
85
|
+
"""
|
|
86
|
+
|
|
87
|
+
shared_across_hosts = False
|
|
88
|
+
|
|
89
|
+
def __init__(self, path: str | Path, *, store_incarnation: str, initialize: bool = False):
|
|
90
|
+
if not isinstance(store_incarnation, str) or not store_incarnation:
|
|
91
|
+
raise ValueError("store_incarnation_required")
|
|
92
|
+
self.path = Path(path)
|
|
93
|
+
self._lock = threading.RLock()
|
|
94
|
+
if initialize:
|
|
95
|
+
self.path.parent.mkdir(parents=True, exist_ok=True, mode=0o700)
|
|
96
|
+
descriptor = os.open(self.path, os.O_CREAT | os.O_WRONLY, 0o600)
|
|
97
|
+
os.close(descriptor)
|
|
98
|
+
if not self.path.is_file():
|
|
99
|
+
raise EffectConflict("effect_journal_unavailable")
|
|
100
|
+
self.connection = sqlite3.connect(
|
|
101
|
+
self.path.resolve().as_uri() + "?mode=rw",
|
|
102
|
+
uri=True,
|
|
103
|
+
check_same_thread=False,
|
|
104
|
+
timeout=10,
|
|
105
|
+
isolation_level=None,
|
|
106
|
+
)
|
|
107
|
+
self.connection.row_factory = sqlite3.Row
|
|
108
|
+
self.connection.execute("PRAGMA journal_mode=WAL")
|
|
109
|
+
self.connection.execute("PRAGMA synchronous=FULL")
|
|
110
|
+
self.connection.execute("PRAGMA foreign_keys=ON")
|
|
111
|
+
try:
|
|
112
|
+
if initialize:
|
|
113
|
+
self.connection.execute("BEGIN IMMEDIATE")
|
|
114
|
+
try:
|
|
115
|
+
self.connection.execute(
|
|
116
|
+
"CREATE TABLE IF NOT EXISTS teams_effect_invocations "
|
|
117
|
+
"(invocation_key TEXT PRIMARY KEY,invocation_digest TEXT NOT NULL)"
|
|
118
|
+
)
|
|
119
|
+
self.connection.execute(
|
|
120
|
+
"CREATE TABLE IF NOT EXISTS teams_effect_meta (id "
|
|
121
|
+
"INTEGER PRIMARY KEY CHECK(id=1),version INTEGER NOT "
|
|
122
|
+
"NULL,store_incarnation TEXT NOT "
|
|
123
|
+
"NULL,journal_incarnation TEXT NOT NULL)"
|
|
124
|
+
)
|
|
125
|
+
self.connection.execute(
|
|
126
|
+
"CREATE TABLE IF NOT EXISTS teams_effect_entries "
|
|
127
|
+
"(effect_key TEXT PRIMARY KEY,request_digest TEXT NOT "
|
|
128
|
+
"NULL,request_json TEXT NOT NULL,phase TEXT NOT "
|
|
129
|
+
"NULL,revision INTEGER NOT NULL,claim_id "
|
|
130
|
+
"TEXT,record_json TEXT NOT NULL)"
|
|
131
|
+
)
|
|
132
|
+
self.connection.execute(
|
|
133
|
+
"CREATE TABLE IF NOT EXISTS teams_effect_reports "
|
|
134
|
+
"(effect_key TEXT NOT NULL,revision INTEGER NOT "
|
|
135
|
+
"NULL,evidence_digest TEXT NOT NULL,record_json TEXT "
|
|
136
|
+
"NOT NULL,acknowledged INTEGER NOT NULL DEFAULT "
|
|
137
|
+
"0,PRIMARY KEY(effect_key,revision),FOREIGN "
|
|
138
|
+
"KEY(effect_key) REFERENCES "
|
|
139
|
+
"teams_effect_entries(effect_key))"
|
|
140
|
+
)
|
|
141
|
+
self.connection.execute(
|
|
142
|
+
"CREATE INDEX IF NOT EXISTS teams_effect_pending ON "
|
|
143
|
+
"teams_effect_reports(acknowledged,effect_key,revision)"
|
|
144
|
+
)
|
|
145
|
+
self.connection.execute(
|
|
146
|
+
"CREATE INDEX IF NOT EXISTS teams_effect_evidence_execution "
|
|
147
|
+
"ON teams_effect_reports("
|
|
148
|
+
"json_extract(record_json,'$.request.context_ref'),"
|
|
149
|
+
"json_extract(record_json,'$.request.native_run_id'),effect_key,revision)"
|
|
150
|
+
)
|
|
151
|
+
self.connection.execute(
|
|
152
|
+
"INSERT OR IGNORE INTO teams_effect_meta VALUES(1,1,?,?)",
|
|
153
|
+
(store_incarnation, "journal_" + uuid4().hex),
|
|
154
|
+
)
|
|
155
|
+
self.connection.execute("COMMIT")
|
|
156
|
+
except BaseException:
|
|
157
|
+
self.connection.execute("ROLLBACK")
|
|
158
|
+
raise
|
|
159
|
+
row = self.connection.execute("SELECT * FROM teams_effect_meta WHERE id=1").fetchone()
|
|
160
|
+
if row is None or row["version"] != 1 or row["store_incarnation"] != store_incarnation:
|
|
161
|
+
raise EffectConflict("effect_store_incarnation_mismatch")
|
|
162
|
+
self.store_incarnation, self.journal_incarnation = (
|
|
163
|
+
store_incarnation,
|
|
164
|
+
row["journal_incarnation"],
|
|
165
|
+
)
|
|
166
|
+
except BaseException:
|
|
167
|
+
self.connection.close()
|
|
168
|
+
raise
|
|
169
|
+
|
|
170
|
+
async def close(self):
|
|
171
|
+
await asyncio.to_thread(self._close)
|
|
172
|
+
|
|
173
|
+
def _close(self):
|
|
174
|
+
with self._lock:
|
|
175
|
+
self.connection.close()
|
|
176
|
+
|
|
177
|
+
def _request(self, request):
|
|
178
|
+
request = EffectRequest.model_validate(request.model_dump(mode="json"))
|
|
179
|
+
if (
|
|
180
|
+
request.store_incarnation != self.store_incarnation
|
|
181
|
+
or request.journal_incarnation != self.journal_incarnation
|
|
182
|
+
):
|
|
183
|
+
raise EffectConflict("effect_store_incarnation_mismatch")
|
|
184
|
+
if len(canonical_bytes(request.stable())) > 32768:
|
|
185
|
+
raise EffectConflict("effect_request_too_large")
|
|
186
|
+
return request
|
|
187
|
+
|
|
188
|
+
def _row(self, request):
|
|
189
|
+
row = self.connection.execute(
|
|
190
|
+
"SELECT * FROM teams_effect_entries WHERE effect_key=?", (request.effect_key,)
|
|
191
|
+
).fetchone()
|
|
192
|
+
if row and row["request_digest"] != request.request_digest:
|
|
193
|
+
raise EffectConflict("effect_payload_conflict")
|
|
194
|
+
return row
|
|
195
|
+
|
|
196
|
+
@staticmethod
|
|
197
|
+
def _record(row):
|
|
198
|
+
record = EffectRecord.model_validate_json(row["record_json"])
|
|
199
|
+
proof = {
|
|
200
|
+
"requestDigest": record.request.request_digest,
|
|
201
|
+
"phase": record.phase,
|
|
202
|
+
"revision": record.revision,
|
|
203
|
+
"outcome": record.outcome.model_dump(mode="json") if record.outcome else None,
|
|
204
|
+
}
|
|
205
|
+
if digest(proof) != record.evidence_digest:
|
|
206
|
+
raise EffectConflict("effect_evidence_corrupt")
|
|
207
|
+
for column, expected in (
|
|
208
|
+
("effect_key", record.request.effect_key),
|
|
209
|
+
("request_digest", record.request.request_digest),
|
|
210
|
+
("phase", record.phase),
|
|
211
|
+
("revision", record.revision),
|
|
212
|
+
("evidence_digest", record.evidence_digest),
|
|
213
|
+
):
|
|
214
|
+
if column in row.keys() and row[column] != expected:
|
|
215
|
+
raise EffectConflict("effect_evidence_corrupt")
|
|
216
|
+
return record
|
|
217
|
+
|
|
218
|
+
def _persist(self, request, phase, revision, *, claim_id=None, outcome=None):
|
|
219
|
+
proof = {
|
|
220
|
+
"requestDigest": request.request_digest,
|
|
221
|
+
"phase": phase,
|
|
222
|
+
"revision": revision,
|
|
223
|
+
"outcome": outcome.model_dump(mode="json") if outcome else None,
|
|
224
|
+
}
|
|
225
|
+
record = EffectRecord(
|
|
226
|
+
request=request,
|
|
227
|
+
phase=phase,
|
|
228
|
+
revision=revision,
|
|
229
|
+
evidence_digest=digest(proof),
|
|
230
|
+
outcome=outcome,
|
|
231
|
+
)
|
|
232
|
+
encoded = canonical_bytes(record.model_dump(mode="json")).decode()
|
|
233
|
+
self.connection.execute(
|
|
234
|
+
"INSERT INTO teams_effect_entries VALUES(?,?,?,?,?,?,?) ON "
|
|
235
|
+
"CONFLICT(effect_key) DO UPDATE SET "
|
|
236
|
+
"phase=excluded.phase,revision=excluded.revision,claim_id=excluded.claim_id,record_json=excluded.record_json",
|
|
237
|
+
(
|
|
238
|
+
request.effect_key,
|
|
239
|
+
request.request_digest,
|
|
240
|
+
canonical_bytes(request.model_dump(mode="json")).decode(),
|
|
241
|
+
phase,
|
|
242
|
+
revision,
|
|
243
|
+
claim_id,
|
|
244
|
+
encoded,
|
|
245
|
+
),
|
|
246
|
+
)
|
|
247
|
+
self.connection.execute(
|
|
248
|
+
"INSERT INTO "
|
|
249
|
+
"teams_effect_reports(effect_key,revision,evidence_digest,record_json)"
|
|
250
|
+
" VALUES(?,?,?,?)",
|
|
251
|
+
(request.effect_key, revision, record.evidence_digest, encoded),
|
|
252
|
+
)
|
|
253
|
+
return record
|
|
254
|
+
|
|
255
|
+
def _transaction(self, operation):
|
|
256
|
+
with self._lock:
|
|
257
|
+
self.connection.execute("BEGIN IMMEDIATE")
|
|
258
|
+
try:
|
|
259
|
+
identity = self.connection.execute(
|
|
260
|
+
"SELECT * FROM teams_effect_meta WHERE id=1"
|
|
261
|
+
).fetchone()
|
|
262
|
+
if (
|
|
263
|
+
identity is None
|
|
264
|
+
or identity["version"] != 1
|
|
265
|
+
or identity["store_incarnation"] != self.store_incarnation
|
|
266
|
+
or identity["journal_incarnation"] != self.journal_incarnation
|
|
267
|
+
):
|
|
268
|
+
raise EffectConflict("effect_store_incarnation_mismatch")
|
|
269
|
+
result = operation()
|
|
270
|
+
self.connection.execute("COMMIT")
|
|
271
|
+
return result
|
|
272
|
+
except BaseException:
|
|
273
|
+
self.connection.execute("ROLLBACK")
|
|
274
|
+
raise
|
|
275
|
+
|
|
276
|
+
async def get(self, request):
|
|
277
|
+
request = self._request(request)
|
|
278
|
+
|
|
279
|
+
def read():
|
|
280
|
+
row = self._row(request)
|
|
281
|
+
return self._record(row) if row else None
|
|
282
|
+
|
|
283
|
+
return await asyncio.to_thread(self._transaction, read)
|
|
284
|
+
|
|
285
|
+
def _invocation(self, request, *, insert=False):
|
|
286
|
+
row = self.connection.execute(
|
|
287
|
+
"SELECT invocation_digest FROM teams_effect_invocations WHERE invocation_key=?",
|
|
288
|
+
(request.invocation_key,),
|
|
289
|
+
).fetchone()
|
|
290
|
+
if row is not None and row[0] != request.invocation_digest:
|
|
291
|
+
raise EffectConflict("effect_invocation_conflict")
|
|
292
|
+
if row is None and insert:
|
|
293
|
+
self.connection.execute(
|
|
294
|
+
"INSERT INTO teams_effect_invocations VALUES(?,?)",
|
|
295
|
+
(request.invocation_key, request.invocation_digest),
|
|
296
|
+
)
|
|
297
|
+
return row is not None
|
|
298
|
+
|
|
299
|
+
async def record_invocation(self, request):
|
|
300
|
+
request = self._request(request)
|
|
301
|
+
await asyncio.to_thread(self._transaction, lambda: self._invocation(request, insert=True))
|
|
302
|
+
return request.invocation_digest
|
|
303
|
+
|
|
304
|
+
async def get_invocation(self, request):
|
|
305
|
+
request = self._request(request)
|
|
306
|
+
return await asyncio.to_thread(self._transaction, lambda: self._invocation(request))
|
|
307
|
+
|
|
308
|
+
async def prepare(self, request):
|
|
309
|
+
request = self._request(request)
|
|
310
|
+
|
|
311
|
+
def apply():
|
|
312
|
+
row = self._row(request)
|
|
313
|
+
return self._record(row) if row else self._persist(request, "prepared", 1)
|
|
314
|
+
|
|
315
|
+
return await asyncio.to_thread(self._transaction, apply)
|
|
316
|
+
|
|
317
|
+
async def claim(self, request, claim_id):
|
|
318
|
+
request = self._request(request)
|
|
319
|
+
if not isinstance(claim_id, str) or not 1 <= len(claim_id) <= 128:
|
|
320
|
+
raise ValueError("effect_claim_id_invalid")
|
|
321
|
+
|
|
322
|
+
def apply():
|
|
323
|
+
row = self._row(request)
|
|
324
|
+
if row is None:
|
|
325
|
+
raise EffectConflict("effect_not_prepared")
|
|
326
|
+
previous = self._record(row)
|
|
327
|
+
if previous.phase != "prepared":
|
|
328
|
+
return None
|
|
329
|
+
# Persist uncertainty BEFORE touching the external system. Claims
|
|
330
|
+
# never expire into replay eligibility, even across process death.
|
|
331
|
+
return self._persist(request, "unknown", previous.revision + 1, claim_id=claim_id)
|
|
332
|
+
|
|
333
|
+
return await asyncio.to_thread(self._transaction, apply)
|
|
334
|
+
|
|
335
|
+
async def settle(self, request, claim_id, outcome):
|
|
336
|
+
request = self._request(request)
|
|
337
|
+
outcome = EffectOutcome.model_validate(outcome.model_dump(mode="json"))
|
|
338
|
+
|
|
339
|
+
def apply():
|
|
340
|
+
row = self._row(request)
|
|
341
|
+
if row is None or row["claim_id"] != claim_id:
|
|
342
|
+
raise EffectConflict("effect_claim_mismatch")
|
|
343
|
+
previous = self._record(row)
|
|
344
|
+
if previous.outcome:
|
|
345
|
+
if previous.outcome == outcome:
|
|
346
|
+
return previous
|
|
347
|
+
raise EffectConflict("effect_outcome_conflict")
|
|
348
|
+
if previous.phase != "unknown":
|
|
349
|
+
raise EffectConflict("effect_phase_conflict")
|
|
350
|
+
return self._persist(
|
|
351
|
+
request, outcome.phase, row["revision"] + 1, claim_id=claim_id, outcome=outcome
|
|
352
|
+
)
|
|
353
|
+
|
|
354
|
+
return await asyncio.to_thread(self._transaction, apply)
|
|
355
|
+
|
|
356
|
+
@staticmethod
|
|
357
|
+
def _limit(limit):
|
|
358
|
+
if type(limit) is not int or not 1 <= limit <= 100:
|
|
359
|
+
raise ValueError("effect_page_limit_invalid")
|
|
360
|
+
|
|
361
|
+
async def unresolved(self, *, limit=100, after=""):
|
|
362
|
+
self._limit(limit)
|
|
363
|
+
|
|
364
|
+
def read():
|
|
365
|
+
rows = self.connection.execute(
|
|
366
|
+
"SELECT record_json FROM teams_effect_entries WHERE phase IN "
|
|
367
|
+
"('prepared','unknown') AND effect_key>? ORDER BY effect_key "
|
|
368
|
+
"LIMIT ?",
|
|
369
|
+
(after, limit),
|
|
370
|
+
).fetchall()
|
|
371
|
+
return [self._record(row) for row in rows]
|
|
372
|
+
|
|
373
|
+
return await asyncio.to_thread(self._transaction, read)
|
|
374
|
+
|
|
375
|
+
async def pending_reports(self, *, limit=100):
|
|
376
|
+
self._limit(limit)
|
|
377
|
+
|
|
378
|
+
def read():
|
|
379
|
+
rows = self.connection.execute(
|
|
380
|
+
"SELECT record_json FROM teams_effect_reports WHERE "
|
|
381
|
+
"acknowledged=0 ORDER BY effect_key,revision LIMIT ?",
|
|
382
|
+
(limit,),
|
|
383
|
+
).fetchall()
|
|
384
|
+
return [self._record(row) for row in rows]
|
|
385
|
+
|
|
386
|
+
return await asyncio.to_thread(self._transaction, read)
|
|
387
|
+
|
|
388
|
+
async def for_execution(self, context_ref, native_run_id, *, limit=100, after=""):
|
|
389
|
+
self._limit(limit)
|
|
390
|
+
after_key, after_revision = _execution_scope(context_ref, native_run_id, after)
|
|
391
|
+
|
|
392
|
+
def read():
|
|
393
|
+
rows = self.connection.execute(
|
|
394
|
+
"SELECT * FROM teams_effect_reports WHERE "
|
|
395
|
+
"json_extract(record_json,'$.request.context_ref')=? AND "
|
|
396
|
+
"json_extract(record_json,'$.request.native_run_id')=? AND "
|
|
397
|
+
"(effect_key>? OR (effect_key=? AND revision>?)) "
|
|
398
|
+
"ORDER BY effect_key,revision LIMIT ?",
|
|
399
|
+
(context_ref, native_run_id, after_key, after_key, after_revision, limit),
|
|
400
|
+
).fetchall()
|
|
401
|
+
result = [self._record(row) for row in rows]
|
|
402
|
+
for record in result:
|
|
403
|
+
self._request(record.request)
|
|
404
|
+
return result
|
|
405
|
+
|
|
406
|
+
return await asyncio.to_thread(self._transaction, read)
|
|
407
|
+
|
|
408
|
+
async def acknowledge_report(self, effect_key, revision, evidence_digest):
|
|
409
|
+
def apply():
|
|
410
|
+
row = self.connection.execute(
|
|
411
|
+
"SELECT evidence_digest FROM teams_effect_reports WHERE "
|
|
412
|
+
"effect_key=? AND revision=?",
|
|
413
|
+
(effect_key, revision),
|
|
414
|
+
).fetchone()
|
|
415
|
+
if row is None or row[0] != evidence_digest:
|
|
416
|
+
raise EffectConflict("effect_report_ack_mismatch")
|
|
417
|
+
self.connection.execute(
|
|
418
|
+
"UPDATE teams_effect_reports SET acknowledged=1 WHERE effect_key=? AND revision=?",
|
|
419
|
+
(effect_key, revision),
|
|
420
|
+
)
|
|
421
|
+
|
|
422
|
+
await asyncio.to_thread(self._transaction, apply)
|
|
423
|
+
|
|
424
|
+
|
|
425
|
+
def _execution_scope(context_ref, native_run_id, after):
|
|
426
|
+
if (
|
|
427
|
+
not all(
|
|
428
|
+
isinstance(value, str) and 1 <= len(value) <= 256
|
|
429
|
+
for value in (context_ref, native_run_id)
|
|
430
|
+
)
|
|
431
|
+
or not isinstance(after, str)
|
|
432
|
+
or len(after) > 256
|
|
433
|
+
):
|
|
434
|
+
raise ValueError("effect_execution_scope_invalid")
|
|
435
|
+
if not after:
|
|
436
|
+
return "", 0
|
|
437
|
+
parsed = re.fullmatch(r"(effect_[0-9a-f]{64}):([1-3])", after)
|
|
438
|
+
if parsed is None:
|
|
439
|
+
raise ValueError("effect_execution_cursor_invalid")
|
|
440
|
+
return parsed[1], int(parsed[2])
|
|
441
|
+
|
|
442
|
+
|
|
443
|
+
class PostgresEffectJournal:
|
|
444
|
+
"""Native asyncpg journal in the original Kernel pool/schema and tenant.
|
|
445
|
+
|
|
446
|
+
``open(initialize=True)`` is explicit schema provisioning, never a fallback
|
|
447
|
+
for a missing ledger. Runtime reopen verifies both original store identity
|
|
448
|
+
and journal incarnation on every transaction. This adapter owns no pool.
|
|
449
|
+
"""
|
|
450
|
+
|
|
451
|
+
shared_across_hosts = True
|
|
452
|
+
_request = SQLiteEffectJournal._request
|
|
453
|
+
_record = staticmethod(SQLiteEffectJournal._record)
|
|
454
|
+
_limit = staticmethod(SQLiteEffectJournal._limit)
|
|
455
|
+
|
|
456
|
+
def __init__(self, kernel_store, *, store_incarnation):
|
|
457
|
+
from ksadk.kernel.postgres_store import PostgresAgentKernelStore
|
|
458
|
+
|
|
459
|
+
if not isinstance(kernel_store, PostgresAgentKernelStore):
|
|
460
|
+
raise TypeError("original PostgreSQL Kernel store required")
|
|
461
|
+
self.kernel_store = kernel_store
|
|
462
|
+
self.namespace = kernel_store.tenant_id
|
|
463
|
+
self.store_incarnation = store_incarnation
|
|
464
|
+
self.journal_incarnation = None
|
|
465
|
+
|
|
466
|
+
@classmethod
|
|
467
|
+
async def open(cls, kernel_store, *, store_incarnation, initialize=False):
|
|
468
|
+
self = cls(kernel_store, store_incarnation=store_incarnation)
|
|
469
|
+
async with self._transaction(check_journal=False) as db:
|
|
470
|
+
if initialize:
|
|
471
|
+
for statement in (
|
|
472
|
+
"CREATE TABLE IF NOT EXISTS teams_effect_pg_meta (namespace TEXT PRIMARY KEY,"
|
|
473
|
+
"version INTEGER NOT NULL,store_incarnation TEXT NOT NULL,"
|
|
474
|
+
"journal_incarnation TEXT NOT NULL)",
|
|
475
|
+
"CREATE TABLE IF NOT EXISTS teams_effect_pg_invocations "
|
|
476
|
+
"(namespace TEXT NOT NULL,invocation_key TEXT NOT NULL,"
|
|
477
|
+
"invocation_digest TEXT NOT NULL,PRIMARY KEY(namespace,invocation_key))",
|
|
478
|
+
"CREATE TABLE IF NOT EXISTS teams_effect_pg_entries (namespace TEXT NOT NULL,"
|
|
479
|
+
"effect_key TEXT NOT NULL,request_digest TEXT NOT NULL,phase TEXT NOT NULL,"
|
|
480
|
+
"revision BIGINT NOT NULL,claim_id TEXT,record_json TEXT NOT NULL,"
|
|
481
|
+
"PRIMARY KEY(namespace,effect_key))",
|
|
482
|
+
"CREATE TABLE IF NOT EXISTS teams_effect_pg_reports (namespace TEXT NOT NULL,"
|
|
483
|
+
"effect_key TEXT NOT NULL,revision BIGINT NOT NULL,"
|
|
484
|
+
"evidence_digest TEXT NOT NULL,"
|
|
485
|
+
"record_json TEXT NOT NULL,acknowledged BOOLEAN NOT NULL DEFAULT FALSE,"
|
|
486
|
+
"PRIMARY KEY(namespace,effect_key,revision),FOREIGN KEY(namespace,effect_key) "
|
|
487
|
+
"REFERENCES teams_effect_pg_entries(namespace,effect_key))",
|
|
488
|
+
"CREATE INDEX IF NOT EXISTS teams_effect_pg_pending ON teams_effect_pg_reports "
|
|
489
|
+
"(namespace,acknowledged,effect_key,revision)",
|
|
490
|
+
"CREATE INDEX IF NOT EXISTS teams_effect_pg_evidence_execution "
|
|
491
|
+
"ON teams_effect_pg_reports "
|
|
492
|
+
"(namespace, ((record_json::jsonb)->'request'->>'context_ref'),"
|
|
493
|
+
"((record_json::jsonb)->'request'->>'native_run_id'),effect_key,revision)",
|
|
494
|
+
):
|
|
495
|
+
await db.execute(statement)
|
|
496
|
+
await db.execute(
|
|
497
|
+
"INSERT INTO teams_effect_pg_meta VALUES($1,1,$2,$3) "
|
|
498
|
+
"ON CONFLICT(namespace) DO NOTHING",
|
|
499
|
+
self.namespace,
|
|
500
|
+
store_incarnation,
|
|
501
|
+
"journal_" + uuid4().hex,
|
|
502
|
+
)
|
|
503
|
+
await self._identity(db)
|
|
504
|
+
return self
|
|
505
|
+
|
|
506
|
+
async def _identity(self, db):
|
|
507
|
+
row = await db.fetchrow(
|
|
508
|
+
"SELECT * FROM teams_effect_pg_meta WHERE namespace=$1", self.namespace
|
|
509
|
+
)
|
|
510
|
+
if (
|
|
511
|
+
row is None
|
|
512
|
+
or row["version"] != 1
|
|
513
|
+
or row["store_incarnation"] != self.store_incarnation
|
|
514
|
+
or self.journal_incarnation not in {None, row["journal_incarnation"]}
|
|
515
|
+
):
|
|
516
|
+
raise EffectConflict("effect_store_incarnation_mismatch")
|
|
517
|
+
self.journal_incarnation = row["journal_incarnation"]
|
|
518
|
+
|
|
519
|
+
@asynccontextmanager
|
|
520
|
+
async def _transaction(self, *, check_journal=True):
|
|
521
|
+
async with self.kernel_store._connection() as db, db.transaction():
|
|
522
|
+
await db.execute("SET LOCAL lock_timeout='5s'")
|
|
523
|
+
await db.execute("SET LOCAL statement_timeout='10s'")
|
|
524
|
+
# No lease expiry can turn an unknown effect into a fresh sender.
|
|
525
|
+
# Advisory locking serializes per-tenant initialize and transitions
|
|
526
|
+
# across independent pods while retaining original asyncpg storage.
|
|
527
|
+
await db.execute(
|
|
528
|
+
"SELECT pg_advisory_xact_lock(hashtextextended($1,0))",
|
|
529
|
+
"teams-effect-journal:" + self.namespace,
|
|
530
|
+
)
|
|
531
|
+
await db.execute("SELECT 1 FROM kernel_inbox LIMIT 1")
|
|
532
|
+
row = await db.fetchrow(
|
|
533
|
+
"SELECT incarnation FROM teams_host_store_identity WHERE namespace=$1",
|
|
534
|
+
self.namespace,
|
|
535
|
+
)
|
|
536
|
+
if row is None or row["incarnation"] != self.store_incarnation:
|
|
537
|
+
raise EffectConflict("effect_store_incarnation_mismatch")
|
|
538
|
+
if check_journal:
|
|
539
|
+
await self._identity(db)
|
|
540
|
+
yield db
|
|
541
|
+
|
|
542
|
+
async def close(self):
|
|
543
|
+
# Pool lifecycle belongs to the original Kernel.
|
|
544
|
+
return None
|
|
545
|
+
|
|
546
|
+
async def _row(self, db, request):
|
|
547
|
+
row = await db.fetchrow(
|
|
548
|
+
"SELECT * FROM teams_effect_pg_entries WHERE namespace=$1 AND effect_key=$2",
|
|
549
|
+
self.namespace,
|
|
550
|
+
request.effect_key,
|
|
551
|
+
)
|
|
552
|
+
if row and row["request_digest"] != request.request_digest:
|
|
553
|
+
raise EffectConflict("effect_payload_conflict")
|
|
554
|
+
return row
|
|
555
|
+
|
|
556
|
+
async def _invocation(self, db, request, *, insert=False):
|
|
557
|
+
row = await db.fetchrow(
|
|
558
|
+
"SELECT invocation_digest FROM teams_effect_pg_invocations "
|
|
559
|
+
"WHERE namespace=$1 AND invocation_key=$2",
|
|
560
|
+
self.namespace,
|
|
561
|
+
request.invocation_key,
|
|
562
|
+
)
|
|
563
|
+
if row and row["invocation_digest"] != request.invocation_digest:
|
|
564
|
+
raise EffectConflict("effect_invocation_conflict")
|
|
565
|
+
if row is None and insert:
|
|
566
|
+
await db.execute(
|
|
567
|
+
"INSERT INTO teams_effect_pg_invocations VALUES($1,$2,$3)",
|
|
568
|
+
self.namespace,
|
|
569
|
+
request.invocation_key,
|
|
570
|
+
request.invocation_digest,
|
|
571
|
+
)
|
|
572
|
+
return row is not None
|
|
573
|
+
|
|
574
|
+
async def record_invocation(self, request):
|
|
575
|
+
request = self._request(request)
|
|
576
|
+
async with self._transaction() as db:
|
|
577
|
+
await self._invocation(db, request, insert=True)
|
|
578
|
+
return request.invocation_digest
|
|
579
|
+
|
|
580
|
+
async def get_invocation(self, request):
|
|
581
|
+
request = self._request(request)
|
|
582
|
+
async with self._transaction() as db:
|
|
583
|
+
return await self._invocation(db, request)
|
|
584
|
+
|
|
585
|
+
async def _persist(self, db, request, phase, revision, *, claim_id=None, outcome=None):
|
|
586
|
+
proof = {
|
|
587
|
+
"requestDigest": request.request_digest,
|
|
588
|
+
"phase": phase,
|
|
589
|
+
"revision": revision,
|
|
590
|
+
"outcome": outcome.model_dump(mode="json") if outcome else None,
|
|
591
|
+
}
|
|
592
|
+
record = EffectRecord(
|
|
593
|
+
request=request,
|
|
594
|
+
phase=phase,
|
|
595
|
+
revision=revision,
|
|
596
|
+
evidence_digest=digest(proof),
|
|
597
|
+
outcome=outcome,
|
|
598
|
+
)
|
|
599
|
+
encoded = canonical_bytes(record.model_dump(mode="json")).decode()
|
|
600
|
+
await db.execute(
|
|
601
|
+
"INSERT INTO teams_effect_pg_entries VALUES($1,$2,$3,$4,$5,$6,$7) "
|
|
602
|
+
"ON CONFLICT(namespace,effect_key) DO UPDATE SET phase=excluded.phase,"
|
|
603
|
+
"revision=excluded.revision,claim_id=excluded.claim_id,record_json=excluded.record_json",
|
|
604
|
+
self.namespace,
|
|
605
|
+
request.effect_key,
|
|
606
|
+
request.request_digest,
|
|
607
|
+
phase,
|
|
608
|
+
revision,
|
|
609
|
+
claim_id,
|
|
610
|
+
encoded,
|
|
611
|
+
)
|
|
612
|
+
await db.execute(
|
|
613
|
+
"INSERT INTO teams_effect_pg_reports"
|
|
614
|
+
"(namespace,effect_key,revision,evidence_digest,record_json) VALUES($1,$2,$3,$4,$5)",
|
|
615
|
+
self.namespace,
|
|
616
|
+
request.effect_key,
|
|
617
|
+
revision,
|
|
618
|
+
record.evidence_digest,
|
|
619
|
+
encoded,
|
|
620
|
+
)
|
|
621
|
+
return record
|
|
622
|
+
|
|
623
|
+
async def get(self, request):
|
|
624
|
+
request = self._request(request)
|
|
625
|
+
async with self._transaction() as db:
|
|
626
|
+
row = await self._row(db, request)
|
|
627
|
+
return self._record(row) if row else None
|
|
628
|
+
|
|
629
|
+
async def prepare(self, request):
|
|
630
|
+
request = self._request(request)
|
|
631
|
+
async with self._transaction() as db:
|
|
632
|
+
row = await self._row(db, request)
|
|
633
|
+
return self._record(row) if row else await self._persist(db, request, "prepared", 1)
|
|
634
|
+
|
|
635
|
+
async def claim(self, request, claim_id):
|
|
636
|
+
request = self._request(request)
|
|
637
|
+
if not isinstance(claim_id, str) or not 1 <= len(claim_id) <= 128:
|
|
638
|
+
raise ValueError("effect_claim_id_invalid")
|
|
639
|
+
async with self._transaction() as db:
|
|
640
|
+
row = await self._row(db, request)
|
|
641
|
+
if row is None:
|
|
642
|
+
raise EffectConflict("effect_not_prepared")
|
|
643
|
+
previous = self._record(row)
|
|
644
|
+
if previous.phase != "prepared":
|
|
645
|
+
return None
|
|
646
|
+
return await self._persist(
|
|
647
|
+
db, request, "unknown", previous.revision + 1, claim_id=claim_id
|
|
648
|
+
)
|
|
649
|
+
|
|
650
|
+
async def settle(self, request, claim_id, outcome):
|
|
651
|
+
request = self._request(request)
|
|
652
|
+
outcome = EffectOutcome.model_validate(outcome)
|
|
653
|
+
async with self._transaction() as db:
|
|
654
|
+
row = await self._row(db, request)
|
|
655
|
+
if row is None or row["claim_id"] != claim_id:
|
|
656
|
+
raise EffectConflict("effect_claim_mismatch")
|
|
657
|
+
previous = self._record(row)
|
|
658
|
+
if previous.outcome:
|
|
659
|
+
if previous.outcome == outcome:
|
|
660
|
+
return previous
|
|
661
|
+
raise EffectConflict("effect_outcome_conflict")
|
|
662
|
+
if previous.phase != "unknown":
|
|
663
|
+
raise EffectConflict("effect_phase_conflict")
|
|
664
|
+
return await self._persist(
|
|
665
|
+
db,
|
|
666
|
+
request,
|
|
667
|
+
outcome.phase,
|
|
668
|
+
previous.revision + 1,
|
|
669
|
+
claim_id=claim_id,
|
|
670
|
+
outcome=outcome,
|
|
671
|
+
)
|
|
672
|
+
|
|
673
|
+
async def unresolved(self, *, limit=100, after=""):
|
|
674
|
+
self._limit(limit)
|
|
675
|
+
async with self._transaction() as db:
|
|
676
|
+
rows = await db.fetch(
|
|
677
|
+
"SELECT * FROM teams_effect_pg_entries WHERE namespace=$1 "
|
|
678
|
+
"AND phase IN ('prepared','unknown') AND effect_key>$2 "
|
|
679
|
+
"ORDER BY effect_key LIMIT $3",
|
|
680
|
+
self.namespace,
|
|
681
|
+
after,
|
|
682
|
+
limit,
|
|
683
|
+
)
|
|
684
|
+
return [self._record(row) for row in rows]
|
|
685
|
+
|
|
686
|
+
async def pending_reports(self, *, limit=100):
|
|
687
|
+
self._limit(limit)
|
|
688
|
+
async with self._transaction() as db:
|
|
689
|
+
rows = await db.fetch(
|
|
690
|
+
"SELECT * FROM teams_effect_pg_reports WHERE namespace=$1 "
|
|
691
|
+
"AND acknowledged=FALSE ORDER BY effect_key,revision LIMIT $2",
|
|
692
|
+
self.namespace,
|
|
693
|
+
limit,
|
|
694
|
+
)
|
|
695
|
+
return [self._record(row) for row in rows]
|
|
696
|
+
|
|
697
|
+
async def for_execution(self, context_ref, native_run_id, *, limit=100, after=""):
|
|
698
|
+
self._limit(limit)
|
|
699
|
+
after_key, after_revision = _execution_scope(context_ref, native_run_id, after)
|
|
700
|
+
async with self._transaction() as db:
|
|
701
|
+
rows = await db.fetch(
|
|
702
|
+
"SELECT * FROM teams_effect_pg_reports WHERE namespace=$1 AND "
|
|
703
|
+
"record_json::jsonb->'request'->>'context_ref'=$2 AND "
|
|
704
|
+
"record_json::jsonb->'request'->>'native_run_id'=$3 AND "
|
|
705
|
+
"(effect_key>$4 OR (effect_key=$4 AND revision>$5)) "
|
|
706
|
+
"ORDER BY effect_key,revision LIMIT $6",
|
|
707
|
+
self.namespace,
|
|
708
|
+
context_ref,
|
|
709
|
+
native_run_id,
|
|
710
|
+
after_key,
|
|
711
|
+
after_revision,
|
|
712
|
+
limit,
|
|
713
|
+
)
|
|
714
|
+
result = [self._record(row) for row in rows]
|
|
715
|
+
for record in result:
|
|
716
|
+
self._request(record.request)
|
|
717
|
+
return result
|
|
718
|
+
|
|
719
|
+
async def acknowledge_report(self, effect_key, revision, evidence_digest):
|
|
720
|
+
async with self._transaction() as db:
|
|
721
|
+
row = await db.fetchrow(
|
|
722
|
+
"SELECT evidence_digest FROM teams_effect_pg_reports "
|
|
723
|
+
"WHERE namespace=$1 AND effect_key=$2 AND revision=$3",
|
|
724
|
+
self.namespace,
|
|
725
|
+
effect_key,
|
|
726
|
+
revision,
|
|
727
|
+
)
|
|
728
|
+
if row is None or row["evidence_digest"] != evidence_digest:
|
|
729
|
+
raise EffectConflict("effect_report_ack_mismatch")
|
|
730
|
+
await db.execute(
|
|
731
|
+
"UPDATE teams_effect_pg_reports SET acknowledged=TRUE "
|
|
732
|
+
"WHERE namespace=$1 AND effect_key=$2 AND revision=$3",
|
|
733
|
+
self.namespace,
|
|
734
|
+
effect_key,
|
|
735
|
+
revision,
|
|
736
|
+
)
|
|
737
|
+
|
|
738
|
+
|
|
739
|
+
class EffectAdapter(Protocol):
|
|
740
|
+
async def execute(self, arguments: dict[str, Any], *, effect_key: str) -> EffectOutcome: ...
|
|
741
|
+
|
|
742
|
+
|
|
743
|
+
async def drain_effect_reports(
|
|
744
|
+
journal: EffectJournal,
|
|
745
|
+
report_remote: Callable[[EffectRecord], Awaitable[EffectReportReceipt]],
|
|
746
|
+
*,
|
|
747
|
+
limit: int = 100,
|
|
748
|
+
timeout_seconds: float = 30,
|
|
749
|
+
) -> int:
|
|
750
|
+
"""One bounded, cancellable drain; uncertain ACKs remain pending for replay.
|
|
751
|
+
|
|
752
|
+
The transport authenticates the original Host and chooses its live/recovery
|
|
753
|
+
carrier. Acknowledgements cannot delete other effects or evidence revisions.
|
|
754
|
+
The persisted Server receipt, not a newly generated success, must be returned
|
|
755
|
+
after a lost ACK. Callers choose backoff; this function never spins forever.
|
|
756
|
+
"""
|
|
757
|
+
if type(limit) is not int or not 1 <= limit <= 100:
|
|
758
|
+
raise ValueError("effect_page_limit_invalid")
|
|
759
|
+
if type(timeout_seconds) not in {int, float} or not 0 < timeout_seconds <= 60:
|
|
760
|
+
raise ValueError("effect_drain_timeout_invalid")
|
|
761
|
+
acknowledged = 0
|
|
762
|
+
try:
|
|
763
|
+
async with asyncio.timeout(timeout_seconds):
|
|
764
|
+
for record in await journal.pending_reports(limit=limit):
|
|
765
|
+
ack = EffectReportReceipt.model_validate(await report_remote(record))
|
|
766
|
+
if (
|
|
767
|
+
ack.effectKey != record.request.effect_key
|
|
768
|
+
or ack.journalRevision != record.revision
|
|
769
|
+
or ack.evidenceDigest != record.evidence_digest
|
|
770
|
+
):
|
|
771
|
+
raise EffectConflict("effect_report_ack_mismatch")
|
|
772
|
+
await journal.acknowledge_report(
|
|
773
|
+
ack.effectKey, ack.journalRevision, ack.evidenceDigest
|
|
774
|
+
)
|
|
775
|
+
acknowledged += 1
|
|
776
|
+
except (EffectConflict, asyncio.CancelledError):
|
|
777
|
+
raise
|
|
778
|
+
except Exception:
|
|
779
|
+
raise EffectUncertain("effect_report_unconfirmed") from None
|
|
780
|
+
return acknowledged
|
|
781
|
+
|
|
782
|
+
|
|
783
|
+
class EffectExecutor:
|
|
784
|
+
"""Grant-gated, write-ahead wrapper. Returns proof, never raw tool secrets.
|
|
785
|
+
|
|
786
|
+
``authorize`` MUST resolve the live original grant/policy at the real tool
|
|
787
|
+
boundary. ``prepare_remote`` MUST return the Server's persisted same-scope
|
|
788
|
+
receipt; its transport must lookup the original key after ACK uncertainty.
|
|
789
|
+
Runtime assembly must not advertise effectLedger until these are mounted.
|
|
790
|
+
"""
|
|
791
|
+
|
|
792
|
+
def __init__(
|
|
793
|
+
self,
|
|
794
|
+
journal: EffectJournal,
|
|
795
|
+
*,
|
|
796
|
+
authorize: Callable[[EffectRequest], Awaitable[None]],
|
|
797
|
+
prepare_remote: Callable[[EffectRequest], Awaitable[EffectPreparedReceipt]],
|
|
798
|
+
):
|
|
799
|
+
self.journal, self.authorize, self.prepare_remote = journal, authorize, prepare_remote
|
|
800
|
+
|
|
801
|
+
async def invoke(
|
|
802
|
+
self, request: EffectRequest, arguments: dict[str, Any], adapter: EffectAdapter
|
|
803
|
+
) -> EffectRecord:
|
|
804
|
+
request = EffectRequest.model_validate(request.model_dump(mode="json"))
|
|
805
|
+
arguments = json.loads(canonical_bytes(arguments))
|
|
806
|
+
if (
|
|
807
|
+
not isinstance(arguments, dict)
|
|
808
|
+
or effect_payload_digest(request.tool_name, request.adapter_version, arguments)
|
|
809
|
+
!= request.payload_digest
|
|
810
|
+
):
|
|
811
|
+
raise EffectConflict("effect_payload_conflict")
|
|
812
|
+
# Resolve caller scope before exposing even a cached/uncertain record.
|
|
813
|
+
await self.authorize(request)
|
|
814
|
+
await self.journal.record_invocation(request)
|
|
815
|
+
previous = await self.journal.get(request)
|
|
816
|
+
if previous and previous.phase in {"completed", "failed"}:
|
|
817
|
+
return previous
|
|
818
|
+
if previous and previous.phase == "unknown":
|
|
819
|
+
raise EffectUncertain("effect_unknown_requires_reconciliation")
|
|
820
|
+
await self.journal.prepare(request)
|
|
821
|
+
try:
|
|
822
|
+
ack = EffectPreparedReceipt.model_validate(
|
|
823
|
+
(await self.prepare_remote(request)).model_dump(mode="json")
|
|
824
|
+
)
|
|
825
|
+
if (
|
|
826
|
+
ack.effect_key != request.effect_key
|
|
827
|
+
or ack.payload_digest != request.payload_digest
|
|
828
|
+
or ack.request_digest != request.request_digest
|
|
829
|
+
):
|
|
830
|
+
raise EffectConflict("effect_prepare_ack_mismatch")
|
|
831
|
+
if ack.phase != "prepared":
|
|
832
|
+
raise EffectUncertain("effect_remote_requires_reconciliation")
|
|
833
|
+
except (EffectConflict, asyncio.CancelledError):
|
|
834
|
+
raise
|
|
835
|
+
except Exception:
|
|
836
|
+
raise EffectUncertain("effect_prepare_unconfirmed") from None
|
|
837
|
+
await self.authorize(request)
|
|
838
|
+
claim_id = uuid4().hex
|
|
839
|
+
record = await self.journal.claim(request, claim_id)
|
|
840
|
+
if record is None:
|
|
841
|
+
raise EffectUncertain("effect_already_claimed")
|
|
842
|
+
try:
|
|
843
|
+
# A claim may wait on storage; recheck immediately before external I/O.
|
|
844
|
+
await self.authorize(request)
|
|
845
|
+
outcome = await adapter.execute(arguments, effect_key=request.effect_key)
|
|
846
|
+
return await self.journal.settle(request, claim_id, outcome)
|
|
847
|
+
except asyncio.CancelledError:
|
|
848
|
+
# Durable unknown survives cancellation, including after remote send.
|
|
849
|
+
raise
|
|
850
|
+
except Exception:
|
|
851
|
+
raise EffectUncertain("effect_execution_uncertain") from None
|