@cohortapp/agent-sdk 2.3.0
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/.claude/commands/init-agent.md +104 -0
- package/.claude/commands/init-maestro.md +1187 -0
- package/.claude/settings.json +161 -0
- package/.env.example +216 -0
- package/README.md +632 -0
- package/agents/browser-operator/agent.md +52 -0
- package/agents/calendar-ops/agent.md +50 -0
- package/agents/communications/agent.md +96 -0
- package/agents/decision-log/agent.md +65 -0
- package/agents/desktop-operator/agent.md +59 -0
- package/agents/gmail-operator/agent.md +62 -0
- package/agents/inbound-dispatcher/agent.md +66 -0
- package/agents/inbox-processor/agent.md +39 -0
- package/agents/pmo-execution/agent.md +60 -0
- package/agents/session-spawner/agent.md +64 -0
- package/agents/slack-operator/agent.md +60 -0
- package/agents/whatsapp-operator/agent.md +60 -0
- package/agents/workflow-automation/agent.md +61 -0
- package/archetypes/altitudes/c-suite.yaml +58 -0
- package/archetypes/altitudes/founder.yaml +68 -0
- package/archetypes/altitudes/senior-manager.yaml +63 -0
- package/archetypes/altitudes/svp.yaml +60 -0
- package/archetypes/altitudes/vp.yaml +50 -0
- package/archetypes/archetype.schema.json +77 -0
- package/archetypes/base.yaml +47 -0
- package/archetypes/capabilities/commercial-leader.yaml +159 -0
- package/archetypes/capabilities/compliance-officer.yaml +159 -0
- package/archetypes/capabilities/executive-operator.yaml +169 -0
- package/archetypes/capabilities/finance-leader.yaml +162 -0
- package/archetypes/capabilities/operations-leader.yaml +154 -0
- package/archetypes/capabilities/product-leader.yaml +148 -0
- package/archetypes/capabilities/technical-leader.yaml +146 -0
- package/archetypes/functions/commercial-leader.yaml +62 -0
- package/archetypes/functions/compliance-officer.yaml +64 -0
- package/archetypes/functions/executive-operator.yaml +70 -0
- package/archetypes/functions/finance-leader.yaml +70 -0
- package/archetypes/functions/operations-leader.yaml +62 -0
- package/archetypes/functions/product-leader.yaml +61 -0
- package/archetypes/functions/technical-leader.yaml +57 -0
- package/bin/cohort-mcp.mjs +81 -0
- package/bin/maestro.mjs +3516 -0
- package/bin/maestro.test.mjs +1015 -0
- package/desktop-control/README.md +56 -0
- package/desktop-control/app-profiles/gmail.yaml +120 -0
- package/desktop-control/app-profiles/slack.yaml +315 -0
- package/desktop-control/app-profiles/whatsapp.yaml +107 -0
- package/docs/architecture/agent-topology.md +2239 -0
- package/docs/architecture/archetype-agent-factory.md +110 -0
- package/docs/architecture/collective-memory-and-org-mesh.md +115 -0
- package/docs/architecture/continuous-monitoring.md +221 -0
- package/docs/architecture/mcp-capability-map.md +585 -0
- package/docs/architecture/system-architecture.md +1272 -0
- package/docs/company-context/README.md +40 -0
- package/docs/guides/agent-persona-setup.md +600 -0
- package/docs/guides/agents-observe-setup.md +64 -0
- package/docs/guides/billing-console-keys.md +88 -0
- package/docs/guides/ccxray-diagnostics.md +65 -0
- package/docs/guides/channel-bus.md +127 -0
- package/docs/guides/claude-mem-setup.md +79 -0
- package/docs/guides/claude-pace-setup.md +56 -0
- package/docs/guides/claudraband-sessions.md +98 -0
- package/docs/guides/clawteam-swarm.md +116 -0
- package/docs/guides/code-review-graph-setup.md +86 -0
- package/docs/guides/email-setup.md +431 -0
- package/docs/guides/mac-mini.md +119 -0
- package/docs/guides/media-generation-setup.md +349 -0
- package/docs/guides/model-routing.md +162 -0
- package/docs/guides/observability-otel.md +265 -0
- package/docs/guides/org-onboarding.md +132 -0
- package/docs/guides/outbound-governance-setup.md +437 -0
- package/docs/guides/pdf-generation-setup.md +315 -0
- package/docs/guides/poller-daemon-setup.md +563 -0
- package/docs/guides/rag-context-setup.md +459 -0
- package/docs/guides/self-optimization-pattern.md +82 -0
- package/docs/guides/setup-wizard.md +178 -0
- package/docs/guides/slack-setup.md +350 -0
- package/docs/guides/telegram-setup.md +227 -0
- package/docs/guides/twilio-subaccounts-setup.md +223 -0
- package/docs/guides/verification.md +128 -0
- package/docs/guides/voice-mode.md +188 -0
- package/docs/guides/voice-sms-setup.md +698 -0
- package/docs/guides/webhook-relay-setup.md +349 -0
- package/docs/guides/whatsapp-setup.md +288 -0
- package/docs/prompts/board-pack-cover-template.md +36 -0
- package/docs/prompts/decision-recommendation-template.md +88 -0
- package/docs/prompts/followup-message-template.md +141 -0
- package/docs/prompts/investor-letter-template.md +52 -0
- package/docs/prompts/morning-brief-template.md +82 -0
- package/docs/prompts/presentation-template.md +58 -0
- package/docs/prompts/weekly-strategic-memo-template.md +104 -0
- package/docs/research/hallucinated-tool-output-investigation.md +151 -0
- package/docs/runbooks/backup-restore.md +205 -0
- package/docs/runbooks/cohort-cutover.md +129 -0
- package/docs/runbooks/fleet-operations.md +200 -0
- package/docs/runbooks/incident-response.md +226 -0
- package/docs/runbooks/mac-mini-bootstrap.md +431 -0
- package/docs/runbooks/perpetual-operations.md +509 -0
- package/docs/runbooks/recovery-and-failover.md +260 -0
- package/framework-features.json +267 -0
- package/ingest/README.md +87 -0
- package/lib/action-executor.js +689 -0
- package/lib/action-executor.test.mjs +871 -0
- package/lib/agent-root.mjs +37 -0
- package/lib/archetype.mjs +236 -0
- package/lib/archetype.test.mjs +132 -0
- package/lib/autonomy.mjs +114 -0
- package/lib/autonomy.test.mjs +66 -0
- package/lib/backlog.mjs +358 -0
- package/lib/backlog.test.mjs +266 -0
- package/lib/budget-guard.mjs +279 -0
- package/lib/budget-guard.test.mjs +291 -0
- package/lib/cadence-bus-schedule.test.mjs +194 -0
- package/lib/cadence-bus.mjs +1120 -0
- package/lib/cadence-bus.test.mjs +720 -0
- package/lib/cadences.mjs +205 -0
- package/lib/cadences.test.mjs +125 -0
- package/lib/capability.mjs +154 -0
- package/lib/capability.test.mjs +78 -0
- package/lib/channels/base-adapter.mjs +719 -0
- package/lib/channels/base-adapter.test.mjs +590 -0
- package/lib/channels/channel.mjs +128 -0
- package/lib/channels/channels.test.mjs +371 -0
- package/lib/channels/contract.mjs +215 -0
- package/lib/channels/contract.test.mjs +137 -0
- package/lib/channels/conversation-resolver.mjs +95 -0
- package/lib/channels/gmail/adapter.mjs +87 -0
- package/lib/channels/inbox-item.mjs +255 -0
- package/lib/channels/inbox-item.test.mjs +335 -0
- package/lib/channels/index.mjs +94 -0
- package/lib/channels/orgmail/adapter.mjs +353 -0
- package/lib/channels/orgmail/adapter.test.mjs +311 -0
- package/lib/channels/pairing.mjs +363 -0
- package/lib/channels/pairing.test.mjs +270 -0
- package/lib/channels/registry.mjs +164 -0
- package/lib/channels/slack/adapter.mjs +317 -0
- package/lib/channels/slack-adapter.test.mjs +212 -0
- package/lib/channels/sms/adapter.mjs +43 -0
- package/lib/channels/telegram/adapter.mjs +432 -0
- package/lib/channels/telegram-adapter.test.mjs +306 -0
- package/lib/channels/voice/adapter.mjs +301 -0
- package/lib/channels/voice/adapter.test.mjs +278 -0
- package/lib/channels/whatsapp/adapter-baileys.mjs +587 -0
- package/lib/channels/whatsapp/adapter-baileys.test.mjs +359 -0
- package/lib/channels/whatsapp/adapter-twilio.mjs +65 -0
- package/lib/channels/whatsapp/baileys-typing.test.mjs +154 -0
- package/lib/charter.mjs +256 -0
- package/lib/charter.test.mjs +89 -0
- package/lib/claude-bin.mjs +134 -0
- package/lib/claude-bin.test.mjs +75 -0
- package/lib/collective/capture.mjs +185 -0
- package/lib/collective/capture.test.mjs +121 -0
- package/lib/collective/cards.mjs +201 -0
- package/lib/collective/cards.test.mjs +114 -0
- package/lib/collective/config.mjs +186 -0
- package/lib/collective/config.test.mjs +123 -0
- package/lib/collective/global-config.mjs +113 -0
- package/lib/collective/global-config.test.mjs +75 -0
- package/lib/collective/presence.mjs +201 -0
- package/lib/collective/presence.test.mjs +95 -0
- package/lib/collective/recall.mjs +215 -0
- package/lib/collective/recall.test.mjs +116 -0
- package/lib/comms/send-gate.mjs +554 -0
- package/lib/comms/send-gate.test.mjs +577 -0
- package/lib/comms.mjs +67 -0
- package/lib/comms.test.mjs +41 -0
- package/lib/diagnostics/alerts.mjs +424 -0
- package/lib/diagnostics/alerts.test.mjs +318 -0
- package/lib/diagnostics/backup-freshness.mjs +188 -0
- package/lib/diagnostics/backup-freshness.test.mjs +185 -0
- package/lib/diagnostics/counters.mjs +269 -0
- package/lib/diagnostics/counters.test.mjs +206 -0
- package/lib/diagnostics/events.mjs +188 -0
- package/lib/diagnostics/events.test.mjs +290 -0
- package/lib/diagnostics/otel.mjs +237 -0
- package/lib/diagnostics/otel.test.mjs +196 -0
- package/lib/diagnostics/trace.mjs +216 -0
- package/lib/diagnostics/trace.test.mjs +251 -0
- package/lib/env-compat.mjs +74 -0
- package/lib/env-compat.test.mjs +104 -0
- package/lib/feature-init.mjs +331 -0
- package/lib/fs-atomic.mjs +112 -0
- package/lib/fs-atomic.test.mjs +72 -0
- package/lib/fs-ownership.mjs +111 -0
- package/lib/fs-ownership.test.mjs +158 -0
- package/lib/hooks/bus.mjs +347 -0
- package/lib/hooks/bus.test.mjs +387 -0
- package/lib/index.js +16 -0
- package/lib/learning/config.mjs +106 -0
- package/lib/learning/config.test.mjs +75 -0
- package/lib/learning/counters.mjs +156 -0
- package/lib/learning/counters.test.mjs +69 -0
- package/lib/learning/curator-consolidate.test.mjs +238 -0
- package/lib/learning/curator.mjs +453 -0
- package/lib/learning/curator.test.mjs +106 -0
- package/lib/learning/log.mjs +40 -0
- package/lib/learning/reflect.mjs +534 -0
- package/lib/learning/reflect.test.mjs +0 -0
- package/lib/learning/session-index.mjs +352 -0
- package/lib/learning/session-index.test.mjs +125 -0
- package/lib/learning/skill-writer.mjs +474 -0
- package/lib/learning/skill-writer.test.mjs +210 -0
- package/lib/mcp/server.mjs +328 -0
- package/lib/mcp/server.test.mjs +400 -0
- package/lib/model-router/auth-profiles.mjs +758 -0
- package/lib/model-router/auth-profiles.test.mjs +580 -0
- package/lib/model-router/catalog/anthropic.yaml +153 -0
- package/lib/model-router/catalog/deepseek.yaml +86 -0
- package/lib/model-router/catalog/moonshot.yaml +81 -0
- package/lib/model-router/catalog/qwen.yaml +114 -0
- package/lib/model-router/catalog.mjs +925 -0
- package/lib/model-router/catalog.test.mjs +385 -0
- package/lib/model-router/economics.mjs +564 -0
- package/lib/model-router/economics.test.mjs +344 -0
- package/lib/model-router/failover.mjs +298 -0
- package/lib/model-router/failover.test.mjs +439 -0
- package/lib/model-router/health.mjs +453 -0
- package/lib/model-router/health.test.mjs +338 -0
- package/lib/model-router/integration-coverage.test.mjs +829 -0
- package/lib/model-router/integration.test.mjs +564 -0
- package/lib/model-router/ledger.mjs +402 -0
- package/lib/model-router/ledger.test.mjs +382 -0
- package/lib/model-router/llm-task.mjs +515 -0
- package/lib/model-router/llm-task.test.mjs +392 -0
- package/lib/model-router/org-credentials.mjs +260 -0
- package/lib/model-router/org-credentials.test.mjs +265 -0
- package/lib/model-router/pricing-refresh.mjs +463 -0
- package/lib/model-router/pricing-refresh.test.mjs +286 -0
- package/lib/model-router/reconcile.mjs +429 -0
- package/lib/model-router/reconcile.test.mjs +316 -0
- package/lib/model-router/repair.mjs +471 -0
- package/lib/model-router/repair.test.mjs +180 -0
- package/lib/model-router/resolve.mjs +1206 -0
- package/lib/model-router/spawn.mjs +497 -0
- package/lib/model-router/spawn.test.mjs +425 -0
- package/lib/model-router/taxonomy.mjs +893 -0
- package/lib/model-router/taxonomy.test.mjs +410 -0
- package/lib/model-router.mjs +677 -0
- package/lib/model-router.test.mjs +907 -0
- package/lib/org/activity.mjs +211 -0
- package/lib/org/activity.test.mjs +134 -0
- package/lib/org/approvals.mjs +448 -0
- package/lib/org/approvals.test.mjs +216 -0
- package/lib/org/awareness.mjs +222 -0
- package/lib/org/awareness.test.mjs +159 -0
- package/lib/org/board.mjs +229 -0
- package/lib/org/board.test.mjs +177 -0
- package/lib/org/bootstrap-context.mjs +169 -0
- package/lib/org/bootstrap-context.test.mjs +153 -0
- package/lib/org/client.mjs +1628 -0
- package/lib/org/client.test.mjs +1107 -0
- package/lib/org/cohort-client.mjs +67 -0
- package/lib/org/cohort-client.test.mjs +126 -0
- package/lib/org/cost-sync.mjs +227 -0
- package/lib/org/cost-sync.test.mjs +153 -0
- package/lib/org/doctor.mjs +212 -0
- package/lib/org/doctor.test.mjs +212 -0
- package/lib/org/handoff.mjs +293 -0
- package/lib/org/handoff.test.mjs +269 -0
- package/lib/org/integration-tools.mjs +182 -0
- package/lib/org/integration-tools.test.mjs +160 -0
- package/lib/org/keys.mjs +131 -0
- package/lib/org/keys.test.mjs +92 -0
- package/lib/org/knowledge.mjs +463 -0
- package/lib/org/knowledge.test.mjs +319 -0
- package/lib/org/leases.mjs +335 -0
- package/lib/org/leases.test.mjs +235 -0
- package/lib/org/mesh-integration.test.mjs +127 -0
- package/lib/org/mesh.mjs +459 -0
- package/lib/org/mesh.test.mjs +345 -0
- package/lib/org/messaging.mjs +503 -0
- package/lib/org/messaging.test.mjs +238 -0
- package/lib/org/policy.mjs +345 -0
- package/lib/org/policy.test.mjs +237 -0
- package/lib/org/protocol.checksum +1 -0
- package/lib/org/protocol.checksum.test.mjs +90 -0
- package/lib/org/protocol.mjs +967 -0
- package/lib/org/protocol.test.mjs +264 -0
- package/lib/org/registry.mjs +194 -0
- package/lib/org/registry.test.mjs +100 -0
- package/lib/org/tool-surface-integration.test.mjs +120 -0
- package/lib/org/tool-surface.mjs +2535 -0
- package/lib/org/tool-surface.test.mjs +589 -0
- package/lib/org/ui-parity.mjs +3236 -0
- package/lib/org/ui-parity.test.mjs +348 -0
- package/lib/org/verify.mjs +176 -0
- package/lib/org/verify.test.mjs +194 -0
- package/lib/rag/embed.mjs +188 -0
- package/lib/rag/indexer.mjs +425 -0
- package/lib/rag/rag.test.mjs +505 -0
- package/lib/rag/search.mjs +475 -0
- package/lib/rate-guard.mjs +246 -0
- package/lib/rate-guard.test.mjs +201 -0
- package/lib/render.mjs +112 -0
- package/lib/render.test.mjs +68 -0
- package/lib/resource-governor.mjs +297 -0
- package/lib/resource-governor.test.mjs +262 -0
- package/lib/scheduling/dynamic-jobs.mjs +675 -0
- package/lib/scheduling/dynamic-jobs.test.mjs +344 -0
- package/lib/scheduling/jitter.mjs +0 -0
- package/lib/scheduling/jitter.test.mjs +140 -0
- package/lib/secrets/broker.mjs +315 -0
- package/lib/secrets/broker.test.mjs +280 -0
- package/lib/secrets/providers.mjs +461 -0
- package/lib/secrets/providers.test.mjs +274 -0
- package/lib/security/audit-engine.mjs +684 -0
- package/lib/security/audit-engine.test.mjs +389 -0
- package/lib/security/coerce-args.mjs +552 -0
- package/lib/security/coerce-args.test.mjs +281 -0
- package/lib/security/dangerous-tools.mjs +97 -0
- package/lib/security/dangerous-tools.test.mjs +68 -0
- package/lib/security/external-content.mjs +145 -0
- package/lib/security/external-content.test.mjs +67 -0
- package/lib/security/redact.mjs +592 -0
- package/lib/security/redact.test.mjs +441 -0
- package/lib/security/secret-equal.mjs +73 -0
- package/lib/security/secret-equal.test.mjs +55 -0
- package/lib/session-permissions.mjs +101 -0
- package/lib/session-permissions.test.mjs +100 -0
- package/lib/setup/claude-probe.mjs +74 -0
- package/lib/setup/completeness.mjs +175 -0
- package/lib/setup/completeness.test.mjs +110 -0
- package/lib/setup/context-pack.mjs +173 -0
- package/lib/setup/context-pack.test.mjs +89 -0
- package/lib/setup/enrich.mjs +277 -0
- package/lib/setup/enrich.test.mjs +115 -0
- package/lib/setup/enroll-from-cohort.mjs +441 -0
- package/lib/setup/enroll-from-cohort.test.mjs +233 -0
- package/lib/setup/integration.test.mjs +162 -0
- package/lib/setup/io.mjs +360 -0
- package/lib/setup/io.test.mjs +77 -0
- package/lib/setup/run-generator.mjs +81 -0
- package/lib/setup/runner.mjs +244 -0
- package/lib/setup/runner.test.mjs +132 -0
- package/lib/setup/sections/comms.mjs +173 -0
- package/lib/setup/sections/company.mjs +120 -0
- package/lib/setup/sections/enrich.mjs +138 -0
- package/lib/setup/sections/identity.mjs +182 -0
- package/lib/setup/sections/identity.test.mjs +140 -0
- package/lib/setup/sections/learning.mjs +153 -0
- package/lib/setup/sections/learning.test.mjs +81 -0
- package/lib/setup/sections/messaging.mjs +219 -0
- package/lib/setup/sections/messaging.test.mjs +127 -0
- package/lib/setup/sections/model.mjs +102 -0
- package/lib/setup/sections/operating-model.mjs +78 -0
- package/lib/setup/sections/org.mjs +475 -0
- package/lib/setup/sections/org.test.mjs +313 -0
- package/lib/setup/sections/orgmail.mjs +173 -0
- package/lib/setup/sections/orgmail.test.mjs +118 -0
- package/lib/setup/sections/recovery.mjs +159 -0
- package/lib/setup/sections/recovery.test.mjs +98 -0
- package/lib/setup/sections/tools.mjs +132 -0
- package/lib/setup/sections/verify.mjs +97 -0
- package/lib/setup/sot.mjs +205 -0
- package/lib/setup/sot.test.mjs +81 -0
- package/lib/setup/state.mjs +151 -0
- package/lib/setup/state.test.mjs +92 -0
- package/lib/singleton.js +229 -0
- package/lib/singleton.test.mjs +135 -0
- package/lib/telemetry/alerts.mjs +216 -0
- package/lib/telemetry/alerts.test.mjs +109 -0
- package/lib/telemetry/collect.mjs +512 -0
- package/lib/telemetry/collect.test.mjs +202 -0
- package/lib/tool-definitions-integration.test.mjs +83 -0
- package/lib/tool-definitions.js +738 -0
- package/lib/tool-definitions.test.mjs +437 -0
- package/lib/util/fetch-timeout.mjs +136 -0
- package/lib/util/fetch-timeout.test.mjs +202 -0
- package/lib/util/reconnect.mjs +343 -0
- package/lib/util/reconnect.test.mjs +369 -0
- package/lib/util/unhandled.mjs +205 -0
- package/lib/util/unhandled.test.mjs +216 -0
- package/lib/voice/context-loader.mjs +466 -0
- package/lib/voice/index.mjs +100 -0
- package/lib/voice/openai-realtime.mjs +510 -0
- package/lib/voice/outbound.mjs +542 -0
- package/lib/voice/outbound.test.mjs +69 -0
- package/lib/voice/post-call-brief.mjs +428 -0
- package/lib/voice/provider.mjs +52 -0
- package/lib/voice/session-rotation.mjs +257 -0
- package/lib/voice/stt.mjs +161 -0
- package/lib/voice/stt.test.mjs +226 -0
- package/lib/voice/tool-bridge.mjs +370 -0
- package/lib/voice/tts.mjs +104 -0
- package/lib/voice/twilio-sip-bridge.mjs +288 -0
- package/lib/voice/voice.test.mjs +990 -0
- package/mcp/README.md +80 -0
- package/package.json +151 -0
- package/plugins/maestro-skills/plugin.json +139 -0
- package/plugins/maestro-skills/skills/agents-observe.md +110 -0
- package/plugins/maestro-skills/skills/board-deck.md +68 -0
- package/plugins/maestro-skills/skills/books-close.md +77 -0
- package/plugins/maestro-skills/skills/brand-steward.md +121 -0
- package/plugins/maestro-skills/skills/calendar-plan.md +57 -0
- package/plugins/maestro-skills/skills/call-working-sessions.md +124 -0
- package/plugins/maestro-skills/skills/ccxray-diagnostics.md +91 -0
- package/plugins/maestro-skills/skills/claude-pace.md +61 -0
- package/plugins/maestro-skills/skills/code-review-graph.md +99 -0
- package/plugins/maestro-skills/skills/crm-pipeline.md +65 -0
- package/plugins/maestro-skills/skills/decision-brief.md +89 -0
- package/plugins/maestro-skills/skills/directory-hygiene.md +125 -0
- package/plugins/maestro-skills/skills/draft-comms.md +84 -0
- package/plugins/maestro-skills/skills/evening-wrap.md +53 -0
- package/plugins/maestro-skills/skills/files-find.md +65 -0
- package/plugins/maestro-skills/skills/generative-ui.md +228 -0
- package/plugins/maestro-skills/skills/hiring-triage.md +74 -0
- package/plugins/maestro-skills/skills/inbox-triage.md +61 -0
- package/plugins/maestro-skills/skills/mail-triage.md +86 -0
- package/plugins/maestro-skills/skills/morning-brief.md +54 -0
- package/plugins/maestro-skills/skills/native-artifacts.md +157 -0
- package/plugins/maestro-skills/skills/org-board.md +133 -0
- package/plugins/maestro-skills/skills/org-credential.md +68 -0
- package/plugins/maestro-skills/skills/org-recall.md +81 -0
- package/plugins/maestro-skills/skills/pipeline-review.md +76 -0
- package/plugins/maestro-skills/skills/regulatory-status.md +81 -0
- package/plugins/maestro-skills/skills/router-why.md +78 -0
- package/plugins/maestro-skills/skills/schedule-meeting.md +91 -0
- package/plugins/maestro-skills/skills/session-search.md +71 -0
- package/plugins/maestro-skills/skills/set-reminder.md +93 -0
- package/plugins/maestro-skills/skills/slack-followup.md +64 -0
- package/plugins/maestro-skills/skills/team-activity.md +86 -0
- package/plugins/maestro-skills/skills/weekly-memo.md +70 -0
- package/policies/action-classification.yaml +114 -0
- package/policies/ai-disclosure.yaml +294 -0
- package/policies/communication-style.md +139 -0
- package/policies/information-barriers.yaml +118 -0
- package/policies/prompt-injection-defence.yaml +138 -0
- package/public/assets/icon-dark.png +0 -0
- package/public/assets/icon-dark.svg +9 -0
- package/public/assets/icon-light.svg +9 -0
- package/public/assets/logo-dark.svg +15 -0
- package/public/assets/logo-light.svg +15 -0
- package/scaffold/.mcp.json +7 -0
- package/scaffold/CLAUDE.md +368 -0
- package/scaffold/config/agent.json +55 -0
- package/scaffold/config/agent.ts +76 -0
- package/scaffold/config/agent.ts.example +89 -0
- package/scaffold/config/alerts.yaml +23 -0
- package/scaffold/config/allowlist.yaml.example +25 -0
- package/scaffold/config/caller-id-map.yaml +46 -0
- package/scaffold/config/collective.yaml +49 -0
- package/scaffold/config/company.json +20 -0
- package/scaffold/config/known-agents.json +6 -0
- package/scaffold/config/learning.yaml +55 -0
- package/scaffold/config/model-routing.yaml.example +104 -0
- package/scaffold/config/org.yaml +25 -0
- package/scaffold/config/orgmail.yaml.example +19 -0
- package/scaffold/config/recovery.yaml +72 -0
- package/scaffold/config/secrets.yaml +27 -0
- package/scaffold/config/slack.yaml.example +35 -0
- package/scaffold/config/telegram.yaml.example +38 -0
- package/scaffold/config/voice.yaml.example +89 -0
- package/scaffold/config/whatsapp.yaml.example +39 -0
- package/schedules/README.md +49 -0
- package/schedules/triggers/backlog-executor.md +102 -0
- package/schedules/triggers/brand-steward.md +72 -0
- package/schedules/triggers/daily-evening-wrap.md +159 -0
- package/schedules/triggers/daily-midday-sweep.md +58 -0
- package/schedules/triggers/daily-morning-brief.md +55 -0
- package/schedules/triggers/directory-hygiene.md +81 -0
- package/schedules/triggers/dynamic-jobs.md +40 -0
- package/schedules/triggers/inbox-processor.md +115 -0
- package/schedules/triggers/meeting-action-capture.md +60 -0
- package/schedules/triggers/meeting-prep.md +69 -0
- package/schedules/triggers/messaging-inbound.md +50 -0
- package/schedules/triggers/org-pulse.md +24 -0
- package/schedules/triggers/quarterly-self-assessment.md +54 -0
- package/schedules/triggers/weekly-engineering-health.md +37 -0
- package/schedules/triggers/weekly-execution.md +65 -0
- package/schedules/triggers/weekly-hiring.md +53 -0
- package/schedules/triggers/weekly-priorities.md +38 -0
- package/schedules/triggers/weekly-strategic-memo.md +124 -0
- package/scripts/archive-email.sh +55 -0
- package/scripts/cadence/cadence-status.mjs +36 -0
- package/scripts/cadence/enqueue-cadence-tick.mjs +174 -0
- package/scripts/cadence/enqueue-cadence-tick.test.mjs +187 -0
- package/scripts/cadence/launchd-cadence-wrapper.sh +85 -0
- package/scripts/cadence/launchd-cloud-relay-wrapper.sh +95 -0
- package/scripts/cadence/launchd-socket-mode-wrapper.sh +95 -0
- package/scripts/ci/check-docs-accuracy.mjs +493 -0
- package/scripts/ci/check-docs-accuracy.test.mjs +409 -0
- package/scripts/ci/check-exports-exist.mjs +140 -0
- package/scripts/ci/check-files-exist.mjs +107 -0
- package/scripts/ci/check-no-build-artifacts.mjs +111 -0
- package/scripts/ci/check-no-build-artifacts.test.mjs +71 -0
- package/scripts/ci/check-no-confidential.mjs +198 -0
- package/scripts/ci/check-no-conflict-markers.mjs +169 -0
- package/scripts/ci/check-no-residual-identity.mjs +163 -0
- package/scripts/ci/check-no-residual-identity.test.mjs +89 -0
- package/scripts/ci/check-tarball-fidelity.mjs +205 -0
- package/scripts/ci/check-unresolved-tokens.mjs +83 -0
- package/scripts/ci/check.mjs +109 -0
- package/scripts/ci/check.test.mjs +194 -0
- package/scripts/ci/run-coverage.mjs +82 -0
- package/scripts/ci/run-tests.mjs +71 -0
- package/scripts/cloud-relay/README.md +59 -0
- package/scripts/cloud-relay/index.mjs +233 -0
- package/scripts/cloud-relay/package.json +15 -0
- package/scripts/cloud-relay/railway.json +13 -0
- package/scripts/cloud-relay/voice/README.md +94 -0
- package/scripts/cloud-relay/voice/package-lock.json +39 -0
- package/scripts/cloud-relay/voice/package.json +16 -0
- package/scripts/cloud-relay/voice/railway.json +13 -0
- package/scripts/cloud-relay/voice/server.mjs +532 -0
- package/scripts/collective/hook-runner.mjs +211 -0
- package/scripts/collective/hook-runner.test.mjs +90 -0
- package/scripts/collective/org-pulse.mjs +72 -0
- package/scripts/collective/org-sync.mjs +61 -0
- package/scripts/collective/recall.mjs +45 -0
- package/scripts/collective/who.mjs +30 -0
- package/scripts/comms-monitor.sh +288 -0
- package/scripts/configure-whatsapp-sandbox.sh +201 -0
- package/scripts/continuous-monitor.sh +91 -0
- package/scripts/cost/fleet-digest.mjs +407 -0
- package/scripts/cost/fleet-digest.test.mjs +207 -0
- package/scripts/cost/track-claude-usage.mjs +169 -0
- package/scripts/daemon/agent-daemon.mjs +989 -0
- package/scripts/daemon/agent-daemon.test.mjs +525 -0
- package/scripts/daemon/cadence-consumer-governance.test.mjs +220 -0
- package/scripts/daemon/cadence-consumer.mjs +1080 -0
- package/scripts/daemon/cadence-consumer.test.mjs +770 -0
- package/scripts/daemon/cadence-handlers.mjs +1121 -0
- package/scripts/daemon/cadence-handlers.test.mjs +617 -0
- package/scripts/daemon/classifier.mjs +704 -0
- package/scripts/daemon/classifier.test.mjs +238 -0
- package/scripts/daemon/classify-kind.mjs +54 -0
- package/scripts/daemon/classify-kind.test.mjs +40 -0
- package/scripts/daemon/context-compiler.mjs +605 -0
- package/scripts/daemon/context-compiler.test.mjs +300 -0
- package/scripts/daemon/dispatcher-cooldown.test.mjs +122 -0
- package/scripts/daemon/dispatcher-governance.test.mjs +886 -0
- package/scripts/daemon/dispatcher.mjs +1516 -0
- package/scripts/daemon/health.mjs +72 -0
- package/scripts/daemon/inbox-deferral.mjs +210 -0
- package/scripts/daemon/inbox-deferral.test.mjs +242 -0
- package/scripts/daemon/integration.test.mjs +149 -0
- package/scripts/daemon/launchd-wrapper-generic.sh +96 -0
- package/scripts/daemon/launchd-wrapper-slack-events.sh +37 -0
- package/scripts/daemon/launchd-wrapper.sh +91 -0
- package/scripts/daemon/lib/session-router.mjs +274 -0
- package/scripts/daemon/lib/session-router.test.mjs +295 -0
- package/scripts/daemon/maestro-daemon.mjs +275 -0
- package/scripts/daemon/prompt-builder.mjs +685 -0
- package/scripts/daemon/prompt-builder.test.mjs +213 -0
- package/scripts/daemon/responder.mjs +854 -0
- package/scripts/daemon/session-lock.mjs +721 -0
- package/scripts/daemon/session-lock.test.mjs +252 -0
- package/scripts/daemon/session-outcomes.mjs +640 -0
- package/scripts/daemon/session-outcomes.test.mjs +533 -0
- package/scripts/daemon/typing-registry.mjs +90 -0
- package/scripts/daemon/typing-registry.test.mjs +77 -0
- package/scripts/daemon/voice-webhook-server.mjs +804 -0
- package/scripts/decisions/capture-decision.mjs +116 -0
- package/scripts/disclosure_assessment.py +873 -0
- package/scripts/disclosure_boundaries.py +562 -0
- package/scripts/email-signature-principal.html +52 -0
- package/scripts/email-signature.html +60 -0
- package/scripts/email_quote_thread.py +167 -0
- package/scripts/email_thread_dedup.py +362 -0
- package/scripts/emergency-stop.sh +81 -0
- package/scripts/healthcheck.sh +116 -0
- package/scripts/hooks/block-mcp-cohort-send.sh +15 -0
- package/scripts/hooks/block-mcp-slack-send.sh +7 -0
- package/scripts/hooks/post-action-log.sh +126 -0
- package/scripts/hooks/pre-send-audit.sh +174 -0
- package/scripts/hooks/pre-send-audit.test.mjs +215 -0
- package/scripts/hooks/session-end-log.sh +27 -0
- package/scripts/hooks/session-start-banner.sh +115 -0
- package/scripts/huddle/audio-bridge.mjs +664 -0
- package/scripts/huddle/boot-slack-cdp.sh +102 -0
- package/scripts/huddle/huddle-controller.mjs +942 -0
- package/scripts/huddle/huddle-server.mjs +1229 -0
- package/scripts/huddle/launch-slack.sh +232 -0
- package/scripts/huddle/openai-realtime-bridge.mjs +462 -0
- package/scripts/huddle/package-lock.json +62 -0
- package/scripts/huddle/package.json +22 -0
- package/scripts/huddle/setup-audio.sh +239 -0
- package/scripts/huddle/start-call.mjs +318 -0
- package/scripts/huddle/test-pipeline.mjs +263 -0
- package/scripts/learning/consolidate-skills.mjs +72 -0
- package/scripts/learning/session-search.mjs +125 -0
- package/scripts/llm_email_dedup.py +442 -0
- package/scripts/local-triggers/generate-plists.sh +432 -0
- package/scripts/local-triggers/generate-plists.test.mjs +413 -0
- package/scripts/local-triggers/install-all.sh +49 -0
- package/scripts/local-triggers/plists/.gitkeep +0 -0
- package/scripts/local-triggers/run-trigger.sh +63 -0
- package/scripts/local-triggers/templates/rag-reindex.plist.template +47 -0
- package/scripts/local-triggers/templates/voice-relay-poller.plist.template +54 -0
- package/scripts/local-triggers/templates/voice-tunnel.plist.template +55 -0
- package/scripts/local-triggers/templates/voice-webhook.plist.template +51 -0
- package/scripts/maintenance/backup-to-cloud.sh +124 -0
- package/scripts/maintenance/health-check.sh +377 -0
- package/scripts/media-generation/README.md +105 -0
- package/scripts/media-generation/gemini-image-client.mjs +173 -0
- package/scripts/media-generation/generate-assets.mjs +289 -0
- package/scripts/media-generation/veo-video-client.mjs +219 -0
- package/scripts/org/send-orgmail.mjs +227 -0
- package/scripts/outbound-dedup-cleanup.sh +43 -0
- package/scripts/outbound-dedup.sh +477 -0
- package/scripts/outbound_dedup.py +115 -0
- package/scripts/parse-voice-transcript.mjs +481 -0
- package/scripts/pdf-generation/README.md +63 -0
- package/scripts/pdf-generation/build-document.mjs +247 -0
- package/scripts/pdf-generation/templates/board-pack.latex +136 -0
- package/scripts/pdf-generation/templates/corporate-letter.latex +126 -0
- package/scripts/pdf-generation/templates/memo.latex +114 -0
- package/scripts/poll-slack-events.sh +35 -0
- package/scripts/poller/calendar-poller.mjs +12 -0
- package/scripts/poller/gmail-poller.mjs +192 -0
- package/scripts/poller/imap-client.mjs +289 -0
- package/scripts/poller/inbox-scan-poller.mjs +156 -0
- package/scripts/poller/inbox-scan-poller.test.mjs +231 -0
- package/scripts/poller/index.mjs +73 -0
- package/scripts/poller/intra-session-check.mjs +285 -0
- package/scripts/poller/lib/cloud-relay-dedup.mjs +88 -0
- package/scripts/poller/lib/cloud-relay-dedup.test.mjs +133 -0
- package/scripts/poller/lib/slash-command-handlers.mjs +177 -0
- package/scripts/poller/secondary-gmail-poller.mjs +132 -0
- package/scripts/poller/slack-cloud-relay-client.mjs +368 -0
- package/scripts/poller/slack-poller.mjs +854 -0
- package/scripts/poller/slack-socket-mode.mjs +917 -0
- package/scripts/poller/slack-socket-mode.test.mjs +753 -0
- package/scripts/poller/trigger.mjs +75 -0
- package/scripts/poller/utils.mjs +371 -0
- package/scripts/poller/voice-cloud-relay-client.mjs +179 -0
- package/scripts/poller/voice-poller.mjs +236 -0
- package/scripts/poller-launchd/install.sh +66 -0
- package/scripts/poller-launchd/poller.plist.template +40 -0
- package/scripts/poller-launchd/whatsapp-handler.plist.template +39 -0
- package/scripts/post-interaction-indexer.py +1598 -0
- package/scripts/pre-draft-context.py +994 -0
- package/scripts/pre_draft_lookup.py +258 -0
- package/scripts/rag/build-index.mjs +47 -0
- package/scripts/rag/ingest.mjs +111 -0
- package/scripts/rag/search.mjs +119 -0
- package/scripts/rag-indexer.py +629 -0
- package/scripts/restore-from-backup.sh +248 -0
- package/scripts/restore-from-backup.test.mjs +178 -0
- package/scripts/resume-operations.sh +80 -0
- package/scripts/search-secondary-inbox.py +181 -0
- package/scripts/secondary-inbox-poller.py +437 -0
- package/scripts/self-optimization/compute-metrics.py +398 -0
- package/scripts/send-email-as-principal.py +369 -0
- package/scripts/send-email-threaded.py +392 -0
- package/scripts/send-email-with-attachment.py +377 -0
- package/scripts/send-email.sh +131 -0
- package/scripts/send-sms.sh +175 -0
- package/scripts/send-whatsapp.sh +292 -0
- package/scripts/session-start.sh +106 -0
- package/scripts/setup/boot-claude-session.sh +94 -0
- package/scripts/setup/configure-macos.sh +674 -0
- package/scripts/setup/configure-twilio-sip-trunk.mjs +207 -0
- package/scripts/setup/configure-voice-tunnel.mjs +182 -0
- package/scripts/setup/generate-agent-env.mjs +92 -0
- package/scripts/setup/generate-agent-package-json.mjs +222 -0
- package/scripts/setup/generate-agent-package-json.test.mjs +143 -0
- package/scripts/setup/generate-autonomy.mjs +60 -0
- package/scripts/setup/generate-backlog.mjs +101 -0
- package/scripts/setup/generate-cadences.mjs +92 -0
- package/scripts/setup/generate-capability.mjs +162 -0
- package/scripts/setup/generate-charter.mjs +76 -0
- package/scripts/setup/generate-comms.mjs +59 -0
- package/scripts/setup/generate-company.mjs +92 -0
- package/scripts/setup/init-agent.sh +547 -0
- package/scripts/setup/init-agent.test.mjs +151 -0
- package/scripts/setup/init-archetype.mjs +74 -0
- package/scripts/setup/init-backup.mjs +54 -0
- package/scripts/setup/init-cadence-bus.mjs +60 -0
- package/scripts/setup/init-channel-bus.mjs +46 -0
- package/scripts/setup/init-cost-tracking.mjs +45 -0
- package/scripts/setup/init-decision-capture.mjs +66 -0
- package/scripts/setup/init-known-agents.mjs +57 -0
- package/scripts/setup/init-learning.mjs +70 -0
- package/scripts/setup/init-memory-executive.mjs +45 -0
- package/scripts/setup/init-model-router.mjs +124 -0
- package/scripts/setup/init-rag.mjs +174 -0
- package/scripts/setup/init-session-router.mjs +38 -0
- package/scripts/setup/init-slack-socket-mode.mjs +260 -0
- package/scripts/setup/init-telegram.mjs +165 -0
- package/scripts/setup/init-voice-realtime.mjs +204 -0
- package/scripts/setup/init-whatsapp-baileys.mjs +77 -0
- package/scripts/setup/install-dev-tools.sh +150 -0
- package/scripts/setup/lib/install-plist.mjs +95 -0
- package/scripts/setup/migrate-agent-to-sot.mjs +192 -0
- package/scripts/setup/render-environment-yaml.mjs +133 -0
- package/scripts/slack-events-ctl.sh +177 -0
- package/scripts/slack-events-server.mjs +1045 -0
- package/scripts/slack-react.mjs +89 -0
- package/scripts/slack-responded.sh +232 -0
- package/scripts/slack-send.sh +287 -0
- package/scripts/slack-typing.mjs +196 -0
- package/scripts/slack-upload-v2.py +95 -0
- package/scripts/sms-handler.mjs +450 -0
- package/scripts/spawn-session.sh +120 -0
- package/scripts/sync-protocol.mjs +217 -0
- package/scripts/system-verify.sh +184 -0
- package/scripts/test-email-thread-dedup.py +239 -0
- package/scripts/test-information-barriers.py +484 -0
- package/scripts/test-llm-email-dedup.py +251 -0
- package/scripts/test-pre-draft-integration.py +203 -0
- package/scripts/test-rag-phase2.sh +442 -0
- package/scripts/test-rag-search.sh +251 -0
- package/scripts/test-voice-parser.mjs +316 -0
- package/scripts/user-context-search.py +659 -0
- package/scripts/validate_outbound.py +1504 -0
- package/scripts/watchdog/ai.maestro.memory-watchdog.plist +41 -0
- package/scripts/watchdog/force-reboot.sh +157 -0
- package/scripts/watchdog/memory-watchdog.sh +473 -0
- package/scripts/whatsapp-handler.mjs +538 -0
- package/teams/desktop-operations.yaml +34 -0
- package/teams/executive-office.yaml +27 -0
- package/teams/legal-and-regulatory.yaml +24 -0
- package/teams/platform-and-engineering.yaml +23 -0
- package/teams/strategy-and-growth.yaml +29 -0
- package/workflows/continuous/backlog-executor.yaml +141 -0
- package/workflows/continuous/inbound-monitor.yaml +168 -0
- package/workflows/daily/applicant-triage.yaml +197 -0
- package/workflows/daily/comms-triage.yaml +80 -0
- package/workflows/daily/evening-wrap.yaml +105 -0
- package/workflows/daily/morning-brief.yaml +164 -0
- package/workflows/daily/slack-followup-sweep.yaml +87 -0
- package/workflows/event-driven/README.md +50 -0
- package/workflows/event-driven/agent-failure-investigation.yaml +137 -0
- package/workflows/event-driven/pr-review.yaml +107 -0
- package/workflows/monthly/board-readiness.yaml +76 -0
- package/workflows/quarterly/strategic-scenario-analysis.yaml +85 -0
- package/workflows/session-protocol.md +171 -0
- package/workflows/weekly/engineering-health.yaml +154 -0
- package/workflows/weekly/hiring-review.yaml +169 -0
- package/workflows/weekly/rollup-pipeline-review.yaml +76 -0
- package/workflows/weekly/strategic-memo.yaml +79 -0
|
@@ -0,0 +1,265 @@
|
|
|
1
|
+
# Observability — trace IDs, the event spine, and Claude Code OTLP
|
|
2
|
+
|
|
3
|
+
Maestro's per-node substrate is strong, but historically there was no way to
|
|
4
|
+
answer two questions an enterprise operator asks every day: *"show me everything
|
|
5
|
+
that happened for this one user message"* and *"is the fleet meeting its SLO?"*.
|
|
6
|
+
There were no correlation IDs, no metrics, and the daemon's counters lived in
|
|
7
|
+
memory and reset on every restart (gap analysis G7).
|
|
8
|
+
|
|
9
|
+
This guide covers the agent-side observability spine that fixes that:
|
|
10
|
+
|
|
11
|
+
1. a `trace_id` minted at the start of every interaction and carried through
|
|
12
|
+
every hop, so one user message is reconstructable end-to-end;
|
|
13
|
+
2. a typed diagnostic-event stream (`logs/diagnostics/<date>.jsonl`) that any
|
|
14
|
+
hot path can emit onto without risk of crashing;
|
|
15
|
+
3. Claude Code's **native** OpenTelemetry export — the cheap 70% — turned on
|
|
16
|
+
fleet-wide via managed settings and stamped with each agent's identity.
|
|
17
|
+
|
|
18
|
+
The first two are local and always-on (failure-tolerant); the third is opt-in
|
|
19
|
+
and exports to your collector.
|
|
20
|
+
|
|
21
|
+
---
|
|
22
|
+
|
|
23
|
+
## 1. Trace IDs: correlating one interaction end-to-end
|
|
24
|
+
|
|
25
|
+
`lib/diagnostics/trace.mjs` mints a ULID-shaped `trace_id` (26 chars,
|
|
26
|
+
time-sortable, no SDK dependency) and propagates it through the canonical hops
|
|
27
|
+
of an interaction:
|
|
28
|
+
|
|
29
|
+
```
|
|
30
|
+
item_received → classified → dispatched → session_opened …
|
|
31
|
+
↑ trace_id minted here, carried unchanged through every hop below
|
|
32
|
+
```
|
|
33
|
+
|
|
34
|
+
Mint once at the boundary where an interaction begins — a poller item or a
|
|
35
|
+
cadence tick — and run the rest of the work inside that context. (The examples
|
|
36
|
+
below import directly from `lib/diagnostics/` — the direct-`lib` path CLAUDE.md
|
|
37
|
+
sanctions for in-tree development; add short `./diagnostics/*` entries to the
|
|
38
|
+
package `exports` map when the daemon starts consuming these as a published
|
|
39
|
+
subpath.)
|
|
40
|
+
|
|
41
|
+
```js
|
|
42
|
+
import { mintTraceId, withTrace, childSpan, currentTraceId } from "@cohortapp/agent-sdk/lib/diagnostics/trace.mjs";
|
|
43
|
+
|
|
44
|
+
const traceId = mintTraceId();
|
|
45
|
+
await withTrace(traceId, async () => {
|
|
46
|
+
// anywhere beneath here, however deep the await chain:
|
|
47
|
+
currentTraceId(); // → traceId
|
|
48
|
+
|
|
49
|
+
// each hop extends the span path without changing the trace_id:
|
|
50
|
+
await withTrace(childSpan("classify"), async () => { /* … */ });
|
|
51
|
+
await withTrace(childSpan("dispatch"), async () => { /* … */ });
|
|
52
|
+
});
|
|
53
|
+
```
|
|
54
|
+
|
|
55
|
+
Propagation uses `AsyncLocalStorage`, so deep callees read the current trace with
|
|
56
|
+
`currentTrace()` / `currentTraceId()` without threading it through every
|
|
57
|
+
function signature. Span paths are dotted and human-readable
|
|
58
|
+
(`root.classify.send`), giving a cheap parent/child lattice.
|
|
59
|
+
|
|
60
|
+
When work crosses a process or queue boundary — a spawned `claude --print`
|
|
61
|
+
sub-session, a serialized inbox item — carry the context as plain fields and
|
|
62
|
+
rebuild it on the far side:
|
|
63
|
+
|
|
64
|
+
```js
|
|
65
|
+
import { traceHeaders, traceFromHeaders } from "@cohortapp/agent-sdk/lib/diagnostics/trace.mjs";
|
|
66
|
+
|
|
67
|
+
// before the boundary:
|
|
68
|
+
const headers = traceHeaders(); // { trace_id, span } (or {} if none)
|
|
69
|
+
|
|
70
|
+
// after the boundary (child process / consumer):
|
|
71
|
+
const ctx = traceFromHeaders(received); // { trace_id, span } or null
|
|
72
|
+
await withTrace(ctx ?? mintTraceId(), async () => { /* … */ });
|
|
73
|
+
```
|
|
74
|
+
|
|
75
|
+
Nothing here throws: an un-instrumented call site that asks for the current
|
|
76
|
+
trace simply gets `null`, and a boundary that didn't carry a trace mints a fresh
|
|
77
|
+
one rather than failing. Correlation degrades gracefully; it never bricks the
|
|
78
|
+
path it observes.
|
|
79
|
+
|
|
80
|
+
---
|
|
81
|
+
|
|
82
|
+
## 2. The diagnostic-event stream
|
|
83
|
+
|
|
84
|
+
`lib/diagnostics/events.mjs` is the one typed event contract every hot path can
|
|
85
|
+
emit onto. Each event appends a single JSON line to a date-stamped stream at
|
|
86
|
+
`logs/diagnostics/<YYYY-MM-DD>.jsonl` (via the shared atomic appender), matching
|
|
87
|
+
maestro's existing JSONL logging idiom.
|
|
88
|
+
|
|
89
|
+
The event-type set is **closed** — eight types that trace the interaction:
|
|
90
|
+
|
|
91
|
+
| type | emitted when |
|
|
92
|
+
| ---------------- | ---------------------------------------------- |
|
|
93
|
+
| `item_received` | inbound message/tick admitted (interaction start) |
|
|
94
|
+
| `classified` | classifier verdict produced |
|
|
95
|
+
| `dispatched` | a session spawn is decided/launched |
|
|
96
|
+
| `session_opened` | a `claude` sub-session starts |
|
|
97
|
+
| `session_closed` | a `claude` sub-session ends |
|
|
98
|
+
| `sent` | an outbound message leaves the agent (interaction end) |
|
|
99
|
+
| `guard_fail` | a governor/breaker/budget/permission gate refused work |
|
|
100
|
+
| `error` | an unexpected failure on the path |
|
|
101
|
+
|
|
102
|
+
An unknown type is coerced to `error` (with the offending value preserved at
|
|
103
|
+
`attrs._invalid_type`) rather than silently widening the schema.
|
|
104
|
+
|
|
105
|
+
```js
|
|
106
|
+
import { emitEvent, EVENT_TYPES } from "@cohortapp/agent-sdk/lib/diagnostics/events.mjs";
|
|
107
|
+
|
|
108
|
+
emitEvent({
|
|
109
|
+
type: EVENT_TYPES.ITEM_RECEIVED,
|
|
110
|
+
attrs: { source: "slack", item_id: "C123.456" },
|
|
111
|
+
});
|
|
112
|
+
// trace_id/span are filled from the ambient withTrace context automatically.
|
|
113
|
+
```
|
|
114
|
+
|
|
115
|
+
Every row has the shape `{ ts, type, trace_id, span, attrs }`. Because
|
|
116
|
+
`trace_id` is the same across every hop of one interaction, the whole thing is a
|
|
117
|
+
`grep`/`jq` away:
|
|
118
|
+
|
|
119
|
+
```bash
|
|
120
|
+
# everything that happened for one interaction, in order:
|
|
121
|
+
jq -c 'select(.trace_id == "01J…")' logs/diagnostics/2026-06-11.jsonl
|
|
122
|
+
```
|
|
123
|
+
|
|
124
|
+
### Measuring the <2 min DM SLO
|
|
125
|
+
|
|
126
|
+
The SLO is now a computable number: per `trace_id`, take the first
|
|
127
|
+
`item_received` and the last `sent`, and the delta is the user-perceived
|
|
128
|
+
latency.
|
|
129
|
+
|
|
130
|
+
```bash
|
|
131
|
+
jq -s '
|
|
132
|
+
group_by(.trace_id)[]
|
|
133
|
+
| { trace_id: .[0].trace_id,
|
|
134
|
+
start: (map(select(.type=="item_received")) | min_by(.ts) | .ts),
|
|
135
|
+
end: (map(select(.type=="sent")) | max_by(.ts) | .ts) }
|
|
136
|
+
| select(.start and .end)
|
|
137
|
+
| .latency_s = ((.end|fromdateiso8601) - (.start|fromdateiso8601))
|
|
138
|
+
' logs/diagnostics/2026-06-11.jsonl
|
|
139
|
+
```
|
|
140
|
+
|
|
141
|
+
`emitEvent` **never throws**. A bad directory, an unwritable disk, a
|
|
142
|
+
non-serializable attr — all degrade to a `false` return. Diagnostics must not be
|
|
143
|
+
able to take down the path they observe, so it is safe to sprinkle `emitEvent`
|
|
144
|
+
liberally through the daemon's hot paths.
|
|
145
|
+
|
|
146
|
+
---
|
|
147
|
+
|
|
148
|
+
## 3. Claude Code native OTLP — the cheap 70%
|
|
149
|
+
|
|
150
|
+
For a Claude-Code fleet, most observability is "turn on the env vars". Claude
|
|
151
|
+
Code natively emits OpenTelemetry **metrics, logs, and traces** — including
|
|
152
|
+
cost-per-session in USD, `api_error` / `api_refusal` / `tool_decision` events,
|
|
153
|
+
and `TRACEPARENT` inheritance — once telemetry is enabled. There is no SDK to
|
|
154
|
+
add; `lib/diagnostics/otel.mjs` is a pure builder that produces the env block.
|
|
155
|
+
|
|
156
|
+
```js
|
|
157
|
+
import { buildOtelEnv } from "@cohortapp/agent-sdk/lib/diagnostics/otel.mjs";
|
|
158
|
+
|
|
159
|
+
// identity is the config/agent.json record; config is the observability block.
|
|
160
|
+
const otelEnv = buildOtelEnv({ identity, config: observabilityConfig });
|
|
161
|
+
|
|
162
|
+
// spread into a spawned sub-session's env, or render into managed settings:
|
|
163
|
+
spawn(claudeBin, args, { env: { ...process.env, ...otelEnv } });
|
|
164
|
+
```
|
|
165
|
+
|
|
166
|
+
It is **disabled by default**: with no config and `MAESTRO_OTEL` unset,
|
|
167
|
+
`buildOtelEnv` returns `{}`, so spreading it is a no-op and the agent emits
|
|
168
|
+
nothing. Enable it with `MAESTRO_OTEL=1` (or `config.enabled: true`). When
|
|
169
|
+
enabled it returns:
|
|
170
|
+
|
|
171
|
+
| env var | value |
|
|
172
|
+
| ------------------------------ | ------------------------------------------------ |
|
|
173
|
+
| `CLAUDE_CODE_ENABLE_TELEMETRY` | `1` |
|
|
174
|
+
| `OTEL_METRICS_EXPORTER` | `otlp` (override via config/env) |
|
|
175
|
+
| `OTEL_LOGS_EXPORTER` | `otlp` |
|
|
176
|
+
| `OTEL_TRACES_EXPORTER` | `otlp` |
|
|
177
|
+
| `OTEL_EXPORTER_OTLP_PROTOCOL` | `http/protobuf` (or `grpc` / `http/json`) |
|
|
178
|
+
| `OTEL_EXPORTER_OTLP_ENDPOINT` | your collector (only when configured) |
|
|
179
|
+
| `OTEL_EXPORTER_OTLP_HEADERS` | auth headers (only when configured) |
|
|
180
|
+
| `OTEL_METRIC_EXPORT_INTERVAL` | ms between metric exports (only when configured) |
|
|
181
|
+
| `OTEL_LOGS_EXPORT_INTERVAL` | ms between log exports (only when configured) |
|
|
182
|
+
| `OTEL_RESOURCE_ATTRIBUTES` | `service.name`, `service.version`, the agent id |
|
|
183
|
+
|
|
184
|
+
Optional knobs (endpoint, headers, intervals) are emitted **only** when you set
|
|
185
|
+
them, so Claude Code's own OTLP defaults apply otherwise — the builder never
|
|
186
|
+
clobbers a default with a blank.
|
|
187
|
+
|
|
188
|
+
### Resource attributes: attributing signals to the right agent
|
|
189
|
+
|
|
190
|
+
`OTEL_RESOURCE_ATTRIBUTES` is what lets a fleet collector tell 60 Mac minis
|
|
191
|
+
apart. The builder stamps `service.name` (default `maestro-agent`) plus the agent
|
|
192
|
+
id — derived from `config/agent.json` (`agentId` → `repoSlug` → slugified name) —
|
|
193
|
+
as both `service.instance.id` and a friendly `agent.id`. Pass extra attributes
|
|
194
|
+
(e.g. `deployment.environment`) via `config.resourceAttributes`.
|
|
195
|
+
|
|
196
|
+
Values are sanitized so a stray `,` or `=` inside an attribute can't corrupt the
|
|
197
|
+
`k=v,k=v` list.
|
|
198
|
+
|
|
199
|
+
---
|
|
200
|
+
|
|
201
|
+
## 4. Enabling OTLP fleet-wide via managed settings
|
|
202
|
+
|
|
203
|
+
The point of a fleet is that you flip telemetry on **once**, centrally, not by
|
|
204
|
+
SSHing into 60 machines. Claude Code reads an `env` block from its settings
|
|
205
|
+
files, and managed/admin settings take precedence over per-user settings — so
|
|
206
|
+
the operator-controlled managed settings are where fleet-wide telemetry belongs.
|
|
207
|
+
|
|
208
|
+
The env map `buildOtelEnv` returns is exactly what goes in that `env` block:
|
|
209
|
+
|
|
210
|
+
```jsonc
|
|
211
|
+
// managed settings (operator-controlled, highest precedence)
|
|
212
|
+
{
|
|
213
|
+
"env": {
|
|
214
|
+
"CLAUDE_CODE_ENABLE_TELEMETRY": "1",
|
|
215
|
+
"OTEL_METRICS_EXPORTER": "otlp",
|
|
216
|
+
"OTEL_LOGS_EXPORTER": "otlp",
|
|
217
|
+
"OTEL_TRACES_EXPORTER": "otlp",
|
|
218
|
+
"OTEL_EXPORTER_OTLP_PROTOCOL": "http/protobuf",
|
|
219
|
+
"OTEL_EXPORTER_OTLP_ENDPOINT": "https://otel-collector.fleet.internal:4318",
|
|
220
|
+
"OTEL_EXPORTER_OTLP_HEADERS": "Authorization=Bearer <collector-token>",
|
|
221
|
+
"OTEL_RESOURCE_ATTRIBUTES": "service.name=maestro-agent,service.instance.id=alex-ai,agent.id=alex-ai"
|
|
222
|
+
}
|
|
223
|
+
}
|
|
224
|
+
```
|
|
225
|
+
|
|
226
|
+
Because the agent id belongs in `OTEL_RESOURCE_ATTRIBUTES` and differs per
|
|
227
|
+
machine, the practical pattern is: keep the shared exporter knobs (endpoint,
|
|
228
|
+
protocol, headers) in the org-wide managed template, and let each agent render
|
|
229
|
+
its own `OTEL_RESOURCE_ATTRIBUTES` from `buildOtelEnv({ identity })` at provision
|
|
230
|
+
time. The builder reads config first, then env, then defaults — so either layout
|
|
231
|
+
works.
|
|
232
|
+
|
|
233
|
+
A second, lighter path is per-spawn injection: the daemon calls `buildOtelEnv`
|
|
234
|
+
once and spreads the result into every `claude --print` sub-session it launches.
|
|
235
|
+
That keeps telemetry scoped to the agent's own sessions (Claude Code already
|
|
236
|
+
declines to leak `OTEL_*` into Bash/MCP/hook subprocesses, so an OTEL-instrumented
|
|
237
|
+
tool run via Bash won't accidentally inherit the agent's collector endpoint).
|
|
238
|
+
|
|
239
|
+
### What you get on the collector
|
|
240
|
+
|
|
241
|
+
- **Per-session cost in USD** and token usage — the missing fleet cost signal.
|
|
242
|
+
- **Behavioral events** — `api_error` rates, `api_refusal` spikes, per-tool
|
|
243
|
+
`tool_decision` baselines. Alert on patterns, not single failures: agents fail
|
|
244
|
+
silently by completing with the wrong output.
|
|
245
|
+
- **Traces** with `TRACEPARENT` inheritance, attributable per agent via the
|
|
246
|
+
resource attributes above.
|
|
247
|
+
|
|
248
|
+
Where the metrics land (collector → Prometheus/VictoriaMetrics + Grafana +
|
|
249
|
+
Alertmanager) and the GenAI-semconv export are the export-stack layer (gap G14)
|
|
250
|
+
and out of scope here; this guide gets the signal *off the agent* with the right
|
|
251
|
+
identity stamped on it.
|
|
252
|
+
|
|
253
|
+
---
|
|
254
|
+
|
|
255
|
+
## How the three layers fit together
|
|
256
|
+
|
|
257
|
+
The local event stream and the native OTLP export are complementary, not
|
|
258
|
+
redundant. The diagnostic-event JSONL is the always-on, never-throw, on-disk
|
|
259
|
+
record that survives with no collector and feeds the local SLO math and the
|
|
260
|
+
(forthcoming) off-machine audit copy. The OTLP export is the rich, fleet-level
|
|
261
|
+
signal — cost, refusals, traces — that a central collector aggregates across all
|
|
262
|
+
60 agents. The `trace_id` is the thread that ties them: stamp it into your
|
|
263
|
+
diagnostic events, and carry it in `OTEL_RESOURCE_ATTRIBUTES` /
|
|
264
|
+
`TRACEPARENT` context so a trace in your collector and the JSONL rows on a given
|
|
265
|
+
mini describe the same interaction.
|
|
@@ -0,0 +1,132 @@
|
|
|
1
|
+
# Org onboarding — admin checklist
|
|
2
|
+
|
|
3
|
+
The condensed version of [`DEPLOYMENT.md`](../../DEPLOYMENT.md). Use that for the
|
|
4
|
+
full story (architecture, Railway specifics, the credential broker in depth);
|
|
5
|
+
this is the running order an admin follows to bring an org online.
|
|
6
|
+
|
|
7
|
+
The shape: one Cohort server is the org source of truth (registry, hierarchy,
|
|
8
|
+
board, approvals, audit, and the encrypted credential vault); the agent Mac minis
|
|
9
|
+
lease from it. No web portal is needed for v1 — every step below is CLI- and
|
|
10
|
+
admin-token-driven against the deployed Cohort.
|
|
11
|
+
|
|
12
|
+
|
|
13
|
+
## Prerequisites
|
|
14
|
+
|
|
15
|
+
- Cohort deployed (Railway service from `services/cohort/`, or self-hosted via
|
|
16
|
+
`services/cohort/docker-compose.yml`). Build context is the maestro repo root.
|
|
17
|
+
- Three secrets set on the server, each via `openssl rand -hex 32` (or
|
|
18
|
+
`openssl genpkey -algorithm ed25519` for the signing key):
|
|
19
|
+
- `COHORT_ADMIN_TOKEN` — the admin bearer (pairing, kill switch, credentials).
|
|
20
|
+
- `COHORT_SIGNING_KEY` — signs snapshots / policy bundles / checkpoints.
|
|
21
|
+
- `COHORT_CRED_KEY` — AES-256-GCM key for credentials at rest (required for HA;
|
|
22
|
+
auto-generated and persisted `0600` on the volume for a single-node pilot).
|
|
23
|
+
- A reachable public HTTPS URL for the server, and its pinned TLS fingerprint.
|
|
24
|
+
|
|
25
|
+
|
|
26
|
+
## Steps
|
|
27
|
+
|
|
28
|
+
1. **Health check.** `cohort doctor` — confirm the registry loads, the schema is
|
|
29
|
+
present, the chain verifies, and the admin token is set.
|
|
30
|
+
|
|
31
|
+
2. **Ingest governance.** `cohort governance ingest --repo <org-governance>` —
|
|
32
|
+
populates hierarchy, decision rights, budgets, and policy bundles. The server
|
|
33
|
+
refuses to route handoffs and board assignment until decision rights exist, so
|
|
34
|
+
this comes before any agent does real work.
|
|
35
|
+
|
|
36
|
+
3. **Set org credentials ONCE.** For each provider, pipe the key on stdin so it
|
|
37
|
+
never hits shell history:
|
|
38
|
+
```bash
|
|
39
|
+
printf '%s' "$DEEPSEEK_API_KEY" | cohort credential put --provider deepseek
|
|
40
|
+
printf '%s' "$MOONSHOT_API_KEY" | cohort credential put --provider moonshot
|
|
41
|
+
printf '%s' "$OPENAI_API_KEY" | cohort credential put --provider openai
|
|
42
|
+
```
|
|
43
|
+
The value is encrypted at rest (AES-256-GCM under `COHORT_CRED_KEY`), never
|
|
44
|
+
logged. Add `--allowed-roles` / `--allowed-agents` to scope who may lease it.
|
|
45
|
+
This replaces putting provider keys on every mini.
|
|
46
|
+
|
|
47
|
+
4. **Pair the agents.** As each agent first boots and requests pairing:
|
|
48
|
+
```bash
|
|
49
|
+
cohort pair list
|
|
50
|
+
cohort pair approve <agentId> --scopes default
|
|
51
|
+
```
|
|
52
|
+
This mints the agent's short-lived token (printed once — capture it) carrying
|
|
53
|
+
`credential.use`, so the agent can lease provider keys on demand.
|
|
54
|
+
|
|
55
|
+
5. **Per agent:** drop `config/org.yaml` (Cohort URL + pinned fingerprint +
|
|
56
|
+
`roleRequested`) on the mini. The paired token is the only org secret it
|
|
57
|
+
holds. It needs its Anthropic billing
|
|
58
|
+
([`billing-console-keys.md`](billing-console-keys.md)) but **no** third-party
|
|
59
|
+
provider keys — those are leased from Cohort and never persisted.
|
|
60
|
+
|
|
61
|
+
|
|
62
|
+
## Cohort-driven agent init (what `maestro setup` pulls)
|
|
63
|
+
|
|
64
|
+
When an agent boots with the Cohort pull env set, `maestro setup` (and the
|
|
65
|
+
re-runnable `maestro sync`) treat the org as the source of truth: instead of
|
|
66
|
+
prompting the operator field-by-field, they PULL the agent's record + the org
|
|
67
|
+
context from Cohort and shape the agent's config from it.
|
|
68
|
+
|
|
69
|
+
### Env contract
|
|
70
|
+
|
|
71
|
+
| Var | Required | Purpose |
|
|
72
|
+
| --- | --- | --- |
|
|
73
|
+
| `COHORT_API_KEY` | yes | Bearer OrgApiKey for the org-data DTO reads AND the `/v1` read/RPC surface. hq's documented agent var. (`COHORT_API_TOKEN` / `COHORT_TOKEN` are accepted for back-compat.) |
|
|
74
|
+
| `COHORT_ORG_ID` | yes | Org id / slug — the tenant. Sent as `?slug=` on org-data reads and as the `x-org-id` pin on `/v1`. |
|
|
75
|
+
| `COHORT_AGENT_ID` | optional | This agent's member slug. When set it selects `members/<slug>` + keys relationships; when absent the pull resolves via `whoami`. |
|
|
76
|
+
| `COHORT_BASE` / `COHORT_API_URL` | optional | Server origin. Falls back to the persisted `config/org.yaml` endpoint. |
|
|
77
|
+
| `COHORT_AGENT_EMAIL` | optional | Email hint for `whoami` resolution when no `COHORT_AGENT_ID` is given. |
|
|
78
|
+
|
|
79
|
+
The pull is gated on `COHORT_API_KEY` + `COHORT_ORG_ID` (see
|
|
80
|
+
`lib/setup/enroll-from-cohort.cohortPullEnv`). Everything is **fail-open**: a
|
|
81
|
+
missing var or an unreachable server is a no-op and the manual prompts stand — a
|
|
82
|
+
degraded Cohort can never block setup.
|
|
83
|
+
|
|
84
|
+
### What init pulls — and how it SHAPES the agent
|
|
85
|
+
|
|
86
|
+
1. **Persona → `config/agent.json` (source of truth).** The MemberProfileDTO
|
|
87
|
+
maps firstName/lastName/title/email, the function/altitude archetype (derived
|
|
88
|
+
from role+team), and the supervisor (`principal`).
|
|
89
|
+
(`enroll-from-cohort.mapProfileToAgentConfig`)
|
|
90
|
+
2. **Mandates / responsibilities → `config/agent.json`.** From the profile
|
|
91
|
+
sections (`responsibilities` / `operating-principles` / communication tone).
|
|
92
|
+
3. **Charter(s) → `config/agent.json.charter`, rendered to
|
|
93
|
+
`config/operating-charter.md`.** The Cohort-authored `CharterDTO` is the
|
|
94
|
+
source `generate-charter.mjs` renders from (overriding the archetype skeleton).
|
|
95
|
+
4. **Org context → `config/org-context.json`.** One pass fetches self profile,
|
|
96
|
+
org chart, relationships, strategy (north star / levers / streams), hierarchy,
|
|
97
|
+
adopted decisions, policy bundle, and the ready board.
|
|
98
|
+
(`lib/org/bootstrap-context.bootstrapContext`)
|
|
99
|
+
5. **Work backlog → `state/backlog/wbs.yaml` + `state/queues/backlog.yaml` +
|
|
100
|
+
`config/priorities.yaml`.** `generate-backlog.mjs` reads
|
|
101
|
+
`config/org-context.json` and lets the fetched org context **shape** the
|
|
102
|
+
backlog: each org **strategy stream** becomes a leading WBS stream (intent =
|
|
103
|
+
its mission, north star woven in), and every **ready-board** item becomes a
|
|
104
|
+
concrete high-priority day-30 task. A standalone (un-enrolled) agent with no
|
|
105
|
+
cached context gets the archetype-only skeleton unchanged.
|
|
106
|
+
|
|
107
|
+
Ordering note: the operating-model section (order 60) seeds the archetype backlog
|
|
108
|
+
first; the org section (order 75) then caches `config/org-context.json` and
|
|
109
|
+
**re-runs `generate-backlog.mjs`** so the org context actually shapes the backlog
|
|
110
|
+
on the first pass. `maestro sync` re-pulls and re-materialises to keep the agent
|
|
111
|
+
in step as the org evolves.
|
|
112
|
+
|
|
113
|
+
|
|
114
|
+
## Ongoing
|
|
115
|
+
|
|
116
|
+
- **Rotate a key:** re-run `cohort credential put --provider <p>` with the new
|
|
117
|
+
value. Every agent picks it up on its next lease — nothing to push to the fleet.
|
|
118
|
+
- **Revoke a key:** `cohort credential revoke --provider <p>` — subsequent leases
|
|
119
|
+
fail closed.
|
|
120
|
+
- **Contain an agent:** the kill switch deactivates an agent and revokes its
|
|
121
|
+
token on the next presence beat (≤ ~60s), so it can no longer lease anything.
|
|
122
|
+
- **Audit:** every `credential.put` / `lease` / `revoke` appends one row to the
|
|
123
|
+
hash-chained `org_events` log recording provider + agent + time — never the
|
|
124
|
+
secret. `cohort credential list` shows metadata only.
|
|
125
|
+
|
|
126
|
+
|
|
127
|
+
## Need a portal?
|
|
128
|
+
|
|
129
|
+
Not for v1. When admin toil justifies it, add a thin admin UI over the
|
|
130
|
+
read-mostly `/ops` dashboard (same method registry, same auth, no new trust
|
|
131
|
+
boundary): self-serve org creation, a credential/keys form, and an agent-pairing
|
|
132
|
+
approval screen. Until then the steps above are the supported path.
|