@ouro.bot/cli 0.1.0-alpha.55 → 0.1.0-alpha.550
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 +133 -19
- package/RepairGuide.ouro/agent.json +5 -0
- package/RepairGuide.ouro/psyche/IDENTITY.md +19 -0
- package/RepairGuide.ouro/psyche/SOUL.md +55 -0
- package/RepairGuide.ouro/skills/diagnose-bootstrap-drift.md +54 -0
- package/RepairGuide.ouro/skills/diagnose-broken-remote.md +63 -0
- package/RepairGuide.ouro/skills/diagnose-stacked-typed-issues.md +35 -0
- package/RepairGuide.ouro/skills/diagnose-sync-blocked.md +54 -0
- package/RepairGuide.ouro/skills/diagnose-vault-expired.md +60 -0
- package/{AdoptionSpecialist.ouro → SerpentGuide.ouro}/agent.json +4 -2
- package/{AdoptionSpecialist.ouro → SerpentGuide.ouro}/psyche/SOUL.md +2 -2
- package/{AdoptionSpecialist.ouro → SerpentGuide.ouro}/psyche/identities/the-serpent.md +1 -1
- package/changelog.json +3555 -0
- package/dist/arc/attention-types.js +8 -0
- package/dist/arc/cares.js +140 -0
- package/dist/arc/episodes.js +117 -0
- package/dist/arc/intentions.js +133 -0
- package/dist/arc/json-store.js +117 -0
- package/dist/arc/obligations.js +237 -0
- package/dist/arc/packets.js +193 -0
- package/dist/arc/presence.js +185 -0
- package/dist/arc/task-lifecycle.js +65 -0
- package/dist/heart/active-work.js +837 -26
- package/dist/heart/agent-entry.js +58 -3
- package/dist/heart/attachments/image-normalize.js +194 -0
- package/dist/heart/attachments/materialize.js +97 -0
- package/dist/heart/attachments/originals.js +88 -0
- package/dist/heart/attachments/render.js +29 -0
- package/dist/heart/attachments/sources/adapter.js +2 -0
- package/dist/heart/attachments/sources/bluebubbles.js +156 -0
- package/dist/heart/attachments/sources/cli-local-file.js +78 -0
- package/dist/heart/attachments/sources/index.js +16 -0
- package/dist/heart/attachments/store.js +103 -0
- package/dist/heart/attachments/types.js +93 -0
- package/dist/heart/auth/auth-flow.js +479 -0
- package/dist/heart/background-operations.js +281 -0
- package/dist/heart/bundle-state.js +168 -0
- package/dist/heart/commitments.js +111 -0
- package/dist/heart/config-registry.js +304 -0
- package/dist/heart/config.js +114 -118
- package/dist/heart/core.js +925 -246
- package/dist/heart/cross-chat-delivery.js +3 -18
- package/dist/heart/daemon/agent-config-check.js +512 -0
- package/dist/heart/daemon/agent-discovery.js +102 -3
- package/dist/heart/daemon/agent-service.js +522 -0
- package/dist/heart/daemon/agentic-repair.js +554 -0
- package/dist/heart/daemon/bluebubbles-health-diagnostics.js +122 -0
- package/dist/heart/daemon/boot-sync-probe.js +197 -0
- package/dist/heart/daemon/cadence.js +70 -0
- package/dist/heart/daemon/cli-defaults.js +665 -0
- package/dist/heart/daemon/cli-exec.js +7565 -0
- package/dist/heart/daemon/cli-help.js +498 -0
- package/dist/heart/daemon/cli-parse.js +1590 -0
- package/dist/heart/daemon/cli-render-doctor.js +57 -0
- package/dist/heart/daemon/cli-render.js +775 -0
- package/dist/heart/daemon/cli-types.js +8 -0
- package/dist/heart/daemon/connect-bay.js +323 -0
- package/dist/heart/daemon/daemon-cli.js +29 -1672
- package/dist/heart/daemon/daemon-entry.js +417 -2
- package/dist/heart/daemon/daemon-health.js +183 -0
- package/dist/heart/daemon/daemon-rollup.js +58 -0
- package/dist/heart/daemon/daemon-runtime-sync.js +87 -13
- package/dist/heart/daemon/daemon-tombstone.js +236 -0
- package/dist/heart/daemon/daemon.js +758 -71
- package/dist/heart/daemon/dns-workflow.js +394 -0
- package/dist/heart/daemon/doctor-types.js +8 -0
- package/dist/heart/daemon/doctor.js +844 -0
- package/dist/heart/daemon/drift-detection.js +146 -0
- package/dist/heart/daemon/health-monitor.js +122 -1
- package/dist/heart/daemon/hooks/agent-config-v2.js +33 -0
- package/dist/heart/daemon/hooks/bundle-meta.js +115 -1
- package/dist/heart/daemon/http-health-probe.js +80 -0
- package/dist/heart/daemon/human-command-screens.js +234 -0
- package/dist/heart/daemon/human-readiness.js +114 -0
- package/dist/heart/daemon/inner-status.js +102 -0
- package/dist/heart/daemon/interactive-repair.js +394 -0
- package/dist/heart/daemon/launchd.js +37 -8
- package/dist/heart/daemon/log-tailer.js +82 -12
- package/dist/heart/daemon/logs-prune.js +110 -0
- package/dist/heart/daemon/mcp-canary.js +297 -0
- package/dist/heart/daemon/message-router.js +2 -2
- package/dist/heart/daemon/os-cron-deps.js +135 -0
- package/dist/heart/daemon/os-cron.js +14 -12
- package/dist/heart/daemon/ouro-bot-entry.js +4 -2
- package/dist/heart/daemon/ouro-entry.js +3 -1
- package/dist/heart/daemon/process-manager.js +375 -33
- package/dist/heart/daemon/provider-discovery.js +137 -0
- package/dist/heart/daemon/provider-ping-progress.js +83 -0
- package/dist/heart/daemon/pulse.js +475 -0
- package/dist/heart/daemon/readiness-repair.js +365 -0
- package/dist/heart/daemon/run-hooks.js +2 -0
- package/dist/heart/daemon/runtime-logging.js +67 -16
- package/dist/heart/daemon/runtime-metadata.js +3 -31
- package/dist/heart/daemon/safe-mode.js +161 -0
- package/dist/heart/daemon/sense-manager.js +353 -38
- package/dist/heart/daemon/session-id-resolver.js +131 -0
- package/dist/heart/daemon/skill-management-installer.js +94 -0
- package/dist/heart/daemon/socket-client.js +158 -11
- package/dist/heart/daemon/stale-bundle-prune.js +96 -0
- package/dist/heart/daemon/startup-tui.js +330 -0
- package/dist/heart/daemon/task-scheduler.js +3 -25
- package/dist/heart/daemon/terminal-ui.js +499 -0
- package/dist/heart/daemon/thoughts.js +162 -17
- package/dist/heart/daemon/up-progress.js +366 -0
- package/dist/heart/daemon/vault-items.js +56 -0
- package/dist/heart/delegation.js +1 -1
- package/dist/heart/habits/habit-migration.js +189 -0
- package/dist/heart/habits/habit-parser.js +140 -0
- package/dist/heart/habits/habit-runtime-state.js +100 -0
- package/dist/heart/habits/habit-scheduler.js +372 -0
- package/dist/heart/{daemon → hatch}/hatch-flow.js +52 -117
- package/dist/heart/{daemon → hatch}/hatch-specialist.js +6 -8
- package/dist/heart/{daemon → hatch}/specialist-prompt.js +12 -9
- package/dist/heart/{daemon → hatch}/specialist-tools.js +35 -12
- package/dist/heart/identity.js +200 -51
- package/dist/heart/kept-notes.js +357 -0
- package/dist/heart/kicks.js +1 -1
- package/dist/heart/machine-identity.js +161 -0
- package/dist/heart/mail-import-discovery.js +353 -0
- package/dist/heart/mailbox/mailbox-http-hooks.js +66 -0
- package/dist/heart/mailbox/mailbox-http-response.js +7 -0
- package/dist/heart/mailbox/mailbox-http-routes.js +246 -0
- package/dist/heart/mailbox/mailbox-http-static.js +103 -0
- package/dist/heart/mailbox/mailbox-http-transport.js +116 -0
- package/dist/heart/mailbox/mailbox-http.js +99 -0
- package/dist/heart/mailbox/mailbox-read.js +31 -0
- package/dist/heart/mailbox/mailbox-types.js +27 -0
- package/dist/heart/mailbox/mailbox-view.js +195 -0
- package/dist/heart/mailbox/readers/agent-machine.js +382 -0
- package/dist/heart/mailbox/readers/continuity-readers.js +338 -0
- package/dist/heart/mailbox/readers/mail.js +362 -0
- package/dist/heart/mailbox/readers/runtime-readers.js +651 -0
- package/dist/heart/mailbox/readers/sessions.js +232 -0
- package/dist/heart/mailbox/readers/shared.js +111 -0
- package/dist/heart/mcp/mcp-server.js +683 -0
- package/dist/heart/migrate-config.js +100 -0
- package/dist/heart/model-capabilities.js +19 -0
- package/dist/heart/platform.js +81 -0
- package/dist/heart/provider-attempt.js +134 -0
- package/dist/heart/provider-binding-resolver.js +255 -0
- package/dist/heart/provider-credentials.js +425 -0
- package/dist/heart/provider-failover.js +301 -0
- package/dist/heart/provider-models.js +81 -0
- package/dist/heart/provider-ping.js +262 -0
- package/dist/heart/provider-state.js +216 -0
- package/dist/heart/provider-visibility.js +188 -0
- package/dist/heart/providers/anthropic-token.js +131 -0
- package/dist/heart/providers/anthropic.js +139 -52
- package/dist/heart/providers/azure.js +97 -13
- package/dist/heart/providers/error-classification.js +127 -0
- package/dist/heart/providers/github-copilot.js +145 -0
- package/dist/heart/providers/minimax-vlm.js +189 -0
- package/dist/heart/providers/minimax.js +26 -8
- package/dist/heart/providers/openai-codex.js +55 -40
- package/dist/heart/runtime-capability-check.js +170 -0
- package/dist/heart/runtime-credentials.js +367 -0
- package/dist/heart/runtime-cwd.js +87 -0
- package/dist/heart/sense-truth.js +11 -4
- package/dist/heart/session-activity.js +43 -22
- package/dist/heart/session-events.js +1149 -0
- package/dist/heart/session-playback-cli-main.js +5 -0
- package/dist/heart/session-playback-cli.js +36 -0
- package/dist/heart/session-playback.js +231 -0
- package/dist/heart/session-stats-cli-main.js +5 -0
- package/dist/heart/session-stats.js +182 -0
- package/dist/heart/session-transcript.js +243 -0
- package/dist/heart/start-of-turn-packet.js +345 -0
- package/dist/heart/streaming.js +44 -27
- package/dist/heart/sync-classification.js +176 -0
- package/dist/heart/sync.js +449 -0
- package/dist/heart/target-resolution.js +9 -5
- package/dist/heart/tempo.js +93 -0
- package/dist/heart/temporal-view.js +41 -0
- package/dist/heart/timeouts.js +101 -0
- package/dist/heart/tool-activity-callbacks.js +59 -0
- package/dist/heart/tool-description.js +139 -0
- package/dist/heart/tool-friction.js +55 -0
- package/dist/heart/tool-loop.js +200 -0
- package/dist/heart/turn-context.js +381 -0
- package/dist/heart/{daemon → versioning}/ouro-bot-global-installer.js +6 -5
- package/dist/heart/{daemon → versioning}/ouro-bot-wrapper.js +1 -1
- package/dist/heart/versioning/ouro-path-installer.js +426 -0
- package/dist/heart/versioning/ouro-version-manager.js +295 -0
- package/dist/heart/{daemon → versioning}/staged-restart.js +40 -8
- package/dist/heart/{daemon → versioning}/update-checker.js +6 -1
- package/dist/heart/{daemon → versioning}/update-hooks.js +63 -59
- package/dist/mailbox-ui/assets/index-BPr5vNuM.css +1 -0
- package/dist/mailbox-ui/assets/index-Cm51CY9W.js +61 -0
- package/dist/mailbox-ui/index.html +15 -0
- package/dist/mailroom/attention.js +167 -0
- package/dist/mailroom/autonomy.js +209 -0
- package/dist/mailroom/blob-store.js +674 -0
- package/dist/mailroom/body-cache.js +61 -0
- package/dist/mailroom/core.js +720 -0
- package/dist/mailroom/entry.js +160 -0
- package/dist/mailroom/file-store.js +430 -0
- package/dist/mailroom/mbox-import.js +383 -0
- package/dist/mailroom/outbound.js +380 -0
- package/dist/mailroom/policy.js +263 -0
- package/dist/mailroom/reader.js +233 -0
- package/dist/mailroom/search-cache.js +256 -0
- package/dist/mailroom/search-relevance.js +319 -0
- package/dist/mailroom/smtp-ingress.js +176 -0
- package/dist/mailroom/source-state.js +176 -0
- package/dist/mailroom/thread.js +109 -0
- package/dist/mailroom/travel-extract.js +89 -0
- package/dist/mind/bundle-manifest.js +7 -1
- package/dist/mind/context.js +165 -101
- package/dist/mind/diary-integrity.js +60 -0
- package/dist/mind/{memory.js → diary.js} +62 -75
- package/dist/mind/embedding-provider.js +60 -0
- package/dist/mind/file-state.js +179 -0
- package/dist/mind/friends/channel.js +30 -0
- package/dist/mind/friends/resolver.js +54 -2
- package/dist/mind/friends/store-file.js +39 -3
- package/dist/mind/friends/types.js +2 -2
- package/dist/mind/journal-index.js +161 -0
- package/dist/mind/note-search.js +268 -0
- package/dist/mind/obligation-steering.js +221 -0
- package/dist/mind/pending.js +4 -0
- package/dist/mind/prompt-refresh.js +3 -2
- package/dist/mind/prompt.js +995 -123
- package/dist/mind/provenance-trust.js +26 -0
- package/dist/mind/scrutiny.js +173 -0
- package/dist/nerves/cli-logging.js +7 -1
- package/dist/nerves/coverage/audit-rules.js +15 -6
- package/dist/nerves/coverage/audit.js +28 -2
- package/dist/nerves/coverage/cli.js +1 -1
- package/dist/nerves/coverage/contract.js +5 -5
- package/dist/nerves/coverage/file-completeness.js +139 -5
- package/dist/nerves/coverage/run-artifacts.js +1 -1
- package/dist/nerves/event-buffer.js +111 -0
- package/dist/nerves/index.js +224 -4
- package/dist/nerves/observation.js +20 -0
- package/dist/nerves/redact.js +79 -0
- package/dist/nerves/review/cli-main.js +5 -0
- package/dist/nerves/review/cli.js +156 -0
- package/dist/nerves/review/core.js +152 -0
- package/dist/nerves/runtime.js +5 -1
- package/dist/repertoire/ado-client.js +15 -56
- package/dist/repertoire/ado-semantic.js +11 -10
- package/dist/repertoire/api-client.js +97 -0
- package/dist/repertoire/bitwarden-store.js +816 -0
- package/dist/repertoire/bundle-templates.js +72 -0
- package/dist/repertoire/bw-installer.js +180 -0
- package/dist/repertoire/coding/codex-jsonl.js +64 -0
- package/dist/repertoire/coding/context-pack.js +330 -0
- package/dist/repertoire/coding/feedback.js +197 -30
- package/dist/repertoire/coding/manager.js +158 -9
- package/dist/repertoire/coding/spawner.js +55 -9
- package/dist/repertoire/coding/tools.js +170 -7
- package/dist/repertoire/commerce-errors.js +109 -0
- package/dist/repertoire/commerce-self-test.js +156 -0
- package/dist/repertoire/credential-access.js +111 -0
- package/dist/repertoire/duffel-client.js +185 -0
- package/dist/repertoire/github-client.js +14 -55
- package/dist/repertoire/graph-client.js +11 -52
- package/dist/repertoire/guardrails.js +396 -0
- package/dist/repertoire/mcp-client.js +295 -0
- package/dist/repertoire/mcp-manager.js +362 -0
- package/dist/repertoire/mcp-tools.js +63 -0
- package/dist/repertoire/shell-sessions.js +133 -0
- package/dist/repertoire/skills.js +15 -24
- package/dist/repertoire/stripe-client.js +131 -0
- package/dist/repertoire/tasks/board.js +31 -5
- package/dist/repertoire/tasks/fix.js +182 -0
- package/dist/repertoire/tasks/index.js +16 -4
- package/dist/repertoire/tasks/lifecycle.js +2 -2
- package/dist/repertoire/tasks/parser.js +3 -2
- package/dist/repertoire/tasks/scanner.js +194 -37
- package/dist/repertoire/tasks/transitions.js +16 -78
- package/dist/repertoire/tool-results.js +29 -0
- package/dist/repertoire/tools-attachments.js +317 -0
- package/dist/repertoire/tools-base.js +47 -1075
- package/dist/repertoire/tools-bluebubbles.js +1 -0
- package/dist/repertoire/tools-bridge.js +142 -0
- package/dist/repertoire/tools-bundle.js +984 -0
- package/dist/repertoire/tools-config.js +185 -0
- package/dist/repertoire/tools-continuity.js +248 -0
- package/dist/repertoire/tools-credential.js +381 -0
- package/dist/repertoire/tools-files.js +342 -0
- package/dist/repertoire/tools-flight.js +224 -0
- package/dist/repertoire/tools-flow.js +119 -0
- package/dist/repertoire/tools-github.js +1 -7
- package/dist/repertoire/tools-mail.js +1857 -0
- package/dist/repertoire/tools-notes.js +421 -0
- package/dist/repertoire/tools-session.js +750 -0
- package/dist/repertoire/tools-shell.js +120 -0
- package/dist/repertoire/tools-stripe.js +180 -0
- package/dist/repertoire/tools-surface.js +243 -0
- package/dist/repertoire/tools-teams.js +9 -39
- package/dist/repertoire/tools-travel.js +125 -0
- package/dist/repertoire/tools-trip.js +604 -0
- package/dist/repertoire/tools-user-profile.js +144 -0
- package/dist/repertoire/tools-vault.js +40 -0
- package/dist/repertoire/tools.js +108 -100
- package/dist/repertoire/travel-api-client.js +360 -0
- package/dist/repertoire/user-profile.js +131 -0
- package/dist/repertoire/vault-setup.js +246 -0
- package/dist/repertoire/vault-unlock.js +561 -0
- package/dist/scripts/claude-code-hook.js +41 -0
- package/dist/scripts/claude-code-stop-hook.js +47 -0
- package/dist/senses/attention-queue.js +116 -0
- package/dist/senses/bluebubbles/active-turns.js +216 -0
- package/dist/senses/bluebubbles/attachment-cache.js +53 -0
- package/dist/senses/bluebubbles/attachment-download.js +137 -0
- package/dist/senses/{bluebubbles-client.js → bluebubbles/client.js} +219 -18
- package/dist/senses/bluebubbles/entry.js +77 -0
- package/dist/senses/{bluebubbles-inbound-log.js → bluebubbles/inbound-log.js} +20 -3
- package/dist/senses/bluebubbles/index.js +2305 -0
- package/dist/senses/{bluebubbles-media.js → bluebubbles/media.js} +121 -70
- package/dist/senses/{bluebubbles-model.js → bluebubbles/model.js} +33 -12
- package/dist/senses/{bluebubbles-mutation-log.js → bluebubbles/mutation-log.js} +3 -3
- package/dist/senses/bluebubbles/processed-log.js +133 -0
- package/dist/senses/bluebubbles/replay.js +137 -0
- package/dist/senses/{bluebubbles-runtime-state.js → bluebubbles/runtime-state.js} +30 -2
- package/dist/senses/{bluebubbles-session-cleanup.js → bluebubbles/session-cleanup.js} +1 -1
- package/dist/senses/cli/bracketed-paste.js +82 -0
- package/dist/senses/cli/image-paste.js +287 -0
- package/dist/senses/cli/image-ref-navigation.js +75 -0
- package/dist/senses/cli/ink-app.js +156 -0
- package/dist/senses/cli/inline-diff.js +64 -0
- package/dist/senses/cli/input-keys.js +174 -0
- package/dist/senses/cli/kill-ring.js +86 -0
- package/dist/senses/cli/message-list.js +51 -0
- package/dist/senses/cli/ouro-tui.js +607 -0
- package/dist/senses/cli/spinner-imperative.js +135 -0
- package/dist/senses/cli/spinner.js +101 -0
- package/dist/senses/cli/status-line.js +60 -0
- package/dist/senses/cli/streaming-markdown.js +526 -0
- package/dist/senses/cli/tool-display.js +85 -0
- package/dist/senses/cli/tool-render.js +85 -0
- package/dist/senses/cli/tui-store.js +240 -0
- package/dist/senses/cli/virtual-list.js +35 -0
- package/dist/senses/cli-entry.js +60 -8
- package/dist/senses/cli-layout.js +187 -0
- package/dist/senses/cli.js +520 -209
- package/dist/senses/commands.js +66 -3
- package/dist/senses/habit-turn-message.js +108 -0
- package/dist/senses/inner-dialog-worker.js +175 -21
- package/dist/senses/inner-dialog.js +330 -27
- package/dist/senses/mail-entry.js +66 -0
- package/dist/senses/mail.js +379 -0
- package/dist/senses/pipeline.js +569 -182
- package/dist/senses/proactive-content-guard.js +51 -0
- package/dist/senses/shared-turn.js +248 -0
- package/dist/senses/surface-tool.js +68 -0
- package/dist/senses/teams-entry.js +60 -8
- package/dist/senses/teams.js +387 -98
- package/dist/senses/trust-gate.js +100 -5
- package/dist/trips/core.js +138 -0
- package/dist/trips/store.js +146 -0
- package/package.json +38 -7
- package/skills/agent-commerce.md +106 -0
- package/skills/browser-navigation.md +117 -0
- package/skills/commerce-setup-guide.md +116 -0
- package/skills/commerce-setup.md +84 -0
- package/skills/configure-dev-tools.md +101 -0
- package/skills/travel-planning.md +138 -0
- package/dist/heart/daemon/ouro-path-installer.js +0 -178
- package/dist/heart/daemon/subagent-installer.js +0 -166
- package/dist/heart/session-recall.js +0 -116
- package/dist/mind/associative-recall.js +0 -209
- package/dist/senses/bluebubbles-entry.js +0 -13
- package/dist/senses/bluebubbles.js +0 -1177
- package/dist/senses/debug-activity.js +0 -148
- package/subagents/README.md +0 -86
- package/subagents/work-doer.md +0 -237
- package/subagents/work-merger.md +0 -618
- package/subagents/work-planner.md +0 -390
- /package/{AdoptionSpecialist.ouro → SerpentGuide.ouro}/psyche/identities/basilisk.md +0 -0
- /package/{AdoptionSpecialist.ouro → SerpentGuide.ouro}/psyche/identities/jafar.md +0 -0
- /package/{AdoptionSpecialist.ouro → SerpentGuide.ouro}/psyche/identities/jormungandr.md +0 -0
- /package/{AdoptionSpecialist.ouro → SerpentGuide.ouro}/psyche/identities/kaa.md +0 -0
- /package/{AdoptionSpecialist.ouro → SerpentGuide.ouro}/psyche/identities/medusa.md +0 -0
- /package/{AdoptionSpecialist.ouro → SerpentGuide.ouro}/psyche/identities/monty.md +0 -0
- /package/{AdoptionSpecialist.ouro → SerpentGuide.ouro}/psyche/identities/nagini.md +0 -0
- /package/{AdoptionSpecialist.ouro → SerpentGuide.ouro}/psyche/identities/ouroboros.md +0 -0
- /package/{AdoptionSpecialist.ouro → SerpentGuide.ouro}/psyche/identities/python.md +0 -0
- /package/{AdoptionSpecialist.ouro → SerpentGuide.ouro}/psyche/identities/quetzalcoatl.md +0 -0
- /package/{AdoptionSpecialist.ouro → SerpentGuide.ouro}/psyche/identities/sir-hiss.md +0 -0
- /package/{AdoptionSpecialist.ouro → SerpentGuide.ouro}/psyche/identities/the-snake.md +0 -0
- /package/dist/heart/{daemon → hatch}/hatch-animation.js +0 -0
- /package/dist/heart/{daemon → hatch}/specialist-orchestrator.js +0 -0
- /package/dist/heart/{daemon → versioning}/ouro-uti.js +0 -0
- /package/dist/heart/{daemon → versioning}/wrapper-publish-guard.js +0 -0
|
@@ -38,31 +38,16 @@ async function deliverCrossChatMessage(request, deps) {
|
|
|
38
38
|
authorizingTrustLevel: request.authorizingSession?.trustLevel ?? null,
|
|
39
39
|
},
|
|
40
40
|
});
|
|
41
|
-
if (request.intent
|
|
42
|
-
const result = queueForLater(request, deps, "generic outreach stays queued until the target session is next active");
|
|
43
|
-
(0, runtime_1.emitNervesEvent)({
|
|
44
|
-
component: "engine",
|
|
45
|
-
event: "engine.cross_chat_delivery_end",
|
|
46
|
-
message: "queued generic outreach for later delivery",
|
|
47
|
-
meta: {
|
|
48
|
-
friendId: request.friendId,
|
|
49
|
-
channel: request.channel,
|
|
50
|
-
key: request.key,
|
|
51
|
-
status: result.status,
|
|
52
|
-
},
|
|
53
|
-
});
|
|
54
|
-
return result;
|
|
55
|
-
}
|
|
56
|
-
if (!isExplicitlyAuthorized(request)) {
|
|
41
|
+
if (!isExplicitlyAuthorized(request) && request.intent !== "generic_outreach") {
|
|
57
42
|
const result = {
|
|
58
43
|
status: "blocked",
|
|
59
|
-
detail: "
|
|
44
|
+
detail: "cross-chat delivery requires a trusted asking session or generic outreach intent",
|
|
60
45
|
};
|
|
61
46
|
(0, runtime_1.emitNervesEvent)({
|
|
62
47
|
level: "warn",
|
|
63
48
|
component: "engine",
|
|
64
49
|
event: "engine.cross_chat_delivery_end",
|
|
65
|
-
message: "blocked
|
|
50
|
+
message: "blocked cross-chat delivery",
|
|
66
51
|
meta: {
|
|
67
52
|
friendId: request.friendId,
|
|
68
53
|
channel: request.channel,
|
|
@@ -0,0 +1,512 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
|
|
3
|
+
if (k2 === undefined) k2 = k;
|
|
4
|
+
var desc = Object.getOwnPropertyDescriptor(m, k);
|
|
5
|
+
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
|
|
6
|
+
desc = { enumerable: true, get: function() { return m[k]; } };
|
|
7
|
+
}
|
|
8
|
+
Object.defineProperty(o, k2, desc);
|
|
9
|
+
}) : (function(o, m, k, k2) {
|
|
10
|
+
if (k2 === undefined) k2 = k;
|
|
11
|
+
o[k2] = m[k];
|
|
12
|
+
}));
|
|
13
|
+
var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
|
|
14
|
+
Object.defineProperty(o, "default", { enumerable: true, value: v });
|
|
15
|
+
}) : function(o, v) {
|
|
16
|
+
o["default"] = v;
|
|
17
|
+
});
|
|
18
|
+
var __importStar = (this && this.__importStar) || (function () {
|
|
19
|
+
var ownKeys = function(o) {
|
|
20
|
+
ownKeys = Object.getOwnPropertyNames || function (o) {
|
|
21
|
+
var ar = [];
|
|
22
|
+
for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
|
|
23
|
+
return ar;
|
|
24
|
+
};
|
|
25
|
+
return ownKeys(o);
|
|
26
|
+
};
|
|
27
|
+
return function (mod) {
|
|
28
|
+
if (mod && mod.__esModule) return mod;
|
|
29
|
+
var result = {};
|
|
30
|
+
if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
|
|
31
|
+
__setModuleDefault(result, mod);
|
|
32
|
+
return result;
|
|
33
|
+
};
|
|
34
|
+
})();
|
|
35
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
36
|
+
exports.vaultUnlockOrRecoverFix = vaultUnlockOrRecoverFix;
|
|
37
|
+
exports.checkAgentConfig = checkAgentConfig;
|
|
38
|
+
exports.checkAgentConfigWithProviderHealth = checkAgentConfigWithProviderHealth;
|
|
39
|
+
const fs = __importStar(require("fs"));
|
|
40
|
+
const path = __importStar(require("path"));
|
|
41
|
+
const identity_1 = require("../identity");
|
|
42
|
+
const runtime_1 = require("../../nerves/runtime");
|
|
43
|
+
const provider_models_1 = require("../provider-models");
|
|
44
|
+
const machine_identity_1 = require("../machine-identity");
|
|
45
|
+
const provider_state_1 = require("../provider-state");
|
|
46
|
+
const provider_credentials_1 = require("../provider-credentials");
|
|
47
|
+
const vault_unlock_1 = require("../../repertoire/vault-unlock");
|
|
48
|
+
const readiness_repair_1 = require("./readiness-repair");
|
|
49
|
+
const provider_ping_progress_1 = require("./provider-ping-progress");
|
|
50
|
+
const drift_detection_1 = require("./drift-detection");
|
|
51
|
+
function isAgentProvider(value) {
|
|
52
|
+
return Object.prototype.hasOwnProperty.call(identity_1.PROVIDER_CREDENTIALS, value);
|
|
53
|
+
}
|
|
54
|
+
function agentRootFor(agentName, bundlesRoot) {
|
|
55
|
+
return path.join(bundlesRoot, `${agentName}.ouro`);
|
|
56
|
+
}
|
|
57
|
+
function configPathFor(agentName, bundlesRoot) {
|
|
58
|
+
return path.join(agentRootFor(agentName, bundlesRoot), "agent.json");
|
|
59
|
+
}
|
|
60
|
+
function resolveFacingProvider(parsed, facing, agentName, agentJsonPath) {
|
|
61
|
+
const raw = parsed[facing];
|
|
62
|
+
if (!raw || typeof raw !== "object" || Array.isArray(raw)) {
|
|
63
|
+
return {
|
|
64
|
+
ok: false,
|
|
65
|
+
result: {
|
|
66
|
+
ok: false,
|
|
67
|
+
error: `agent.json for '${agentName}' is missing ${facing}.provider`,
|
|
68
|
+
fix: `Add ${facing}: { provider, model } to ${agentJsonPath}. Valid providers: ${Object.keys(identity_1.PROVIDER_CREDENTIALS).join(", ")}`,
|
|
69
|
+
},
|
|
70
|
+
};
|
|
71
|
+
}
|
|
72
|
+
const provider = raw.provider;
|
|
73
|
+
if (typeof provider !== "string" || provider.length === 0) {
|
|
74
|
+
return {
|
|
75
|
+
ok: false,
|
|
76
|
+
result: {
|
|
77
|
+
ok: false,
|
|
78
|
+
error: `agent.json for '${agentName}' is missing ${facing}.provider`,
|
|
79
|
+
fix: `Set ${facing}.provider in ${agentJsonPath}. Valid providers: ${Object.keys(identity_1.PROVIDER_CREDENTIALS).join(", ")}`,
|
|
80
|
+
},
|
|
81
|
+
};
|
|
82
|
+
}
|
|
83
|
+
if (!isAgentProvider(provider)) {
|
|
84
|
+
return {
|
|
85
|
+
ok: false,
|
|
86
|
+
result: {
|
|
87
|
+
ok: false,
|
|
88
|
+
error: `Unknown provider '${provider}' in ${facing}.provider for '${agentName}'`,
|
|
89
|
+
fix: `Set ${facing}.provider to one of: ${Object.keys(identity_1.PROVIDER_CREDENTIALS).join(", ")}`,
|
|
90
|
+
},
|
|
91
|
+
};
|
|
92
|
+
}
|
|
93
|
+
return { ok: true, selected: { facing, provider } };
|
|
94
|
+
}
|
|
95
|
+
function readAgentConfigForProviderState(agentName, bundlesRoot) {
|
|
96
|
+
const agentJsonPath = configPathFor(agentName, bundlesRoot);
|
|
97
|
+
let raw;
|
|
98
|
+
try {
|
|
99
|
+
raw = fs.readFileSync(agentJsonPath, "utf-8");
|
|
100
|
+
}
|
|
101
|
+
catch {
|
|
102
|
+
return {
|
|
103
|
+
ok: false,
|
|
104
|
+
result: {
|
|
105
|
+
ok: false,
|
|
106
|
+
error: `agent.json not found at ${agentJsonPath}`,
|
|
107
|
+
fix: `Run 'ouro hatch ${agentName}' to create the agent bundle, or verify that ${bundlesRoot}/${agentName}.ouro/ exists.`,
|
|
108
|
+
},
|
|
109
|
+
};
|
|
110
|
+
}
|
|
111
|
+
let parsed;
|
|
112
|
+
try {
|
|
113
|
+
parsed = JSON.parse(raw);
|
|
114
|
+
}
|
|
115
|
+
catch {
|
|
116
|
+
return {
|
|
117
|
+
ok: false,
|
|
118
|
+
result: {
|
|
119
|
+
ok: false,
|
|
120
|
+
error: `agent.json at ${agentJsonPath} contains invalid JSON`,
|
|
121
|
+
fix: `Open ${agentJsonPath} and fix the JSON syntax.`,
|
|
122
|
+
},
|
|
123
|
+
};
|
|
124
|
+
}
|
|
125
|
+
if (parsed.enabled === false) {
|
|
126
|
+
return { ok: true, disabled: true, agentJsonPath, parsed };
|
|
127
|
+
}
|
|
128
|
+
return { ok: true, disabled: false, agentJsonPath, parsed };
|
|
129
|
+
}
|
|
130
|
+
function readFacingForBootstrap(parsed, facing, agentName, agentJsonPath) {
|
|
131
|
+
const providerResult = resolveFacingProvider(parsed, facing, agentName, agentJsonPath);
|
|
132
|
+
if (!providerResult.ok) {
|
|
133
|
+
return {
|
|
134
|
+
ok: false,
|
|
135
|
+
result: {
|
|
136
|
+
ok: false,
|
|
137
|
+
error: providerResult.result.error,
|
|
138
|
+
fix: `Run 'ouro use --agent ${agentName} --lane ${facing === "humanFacing" ? "outward" : "inner"} --provider <provider> --model <model>' to configure this machine's provider binding.`,
|
|
139
|
+
},
|
|
140
|
+
};
|
|
141
|
+
}
|
|
142
|
+
const raw = parsed[facing];
|
|
143
|
+
const model = typeof raw.model === "string" && raw.model.trim().length > 0
|
|
144
|
+
? raw.model.trim()
|
|
145
|
+
: (0, provider_models_1.getDefaultModelForProvider)(providerResult.selected.provider);
|
|
146
|
+
return { ok: true, provider: providerResult.selected.provider, model };
|
|
147
|
+
}
|
|
148
|
+
function bootstrapMissingProviderState(input) {
|
|
149
|
+
const outward = readFacingForBootstrap(input.parsed, "humanFacing", input.agentName, input.agentJsonPath);
|
|
150
|
+
if (!outward.ok)
|
|
151
|
+
return { ok: false, error: outward.result.error, fix: outward.result.fix };
|
|
152
|
+
const inner = readFacingForBootstrap(input.parsed, "agentFacing", input.agentName, input.agentJsonPath);
|
|
153
|
+
if (!inner.ok)
|
|
154
|
+
return { ok: false, error: inner.result.error, fix: inner.result.fix };
|
|
155
|
+
const now = new Date();
|
|
156
|
+
const homeDir = (0, provider_credentials_1.providerCredentialMachineHomeDir)(input.homeDir);
|
|
157
|
+
const machine = (0, machine_identity_1.loadOrCreateMachineIdentity)({ homeDir, now: () => now });
|
|
158
|
+
const state = (0, provider_state_1.bootstrapProviderStateFromAgentConfig)({
|
|
159
|
+
machineId: machine.machineId,
|
|
160
|
+
now,
|
|
161
|
+
agentConfig: {
|
|
162
|
+
humanFacing: { provider: outward.provider, model: outward.model },
|
|
163
|
+
agentFacing: { provider: inner.provider, model: inner.model },
|
|
164
|
+
},
|
|
165
|
+
});
|
|
166
|
+
const agentRoot = agentRootFor(input.agentName, input.bundlesRoot);
|
|
167
|
+
(0, provider_state_1.writeProviderState)(agentRoot, state);
|
|
168
|
+
(0, runtime_1.emitNervesEvent)({
|
|
169
|
+
component: "daemon",
|
|
170
|
+
event: "daemon.provider_state_bootstrapped",
|
|
171
|
+
message: "bootstrapped local provider state from agent config",
|
|
172
|
+
meta: { agent: input.agentName, agentRoot },
|
|
173
|
+
});
|
|
174
|
+
return { ok: true, agentRoot, state };
|
|
175
|
+
}
|
|
176
|
+
function readOrBootstrapProviderStateForCheck(agentName, bundlesRoot, deps = {}) {
|
|
177
|
+
const configResult = readAgentConfigForProviderState(agentName, bundlesRoot);
|
|
178
|
+
if (!configResult.ok)
|
|
179
|
+
return { ok: false, result: configResult.result };
|
|
180
|
+
if (configResult.disabled)
|
|
181
|
+
return { ok: true, disabled: true };
|
|
182
|
+
const agentRoot = agentRootFor(agentName, bundlesRoot);
|
|
183
|
+
const stateResult = (0, provider_state_1.readProviderState)(agentRoot);
|
|
184
|
+
if (stateResult.ok) {
|
|
185
|
+
return { ok: true, disabled: false, agentRoot, state: stateResult.state };
|
|
186
|
+
}
|
|
187
|
+
if (stateResult.reason === "invalid") {
|
|
188
|
+
return {
|
|
189
|
+
ok: false,
|
|
190
|
+
result: {
|
|
191
|
+
ok: false,
|
|
192
|
+
error: `provider state for ${agentName} is invalid at ${stateResult.statePath}: ${stateResult.error}`,
|
|
193
|
+
fix: `Run 'ouro use --agent ${agentName} --lane outward --provider <provider> --model <model> --force' to rewrite this machine's provider binding.`,
|
|
194
|
+
},
|
|
195
|
+
};
|
|
196
|
+
}
|
|
197
|
+
const bootstrap = bootstrapMissingProviderState({
|
|
198
|
+
agentName,
|
|
199
|
+
bundlesRoot,
|
|
200
|
+
parsed: configResult.parsed,
|
|
201
|
+
agentJsonPath: configResult.agentJsonPath,
|
|
202
|
+
homeDir: deps.homeDir,
|
|
203
|
+
});
|
|
204
|
+
if (!bootstrap.ok)
|
|
205
|
+
return { ok: false, result: bootstrap };
|
|
206
|
+
return { ok: true, disabled: false, agentRoot: bootstrap.agentRoot, state: bootstrap.state };
|
|
207
|
+
}
|
|
208
|
+
function providerCredentialConfig(record) {
|
|
209
|
+
return {
|
|
210
|
+
...record.credentials,
|
|
211
|
+
...record.config,
|
|
212
|
+
};
|
|
213
|
+
}
|
|
214
|
+
function pingAttemptCount(result) {
|
|
215
|
+
if (Array.isArray(result.attempts))
|
|
216
|
+
return result.attempts.length;
|
|
217
|
+
return undefined;
|
|
218
|
+
}
|
|
219
|
+
function writeLaneReadiness(input) {
|
|
220
|
+
const binding = input.state.lanes[input.lane];
|
|
221
|
+
const checkedAt = new Date().toISOString();
|
|
222
|
+
input.state.updatedAt = checkedAt;
|
|
223
|
+
input.state.readiness[input.lane] = {
|
|
224
|
+
status: input.status,
|
|
225
|
+
provider: binding.provider,
|
|
226
|
+
model: binding.model,
|
|
227
|
+
checkedAt,
|
|
228
|
+
credentialRevision: input.credentialRevision,
|
|
229
|
+
...(input.error ? { error: input.error } : {}),
|
|
230
|
+
...(input.attempts !== undefined ? { attempts: input.attempts } : {}),
|
|
231
|
+
};
|
|
232
|
+
(0, provider_state_1.writeProviderState)(input.agentRoot, input.state);
|
|
233
|
+
}
|
|
234
|
+
function missingCredentialResult(agentName, lane, provider, model, credentialPath) {
|
|
235
|
+
return {
|
|
236
|
+
ok: false,
|
|
237
|
+
error: `${lane} provider ${provider} model ${model} has no credentials in ${agentName}'s vault at ${credentialPath}`,
|
|
238
|
+
fix: `Run 'ouro auth --agent ${agentName} --provider ${provider}' to authenticate.`,
|
|
239
|
+
issue: (0, readiness_repair_1.providerCredentialMissingIssue)({
|
|
240
|
+
agentName,
|
|
241
|
+
lane,
|
|
242
|
+
provider,
|
|
243
|
+
model,
|
|
244
|
+
credentialPath,
|
|
245
|
+
}),
|
|
246
|
+
};
|
|
247
|
+
}
|
|
248
|
+
function isTransientVaultError(error) {
|
|
249
|
+
const normalized = error.toLowerCase();
|
|
250
|
+
return (normalized.includes("timed out") ||
|
|
251
|
+
normalized.includes("econnrefused") ||
|
|
252
|
+
normalized.includes("socket hang up") ||
|
|
253
|
+
normalized.includes("etimedout"));
|
|
254
|
+
}
|
|
255
|
+
function invalidPoolResult(agentName, lane, provider, model, pool) {
|
|
256
|
+
if (pool.reason === "unavailable" && isTransientVaultError(pool.error)) {
|
|
257
|
+
return {
|
|
258
|
+
ok: false,
|
|
259
|
+
error: `${lane} provider ${provider} model ${model} cannot read provider credentials from ${agentName}'s vault: ${pool.error}`,
|
|
260
|
+
fix: `Vault read timed out -- this usually resolves on retry. Run 'ouro up' again.`,
|
|
261
|
+
};
|
|
262
|
+
}
|
|
263
|
+
if (pool.reason === "unavailable" && isVaultLockedError(pool.error)) {
|
|
264
|
+
return {
|
|
265
|
+
ok: false,
|
|
266
|
+
error: `${lane} provider ${provider} model ${model} cannot read provider credentials because ${agentName}'s credential vault is locked on this machine.`,
|
|
267
|
+
fix: vaultUnlockOrRecoverFix(agentName),
|
|
268
|
+
issue: (0, readiness_repair_1.vaultLockedIssue)(agentName),
|
|
269
|
+
};
|
|
270
|
+
}
|
|
271
|
+
if (pool.reason === "unavailable" && (0, vault_unlock_1.isCredentialVaultNotConfiguredError)(pool.error)) {
|
|
272
|
+
return {
|
|
273
|
+
ok: false,
|
|
274
|
+
error: `${lane} provider ${provider} model ${model} cannot read provider credentials because ${agentName}'s credential vault is not configured in agent.json.`,
|
|
275
|
+
fix: (0, vault_unlock_1.vaultCreateRecoverFix)(agentName, `Then run 'ouro auth --agent ${agentName} --provider ${provider}' and rerun 'ouro up'.`),
|
|
276
|
+
issue: (0, readiness_repair_1.vaultUnconfiguredIssue)(agentName),
|
|
277
|
+
};
|
|
278
|
+
}
|
|
279
|
+
if (pool.reason === "invalid") {
|
|
280
|
+
return {
|
|
281
|
+
ok: false,
|
|
282
|
+
error: `${lane} provider ${provider} model ${model} cannot read provider credentials from ${agentName}'s vault at ${pool.poolPath}: ${pool.error}`,
|
|
283
|
+
fix: `Run 'ouro auth --agent ${agentName} --provider ${provider}' to rewrite this provider credential, then run 'ouro up' again.`,
|
|
284
|
+
};
|
|
285
|
+
}
|
|
286
|
+
return {
|
|
287
|
+
ok: false,
|
|
288
|
+
error: `${lane} provider ${provider} model ${model} cannot read provider credentials from ${agentName}'s vault at ${pool.poolPath}: ${pool.error}`,
|
|
289
|
+
fix: vaultUnlockOrRecoverFix(agentName, `Then run 'ouro up' again. If the credential is missing or stale after unlock or recovery, run 'ouro auth --agent ${agentName} --provider ${provider}'.`),
|
|
290
|
+
};
|
|
291
|
+
}
|
|
292
|
+
function isVaultLockedError(error) {
|
|
293
|
+
const normalized = error.toLowerCase();
|
|
294
|
+
return /(?:ouro )?credential vault is locked|vault(?: is)? locked/.test(normalized);
|
|
295
|
+
}
|
|
296
|
+
function vaultUnlockOrRecoverFix(agentName, nextStep = "Then run 'ouro up' again.") {
|
|
297
|
+
return (0, vault_unlock_1.vaultUnlockReplaceRecoverFix)(agentName, nextStep);
|
|
298
|
+
}
|
|
299
|
+
function failedPingResult(agentName, lane, provider, model, result) {
|
|
300
|
+
return {
|
|
301
|
+
ok: false,
|
|
302
|
+
error: `${lane} provider ${provider} model ${model} failed live check: ${result.message}`,
|
|
303
|
+
fix: (0, readiness_repair_1.providerLiveCheckFix)({
|
|
304
|
+
agentName,
|
|
305
|
+
lane,
|
|
306
|
+
provider,
|
|
307
|
+
classification: result.classification,
|
|
308
|
+
}),
|
|
309
|
+
issue: (0, readiness_repair_1.providerLiveCheckFailedIssue)({
|
|
310
|
+
agentName,
|
|
311
|
+
lane,
|
|
312
|
+
provider,
|
|
313
|
+
model,
|
|
314
|
+
classification: result.classification,
|
|
315
|
+
message: result.message,
|
|
316
|
+
}),
|
|
317
|
+
};
|
|
318
|
+
}
|
|
319
|
+
function credentialRecordForLane(pool, provider) {
|
|
320
|
+
return pool.providers[provider];
|
|
321
|
+
}
|
|
322
|
+
function laneAudienceLabel(lane) {
|
|
323
|
+
return lane === "outward" ? "chat" : "inner dialog";
|
|
324
|
+
}
|
|
325
|
+
function bindingLabel(binding) {
|
|
326
|
+
return `${binding.provider} / ${binding.model}`;
|
|
327
|
+
}
|
|
328
|
+
function selectedProviderPlan(agentName, state) {
|
|
329
|
+
return [
|
|
330
|
+
`${agentName}: checking the providers this agent uses right now`,
|
|
331
|
+
...["outward", "inner"].map((lane) => `- ${laneAudienceLabel(lane)}: ${bindingLabel(state.lanes[lane])}`),
|
|
332
|
+
].join("\n");
|
|
333
|
+
}
|
|
334
|
+
function selectedProvidersForState(state) {
|
|
335
|
+
return [...new Set(["outward", "inner"].map((lane) => state.lanes[lane].provider))];
|
|
336
|
+
}
|
|
337
|
+
function mapVaultRefreshProgress(agentName, onProgress) {
|
|
338
|
+
return (message) => {
|
|
339
|
+
if (message.startsWith("reading vault items for ")) {
|
|
340
|
+
onProgress(`${agentName}: opening saved provider credentials in the vault`);
|
|
341
|
+
return;
|
|
342
|
+
}
|
|
343
|
+
const providerRead = message.match(/^reading ([a-z0-9-]+) credentials\.\.\.$/i);
|
|
344
|
+
if (providerRead) {
|
|
345
|
+
onProgress(`${agentName}: reading saved ${providerRead[1]} credentials`);
|
|
346
|
+
return;
|
|
347
|
+
}
|
|
348
|
+
if (message === "parsing provider credentials...") {
|
|
349
|
+
onProgress(`${agentName}: organizing saved provider credentials`);
|
|
350
|
+
}
|
|
351
|
+
};
|
|
352
|
+
}
|
|
353
|
+
function providerPingSubject(agentName, lanes) {
|
|
354
|
+
const laneList = lanes.map((lane) => laneAudienceLabel(lane)).join(" + ");
|
|
355
|
+
return `${agentName} (${laneList})`;
|
|
356
|
+
}
|
|
357
|
+
/**
|
|
358
|
+
* Structural validation only. Live provider credential validation belongs to
|
|
359
|
+
* checkAgentConfigWithProviderHealth(), which reads the agent vault and pings.
|
|
360
|
+
*/
|
|
361
|
+
function checkAgentConfig(agentName, bundlesRoot) {
|
|
362
|
+
const configResult = readAgentConfigForProviderState(agentName, bundlesRoot);
|
|
363
|
+
if (!configResult.ok)
|
|
364
|
+
return configResult.result;
|
|
365
|
+
if (configResult.disabled)
|
|
366
|
+
return { ok: true };
|
|
367
|
+
const outward = readFacingForBootstrap(configResult.parsed, "humanFacing", agentName, configResult.agentJsonPath);
|
|
368
|
+
if (!outward.ok)
|
|
369
|
+
return outward.result;
|
|
370
|
+
const inner = readFacingForBootstrap(configResult.parsed, "agentFacing", agentName, configResult.agentJsonPath);
|
|
371
|
+
if (!inner.ok)
|
|
372
|
+
return inner.result;
|
|
373
|
+
(0, runtime_1.emitNervesEvent)({
|
|
374
|
+
component: "daemon",
|
|
375
|
+
event: "daemon.agent_config_valid",
|
|
376
|
+
message: "agent config validation passed",
|
|
377
|
+
meta: {
|
|
378
|
+
agent: agentName,
|
|
379
|
+
providers: [...new Set([outward.provider, inner.provider])],
|
|
380
|
+
liveProviderCheck: false,
|
|
381
|
+
},
|
|
382
|
+
});
|
|
383
|
+
return { ok: true };
|
|
384
|
+
}
|
|
385
|
+
async function checkAgentConfigWithProviderHealth(agentName, bundlesRoot, deps = {}) {
|
|
386
|
+
const stateResult = readOrBootstrapProviderStateForCheck(agentName, bundlesRoot, deps);
|
|
387
|
+
if (!stateResult.ok)
|
|
388
|
+
return stateResult.result;
|
|
389
|
+
if (stateResult.disabled)
|
|
390
|
+
return { ok: true };
|
|
391
|
+
// Layer 4 drift detection. Runs once per call after state setup so that
|
|
392
|
+
// drift findings ride along regardless of ping outcome — consumers
|
|
393
|
+
// (Layer 4 rollup, Layer 3 RepairGuide) want to see drift even when a
|
|
394
|
+
// live-check is failing for unrelated reasons. Drift detection is pure
|
|
395
|
+
// and never throws on a malformed agent.json: any read error here would
|
|
396
|
+
// indicate the bundle disappeared between state setup and now (a
|
|
397
|
+
// race), which we surface as `[]` rather than a hard failure.
|
|
398
|
+
let driftFindings = [];
|
|
399
|
+
try {
|
|
400
|
+
const inputs = (0, drift_detection_1.loadDriftInputsForAgent)(bundlesRoot, agentName);
|
|
401
|
+
driftFindings = (0, drift_detection_1.detectProviderBindingDrift)({
|
|
402
|
+
agentName,
|
|
403
|
+
agentJson: inputs.agentJson,
|
|
404
|
+
providerState: inputs.providerState,
|
|
405
|
+
});
|
|
406
|
+
}
|
|
407
|
+
catch {
|
|
408
|
+
/* v8 ignore next 1 -- defensive race-window guard: agent.json went away after state setup. Tested via Unit 5 integration when at all. @preserve */
|
|
409
|
+
driftFindings = [];
|
|
410
|
+
}
|
|
411
|
+
deps.onProgress?.(selectedProviderPlan(agentName, stateResult.state));
|
|
412
|
+
const ping = deps.pingProvider ?? (await Promise.resolve().then(() => __importStar(require("../provider-ping")))).pingProvider;
|
|
413
|
+
const shouldRecordReadiness = deps.recordReadiness ?? true;
|
|
414
|
+
const providers = selectedProvidersForState(stateResult.state);
|
|
415
|
+
const poolResult = await (0, provider_credentials_1.refreshProviderCredentialPool)(agentName, {
|
|
416
|
+
...(deps.onProgress ? { onProgress: mapVaultRefreshProgress(agentName, deps.onProgress) } : {}),
|
|
417
|
+
providers,
|
|
418
|
+
preserveCachedOnFailure: true,
|
|
419
|
+
});
|
|
420
|
+
const pingGroups = new Map();
|
|
421
|
+
const lanes = ["outward", "inner"];
|
|
422
|
+
for (const lane of lanes) {
|
|
423
|
+
const binding = stateResult.state.lanes[lane];
|
|
424
|
+
if (!poolResult.ok) {
|
|
425
|
+
if (poolResult.reason === "missing") {
|
|
426
|
+
return { ...missingCredentialResult(agentName, lane, binding.provider, binding.model, poolResult.poolPath), driftFindings };
|
|
427
|
+
}
|
|
428
|
+
return { ...invalidPoolResult(agentName, lane, binding.provider, binding.model, {
|
|
429
|
+
...poolResult,
|
|
430
|
+
reason: poolResult.reason,
|
|
431
|
+
}), driftFindings };
|
|
432
|
+
}
|
|
433
|
+
const record = credentialRecordForLane(poolResult.pool, binding.provider);
|
|
434
|
+
if (!record) {
|
|
435
|
+
return { ...missingCredentialResult(agentName, lane, binding.provider, binding.model, poolResult.poolPath), driftFindings };
|
|
436
|
+
}
|
|
437
|
+
const key = `${binding.provider}\0${binding.model}\0${record.revision}`;
|
|
438
|
+
const group = pingGroups.get(key);
|
|
439
|
+
if (group) {
|
|
440
|
+
group.lanes.push(lane);
|
|
441
|
+
}
|
|
442
|
+
else {
|
|
443
|
+
pingGroups.set(key, {
|
|
444
|
+
provider: binding.provider,
|
|
445
|
+
model: binding.model,
|
|
446
|
+
record,
|
|
447
|
+
lanes: [lane],
|
|
448
|
+
});
|
|
449
|
+
}
|
|
450
|
+
}
|
|
451
|
+
const groups = [...pingGroups.values()];
|
|
452
|
+
const pingResults = await Promise.all(groups.map(async (group) => {
|
|
453
|
+
const result = await ping(group.provider, providerCredentialConfig(group.record), {
|
|
454
|
+
model: group.model,
|
|
455
|
+
...(deps.providerPingOptions ?? {}),
|
|
456
|
+
...(deps.onProgress
|
|
457
|
+
? (0, provider_ping_progress_1.createProviderPingProgressReporter)({
|
|
458
|
+
provider: group.provider,
|
|
459
|
+
model: group.model,
|
|
460
|
+
subject: providerPingSubject(agentName, group.lanes),
|
|
461
|
+
}, deps.onProgress)
|
|
462
|
+
: {}),
|
|
463
|
+
});
|
|
464
|
+
return { group, result };
|
|
465
|
+
}));
|
|
466
|
+
let firstFailure = null;
|
|
467
|
+
for (const { group, result } of pingResults) {
|
|
468
|
+
if (!result.ok) {
|
|
469
|
+
if (shouldRecordReadiness) {
|
|
470
|
+
for (const lane of group.lanes) {
|
|
471
|
+
writeLaneReadiness({
|
|
472
|
+
agentRoot: stateResult.agentRoot,
|
|
473
|
+
state: stateResult.state,
|
|
474
|
+
lane,
|
|
475
|
+
status: "failed",
|
|
476
|
+
credentialRevision: group.record.revision,
|
|
477
|
+
error: result.message,
|
|
478
|
+
attempts: pingAttemptCount(result),
|
|
479
|
+
});
|
|
480
|
+
}
|
|
481
|
+
}
|
|
482
|
+
firstFailure ??= failedPingResult(agentName, group.lanes[0], group.provider, group.model, result);
|
|
483
|
+
continue;
|
|
484
|
+
}
|
|
485
|
+
if (shouldRecordReadiness) {
|
|
486
|
+
for (const lane of group.lanes) {
|
|
487
|
+
writeLaneReadiness({
|
|
488
|
+
agentRoot: stateResult.agentRoot,
|
|
489
|
+
state: stateResult.state,
|
|
490
|
+
lane,
|
|
491
|
+
status: "ready",
|
|
492
|
+
credentialRevision: group.record.revision,
|
|
493
|
+
attempts: pingAttemptCount(result),
|
|
494
|
+
});
|
|
495
|
+
}
|
|
496
|
+
}
|
|
497
|
+
}
|
|
498
|
+
if (firstFailure)
|
|
499
|
+
return { ...firstFailure, driftFindings };
|
|
500
|
+
(0, runtime_1.emitNervesEvent)({
|
|
501
|
+
component: "daemon",
|
|
502
|
+
event: "daemon.agent_config_valid",
|
|
503
|
+
message: "agent config validation passed",
|
|
504
|
+
meta: {
|
|
505
|
+
agent: agentName,
|
|
506
|
+
providers: [...new Set([...pingGroups.values()].map((group) => group.provider))],
|
|
507
|
+
liveProviderCheck: true,
|
|
508
|
+
driftCount: driftFindings.length,
|
|
509
|
+
},
|
|
510
|
+
});
|
|
511
|
+
return { ok: true, driftFindings };
|
|
512
|
+
}
|
|
@@ -33,12 +33,34 @@ var __importStar = (this && this.__importStar) || (function () {
|
|
|
33
33
|
};
|
|
34
34
|
})();
|
|
35
35
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
36
|
+
exports.isLibraryKind = isLibraryKind;
|
|
37
|
+
exports.listAllBundleAgents = listAllBundleAgents;
|
|
36
38
|
exports.listEnabledBundleAgents = listEnabledBundleAgents;
|
|
39
|
+
exports.listBundleSyncRows = listBundleSyncRows;
|
|
37
40
|
const fs = __importStar(require("fs"));
|
|
38
41
|
const path = __importStar(require("path"));
|
|
42
|
+
const child_process_1 = require("child_process");
|
|
39
43
|
const identity_1 = require("../identity");
|
|
40
44
|
const runtime_1 = require("../../nerves/runtime");
|
|
41
|
-
|
|
45
|
+
/**
|
|
46
|
+
* True when the value is the string `"library"`. Library bundles are
|
|
47
|
+
* content-only resources — never run as agents, never appear in sync surfaces.
|
|
48
|
+
*/
|
|
49
|
+
function isLibraryKind(kind) {
|
|
50
|
+
return kind === "library";
|
|
51
|
+
}
|
|
52
|
+
/**
|
|
53
|
+
* Walk the bundles root and return one row per `<name>.ouro` directory whose
|
|
54
|
+
* `agent.json` is readable and parseable. Includes both enabled and disabled
|
|
55
|
+
* agents AND library-kind bundles — callers that need only real agents should
|
|
56
|
+
* use `listEnabledBundleAgents` (which filters both `enabled` and `kind`).
|
|
57
|
+
*
|
|
58
|
+
* Bundles whose `agent.json` is missing, malformed, or unreadable are skipped
|
|
59
|
+
* silently (they aren't real agents from the harness's perspective).
|
|
60
|
+
*
|
|
61
|
+
* Sorted alphabetically by name for stable display.
|
|
62
|
+
*/
|
|
63
|
+
function listAllBundleAgents(options = {}) {
|
|
42
64
|
const bundlesRoot = options.bundlesRoot ?? (0, identity_1.getAgentBundlesRoot)();
|
|
43
65
|
const readdirSync = options.readdirSync ?? fs.readdirSync;
|
|
44
66
|
const readFileSync = options.readFileSync ?? fs.readFileSync;
|
|
@@ -63,19 +85,96 @@ function listEnabledBundleAgents(options = {}) {
|
|
|
63
85
|
const agentName = entry.name.slice(0, -5);
|
|
64
86
|
const configPath = path.join(bundlesRoot, entry.name, "agent.json");
|
|
65
87
|
let enabled = true;
|
|
88
|
+
let kind;
|
|
66
89
|
try {
|
|
67
90
|
const raw = readFileSync(configPath, "utf-8");
|
|
68
91
|
const parsed = JSON.parse(raw);
|
|
69
92
|
if (typeof parsed.enabled === "boolean") {
|
|
70
93
|
enabled = parsed.enabled;
|
|
71
94
|
}
|
|
95
|
+
if (typeof parsed.kind === "string") {
|
|
96
|
+
kind = parsed.kind;
|
|
97
|
+
}
|
|
72
98
|
}
|
|
73
99
|
catch {
|
|
74
100
|
continue;
|
|
75
101
|
}
|
|
102
|
+
const row = { name: agentName, enabled };
|
|
103
|
+
if (kind !== undefined)
|
|
104
|
+
row.kind = kind;
|
|
105
|
+
discovered.push(row);
|
|
106
|
+
}
|
|
107
|
+
return discovered.sort((left, right) => left.name.localeCompare(right.name));
|
|
108
|
+
}
|
|
109
|
+
/**
|
|
110
|
+
* Real agents only — excludes both disabled bundles and library-kind bundles.
|
|
111
|
+
* Library bundles (SerpentGuide, RepairGuide, …) are content-only and must
|
|
112
|
+
* never appear in spawn lists, status rollups, or sync rows.
|
|
113
|
+
*/
|
|
114
|
+
function listEnabledBundleAgents(options = {}) {
|
|
115
|
+
return listAllBundleAgents(options)
|
|
116
|
+
.filter((row) => row.enabled && !isLibraryKind(row.kind))
|
|
117
|
+
.map((row) => row.name);
|
|
118
|
+
}
|
|
119
|
+
/**
|
|
120
|
+
* Read the per-agent sync block from each enabled bundle's agent.json.
|
|
121
|
+
* Used by the daemon (and stopped-state status renderer) to build per-agent
|
|
122
|
+
* sync rows without depending on argv-derived global identity. Bundles that
|
|
123
|
+
* cannot be read are skipped silently.
|
|
124
|
+
*
|
|
125
|
+
* For rows with sync enabled, also checks whether the bundle is a git repo
|
|
126
|
+
* (via .git directory presence) and resolves the remote URL via
|
|
127
|
+
* `git remote get-url <remote>`. On any error the URL is left undefined and
|
|
128
|
+
* the status renderer falls back to "local only" or "not a git repo".
|
|
129
|
+
*/
|
|
130
|
+
function listBundleSyncRows(options = {}) {
|
|
131
|
+
const bundlesRoot = options.bundlesRoot ?? (0, identity_1.getAgentBundlesRoot)();
|
|
132
|
+
const readFileSync = options.readFileSync ?? fs.readFileSync;
|
|
133
|
+
const execFileSync = options.execFileSync ?? child_process_1.execFileSync;
|
|
134
|
+
const existsSync = options.existsSync ?? fs.existsSync;
|
|
135
|
+
const agents = listEnabledBundleAgents(options);
|
|
136
|
+
const rows = [];
|
|
137
|
+
for (const agent of agents) {
|
|
138
|
+
const bundleRoot = path.join(bundlesRoot, `${agent}.ouro`);
|
|
139
|
+
const configPath = path.join(bundleRoot, "agent.json");
|
|
140
|
+
let enabled = false;
|
|
141
|
+
let remote = "origin";
|
|
142
|
+
try {
|
|
143
|
+
const raw = readFileSync(configPath, "utf-8");
|
|
144
|
+
const parsed = JSON.parse(raw);
|
|
145
|
+
if (parsed.sync && typeof parsed.sync === "object") {
|
|
146
|
+
if (typeof parsed.sync.enabled === "boolean")
|
|
147
|
+
enabled = parsed.sync.enabled;
|
|
148
|
+
if (typeof parsed.sync.remote === "string" && parsed.sync.remote.length > 0) {
|
|
149
|
+
remote = parsed.sync.remote;
|
|
150
|
+
}
|
|
151
|
+
}
|
|
152
|
+
}
|
|
153
|
+
catch {
|
|
154
|
+
// Best-effort: bundle without readable config still gets a row with defaults
|
|
155
|
+
}
|
|
156
|
+
const row = { agent, enabled, remote };
|
|
76
157
|
if (enabled) {
|
|
77
|
-
|
|
158
|
+
// Only meaningful when sync is enabled — we don't care about disabled bundles'
|
|
159
|
+
// git state. Check .git presence before attempting any git invocation.
|
|
160
|
+
const gitInitialized = existsSync(path.join(bundleRoot, ".git"));
|
|
161
|
+
row.gitInitialized = gitInitialized;
|
|
162
|
+
if (gitInitialized) {
|
|
163
|
+
try {
|
|
164
|
+
const out = execFileSync("git", ["remote", "get-url", remote], {
|
|
165
|
+
cwd: bundleRoot,
|
|
166
|
+
stdio: "pipe",
|
|
167
|
+
timeout: 5000,
|
|
168
|
+
}).toString().trim();
|
|
169
|
+
if (out.length > 0)
|
|
170
|
+
row.remoteUrl = out;
|
|
171
|
+
}
|
|
172
|
+
catch {
|
|
173
|
+
// No remote configured or git missing — leave remoteUrl undefined.
|
|
174
|
+
}
|
|
175
|
+
}
|
|
78
176
|
}
|
|
177
|
+
rows.push(row);
|
|
79
178
|
}
|
|
80
|
-
return
|
|
179
|
+
return rows;
|
|
81
180
|
}
|