ummaya 0.2.4 → 0.2.5
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.
- package/README.md +15 -2
- package/bin/ummaya +10 -1
- package/npm-shrinkwrap.json +253 -2
- package/package.json +5 -1
- package/prompts/manifest.yaml +1 -1
- package/prompts/system_v1.md +1 -0
- package/pyproject.toml +26 -2
- package/specs/2803-document-production-hardening/contracts/document-tools.schema.json +1043 -0
- package/src/ummaya/_canonical/__init__.py +2 -0
- package/src/ummaya/engine/engine.py +29 -132
- package/src/ummaya/evidence/__init__.py +21 -2
- package/src/ummaya/evidence/dataset_contract.py +193 -0
- package/src/ummaya/evidence/document_authoring_cases.py +33 -0
- package/src/ummaya/evidence/document_harness.py +313 -0
- package/src/ummaya/evidence/document_viewer_ux.py +391 -0
- package/src/ummaya/evidence/gates.py +70 -0
- package/src/ummaya/evidence/json_types.py +20 -0
- package/src/ummaya/evidence/models.py +88 -1
- package/src/ummaya/evidence/output_payload.py +89 -0
- package/src/ummaya/evidence/payload_documents.py +233 -0
- package/src/ummaya/evidence/route_contracts.py +224 -0
- package/src/ummaya/evidence/route_helpers.py +150 -0
- package/src/ummaya/evidence/runner.py +81 -212
- package/src/ummaya/evidence/source_provenance.py +246 -0
- package/src/ummaya/evidence/source_provenance_redaction.py +176 -0
- package/src/ummaya/evidence/tool_layer.py +39 -0
- package/src/ummaya/evidence/tool_layer_models.py +151 -0
- package/src/ummaya/ipc/adapter_manifest_emitter.py +26 -10
- package/src/ummaya/ipc/document_intent_normalization.py +185 -0
- package/src/ummaya/ipc/frame_schema.py +5 -5
- package/src/ummaya/ipc/route_diagnostics.py +73 -0
- package/src/ummaya/ipc/stdio.py +1109 -477
- package/src/ummaya/llm/client.py +102 -3
- package/src/ummaya/llm/config.py +8 -3
- package/src/ummaya/primitives/__init__.py +6 -2
- package/src/ummaya/primitives/delegation.py +1 -1
- package/src/ummaya/primitives/document.py +28 -0
- package/src/ummaya/settings.py +0 -3
- package/src/ummaya/tools/discovery_bridge.py +17 -1
- package/src/ummaya/tools/documents/__init__.py +297 -0
- package/src/ummaya/tools/documents/adapter_registry.py +487 -0
- package/src/ummaya/tools/documents/archive_container_probe.py +167 -0
- package/src/ummaya/tools/documents/artifact_store.py +454 -0
- package/src/ummaya/tools/documents/authoring.py +283 -0
- package/src/ummaya/tools/documents/baselines.py +114 -0
- package/src/ummaya/tools/documents/capability.py +331 -0
- package/src/ummaya/tools/documents/contracts.py +112 -0
- package/src/ummaya/tools/documents/conversion.py +521 -0
- package/src/ummaya/tools/documents/diff.py +275 -0
- package/src/ummaya/tools/documents/engines.py +163 -0
- package/src/ummaya/tools/documents/evaluation.py +291 -0
- package/src/ummaya/tools/documents/explicit_values.py +108 -0
- package/src/ummaya/tools/documents/fixtures.py +174 -0
- package/src/ummaya/tools/documents/format_completion_audit.py +471 -0
- package/src/ummaya/tools/documents/formats/__init__.py +2 -0
- package/src/ummaya/tools/documents/formats/archive.py +528 -0
- package/src/ummaya/tools/documents/formats/base.py +41 -0
- package/src/ummaya/tools/documents/formats/code_file.py +211 -0
- package/src/ummaya/tools/documents/formats/data_file.py +272 -0
- package/src/ummaya/tools/documents/formats/hwp.py +284 -0
- package/src/ummaya/tools/documents/formats/hwpx.py +1837 -0
- package/src/ummaya/tools/documents/formats/odf.py +435 -0
- package/src/ummaya/tools/documents/formats/ooxml.py +1030 -0
- package/src/ummaya/tools/documents/formats/passive.py +766 -0
- package/src/ummaya/tools/documents/formats/pdf.py +702 -0
- package/src/ummaya/tools/documents/formats/text_web.py +268 -0
- package/src/ummaya/tools/documents/hwp_conversion_probe.py +178 -0
- package/src/ummaya/tools/documents/hwp_direct_candidate.py +141 -0
- package/src/ummaya/tools/documents/inspection.py +289 -0
- package/src/ummaya/tools/documents/intake.py +1079 -0
- package/src/ummaya/tools/documents/legacy_office_promotion_probe.py +366 -0
- package/src/ummaya/tools/documents/models.py +1598 -0
- package/src/ummaya/tools/documents/odf_promotion_probe.py +167 -0
- package/src/ummaya/tools/documents/orchestrator.py +96 -0
- package/src/ummaya/tools/documents/passive_capability_probe.py +251 -0
- package/src/ummaya/tools/documents/patch.py +170 -0
- package/src/ummaya/tools/documents/pdfa_conformance.py +284 -0
- package/src/ummaya/tools/documents/pdfa_promotion_probe.py +198 -0
- package/src/ummaya/tools/documents/permissions.py +110 -0
- package/src/ummaya/tools/documents/planner.py +616 -0
- package/src/ummaya/tools/documents/registry.py +2733 -0
- package/src/ummaya/tools/documents/render.py +978 -0
- package/src/ummaya/tools/documents/render_comparison.py +113 -0
- package/src/ummaya/tools/documents/render_comparison_models.py +74 -0
- package/src/ummaya/tools/documents/render_comparison_regions.py +73 -0
- package/src/ummaya/tools/documents/render_comparison_style.py +161 -0
- package/src/ummaya/tools/documents/reread.py +157 -0
- package/src/ummaya/tools/documents/runtime_authoring.py +244 -0
- package/src/ummaya/tools/documents/runtime_authoring_bundle.py +76 -0
- package/src/ummaya/tools/documents/scorecard.py +184 -0
- package/src/ummaya/tools/documents/socratic_planner.py +193 -0
- package/src/ummaya/tools/documents/style.py +48 -0
- package/src/ummaya/tools/documents/tool_defs.py +523 -0
- package/src/ummaya/tools/documents/validate.py +347 -0
- package/src/ummaya/tools/executor.py +29 -0
- package/src/ummaya/tools/live_proxy.py +0 -3
- package/src/ummaya/tools/models.py +5 -1
- package/src/ummaya/tools/register_all.py +8 -0
- package/src/ummaya/tools/registry.py +10 -1
- package/src/ummaya/tools/routing/__init__.py +59 -0
- package/src/ummaya/tools/routing/builder.py +105 -0
- package/src/ummaya/tools/routing/cards.py +29 -0
- package/src/ummaya/tools/routing/decision_service.py +534 -0
- package/src/ummaya/tools/routing/decision_types.py +74 -0
- package/src/ummaya/tools/routing/feasibility.py +122 -0
- package/src/ummaya/tools/routing/intent.py +17 -0
- package/src/ummaya/tools/routing/intent_extractor.py +207 -0
- package/src/ummaya/tools/routing/intent_patterns.py +160 -0
- package/src/ummaya/tools/routing/intent_public_data.py +150 -0
- package/src/ummaya/tools/routing/intent_types.py +48 -0
- package/src/ummaya/tools/routing/lint.py +78 -0
- package/src/ummaya/tools/routing/metadata.py +174 -0
- package/src/ummaya/tools/routing/projection.py +340 -0
- package/src/ummaya/tools/routing/retrieval_policy.py +629 -0
- package/src/ummaya/tools/routing/schema.py +81 -0
- package/src/ummaya/tools/routing/types.py +96 -0
- package/src/ummaya/tools/routing_index.py +2 -2
- package/src/ummaya/tools/search.py +34 -746
- package/tests/fixtures/documents/public_forms/baselines.yaml +113 -0
- package/tui/package.json +1 -1
- package/tui/src/.cc-byte-identical-whitelist.yaml +266 -0
- package/tui/src/QueryEngine.ts +12 -8
- package/tui/src/bridge/inboundAttachments.ts +3 -3
- package/tui/src/cli/handlers/auth.ts +3 -12
- package/tui/src/cli/print.ts +7 -7
- package/tui/src/commands/insights.ts +1 -1
- package/tui/src/commands/install-github-app/types.ts +8 -30
- package/tui/src/commands/plugin/types.ts +6 -28
- package/tui/src/commands/plugin/unifiedTypes.ts +4 -26
- package/tui/src/commands/rename/generateSessionName.ts +1 -1
- package/tui/src/components/Feedback.tsx +1 -1
- package/tui/src/components/LogoV2/EmergencyTip.tsx +11 -2
- package/tui/src/components/LogoV2/WelcomeV2.tsx +1 -3
- package/tui/src/components/ScrollKeybindingHandler.tsx +6 -6
- package/tui/src/components/Spinner/types.ts +6 -28
- package/tui/src/components/agents/generateAgent.ts +1 -1
- package/tui/src/components/agents/new-agent-creation/types.ts +4 -26
- package/tui/src/components/config/EnvSecretIsolatedEditor.tsx +1 -1
- package/tui/src/components/mcp/types.ts +16 -38
- package/tui/src/components/messages/AssistantToolUseMessage.tsx +3 -2
- package/tui/src/components/messages/UserCrossSessionMessage.ts +16 -4
- package/tui/src/components/messages/UserForkBoilerplateMessage.ts +16 -4
- package/tui/src/components/messages/UserGitHubWebhookMessage.ts +16 -4
- package/tui/src/components/messages/UserToolResultMessage/utils.tsx +3 -2
- package/tui/src/components/permissions/MonitorPermissionRequest/MonitorPermissionRequest.ts +9 -4
- package/tui/src/components/permissions/ReviewArtifactPermissionRequest/ReviewArtifactPermissionRequest.ts +9 -4
- package/tui/src/components/primitive/DocumentSocraticReviewBlock.tsx +129 -0
- package/tui/src/components/primitive/DocumentToolResultCard.tsx +224 -0
- package/tui/src/components/primitive/documentSocraticReview.ts +215 -0
- package/tui/src/components/primitive/index.tsx +43 -1
- package/tui/src/components/primitive/types.ts +137 -0
- package/tui/src/components/ui/option.ts +4 -26
- package/tui/src/constants/common.ts +0 -2
- package/tui/src/constants/prompts.ts +4 -3
- package/tui/src/constants/querySource.ts +4 -26
- package/tui/src/entrypoints/sdk/controlTypes.ts +26 -48
- package/tui/src/entrypoints/sdk/coreTypes.generated.ts +3 -25
- package/tui/src/entrypoints/sdk/runtimeTypes.ts +38 -60
- package/tui/src/entrypoints/sdk/sdkUtilityTypes.ts +4 -26
- package/tui/src/entrypoints/sdk/settingsTypes.generated.ts +3 -25
- package/tui/src/entrypoints/sdk/toolTypes.ts +3 -25
- package/tui/src/hooks/toolPermission/handlers/interactiveHandler.ts +10 -0
- package/tui/src/hooks/useApiKeyVerification.ts +1 -1
- package/tui/src/hooks/useVirtualScroll.ts +1 -1
- package/tui/src/ink/ink.tsx +33 -14
- package/tui/src/ink/reconciler.ts +2 -3
- package/tui/src/ink/render-to-screen.ts +30 -10
- package/tui/src/ipc/bridge.ts +62 -15
- package/tui/src/ipc/bridgeSingleton.ts +5 -1
- package/tui/src/ipc/codec.ts +3 -3
- package/tui/src/ipc/frames.generated.ts +12 -12
- package/tui/src/ipc/llmClient.ts +151 -27
- package/tui/src/ipc/schema/frame.schema.json +1 -1
- package/tui/src/keybindings/defaultBindings.ts +4 -0
- package/tui/src/main.tsx +29 -11
- package/tui/src/native-ts/file-index/index.ts +33 -3
- package/tui/src/observability/surface.ts +2 -2
- package/tui/src/probes/toolRegistryProbe.tsx +3 -1
- package/tui/src/projectOnboardingState.ts +7 -6
- package/tui/src/query/chatMessageTypes.ts +18 -0
- package/tui/src/query/chatMessagesBuilder.ts +1 -1
- package/tui/src/query/deps.ts +1 -1
- package/tui/src/query/messageGuards.ts +106 -0
- package/tui/src/query/publicDataTerminalRepair.ts +384 -0
- package/tui/src/query/run.ts +1075 -0
- package/tui/src/query/supportBoundary.ts +168 -0
- package/tui/src/query/toolResultErrors.ts +103 -0
- package/tui/src/query/toolRunner.ts +687 -0
- package/tui/src/query/unavailableToolRepair.ts +118 -0
- package/tui/src/query.ts +9 -2186
- package/tui/src/screens/REPL.tsx +40 -29
- package/tui/src/services/api/adapterManifest.ts +4 -0
- package/tui/src/services/api/backendChat/events.ts +117 -0
- package/tui/src/services/api/backendChat/finalMessage.ts +40 -0
- package/tui/src/services/api/backendChat/frame.ts +9 -0
- package/tui/src/services/api/backendChat/streaming.ts +430 -0
- package/tui/src/services/api/backendChat/types.ts +62 -0
- package/tui/src/services/api/backendChat.ts +1 -0
- package/tui/src/services/api/client.ts +65 -2
- package/tui/src/services/api/errorUtils.ts +5 -5
- package/tui/src/services/api/errors.ts +1 -1
- package/tui/src/services/api/logging.ts +1 -1
- package/tui/src/services/api/ummaya/evidence.ts +194 -0
- package/tui/src/services/api/ummaya/messages.ts +255 -0
- package/tui/src/services/api/ummaya/nonStreaming.ts +66 -0
- package/tui/src/services/api/ummaya/provider.ts +200 -0
- package/tui/src/services/api/ummaya/reasoning.ts +24 -0
- package/tui/src/services/api/ummaya/request.ts +200 -0
- package/tui/src/services/api/ummaya/selectionContext.ts +240 -0
- package/tui/src/services/api/ummaya/streaming.ts +365 -0
- package/tui/src/services/api/ummaya/streamingPayload.ts +129 -0
- package/tui/src/services/api/ummaya/streamingReader.ts +40 -0
- package/tui/src/services/api/ummaya/toolSelection.ts +217 -0
- package/tui/src/services/api/ummaya/types.ts +110 -0
- package/tui/src/services/api/ummaya/usage.ts +30 -0
- package/tui/src/services/api/ummaya.ts +26 -418
- package/tui/src/services/api/withRetry.ts +1 -1
- package/tui/src/services/awaySummary.ts +2 -2
- package/tui/src/services/claudeAiLimits.ts +1 -1
- package/tui/src/services/compact/autoCompact.ts +1 -1
- package/tui/src/services/compact/compact.ts +1 -1
- package/tui/src/services/lsp/types.ts +8 -30
- package/tui/src/services/tips/types.ts +6 -28
- package/tui/src/services/tokenEstimation.ts +1 -1
- package/tui/src/services/toolRegistry/bootGuard.ts +5 -5
- package/tui/src/services/toolUseSummary/toolUseSummaryGenerator.ts +1 -1
- package/tui/src/services/tools/toolExecution.ts +94 -1
- package/tui/src/store/pendingPermissionSlot.ts +1 -1
- package/tui/src/store/session-store.ts +10 -36
- package/tui/src/stubs/any-stub.ts +15 -10
- package/tui/src/stubs/color-diff-napi.ts +37 -23
- package/tui/src/stubs/globals.d.ts +3 -3
- package/tui/src/stubs/macro-preload.ts +23 -12
- package/tui/src/tools/AdapterTool/AdapterTool.ts +1207 -714
- package/tui/src/tools/AdapterTool/routeDiagnostics.ts +75 -0
- package/tui/src/tools/AgentTool/AgentTool.tsx +84 -1371
- package/tui/src/tools/AgentTool/agentToolHandoff.ts +114 -0
- package/tui/src/tools/AgentTool/agentToolPartialResult.ts +16 -0
- package/tui/src/tools/AgentTool/agentToolProgress.ts +32 -0
- package/tui/src/tools/AgentTool/agentToolResolver.ts +161 -0
- package/tui/src/tools/AgentTool/agentToolResult.ts +163 -0
- package/tui/src/tools/AgentTool/agentToolUtils.ts +14 -686
- package/tui/src/tools/AgentTool/asyncAgentLifecycle.ts +208 -0
- package/tui/src/tools/AgentTool/asyncLifecycle.ts +153 -0
- package/tui/src/tools/AgentTool/backgroundedCompletion.ts +126 -0
- package/tui/src/tools/AgentTool/backgroundedLifecycle.ts +174 -0
- package/tui/src/tools/AgentTool/foregroundBackground.ts +83 -0
- package/tui/src/tools/AgentTool/foregroundDrain.tsx +133 -0
- package/tui/src/tools/AgentTool/foregroundFinalize.ts +98 -0
- package/tui/src/tools/AgentTool/foregroundLifecycle.tsx +237 -0
- package/tui/src/tools/AgentTool/foregroundProgress.tsx +169 -0
- package/tui/src/tools/AgentTool/foregroundTask.ts +89 -0
- package/tui/src/tools/AgentTool/forkSubagent.ts +1 -12
- package/tui/src/tools/AgentTool/forkSubagentGate.ts +34 -0
- package/tui/src/tools/AgentTool/launchRouting.ts +203 -0
- package/tui/src/tools/AgentTool/lifecycle.ts +244 -0
- package/tui/src/tools/AgentTool/mcpRouting.ts +73 -0
- package/tui/src/tools/AgentTool/orchestrationSupport.ts +70 -0
- package/tui/src/tools/AgentTool/permissions.ts +39 -0
- package/tui/src/tools/AgentTool/promptSetup.ts +181 -0
- package/tui/src/tools/AgentTool/remoteRouting.ts +62 -0
- package/tui/src/tools/AgentTool/resultMapping.ts +116 -0
- package/tui/src/tools/AgentTool/resumeAgent.ts +39 -107
- package/tui/src/tools/AgentTool/resumeAgentHelpers.ts +140 -0
- package/tui/src/tools/AgentTool/runAgent.ts +1 -1
- package/tui/src/tools/AgentTool/runtimeConfig.ts +57 -0
- package/tui/src/tools/AgentTool/schemas.ts +196 -0
- package/tui/src/tools/AgentTool/sourceVerificationPropagation.ts +263 -0
- package/tui/src/tools/AgentTool/worktreeLifecycle.ts +105 -0
- package/tui/src/tools/AskUserQuestionTool/AskUserQuestionTool.tsx +174 -202
- package/tui/src/tools/BashTool/BashTool.tsx +71 -1072
- package/tui/src/tools/BashTool/bashCommandHelpers.ts +12 -12
- package/tui/src/tools/BashTool/bashPermissions/astPreflight.ts +173 -0
- package/tui/src/tools/BashTool/bashPermissions/classifierChecks.ts +199 -0
- package/tui/src/tools/BashTool/bashPermissions/compoundGuards.ts +53 -0
- package/tui/src/tools/BashTool/bashPermissions/constants.ts +99 -0
- package/tui/src/tools/BashTool/bashPermissions/index.ts +38 -0
- package/tui/src/tools/BashTool/bashPermissions/legacyMisparsing.ts +62 -0
- package/tui/src/tools/BashTool/bashPermissions/main.ts +135 -0
- package/tui/src/tools/BashTool/bashPermissions/normalizedCommands.ts +33 -0
- package/tui/src/tools/BashTool/bashPermissions/operatorFlow.ts +98 -0
- package/tui/src/tools/BashTool/bashPermissions/permissionChecks.ts +200 -0
- package/tui/src/tools/BashTool/bashPermissions/prefixSuggestions.ts +88 -0
- package/tui/src/tools/BashTool/bashPermissions/promptClassifierRules.ts +125 -0
- package/tui/src/tools/BashTool/bashPermissions/ruleDelegates.ts +19 -0
- package/tui/src/tools/BashTool/bashPermissions/ruleMatching.ts +145 -0
- package/tui/src/tools/BashTool/bashPermissions/sandboxAutoAllow.ts +75 -0
- package/tui/src/tools/BashTool/bashPermissions/subcommandFlow.ts +205 -0
- package/tui/src/tools/BashTool/bashPermissions/subcommandGuards.ts +73 -0
- package/tui/src/tools/BashTool/bashPermissions/subcommandResultHelpers.ts +116 -0
- package/tui/src/tools/BashTool/bashPermissions/types.ts +26 -0
- package/tui/src/tools/BashTool/bashPermissions/wrapperStripping.ts +139 -0
- package/tui/src/tools/BashTool/bashPermissions.ts +26 -2621
- package/tui/src/tools/BashTool/call.ts +202 -0
- package/tui/src/tools/BashTool/callLoader.ts +35 -0
- package/tui/src/tools/BashTool/commandClassification.ts +151 -0
- package/tui/src/tools/BashTool/commandClassificationLoader.ts +40 -0
- package/tui/src/tools/BashTool/cwdReset.ts +33 -0
- package/tui/src/tools/BashTool/lineTruncation.ts +11 -0
- package/tui/src/tools/BashTool/modeValidation.ts +13 -1
- package/tui/src/tools/BashTool/outputPersistence.ts +42 -0
- package/tui/src/tools/BashTool/permissionClassification.ts +66 -0
- package/tui/src/tools/BashTool/permissionLoader.ts +44 -0
- package/tui/src/tools/BashTool/resultLoader.ts +29 -0
- package/tui/src/tools/BashTool/resultMapping.ts +83 -0
- package/tui/src/tools/BashTool/sandboxPolicy.ts +79 -0
- package/tui/src/tools/BashTool/schemas.ts +65 -0
- package/tui/src/tools/BashTool/sedEditExecution.ts +59 -0
- package/tui/src/tools/BashTool/shellExecution.tsx +245 -0
- package/tui/src/tools/BashTool/shellOutputUtils.ts +85 -0
- package/tui/src/tools/BashTool/shellPermissionGauntlet.ts +97 -0
- package/tui/src/tools/BashTool/uiLoader.ts +37 -0
- package/tui/src/tools/BriefTool/upload.ts +1 -1
- package/tui/src/tools/CalculatorTool/parser.ts +2 -2
- package/tui/src/tools/DocumentPrimitive/DocumentPrimitive.ts +262 -0
- package/tui/src/tools/DocumentPrimitive/dispatchNormalization.ts +270 -0
- package/tui/src/tools/DocumentPrimitive/documentDestinationPath.ts +18 -0
- package/tui/src/tools/DocumentPrimitive/documentMutationGuard.ts +22 -0
- package/tui/src/tools/DocumentPrimitive/documentPatchNormalization.ts +248 -0
- package/tui/src/tools/DocumentPrimitive/documentSourceVerification.ts +245 -0
- package/tui/src/tools/DocumentPrimitive/documentSourceVerificationFields.ts +103 -0
- package/tui/src/tools/DocumentPrimitive/modelVisibleOutput.ts +40 -0
- package/tui/src/tools/DocumentPrimitive/prompt.ts +35 -0
- package/tui/src/tools/FileEditTool/FileEditTool.ts +9 -507
- package/tui/src/tools/FileEditTool/call.ts +228 -0
- package/tui/src/tools/FileEditTool/validateInput.ts +196 -0
- package/tui/src/tools/FileReadTool/imageProcessor.ts +13 -0
- package/tui/src/tools/FileWriteTool/FileWriteTool.ts +7 -300
- package/tui/src/tools/FileWriteTool/call.ts +223 -0
- package/tui/src/tools/FileWriteTool/validateInput.ts +80 -0
- package/tui/src/tools/ListMcpResourcesTool/ListMcpResourcesTool.ts +19 -3
- package/tui/src/tools/LookupPrimitive/LookupPrimitive.ts +25 -32
- package/tui/src/tools/LookupPrimitive/prompt.ts +0 -2
- package/tui/src/tools/MCPTool/trustPolicy.ts +118 -0
- package/tui/src/tools/McpAuthTool/McpAuthTool.ts +21 -3
- package/tui/src/tools/NotebookEditTool/NotebookEditTool.ts +7 -326
- package/tui/src/tools/NotebookEditTool/call.ts +254 -0
- package/tui/src/tools/NotebookEditTool/notebookModel.ts +51 -0
- package/tui/src/tools/NotebookEditTool/validateInput.ts +142 -0
- package/tui/src/tools/PowerShellTool/PowerShellTool.tsx +46 -937
- package/tui/src/tools/PowerShellTool/acceptEditsCommandValidation.ts +162 -0
- package/tui/src/tools/PowerShellTool/call.ts +179 -0
- package/tui/src/tools/PowerShellTool/callLoader.ts +37 -0
- package/tui/src/tools/PowerShellTool/commandClassification.ts +86 -0
- package/tui/src/tools/PowerShellTool/modeValidation.ts +25 -332
- package/tui/src/tools/PowerShellTool/outputPersistence.ts +42 -0
- package/tui/src/tools/PowerShellTool/permissionClassification.ts +28 -0
- package/tui/src/tools/PowerShellTool/resultLoader.ts +31 -0
- package/tui/src/tools/PowerShellTool/resultMapping.ts +75 -0
- package/tui/src/tools/PowerShellTool/schemas.ts +40 -0
- package/tui/src/tools/PowerShellTool/shellExecution.tsx +258 -0
- package/tui/src/tools/PowerShellTool/symlinkModeValidation.ts +44 -0
- package/tui/src/tools/PowerShellTool/uiLoader.ts +37 -0
- package/tui/src/tools/PowerShellTool/validation.ts +39 -0
- package/tui/src/tools/ReadMcpResourceTool/ReadMcpResourceTool.ts +19 -3
- package/tui/src/tools/ResolveLocationPrimitive/ResolveLocationPrimitive.ts +1 -11
- package/tui/src/tools/ResolveLocationPrimitive/prompt.ts +2 -6
- package/tui/src/tools/SkillTool/SkillTool.ts +2 -2
- package/tui/src/tools/SubmitPrimitive/SubmitPrimitive.ts +27 -10
- package/tui/src/tools/TaskCreateTool/TaskCreateTool.ts +16 -2
- package/tui/src/tools/TaskGetTool/TaskGetTool.ts +23 -3
- package/tui/src/tools/TaskListTool/TaskListTool.ts +22 -4
- package/tui/src/tools/TaskOutputTool/TaskOutputTool.tsx +46 -547
- package/tui/src/tools/TaskOutputTool/lookup.ts +216 -0
- package/tui/src/tools/TaskOutputTool/render.tsx +257 -0
- package/tui/src/tools/TaskOutputTool/schemas.ts +55 -0
- package/tui/src/tools/TaskOutputTool/serialization.ts +36 -0
- package/tui/src/tools/TaskStopTool/TaskStopTool.ts +10 -0
- package/tui/src/tools/TaskUpdateTool/TaskUpdateTool.ts +14 -364
- package/tui/src/tools/TaskUpdateTool/completion.ts +62 -0
- package/tui/src/tools/TaskUpdateTool/schemas.ts +62 -0
- package/tui/src/tools/TaskUpdateTool/serialization.ts +46 -0
- package/tui/src/tools/TaskUpdateTool/statusUpdate.ts +247 -0
- package/tui/src/tools/TodoWriteTool/TodoWriteTool.ts +21 -2
- package/tui/src/tools/ToolSearchTool/ToolSearchTool.ts +21 -302
- package/tui/src/tools/ToolSearchTool/ccSupportTools.ts +223 -0
- package/tui/src/tools/ToolSearchTool/descriptionCache.ts +50 -0
- package/tui/src/tools/ToolSearchTool/keywordSearch.ts +216 -0
- package/tui/src/tools/ToolSearchTool/prompt.ts +10 -4
- package/tui/src/tools/ToolSearchTool/resultMapping.ts +30 -0
- package/tui/src/tools/ToolSearchTool/schemas.ts +30 -0
- package/tui/src/tools/ToolSearchTool/searchPool.ts +47 -0
- package/tui/src/tools/ToolSearchTool/supportIntentHints.ts +140 -0
- package/tui/src/tools/TranslateTool/TranslateTool.ts +1 -1
- package/tui/src/tools/VerifyPrimitive/VerifyPrimitive.ts +2 -1
- package/tui/src/tools/WebFetchTool/WebFetchTool.ts +43 -138
- package/tui/src/tools/WebFetchTool/call.ts +227 -0
- package/tui/src/tools/WebFetchTool/resolvedAddressSafety.ts +78 -0
- package/tui/src/tools/WebFetchTool/sourceVerification.ts +204 -0
- package/tui/src/tools/WebFetchTool/types.ts +23 -0
- package/tui/src/tools/WebFetchTool/urlSafety.ts +181 -0
- package/tui/src/tools/WebFetchTool/utils.ts +1 -1
- package/tui/src/tools/WebSearchTool/UI.tsx +0 -1
- package/tui/src/tools/WebSearchTool/WebSearchTool.ts +9 -313
- package/tui/src/tools/WebSearchTool/call.ts +33 -0
- package/tui/src/tools/WebSearchTool/responseMapping.ts +190 -0
- package/tui/src/tools/WebSearchTool/resultBlock.ts +47 -0
- package/tui/src/tools/WebSearchTool/schemas.ts +47 -0
- package/tui/src/tools/WebSearchTool/toolSchema.ts +12 -0
- package/tui/src/tools/WorkspaceToolAdapter/WorkspaceToolAdapter.ts +79 -0
- package/tui/src/tools/WorkspaceToolAdapter/allowedRootPolicy.ts +85 -0
- package/tui/src/tools/WorkspaceToolAdapter/documentFormatGuards.ts +73 -0
- package/tui/src/tools/WorkspaceToolAdapter/inputNormalization.ts +105 -0
- package/tui/src/tools/WorkspaceToolAdapter/mcpExposurePolicy.ts +64 -0
- package/tui/src/tools/WorkspaceToolAdapter/toolDefFactory.ts +215 -0
- package/tui/src/tools/WorkspaceToolAdapter/toolNames.ts +6 -0
- package/tui/src/tools/WorkspaceToolAdapter/workspacePolicy.ts +15 -0
- package/tui/src/tools/_shared/dispatchPrimitive.ts +6 -6
- package/tui/src/tools/_shared/documentChangeToPatch.ts +125 -0
- package/tui/src/tools/_shared/documentDispatchArguments.ts +87 -0
- package/tui/src/tools/_shared/documentPrimitiveTimeout.ts +13 -0
- package/tui/src/tools/_shared/documentToolResultRender.ts +98 -0
- package/tui/src/tools/_shared/pendingCallRegistry.ts +1 -6
- package/tui/src/tools/_shared/rootPrimitiveInput.ts +1 -0
- package/tui/src/tools/_shared/toolChoiceRepair/documentCompletionPatterns.ts +58 -0
- package/tui/src/tools/_shared/toolChoiceRepair/documentCompletionPrompt.ts +271 -0
- package/tui/src/tools/_shared/toolChoiceRepair/documentRepair.ts +452 -0
- package/tui/src/tools/_shared/toolChoiceRepair/messageAccess.ts +80 -0
- package/tui/src/tools/_shared/toolChoiceRepair/publicDataRepair.ts +92 -0
- package/tui/src/tools/_shared/toolChoiceRepair/supportRepair.ts +135 -0
- package/tui/src/tools/_shared/toolChoiceRepair.ts +55 -860
- package/tui/src/tools/shared/mockDisclaimer.ts +1 -1
- package/tui/src/tools.ts +39 -190
- package/tui/src/types/fileSuggestion.ts +4 -26
- package/tui/src/types/generated/events_mono/claude_code/v1/claude_code_internal_event.ts +186 -148
- package/tui/src/types/generated/events_mono/common/v1/auth.ts +25 -11
- package/tui/src/types/generated/events_mono/growthbook/v1/growthbook_experiment_event.ts +47 -30
- package/tui/src/types/generated/google/protobuf/timestamp.ts +21 -7
- package/tui/src/types/message.ts +80 -102
- package/tui/src/types/messageQueueTypes.ts +6 -28
- package/tui/src/types/notebook.ts +16 -38
- package/tui/src/types/statusLine.ts +4 -26
- package/tui/src/types/tools.ts +24 -46
- package/tui/src/types/utils.ts +6 -28
- package/tui/src/upstreamproxy/relay.ts +7 -3
- package/tui/src/upstreamproxy/upstreamproxy.ts +1 -1
- package/tui/src/utils/assistantMessageFactories.ts +9 -3
- package/tui/src/utils/auth.ts +129 -139
- package/tui/src/utils/bash/ast.ts +23 -23
- package/tui/src/utils/bash/bashParser.ts +5 -5
- package/tui/src/utils/billing.ts +1 -1
- package/tui/src/utils/collapseReadSearch.ts +3 -3
- package/tui/src/utils/cronTasks.ts +1 -1
- package/tui/src/utils/execFileNoThrow.ts +1 -1
- package/tui/src/utils/filePersistence/types.ts +16 -38
- package/tui/src/utils/forkedAgent.ts +1 -1
- package/tui/src/utils/gracefulShutdown.ts +4 -4
- package/tui/src/utils/heapDumpService.ts +12 -8
- package/tui/src/utils/hooks/apiQueryHookHelper.ts +1 -1
- package/tui/src/utils/hooks/execPromptHook.ts +1 -1
- package/tui/src/utils/hooks/skillImprovement.ts +1 -1
- package/tui/src/utils/mcp/dateTimeParser.ts +1 -1
- package/tui/src/utils/messages.ts +18 -0
- package/tui/src/utils/migrateSessions.ts +3 -3
- package/tui/src/utils/model/model.ts +6 -6
- package/tui/src/utils/permissions/yoloClassifier.ts +1 -1
- package/tui/src/utils/plugins/headlessPluginInstall.ts +1 -1
- package/tui/src/utils/plugins/mcpPluginIntegration.ts +1 -1
- package/tui/src/utils/plugins/mcpbHandler.ts +1 -1
- package/tui/src/utils/plugins/pluginLoader.ts +8 -8
- package/tui/src/utils/protectedNamespace.ts +5 -3
- package/tui/src/utils/rawJsonToolCall.ts +242 -0
- package/tui/src/utils/ripgrep.ts +16 -7
- package/tui/src/utils/sessionTitle.ts +1 -1
- package/tui/src/utils/settings/permissionValidation.ts +14 -2
- package/tui/src/utils/shell/prefix.ts +1 -1
- package/tui/src/utils/sideQuery.ts +1 -1
- package/tui/src/utils/systemThemeWatcher.ts +13 -3
- package/tui/src/utils/teleport.tsx +1 -1
- package/uv.lock +400 -14
- package/tui/src/services/api/claude.ts +0 -3540
- package/tui/src/tools/_shared/directPublicDataGuard.ts +0 -362
- package/tui/src/tools/_shared/kmaAnalysisGuard.ts +0 -197
- package/tui/src/tools/_shared/kmaAviationGuard.ts +0 -70
- package/tui/src/tools/_shared/nmcAedGuard.ts +0 -234
- package/tui/src/tools/_shared/protectedCheckGuard.ts +0 -207
- package/tui/src/tools/_shared/textToolCallGuard.ts +0 -91
|
@@ -34,9 +34,8 @@ if (process.env.NODE_ENV === 'development') {
|
|
|
34
34
|
try {
|
|
35
35
|
// eslint-disable-next-line custom-rules/no-top-level-dynamic-import -- dev-only; NODE_ENV check is DCE'd in production
|
|
36
36
|
void import('./devtools.js')
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
if (error.code === 'ERR_MODULE_NOT_FOUND') {
|
|
37
|
+
} catch (error: unknown) {
|
|
38
|
+
if (error instanceof Error && 'code' in error && error.code === 'ERR_MODULE_NOT_FOUND') {
|
|
40
39
|
// biome-ignore lint/suspicious/noConsole: intentional warning
|
|
41
40
|
console.warn(
|
|
42
41
|
`
|
|
@@ -45,6 +45,31 @@ let output: Output | undefined
|
|
|
45
45
|
const timing = { reconcile: 0, yoga: 0, paint: 0, scan: 0, calls: 0 }
|
|
46
46
|
const LOG_EVERY = 20
|
|
47
47
|
|
|
48
|
+
type SearchRendererContainer = ReturnType<typeof reconciler.createContainer>
|
|
49
|
+
type SearchReconcilerRuntime = typeof reconciler & {
|
|
50
|
+
createContainer(
|
|
51
|
+
root: DOMElement,
|
|
52
|
+
tag: typeof LegacyRoot,
|
|
53
|
+
hydrationCallbacks: null,
|
|
54
|
+
isStrictMode: boolean,
|
|
55
|
+
concurrentUpdatesByDefaultOverride: null,
|
|
56
|
+
identifierPrefix: string,
|
|
57
|
+
onUncaughtError: () => void,
|
|
58
|
+
onCaughtError: () => void,
|
|
59
|
+
onRecoverableError: () => void,
|
|
60
|
+
onDefaultTransitionIndicator: () => void,
|
|
61
|
+
): SearchRendererContainer
|
|
62
|
+
updateContainerSync(
|
|
63
|
+
element: ReactElement | null,
|
|
64
|
+
container: SearchRendererContainer,
|
|
65
|
+
parentComponent: null,
|
|
66
|
+
callback: () => void,
|
|
67
|
+
): void
|
|
68
|
+
flushSyncWork(): void
|
|
69
|
+
}
|
|
70
|
+
|
|
71
|
+
const searchReconciler = reconciler as SearchReconcilerRuntime
|
|
72
|
+
|
|
48
73
|
/** Render a React element (wrapped in all contexts the component needs —
|
|
49
74
|
* caller's job) to an isolated Screen buffer at the given width. Returns
|
|
50
75
|
* the Screen + natural height (from yoga). Used for search: render ONE
|
|
@@ -66,8 +91,7 @@ export function renderToScreen(
|
|
|
66
91
|
stylePool = new StylePool()
|
|
67
92
|
charPool = new CharPool()
|
|
68
93
|
hyperlinkPool = new HyperlinkPool()
|
|
69
|
-
|
|
70
|
-
container = reconciler.createContainer(
|
|
94
|
+
container = searchReconciler.createContainer(
|
|
71
95
|
root,
|
|
72
96
|
LegacyRoot,
|
|
73
97
|
null,
|
|
@@ -82,10 +106,8 @@ export function renderToScreen(
|
|
|
82
106
|
}
|
|
83
107
|
|
|
84
108
|
const t0 = performance.now()
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
// @ts-expect-error flushSyncWork exists but not in @types
|
|
88
|
-
reconciler.flushSyncWork()
|
|
109
|
+
searchReconciler.updateContainerSync(el, container, null, noop)
|
|
110
|
+
searchReconciler.flushSyncWork()
|
|
89
111
|
const t1 = performance.now()
|
|
90
112
|
|
|
91
113
|
// Yoga layout. Root might not have a yogaNode if the tree is empty.
|
|
@@ -117,10 +139,8 @@ export function renderToScreen(
|
|
|
117
139
|
const t3 = performance.now()
|
|
118
140
|
|
|
119
141
|
// Unmount so next call gets a fresh tree. Leaves root/container/pools.
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
// @ts-expect-error flushSyncWork exists but not in @types
|
|
123
|
-
reconciler.flushSyncWork()
|
|
142
|
+
searchReconciler.updateContainerSync(null, container, null, noop)
|
|
143
|
+
searchReconciler.flushSyncWork()
|
|
124
144
|
|
|
125
145
|
timing.reconcile += t1 - t0
|
|
126
146
|
timing.yoga += t2 - t1
|
package/tui/src/ipc/bridge.ts
CHANGED
|
@@ -255,6 +255,14 @@ class AsyncQueue<T> {
|
|
|
255
255
|
this._resolve = resolve
|
|
256
256
|
})
|
|
257
257
|
},
|
|
258
|
+
return: (): Promise<IteratorResult<T>> => {
|
|
259
|
+
if (this._resolve) {
|
|
260
|
+
const r = this._resolve
|
|
261
|
+
this._resolve = null
|
|
262
|
+
r({ value: undefined as unknown as T, done: true })
|
|
263
|
+
}
|
|
264
|
+
return Promise.resolve({ value: undefined as unknown as T, done: true })
|
|
265
|
+
},
|
|
258
266
|
}
|
|
259
267
|
}
|
|
260
268
|
}
|
|
@@ -339,13 +347,19 @@ export function createBridge(opts: BridgeOptions = {}): IPCBridge {
|
|
|
339
347
|
let _tuiSessionToken: string | null = opts.tuiSessionToken ?? null
|
|
340
348
|
let _lastSeenCorrelationId: string | null = null
|
|
341
349
|
let _lastSeenFrameSeq: number | null = null
|
|
342
|
-
// Bounded
|
|
343
|
-
//
|
|
344
|
-
//
|
|
345
|
-
//
|
|
350
|
+
// Bounded rings for replay de-duplication.
|
|
351
|
+
//
|
|
352
|
+
// `applied_frame_seqs` remains the public debug surface expected by the
|
|
353
|
+
// resume tests. The actual skip decision uses a fuller frame identity below:
|
|
354
|
+
// some TUI-owned tool_call result paths are not ring-stamped by the backend
|
|
355
|
+
// yet and legally arrive with the default frame_seq=0. Dropping by
|
|
356
|
+
// session:frame_seq alone loses distinct tool_result frames in ordinary
|
|
357
|
+
// runtime, which is worse than replay duplication.
|
|
346
358
|
const _APPLIED_FRAME_SEQS_CAP = 256
|
|
347
359
|
const _appliedFrameSeqs = new Set<string>()
|
|
348
360
|
const _appliedFrameSeqsOrder: string[] = []
|
|
361
|
+
const _appliedFrameIdentities = new Set<string>()
|
|
362
|
+
const _appliedFrameIdentitiesOrder: string[] = []
|
|
349
363
|
|
|
350
364
|
// ------------------------------------------------------------------
|
|
351
365
|
// Spawn first process
|
|
@@ -435,6 +449,40 @@ export function createBridge(opts: BridgeOptions = {}): IPCBridge {
|
|
|
435
449
|
}
|
|
436
450
|
}
|
|
437
451
|
|
|
452
|
+
function _frameReplayIdentity(frame: IPCFrame): string | null {
|
|
453
|
+
if (frame.frame_seq == null) return null
|
|
454
|
+
const sessionKey = frame.session_id ?? _sessionId
|
|
455
|
+
if (!sessionKey) return null
|
|
456
|
+
return [
|
|
457
|
+
sessionKey,
|
|
458
|
+
frame.frame_seq,
|
|
459
|
+
frame.kind,
|
|
460
|
+
frame.correlation_id ?? '',
|
|
461
|
+
frame.transaction_id ?? '',
|
|
462
|
+
].join(':')
|
|
463
|
+
}
|
|
464
|
+
|
|
465
|
+
function _rememberAppliedFrameIdentity(identity: string): void {
|
|
466
|
+
_appliedFrameIdentities.add(identity)
|
|
467
|
+
_appliedFrameIdentitiesOrder.push(identity)
|
|
468
|
+
if (_appliedFrameIdentitiesOrder.length > _APPLIED_FRAME_SEQS_CAP) {
|
|
469
|
+
const evicted = _appliedFrameIdentitiesOrder.shift()
|
|
470
|
+
if (evicted !== undefined) _appliedFrameIdentities.delete(evicted)
|
|
471
|
+
}
|
|
472
|
+
}
|
|
473
|
+
|
|
474
|
+
function _rememberAppliedFrameSeq(frame: IPCFrame): void {
|
|
475
|
+
if (!_sessionId || frame.frame_seq == null) return
|
|
476
|
+
const key = `${frame.session_id ?? _sessionId}:${frame.frame_seq}`
|
|
477
|
+
if (_appliedFrameSeqs.has(key)) return
|
|
478
|
+
_appliedFrameSeqs.add(key)
|
|
479
|
+
_appliedFrameSeqsOrder.push(key)
|
|
480
|
+
if (_appliedFrameSeqsOrder.length > _APPLIED_FRAME_SEQS_CAP) {
|
|
481
|
+
const evicted = _appliedFrameSeqsOrder.shift()
|
|
482
|
+
if (evicted !== undefined) _appliedFrameSeqs.delete(evicted)
|
|
483
|
+
}
|
|
484
|
+
}
|
|
485
|
+
|
|
438
486
|
async function _doReconnect(): Promise<void> {
|
|
439
487
|
if (_closed || _reconnecting) return
|
|
440
488
|
_reconnecting = true
|
|
@@ -536,22 +584,21 @@ export function createBridge(opts: BridgeOptions = {}): IPCBridge {
|
|
|
536
584
|
_lastSeenCorrelationId = frame.correlation_id
|
|
537
585
|
}
|
|
538
586
|
|
|
539
|
-
// De-duplicate replayed frames
|
|
540
|
-
|
|
541
|
-
|
|
542
|
-
|
|
587
|
+
// De-duplicate replayed frames by full frame identity. Do not
|
|
588
|
+
// use session:frame_seq as the skip key: TUI-owned tool_result
|
|
589
|
+
// frames can currently share the default frame_seq=0 while still
|
|
590
|
+
// being separate, valid results.
|
|
591
|
+
const replayIdentity = _frameReplayIdentity(frame)
|
|
592
|
+
if (replayIdentity !== null) {
|
|
593
|
+
if (_appliedFrameIdentities.has(replayIdentity)) {
|
|
543
594
|
_log(
|
|
544
595
|
'DEBUG',
|
|
545
|
-
`Skipping duplicate replay frame
|
|
596
|
+
`Skipping duplicate replay frame identity=${replayIdentity}`,
|
|
546
597
|
)
|
|
547
598
|
continue
|
|
548
599
|
}
|
|
549
|
-
|
|
550
|
-
|
|
551
|
-
if (_appliedFrameSeqsOrder.length > _APPLIED_FRAME_SEQS_CAP) {
|
|
552
|
-
const evicted = _appliedFrameSeqsOrder.shift()
|
|
553
|
-
if (evicted !== undefined) _appliedFrameSeqs.delete(evicted)
|
|
554
|
-
}
|
|
600
|
+
_rememberAppliedFrameIdentity(replayIdentity)
|
|
601
|
+
_rememberAppliedFrameSeq(frame)
|
|
555
602
|
}
|
|
556
603
|
|
|
557
604
|
_log('DEBUG', `recv kind=${frame.kind} session=${frame.session_id}`)
|
|
@@ -11,6 +11,7 @@
|
|
|
11
11
|
// prompt is actually typed. Subsequent turns reuse the running child.
|
|
12
12
|
|
|
13
13
|
import { createBridge, type IPCBridge } from './bridge.js'
|
|
14
|
+
import { getSessionId } from '../bootstrap/state.js'
|
|
14
15
|
import {
|
|
15
16
|
ingestManifestFrame,
|
|
16
17
|
waitForManifestSync,
|
|
@@ -36,7 +37,9 @@ let _pluginsModifiedThisSession = false
|
|
|
36
37
|
|
|
37
38
|
export function getOrCreateUmmayaBridge(): IPCBridge {
|
|
38
39
|
if (_bridge !== null) return _bridge
|
|
40
|
+
const sessionId = getUmmayaBridgeSessionId()
|
|
39
41
|
_bridge = createBridge({
|
|
42
|
+
sessionId,
|
|
40
43
|
// Epic ε #2296 T010 — route adapter_manifest_sync frames to the TS-side
|
|
41
44
|
// manifest cache on receipt (before any LLM turn, at backend boot time).
|
|
42
45
|
// FR-015: fires once per backend lifecycle; FR-016: replace-on-frame
|
|
@@ -69,7 +72,7 @@ export async function ensureUmmayaAdapterManifest(
|
|
|
69
72
|
|
|
70
73
|
export function getUmmayaBridgeSessionId(): string {
|
|
71
74
|
if (_sessionId === null) {
|
|
72
|
-
_sessionId =
|
|
75
|
+
_sessionId = getSessionId()
|
|
73
76
|
}
|
|
74
77
|
return _sessionId
|
|
75
78
|
}
|
|
@@ -104,4 +107,5 @@ export async function closeUmmayaBridge(): Promise<void> {
|
|
|
104
107
|
await b.close()
|
|
105
108
|
}
|
|
106
109
|
_pluginsModifiedThisSession = false
|
|
110
|
+
_sessionId = null
|
|
107
111
|
}
|
package/tui/src/ipc/codec.ts
CHANGED
|
@@ -158,7 +158,7 @@ const ToolCallFrameSchema = BaseFrame.extend({
|
|
|
158
158
|
})
|
|
159
159
|
|
|
160
160
|
const ToolResultEnvelopeSchema = z.object({
|
|
161
|
-
kind: z.enum(['find', 'locate', 'send', 'check']),
|
|
161
|
+
kind: z.enum(['find', 'locate', 'send', 'check', 'document']),
|
|
162
162
|
}).passthrough()
|
|
163
163
|
|
|
164
164
|
const ToolResultFrameSchema = BaseFrame.extend({
|
|
@@ -176,7 +176,7 @@ const WorkerStatusFrameSchema = BaseFrame.extend({
|
|
|
176
176
|
kind: z.literal('worker_status'),
|
|
177
177
|
worker_id: z.string(),
|
|
178
178
|
role_id: z.string(),
|
|
179
|
-
current_primitive: z.enum(['find', 'locate', 'send', 'check']),
|
|
179
|
+
current_primitive: z.enum(['find', 'locate', 'send', 'check', 'document']),
|
|
180
180
|
status: z.enum(['idle', 'running', 'waiting_permission', 'error']),
|
|
181
181
|
})
|
|
182
182
|
|
|
@@ -184,7 +184,7 @@ const PermissionRequestFrameSchema = BaseFrame.extend({
|
|
|
184
184
|
kind: z.literal('permission_request'),
|
|
185
185
|
request_id: z.string(),
|
|
186
186
|
worker_id: z.string(),
|
|
187
|
-
primitive_kind: z.enum(['find', 'locate', 'send', 'check']),
|
|
187
|
+
primitive_kind: z.enum(['find', 'locate', 'send', 'check', 'document']),
|
|
188
188
|
description_ko: z.string(),
|
|
189
189
|
description_en: z.string(),
|
|
190
190
|
risk_level: z.enum(['low', 'medium', 'high']),
|
|
@@ -381,7 +381,7 @@ export type CallId2 = string;
|
|
|
381
381
|
/**
|
|
382
382
|
* Primitive kind discriminator per Spec 031.
|
|
383
383
|
*/
|
|
384
|
-
export type Kind6 = 'find' | 'locate' | 'send' | 'check';
|
|
384
|
+
export type Kind6 = 'find' | 'locate' | 'send' | 'check' | 'document';
|
|
385
385
|
/**
|
|
386
386
|
* Opaque session identifier.
|
|
387
387
|
*/
|
|
@@ -461,7 +461,7 @@ export type RoleId = string;
|
|
|
461
461
|
/**
|
|
462
462
|
* Primitive currently being invoked by this worker.
|
|
463
463
|
*/
|
|
464
|
-
export type CurrentPrimitive = 'find' | 'locate' | 'send' | 'check';
|
|
464
|
+
export type CurrentPrimitive = 'find' | 'locate' | 'send' | 'check' | 'document';
|
|
465
465
|
/**
|
|
466
466
|
* Worker execution status.
|
|
467
467
|
*/
|
|
@@ -509,7 +509,7 @@ export type WorkerId1 = string;
|
|
|
509
509
|
/**
|
|
510
510
|
* The primitive the worker wants to invoke.
|
|
511
511
|
*/
|
|
512
|
-
export type PrimitiveKind = 'find' | 'locate' | 'send' | 'check';
|
|
512
|
+
export type PrimitiveKind = 'find' | 'locate' | 'send' | 'check' | 'document';
|
|
513
513
|
/**
|
|
514
514
|
* Korean-language description shown to the citizen.
|
|
515
515
|
*/
|
|
@@ -573,7 +573,7 @@ export type ReceiptId = string | null;
|
|
|
573
573
|
/**
|
|
574
574
|
* The primitive that was authorised. The TUI feeds this into `aalToLayer(primitive, isIrreversible)` to recompute the gauntlet layer (1=green / 2=orange / 3=red) for the receipt row. None on deny / timeout / legacy backends.
|
|
575
575
|
*/
|
|
576
|
-
export type PrimitiveKind1 = ('find' | 'locate' | 'send' | 'check') | null;
|
|
576
|
+
export type PrimitiveKind1 = ('find' | 'locate' | 'send' | 'check' | 'document') | null;
|
|
577
577
|
/**
|
|
578
578
|
* The fully-qualified adapter id (e.g. `mock_verify_mobile_id`, `mock_submit_welfare_grant`) the citizen authorised. The TUI uses this to render the human-readable Korean adapter name in /consent list and the modal title. None for non-adapter primitives (rare) or legacy backends.
|
|
579
579
|
*/
|
|
@@ -1200,7 +1200,7 @@ export type Name5 = string;
|
|
|
1200
1200
|
/**
|
|
1201
1201
|
* Primitive verb the adapter is registered under (I6).
|
|
1202
1202
|
*/
|
|
1203
|
-
export type Primitive = 'find' | 'send' | 'check' | 'locate';
|
|
1203
|
+
export type Primitive = 'find' | 'send' | 'check' | 'locate' | 'document';
|
|
1204
1204
|
/**
|
|
1205
1205
|
* Agency-published policy URL (HTTPS). None only when source_mode == 'internal' (I4/I5).
|
|
1206
1206
|
*/
|
|
@@ -1442,7 +1442,7 @@ export interface ToolDefinitionFunction {
|
|
|
1442
1442
|
* JSON Schema (Draft 2020-12) for the tool input. Pydantic accepts any dict shape; deeper schema validation is delegated to LLMClient.
|
|
1443
1443
|
*/
|
|
1444
1444
|
export interface Parameters {
|
|
1445
|
-
[k: string]:
|
|
1445
|
+
[k: string]: unknown;
|
|
1446
1446
|
}
|
|
1447
1447
|
/**
|
|
1448
1448
|
* backend -> TUI: streaming assistant text delta.
|
|
@@ -1527,7 +1527,7 @@ export interface ToolCallFrame {
|
|
|
1527
1527
|
* Tool-specific arguments. Concrete adapter calls carry adapter schema fields directly.
|
|
1528
1528
|
*/
|
|
1529
1529
|
export interface Arguments1 {
|
|
1530
|
-
[k: string]:
|
|
1530
|
+
[k: string]: unknown;
|
|
1531
1531
|
}
|
|
1532
1532
|
/**
|
|
1533
1533
|
* backend -> TUI (render): the output of a tool invocation.
|
|
@@ -1553,7 +1553,7 @@ export interface ToolResultFrame {
|
|
|
1553
1553
|
*/
|
|
1554
1554
|
export interface ToolResultEnvelope {
|
|
1555
1555
|
kind: Kind6;
|
|
1556
|
-
[k: string]:
|
|
1556
|
+
[k: string]: unknown;
|
|
1557
1557
|
}
|
|
1558
1558
|
/**
|
|
1559
1559
|
* backend -> TUI: Spec 027 coordinator phase update.
|
|
@@ -1663,7 +1663,7 @@ export interface SessionEventFrame {
|
|
|
1663
1663
|
* Event-specific payload. For list: {sessions: [{id, created_at, turn_count}]}. For resume: {id: str}. For others: {}.
|
|
1664
1664
|
*/
|
|
1665
1665
|
export interface Payload {
|
|
1666
|
-
[k: string]:
|
|
1666
|
+
[k: string]: unknown;
|
|
1667
1667
|
}
|
|
1668
1668
|
/**
|
|
1669
1669
|
* backend -> TUI: a backend error surfaced to the TUI for rendering.
|
|
@@ -1689,7 +1689,7 @@ export interface ErrorFrame {
|
|
|
1689
1689
|
* Structured error details. UMMAYA_* env var values MUST be redacted.
|
|
1690
1690
|
*/
|
|
1691
1691
|
export interface Details {
|
|
1692
|
-
[k: string]:
|
|
1692
|
+
[k: string]: unknown;
|
|
1693
1693
|
}
|
|
1694
1694
|
/**
|
|
1695
1695
|
* Begins a streamed payload (assistant output, tool result chunking).
|
|
@@ -2020,13 +2020,13 @@ export interface AdapterManifestEntry {
|
|
|
2020
2020
|
* Full backend Pydantic JSON Schema for adapter input parameters. Credential-only fields such as authKey must be omitted by adapters.
|
|
2021
2021
|
*/
|
|
2022
2022
|
export interface InputSchemaJson {
|
|
2023
|
-
[k: string]:
|
|
2023
|
+
[k: string]: unknown;
|
|
2024
2024
|
}
|
|
2025
2025
|
/**
|
|
2026
2026
|
* Full backend Pydantic JSON Schema for adapter output data.
|
|
2027
2027
|
*/
|
|
2028
2028
|
export interface OutputSchemaJson {
|
|
2029
|
-
[k: string]:
|
|
2029
|
+
[k: string]: unknown;
|
|
2030
2030
|
}
|
|
2031
2031
|
/**
|
|
2032
2032
|
* TUI -> backend: citizen requests revocation of a prior consent receipt.
|
package/tui/src/ipc/llmClient.ts
CHANGED
|
@@ -29,8 +29,13 @@ import type {
|
|
|
29
29
|
UmmayaContentBlockParam,
|
|
30
30
|
UmmayaStopReason,
|
|
31
31
|
} from './llmTypes.js'
|
|
32
|
+
import {
|
|
33
|
+
extractTextualToolCallProposals,
|
|
34
|
+
parseTrailingRawJsonToolCallProposal,
|
|
35
|
+
} from '../utils/rawJsonToolCall.js'
|
|
32
36
|
|
|
33
37
|
export const UMMAYA_DEFAULT_MODEL = 'LGAI-EXAONE/K-EXAONE-236B-A23B'
|
|
38
|
+
const TEXTUAL_TOOL_CALL_OPEN = '<tool_call>'
|
|
34
39
|
|
|
35
40
|
export type LLMClientErrorClass = 'llm' | 'tool' | 'network'
|
|
36
41
|
|
|
@@ -78,6 +83,9 @@ const _tracer = trace.getTracer('ummaya.tui.llm', '0.1.0')
|
|
|
78
83
|
interface _TurnAccumulator {
|
|
79
84
|
messageId: string | null
|
|
80
85
|
contentBlocks: UmmayaContentBlockParam[]
|
|
86
|
+
accumulatedText: string
|
|
87
|
+
emittedTextLength: number
|
|
88
|
+
shouldBufferTextDeltas: boolean
|
|
81
89
|
usage: UmmayaUsage
|
|
82
90
|
stopReason: UmmayaStopReason
|
|
83
91
|
/** Index of the current text block. It is opened lazily on the first
|
|
@@ -105,6 +113,9 @@ function _defaultAccumulator(): _TurnAccumulator {
|
|
|
105
113
|
return {
|
|
106
114
|
messageId: null,
|
|
107
115
|
contentBlocks: [],
|
|
116
|
+
accumulatedText: '',
|
|
117
|
+
emittedTextLength: 0,
|
|
118
|
+
shouldBufferTextDeltas: false,
|
|
108
119
|
usage: { input_tokens: 0, output_tokens: 0 },
|
|
109
120
|
stopReason: 'end_turn',
|
|
110
121
|
blockIndex: -1,
|
|
@@ -115,13 +126,21 @@ function _defaultAccumulator(): _TurnAccumulator {
|
|
|
115
126
|
}
|
|
116
127
|
}
|
|
117
128
|
|
|
129
|
+
function firstToolCallTextOffset(text: string): number {
|
|
130
|
+
const braceOffset = text.indexOf('{')
|
|
131
|
+
const tagOffset = text.indexOf(TEXTUAL_TOOL_CALL_OPEN)
|
|
132
|
+
if (braceOffset < 0) return tagOffset
|
|
133
|
+
if (tagOffset < 0) return braceOffset
|
|
134
|
+
return Math.min(braceOffset, tagOffset)
|
|
135
|
+
}
|
|
136
|
+
|
|
118
137
|
// ---------------------------------------------------------------------------
|
|
119
138
|
// Helper: extract usage from an AssistantChunkFrame done-trailer.
|
|
120
139
|
//
|
|
121
140
|
// Spec 032 does not currently define a typed usage payload on the frame itself;
|
|
122
141
|
// the Python backend is expected to embed usage counts in the frame's `trailer`
|
|
123
142
|
// extra fields or in a sibling ephemeral dict. Until the backend-side contract
|
|
124
|
-
// is finalised in Spec 032 US4, we read from
|
|
143
|
+
// is finalised in Spec 032 US4, we read from the typed legacy `usage` field first
|
|
125
144
|
// (a forward-compatible extension field the backend may include) and fall back
|
|
126
145
|
// to zeros. A TODO(T091) marks the binding point for the actual backend wiring.
|
|
127
146
|
// ---------------------------------------------------------------------------
|
|
@@ -417,6 +436,103 @@ export class LLMClient {
|
|
|
417
436
|
} satisfies UmmayaRawMessageStreamEvent
|
|
418
437
|
}
|
|
419
438
|
|
|
439
|
+
const appendVisibleTextDelta = function* (
|
|
440
|
+
text: string,
|
|
441
|
+
previousTextLength: number,
|
|
442
|
+
): Generator<UmmayaRawMessageStreamEvent, void, unknown> {
|
|
443
|
+
if (text.length === 0) return
|
|
444
|
+
yield* ensureTextBlock()
|
|
445
|
+
yield {
|
|
446
|
+
type: 'content_block_delta',
|
|
447
|
+
index: acc.blockIndex,
|
|
448
|
+
delta: { type: 'text_delta', text },
|
|
449
|
+
} satisfies UmmayaRawMessageStreamEvent
|
|
450
|
+
|
|
451
|
+
const existing = acc.contentBlocks[acc.blockIndex]
|
|
452
|
+
if (existing && existing.type === 'text') {
|
|
453
|
+
existing.text += text
|
|
454
|
+
} else {
|
|
455
|
+
acc.contentBlocks[acc.blockIndex] = { type: 'text', text }
|
|
456
|
+
}
|
|
457
|
+
acc.emittedTextLength = previousTextLength + text.length
|
|
458
|
+
}
|
|
459
|
+
|
|
460
|
+
const appendAssistantText = function* (
|
|
461
|
+
text: string,
|
|
462
|
+
): Generator<UmmayaRawMessageStreamEvent, void, unknown> {
|
|
463
|
+
if (text.length === 0) return
|
|
464
|
+
const previousTextLength = acc.accumulatedText.length
|
|
465
|
+
const bufferOffset = firstToolCallTextOffset(text)
|
|
466
|
+
const startsBuffering = !acc.shouldBufferTextDeltas && bufferOffset >= 0
|
|
467
|
+
if (startsBuffering) acc.shouldBufferTextDeltas = true
|
|
468
|
+
acc.accumulatedText += text
|
|
469
|
+
if (startsBuffering) {
|
|
470
|
+
if (bufferOffset > 0) {
|
|
471
|
+
yield* appendVisibleTextDelta(
|
|
472
|
+
text.slice(0, bufferOffset),
|
|
473
|
+
previousTextLength,
|
|
474
|
+
)
|
|
475
|
+
}
|
|
476
|
+
return
|
|
477
|
+
}
|
|
478
|
+
if (!acc.shouldBufferTextDeltas) {
|
|
479
|
+
yield* appendVisibleTextDelta(text, previousTextLength)
|
|
480
|
+
}
|
|
481
|
+
}
|
|
482
|
+
|
|
483
|
+
const flushBufferedText = function* (): Generator<
|
|
484
|
+
UmmayaRawMessageStreamEvent,
|
|
485
|
+
void,
|
|
486
|
+
unknown
|
|
487
|
+
> {
|
|
488
|
+
if (acc.accumulatedText.length <= acc.emittedTextLength) return
|
|
489
|
+
yield* appendVisibleTextDelta(
|
|
490
|
+
acc.accumulatedText.slice(acc.emittedTextLength),
|
|
491
|
+
acc.emittedTextLength,
|
|
492
|
+
)
|
|
493
|
+
}
|
|
494
|
+
|
|
495
|
+
const flushPreludeBeforeRawJsonToolUse = function* (
|
|
496
|
+
prelude: string,
|
|
497
|
+
): Generator<UmmayaRawMessageStreamEvent, void, unknown> {
|
|
498
|
+
if (prelude.length <= acc.emittedTextLength) return
|
|
499
|
+
yield* appendVisibleTextDelta(
|
|
500
|
+
prelude.slice(acc.emittedTextLength),
|
|
501
|
+
acc.emittedTextLength,
|
|
502
|
+
)
|
|
503
|
+
}
|
|
504
|
+
|
|
505
|
+
const appendRawJsonToolUseBlock = function* (params: {
|
|
506
|
+
readonly name: string
|
|
507
|
+
readonly input: Record<string, unknown>
|
|
508
|
+
readonly id?: string
|
|
509
|
+
}): Generator<UmmayaRawMessageStreamEvent, void, unknown> {
|
|
510
|
+
const toolBlockIndex = acc.contentBlocks.length
|
|
511
|
+
acc.toolBlockCounter += 1
|
|
512
|
+
const toolUseId = params.id ?? 'call_raw_json_tool_0'
|
|
513
|
+
yield {
|
|
514
|
+
type: 'content_block_start',
|
|
515
|
+
index: toolBlockIndex,
|
|
516
|
+
content_block: {
|
|
517
|
+
type: 'tool_use',
|
|
518
|
+
id: toolUseId,
|
|
519
|
+
name: params.name,
|
|
520
|
+
input: params.input,
|
|
521
|
+
},
|
|
522
|
+
} satisfies UmmayaRawMessageStreamEvent
|
|
523
|
+
yield {
|
|
524
|
+
type: 'content_block_stop',
|
|
525
|
+
index: toolBlockIndex,
|
|
526
|
+
} satisfies UmmayaRawMessageStreamEvent
|
|
527
|
+
acc.contentBlocks[toolBlockIndex] = {
|
|
528
|
+
type: 'tool_use',
|
|
529
|
+
id: toolUseId,
|
|
530
|
+
name: params.name,
|
|
531
|
+
input: params.input,
|
|
532
|
+
}
|
|
533
|
+
acc.stopReason = 'tool_use'
|
|
534
|
+
}
|
|
535
|
+
|
|
420
536
|
for await (const frame of this.bridge.frames()) {
|
|
421
537
|
// Filter: only process frames for this turn's correlation_id.
|
|
422
538
|
if (frame.correlation_id !== correlationId) continue
|
|
@@ -483,21 +599,7 @@ export class LLMClient {
|
|
|
483
599
|
|
|
484
600
|
// Emit text delta (even if delta is empty — forward compat).
|
|
485
601
|
if (chunk.delta.length > 0) {
|
|
486
|
-
yield*
|
|
487
|
-
yield {
|
|
488
|
-
type: 'content_block_delta',
|
|
489
|
-
index: acc.blockIndex,
|
|
490
|
-
delta: { type: 'text_delta', text: chunk.delta },
|
|
491
|
-
} satisfies UmmayaRawMessageStreamEvent
|
|
492
|
-
|
|
493
|
-
// Accumulate text into the content block for the final object.
|
|
494
|
-
const existing = acc.contentBlocks[acc.blockIndex]
|
|
495
|
-
if (existing && existing.type === 'text') {
|
|
496
|
-
existing.text += chunk.delta
|
|
497
|
-
} else {
|
|
498
|
-
// First delta for this block index.
|
|
499
|
-
acc.contentBlocks[acc.blockIndex] = { type: 'text', text: chunk.delta }
|
|
500
|
-
}
|
|
602
|
+
yield* appendAssistantText(chunk.delta)
|
|
501
603
|
}
|
|
502
604
|
} else {
|
|
503
605
|
// done=true: terminal chunk (V2 invariant satisfied here).
|
|
@@ -510,18 +612,37 @@ export class LLMClient {
|
|
|
510
612
|
|
|
511
613
|
// Emit any final delta text if present.
|
|
512
614
|
if (chunk.delta.length > 0) {
|
|
513
|
-
yield*
|
|
514
|
-
|
|
515
|
-
|
|
516
|
-
|
|
517
|
-
|
|
518
|
-
|
|
519
|
-
|
|
520
|
-
|
|
521
|
-
|
|
522
|
-
|
|
523
|
-
|
|
615
|
+
yield* appendAssistantText(chunk.delta)
|
|
616
|
+
}
|
|
617
|
+
|
|
618
|
+
const textualToolUse = extractTextualToolCallProposals({
|
|
619
|
+
text: acc.accumulatedText,
|
|
620
|
+
})
|
|
621
|
+
const rawJsonToolUse = textualToolUse === undefined
|
|
622
|
+
? parseTrailingRawJsonToolCallProposal({
|
|
623
|
+
text: acc.accumulatedText,
|
|
624
|
+
})
|
|
625
|
+
: undefined
|
|
626
|
+
if (textualToolUse !== undefined || rawJsonToolUse !== undefined) {
|
|
627
|
+
const prelude = textualToolUse?.text ?? rawJsonToolUse?.prelude ?? ''
|
|
628
|
+
yield* flushPreludeBeforeRawJsonToolUse(prelude)
|
|
629
|
+
yield* closeOpenBlock()
|
|
630
|
+
const proposals = textualToolUse?.proposals ??
|
|
631
|
+
(rawJsonToolUse !== undefined ? [rawJsonToolUse.proposal] : [])
|
|
632
|
+
for (let index = 0; index < proposals.length; index += 1) {
|
|
633
|
+
const proposal = proposals[index]
|
|
634
|
+
if (!proposal) continue
|
|
635
|
+
yield* appendRawJsonToolUseBlock({
|
|
636
|
+
name: proposal.name,
|
|
637
|
+
input: proposal.input,
|
|
638
|
+
id: textualToolUse !== undefined
|
|
639
|
+
? `call_textual_tool_${index}`
|
|
640
|
+
: 'call_raw_json_tool_0',
|
|
641
|
+
})
|
|
524
642
|
}
|
|
643
|
+
acc.accumulatedText = prelude
|
|
644
|
+
} else if (acc.shouldBufferTextDeltas) {
|
|
645
|
+
yield* flushBufferedText()
|
|
525
646
|
}
|
|
526
647
|
|
|
527
648
|
// Extract usage from the done-frame.
|
|
@@ -557,6 +678,9 @@ export class LLMClient {
|
|
|
557
678
|
else if (frame.kind === 'tool_call') {
|
|
558
679
|
const toolFrame = frame as ToolCallFrame
|
|
559
680
|
yield* ensureMessageStart(`tool-${correlationId}`)
|
|
681
|
+
if (acc.shouldBufferTextDeltas) {
|
|
682
|
+
yield* flushBufferedText()
|
|
683
|
+
}
|
|
560
684
|
yield* closeOpenBlock()
|
|
561
685
|
// tool_call frames may arrive interleaved with text streaming AND
|
|
562
686
|
// thinking streaming in a multi-turn / parallel-tool / K-EXAONE
|