@probelabs/visor 0.1.187-ee → 0.1.188
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/dist/{102.index.js → 140.index.js} +3 -3
- package/dist/{736.index.js → 142.index.js} +36 -36
- package/dist/{961.index.js → 223.index.js} +16 -16
- package/dist/{840.index.js → 676.index.js} +12 -12
- package/dist/{663.index.js → 85.index.js} +15 -15
- package/dist/action-cli-bridge.d.ts.map +1 -1
- package/dist/agent-protocol/a2a-frontend.d.ts.map +1 -1
- package/dist/agent-protocol/index.d.ts.map +1 -1
- package/dist/agent-protocol/push-notification-manager.d.ts.map +1 -1
- package/dist/agent-protocol/state-transitions.d.ts.map +1 -1
- package/dist/agent-protocol/task-evaluator.d.ts.map +1 -1
- package/dist/agent-protocol/task-live-update-slack.d.ts.map +1 -1
- package/dist/agent-protocol/task-live-update-teams.d.ts.map +1 -1
- package/dist/agent-protocol/task-live-update-telegram.d.ts.map +1 -1
- package/dist/agent-protocol/task-live-updates.d.ts.map +1 -1
- package/dist/agent-protocol/task-progress-tool.d.ts.map +1 -1
- package/dist/agent-protocol/task-queue.d.ts.map +1 -1
- package/dist/agent-protocol/task-store.d.ts.map +1 -1
- package/dist/agent-protocol/task-stream-manager.d.ts.map +1 -1
- package/dist/agent-protocol/task-trace-resolution.d.ts.map +1 -1
- package/dist/agent-protocol/tasks-cli-handler.d.ts.map +1 -1
- package/dist/agent-protocol/tasks-tui.d.ts.map +1 -1
- package/dist/agent-protocol/trace-serializer.d.ts.map +1 -1
- package/dist/agent-protocol/track-execution.d.ts.map +1 -1
- package/dist/agent-protocol/types.d.ts.map +1 -1
- package/dist/ai-review-service.d.ts.map +1 -1
- package/dist/check-execution-engine.d.ts.map +1 -1
- package/dist/cli-main.d.ts.map +1 -1
- package/dist/cli.d.ts.map +1 -1
- package/dist/commands.d.ts.map +1 -1
- package/dist/config/cli-handler.d.ts.map +1 -1
- package/dist/config/config-reloader.d.ts.map +1 -1
- package/dist/config/config-snapshot-store.d.ts.map +1 -1
- package/dist/config/config-watcher.d.ts.map +1 -1
- package/dist/config/types.d.ts.map +1 -1
- package/dist/config.d.ts.map +1 -1
- package/dist/cron-scheduler.d.ts.map +1 -1
- package/dist/debug-visualizer/debug-span-exporter.d.ts.map +1 -1
- package/dist/debug-visualizer/trace-reader.d.ts.map +1 -1
- package/dist/debug-visualizer/ws-server.d.ts.map +1 -1
- package/dist/dependency-resolver.d.ts.map +1 -1
- package/dist/email/adapter.d.ts.map +1 -1
- package/dist/email/client.d.ts.map +1 -1
- package/dist/email/markdown.d.ts.map +1 -1
- package/dist/email/polling-runner.d.ts.map +1 -1
- package/dist/engine/on-finish/orchestrator.d.ts.map +1 -1
- package/dist/engine/on-finish/utils.d.ts.map +1 -1
- package/dist/event-bus/event-bus.d.ts.map +1 -1
- package/dist/event-bus/types.d.ts.map +1 -1
- package/dist/event-mapper.d.ts.map +1 -1
- package/dist/failure-condition-evaluator.d.ts.map +1 -1
- package/dist/footer.d.ts.map +1 -1
- package/dist/frontends/email-frontend.d.ts.map +1 -1
- package/dist/frontends/github-frontend.d.ts.map +1 -1
- package/dist/frontends/host.d.ts.map +1 -1
- package/dist/frontends/ndjson-sink.d.ts.map +1 -1
- package/dist/frontends/slack-frontend.d.ts.map +1 -1
- package/dist/frontends/teams-frontend.d.ts.map +1 -1
- package/dist/frontends/telegram-frontend.d.ts.map +1 -1
- package/dist/frontends/whatsapp-frontend.d.ts.map +1 -1
- package/dist/generated/config-schema.d.ts.map +1 -1
- package/dist/git-repository-analyzer.d.ts.map +1 -1
- package/dist/github-auth.d.ts.map +1 -1
- package/dist/github-check-service.d.ts.map +1 -1
- package/dist/github-comments.d.ts.map +1 -1
- package/dist/github-reactions.d.ts.map +1 -1
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +8172 -9972
- package/dist/issue-filter.d.ts.map +1 -1
- package/dist/liquid-extensions.d.ts.map +1 -1
- package/dist/logger.d.ts.map +1 -1
- package/dist/mcp-job-manager.d.ts.map +1 -1
- package/dist/mcp-server.d.ts.map +1 -1
- package/dist/memory-store.d.ts.map +1 -1
- package/dist/output/traces/run-2026-08-22T04-10-00-135Z.ndjson +3148 -0
- package/dist/output-formatters.d.ts.map +1 -1
- package/dist/policy/default-engine.d.ts.map +1 -1
- package/dist/policy/index.d.ts.map +1 -1
- package/dist/policy/policy-check-command.d.ts.map +1 -1
- package/dist/policy/types.d.ts.map +1 -1
- package/dist/pr-analyzer.d.ts.map +1 -1
- package/dist/pr-detector.d.ts.map +1 -1
- package/dist/providers/a2a-check-provider.d.ts.map +1 -1
- package/dist/providers/ai-check-provider.d.ts.map +1 -1
- package/dist/providers/api-tool-executor.d.ts.map +1 -1
- package/dist/providers/check-provider-registry.d.ts.map +1 -1
- package/dist/providers/check-provider.interface.d.ts.map +1 -1
- package/dist/providers/claude-code-check-provider.d.ts.map +1 -1
- package/dist/providers/claude-code-types.d.ts.map +1 -1
- package/dist/providers/command-check-provider.d.ts.map +1 -1
- package/dist/providers/custom-tool-executor.d.ts.map +1 -1
- package/dist/providers/git-checkout-provider.d.ts.map +1 -1
- package/dist/providers/github-ops-provider.d.ts.map +1 -1
- package/dist/providers/http-check-provider.d.ts.map +1 -1
- package/dist/providers/http-client-provider.d.ts.map +1 -1
- package/dist/providers/http-input-provider.d.ts.map +1 -1
- package/dist/providers/human-input-check-provider.d.ts.map +1 -1
- package/dist/providers/index.d.ts.map +1 -1
- package/dist/providers/log-check-provider.d.ts.map +1 -1
- package/dist/providers/mcp-check-provider.d.ts.map +1 -1
- package/dist/providers/mcp-custom-sse-server.d.ts.map +1 -1
- package/dist/providers/mcp-tools.d.ts.map +1 -1
- package/dist/providers/memory-check-provider.d.ts.map +1 -1
- package/dist/providers/noop-check-provider.d.ts.map +1 -1
- package/dist/providers/script-check-provider.d.ts.map +1 -1
- package/dist/providers/utcp-check-provider.d.ts.map +1 -1
- package/dist/providers/workflow-check-provider.d.ts.map +1 -1
- package/dist/providers/workflow-tool-executor.d.ts.map +1 -1
- package/dist/reviewer.d.ts.map +1 -1
- package/dist/runners/config-reload-runtime.d.ts.map +1 -1
- package/dist/runners/graceful-restart.d.ts.map +1 -1
- package/dist/runners/mcp-server-runner.d.ts.map +1 -1
- package/dist/runners/process-cli-handler.d.ts.map +1 -1
- package/dist/runners/process-discovery.d.ts.map +1 -1
- package/dist/runners/runner-factory.d.ts.map +1 -1
- package/dist/runners/runner-host.d.ts.map +1 -1
- package/dist/runners/runner.d.ts.map +1 -1
- package/dist/runners/telemetry-init.d.ts.map +1 -1
- package/dist/sandbox/bubblewrap-sandbox.d.ts.map +1 -1
- package/dist/sandbox/cache-volume-manager.d.ts.map +1 -1
- package/dist/sandbox/check-runner.d.ts.map +1 -1
- package/dist/sandbox/compose-generator.d.ts.map +1 -1
- package/dist/sandbox/docker-compose-sandbox.d.ts.map +1 -1
- package/dist/sandbox/docker-image-sandbox.d.ts.map +1 -1
- package/dist/sandbox/env-filter.d.ts.map +1 -1
- package/dist/sandbox/index.d.ts.map +1 -1
- package/dist/sandbox/sandbox-manager.d.ts.map +1 -1
- package/dist/sandbox/sandbox-telemetry.d.ts.map +1 -1
- package/dist/sandbox/seatbelt-sandbox.d.ts.map +1 -1
- package/dist/sandbox/trace-ingester.d.ts.map +1 -1
- package/dist/sandbox/types.d.ts.map +1 -1
- package/dist/scheduler/cli-handler.d.ts.map +1 -1
- package/dist/scheduler/index.d.ts.map +1 -1
- package/dist/scheduler/message-trigger.d.ts.map +1 -1
- package/dist/scheduler/schedule-parser.d.ts.map +1 -1
- package/dist/scheduler/schedule-store.d.ts.map +1 -1
- package/dist/scheduler/schedule-tool.d.ts.map +1 -1
- package/dist/scheduler/scheduler.d.ts.map +1 -1
- package/dist/scheduler/store/index.d.ts.map +1 -1
- package/dist/scheduler/store/json-migrator.d.ts.map +1 -1
- package/dist/scheduler/store/sqlite-store.d.ts.map +1 -1
- package/dist/scheduler/store/types.d.ts.map +1 -1
- package/dist/sdk/{a2a-frontend-QVKJ7MVW.mjs → a2a-frontend-ISEEKHDN.mjs} +3 -3
- package/dist/sdk/{check-provider-registry-QUUL6JI2.mjs → check-provider-registry-DVKGIOS3.mjs} +6 -6
- package/dist/sdk/{chunk-HQCCT6WP.mjs → chunk-26CYHBIS.mjs} +203 -203
- package/dist/sdk/chunk-26CYHBIS.mjs.map +1 -0
- package/dist/sdk/{chunk-QLT42TX7.mjs → chunk-3RWJRAA5.mjs} +2 -2
- package/dist/sdk/{chunk-6LQEODDA.mjs → chunk-4VX6DV2G.mjs} +2 -2
- package/dist/sdk/chunk-4VX6DV2G.mjs.map +1 -0
- package/dist/sdk/{chunk-BBLBZVWC.mjs → chunk-IZCAV5EP.mjs} +3 -3
- package/dist/sdk/{chunk-PZADRRLX.mjs → chunk-WX3QPTJA.mjs} +2 -2
- package/dist/sdk/{dist-YLO6HUFD.mjs → dist-VBYEFQ6T.mjs} +85 -311
- package/dist/sdk/dist-VBYEFQ6T.mjs.map +1 -0
- package/dist/sdk/{email-frontend-6O454VL5.mjs → email-frontend-AE5TYWNC.mjs} +2 -2
- package/dist/sdk/{failure-condition-evaluator-USY3ISVA.mjs → failure-condition-evaluator-3KCCLM7Q.mjs} +4 -4
- package/dist/sdk/{github-frontend-2T5PWYD5.mjs → github-frontend-TVDKBISH.mjs} +4 -4
- package/dist/sdk/{host-UZESVA6Z.mjs → host-QZKTPGJC.mjs} +4 -4
- package/dist/sdk/{routing-TYXT3STD.mjs → routing-PCVZ4NF3.mjs} +5 -5
- package/dist/sdk/{schedule-tool-ODMIDBMT.mjs → schedule-tool-MBKRZFP7.mjs} +6 -6
- package/dist/sdk/{schedule-tool-handler-IQSKBFLS.mjs → schedule-tool-handler-7S3SONDU.mjs} +6 -6
- package/dist/sdk/sdk.js +916 -2290
- package/dist/sdk/sdk.js.map +1 -1
- package/dist/sdk/sdk.mjs +5 -5
- package/dist/sdk/{trace-helpers-AM2QE5UZ.mjs → trace-helpers-ZF36XBBN.mjs} +3 -3
- package/dist/sdk/{track-execution-VJJVJH6K.mjs → track-execution-XMGTAML7.mjs} +2 -2
- package/dist/sdk/{workflow-check-provider-XOWQYWTC.mjs → workflow-check-provider-IJLJKHIE.mjs} +6 -6
- package/dist/sdk.d.ts.map +1 -1
- package/dist/session-registry.d.ts.map +1 -1
- package/dist/slack/adapter.d.ts.map +1 -1
- package/dist/slack/cache-prewarmer.d.ts.map +1 -1
- package/dist/slack/client.d.ts.map +1 -1
- package/dist/slack/markdown.d.ts.map +1 -1
- package/dist/slack/prompt-state.d.ts.map +1 -1
- package/dist/slack/rate-limiter.d.ts.map +1 -1
- package/dist/slack/schedule-tool-handler.d.ts.map +1 -1
- package/dist/slack/signature.d.ts.map +1 -1
- package/dist/slack/slack-output-adapter.d.ts.map +1 -1
- package/dist/slack/socket-runner.d.ts +1 -0
- package/dist/slack/socket-runner.d.ts.map +1 -1
- package/dist/slack/thread-cache.d.ts.map +1 -1
- package/dist/snapshot-store.d.ts.map +1 -1
- package/dist/state-machine/context/build-engine-context.d.ts.map +1 -1
- package/dist/state-machine/context/workflow-inputs.d.ts.map +1 -1
- package/dist/state-machine/dispatch/debounce-manager.d.ts.map +1 -1
- package/dist/state-machine/dispatch/dependency-gating.d.ts.map +1 -1
- package/dist/state-machine/dispatch/execution-invoker.d.ts.map +1 -1
- package/dist/state-machine/dispatch/foreach-processor.d.ts.map +1 -1
- package/dist/state-machine/dispatch/history-snapshot.d.ts.map +1 -1
- package/dist/state-machine/dispatch/on-init-handlers.d.ts.map +1 -1
- package/dist/state-machine/dispatch/policy-gate.d.ts.map +1 -1
- package/dist/state-machine/dispatch/renderer-schema.d.ts.map +1 -1
- package/dist/state-machine/dispatch/sandbox-routing.d.ts.map +1 -1
- package/dist/state-machine/dispatch/stats-manager.d.ts.map +1 -1
- package/dist/state-machine/dispatch/template-renderer.d.ts.map +1 -1
- package/dist/state-machine/execution/summary.d.ts.map +1 -1
- package/dist/state-machine/runner.d.ts.map +1 -1
- package/dist/state-machine/states/check-running.d.ts.map +1 -1
- package/dist/state-machine/states/completed.d.ts.map +1 -1
- package/dist/state-machine/states/error.d.ts.map +1 -1
- package/dist/state-machine/states/init.d.ts.map +1 -1
- package/dist/state-machine/states/level-dispatch.d.ts.map +1 -1
- package/dist/state-machine/states/plan-ready.d.ts.map +1 -1
- package/dist/state-machine/states/routing.d.ts.map +1 -1
- package/dist/state-machine/states/wave-planning.d.ts.map +1 -1
- package/dist/state-machine/workflow-projection.d.ts.map +1 -1
- package/dist/state-machine-execution-engine.d.ts.map +1 -1
- package/dist/teams/adapter.d.ts.map +1 -1
- package/dist/teams/client.d.ts.map +1 -1
- package/dist/teams/markdown.d.ts.map +1 -1
- package/dist/teams/webhook-runner.d.ts.map +1 -1
- package/dist/telegram/adapter.d.ts.map +1 -1
- package/dist/telegram/client.d.ts.map +1 -1
- package/dist/telegram/markdown.d.ts.map +1 -1
- package/dist/telegram/polling-runner.d.ts.map +1 -1
- package/dist/telemetry/fallback-ndjson.d.ts.map +1 -1
- package/dist/telemetry/file-span-exporter.d.ts.map +1 -1
- package/dist/telemetry/lazy-otel.d.ts.map +1 -1
- package/dist/telemetry/metrics.d.ts.map +1 -1
- package/dist/telemetry/opentelemetry.d.ts.map +1 -1
- package/dist/telemetry/state-capture.d.ts.map +1 -1
- package/dist/telemetry/trace-helpers.d.ts.map +1 -1
- package/dist/telemetry/trace-report-exporter.d.ts.map +1 -1
- package/dist/test-runner/assertions.d.ts.map +1 -1
- package/dist/test-runner/conversation-sugar.d.ts.map +1 -1
- package/dist/test-runner/core/environment.d.ts.map +1 -1
- package/dist/test-runner/core/fixture.d.ts.map +1 -1
- package/dist/test-runner/core/flow-stage.d.ts.map +1 -1
- package/dist/test-runner/core/mocks.d.ts.map +1 -1
- package/dist/test-runner/core/test-execution-wrapper.d.ts.map +1 -1
- package/dist/test-runner/evaluators.d.ts.map +1 -1
- package/dist/test-runner/fixture-loader.d.ts.map +1 -1
- package/dist/test-runner/index.d.ts.map +1 -1
- package/dist/test-runner/llm-judge.d.ts.map +1 -1
- package/dist/test-runner/recorders/github-recorder.d.ts.map +1 -1
- package/dist/test-runner/recorders/global-recorder.d.ts.map +1 -1
- package/dist/test-runner/recorders/slack-recorder.d.ts.map +1 -1
- package/dist/test-runner/utils/selectors.d.ts.map +1 -1
- package/dist/test-runner/validator.d.ts.map +1 -1
- package/dist/traces/run-2026-08-22T04-10-00-135Z.ndjson +3148 -0
- package/dist/tui/chat-runner.d.ts.map +1 -1
- package/dist/tui/chat-state.d.ts.map +1 -1
- package/dist/tui/chat-tui.d.ts.map +1 -1
- package/dist/tui/components/chat-box.d.ts.map +1 -1
- package/dist/tui/components/input-bar.d.ts.map +1 -1
- package/dist/tui/components/status-bar.d.ts.map +1 -1
- package/dist/tui/components/trace-viewer.d.ts.map +1 -1
- package/dist/tui/index.d.ts.map +1 -1
- package/dist/tui/tui-frontend.d.ts.map +1 -1
- package/dist/types/bot.d.ts.map +1 -1
- package/dist/types/cli.d.ts.map +1 -1
- package/dist/types/config.d.ts.map +1 -1
- package/dist/types/engine.d.ts.map +1 -1
- package/dist/types/execution.d.ts.map +1 -1
- package/dist/types/git-checkout.d.ts.map +1 -1
- package/dist/types/github.d.ts.map +1 -1
- package/dist/types/workflow.d.ts.map +1 -1
- package/dist/utils/author-permissions.d.ts.map +1 -1
- package/dist/utils/child-process-error-handler.d.ts.map +1 -1
- package/dist/utils/command-executor.d.ts.map +1 -1
- package/dist/utils/comment-metadata.d.ts.map +1 -1
- package/dist/utils/config-loader.d.ts.map +1 -1
- package/dist/utils/config-merger.d.ts.map +1 -1
- package/dist/utils/diff-processor.d.ts.map +1 -1
- package/dist/utils/env-exposure.d.ts.map +1 -1
- package/dist/utils/env-resolver.d.ts.map +1 -1
- package/dist/utils/fair-concurrency-limiter.d.ts.map +1 -1
- package/dist/utils/file-exclusion.d.ts.map +1 -1
- package/dist/utils/head-sha.d.ts.map +1 -1
- package/dist/utils/human-id.d.ts.map +1 -1
- package/dist/utils/instance-id.d.ts.map +1 -1
- package/dist/utils/interactive-prompt.d.ts.map +1 -1
- package/dist/utils/issue-normalizer.d.ts.map +1 -1
- package/dist/utils/json-text-extractor.d.ts.map +1 -1
- package/dist/utils/mermaid-telemetry.d.ts.map +1 -1
- package/dist/utils/oauth2-token-cache.d.ts.map +1 -1
- package/dist/utils/rate-limiter.d.ts.map +1 -1
- package/dist/utils/sandbox.d.ts.map +1 -1
- package/dist/utils/script-memory-ops.d.ts.map +1 -1
- package/dist/utils/script-tool-environment.d.ts.map +1 -1
- package/dist/utils/stdin-reader.d.ts.map +1 -1
- package/dist/utils/template-context.d.ts.map +1 -1
- package/dist/utils/tool-resolver.d.ts.map +1 -1
- package/dist/utils/toolkit-expander.d.ts.map +1 -1
- package/dist/utils/tracer-init.d.ts.map +1 -1
- package/dist/utils/ui-helpers.d.ts.map +1 -1
- package/dist/utils/user-facing-error.d.ts.map +1 -1
- package/dist/utils/workspace-manager.d.ts.map +1 -1
- package/dist/utils/worktree-cleanup.d.ts.map +1 -1
- package/dist/utils/worktree-manager.d.ts.map +1 -1
- package/dist/webhook-server.d.ts.map +1 -1
- package/dist/whatsapp/adapter.d.ts.map +1 -1
- package/dist/whatsapp/client.d.ts.map +1 -1
- package/dist/whatsapp/markdown.d.ts.map +1 -1
- package/dist/whatsapp/webhook-runner.d.ts.map +1 -1
- package/dist/workflow-executor.d.ts.map +1 -1
- package/dist/workflow-registry.d.ts.map +1 -1
- package/package.json +1 -1
- package/dist/enterprise/license/validator.d.ts +0 -39
- package/dist/enterprise/license/validator.d.ts.map +0 -1
- package/dist/enterprise/loader.d.ts +0 -25
- package/dist/enterprise/loader.d.ts.map +0 -1
- package/dist/enterprise/policy/opa-compiler.d.ts +0 -37
- package/dist/enterprise/policy/opa-compiler.d.ts.map +0 -1
- package/dist/enterprise/policy/opa-http-evaluator.d.ts +0 -36
- package/dist/enterprise/policy/opa-http-evaluator.d.ts.map +0 -1
- package/dist/enterprise/policy/opa-policy-engine.d.ts +0 -48
- package/dist/enterprise/policy/opa-policy-engine.d.ts.map +0 -1
- package/dist/enterprise/policy/opa-wasm-evaluator.d.ts +0 -34
- package/dist/enterprise/policy/opa-wasm-evaluator.d.ts.map +0 -1
- package/dist/enterprise/policy/policy-input-builder.d.ts +0 -122
- package/dist/enterprise/policy/policy-input-builder.d.ts.map +0 -1
- package/dist/enterprise/scheduler/knex-store.d.ts +0 -47
- package/dist/enterprise/scheduler/knex-store.d.ts.map +0 -1
- package/dist/sdk/a2a-frontend-7EGXSULE.mjs +0 -1751
- package/dist/sdk/a2a-frontend-7EGXSULE.mjs.map +0 -1
- package/dist/sdk/check-provider-registry-IGNTM4MW.mjs +0 -32
- package/dist/sdk/chunk-6DDNEBZ7.mjs +0 -6119
- package/dist/sdk/chunk-6DDNEBZ7.mjs.map +0 -1
- package/dist/sdk/chunk-6LQEODDA.mjs.map +0 -1
- package/dist/sdk/chunk-7XKHFRPN.mjs +0 -739
- package/dist/sdk/chunk-D6O5SCPC.mjs +0 -621
- package/dist/sdk/chunk-D6O5SCPC.mjs.map +0 -1
- package/dist/sdk/chunk-H2ZWNJJO.mjs +0 -204
- package/dist/sdk/chunk-H2ZWNJJO.mjs.map +0 -1
- package/dist/sdk/chunk-HMVD3AEC.mjs +0 -47064
- package/dist/sdk/chunk-HMVD3AEC.mjs.map +0 -1
- package/dist/sdk/chunk-HQCCT6WP.mjs.map +0 -1
- package/dist/sdk/chunk-IY5PQ5EN.mjs +0 -1724
- package/dist/sdk/chunk-IY5PQ5EN.mjs.map +0 -1
- package/dist/sdk/chunk-PDQTEBOJ.mjs +0 -213
- package/dist/sdk/chunk-PDQTEBOJ.mjs.map +0 -1
- package/dist/sdk/chunk-PUHU6UY6.mjs +0 -391
- package/dist/sdk/chunk-PUHU6UY6.mjs.map +0 -1
- package/dist/sdk/chunk-PZADRRLX.mjs.map +0 -1
- package/dist/sdk/chunk-RQDLVMER.mjs +0 -1507
- package/dist/sdk/chunk-RQDLVMER.mjs.map +0 -1
- package/dist/sdk/chunk-TSX3YS3F.mjs +0 -825
- package/dist/sdk/chunk-TSX3YS3F.mjs.map +0 -1
- package/dist/sdk/chunk-WZQMTD7W.mjs +0 -33
- package/dist/sdk/chunk-WZQMTD7W.mjs.map +0 -1
- package/dist/sdk/chunk-XXAEN5KU.mjs +0 -197
- package/dist/sdk/chunk-XXAEN5KU.mjs.map +0 -1
- package/dist/sdk/chunk-ZCBVXBKG.mjs +0 -1150
- package/dist/sdk/chunk-ZCBVXBKG.mjs.map +0 -1
- package/dist/sdk/config-BI5ZXG6D.mjs +0 -16
- package/dist/sdk/dist-NERCHNRR.mjs +0 -7955
- package/dist/sdk/dist-NERCHNRR.mjs.map +0 -1
- package/dist/sdk/dist-YLO6HUFD.mjs.map +0 -1
- package/dist/sdk/email-frontend-JE7H3LBC.mjs +0 -701
- package/dist/sdk/email-frontend-JE7H3LBC.mjs.map +0 -1
- package/dist/sdk/failure-condition-evaluator-7WHZUYDC.mjs +0 -18
- package/dist/sdk/github-frontend-RGK4DPRI.mjs +0 -1394
- package/dist/sdk/github-frontend-RGK4DPRI.mjs.map +0 -1
- package/dist/sdk/host-YWXWROIE.mjs +0 -87
- package/dist/sdk/host-YWXWROIE.mjs.map +0 -1
- package/dist/sdk/knex-store-KCMFAMH5.mjs +0 -527
- package/dist/sdk/knex-store-KCMFAMH5.mjs.map +0 -1
- package/dist/sdk/loader-35YWX5UQ.mjs +0 -89
- package/dist/sdk/loader-35YWX5UQ.mjs.map +0 -1
- package/dist/sdk/opa-policy-engine-FY5D45YS.mjs +0 -655
- package/dist/sdk/opa-policy-engine-FY5D45YS.mjs.map +0 -1
- package/dist/sdk/routing-PHHRW2C7.mjs +0 -26
- package/dist/sdk/schedule-tool-ITD445EO.mjs +0 -38
- package/dist/sdk/schedule-tool-ITD445EO.mjs.map +0 -1
- package/dist/sdk/schedule-tool-ODMIDBMT.mjs.map +0 -1
- package/dist/sdk/schedule-tool-handler-5WPHFBOG.mjs +0 -42
- package/dist/sdk/schedule-tool-handler-5WPHFBOG.mjs.map +0 -1
- package/dist/sdk/schedule-tool-handler-IQSKBFLS.mjs.map +0 -1
- package/dist/sdk/session-registry-6PV6SGEJ.mjs +0 -10
- package/dist/sdk/session-registry-6PV6SGEJ.mjs.map +0 -1
- package/dist/sdk/slack-frontend-H7PX5GE7.mjs +0 -985
- package/dist/sdk/slack-frontend-H7PX5GE7.mjs.map +0 -1
- package/dist/sdk/task-evaluator-H3BXC7SE.mjs +0 -263
- package/dist/sdk/task-evaluator-H3BXC7SE.mjs.map +0 -1
- package/dist/sdk/teams-frontend-HCT4MTY4.mjs +0 -342
- package/dist/sdk/teams-frontend-HCT4MTY4.mjs.map +0 -1
- package/dist/sdk/telegram-frontend-YQRYDKPN.mjs +0 -586
- package/dist/sdk/telegram-frontend-YQRYDKPN.mjs.map +0 -1
- package/dist/sdk/trace-helpers-AM2QE5UZ.mjs.map +0 -1
- package/dist/sdk/trace-helpers-OMF4C24T.mjs +0 -31
- package/dist/sdk/trace-helpers-OMF4C24T.mjs.map +0 -1
- package/dist/sdk/trace-reader-OVE4DL2D.mjs +0 -270
- package/dist/sdk/trace-reader-OVE4DL2D.mjs.map +0 -1
- package/dist/sdk/trace-serializer-EBHTHZYT.mjs +0 -24
- package/dist/sdk/trace-serializer-EBHTHZYT.mjs.map +0 -1
- package/dist/sdk/track-execution-BULXL2XD.mjs +0 -249
- package/dist/sdk/track-execution-BULXL2XD.mjs.map +0 -1
- package/dist/sdk/utcp-check-provider-Q4PD5EP2.mjs +0 -16
- package/dist/sdk/utcp-check-provider-Q4PD5EP2.mjs.map +0 -1
- package/dist/sdk/validator-XTZJZZJH.mjs +0 -134
- package/dist/sdk/validator-XTZJZZJH.mjs.map +0 -1
- package/dist/sdk/whatsapp-frontend-72XEIUIR.mjs +0 -438
- package/dist/sdk/whatsapp-frontend-72XEIUIR.mjs.map +0 -1
- package/dist/sdk/workflow-check-provider-OVZDCL4E.mjs +0 -32
- package/dist/sdk/workflow-check-provider-OVZDCL4E.mjs.map +0 -1
- package/dist/sdk/workflow-check-provider-XOWQYWTC.mjs.map +0 -1
- /package/dist/sdk/{a2a-frontend-QVKJ7MVW.mjs.map → a2a-frontend-ISEEKHDN.mjs.map} +0 -0
- /package/dist/sdk/{check-provider-registry-IGNTM4MW.mjs.map → check-provider-registry-DVKGIOS3.mjs.map} +0 -0
- /package/dist/sdk/{chunk-QLT42TX7.mjs.map → chunk-3RWJRAA5.mjs.map} +0 -0
- /package/dist/sdk/{chunk-BBLBZVWC.mjs.map → chunk-IZCAV5EP.mjs.map} +0 -0
- /package/dist/sdk/{chunk-7XKHFRPN.mjs.map → chunk-WX3QPTJA.mjs.map} +0 -0
- /package/dist/sdk/{email-frontend-6O454VL5.mjs.map → email-frontend-AE5TYWNC.mjs.map} +0 -0
- /package/dist/sdk/{check-provider-registry-QUUL6JI2.mjs.map → failure-condition-evaluator-3KCCLM7Q.mjs.map} +0 -0
- /package/dist/sdk/{github-frontend-2T5PWYD5.mjs.map → github-frontend-TVDKBISH.mjs.map} +0 -0
- /package/dist/sdk/{host-UZESVA6Z.mjs.map → host-QZKTPGJC.mjs.map} +0 -0
- /package/dist/sdk/{config-BI5ZXG6D.mjs.map → routing-PCVZ4NF3.mjs.map} +0 -0
- /package/dist/sdk/{failure-condition-evaluator-7WHZUYDC.mjs.map → schedule-tool-MBKRZFP7.mjs.map} +0 -0
- /package/dist/sdk/{failure-condition-evaluator-USY3ISVA.mjs.map → schedule-tool-handler-7S3SONDU.mjs.map} +0 -0
- /package/dist/sdk/{routing-PHHRW2C7.mjs.map → trace-helpers-ZF36XBBN.mjs.map} +0 -0
- /package/dist/sdk/{track-execution-VJJVJH6K.mjs.map → track-execution-XMGTAML7.mjs.map} +0 -0
- /package/dist/sdk/{routing-TYXT3STD.mjs.map → workflow-check-provider-IJLJKHIE.mjs.map} +0 -0
|
@@ -1,16 +0,0 @@
|
|
|
1
|
-
import {
|
|
2
|
-
UtcpCheckProvider,
|
|
3
|
-
init_utcp_check_provider
|
|
4
|
-
} from "./chunk-TSX3YS3F.mjs";
|
|
5
|
-
import "./chunk-4HIWZA6M.mjs";
|
|
6
|
-
import "./chunk-25IC7KXZ.mjs";
|
|
7
|
-
import "./chunk-LW3INISN.mjs";
|
|
8
|
-
import "./chunk-4MHHELVZ.mjs";
|
|
9
|
-
import "./chunk-6E625R3C.mjs";
|
|
10
|
-
import "./chunk-B2OUZAWY.mjs";
|
|
11
|
-
import "./chunk-J7LXIPZS.mjs";
|
|
12
|
-
init_utcp_check_provider();
|
|
13
|
-
export {
|
|
14
|
-
UtcpCheckProvider
|
|
15
|
-
};
|
|
16
|
-
//# sourceMappingURL=utcp-check-provider-Q4PD5EP2.mjs.map
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"sources":[],"sourcesContent":[],"mappings":"","names":[]}
|
|
@@ -1,134 +0,0 @@
|
|
|
1
|
-
import {
|
|
2
|
-
__esm
|
|
3
|
-
} from "./chunk-J7LXIPZS.mjs";
|
|
4
|
-
|
|
5
|
-
// src/enterprise/license/validator.ts
|
|
6
|
-
import * as crypto from "crypto";
|
|
7
|
-
import * as fs from "fs";
|
|
8
|
-
import * as path from "path";
|
|
9
|
-
var LicenseValidator;
|
|
10
|
-
var init_validator = __esm({
|
|
11
|
-
"src/enterprise/license/validator.ts"() {
|
|
12
|
-
LicenseValidator = class _LicenseValidator {
|
|
13
|
-
/** Ed25519 public key for license verification (PEM format). */
|
|
14
|
-
static PUBLIC_KEY = "-----BEGIN PUBLIC KEY-----\nMCowBQYDK2VwAyEAI/Zd08EFmgIdrDm/HXd0l3/5GBt7R1PrdvhdmEXhJlU=\n-----END PUBLIC KEY-----\n";
|
|
15
|
-
cache = null;
|
|
16
|
-
static CACHE_TTL = 5 * 60 * 1e3;
|
|
17
|
-
// 5 minutes
|
|
18
|
-
static GRACE_PERIOD = 72 * 3600 * 1e3;
|
|
19
|
-
// 72 hours after expiry
|
|
20
|
-
/**
|
|
21
|
-
* Load and validate license from environment or file.
|
|
22
|
-
*
|
|
23
|
-
* Resolution order:
|
|
24
|
-
* 1. VISOR_LICENSE env var (JWT string)
|
|
25
|
-
* 2. VISOR_LICENSE_FILE env var (path to file)
|
|
26
|
-
* 3. .visor-license in project root (cwd)
|
|
27
|
-
* 4. .visor-license in ~/.config/visor/
|
|
28
|
-
*/
|
|
29
|
-
async loadAndValidate() {
|
|
30
|
-
if (this.cache && Date.now() - this.cache.validatedAt < _LicenseValidator.CACHE_TTL) {
|
|
31
|
-
return this.cache.payload;
|
|
32
|
-
}
|
|
33
|
-
const token = this.resolveToken();
|
|
34
|
-
if (!token) return null;
|
|
35
|
-
const payload = this.verifyAndDecode(token);
|
|
36
|
-
if (!payload) return null;
|
|
37
|
-
this.cache = { payload, validatedAt: Date.now() };
|
|
38
|
-
return payload;
|
|
39
|
-
}
|
|
40
|
-
/** Check if a specific feature is licensed */
|
|
41
|
-
hasFeature(feature) {
|
|
42
|
-
if (!this.cache) return false;
|
|
43
|
-
return this.cache.payload.features.includes(feature);
|
|
44
|
-
}
|
|
45
|
-
/** Check if license is valid (with grace period) */
|
|
46
|
-
isValid() {
|
|
47
|
-
if (!this.cache) return false;
|
|
48
|
-
const now = Date.now();
|
|
49
|
-
const expiryMs = this.cache.payload.exp * 1e3;
|
|
50
|
-
return now < expiryMs + _LicenseValidator.GRACE_PERIOD;
|
|
51
|
-
}
|
|
52
|
-
/** Check if the license is within its grace period (expired but still valid) */
|
|
53
|
-
isInGracePeriod() {
|
|
54
|
-
if (!this.cache) return false;
|
|
55
|
-
const now = Date.now();
|
|
56
|
-
const expiryMs = this.cache.payload.exp * 1e3;
|
|
57
|
-
return now >= expiryMs && now < expiryMs + _LicenseValidator.GRACE_PERIOD;
|
|
58
|
-
}
|
|
59
|
-
resolveToken() {
|
|
60
|
-
if (process.env.VISOR_LICENSE) {
|
|
61
|
-
return process.env.VISOR_LICENSE.trim();
|
|
62
|
-
}
|
|
63
|
-
if (process.env.VISOR_LICENSE_FILE) {
|
|
64
|
-
const resolved = path.resolve(process.env.VISOR_LICENSE_FILE);
|
|
65
|
-
const home2 = process.env.HOME || process.env.USERPROFILE || "";
|
|
66
|
-
const allowedPrefixes = [path.normalize(process.cwd())];
|
|
67
|
-
if (home2) allowedPrefixes.push(path.normalize(path.join(home2, ".config", "visor")));
|
|
68
|
-
let realPath;
|
|
69
|
-
try {
|
|
70
|
-
realPath = fs.realpathSync(resolved);
|
|
71
|
-
} catch {
|
|
72
|
-
return null;
|
|
73
|
-
}
|
|
74
|
-
const isSafe = allowedPrefixes.some(
|
|
75
|
-
(prefix) => realPath === prefix || realPath.startsWith(prefix + path.sep)
|
|
76
|
-
);
|
|
77
|
-
if (!isSafe) return null;
|
|
78
|
-
return this.readFile(realPath);
|
|
79
|
-
}
|
|
80
|
-
const cwdPath = path.join(process.cwd(), ".visor-license");
|
|
81
|
-
const cwdToken = this.readFile(cwdPath);
|
|
82
|
-
if (cwdToken) return cwdToken;
|
|
83
|
-
const home = process.env.HOME || process.env.USERPROFILE || "";
|
|
84
|
-
if (home) {
|
|
85
|
-
const configPath = path.join(home, ".config", "visor", ".visor-license");
|
|
86
|
-
const configToken = this.readFile(configPath);
|
|
87
|
-
if (configToken) return configToken;
|
|
88
|
-
}
|
|
89
|
-
return null;
|
|
90
|
-
}
|
|
91
|
-
readFile(filePath) {
|
|
92
|
-
try {
|
|
93
|
-
return fs.readFileSync(filePath, "utf-8").trim();
|
|
94
|
-
} catch {
|
|
95
|
-
return null;
|
|
96
|
-
}
|
|
97
|
-
}
|
|
98
|
-
verifyAndDecode(token) {
|
|
99
|
-
try {
|
|
100
|
-
const parts = token.split(".");
|
|
101
|
-
if (parts.length !== 3) return null;
|
|
102
|
-
const [headerB64, payloadB64, signatureB64] = parts;
|
|
103
|
-
const header = JSON.parse(Buffer.from(headerB64, "base64url").toString());
|
|
104
|
-
if (header.alg !== "EdDSA") return null;
|
|
105
|
-
const data = `${headerB64}.${payloadB64}`;
|
|
106
|
-
const signature = Buffer.from(signatureB64, "base64url");
|
|
107
|
-
const publicKey = crypto.createPublicKey(_LicenseValidator.PUBLIC_KEY);
|
|
108
|
-
if (publicKey.asymmetricKeyType !== "ed25519") {
|
|
109
|
-
return null;
|
|
110
|
-
}
|
|
111
|
-
const isValid = crypto.verify(null, Buffer.from(data), publicKey, signature);
|
|
112
|
-
if (!isValid) return null;
|
|
113
|
-
const payload = JSON.parse(Buffer.from(payloadB64, "base64url").toString());
|
|
114
|
-
if (!payload.org || !Array.isArray(payload.features) || typeof payload.exp !== "number" || typeof payload.iat !== "number" || !payload.sub) {
|
|
115
|
-
return null;
|
|
116
|
-
}
|
|
117
|
-
const now = Date.now();
|
|
118
|
-
const expiryMs = payload.exp * 1e3;
|
|
119
|
-
if (now >= expiryMs + _LicenseValidator.GRACE_PERIOD) {
|
|
120
|
-
return null;
|
|
121
|
-
}
|
|
122
|
-
return payload;
|
|
123
|
-
} catch {
|
|
124
|
-
return null;
|
|
125
|
-
}
|
|
126
|
-
}
|
|
127
|
-
};
|
|
128
|
-
}
|
|
129
|
-
});
|
|
130
|
-
init_validator();
|
|
131
|
-
export {
|
|
132
|
-
LicenseValidator
|
|
133
|
-
};
|
|
134
|
-
//# sourceMappingURL=validator-XTZJZZJH.mjs.map
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"sources":["../../src/enterprise/license/validator.ts"],"sourcesContent":["/**\n * Copyright (c) ProbeLabs. All rights reserved.\n * Licensed under the Elastic License 2.0; you may not use this file except\n * in compliance with the Elastic License 2.0.\n */\n\nimport * as crypto from 'crypto';\nimport * as fs from 'fs';\nimport * as path from 'path';\n\nexport interface LicensePayload {\n org: string;\n features: string[];\n exp: number;\n iat: number;\n sub: string;\n}\n\nexport class LicenseValidator {\n /** Ed25519 public key for license verification (PEM format). */\n private static PUBLIC_KEY =\n '-----BEGIN PUBLIC KEY-----\\n' +\n 'MCowBQYDK2VwAyEAI/Zd08EFmgIdrDm/HXd0l3/5GBt7R1PrdvhdmEXhJlU=\\n' +\n '-----END PUBLIC KEY-----\\n';\n\n private cache: { payload: LicensePayload; validatedAt: number } | null = null;\n private static CACHE_TTL = 5 * 60 * 1000; // 5 minutes\n private static GRACE_PERIOD = 72 * 3600 * 1000; // 72 hours after expiry\n\n /**\n * Load and validate license from environment or file.\n *\n * Resolution order:\n * 1. VISOR_LICENSE env var (JWT string)\n * 2. VISOR_LICENSE_FILE env var (path to file)\n * 3. .visor-license in project root (cwd)\n * 4. .visor-license in ~/.config/visor/\n */\n async loadAndValidate(): Promise<LicensePayload | null> {\n // Return cached result if still fresh\n if (this.cache && Date.now() - this.cache.validatedAt < LicenseValidator.CACHE_TTL) {\n return this.cache.payload;\n }\n\n const token = this.resolveToken();\n if (!token) return null;\n\n const payload = this.verifyAndDecode(token);\n if (!payload) return null;\n\n this.cache = { payload, validatedAt: Date.now() };\n return payload;\n }\n\n /** Check if a specific feature is licensed */\n hasFeature(feature: string): boolean {\n if (!this.cache) return false;\n return this.cache.payload.features.includes(feature);\n }\n\n /** Check if license is valid (with grace period) */\n isValid(): boolean {\n if (!this.cache) return false;\n const now = Date.now();\n const expiryMs = this.cache.payload.exp * 1000;\n return now < expiryMs + LicenseValidator.GRACE_PERIOD;\n }\n\n /** Check if the license is within its grace period (expired but still valid) */\n isInGracePeriod(): boolean {\n if (!this.cache) return false;\n const now = Date.now();\n const expiryMs = this.cache.payload.exp * 1000;\n return now >= expiryMs && now < expiryMs + LicenseValidator.GRACE_PERIOD;\n }\n\n private resolveToken(): string | null {\n // 1. Direct env var\n if (process.env.VISOR_LICENSE) {\n return process.env.VISOR_LICENSE.trim();\n }\n\n // 2. File path from env (validate against path traversal)\n if (process.env.VISOR_LICENSE_FILE) {\n // path.resolve() produces an absolute path with all '..' segments resolved,\n // so a separate resolved.includes('..') check is unnecessary.\n const resolved = path.resolve(process.env.VISOR_LICENSE_FILE);\n const home = process.env.HOME || process.env.USERPROFILE || '';\n const allowedPrefixes = [path.normalize(process.cwd())];\n if (home) allowedPrefixes.push(path.normalize(path.join(home, '.config', 'visor')));\n\n // Resolve symlinks so an attacker cannot create a symlink inside an\n // allowed prefix that points to an arbitrary file outside it.\n let realPath: string;\n try {\n realPath = fs.realpathSync(resolved);\n } catch {\n return null; // File doesn't exist or isn't accessible\n }\n\n const isSafe = allowedPrefixes.some(\n prefix => realPath === prefix || realPath.startsWith(prefix + path.sep)\n );\n if (!isSafe) return null;\n return this.readFile(realPath);\n }\n\n // 3. .visor-license in cwd\n const cwdPath = path.join(process.cwd(), '.visor-license');\n const cwdToken = this.readFile(cwdPath);\n if (cwdToken) return cwdToken;\n\n // 4. ~/.config/visor/.visor-license\n const home = process.env.HOME || process.env.USERPROFILE || '';\n if (home) {\n const configPath = path.join(home, '.config', 'visor', '.visor-license');\n const configToken = this.readFile(configPath);\n if (configToken) return configToken;\n }\n\n return null;\n }\n\n private readFile(filePath: string): string | null {\n try {\n return fs.readFileSync(filePath, 'utf-8').trim();\n } catch {\n return null;\n }\n }\n\n private verifyAndDecode(token: string): LicensePayload | null {\n try {\n const parts = token.split('.');\n if (parts.length !== 3) return null;\n\n const [headerB64, payloadB64, signatureB64] = parts;\n\n // Decode header to verify algorithm\n const header = JSON.parse(Buffer.from(headerB64, 'base64url').toString());\n if (header.alg !== 'EdDSA') return null;\n\n // Verify signature\n const data = `${headerB64}.${payloadB64}`;\n const signature = Buffer.from(signatureB64, 'base64url');\n\n const publicKey = crypto.createPublicKey(LicenseValidator.PUBLIC_KEY);\n\n // Validate that the loaded public key is actually Ed25519 (OID 1.3.101.112).\n // This prevents algorithm-confusion attacks if the embedded key were ever\n // swapped to a different type.\n if (publicKey.asymmetricKeyType !== 'ed25519') {\n return null;\n }\n\n // Ed25519 verification: algorithm must be null because EdDSA performs its\n // own internal hashing (SHA-512) — passing a digest algorithm here would\n // cause Node.js to throw. The key type is validated above.\n const isValid = crypto.verify(null, Buffer.from(data), publicKey, signature);\n if (!isValid) return null;\n\n // Decode payload\n const payload: LicensePayload = JSON.parse(Buffer.from(payloadB64, 'base64url').toString());\n\n // Validate required fields\n if (\n !payload.org ||\n !Array.isArray(payload.features) ||\n typeof payload.exp !== 'number' ||\n typeof payload.iat !== 'number' ||\n !payload.sub\n ) {\n return null;\n }\n\n // Check expiry (with grace period)\n const now = Date.now();\n const expiryMs = payload.exp * 1000;\n if (now >= expiryMs + LicenseValidator.GRACE_PERIOD) {\n return null;\n }\n\n return payload;\n } catch {\n return null;\n }\n }\n}\n"],"mappings":"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","names":["home"]}
|
|
@@ -1,438 +0,0 @@
|
|
|
1
|
-
import {
|
|
2
|
-
__esm
|
|
3
|
-
} from "./chunk-J7LXIPZS.mjs";
|
|
4
|
-
|
|
5
|
-
// src/whatsapp/markdown.ts
|
|
6
|
-
function markdownToWhatsApp(text) {
|
|
7
|
-
if (!text || typeof text !== "string") return "";
|
|
8
|
-
const lines = text.split(/\r?\n/);
|
|
9
|
-
const result = [];
|
|
10
|
-
let inCodeBlock = false;
|
|
11
|
-
let codeLines = [];
|
|
12
|
-
for (let i = 0; i < lines.length; i++) {
|
|
13
|
-
const trimmed = lines[i].trimStart();
|
|
14
|
-
if (/^```/.test(trimmed)) {
|
|
15
|
-
if (!inCodeBlock) {
|
|
16
|
-
inCodeBlock = true;
|
|
17
|
-
codeLines = [];
|
|
18
|
-
} else {
|
|
19
|
-
result.push("```" + codeLines.join("\n") + "```");
|
|
20
|
-
inCodeBlock = false;
|
|
21
|
-
codeLines = [];
|
|
22
|
-
}
|
|
23
|
-
continue;
|
|
24
|
-
}
|
|
25
|
-
if (inCodeBlock) {
|
|
26
|
-
codeLines.push(lines[i]);
|
|
27
|
-
continue;
|
|
28
|
-
}
|
|
29
|
-
const line = lines[i];
|
|
30
|
-
const headerMatch = /^(#{1,6})\s+(.+)$/.exec(line.trimStart());
|
|
31
|
-
if (headerMatch) {
|
|
32
|
-
result.push(`*${convertInline(headerMatch[2].trim())}*`);
|
|
33
|
-
continue;
|
|
34
|
-
}
|
|
35
|
-
if (/^[-*_]{3,}\s*$/.test(trimmed)) {
|
|
36
|
-
result.push("---");
|
|
37
|
-
continue;
|
|
38
|
-
}
|
|
39
|
-
const bulletMatch = /^(\s*)([-*])\s+(.+)$/.exec(line);
|
|
40
|
-
if (bulletMatch) {
|
|
41
|
-
result.push(`${bulletMatch[1]}- ${convertInline(bulletMatch[3])}`);
|
|
42
|
-
continue;
|
|
43
|
-
}
|
|
44
|
-
const numMatch = /^(\s*)(\d+\.)\s+(.+)$/.exec(line);
|
|
45
|
-
if (numMatch) {
|
|
46
|
-
result.push(`${numMatch[1]}${numMatch[2]} ${convertInline(numMatch[3])}`);
|
|
47
|
-
continue;
|
|
48
|
-
}
|
|
49
|
-
const bqMatch = /^>\s?(.*)$/.exec(trimmed);
|
|
50
|
-
if (bqMatch) {
|
|
51
|
-
result.push(`> ${convertInline(bqMatch[1])}`);
|
|
52
|
-
continue;
|
|
53
|
-
}
|
|
54
|
-
result.push(convertInline(line));
|
|
55
|
-
}
|
|
56
|
-
if (inCodeBlock && codeLines.length > 0) {
|
|
57
|
-
result.push("```" + codeLines.join("\n") + "```");
|
|
58
|
-
}
|
|
59
|
-
return result.join("\n");
|
|
60
|
-
}
|
|
61
|
-
function convertInline(line) {
|
|
62
|
-
const codeSpans = [];
|
|
63
|
-
let processed = line.replace(/`([^`]+)`/g, (_m, code) => {
|
|
64
|
-
const idx = codeSpans.length;
|
|
65
|
-
codeSpans.push("```" + code + "```");
|
|
66
|
-
return `\0CODE${idx}\0`;
|
|
67
|
-
});
|
|
68
|
-
processed = processed.replace(
|
|
69
|
-
/!\[([^\]]*)\]\(([^)\s]+)(?:\s+"[^"]*")?\)/g,
|
|
70
|
-
(_m, alt, url) => `${alt || "image"} (${url})`
|
|
71
|
-
);
|
|
72
|
-
processed = processed.replace(
|
|
73
|
-
/\[([^\]]+)\]\(([^)\s]+)(?:\s+"[^"]*")?\)/g,
|
|
74
|
-
(_m, label, url) => `${label} (${url})`
|
|
75
|
-
);
|
|
76
|
-
const boldSpans = [];
|
|
77
|
-
processed = processed.replace(/\*\*([^*]+)\*\*/g, (_m, content) => {
|
|
78
|
-
const idx = boldSpans.length;
|
|
79
|
-
boldSpans.push(`*${content}*`);
|
|
80
|
-
return `\0BOLD${idx}\0`;
|
|
81
|
-
});
|
|
82
|
-
processed = processed.replace(/__([^_]+)__/g, (_m, content) => {
|
|
83
|
-
const idx = boldSpans.length;
|
|
84
|
-
boldSpans.push(`*${content}*`);
|
|
85
|
-
return `\0BOLD${idx}\0`;
|
|
86
|
-
});
|
|
87
|
-
processed = processed.replace(/(?<!\*)\*([^*]+)\*(?!\*)/g, "_$1_");
|
|
88
|
-
processed = processed.replace(/~~([^~]+)~~/g, "~$1~");
|
|
89
|
-
processed = processed.replace(
|
|
90
|
-
/\x00BOLD(\d+)\x00/g,
|
|
91
|
-
(_m, idx) => boldSpans[parseInt(idx)]
|
|
92
|
-
);
|
|
93
|
-
processed = processed.replace(
|
|
94
|
-
/\x00CODE(\d+)\x00/g,
|
|
95
|
-
(_m, idx) => codeSpans[parseInt(idx)]
|
|
96
|
-
);
|
|
97
|
-
return processed;
|
|
98
|
-
}
|
|
99
|
-
function chunkText(text, limit = 4096) {
|
|
100
|
-
if (text.length <= limit) return [text];
|
|
101
|
-
const chunks = [];
|
|
102
|
-
const lines = text.split("\n");
|
|
103
|
-
let current = "";
|
|
104
|
-
for (const line of lines) {
|
|
105
|
-
const candidate = current ? current + "\n" + line : line;
|
|
106
|
-
if (candidate.length > limit) {
|
|
107
|
-
if (current) {
|
|
108
|
-
chunks.push(current);
|
|
109
|
-
current = line;
|
|
110
|
-
} else {
|
|
111
|
-
let remaining = line;
|
|
112
|
-
while (remaining.length > limit) {
|
|
113
|
-
chunks.push(remaining.slice(0, limit));
|
|
114
|
-
remaining = remaining.slice(limit);
|
|
115
|
-
}
|
|
116
|
-
current = remaining;
|
|
117
|
-
}
|
|
118
|
-
} else {
|
|
119
|
-
current = candidate;
|
|
120
|
-
}
|
|
121
|
-
}
|
|
122
|
-
if (current) chunks.push(current);
|
|
123
|
-
return chunks;
|
|
124
|
-
}
|
|
125
|
-
function formatWhatsAppText(text) {
|
|
126
|
-
return markdownToWhatsApp(text);
|
|
127
|
-
}
|
|
128
|
-
var init_markdown = __esm({
|
|
129
|
-
"src/whatsapp/markdown.ts"() {
|
|
130
|
-
"use strict";
|
|
131
|
-
}
|
|
132
|
-
});
|
|
133
|
-
|
|
134
|
-
// src/whatsapp/client.ts
|
|
135
|
-
import { createHmac } from "crypto";
|
|
136
|
-
var WhatsAppClient;
|
|
137
|
-
var init_client = __esm({
|
|
138
|
-
"src/whatsapp/client.ts"() {
|
|
139
|
-
"use strict";
|
|
140
|
-
init_markdown();
|
|
141
|
-
WhatsAppClient = class {
|
|
142
|
-
accessToken;
|
|
143
|
-
phoneNumberId;
|
|
144
|
-
appSecret;
|
|
145
|
-
verifyToken;
|
|
146
|
-
baseUrl;
|
|
147
|
-
constructor(opts) {
|
|
148
|
-
if (!opts.accessToken || typeof opts.accessToken !== "string") {
|
|
149
|
-
throw new Error("WhatsAppClient: accessToken is required");
|
|
150
|
-
}
|
|
151
|
-
if (!opts.phoneNumberId || typeof opts.phoneNumberId !== "string") {
|
|
152
|
-
throw new Error("WhatsAppClient: phoneNumberId is required");
|
|
153
|
-
}
|
|
154
|
-
this.accessToken = opts.accessToken;
|
|
155
|
-
this.phoneNumberId = opts.phoneNumberId;
|
|
156
|
-
this.appSecret = opts.appSecret;
|
|
157
|
-
this.verifyToken = opts.verifyToken;
|
|
158
|
-
const version = opts.apiVersion || "v21.0";
|
|
159
|
-
this.baseUrl = `https://graph.facebook.com/${version}/${this.phoneNumberId}`;
|
|
160
|
-
}
|
|
161
|
-
/** Get the Phone Number ID */
|
|
162
|
-
getPhoneNumberId() {
|
|
163
|
-
return this.phoneNumberId;
|
|
164
|
-
}
|
|
165
|
-
/**
|
|
166
|
-
* Send a text message. Auto-chunks at 4096 characters.
|
|
167
|
-
*/
|
|
168
|
-
async sendMessage(opts) {
|
|
169
|
-
const chunks = chunkText(opts.text, 4096);
|
|
170
|
-
let lastResult = { ok: false, error: "No chunks to send" };
|
|
171
|
-
for (const chunk of chunks) {
|
|
172
|
-
const body = {
|
|
173
|
-
messaging_product: "whatsapp",
|
|
174
|
-
to: opts.to,
|
|
175
|
-
type: "text",
|
|
176
|
-
text: { body: chunk }
|
|
177
|
-
};
|
|
178
|
-
if (opts.replyToMessageId) {
|
|
179
|
-
body.context = { message_id: opts.replyToMessageId };
|
|
180
|
-
}
|
|
181
|
-
try {
|
|
182
|
-
const resp = await fetch(`${this.baseUrl}/messages`, {
|
|
183
|
-
method: "POST",
|
|
184
|
-
headers: {
|
|
185
|
-
"Content-Type": "application/json",
|
|
186
|
-
Authorization: `Bearer ${this.accessToken}`
|
|
187
|
-
},
|
|
188
|
-
body: JSON.stringify(body)
|
|
189
|
-
});
|
|
190
|
-
const data = await resp.json();
|
|
191
|
-
if (!resp.ok) {
|
|
192
|
-
const errMsg = data?.error?.message || `HTTP ${resp.status}`;
|
|
193
|
-
return { ok: false, error: errMsg };
|
|
194
|
-
}
|
|
195
|
-
const msgId = data?.messages?.[0]?.id;
|
|
196
|
-
lastResult = { ok: true, messageId: msgId };
|
|
197
|
-
} catch (err) {
|
|
198
|
-
return {
|
|
199
|
-
ok: false,
|
|
200
|
-
error: err instanceof Error ? err.message : String(err)
|
|
201
|
-
};
|
|
202
|
-
}
|
|
203
|
-
}
|
|
204
|
-
return lastResult;
|
|
205
|
-
}
|
|
206
|
-
/**
|
|
207
|
-
* Mark a message as read (send read receipt).
|
|
208
|
-
*/
|
|
209
|
-
async markAsRead(messageId) {
|
|
210
|
-
try {
|
|
211
|
-
const resp = await fetch(`${this.baseUrl}/messages`, {
|
|
212
|
-
method: "POST",
|
|
213
|
-
headers: {
|
|
214
|
-
"Content-Type": "application/json",
|
|
215
|
-
Authorization: `Bearer ${this.accessToken}`
|
|
216
|
-
},
|
|
217
|
-
body: JSON.stringify({
|
|
218
|
-
messaging_product: "whatsapp",
|
|
219
|
-
status: "read",
|
|
220
|
-
message_id: messageId
|
|
221
|
-
})
|
|
222
|
-
});
|
|
223
|
-
if (!resp.ok) {
|
|
224
|
-
const data = await resp.json();
|
|
225
|
-
return {
|
|
226
|
-
ok: false,
|
|
227
|
-
error: data?.error?.message || `HTTP ${resp.status}`
|
|
228
|
-
};
|
|
229
|
-
}
|
|
230
|
-
return { ok: true };
|
|
231
|
-
} catch (err) {
|
|
232
|
-
return {
|
|
233
|
-
ok: false,
|
|
234
|
-
error: err instanceof Error ? err.message : String(err)
|
|
235
|
-
};
|
|
236
|
-
}
|
|
237
|
-
}
|
|
238
|
-
/**
|
|
239
|
-
* Verify webhook signature (HMAC-SHA256 with X-Hub-Signature-256).
|
|
240
|
-
* Returns true if valid or if no appSecret is configured (skip verification).
|
|
241
|
-
*/
|
|
242
|
-
verifyWebhookSignature(rawBody, signatureHeader) {
|
|
243
|
-
if (!this.appSecret) return true;
|
|
244
|
-
if (!signatureHeader) return false;
|
|
245
|
-
const expected = "sha256=" + createHmac("sha256", this.appSecret).update(rawBody).digest("hex");
|
|
246
|
-
return signatureHeader === expected;
|
|
247
|
-
}
|
|
248
|
-
/**
|
|
249
|
-
* Verify GET challenge-response for webhook subscription.
|
|
250
|
-
*/
|
|
251
|
-
verifyChallenge(params) {
|
|
252
|
-
const mode = params["hub.mode"];
|
|
253
|
-
const token = params["hub.verify_token"];
|
|
254
|
-
const challenge = params["hub.challenge"];
|
|
255
|
-
if (mode === "subscribe" && token === this.verifyToken) {
|
|
256
|
-
return { ok: true, challenge };
|
|
257
|
-
}
|
|
258
|
-
return { ok: false };
|
|
259
|
-
}
|
|
260
|
-
};
|
|
261
|
-
}
|
|
262
|
-
});
|
|
263
|
-
|
|
264
|
-
// src/frontends/whatsapp-frontend.ts
|
|
265
|
-
var WhatsAppFrontend;
|
|
266
|
-
var init_whatsapp_frontend = __esm({
|
|
267
|
-
"src/frontends/whatsapp-frontend.ts"() {
|
|
268
|
-
init_client();
|
|
269
|
-
init_markdown();
|
|
270
|
-
WhatsAppFrontend = class {
|
|
271
|
-
name = "whatsapp";
|
|
272
|
-
subs = [];
|
|
273
|
-
cfg;
|
|
274
|
-
errorNotified = false;
|
|
275
|
-
constructor(config) {
|
|
276
|
-
this.cfg = config || {};
|
|
277
|
-
}
|
|
278
|
-
start(ctx) {
|
|
279
|
-
const bus = ctx.eventBus;
|
|
280
|
-
try {
|
|
281
|
-
ctx.logger.info(`[whatsapp-frontend] started`);
|
|
282
|
-
} catch {
|
|
283
|
-
}
|
|
284
|
-
this.subs.push(
|
|
285
|
-
bus.on("CheckCompleted", async (env) => {
|
|
286
|
-
const ev = env && env.payload || env;
|
|
287
|
-
await this.maybePostDirectReply(ctx, ev.checkId, ev.result).catch(() => {
|
|
288
|
-
});
|
|
289
|
-
})
|
|
290
|
-
);
|
|
291
|
-
this.subs.push(
|
|
292
|
-
bus.on("CheckErrored", async (env) => {
|
|
293
|
-
const ev = env && env.payload || env;
|
|
294
|
-
const message = ev?.error?.message || "Execution error";
|
|
295
|
-
await this.maybePostError(ctx, "Check failed", message, ev?.checkId).catch(() => {
|
|
296
|
-
});
|
|
297
|
-
})
|
|
298
|
-
);
|
|
299
|
-
this.subs.push(
|
|
300
|
-
bus.on("Shutdown", async (env) => {
|
|
301
|
-
const ev = env && env.payload || env;
|
|
302
|
-
const message = ev?.error?.message || "Fatal error";
|
|
303
|
-
await this.maybePostError(ctx, "Run failed", message).catch(() => {
|
|
304
|
-
});
|
|
305
|
-
})
|
|
306
|
-
);
|
|
307
|
-
}
|
|
308
|
-
stop() {
|
|
309
|
-
for (const s of this.subs) s.unsubscribe();
|
|
310
|
-
this.subs = [];
|
|
311
|
-
}
|
|
312
|
-
getWhatsApp(ctx) {
|
|
313
|
-
const injected = ctx.whatsapp || ctx.whatsappClient;
|
|
314
|
-
if (injected) return injected;
|
|
315
|
-
try {
|
|
316
|
-
const token = this.cfg.accessToken || process.env.WHATSAPP_ACCESS_TOKEN;
|
|
317
|
-
const phoneId = this.cfg.phoneNumberId || process.env.WHATSAPP_PHONE_NUMBER_ID;
|
|
318
|
-
if (typeof token === "string" && token.trim() && typeof phoneId === "string" && phoneId.trim()) {
|
|
319
|
-
return new WhatsAppClient({
|
|
320
|
-
accessToken: token.trim(),
|
|
321
|
-
phoneNumberId: phoneId.trim()
|
|
322
|
-
});
|
|
323
|
-
}
|
|
324
|
-
} catch {
|
|
325
|
-
}
|
|
326
|
-
return void 0;
|
|
327
|
-
}
|
|
328
|
-
getInboundWhatsAppPayload(ctx) {
|
|
329
|
-
try {
|
|
330
|
-
const endpoint = "/bots/whatsapp/message";
|
|
331
|
-
return ctx.webhookContext?.webhookData?.get(endpoint) || null;
|
|
332
|
-
} catch {
|
|
333
|
-
return null;
|
|
334
|
-
}
|
|
335
|
-
}
|
|
336
|
-
async maybePostError(ctx, title, message, checkId) {
|
|
337
|
-
if (this.errorNotified) return;
|
|
338
|
-
const whatsapp = this.getWhatsApp(ctx);
|
|
339
|
-
if (!whatsapp) return;
|
|
340
|
-
const payload = this.getInboundWhatsAppPayload(ctx);
|
|
341
|
-
const ev = payload?.event;
|
|
342
|
-
const from = ev?.from;
|
|
343
|
-
if (!from) return;
|
|
344
|
-
let text = `${title}`;
|
|
345
|
-
if (checkId) text += `
|
|
346
|
-
Check: ${checkId}`;
|
|
347
|
-
if (message) text += `
|
|
348
|
-
${message}`;
|
|
349
|
-
await whatsapp.sendMessage({
|
|
350
|
-
to: from,
|
|
351
|
-
text,
|
|
352
|
-
replyToMessageId: ev?.message_id
|
|
353
|
-
});
|
|
354
|
-
this.errorNotified = true;
|
|
355
|
-
}
|
|
356
|
-
async maybePostDirectReply(ctx, checkId, result) {
|
|
357
|
-
try {
|
|
358
|
-
const cfg = ctx.config || {};
|
|
359
|
-
const checkCfg = cfg.checks?.[checkId];
|
|
360
|
-
if (!checkCfg) return;
|
|
361
|
-
const providerType = checkCfg.type || "";
|
|
362
|
-
const isAi = providerType === "ai";
|
|
363
|
-
const isLogChat = providerType === "log" && checkCfg.group === "chat";
|
|
364
|
-
const isWorkflow = providerType === "workflow";
|
|
365
|
-
if (!isAi && !isLogChat && !isWorkflow) return;
|
|
366
|
-
if (checkCfg.criticality === "internal") return;
|
|
367
|
-
if (isAi) {
|
|
368
|
-
const schema = checkCfg.schema;
|
|
369
|
-
if (typeof schema === "string") {
|
|
370
|
-
const simpleSchemas = ["code-review", "markdown", "text", "plain"];
|
|
371
|
-
if (!simpleSchemas.includes(schema)) return;
|
|
372
|
-
}
|
|
373
|
-
}
|
|
374
|
-
const whatsapp = this.getWhatsApp(ctx);
|
|
375
|
-
if (!whatsapp) return;
|
|
376
|
-
const payload = this.getInboundWhatsAppPayload(ctx);
|
|
377
|
-
const ev = payload?.event;
|
|
378
|
-
const from = ev?.from;
|
|
379
|
-
if (!from) {
|
|
380
|
-
ctx.logger.warn(
|
|
381
|
-
`[whatsapp-frontend] skip posting reply for ${checkId}: missing from number`
|
|
382
|
-
);
|
|
383
|
-
return;
|
|
384
|
-
}
|
|
385
|
-
const out = result?.output;
|
|
386
|
-
let text;
|
|
387
|
-
if (out && typeof out.text === "string" && out.text.trim().length > 0) {
|
|
388
|
-
text = out.text.trim();
|
|
389
|
-
} else if (isAi && typeof checkCfg.schema === "string") {
|
|
390
|
-
if (typeof result?.content === "string" && result.content.trim().length > 0) {
|
|
391
|
-
text = result.content.trim();
|
|
392
|
-
}
|
|
393
|
-
} else if (isLogChat && typeof result?.logOutput === "string") {
|
|
394
|
-
const raw = result.logOutput;
|
|
395
|
-
if (raw.trim().length > 0) text = raw.trim();
|
|
396
|
-
}
|
|
397
|
-
if (out && typeof out._rawOutput === "string" && out._rawOutput.trim().length > 0) {
|
|
398
|
-
text = (text || "") + "\n\n" + out._rawOutput.trim();
|
|
399
|
-
}
|
|
400
|
-
if (!text) {
|
|
401
|
-
ctx.logger.info(
|
|
402
|
-
`[whatsapp-frontend] skip posting reply for ${checkId}: no renderable text`
|
|
403
|
-
);
|
|
404
|
-
return;
|
|
405
|
-
}
|
|
406
|
-
text = text.replace(/\\n/g, "\n");
|
|
407
|
-
const formattedText = formatWhatsAppText(text);
|
|
408
|
-
const postResult = await whatsapp.sendMessage({
|
|
409
|
-
to: from,
|
|
410
|
-
text: formattedText,
|
|
411
|
-
replyToMessageId: ev?.message_id
|
|
412
|
-
});
|
|
413
|
-
if (!postResult.ok) {
|
|
414
|
-
ctx.logger.warn(
|
|
415
|
-
`[whatsapp-frontend] failed to post reply for ${checkId}: ${postResult.error}`
|
|
416
|
-
);
|
|
417
|
-
return;
|
|
418
|
-
}
|
|
419
|
-
ctx.logger.info(
|
|
420
|
-
`[whatsapp-frontend] posted reply for ${checkId} to ${from} (messageId=${postResult.messageId})`
|
|
421
|
-
);
|
|
422
|
-
} catch (err) {
|
|
423
|
-
try {
|
|
424
|
-
ctx.logger.warn(
|
|
425
|
-
`[whatsapp-frontend] maybePostDirectReply failed for ${checkId}: ${err instanceof Error ? err.message : String(err)}`
|
|
426
|
-
);
|
|
427
|
-
} catch {
|
|
428
|
-
}
|
|
429
|
-
}
|
|
430
|
-
}
|
|
431
|
-
};
|
|
432
|
-
}
|
|
433
|
-
});
|
|
434
|
-
init_whatsapp_frontend();
|
|
435
|
-
export {
|
|
436
|
-
WhatsAppFrontend
|
|
437
|
-
};
|
|
438
|
-
//# sourceMappingURL=whatsapp-frontend-72XEIUIR.mjs.map
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"sources":["../../src/whatsapp/markdown.ts","../../src/whatsapp/client.ts","../../src/frontends/whatsapp-frontend.ts"],"sourcesContent":["// Lightweight Markdown → WhatsApp formatter.\n// Converts common Markdown output from AI steps to WhatsApp-compatible text.\n//\n// Supported conversions:\n// - # Header / ## Header → *Header* (bold, no header support)\n// - **bold** / __bold__ → *bold*\n// - *italic* → _italic_\n// - ~~strike~~ → ~strike~\n// - `code` → ```code```\n// - ```block``` → ```block``` (preserved)\n// - [label](url) → label (url)\n// - > blockquote → > blockquote (preserved, WhatsApp renders this)\n//\n// WhatsApp text messages have a 4096 character limit.\n\n/**\n * Convert Markdown text to WhatsApp-compatible format.\n * Processes line-by-line, respecting fenced code blocks.\n */\nexport function markdownToWhatsApp(text: string): string {\n if (!text || typeof text !== 'string') return '';\n\n const lines = text.split(/\\r?\\n/);\n const result: string[] = [];\n let inCodeBlock = false;\n let codeLines: string[] = [];\n\n for (let i = 0; i < lines.length; i++) {\n const trimmed = lines[i].trimStart();\n\n // Track fenced code blocks\n if (/^```/.test(trimmed)) {\n if (!inCodeBlock) {\n inCodeBlock = true;\n codeLines = [];\n } else {\n // Close code block\n result.push('```' + codeLines.join('\\n') + '```');\n inCodeBlock = false;\n codeLines = [];\n }\n continue;\n }\n if (inCodeBlock) {\n codeLines.push(lines[i]);\n continue;\n }\n\n const line = lines[i];\n\n // Headers: # Header → *Header* (bold)\n const headerMatch = /^(#{1,6})\\s+(.+)$/.exec(line.trimStart());\n if (headerMatch) {\n result.push(`*${convertInline(headerMatch[2].trim())}*`);\n continue;\n }\n\n // Horizontal rules\n if (/^[-*_]{3,}\\s*$/.test(trimmed)) {\n result.push('---');\n continue;\n }\n\n // Bullet lists: \"- item\" or \"* item\" preserved\n const bulletMatch = /^(\\s*)([-*])\\s+(.+)$/.exec(line);\n if (bulletMatch) {\n result.push(`${bulletMatch[1]}- ${convertInline(bulletMatch[3])}`);\n continue;\n }\n\n // Numbered lists: preserve as-is but convert inline\n const numMatch = /^(\\s*)(\\d+\\.)\\s+(.+)$/.exec(line);\n if (numMatch) {\n result.push(`${numMatch[1]}${numMatch[2]} ${convertInline(numMatch[3])}`);\n continue;\n }\n\n // Blockquotes: > text — preserved (WhatsApp renders these)\n const bqMatch = /^>\\s?(.*)$/.exec(trimmed);\n if (bqMatch) {\n result.push(`> ${convertInline(bqMatch[1])}`);\n continue;\n }\n\n // Regular line: apply inline conversions\n result.push(convertInline(line));\n }\n\n // Close any unclosed code block\n if (inCodeBlock && codeLines.length > 0) {\n result.push('```' + codeLines.join('\\n') + '```');\n }\n\n return result.join('\\n');\n}\n\n/**\n * Apply inline Markdown conversions to a single line.\n */\nfunction convertInline(line: string): string {\n // First, identify and protect inline code spans\n const codeSpans: string[] = [];\n let processed = line.replace(/`([^`]+)`/g, (_m, code: string) => {\n const idx = codeSpans.length;\n codeSpans.push('```' + code + '```');\n return `\\x00CODE${idx}\\x00`;\n });\n\n // Images:  → alt (url)\n processed = processed.replace(\n /!\\[([^\\]]*)\\]\\(([^)\\s]+)(?:\\s+\"[^\"]*\")?\\)/g,\n (_m, alt: string, url: string) => `${alt || 'image'} (${url})`\n );\n\n // Links: [label](url) → label (url)\n processed = processed.replace(\n /\\[([^\\]]+)\\]\\(([^)\\s]+)(?:\\s+\"[^\"]*\")?\\)/g,\n (_m, label: string, url: string) => `${label} (${url})`\n );\n\n // Bold: **text** or __text__ → *text* (protect with placeholders first)\n const boldSpans: string[] = [];\n processed = processed.replace(/\\*\\*([^*]+)\\*\\*/g, (_m, content: string) => {\n const idx = boldSpans.length;\n boldSpans.push(`*${content}*`);\n return `\\x00BOLD${idx}\\x00`;\n });\n processed = processed.replace(/__([^_]+)__/g, (_m, content: string) => {\n const idx = boldSpans.length;\n boldSpans.push(`*${content}*`);\n return `\\x00BOLD${idx}\\x00`;\n });\n\n // Italic: *text* → _text_ (bold already protected)\n processed = processed.replace(/(?<!\\*)\\*([^*]+)\\*(?!\\*)/g, '_$1_');\n\n // Strikethrough: ~~text~~ → ~text~\n processed = processed.replace(/~~([^~]+)~~/g, '~$1~');\n\n // Restore bold spans\n processed = processed.replace(\n /\\x00BOLD(\\d+)\\x00/g,\n (_m, idx: string) => boldSpans[parseInt(idx)]\n );\n\n // Restore code spans\n processed = processed.replace(\n /\\x00CODE(\\d+)\\x00/g,\n (_m, idx: string) => codeSpans[parseInt(idx)]\n );\n\n return processed;\n}\n\n/**\n * Chunk text into segments no larger than limit, splitting at newlines.\n */\nexport function chunkText(text: string, limit: number = 4096): string[] {\n if (text.length <= limit) return [text];\n\n const chunks: string[] = [];\n const lines = text.split('\\n');\n let current = '';\n\n for (const line of lines) {\n const candidate = current ? current + '\\n' + line : line;\n if (candidate.length > limit) {\n if (current) {\n chunks.push(current);\n current = line;\n } else {\n // Single line exceeds limit — force split\n let remaining = line;\n while (remaining.length > limit) {\n chunks.push(remaining.slice(0, limit));\n remaining = remaining.slice(limit);\n }\n current = remaining;\n }\n } else {\n current = candidate;\n }\n }\n if (current) chunks.push(current);\n\n return chunks;\n}\n\n/**\n * Main entry point: convert Markdown to WhatsApp format.\n */\nexport function formatWhatsAppText(text: string): string {\n return markdownToWhatsApp(text);\n}\n","// WhatsApp Cloud API client.\n// Wraps Graph API calls behind a clean interface.\n// Uses fetch directly (no npm dependency — Meta's official SDK is archived).\n\nimport { createHmac } from 'crypto';\nimport { chunkText } from './markdown';\n\nexport interface WhatsAppSendResult {\n ok: boolean;\n messageId?: string; // wamid.* format\n error?: string;\n}\n\nexport interface WhatsAppMessageStatus {\n ok: boolean;\n error?: string;\n}\n\nexport interface WhatsAppClientOptions {\n accessToken: string;\n phoneNumberId: string;\n appSecret?: string;\n verifyToken?: string;\n apiVersion?: string; // default 'v21.0'\n}\n\nexport class WhatsAppClient {\n private accessToken: string;\n private phoneNumberId: string;\n private appSecret?: string;\n private verifyToken?: string;\n private baseUrl: string;\n\n constructor(opts: WhatsAppClientOptions) {\n if (!opts.accessToken || typeof opts.accessToken !== 'string') {\n throw new Error('WhatsAppClient: accessToken is required');\n }\n if (!opts.phoneNumberId || typeof opts.phoneNumberId !== 'string') {\n throw new Error('WhatsAppClient: phoneNumberId is required');\n }\n this.accessToken = opts.accessToken;\n this.phoneNumberId = opts.phoneNumberId;\n this.appSecret = opts.appSecret;\n this.verifyToken = opts.verifyToken;\n const version = opts.apiVersion || 'v21.0';\n this.baseUrl = `https://graph.facebook.com/${version}/${this.phoneNumberId}`;\n }\n\n /** Get the Phone Number ID */\n getPhoneNumberId(): string {\n return this.phoneNumberId;\n }\n\n /**\n * Send a text message. Auto-chunks at 4096 characters.\n */\n async sendMessage(opts: {\n to: string;\n text: string;\n replyToMessageId?: string;\n }): Promise<WhatsAppSendResult> {\n const chunks = chunkText(opts.text, 4096);\n let lastResult: WhatsAppSendResult = { ok: false, error: 'No chunks to send' };\n\n for (const chunk of chunks) {\n const body: any = {\n messaging_product: 'whatsapp',\n to: opts.to,\n type: 'text',\n text: { body: chunk },\n };\n\n // Add quoted reply context\n if (opts.replyToMessageId) {\n body.context = { message_id: opts.replyToMessageId };\n }\n\n try {\n const resp = await fetch(`${this.baseUrl}/messages`, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/json',\n Authorization: `Bearer ${this.accessToken}`,\n },\n body: JSON.stringify(body),\n });\n\n const data = await resp.json();\n\n if (!resp.ok) {\n const errMsg = (data as any)?.error?.message || `HTTP ${resp.status}`;\n return { ok: false, error: errMsg };\n }\n\n const msgId = (data as any)?.messages?.[0]?.id;\n lastResult = { ok: true, messageId: msgId };\n } catch (err) {\n return {\n ok: false,\n error: err instanceof Error ? err.message : String(err),\n };\n }\n }\n\n return lastResult;\n }\n\n /**\n * Mark a message as read (send read receipt).\n */\n async markAsRead(messageId: string): Promise<WhatsAppMessageStatus> {\n try {\n const resp = await fetch(`${this.baseUrl}/messages`, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/json',\n Authorization: `Bearer ${this.accessToken}`,\n },\n body: JSON.stringify({\n messaging_product: 'whatsapp',\n status: 'read',\n message_id: messageId,\n }),\n });\n\n if (!resp.ok) {\n const data = await resp.json();\n return {\n ok: false,\n error: (data as any)?.error?.message || `HTTP ${resp.status}`,\n };\n }\n\n return { ok: true };\n } catch (err) {\n return {\n ok: false,\n error: err instanceof Error ? err.message : String(err),\n };\n }\n }\n\n /**\n * Verify webhook signature (HMAC-SHA256 with X-Hub-Signature-256).\n * Returns true if valid or if no appSecret is configured (skip verification).\n */\n verifyWebhookSignature(rawBody: string, signatureHeader: string): boolean {\n if (!this.appSecret) return true; // no secret = skip verification\n if (!signatureHeader) return false;\n\n const expected = 'sha256=' + createHmac('sha256', this.appSecret).update(rawBody).digest('hex');\n\n return signatureHeader === expected;\n }\n\n /**\n * Verify GET challenge-response for webhook subscription.\n */\n verifyChallenge(params: Record<string, string>): {\n ok: boolean;\n challenge?: string;\n } {\n const mode = params['hub.mode'];\n const token = params['hub.verify_token'];\n const challenge = params['hub.challenge'];\n\n if (mode === 'subscribe' && token === this.verifyToken) {\n return { ok: true, challenge };\n }\n\n return { ok: false };\n }\n}\n","/**\n * WhatsApp Frontend for Visor workflows.\n *\n * Mirrors the TelegramFrontend pattern:\n * - Sends AI replies as WhatsApp text messages\n * - Converts Markdown to WhatsApp format\n * - No reaction equivalent (CheckScheduled is a no-op)\n */\nimport type { Frontend, FrontendContext } from './host';\nimport { WhatsAppClient } from '../whatsapp/client';\nimport { formatWhatsAppText } from '../whatsapp/markdown';\n\ntype WhatsAppFrontendConfig = {\n accessToken?: string;\n phoneNumberId?: string;\n};\n\nexport class WhatsAppFrontend implements Frontend {\n public readonly name = 'whatsapp';\n private subs: Array<{ unsubscribe(): void }> = [];\n private cfg: WhatsAppFrontendConfig;\n private errorNotified: boolean = false;\n\n constructor(config?: WhatsAppFrontendConfig) {\n this.cfg = config || {};\n }\n\n start(ctx: FrontendContext): void {\n const bus = ctx.eventBus;\n\n try {\n ctx.logger.info(`[whatsapp-frontend] started`);\n } catch {}\n\n // CheckCompleted: post AI replies\n this.subs.push(\n bus.on('CheckCompleted', async (env: any) => {\n const ev = (env && env.payload) || env;\n await this.maybePostDirectReply(ctx, ev.checkId, ev.result).catch(() => {});\n })\n );\n\n // CheckErrored: post error notice\n this.subs.push(\n bus.on('CheckErrored', async (env: any) => {\n const ev = (env && env.payload) || env;\n const message = ev?.error?.message || 'Execution error';\n await this.maybePostError(ctx, 'Check failed', message, ev?.checkId).catch(() => {});\n })\n );\n\n // Shutdown: post error\n this.subs.push(\n bus.on('Shutdown', async (env: any) => {\n const ev = (env && env.payload) || env;\n const message = ev?.error?.message || 'Fatal error';\n await this.maybePostError(ctx, 'Run failed', message).catch(() => {});\n })\n );\n\n // CheckScheduled: no-op (WhatsApp has no reaction equivalent)\n // StateTransition: no-op\n }\n\n stop(): void {\n for (const s of this.subs) s.unsubscribe();\n this.subs = [];\n }\n\n private getWhatsApp(ctx: FrontendContext): WhatsAppClient | undefined {\n // Prefer injected client (for tests or shared runner context)\n const injected = (ctx as any).whatsapp || (ctx as any).whatsappClient;\n if (injected) return injected;\n // Lazy-create from env or frontend config\n try {\n const token = this.cfg.accessToken || process.env.WHATSAPP_ACCESS_TOKEN;\n const phoneId = this.cfg.phoneNumberId || process.env.WHATSAPP_PHONE_NUMBER_ID;\n if (\n typeof token === 'string' &&\n token.trim() &&\n typeof phoneId === 'string' &&\n phoneId.trim()\n ) {\n return new WhatsAppClient({\n accessToken: token.trim(),\n phoneNumberId: phoneId.trim(),\n });\n }\n } catch {}\n return undefined;\n }\n\n private getInboundWhatsAppPayload(ctx: FrontendContext): any | null {\n try {\n const endpoint = '/bots/whatsapp/message';\n return (ctx as any).webhookContext?.webhookData?.get(endpoint) || null;\n } catch {\n return null;\n }\n }\n\n private async maybePostError(\n ctx: FrontendContext,\n title: string,\n message: string,\n checkId?: string\n ): Promise<void> {\n if (this.errorNotified) return;\n const whatsapp = this.getWhatsApp(ctx);\n if (!whatsapp) return;\n const payload = this.getInboundWhatsAppPayload(ctx);\n const ev: any = payload?.event;\n const from = ev?.from;\n if (!from) return;\n\n let text = `${title}`;\n if (checkId) text += `\\nCheck: ${checkId}`;\n if (message) text += `\\n${message}`;\n\n await whatsapp.sendMessage({\n to: from,\n text,\n replyToMessageId: ev?.message_id,\n });\n this.errorNotified = true;\n }\n\n private async maybePostDirectReply(\n ctx: FrontendContext,\n checkId: string,\n result: { output?: any; content?: string }\n ): Promise<void> {\n try {\n const cfg: any = ctx.config || {};\n const checkCfg: any = cfg.checks?.[checkId];\n if (!checkCfg) return;\n\n const providerType = (checkCfg.type as string) || '';\n const isAi = providerType === 'ai';\n const isLogChat = providerType === 'log' && checkCfg.group === 'chat';\n const isWorkflow = providerType === 'workflow';\n if (!isAi && !isLogChat && !isWorkflow) return;\n if (checkCfg.criticality === 'internal') return;\n\n // For AI checks, only post simple schemas\n if (isAi) {\n const schema = checkCfg.schema;\n if (typeof schema === 'string') {\n const simpleSchemas = ['code-review', 'markdown', 'text', 'plain'];\n if (!simpleSchemas.includes(schema)) return;\n }\n }\n\n const whatsapp = this.getWhatsApp(ctx);\n if (!whatsapp) return;\n\n const payload = this.getInboundWhatsAppPayload(ctx);\n const ev: any = payload?.event;\n const from = ev?.from;\n if (!from) {\n ctx.logger.warn(\n `[whatsapp-frontend] skip posting reply for ${checkId}: missing from number`\n );\n return;\n }\n\n // Extract text (same logic as Telegram/Email/Slack frontends)\n const out: any = (result as any)?.output;\n let text: string | undefined;\n if (out && typeof out.text === 'string' && out.text.trim().length > 0) {\n text = out.text.trim();\n } else if (isAi && typeof checkCfg.schema === 'string') {\n if (\n typeof (result as any)?.content === 'string' &&\n (result as any).content.trim().length > 0\n ) {\n text = (result as any).content.trim();\n }\n } else if (isLogChat && typeof (result as any)?.logOutput === 'string') {\n const raw = (result as any).logOutput;\n if (raw.trim().length > 0) text = raw.trim();\n }\n\n // Append raw output\n if (out && typeof out._rawOutput === 'string' && out._rawOutput.trim().length > 0) {\n text = (text || '') + '\\n\\n' + out._rawOutput.trim();\n }\n\n if (!text) {\n ctx.logger.info(\n `[whatsapp-frontend] skip posting reply for ${checkId}: no renderable text`\n );\n return;\n }\n\n // Normalize literal \\n escape sequences\n text = text.replace(/\\\\n/g, '\\n');\n\n const formattedText = formatWhatsAppText(text);\n const postResult = await whatsapp.sendMessage({\n to: from,\n text: formattedText,\n replyToMessageId: ev?.message_id,\n });\n\n if (!postResult.ok) {\n ctx.logger.warn(\n `[whatsapp-frontend] failed to post reply for ${checkId}: ${postResult.error}`\n );\n return;\n }\n ctx.logger.info(\n `[whatsapp-frontend] posted reply for ${checkId} to ${from} (messageId=${postResult.messageId})`\n );\n } catch (err) {\n try {\n ctx.logger.warn(\n `[whatsapp-frontend] maybePostDirectReply failed for ${checkId}: ${\n err instanceof Error ? err.message : String(err)\n }`\n );\n } catch {}\n }\n }\n}\n"],"mappings":";;;;;AAmBO,SAAS,mBAAmB,MAAsB;AACvD,MAAI,CAAC,QAAQ,OAAO,SAAS,SAAU,QAAO;AAE9C,QAAM,QAAQ,KAAK,MAAM,OAAO;AAChC,QAAM,SAAmB,CAAC;AAC1B,MAAI,cAAc;AAClB,MAAI,YAAsB,CAAC;AAE3B,WAAS,IAAI,GAAG,IAAI,MAAM,QAAQ,KAAK;AACrC,UAAM,UAAU,MAAM,CAAC,EAAE,UAAU;AAGnC,QAAI,OAAO,KAAK,OAAO,GAAG;AACxB,UAAI,CAAC,aAAa;AAChB,sBAAc;AACd,oBAAY,CAAC;AAAA,MACf,OAAO;AAEL,eAAO,KAAK,QAAQ,UAAU,KAAK,IAAI,IAAI,KAAK;AAChD,sBAAc;AACd,oBAAY,CAAC;AAAA,MACf;AACA;AAAA,IACF;AACA,QAAI,aAAa;AACf,gBAAU,KAAK,MAAM,CAAC,CAAC;AACvB;AAAA,IACF;AAEA,UAAM,OAAO,MAAM,CAAC;AAGpB,UAAM,cAAc,oBAAoB,KAAK,KAAK,UAAU,CAAC;AAC7D,QAAI,aAAa;AACf,aAAO,KAAK,IAAI,cAAc,YAAY,CAAC,EAAE,KAAK,CAAC,CAAC,GAAG;AACvD;AAAA,IACF;AAGA,QAAI,iBAAiB,KAAK,OAAO,GAAG;AAClC,aAAO,KAAK,KAAK;AACjB;AAAA,IACF;AAGA,UAAM,cAAc,uBAAuB,KAAK,IAAI;AACpD,QAAI,aAAa;AACf,aAAO,KAAK,GAAG,YAAY,CAAC,CAAC,KAAK,cAAc,YAAY,CAAC,CAAC,CAAC,EAAE;AACjE;AAAA,IACF;AAGA,UAAM,WAAW,wBAAwB,KAAK,IAAI;AAClD,QAAI,UAAU;AACZ,aAAO,KAAK,GAAG,SAAS,CAAC,CAAC,GAAG,SAAS,CAAC,CAAC,IAAI,cAAc,SAAS,CAAC,CAAC,CAAC,EAAE;AACxE;AAAA,IACF;AAGA,UAAM,UAAU,aAAa,KAAK,OAAO;AACzC,QAAI,SAAS;AACX,aAAO,KAAK,KAAK,cAAc,QAAQ,CAAC,CAAC,CAAC,EAAE;AAC5C;AAAA,IACF;AAGA,WAAO,KAAK,cAAc,IAAI,CAAC;AAAA,EACjC;AAGA,MAAI,eAAe,UAAU,SAAS,GAAG;AACvC,WAAO,KAAK,QAAQ,UAAU,KAAK,IAAI,IAAI,KAAK;AAAA,EAClD;AAEA,SAAO,OAAO,KAAK,IAAI;AACzB;AAKA,SAAS,cAAc,MAAsB;AAE3C,QAAM,YAAsB,CAAC;AAC7B,MAAI,YAAY,KAAK,QAAQ,cAAc,CAAC,IAAI,SAAiB;AAC/D,UAAM,MAAM,UAAU;AACtB,cAAU,KAAK,QAAQ,OAAO,KAAK;AACnC,WAAO,SAAW,GAAG;AAAA,EACvB,CAAC;AAGD,cAAY,UAAU;AAAA,IACpB;AAAA,IACA,CAAC,IAAI,KAAa,QAAgB,GAAG,OAAO,OAAO,KAAK,GAAG;AAAA,EAC7D;AAGA,cAAY,UAAU;AAAA,IACpB;AAAA,IACA,CAAC,IAAI,OAAe,QAAgB,GAAG,KAAK,KAAK,GAAG;AAAA,EACtD;AAGA,QAAM,YAAsB,CAAC;AAC7B,cAAY,UAAU,QAAQ,oBAAoB,CAAC,IAAI,YAAoB;AACzE,UAAM,MAAM,UAAU;AACtB,cAAU,KAAK,IAAI,OAAO,GAAG;AAC7B,WAAO,SAAW,GAAG;AAAA,EACvB,CAAC;AACD,cAAY,UAAU,QAAQ,gBAAgB,CAAC,IAAI,YAAoB;AACrE,UAAM,MAAM,UAAU;AACtB,cAAU,KAAK,IAAI,OAAO,GAAG;AAC7B,WAAO,SAAW,GAAG;AAAA,EACvB,CAAC;AAGD,cAAY,UAAU,QAAQ,6BAA6B,MAAM;AAGjE,cAAY,UAAU,QAAQ,gBAAgB,MAAM;AAGpD,cAAY,UAAU;AAAA,IACpB;AAAA,IACA,CAAC,IAAI,QAAgB,UAAU,SAAS,GAAG,CAAC;AAAA,EAC9C;AAGA,cAAY,UAAU;AAAA,IACpB;AAAA,IACA,CAAC,IAAI,QAAgB,UAAU,SAAS,GAAG,CAAC;AAAA,EAC9C;AAEA,SAAO;AACT;AAKO,SAAS,UAAU,MAAc,QAAgB,MAAgB;AACtE,MAAI,KAAK,UAAU,MAAO,QAAO,CAAC,IAAI;AAEtC,QAAM,SAAmB,CAAC;AAC1B,QAAM,QAAQ,KAAK,MAAM,IAAI;AAC7B,MAAI,UAAU;AAEd,aAAW,QAAQ,OAAO;AACxB,UAAM,YAAY,UAAU,UAAU,OAAO,OAAO;AACpD,QAAI,UAAU,SAAS,OAAO;AAC5B,UAAI,SAAS;AACX,eAAO,KAAK,OAAO;AACnB,kBAAU;AAAA,MACZ,OAAO;AAEL,YAAI,YAAY;AAChB,eAAO,UAAU,SAAS,OAAO;AAC/B,iBAAO,KAAK,UAAU,MAAM,GAAG,KAAK,CAAC;AACrC,sBAAY,UAAU,MAAM,KAAK;AAAA,QACnC;AACA,kBAAU;AAAA,MACZ;AAAA,IACF,OAAO;AACL,gBAAU;AAAA,IACZ;AAAA,EACF;AACA,MAAI,QAAS,QAAO,KAAK,OAAO;AAEhC,SAAO;AACT;AAKO,SAAS,mBAAmB,MAAsB;AACvD,SAAO,mBAAmB,IAAI;AAChC;AAjMA;AAAA;AAAA;AAAA;AAAA;;;ACIA,SAAS,kBAAkB;AAJ3B,IA0Ba;AA1Bb;AAAA;AAAA;AAKA;AAqBO,IAAM,iBAAN,MAAqB;AAAA,MAClB;AAAA,MACA;AAAA,MACA;AAAA,MACA;AAAA,MACA;AAAA,MAER,YAAY,MAA6B;AACvC,YAAI,CAAC,KAAK,eAAe,OAAO,KAAK,gBAAgB,UAAU;AAC7D,gBAAM,IAAI,MAAM,yCAAyC;AAAA,QAC3D;AACA,YAAI,CAAC,KAAK,iBAAiB,OAAO,KAAK,kBAAkB,UAAU;AACjE,gBAAM,IAAI,MAAM,2CAA2C;AAAA,QAC7D;AACA,aAAK,cAAc,KAAK;AACxB,aAAK,gBAAgB,KAAK;AAC1B,aAAK,YAAY,KAAK;AACtB,aAAK,cAAc,KAAK;AACxB,cAAM,UAAU,KAAK,cAAc;AACnC,aAAK,UAAU,8BAA8B,OAAO,IAAI,KAAK,aAAa;AAAA,MAC5E;AAAA;AAAA,MAGA,mBAA2B;AACzB,eAAO,KAAK;AAAA,MACd;AAAA;AAAA;AAAA;AAAA,MAKA,MAAM,YAAY,MAIc;AAC9B,cAAM,SAAS,UAAU,KAAK,MAAM,IAAI;AACxC,YAAI,aAAiC,EAAE,IAAI,OAAO,OAAO,oBAAoB;AAE7E,mBAAW,SAAS,QAAQ;AAC1B,gBAAM,OAAY;AAAA,YAChB,mBAAmB;AAAA,YACnB,IAAI,KAAK;AAAA,YACT,MAAM;AAAA,YACN,MAAM,EAAE,MAAM,MAAM;AAAA,UACtB;AAGA,cAAI,KAAK,kBAAkB;AACzB,iBAAK,UAAU,EAAE,YAAY,KAAK,iBAAiB;AAAA,UACrD;AAEA,cAAI;AACF,kBAAM,OAAO,MAAM,MAAM,GAAG,KAAK,OAAO,aAAa;AAAA,cACnD,QAAQ;AAAA,cACR,SAAS;AAAA,gBACP,gBAAgB;AAAA,gBAChB,eAAe,UAAU,KAAK,WAAW;AAAA,cAC3C;AAAA,cACA,MAAM,KAAK,UAAU,IAAI;AAAA,YAC3B,CAAC;AAED,kBAAM,OAAO,MAAM,KAAK,KAAK;AAE7B,gBAAI,CAAC,KAAK,IAAI;AACZ,oBAAM,SAAU,MAAc,OAAO,WAAW,QAAQ,KAAK,MAAM;AACnE,qBAAO,EAAE,IAAI,OAAO,OAAO,OAAO;AAAA,YACpC;AAEA,kBAAM,QAAS,MAAc,WAAW,CAAC,GAAG;AAC5C,yBAAa,EAAE,IAAI,MAAM,WAAW,MAAM;AAAA,UAC5C,SAAS,KAAK;AACZ,mBAAO;AAAA,cACL,IAAI;AAAA,cACJ,OAAO,eAAe,QAAQ,IAAI,UAAU,OAAO,GAAG;AAAA,YACxD;AAAA,UACF;AAAA,QACF;AAEA,eAAO;AAAA,MACT;AAAA;AAAA;AAAA;AAAA,MAKA,MAAM,WAAW,WAAmD;AAClE,YAAI;AACF,gBAAM,OAAO,MAAM,MAAM,GAAG,KAAK,OAAO,aAAa;AAAA,YACnD,QAAQ;AAAA,YACR,SAAS;AAAA,cACP,gBAAgB;AAAA,cAChB,eAAe,UAAU,KAAK,WAAW;AAAA,YAC3C;AAAA,YACA,MAAM,KAAK,UAAU;AAAA,cACnB,mBAAmB;AAAA,cACnB,QAAQ;AAAA,cACR,YAAY;AAAA,YACd,CAAC;AAAA,UACH,CAAC;AAED,cAAI,CAAC,KAAK,IAAI;AACZ,kBAAM,OAAO,MAAM,KAAK,KAAK;AAC7B,mBAAO;AAAA,cACL,IAAI;AAAA,cACJ,OAAQ,MAAc,OAAO,WAAW,QAAQ,KAAK,MAAM;AAAA,YAC7D;AAAA,UACF;AAEA,iBAAO,EAAE,IAAI,KAAK;AAAA,QACpB,SAAS,KAAK;AACZ,iBAAO;AAAA,YACL,IAAI;AAAA,YACJ,OAAO,eAAe,QAAQ,IAAI,UAAU,OAAO,GAAG;AAAA,UACxD;AAAA,QACF;AAAA,MACF;AAAA;AAAA;AAAA;AAAA;AAAA,MAMA,uBAAuB,SAAiB,iBAAkC;AACxE,YAAI,CAAC,KAAK,UAAW,QAAO;AAC5B,YAAI,CAAC,gBAAiB,QAAO;AAE7B,cAAM,WAAW,YAAY,WAAW,UAAU,KAAK,SAAS,EAAE,OAAO,OAAO,EAAE,OAAO,KAAK;AAE9F,eAAO,oBAAoB;AAAA,MAC7B;AAAA;AAAA;AAAA;AAAA,MAKA,gBAAgB,QAGd;AACA,cAAM,OAAO,OAAO,UAAU;AAC9B,cAAM,QAAQ,OAAO,kBAAkB;AACvC,cAAM,YAAY,OAAO,eAAe;AAExC,YAAI,SAAS,eAAe,UAAU,KAAK,aAAa;AACtD,iBAAO,EAAE,IAAI,MAAM,UAAU;AAAA,QAC/B;AAEA,eAAO,EAAE,IAAI,MAAM;AAAA,MACrB;AAAA,IACF;AAAA;AAAA;;;AC5KA,IAiBa;AAjBb;AAAA;AASA;AACA;AAOO,IAAM,mBAAN,MAA2C;AAAA,MAChC,OAAO;AAAA,MACf,OAAuC,CAAC;AAAA,MACxC;AAAA,MACA,gBAAyB;AAAA,MAEjC,YAAY,QAAiC;AAC3C,aAAK,MAAM,UAAU,CAAC;AAAA,MACxB;AAAA,MAEA,MAAM,KAA4B;AAChC,cAAM,MAAM,IAAI;AAEhB,YAAI;AACF,cAAI,OAAO,KAAK,6BAA6B;AAAA,QAC/C,QAAQ;AAAA,QAAC;AAGT,aAAK,KAAK;AAAA,UACR,IAAI,GAAG,kBAAkB,OAAO,QAAa;AAC3C,kBAAM,KAAM,OAAO,IAAI,WAAY;AACnC,kBAAM,KAAK,qBAAqB,KAAK,GAAG,SAAS,GAAG,MAAM,EAAE,MAAM,MAAM;AAAA,YAAC,CAAC;AAAA,UAC5E,CAAC;AAAA,QACH;AAGA,aAAK,KAAK;AAAA,UACR,IAAI,GAAG,gBAAgB,OAAO,QAAa;AACzC,kBAAM,KAAM,OAAO,IAAI,WAAY;AACnC,kBAAM,UAAU,IAAI,OAAO,WAAW;AACtC,kBAAM,KAAK,eAAe,KAAK,gBAAgB,SAAS,IAAI,OAAO,EAAE,MAAM,MAAM;AAAA,YAAC,CAAC;AAAA,UACrF,CAAC;AAAA,QACH;AAGA,aAAK,KAAK;AAAA,UACR,IAAI,GAAG,YAAY,OAAO,QAAa;AACrC,kBAAM,KAAM,OAAO,IAAI,WAAY;AACnC,kBAAM,UAAU,IAAI,OAAO,WAAW;AACtC,kBAAM,KAAK,eAAe,KAAK,cAAc,OAAO,EAAE,MAAM,MAAM;AAAA,YAAC,CAAC;AAAA,UACtE,CAAC;AAAA,QACH;AAAA,MAIF;AAAA,MAEA,OAAa;AACX,mBAAW,KAAK,KAAK,KAAM,GAAE,YAAY;AACzC,aAAK,OAAO,CAAC;AAAA,MACf;AAAA,MAEQ,YAAY,KAAkD;AAEpE,cAAM,WAAY,IAAY,YAAa,IAAY;AACvD,YAAI,SAAU,QAAO;AAErB,YAAI;AACF,gBAAM,QAAQ,KAAK,IAAI,eAAe,QAAQ,IAAI;AAClD,gBAAM,UAAU,KAAK,IAAI,iBAAiB,QAAQ,IAAI;AACtD,cACE,OAAO,UAAU,YACjB,MAAM,KAAK,KACX,OAAO,YAAY,YACnB,QAAQ,KAAK,GACb;AACA,mBAAO,IAAI,eAAe;AAAA,cACxB,aAAa,MAAM,KAAK;AAAA,cACxB,eAAe,QAAQ,KAAK;AAAA,YAC9B,CAAC;AAAA,UACH;AAAA,QACF,QAAQ;AAAA,QAAC;AACT,eAAO;AAAA,MACT;AAAA,MAEQ,0BAA0B,KAAkC;AAClE,YAAI;AACF,gBAAM,WAAW;AACjB,iBAAQ,IAAY,gBAAgB,aAAa,IAAI,QAAQ,KAAK;AAAA,QACpE,QAAQ;AACN,iBAAO;AAAA,QACT;AAAA,MACF;AAAA,MAEA,MAAc,eACZ,KACA,OACA,SACA,SACe;AACf,YAAI,KAAK,cAAe;AACxB,cAAM,WAAW,KAAK,YAAY,GAAG;AACrC,YAAI,CAAC,SAAU;AACf,cAAM,UAAU,KAAK,0BAA0B,GAAG;AAClD,cAAM,KAAU,SAAS;AACzB,cAAM,OAAO,IAAI;AACjB,YAAI,CAAC,KAAM;AAEX,YAAI,OAAO,GAAG,KAAK;AACnB,YAAI,QAAS,SAAQ;AAAA,SAAY,OAAO;AACxC,YAAI,QAAS,SAAQ;AAAA,EAAK,OAAO;AAEjC,cAAM,SAAS,YAAY;AAAA,UACzB,IAAI;AAAA,UACJ;AAAA,UACA,kBAAkB,IAAI;AAAA,QACxB,CAAC;AACD,aAAK,gBAAgB;AAAA,MACvB;AAAA,MAEA,MAAc,qBACZ,KACA,SACA,QACe;AACf,YAAI;AACF,gBAAM,MAAW,IAAI,UAAU,CAAC;AAChC,gBAAM,WAAgB,IAAI,SAAS,OAAO;AAC1C,cAAI,CAAC,SAAU;AAEf,gBAAM,eAAgB,SAAS,QAAmB;AAClD,gBAAM,OAAO,iBAAiB;AAC9B,gBAAM,YAAY,iBAAiB,SAAS,SAAS,UAAU;AAC/D,gBAAM,aAAa,iBAAiB;AACpC,cAAI,CAAC,QAAQ,CAAC,aAAa,CAAC,WAAY;AACxC,cAAI,SAAS,gBAAgB,WAAY;AAGzC,cAAI,MAAM;AACR,kBAAM,SAAS,SAAS;AACxB,gBAAI,OAAO,WAAW,UAAU;AAC9B,oBAAM,gBAAgB,CAAC,eAAe,YAAY,QAAQ,OAAO;AACjE,kBAAI,CAAC,cAAc,SAAS,MAAM,EAAG;AAAA,YACvC;AAAA,UACF;AAEA,gBAAM,WAAW,KAAK,YAAY,GAAG;AACrC,cAAI,CAAC,SAAU;AAEf,gBAAM,UAAU,KAAK,0BAA0B,GAAG;AAClD,gBAAM,KAAU,SAAS;AACzB,gBAAM,OAAO,IAAI;AACjB,cAAI,CAAC,MAAM;AACT,gBAAI,OAAO;AAAA,cACT,8CAA8C,OAAO;AAAA,YACvD;AACA;AAAA,UACF;AAGA,gBAAM,MAAY,QAAgB;AAClC,cAAI;AACJ,cAAI,OAAO,OAAO,IAAI,SAAS,YAAY,IAAI,KAAK,KAAK,EAAE,SAAS,GAAG;AACrE,mBAAO,IAAI,KAAK,KAAK;AAAA,UACvB,WAAW,QAAQ,OAAO,SAAS,WAAW,UAAU;AACtD,gBACE,OAAQ,QAAgB,YAAY,YACnC,OAAe,QAAQ,KAAK,EAAE,SAAS,GACxC;AACA,qBAAQ,OAAe,QAAQ,KAAK;AAAA,YACtC;AAAA,UACF,WAAW,aAAa,OAAQ,QAAgB,cAAc,UAAU;AACtE,kBAAM,MAAO,OAAe;AAC5B,gBAAI,IAAI,KAAK,EAAE,SAAS,EAAG,QAAO,IAAI,KAAK;AAAA,UAC7C;AAGA,cAAI,OAAO,OAAO,IAAI,eAAe,YAAY,IAAI,WAAW,KAAK,EAAE,SAAS,GAAG;AACjF,oBAAQ,QAAQ,MAAM,SAAS,IAAI,WAAW,KAAK;AAAA,UACrD;AAEA,cAAI,CAAC,MAAM;AACT,gBAAI,OAAO;AAAA,cACT,8CAA8C,OAAO;AAAA,YACvD;AACA;AAAA,UACF;AAGA,iBAAO,KAAK,QAAQ,QAAQ,IAAI;AAEhC,gBAAM,gBAAgB,mBAAmB,IAAI;AAC7C,gBAAM,aAAa,MAAM,SAAS,YAAY;AAAA,YAC5C,IAAI;AAAA,YACJ,MAAM;AAAA,YACN,kBAAkB,IAAI;AAAA,UACxB,CAAC;AAED,cAAI,CAAC,WAAW,IAAI;AAClB,gBAAI,OAAO;AAAA,cACT,gDAAgD,OAAO,KAAK,WAAW,KAAK;AAAA,YAC9E;AACA;AAAA,UACF;AACA,cAAI,OAAO;AAAA,YACT,wCAAwC,OAAO,OAAO,IAAI,eAAe,WAAW,SAAS;AAAA,UAC/F;AAAA,QACF,SAAS,KAAK;AACZ,cAAI;AACF,gBAAI,OAAO;AAAA,cACT,uDAAuD,OAAO,KAC5D,eAAe,QAAQ,IAAI,UAAU,OAAO,GAAG,CACjD;AAAA,YACF;AAAA,UACF,QAAQ;AAAA,UAAC;AAAA,QACX;AAAA,MACF;AAAA,IACF;AAAA;AAAA;","names":[]}
|