create-principles-disciple 1.100.0 → 1.102.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/console/dist/server/index.js +9 -0
- package/console/dist/server/models/ActivationsConsoleModel.d.ts +37 -1
- package/console/dist/server/models/ActivationsConsoleModel.js +114 -13
- package/console/dist/server/routes/onboarding.d.ts +34 -0
- package/console/dist/server/routes/onboarding.js +324 -0
- package/console/dist/ui/App.js +74 -15
- package/console/dist/ui/api.d.ts +17 -1
- package/console/dist/ui/api.js +6 -1
- package/console/dist/ui/components/onboarding/CircuitDiagram.d.ts +8 -0
- package/console/dist/ui/components/onboarding/CircuitDiagram.js +18 -0
- package/console/dist/ui/components/onboarding/DemoResultView.d.ts +22 -0
- package/console/dist/ui/components/onboarding/DemoResultView.js +15 -0
- package/console/dist/ui/i18n/en.json +127 -0
- package/console/dist/ui/i18n/zh-CN.json +127 -0
- package/console/dist/ui/pages/activation/ActivationValidators.js +1 -1
- package/console/dist/ui/pages/control-center/AgentCard.js +10 -3
- package/console/dist/ui/pages/control-center/ControlCenterPage.js +1 -1
- package/console/dist/ui/pages/settings/SettingsPage.js +64 -5
- package/console/dist/ui/pages/signal-keywords/KeywordEditDialog.d.ts +12 -0
- package/console/dist/ui/pages/signal-keywords/KeywordEditDialog.js +41 -0
- package/console/dist/ui/pages/signal-keywords/KeywordListSection.d.ts +10 -0
- package/console/dist/ui/pages/signal-keywords/KeywordListSection.js +39 -0
- package/console/dist/ui/pages/signal-keywords/PendingTermsSection.d.ts +14 -0
- package/console/dist/ui/pages/signal-keywords/PendingTermsSection.js +35 -0
- package/console/dist/ui/pages/signal-keywords/SignalKeywordsPage.d.ts +1 -0
- package/console/dist/ui/pages/signal-keywords/SignalKeywordsPage.js +49 -0
- package/console/dist/ui/pages/welcome/WelcomePage.d.ts +5 -0
- package/console/dist/ui/pages/welcome/WelcomePage.js +185 -0
- package/console/dist/ui/utils/__tests__/onboarding-state.test.d.ts +1 -0
- package/console/dist/ui/utils/__tests__/onboarding-state.test.js +72 -0
- package/console/dist/ui/utils/agent-metadata.d.ts +13 -0
- package/console/dist/ui/utils/agent-metadata.js +26 -0
- package/console/dist/ui/utils/onboarding-state.d.ts +25 -0
- package/console/dist/ui/utils/onboarding-state.js +77 -0
- package/console/dist/ui/utils/signal-keywords-api.d.ts +68 -0
- package/console/dist/ui/utils/signal-keywords-api.js +121 -0
- package/console/dist/ui/utils/signal-keywords-types.d.ts +57 -0
- package/console/dist/ui/utils/signal-keywords-types.js +10 -0
- package/console/dist/ui/utils/signal-keywords-validators.d.ts +20 -0
- package/console/dist/ui/utils/signal-keywords-validators.js +114 -0
- package/console/dist/web/assets/app.css +401 -0
- package/console/dist/web/assets/app.js +6904 -1835
- package/core/dist/index.d.ts +2 -0
- package/core/dist/index.d.ts.map +1 -1
- package/core/dist/index.js +1 -0
- package/core/dist/index.js.map +1 -1
- package/core/dist/runtime-v2/__tests__/admission-gate.test.js +63 -1
- package/core/dist/runtime-v2/__tests__/admission-gate.test.js.map +1 -1
- package/core/dist/runtime-v2/__tests__/architecture-regression.test.js +21 -5
- package/core/dist/runtime-v2/__tests__/architecture-regression.test.js.map +1 -1
- package/core/dist/runtime-v2/__tests__/chain-integrity-attack.test.js +17 -0
- package/core/dist/runtime-v2/__tests__/chain-integrity-attack.test.js.map +1 -1
- package/core/dist/runtime-v2/__tests__/chain-integrity-real-path.test.js +12 -0
- package/core/dist/runtime-v2/__tests__/chain-integrity-real-path.test.js.map +1 -1
- package/core/dist/runtime-v2/__tests__/evaluator-runner-vslice-v2.test.js +28 -0
- package/core/dist/runtime-v2/__tests__/evaluator-runner-vslice-v2.test.js.map +1 -1
- package/core/dist/runtime-v2/__tests__/internalization-chain-integrity-read-model.test.js +168 -1
- package/core/dist/runtime-v2/__tests__/internalization-chain-integrity-read-model.test.js.map +1 -1
- package/core/dist/runtime-v2/__tests__/pain-to-principle-service.test.js +8 -0
- package/core/dist/runtime-v2/__tests__/pain-to-principle-service.test.js.map +1 -1
- package/core/dist/runtime-v2/activation/__tests__/activation-dispatcher.test.js +53 -0
- package/core/dist/runtime-v2/activation/__tests__/activation-dispatcher.test.js.map +1 -1
- package/core/dist/runtime-v2/activation/__tests__/helpers.d.ts +21 -0
- package/core/dist/runtime-v2/activation/__tests__/helpers.d.ts.map +1 -0
- package/core/dist/runtime-v2/activation/__tests__/helpers.js +132 -0
- package/core/dist/runtime-v2/activation/__tests__/helpers.js.map +1 -0
- package/core/dist/runtime-v2/activation/__tests__/story-a-acceptance.test.js +2 -117
- package/core/dist/runtime-v2/activation/__tests__/story-a-acceptance.test.js.map +1 -1
- package/core/dist/runtime-v2/activation/activation-dispatcher.d.ts.map +1 -1
- package/core/dist/runtime-v2/activation/activation-dispatcher.js +18 -2
- package/core/dist/runtime-v2/activation/activation-dispatcher.js.map +1 -1
- package/core/dist/runtime-v2/activation/index.d.ts +1 -1
- package/core/dist/runtime-v2/activation/index.d.ts.map +1 -1
- package/core/dist/runtime-v2/activation/index.js +1 -1
- package/core/dist/runtime-v2/activation/index.js.map +1 -1
- package/core/dist/runtime-v2/activation/writers/__tests__/rule-host-writer.test.js +253 -6
- package/core/dist/runtime-v2/activation/writers/__tests__/rule-host-writer.test.js.map +1 -1
- package/core/dist/runtime-v2/activation/writers/rule-host-writer.d.ts +12 -0
- package/core/dist/runtime-v2/activation/writers/rule-host-writer.d.ts.map +1 -1
- package/core/dist/runtime-v2/activation/writers/rule-host-writer.js +96 -2
- package/core/dist/runtime-v2/activation/writers/rule-host-writer.js.map +1 -1
- package/core/dist/runtime-v2/admission-gate.d.ts +27 -0
- package/core/dist/runtime-v2/admission-gate.d.ts.map +1 -1
- package/core/dist/runtime-v2/admission-gate.js +55 -0
- package/core/dist/runtime-v2/admission-gate.js.map +1 -1
- package/core/dist/runtime-v2/cli/diagnose.d.ts +4 -0
- package/core/dist/runtime-v2/cli/diagnose.d.ts.map +1 -1
- package/core/dist/runtime-v2/cli/diagnose.js +25 -0
- package/core/dist/runtime-v2/cli/diagnose.js.map +1 -1
- package/core/dist/runtime-v2/config/__tests__/internal-agent-names.test.d.ts +2 -0
- package/core/dist/runtime-v2/config/__tests__/internal-agent-names.test.d.ts.map +1 -0
- package/core/dist/runtime-v2/config/__tests__/internal-agent-names.test.js +15 -0
- package/core/dist/runtime-v2/config/__tests__/internal-agent-names.test.js.map +1 -0
- package/core/dist/runtime-v2/config/__tests__/pd-config-agent-binding.test.js +7 -0
- package/core/dist/runtime-v2/config/__tests__/pd-config-agent-binding.test.js.map +1 -1
- package/core/dist/runtime-v2/config/__tests__/pd-config-contract.test.js +28 -0
- package/core/dist/runtime-v2/config/__tests__/pd-config-contract.test.js.map +1 -1
- package/core/dist/runtime-v2/config/__tests__/pd-config-redaction-deep.test.js +1 -0
- package/core/dist/runtime-v2/config/__tests__/pd-config-redaction-deep.test.js.map +1 -1
- package/core/dist/runtime-v2/config/__tests__/pd-config-validation-edge-cases.test.js +1 -0
- package/core/dist/runtime-v2/config/__tests__/pd-config-validation-edge-cases.test.js.map +1 -1
- package/core/dist/runtime-v2/config/index.d.ts +5 -3
- package/core/dist/runtime-v2/config/index.d.ts.map +1 -1
- package/core/dist/runtime-v2/config/index.js +8 -2
- package/core/dist/runtime-v2/config/index.js.map +1 -1
- package/core/dist/runtime-v2/config/pd-config-defaults.d.ts +2 -1
- package/core/dist/runtime-v2/config/pd-config-defaults.d.ts.map +1 -1
- package/core/dist/runtime-v2/config/pd-config-defaults.js +12 -0
- package/core/dist/runtime-v2/config/pd-config-defaults.js.map +1 -1
- package/core/dist/runtime-v2/config/pd-config-effective.d.ts.map +1 -1
- package/core/dist/runtime-v2/config/pd-config-effective.js +25 -1
- package/core/dist/runtime-v2/config/pd-config-effective.js.map +1 -1
- package/core/dist/runtime-v2/config/pd-config-feature-flags.d.ts.map +1 -1
- package/core/dist/runtime-v2/config/pd-config-feature-flags.js +6 -1
- package/core/dist/runtime-v2/config/pd-config-feature-flags.js.map +1 -1
- package/core/dist/runtime-v2/config/pd-config-redaction.d.ts.map +1 -1
- package/core/dist/runtime-v2/config/pd-config-redaction.js +9 -0
- package/core/dist/runtime-v2/config/pd-config-redaction.js.map +1 -1
- package/core/dist/runtime-v2/config/pd-config-types.d.ts +110 -1
- package/core/dist/runtime-v2/config/pd-config-types.d.ts.map +1 -1
- package/core/dist/runtime-v2/config/pd-config-types.js +7 -0
- package/core/dist/runtime-v2/config/pd-config-types.js.map +1 -1
- package/core/dist/runtime-v2/config/pd-config-validate.d.ts.map +1 -1
- package/core/dist/runtime-v2/config/pd-config-validate.js +114 -1
- package/core/dist/runtime-v2/config/pd-config-validate.js.map +1 -1
- package/core/dist/runtime-v2/config/pd-profile-constants.d.ts +27 -0
- package/core/dist/runtime-v2/config/pd-profile-constants.d.ts.map +1 -0
- package/core/dist/runtime-v2/config/pd-profile-constants.js +145 -0
- package/core/dist/runtime-v2/config/pd-profile-constants.js.map +1 -0
- package/core/dist/runtime-v2/config/pd-validate-profile.d.ts +28 -0
- package/core/dist/runtime-v2/config/pd-validate-profile.d.ts.map +1 -0
- package/core/dist/runtime-v2/config/pd-validate-profile.js +482 -0
- package/core/dist/runtime-v2/config/pd-validate-profile.js.map +1 -0
- package/core/dist/runtime-v2/feature-flags/__tests__/feature-flag-contract.test.js +26 -0
- package/core/dist/runtime-v2/feature-flags/__tests__/feature-flag-contract.test.js.map +1 -1
- package/core/dist/runtime-v2/feature-flags/__tests__/plugin-surface-registry.test.js +12 -1
- package/core/dist/runtime-v2/feature-flags/__tests__/plugin-surface-registry.test.js.map +1 -1
- package/core/dist/runtime-v2/feature-flags/feature-flag-contract.d.ts.map +1 -1
- package/core/dist/runtime-v2/feature-flags/feature-flag-contract.js +8 -0
- package/core/dist/runtime-v2/feature-flags/feature-flag-contract.js.map +1 -1
- package/core/dist/runtime-v2/feature-flags/plugin-surface-registry.d.ts.map +1 -1
- package/core/dist/runtime-v2/feature-flags/plugin-surface-registry.js +8 -2
- package/core/dist/runtime-v2/feature-flags/plugin-surface-registry.js.map +1 -1
- package/core/dist/runtime-v2/index.d.ts +6 -4
- package/core/dist/runtime-v2/index.d.ts.map +1 -1
- package/core/dist/runtime-v2/index.js +5 -3
- package/core/dist/runtime-v2/index.js.map +1 -1
- package/core/dist/runtime-v2/internalization/__tests__/artificer-prompt-builder-v2.test.js +25 -0
- package/core/dist/runtime-v2/internalization/__tests__/artificer-prompt-builder-v2.test.js.map +1 -1
- package/core/dist/runtime-v2/internalization/__tests__/artificer-rule-output.test.js +139 -0
- package/core/dist/runtime-v2/internalization/__tests__/artificer-rule-output.test.js.map +1 -1
- package/core/dist/runtime-v2/internalization/__tests__/diag-chain-e2e.test.js +20 -1
- package/core/dist/runtime-v2/internalization/__tests__/diag-chain-e2e.test.js.map +1 -1
- package/core/dist/runtime-v2/internalization/__tests__/diag-rootcause-intent-tension.test.js +7 -0
- package/core/dist/runtime-v2/internalization/__tests__/diag-rootcause-intent-tension.test.js.map +1 -1
- package/core/dist/runtime-v2/internalization/__tests__/diag-rootcause-runner.test.js +21 -0
- package/core/dist/runtime-v2/internalization/__tests__/diag-rootcause-runner.test.js.map +1 -1
- package/core/dist/runtime-v2/internalization/__tests__/rule-host-input-builder.test.js +23 -0
- package/core/dist/runtime-v2/internalization/__tests__/rule-host-input-builder.test.js.map +1 -1
- package/core/dist/runtime-v2/internalization/artificer-output.d.ts +7 -0
- package/core/dist/runtime-v2/internalization/artificer-output.d.ts.map +1 -1
- package/core/dist/runtime-v2/internalization/artificer-output.js +22 -1
- package/core/dist/runtime-v2/internalization/artificer-output.js.map +1 -1
- package/core/dist/runtime-v2/internalization/artificer-prompt-builder.d.ts.map +1 -1
- package/core/dist/runtime-v2/internalization/artificer-prompt-builder.js +2 -0
- package/core/dist/runtime-v2/internalization/artificer-prompt-builder.js.map +1 -1
- package/core/dist/runtime-v2/internalization/artificer-runner.d.ts.map +1 -1
- package/core/dist/runtime-v2/internalization/artificer-runner.js +13 -0
- package/core/dist/runtime-v2/internalization/artificer-runner.js.map +1 -1
- package/core/dist/runtime-v2/internalization/diag-distiller-runner.d.ts.map +1 -1
- package/core/dist/runtime-v2/internalization/diag-distiller-runner.js +4 -1
- package/core/dist/runtime-v2/internalization/diag-distiller-runner.js.map +1 -1
- package/core/dist/runtime-v2/internalization/diag-rootcause-runner.d.ts.map +1 -1
- package/core/dist/runtime-v2/internalization/diag-rootcause-runner.js +7 -1
- package/core/dist/runtime-v2/internalization/diag-rootcause-runner.js.map +1 -1
- package/core/dist/runtime-v2/internalization/diag-router-runner.d.ts.map +1 -1
- package/core/dist/runtime-v2/internalization/diag-router-runner.js +4 -1
- package/core/dist/runtime-v2/internalization/diag-router-runner.js.map +1 -1
- package/core/dist/runtime-v2/internalization/evaluator-runner.d.ts.map +1 -1
- package/core/dist/runtime-v2/internalization/evaluator-runner.js +7 -1
- package/core/dist/runtime-v2/internalization/evaluator-runner.js.map +1 -1
- package/core/dist/runtime-v2/internalization/index.d.ts +1 -1
- package/core/dist/runtime-v2/internalization/index.d.ts.map +1 -1
- package/core/dist/runtime-v2/internalization/index.js +1 -1
- package/core/dist/runtime-v2/internalization/index.js.map +1 -1
- package/core/dist/runtime-v2/internalization/internalization-task-guards.d.ts +7 -0
- package/core/dist/runtime-v2/internalization/internalization-task-guards.d.ts.map +1 -1
- package/core/dist/runtime-v2/internalization/internalization-task-guards.js +8 -0
- package/core/dist/runtime-v2/internalization/internalization-task-guards.js.map +1 -1
- package/core/dist/runtime-v2/internalization-chain-integrity-read-model.d.ts.map +1 -1
- package/core/dist/runtime-v2/internalization-chain-integrity-read-model.js +57 -1
- package/core/dist/runtime-v2/internalization-chain-integrity-read-model.js.map +1 -1
- package/core/dist/runtime-v2/proven-channel-baseline.js +1 -1
- package/core/dist/runtime-v2/proven-channel-baseline.js.map +1 -1
- package/core/dist/runtime-v2/runner/__tests__/diagnose.test.js +91 -1
- package/core/dist/runtime-v2/runner/__tests__/diagnose.test.js.map +1 -1
- package/core/dist/runtime-v2/signal-collector/__tests__/keyword-stage.test.d.ts +2 -0
- package/core/dist/runtime-v2/signal-collector/__tests__/keyword-stage.test.d.ts.map +1 -0
- package/core/dist/runtime-v2/signal-collector/__tests__/keyword-stage.test.js +39 -0
- package/core/dist/runtime-v2/signal-collector/__tests__/keyword-stage.test.js.map +1 -0
- package/core/dist/runtime-v2/signal-collector/__tests__/llm-stage.test.d.ts +2 -0
- package/core/dist/runtime-v2/signal-collector/__tests__/llm-stage.test.d.ts.map +1 -0
- package/core/dist/runtime-v2/signal-collector/__tests__/llm-stage.test.js +34 -0
- package/core/dist/runtime-v2/signal-collector/__tests__/llm-stage.test.js.map +1 -0
- package/core/dist/runtime-v2/signal-collector/__tests__/signal-collector.test.d.ts +2 -0
- package/core/dist/runtime-v2/signal-collector/__tests__/signal-collector.test.d.ts.map +1 -0
- package/core/dist/runtime-v2/signal-collector/__tests__/signal-collector.test.js +222 -0
- package/core/dist/runtime-v2/signal-collector/__tests__/signal-collector.test.js.map +1 -0
- package/core/dist/runtime-v2/signal-collector/__tests__/types.test.d.ts +2 -0
- package/core/dist/runtime-v2/signal-collector/__tests__/types.test.d.ts.map +1 -0
- package/core/dist/runtime-v2/signal-collector/__tests__/types.test.js +35 -0
- package/core/dist/runtime-v2/signal-collector/__tests__/types.test.js.map +1 -0
- package/core/dist/runtime-v2/signal-collector/index.d.ts +5 -0
- package/core/dist/runtime-v2/signal-collector/index.d.ts.map +1 -0
- package/core/dist/runtime-v2/signal-collector/index.js +5 -0
- package/core/dist/runtime-v2/signal-collector/index.js.map +1 -0
- package/core/dist/runtime-v2/signal-collector/keyword-stage.d.ts +20 -0
- package/core/dist/runtime-v2/signal-collector/keyword-stage.d.ts.map +1 -0
- package/core/dist/runtime-v2/signal-collector/keyword-stage.js +61 -0
- package/core/dist/runtime-v2/signal-collector/keyword-stage.js.map +1 -0
- package/core/dist/runtime-v2/signal-collector/llm-stage.d.ts +16 -0
- package/core/dist/runtime-v2/signal-collector/llm-stage.d.ts.map +1 -0
- package/core/dist/runtime-v2/signal-collector/llm-stage.js +34 -0
- package/core/dist/runtime-v2/signal-collector/llm-stage.js.map +1 -0
- package/core/dist/runtime-v2/signal-collector/signal-collector.d.ts +16 -0
- package/core/dist/runtime-v2/signal-collector/signal-collector.d.ts.map +1 -0
- package/core/dist/runtime-v2/signal-collector/signal-collector.js +71 -0
- package/core/dist/runtime-v2/signal-collector/signal-collector.js.map +1 -0
- package/core/dist/runtime-v2/signal-collector/types.d.ts +61 -0
- package/core/dist/runtime-v2/signal-collector/types.d.ts.map +1 -0
- package/core/dist/runtime-v2/signal-collector/types.js +45 -0
- package/core/dist/runtime-v2/signal-collector/types.js.map +1 -0
- package/core/dist/runtime-v2/store/candidate/sqlite-candidate-store.d.ts.map +1 -1
- package/core/dist/runtime-v2/store/candidate/sqlite-candidate-store.js +19 -0
- package/core/dist/runtime-v2/store/candidate/sqlite-candidate-store.js.map +1 -1
- package/core/dist/runtime-v2/store/schema-conformance.test.js +73 -0
- package/core/dist/runtime-v2/store/schema-conformance.test.js.map +1 -1
- package/core/dist/runtime-v2/store/sqlite-connection-schema-version.test.js +41 -7
- package/core/dist/runtime-v2/store/sqlite-connection-schema-version.test.js.map +1 -1
- package/core/dist/runtime-v2/store/sqlite-connection.d.ts.map +1 -1
- package/core/dist/runtime-v2/store/sqlite-connection.js +22 -1
- package/core/dist/runtime-v2/store/sqlite-connection.js.map +1 -1
- package/core/dist/runtime-v2/types/event-types.d.ts +40 -3
- package/core/dist/runtime-v2/types/event-types.d.ts.map +1 -1
- package/core/dist/runtime-v2/types/event-types.js +9 -0
- package/core/dist/runtime-v2/types/event-types.js.map +1 -1
- package/core/dist/runtime-v2/types/index.d.ts +2 -2
- package/core/dist/runtime-v2/types/index.d.ts.map +1 -1
- package/core/dist/runtime-v2/types/index.js +1 -1
- package/core/dist/runtime-v2/types/index.js.map +1 -1
- package/core/dist/workflow-funnel-loader.js +1 -1
- package/core/dist/workflow-funnel-loader.js.map +1 -1
- package/dist/i18n.d.ts.map +1 -1
- package/dist/i18n.js +6 -0
- package/dist/i18n.js.map +1 -1
- package/dist/index.js +12 -3
- package/dist/index.js.map +1 -1
- package/dist/installer.d.ts +3 -0
- package/dist/installer.d.ts.map +1 -1
- package/dist/installer.js +167 -1
- package/dist/installer.js.map +1 -1
- package/dist/mvp-config.d.ts +8 -0
- package/dist/mvp-config.d.ts.map +1 -1
- package/dist/mvp-config.js +12 -2
- package/dist/mvp-config.js.map +1 -1
- package/package.json +1 -1
- package/pd-cli/dist/commands/candidate.d.ts.map +1 -1
- package/pd-cli/dist/commands/candidate.js +89 -7
- package/pd-cli/dist/commands/candidate.js.map +1 -1
- package/pd-cli/dist/commands/pain-retry.d.ts +3 -0
- package/pd-cli/dist/commands/pain-retry.d.ts.map +1 -1
- package/pd-cli/dist/commands/pain-retry.js +39 -14
- package/pd-cli/dist/commands/pain-retry.js.map +1 -1
- package/pd-cli/dist/commands/runtime-activation.d.ts +4 -0
- package/pd-cli/dist/commands/runtime-activation.d.ts.map +1 -1
- package/pd-cli/dist/commands/runtime-activation.js +244 -10
- package/pd-cli/dist/commands/runtime-activation.js.map +1 -1
- package/pd-cli/dist/index.js +7 -84
- package/pd-cli/dist/index.js.map +1 -1
- package/pd-cli/dist/services/rulehost-pipeline-runner.js +1 -1
- package/pd-cli/dist/services/rulehost-pipeline-runner.js.map +1 -1
- package/pd-cli/package.json +1 -1
- package/plugin/dist/commands/context.js +17 -11
- package/plugin/dist/commands/samples.js +25 -0
- package/plugin/dist/core/event-log.d.ts +11 -1
- package/plugin/dist/core/event-log.js +13 -0
- package/plugin/dist/core/init.js +3 -4
- package/plugin/dist/core/rule-host.d.ts +68 -0
- package/plugin/dist/core/rule-host.js +167 -28
- package/plugin/dist/core/signal-collector-host.d.ts +105 -0
- package/plugin/dist/core/signal-collector-host.js +337 -0
- package/plugin/dist/hooks/prompt.d.ts +3 -2
- package/plugin/dist/hooks/prompt.js +47 -571
- package/plugin/dist/types/event-types.d.ts +1 -1
- package/plugin/dist/types.d.ts +5 -25
- package/plugin/dist/types.js +4 -9
- package/plugin/dist/utils/hashing.js +1 -1
|
@@ -50,7 +50,23 @@ export class RuleHost {
|
|
|
50
50
|
implementationSources = new Map();
|
|
51
51
|
activationFingerprint = null;
|
|
52
52
|
cachedImplementations = [];
|
|
53
|
+
/**
|
|
54
|
+
* PRI-491: Cached skipped activations from the last load. Returned alongside
|
|
55
|
+
* cachedImplementations on fingerprint hit so evaluateDetailed can surface
|
|
56
|
+
* them without re-scanning SQLite.
|
|
57
|
+
*/
|
|
58
|
+
cachedSkipped = [];
|
|
53
59
|
sqliteConnection = null;
|
|
60
|
+
/**
|
|
61
|
+
* R2-RH-002: Guards the "armed but empty" warn so it fires at most once per
|
|
62
|
+
* RuleHost instance. Without this, the 0-rules path (workspaceDir missing OR
|
|
63
|
+
* zero active code_tool_hook activations) returns [] silently on every
|
|
64
|
+
* evaluation — an observability gap (rc-9-no-silent-fallback). The warn is
|
|
65
|
+
* NOT a degradation fallback (RuleHost correctly has no opinion when empty);
|
|
66
|
+
* it makes the empty-armed state visible so operators can investigate why
|
|
67
|
+
* no live rules are loaded.
|
|
68
|
+
*/
|
|
69
|
+
emptyLoadWarnEmitted = false;
|
|
54
70
|
constructor(stateDir, logger = console, options) {
|
|
55
71
|
this.stateDir = stateDir;
|
|
56
72
|
this.logger = logger;
|
|
@@ -83,12 +99,14 @@ export class RuleHost {
|
|
|
83
99
|
this.sqliteConnection?.close();
|
|
84
100
|
this.sqliteConnection = null;
|
|
85
101
|
this.cachedImplementations = [];
|
|
102
|
+
this.cachedSkipped = [];
|
|
86
103
|
this.activationFingerprint = null;
|
|
87
104
|
this.implementationSources.clear();
|
|
105
|
+
this.emptyLoadWarnEmitted = false;
|
|
88
106
|
}
|
|
89
107
|
evaluateDetailed(input) {
|
|
90
108
|
try {
|
|
91
|
-
const activeImpls = this._loadActiveCodeImplementations(input.context?.version === 2);
|
|
109
|
+
const { loaded: activeImpls, skipped } = this._loadActiveCodeImplementations(input.context?.version === 2);
|
|
92
110
|
const liveImpls = activeImpls.filter((impl) => impl.activationMode === 'live');
|
|
93
111
|
const shadowImpls = activeImpls.filter((impl) => impl.activationMode === 'shadow');
|
|
94
112
|
const shadowDecisions = [];
|
|
@@ -117,12 +135,12 @@ export class RuleHost {
|
|
|
117
135
|
this._recordUnhealthy(source.activationId, source.artifactId, source.ruleId, reason, 'Fix the RuleCode runtime error or return shape, then re-activate the rule');
|
|
118
136
|
},
|
|
119
137
|
});
|
|
120
|
-
return { liveDecision, shadowDecisions };
|
|
138
|
+
return { liveDecision, shadowDecisions, skippedActivations: skipped };
|
|
121
139
|
}
|
|
122
140
|
catch (hostError) {
|
|
123
141
|
// Conservative degradation: log and return undefined (D-08)
|
|
124
142
|
this.logger.warn?.(`[RuleHost] Host evaluation failed, degrading conservatively: ${String(hostError)}`);
|
|
125
|
-
return { liveDecision: undefined, shadowDecisions: [] };
|
|
143
|
+
return { liveDecision: undefined, shadowDecisions: [], skippedActivations: [] };
|
|
126
144
|
}
|
|
127
145
|
}
|
|
128
146
|
/**
|
|
@@ -137,16 +155,38 @@ export class RuleHost {
|
|
|
137
155
|
*/
|
|
138
156
|
_loadActiveCodeImplementations(supportsContextV2) {
|
|
139
157
|
if (!this.workspaceDir) {
|
|
140
|
-
|
|
158
|
+
this._emitEmptyLoadWarn('workspaceDir not configured — RuleHost cannot load active code_tool_hook rules', 'Provide workspaceDir when constructing RuleHost (required for code_tool_hook channel)');
|
|
159
|
+
return { loaded: [], skipped: [] };
|
|
141
160
|
}
|
|
142
161
|
try {
|
|
143
|
-
|
|
162
|
+
const { loaded, skipped } = this._loadFromActivationsTable(this.workspaceDir, supportsContextV2);
|
|
163
|
+
if (loaded.length === 0) {
|
|
164
|
+
this._emitEmptyLoadWarn('armed but empty — 0 active code_tool_hook activations loaded (RuleHost will not block or require approval)', 'If this is unexpected, run `pd runtime activation list --channel code_tool_hook` to inspect activations, or `pd runtime activation promote` to enable a live rule');
|
|
165
|
+
}
|
|
166
|
+
return { loaded, skipped };
|
|
144
167
|
}
|
|
145
168
|
catch (activationError) {
|
|
146
169
|
this.logger.warn?.(`[RuleHost] Failed to load code_tool_hook activations: ${String(activationError)}`);
|
|
147
|
-
return [];
|
|
170
|
+
return { loaded: [], skipped: [] };
|
|
148
171
|
}
|
|
149
172
|
}
|
|
173
|
+
/**
|
|
174
|
+
* R2-RH-002: Emit the "armed but empty" warn at most once per RuleHost
|
|
175
|
+
* instance. The warn is cached via `emptyLoadWarnEmitted` so repeated
|
|
176
|
+
* evaluations (which all hit the empty path) do not spam the log.
|
|
177
|
+
*
|
|
178
|
+
* This is an observability signal, NOT a degradation fallback — RuleHost
|
|
179
|
+
* correctly returns "no opinion" when there are no active rules. The warn
|
|
180
|
+
* makes the empty state visible so operators can distinguish "RuleHost is
|
|
181
|
+
* working but has no rules" from "RuleHost is broken" (rc-9-no-silent-fallback).
|
|
182
|
+
*/
|
|
183
|
+
_emitEmptyLoadWarn(reason, nextAction) {
|
|
184
|
+
if (this.emptyLoadWarnEmitted)
|
|
185
|
+
return;
|
|
186
|
+
this.emptyLoadWarnEmitted = true;
|
|
187
|
+
this.logger.warn?.(`[RuleHost] ${reason}. ` +
|
|
188
|
+
`nextAction=${nextAction}`);
|
|
189
|
+
}
|
|
150
190
|
/**
|
|
151
191
|
* Load active code implementations from the activations table (code_tool_hook channel).
|
|
152
192
|
*
|
|
@@ -169,7 +209,7 @@ export class RuleHost {
|
|
|
169
209
|
const db = sqliteConn.getDb();
|
|
170
210
|
const rows = db.prepare(`
|
|
171
211
|
SELECT a.activation_id, a.artifact_id, a.target_ref, a.action,
|
|
172
|
-
p.content_json, p.source_rule_id
|
|
212
|
+
p.content_json, p.source_rule_id, p.source_principle_id
|
|
173
213
|
FROM activations a
|
|
174
214
|
JOIN pi_artifacts p ON a.artifact_id = p.artifact_id
|
|
175
215
|
WHERE a.channel = 'code_tool_hook' AND a.deactivated_at IS NULL
|
|
@@ -177,7 +217,7 @@ export class RuleHost {
|
|
|
177
217
|
`).all();
|
|
178
218
|
if (!Array.isArray(rows)) {
|
|
179
219
|
this.logger.warn?.('[RuleHost] Activations table query returned non-array, skipping');
|
|
180
|
-
return [];
|
|
220
|
+
return { loaded: [], skipped: [] };
|
|
181
221
|
}
|
|
182
222
|
const fingerprintParts = [supportsContextV2 ? 'context-v2' : 'context-v1'];
|
|
183
223
|
for (const row of rows) {
|
|
@@ -185,12 +225,12 @@ export class RuleHost {
|
|
|
185
225
|
continue;
|
|
186
226
|
const record = row;
|
|
187
227
|
fingerprintParts.push([
|
|
188
|
-
record['activation_id'], record['artifact_id'], record['target_ref'], record['action'], record['content_json'], record['source_rule_id'],
|
|
228
|
+
record['activation_id'], record['artifact_id'], record['target_ref'], record['action'], record['content_json'], record['source_rule_id'], record['source_principle_id'],
|
|
189
229
|
].map((value) => typeof value === 'string' ? value : '').join('\u0001'));
|
|
190
230
|
}
|
|
191
231
|
const fingerprint = fingerprintParts.join('\u0002');
|
|
192
232
|
if (fingerprint === this.activationFingerprint) {
|
|
193
|
-
return [...this.cachedImplementations];
|
|
233
|
+
return { loaded: [...this.cachedImplementations], skipped: [...this.cachedSkipped] };
|
|
194
234
|
}
|
|
195
235
|
this.implementationSources.clear();
|
|
196
236
|
// PRI-436: Group active rows by target_ref to detect duplicates.
|
|
@@ -250,11 +290,18 @@ export class RuleHost {
|
|
|
250
290
|
}
|
|
251
291
|
}
|
|
252
292
|
const loaded = [];
|
|
293
|
+
const skipped = [];
|
|
253
294
|
for (const r of validRows) {
|
|
254
295
|
const activationId = typeof r['activation_id'] === 'string' ? r['activation_id'] : '';
|
|
255
296
|
const artifactId = typeof r['artifact_id'] === 'string' ? r['artifact_id'] : '';
|
|
256
297
|
const contentJson = typeof r['content_json'] === 'string' ? r['content_json'] : '';
|
|
257
298
|
const sourceRuleId = typeof r['source_rule_id'] === 'string' ? r['source_rule_id'] : null;
|
|
299
|
+
// R2-RH-004: Extract source_principle_id from pi_artifacts (DB lineage field).
|
|
300
|
+
// Previously this column was never SELECTed, so principleId was always
|
|
301
|
+
// derived from meta.ruleId (a rule ID, not a principle ID) — violating
|
|
302
|
+
// rc-6-lineage-consistency. Downstream gate.ts:135/164 recorded the
|
|
303
|
+
// wrong principleId in eventLog.recordRuleEnforced().
|
|
304
|
+
const sourcePrincipleId = typeof r['source_principle_id'] === 'string' ? r['source_principle_id'] : null;
|
|
258
305
|
const action = typeof r['action'] === 'string' ? r['action'] : '';
|
|
259
306
|
if (!activationId || !artifactId || !contentJson) {
|
|
260
307
|
this.logger.warn?.(`[RuleHost] Activation row missing required fields, skipping`);
|
|
@@ -266,51 +313,108 @@ export class RuleHost {
|
|
|
266
313
|
? 'live'
|
|
267
314
|
: null;
|
|
268
315
|
if (!activationMode) {
|
|
269
|
-
|
|
270
|
-
|
|
316
|
+
const reason = `unsupported action: ${action || '(missing)'}`;
|
|
317
|
+
const nextAction = 'Deactivate and recreate the activation through RuleHostWriter with action code_tool_hook_shadow_activate or code_tool_hook_live_activate';
|
|
318
|
+
this.logger.warn?.(`[RuleHost] Activation ${activationId}: ${reason}, skipping. nextAction=${nextAction}`);
|
|
319
|
+
const skipRecord = {
|
|
320
|
+
activationId,
|
|
321
|
+
ruleId: sourceRuleId ?? artifactId,
|
|
322
|
+
reason,
|
|
323
|
+
nextAction,
|
|
324
|
+
};
|
|
325
|
+
skipped.push(skipRecord);
|
|
326
|
+
this._recordSkipped(activationId, artifactId, sourceRuleId ?? artifactId, undefined, reason, nextAction);
|
|
271
327
|
continue;
|
|
272
328
|
}
|
|
273
329
|
if (activationMode === 'shadow') {
|
|
274
|
-
//
|
|
275
|
-
// NOT enter mergeDecisions (no block /
|
|
276
|
-
//
|
|
277
|
-
//
|
|
278
|
-
//
|
|
330
|
+
// PRI-489 (seed-MVP readiness): shadow activations are
|
|
331
|
+
// observation-only and do NOT enter mergeDecisions (no block /
|
|
332
|
+
// requireApproval). Owner approval creates a shadow activation
|
|
333
|
+
// first; the only shadow -> live transition is `pd activation
|
|
334
|
+
// promote --activation-id ... --confirm` (atomic action rewrite
|
|
335
|
+
// in SqliteActivationStateStore.promoteActivation). Surface a
|
|
279
336
|
// structured reason + nextAction so the degradation is observable
|
|
280
|
-
// (rc-9-no-silent-fallback), not silent. Fires once per
|
|
281
|
-
// change (cached), not per evaluation.
|
|
337
|
+
// (rc-9-no-silent-fallback), not silent. Fires once per
|
|
338
|
+
// fingerprint change (cached), not per evaluation.
|
|
282
339
|
this.logger.warn?.(`[RuleHost] Activation ${activationId}: loaded in shadow (observation-only) mode; ` +
|
|
283
340
|
'it will NOT block or require approval (shadowDecisions only). ' +
|
|
284
|
-
`nextAction=run \`pd
|
|
341
|
+
`nextAction=run \`pd activation promote --activation-id ${activationId} --confirm\` to enable live blocking, ` +
|
|
285
342
|
'or leave as-is for shadow observation.');
|
|
286
343
|
}
|
|
287
344
|
try {
|
|
288
345
|
const content = JSON.parse(contentJson);
|
|
289
346
|
if (!content || typeof content !== 'object' || Array.isArray(content)) {
|
|
290
|
-
|
|
347
|
+
const reason = 'content_json is not a valid object';
|
|
348
|
+
const nextAction = 'Regenerate the rule artifact with valid JSON content_json';
|
|
349
|
+
this.logger.warn?.(`[RuleHost] Activation ${activationId}: ${reason}, skipping. nextAction=${nextAction}`);
|
|
350
|
+
skipped.push({
|
|
351
|
+
activationId,
|
|
352
|
+
ruleId: sourceRuleId ?? artifactId,
|
|
353
|
+
mode: activationMode,
|
|
354
|
+
reason,
|
|
355
|
+
nextAction,
|
|
356
|
+
});
|
|
357
|
+
this._recordSkipped(activationId, artifactId, sourceRuleId ?? artifactId, activationMode, reason, nextAction);
|
|
291
358
|
continue;
|
|
292
359
|
}
|
|
293
360
|
const contentObj = content;
|
|
294
361
|
if (Object.hasOwn(contentObj, 'requiresContextVersion')) {
|
|
295
362
|
if (contentObj['requiresContextVersion'] !== 2) {
|
|
296
|
-
|
|
297
|
-
|
|
363
|
+
const reason = `unsupported context version: ${String(contentObj['requiresContextVersion'])}`;
|
|
364
|
+
const nextAction = 'Regenerate the rule artifact with requiresContextVersion: 2 or omit the field for v1';
|
|
365
|
+
this.logger.warn?.(`[RuleHost] Activation ${activationId}: ${reason}, skipping. nextAction=${nextAction}`);
|
|
366
|
+
skipped.push({
|
|
367
|
+
activationId,
|
|
368
|
+
ruleId: typeof contentObj['ruleId'] === 'string' ? contentObj['ruleId'] : (sourceRuleId ?? artifactId),
|
|
369
|
+
mode: activationMode,
|
|
370
|
+
reason,
|
|
371
|
+
nextAction,
|
|
372
|
+
});
|
|
373
|
+
this._recordSkipped(activationId, artifactId, typeof contentObj['ruleId'] === 'string' ? contentObj['ruleId'] : (sourceRuleId ?? artifactId), activationMode, reason, nextAction);
|
|
298
374
|
continue;
|
|
299
375
|
}
|
|
300
376
|
if (!supportsContextV2) {
|
|
301
|
-
|
|
302
|
-
|
|
377
|
+
const reason = 'suspended_by_flag: rulecode_context_v2 is disabled or unavailable';
|
|
378
|
+
const nextAction = 'Enable rulecode_context_v2 with valid config, or deactivate this activation';
|
|
379
|
+
this.logger.warn?.(`[RuleHost] Activation ${activationId}: ${reason}, skipping. nextAction=${nextAction}`);
|
|
380
|
+
skipped.push({
|
|
381
|
+
activationId,
|
|
382
|
+
ruleId: typeof contentObj['ruleId'] === 'string' ? contentObj['ruleId'] : (sourceRuleId ?? artifactId),
|
|
383
|
+
mode: activationMode,
|
|
384
|
+
reason,
|
|
385
|
+
nextAction,
|
|
386
|
+
});
|
|
387
|
+
this._recordSkipped(activationId, artifactId, typeof contentObj['ruleId'] === 'string' ? contentObj['ruleId'] : (sourceRuleId ?? artifactId), activationMode, reason, nextAction);
|
|
303
388
|
continue;
|
|
304
389
|
}
|
|
305
390
|
}
|
|
306
391
|
const implementationCode = contentObj['implementationCode'];
|
|
307
392
|
if (typeof implementationCode !== 'string' || implementationCode.length === 0) {
|
|
308
|
-
|
|
393
|
+
const reason = 'no implementationCode in artifact';
|
|
394
|
+
const nextAction = 'Regenerate the rule artifact with a non-empty implementationCode field';
|
|
395
|
+
this.logger.warn?.(`[RuleHost] Activation ${activationId}: ${reason}, skipping. nextAction=${nextAction}`);
|
|
396
|
+
skipped.push({
|
|
397
|
+
activationId,
|
|
398
|
+
ruleId: typeof contentObj['ruleId'] === 'string' ? contentObj['ruleId'] : (sourceRuleId ?? artifactId),
|
|
399
|
+
mode: activationMode,
|
|
400
|
+
reason,
|
|
401
|
+
nextAction,
|
|
402
|
+
});
|
|
403
|
+
this._recordSkipped(activationId, artifactId, typeof contentObj['ruleId'] === 'string' ? contentObj['ruleId'] : (sourceRuleId ?? artifactId), activationMode, reason, nextAction);
|
|
309
404
|
continue;
|
|
310
405
|
}
|
|
311
406
|
const ruleId = typeof contentObj['ruleId'] === 'string'
|
|
312
407
|
? contentObj['ruleId']
|
|
313
408
|
: (sourceRuleId ?? artifactId);
|
|
409
|
+
// R2-RH-004: Extract principleId from artifact content_json.
|
|
410
|
+
// Previously this field was never read, so result.principleId was
|
|
411
|
+
// always set to meta.ruleId (a rule ID) — violating
|
|
412
|
+
// rc-6-lineage-consistency. Precedence: contentJson.principleId
|
|
413
|
+
// (artifact payload) → pi_artifacts.source_principle_id (DB lineage)
|
|
414
|
+
// → meta.ruleId (rule ID fallback) → ruleId (last resort).
|
|
415
|
+
const contentPrincipleId = typeof contentObj['principleId'] === 'string'
|
|
416
|
+
? contentObj['principleId']
|
|
417
|
+
: null;
|
|
314
418
|
const implId = `act-impl-${activationId}`;
|
|
315
419
|
const moduleExports = loadRuleImplementationModule(implementationCode, implId);
|
|
316
420
|
if (!moduleExports || typeof moduleExports.callEvaluate !== 'function') {
|
|
@@ -350,7 +454,13 @@ export class RuleHost {
|
|
|
350
454
|
const result = rawResult;
|
|
351
455
|
if (result.matched && (result.decision === 'block' || result.decision === 'requireApproval')) {
|
|
352
456
|
result.ruleId = ruleId;
|
|
353
|
-
|
|
457
|
+
// R2-RH-004: principleId precedence — contentJson.principleId
|
|
458
|
+
// (artifact payload) → source_principle_id (DB lineage) →
|
|
459
|
+
// meta.ruleId (rule ID fallback) → ruleId (last resort).
|
|
460
|
+
// Previously this was `meta.ruleId ?? ruleId`, which always
|
|
461
|
+
// resolved to a rule ID (never a principle ID) because
|
|
462
|
+
// isRuleHostMeta guarantees meta.ruleId is a non-empty string.
|
|
463
|
+
result.principleId = contentPrincipleId ?? sourcePrincipleId ?? meta.ruleId ?? ruleId;
|
|
354
464
|
}
|
|
355
465
|
return result;
|
|
356
466
|
},
|
|
@@ -366,7 +476,8 @@ export class RuleHost {
|
|
|
366
476
|
}
|
|
367
477
|
this.activationFingerprint = fingerprint;
|
|
368
478
|
this.cachedImplementations = loaded;
|
|
369
|
-
|
|
479
|
+
this.cachedSkipped = skipped;
|
|
480
|
+
return { loaded, skipped };
|
|
370
481
|
}
|
|
371
482
|
}
|
|
372
483
|
/**
|
|
@@ -399,4 +510,32 @@ export class RuleHost {
|
|
|
399
510
|
this.logger.warn?.(`[RuleHost] Failed to record unhealthy event for activation ${activationId}: ${String(recordError)}`);
|
|
400
511
|
}
|
|
401
512
|
}
|
|
513
|
+
/**
|
|
514
|
+
* PRI-491: Record a skipped activation to EventLog.
|
|
515
|
+
*
|
|
516
|
+
* Unlike _recordUnhealthy (compile/load failures), skipped activations have
|
|
517
|
+
* a configuration/flag reason — the RuleCode itself may be valid, but the
|
|
518
|
+
* runtime chose not to execute it (flag-off v2, unsupported context version,
|
|
519
|
+
* unsupported action, content_json not object, no implementationCode).
|
|
520
|
+
*
|
|
521
|
+
* ERR-002: degradation includes a reason and nextAction (rc-9-no-silent-fallback).
|
|
522
|
+
* Failures in EventLog recording are caught and logged (never throw).
|
|
523
|
+
*/
|
|
524
|
+
_recordSkipped(activationId, artifactId, ruleId, mode, reason, nextAction) {
|
|
525
|
+
try {
|
|
526
|
+
const eventLog = EventLogService.get(this.stateDir);
|
|
527
|
+
eventLog.recordRuleHostSkipped({
|
|
528
|
+
activationId,
|
|
529
|
+
artifactId,
|
|
530
|
+
ruleId,
|
|
531
|
+
mode,
|
|
532
|
+
reason,
|
|
533
|
+
nextAction,
|
|
534
|
+
});
|
|
535
|
+
}
|
|
536
|
+
catch (recordError) {
|
|
537
|
+
// EventLog recording must never break RuleHost evaluation
|
|
538
|
+
this.logger.warn?.(`[RuleHost] Failed to record skipped event for activation ${activationId}: ${String(recordError)}`);
|
|
539
|
+
}
|
|
540
|
+
}
|
|
402
541
|
}
|
|
@@ -0,0 +1,105 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* SignalCollectorHost — plugin I/O 外壳 (design spec §4.2)
|
|
3
|
+
*
|
|
4
|
+
* 把 core 的纯逻辑 (collectSync / mapLlmResultToOutput) 接进 openclaw 运行时。
|
|
5
|
+
*
|
|
6
|
+
* 同步路径 (prompt.ts before_prompt_build 钩子调用,绝不阻塞):
|
|
7
|
+
* - trigger 门控 (仅 user)
|
|
8
|
+
* - Stage1 关键词快扫 (零成本)
|
|
9
|
+
* - 写 user_turns (复用 recordUserTurn)
|
|
10
|
+
* - 高精度短语命中 (high) → 直接走 STRONG 分流 (同步,纯内存)
|
|
11
|
+
* - 普通歧义词 / 未命中 → 入队异步 LLM 确认 (不阻塞)
|
|
12
|
+
*
|
|
13
|
+
* 异步路径 (fire-and-forget):
|
|
14
|
+
* - Stage2 LLM 确认 (后台,不阻塞 prompt hook)
|
|
15
|
+
* - LLM 不可用 → 降级:丢弃 ambiguous 候选 (不触发 STRONG,避免误判泛滥)
|
|
16
|
+
* - 按 strength 分流:STRONG → emitPainDetectedEvent (修断裂 ③);WEAK → trackFriction 累积 GFI
|
|
17
|
+
*
|
|
18
|
+
* 降级不静默 (rc-9):所有降级路径走 SystemLogger。
|
|
19
|
+
*/
|
|
20
|
+
import { type UnifiedKeywordStore, type SignalCollectorConfig } from '@principles/core/runtime-v2';
|
|
21
|
+
import type { PluginLogger } from '../openclaw-sdk.js';
|
|
22
|
+
import type { WorkspaceContext } from './workspace-context.js';
|
|
23
|
+
export declare const DEFAULT_SIGNAL_CONFIG: SignalCollectorConfig;
|
|
24
|
+
export declare function buildDefaultKeywordStore(): UnifiedKeywordStore;
|
|
25
|
+
/**
|
|
26
|
+
* adapter 抽象 (Stage2 LLM 调用)。plugin 层可注入真实 adapter (LMStudio);
|
|
27
|
+
* 为 null / 不可用时 host 走纯关键词降级。
|
|
28
|
+
*
|
|
29
|
+
* 本文件不依赖具体的 PDRuntimeAdapter 实现,只依赖一个最小的分类函数,
|
|
30
|
+
* 以保持 host 可单测 (测试可注入 mock classifier)。
|
|
31
|
+
*/
|
|
32
|
+
export type SignalLlmClassifier = (text: string, promptTemplate: string) => Promise<{
|
|
33
|
+
is_feedback: boolean;
|
|
34
|
+
type: 'correction' | 'empathy' | 'none';
|
|
35
|
+
confidence: number;
|
|
36
|
+
reason: string;
|
|
37
|
+
} | null>;
|
|
38
|
+
export interface SignalCollectorHostOptions {
|
|
39
|
+
keywordStore?: UnifiedKeywordStore;
|
|
40
|
+
config?: SignalCollectorConfig;
|
|
41
|
+
/** Stage2 LLM 分类器。null/undefined → 降级纯关键词。 */
|
|
42
|
+
llmClassifier?: SignalLlmClassifier | null;
|
|
43
|
+
}
|
|
44
|
+
export declare class SignalCollectorHost {
|
|
45
|
+
private readonly wctx;
|
|
46
|
+
private readonly store;
|
|
47
|
+
private readonly config;
|
|
48
|
+
private readonly llmClassifier;
|
|
49
|
+
/** rate limit 状态:sessionId → STRONG 计数桶 */
|
|
50
|
+
private readonly rateLimit;
|
|
51
|
+
constructor(wctx: WorkspaceContext, options?: SignalCollectorHostOptions);
|
|
52
|
+
/**
|
|
53
|
+
* ★ 同步路径 (prompt.ts before_prompt_build 钩子里调用,绝不能阻塞)。
|
|
54
|
+
*
|
|
55
|
+
* 只做:trigger 门控 + Stage1 关键词快扫 + 写 user_turns。
|
|
56
|
+
* 高精度短语命中 (high) → 直接走 STRONG 分流 (同步,纯内存)。
|
|
57
|
+
* 普通歧义词 / 未命中 → 入队异步 LLM 确认 (不阻塞)。
|
|
58
|
+
*/
|
|
59
|
+
/**
|
|
60
|
+
* 可选入参:lineage 字段(由调用方算好传入,host 不感知 trajectory 结构)。
|
|
61
|
+
* referencesAssistantTurnId 让诊断 evidence 能 JOIN 到前置 assistant turn。
|
|
62
|
+
*/
|
|
63
|
+
detectSync(userMessage: string, sessionId: string, trigger: string, options?: {
|
|
64
|
+
referencesAssistantTurnId?: number | null;
|
|
65
|
+
turnIndex?: number;
|
|
66
|
+
}): void;
|
|
67
|
+
/**
|
|
68
|
+
* ★ 异步路径 (fire-and-forget)。
|
|
69
|
+
*
|
|
70
|
+
* 1. Stage2 LLM 确认 (后台,不阻塞用户)
|
|
71
|
+
* 2. LLM 不可用 → 降级:empathy ambiguous 候选作为 WEAK 信号路由(保留旧版 GFI 累积);
|
|
72
|
+
* correction ambiguous / 未命中候选丢弃(不触发 STRONG,避免误判泛滥)
|
|
73
|
+
* 3. 按 strength 分流:STRONG → emitPainDetectedEvent;WEAK → trackFriction 累积 GFI;none → 仅记录
|
|
74
|
+
*/
|
|
75
|
+
private detectAsyncAndRoute;
|
|
76
|
+
/**
|
|
77
|
+
* STRONG 分流 → emitPainDetectedEvent (修断裂 ③)。
|
|
78
|
+
* 带 STRONG rate limit 门控 (spec §7.2):单 session 每小时上限 strongRateLimitPerHour。
|
|
79
|
+
*/
|
|
80
|
+
private routeStrong;
|
|
81
|
+
/**
|
|
82
|
+
* WEAK 分流 → trackFriction 累积 GFI + 写 evidence (维持现状,spec §3.2)。
|
|
83
|
+
*
|
|
84
|
+
* WEAK 是 Layer 3 弱信号,用较小的摩擦分(20)累积,过 highGfi 阈值(70)才触发诊断。
|
|
85
|
+
* 不用 strongPainScore(70),因为 WEAK 单条不该直接顶满 GFI。
|
|
86
|
+
*/
|
|
87
|
+
private routeWeak;
|
|
88
|
+
/**
|
|
89
|
+
* STRONG rate limit 门控:成功消耗一个名额返回 true;超限返回 false。
|
|
90
|
+
* 窗口满一小时自动重置。
|
|
91
|
+
*/
|
|
92
|
+
private tryConsumeRateLimit;
|
|
93
|
+
}
|
|
94
|
+
/**
|
|
95
|
+
* 从 .pd/config.yaml 的 signalCollector runtimeProfile 构造 SignalLlmClassifier。
|
|
96
|
+
* 完成配置单轨化(spec §3.3 决策3):统一走 .pd/config.yaml,移除 empathy 的 workflows.yaml 双轨。
|
|
97
|
+
*
|
|
98
|
+
* 返回 null 的情况(走纯关键词降级,rc-9 不静默):
|
|
99
|
+
* - feature flag signal_collector 关闭
|
|
100
|
+
* - runtimeProfile 未配置 / apiKeyEnv 缺失
|
|
101
|
+
* - profile 是 openclaw 类型(observer 不支持)
|
|
102
|
+
*
|
|
103
|
+
* 这是 Task 11 的最后一块:让本地 LLM(LMStudio)真正参与检测。
|
|
104
|
+
*/
|
|
105
|
+
export declare function createSignalLlmClassifierFromConfig(wctx: WorkspaceContext, logger?: Pick<PluginLogger, 'info' | 'warn' | 'error' | 'debug'>): SignalLlmClassifier | null;
|