principles-disciple 1.72.0 → 1.74.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/INSTALL.md +1 -3
- package/openclaw.plugin.json +10 -5
- package/package.json +17 -19
- package/scripts/acceptance-test.mjs +16 -73
- package/scripts/sync-plugin.mjs +382 -77
- package/src/commands/archive-impl.ts +2 -1
- package/src/commands/capabilities.ts +2 -2
- package/src/commands/context.ts +2 -2
- package/src/commands/disable-impl.ts +2 -1
- package/src/commands/evolution-status.ts +16 -16
- package/src/commands/export.ts +12 -67
- package/src/commands/pain.ts +91 -1
- package/src/commands/principle-rollback.ts +2 -1
- package/src/commands/promote-impl.ts +7 -43
- package/src/commands/rollback-impl.ts +2 -1
- package/src/commands/rollback.ts +2 -1
- package/src/commands/samples.ts +2 -1
- package/src/commands/thinking-os.ts +2 -1
- package/src/config/errors.ts +18 -2
- package/src/constants/diagnostician.ts +2 -2
- package/src/constants/tools.ts +2 -1
- package/src/core/__tests__/focus-history.test.ts +210 -0
- package/src/core/config.ts +1 -1
- package/src/core/correction-cue-learner.ts +2 -136
- package/src/core/correction-types.ts +16 -88
- package/src/core/dictionary.ts +19 -20
- package/src/core/empathy-keyword-matcher.ts +17 -289
- package/src/core/empathy-types.ts +18 -229
- package/src/core/event-log.ts +29 -132
- package/src/core/evolution-reducer.ts +21 -2
- package/src/core/evolution-types.ts +76 -464
- package/src/core/file-store.ts +80 -0
- package/src/core/focus-history.ts +228 -955
- package/src/core/local-worker-routing.ts +34 -314
- package/src/core/merge-gate-audit.ts +0 -195
- package/src/core/migration.ts +0 -1
- package/src/core/pain-diagnostic-gate.ts +154 -0
- package/src/core/pain-signal.ts +21 -138
- package/src/core/pain.ts +15 -88
- package/src/core/path-resolver.ts +0 -1
- package/src/core/paths.ts +0 -1
- package/src/core/pd-task-reconciler.ts +26 -115
- package/src/core/pd-task-service.ts +9 -9
- package/src/core/pd-task-types.ts +23 -127
- package/src/core/principle-compiler/__tests__/compiler-replay-gate.test.ts +174 -0
- package/src/core/principle-compiler/code-validator.ts +15 -42
- package/src/core/principle-compiler/compiler.ts +100 -15
- package/src/core/principle-compiler/index.ts +5 -2
- package/src/core/principle-compiler/template-generator.ts +4 -104
- package/src/core/principle-injection.ts +10 -202
- package/src/core/principle-internalization/filesystem-lifecycle-datasource.ts +42 -0
- package/src/core/principle-internalization/lifecycle-read-model.ts +39 -242
- package/src/core/principle-internalization/principle-lifecycle-service.ts +12 -10
- package/src/core/principle-tree-ledger-adapter.ts +145 -0
- package/src/core/principle-tree-ledger.ts +8 -6
- package/src/core/reflection/reflection-context.ts +14 -109
- package/src/core/replay-engine.ts +8 -500
- package/src/core/rule-host-helpers.ts +5 -35
- package/src/core/rule-host-types.ts +10 -82
- package/src/core/rule-host.ts +6 -63
- package/src/core/runtime-v2-prompt-activation-reader.ts +231 -0
- package/src/core/session-tracker.ts +87 -101
- package/src/core/shadow-observation-registry.ts +19 -48
- package/src/core/trajectory.ts +3 -1
- package/src/core/workflow-funnel-loader.ts +62 -68
- package/src/core/workspace-context.ts +46 -0
- package/src/core/workspace-dir-service.ts +1 -1
- package/src/core/workspace-dir-validation.ts +18 -9
- package/src/hooks/AGENTS.md +1 -1
- package/src/hooks/gate-block-helper.ts +71 -64
- package/src/hooks/gate.ts +183 -31
- package/src/hooks/lifecycle.ts +30 -32
- package/src/hooks/llm.ts +60 -32
- package/src/hooks/pain.ts +297 -103
- package/src/hooks/prompt.ts +400 -440
- package/src/hooks/subagent.ts +2 -29
- package/src/i18n/commands.ts +2 -10
- package/src/index.ts +95 -85
- package/src/openclaw-sdk.ts +311 -0
- package/src/service/central-database.ts +8 -4
- package/src/service/evolution-queue-migration.ts +2 -1
- package/src/service/evolution-worker.ts +163 -1786
- package/src/service/internalization-trigger-adapter.ts +302 -0
- package/src/service/keyword-optimization-service.ts +4 -4
- package/src/service/monitoring-query-service.ts +1 -215
- package/src/service/queue-io.ts +60 -331
- package/src/service/runtime-summary-service.ts +59 -16
- package/src/service/subagent-workflow/index.ts +0 -41
- package/src/service/subagent-workflow/types.ts +9 -120
- package/src/service/subagent-workflow/workflow-store.ts +2 -119
- package/src/service/workflow-watchdog.ts +0 -43
- package/src/types/event-payload.ts +16 -74
- package/src/types/event-types.ts +38 -547
- package/src/types/hygiene-types.ts +7 -30
- package/src/types/principle-tree-schema.ts +20 -222
- package/src/types/queue.ts +15 -70
- package/src/types/runtime-summary.ts +5 -49
- package/src/utils/io.ts +8 -20
- package/src/utils/retry.ts +1 -1
- package/src/utils/shadow-fingerprint.ts +2 -2
- package/src/utils/workspace-resolver.ts +50 -0
- package/templates/langs/en/core/AGENTS.md +7 -7
- package/templates/langs/en/core/BOOT.md +1 -1
- package/templates/langs/en/core/HEARTBEAT.md +2 -2
- package/templates/langs/en/principles/THINKING_OS.md +3 -2
- package/templates/langs/en/skills/ai-sprint-orchestration/references/agent-registry.json +1 -72
- package/templates/langs/en/skills/ai-sprint-orchestration/references/specs/bugfix-complex-template.json +6 -6
- package/templates/langs/en/skills/ai-sprint-orchestration/references/specs/feature-complex-template.json +6 -6
- package/templates/langs/en/skills/ai-sprint-orchestration/references/specs/workflow-validation-minimal-verify.json +2 -12
- package/templates/langs/en/skills/ai-sprint-orchestration/references/specs/workflow-validation-minimal.json +2 -12
- package/templates/langs/en/skills/ai-sprint-orchestration/scripts/run.mjs +51 -15
- package/templates/langs/en/skills/evolve-task/SKILL.md +3 -3
- package/templates/langs/en/skills/pd-cli-operator/SKILL.md +67 -0
- package/templates/langs/en/skills/pd-diagnostician/SKILL.md +1 -1
- package/templates/langs/en/skills/pd-mentor/SKILL.md +2 -3
- package/templates/langs/en/skills/pd-pain-signal/SKILL.md +17 -39
- package/templates/langs/en/skills/pd-runtime-v2/SKILL.md +61 -0
- package/templates/langs/zh/core/AGENTS.md +7 -7
- package/templates/langs/zh/core/BOOT.md +1 -1
- package/templates/langs/zh/core/HEARTBEAT.md +2 -2
- package/templates/langs/zh/principles/THINKING_OS.md +3 -2
- package/templates/langs/zh/skills/ai-sprint-orchestration/references/agent-registry.json +1 -72
- package/templates/langs/zh/skills/ai-sprint-orchestration/references/specs/bugfix-complex-template.json +6 -6
- package/templates/langs/zh/skills/ai-sprint-orchestration/references/specs/feature-complex-template.json +6 -6
- package/templates/langs/zh/skills/ai-sprint-orchestration/references/specs/nocturnal-trinity-quality-enhancement.json +8 -8
- package/templates/langs/zh/skills/ai-sprint-orchestration/references/specs/workflow-validation-minimal-verify.json +2 -12
- package/templates/langs/zh/skills/ai-sprint-orchestration/references/specs/workflow-validation-minimal.json +2 -12
- package/templates/langs/zh/skills/ai-sprint-orchestration/scripts/run.mjs +51 -15
- package/templates/langs/zh/skills/ai-sprint-orchestration/test/run.test.mjs +21 -5
- package/templates/langs/zh/skills/evolve-task/SKILL.md +4 -4
- package/templates/langs/zh/skills/pd-cli-operator/SKILL.md +67 -0
- package/templates/langs/zh/skills/pd-diagnostician/SKILL.md +1 -1
- package/templates/langs/zh/skills/pd-mentor/SKILL.md +2 -3
- package/templates/langs/zh/skills/pd-pain-signal/SKILL.md +17 -38
- package/templates/langs/zh/skills/pd-runtime-v2/SKILL.md +61 -0
- package/tests/build-artifacts.test.ts +1 -3
- package/tests/commands/evolution-status.test.ts +0 -118
- package/tests/core/bootstrap-rules.test.ts +1 -1
- package/tests/core/config.test.ts +1 -1
- package/tests/core/event-log.test.ts +35 -0
- package/tests/core/evolution-engine.test.ts +610 -0
- package/tests/core/file-store.test.ts +102 -0
- package/tests/core/focus-history.test.ts +203 -11
- package/tests/core/merge-gate-audit.test.ts +2 -169
- package/tests/core/migration.test.ts +7 -7
- package/tests/core/model-deployment-registry.test.ts +7 -1
- package/tests/core/model-training-registry.test.ts +19 -0
- package/tests/core/observability.test.ts +0 -1
- package/tests/core/pain-diagnostic-gate.test.ts +498 -0
- package/tests/core/pain.test.ts +0 -1
- package/tests/core/path-resolver.test.ts +1 -1
- package/tests/core/paths-refactor.test.ts +0 -22
- package/tests/core/principle-internalization/deprecated-readiness.test.ts +2 -2
- package/tests/core/principle-internalization/lifecycle-metrics.test.ts +2 -2
- package/tests/core/principle-internalization/{internalization-routing-policy.test.ts → lifecycle-routing-policy.test.ts} +6 -6
- package/tests/core/principle-internalization/lineage-source-retired.test.ts +56 -0
- package/tests/core/principle-internalization/principle-lifecycle-service.test.ts +1 -23
- package/tests/core/principle-tree-ledger-adapter.test.ts +253 -0
- package/tests/core/reflection-context.test.ts +0 -14
- package/tests/core/replay-engine.test.ts +127 -215
- package/tests/core/rule-host-helpers.test.ts +2 -2
- package/tests/core/rule-implementation-runtime.test.ts +0 -27
- package/tests/core/workflow-funnel-loader.test.ts +162 -0
- package/tests/core/workspace-context.test.ts +2 -2
- package/tests/core/workspace-dir-validation.test.ts +8 -1
- package/tests/core-anti-growth.test.ts +191 -0
- package/tests/hook-workspace-nextaction-contract.test.ts +42 -0
- package/tests/hooks/confirm-first-removal.test.ts +188 -0
- package/tests/hooks/gate-auto-correct-shadow.test.ts +310 -0
- package/tests/hooks/gate-auto-correct.test.ts +665 -0
- package/tests/hooks/gate-no-path-write-tool.test.ts +172 -0
- package/tests/hooks/gate-rule-host-pipeline.test.ts +2 -1
- package/tests/hooks/pain.test.ts +269 -12
- package/tests/hooks/prompt-characterization.test.ts +500 -0
- package/tests/hooks/prompt-size-guard.test.ts +32 -17
- package/tests/hooks/runtime-v2-prompt-activation.test.ts +869 -0
- package/tests/index.test.ts +94 -1
- package/tests/integration/auto-entry-gate.test.ts +248 -0
- package/tests/integration/internalization-trigger-guard.test.ts +69 -0
- package/tests/integration/m8-legacy-paths.test.ts +63 -0
- package/tests/integration/runtime-v2-pain-guard.test.ts +125 -0
- package/tests/plugin-config-resolution-cutover.test.ts +359 -0
- package/tests/runtime-v2-discovery-guard.test.ts +154 -0
- package/tests/service/central-database.test.ts +457 -0
- package/tests/service/evolution-worker.correction-observer.test.ts +173 -0
- package/tests/service/evolution-worker.timeout.test.ts +11 -129
- package/tests/service/internalization-trigger-adapter.test.ts +251 -0
- package/tests/service/monitoring-query-service.test.ts +1 -47
- package/tests/service/queue-io.test.ts +1 -62
- package/tests/service/runtime-summary-service.test.ts +3 -1
- package/tests/service/workflow-watchdog.test.ts +0 -91
- package/tests/utils/file-lock.test.ts +5 -3
- package/tests/utils/session-key.test.ts +52 -0
- package/tests/utils/subagent-probe.test.ts +48 -1
- package/vitest.config.ts +4 -11
- package/.planning/codebase/ARCHITECTURE.md +0 -157
- package/.planning/codebase/CONCERNS.md +0 -145
- package/.planning/codebase/CONVENTIONS.md +0 -148
- package/.planning/codebase/INTEGRATIONS.md +0 -81
- package/.planning/codebase/STACK.md +0 -87
- package/.planning/codebase/STRUCTURE.md +0 -193
- package/.planning/codebase/TESTING.md +0 -243
- package/.planning/phases/01-basic-visualization/01-GAP-CLOSURE-VERIFICATION.md +0 -113
- package/docs/COMMAND_REFERENCE.md +0 -76
- package/docs/COMMAND_REFERENCE_EN.md +0 -79
- package/scripts/build-web.mjs +0 -46
- package/scripts/diagnose-nocturnal.mjs +0 -537
- package/scripts/seed-nocturnal-scenarios.mjs +0 -384
- package/src/commands/nocturnal-review.ts +0 -322
- package/src/commands/nocturnal-rollout.ts +0 -790
- package/src/commands/nocturnal-train.ts +0 -986
- package/src/commands/pd-reflect.ts +0 -88
- package/src/core/adaptive-thresholds.ts +0 -478
- package/src/core/diagnostician-task-store.ts +0 -192
- package/src/core/nocturnal-arbiter.ts +0 -715
- package/src/core/nocturnal-artifact-lineage.ts +0 -116
- package/src/core/nocturnal-artificer.ts +0 -257
- package/src/core/nocturnal-candidate-scoring.ts +0 -530
- package/src/core/nocturnal-compliance.ts +0 -1146
- package/src/core/nocturnal-dataset.ts +0 -763
- package/src/core/nocturnal-executability.ts +0 -428
- package/src/core/nocturnal-export.ts +0 -499
- package/src/core/nocturnal-paths.ts +0 -240
- package/src/core/nocturnal-reasoning-deriver.ts +0 -343
- package/src/core/nocturnal-rule-implementation-validator.ts +0 -246
- package/src/core/nocturnal-snapshot-contract.ts +0 -99
- package/src/core/nocturnal-trajectory-extractor.ts +0 -512
- package/src/core/nocturnal-trinity-types.ts +0 -218
- package/src/core/nocturnal-trinity.ts +0 -2680
- package/src/core/principle-internalization/deprecated-readiness.ts +0 -93
- package/src/core/principle-internalization/internalization-routing-policy.ts +0 -208
- package/src/core/principle-internalization/lifecycle-metrics.ts +0 -152
- package/src/http/principles-console-route.ts +0 -709
- package/src/service/central-health-service.ts +0 -49
- package/src/service/central-overview-service.ts +0 -138
- package/src/service/control-ui-query-service.ts +0 -900
- package/src/service/cooldown-strategy.ts +0 -97
- package/src/service/evolution-pain-context.ts +0 -79
- package/src/service/evolution-query-service.ts +0 -407
- package/src/service/health-query-service.ts +0 -1038
- package/src/service/nocturnal-config.ts +0 -214
- package/src/service/nocturnal-runtime.ts +0 -734
- package/src/service/nocturnal-service.ts +0 -1605
- package/src/service/nocturnal-target-selector.ts +0 -545
- package/src/service/sleep-cycle.ts +0 -157
- package/src/service/startup-reconciler.ts +0 -112
- package/src/service/subagent-workflow/correction-observer-types.ts +0 -82
- package/src/service/subagent-workflow/correction-observer-workflow-manager.ts +0 -250
- package/src/service/subagent-workflow/deep-reflect-workflow-manager.ts +0 -1
- package/src/service/subagent-workflow/dynamic-timeout.ts +0 -30
- package/src/service/subagent-workflow/empathy-observer-workflow-manager.ts +0 -268
- package/src/service/subagent-workflow/nocturnal-workflow-manager.ts +0 -795
- package/src/service/subagent-workflow/runtime-direct-driver.ts +0 -268
- package/src/service/subagent-workflow/workflow-manager-base.ts +0 -580
- package/src/tools/write-pain-flag.ts +0 -215
- package/templates/langs/en/skills/plan-script/SKILL.md +0 -32
- package/templates/langs/zh/skills/plan-script/SKILL.md +0 -32
- package/tests/commands/nocturnal-review.test.ts +0 -448
- package/tests/commands/nocturnal-train.test.ts +0 -97
- package/tests/commands/pd-reflect.test.ts +0 -49
- package/tests/core/adaptive-thresholds.test.ts +0 -261
- package/tests/core/nocturnal-arbiter.test.ts +0 -559
- package/tests/core/nocturnal-artifact-lineage.test.ts +0 -53
- package/tests/core/nocturnal-artificer.test.ts +0 -241
- package/tests/core/nocturnal-candidate-scoring.test.ts +0 -532
- package/tests/core/nocturnal-compliance-p-principles.test.ts +0 -133
- package/tests/core/nocturnal-compliance.test.ts +0 -646
- package/tests/core/nocturnal-dataset.test.ts +0 -892
- package/tests/core/nocturnal-e2e.test.ts +0 -234
- package/tests/core/nocturnal-executability.test.ts +0 -357
- package/tests/core/nocturnal-export.test.ts +0 -517
- package/tests/core/nocturnal-reasoning-deriver.test.ts +0 -372
- package/tests/core/nocturnal-reviewed-subset-comparison.test.ts +0 -428
- package/tests/core/nocturnal-rule-implementation-validator.test.ts +0 -127
- package/tests/core/nocturnal-snapshot-contract.test.ts +0 -121
- package/tests/core/nocturnal-trajectory-extractor.test.ts +0 -634
- package/tests/core/nocturnal-trinity.test.ts +0 -2053
- package/tests/core/pain-auto-repair.test.ts +0 -96
- package/tests/core/pain-integration.test.ts +0 -510
- package/tests/fixtures/nocturnal-reviewed-subset.json +0 -183
- package/tests/http/principles-console-route.test.ts +0 -162
- package/tests/integration/chaos-resilience.test.ts +0 -348
- package/tests/integration/empathy-workflow-integration.test.ts +0 -626
- package/tests/integration/pain-diagnostician-loop.e2e.test.ts +0 -380
- package/tests/service/control-ui-query-service.test.ts +0 -121
- package/tests/service/cooldown-strategy.test.ts +0 -164
- package/tests/service/data-endpoints-regression.test.ts +0 -834
- package/tests/service/empathy-observer-workflow-manager.test.ts +0 -175
- package/tests/service/evolution-worker.nocturnal.test.ts +0 -601
- package/tests/service/nocturnal-runtime-hardening.test.ts +0 -118
- package/tests/service/nocturnal-runtime.test.ts +0 -473
- package/tests/service/nocturnal-service-code-candidate.test.ts +0 -330
- package/tests/service/nocturnal-target-selector.test.ts +0 -615
- package/tests/service/startup-reconciler.test.ts +0 -148
- package/tests/tools/write-pain-flag.test.ts +0 -358
- package/ui/src/App.tsx +0 -45
- package/ui/src/api.ts +0 -220
- package/ui/src/charts.tsx +0 -955
- package/ui/src/components/ErrorState.tsx +0 -6
- package/ui/src/components/Loading.tsx +0 -13
- package/ui/src/components/ProtectedRoute.tsx +0 -12
- package/ui/src/components/Shell.tsx +0 -91
- package/ui/src/components/WorkspaceConfig.tsx +0 -178
- package/ui/src/components/index.ts +0 -5
- package/ui/src/context/auth.tsx +0 -80
- package/ui/src/context/theme.tsx +0 -66
- package/ui/src/hooks/useAutoRefresh.ts +0 -39
- package/ui/src/i18n/ui.ts +0 -473
- package/ui/src/main.tsx +0 -16
- package/ui/src/pages/EvolutionPage.tsx +0 -333
- package/ui/src/pages/FeedbackPage.tsx +0 -138
- package/ui/src/pages/GateMonitorPage.tsx +0 -136
- package/ui/src/pages/LoginPage.tsx +0 -89
- package/ui/src/pages/OverviewPage.tsx +0 -599
- package/ui/src/pages/SamplesPage.tsx +0 -174
- package/ui/src/pages/ThinkingModelsPage.tsx +0 -702
- package/ui/src/styles.css +0 -2020
- package/ui/src/types.ts +0 -384
- package/ui/src/utils/format.ts +0 -15
|
@@ -254,74 +254,6 @@ describe('runWorkflowWatchdog', () => {
|
|
|
254
254
|
});
|
|
255
255
|
});
|
|
256
256
|
|
|
257
|
-
// ── BUG-03: Nocturnal snapshot validation ─────────────────────────────
|
|
258
|
-
|
|
259
|
-
describe('BUG-03: nocturnal snapshot validation', () => {
|
|
260
|
-
it('detects fallback_snapshot when nocturnal workflow uses pain_context_fallback', async () => {
|
|
261
|
-
const now = Date.now();
|
|
262
|
-
|
|
263
|
-
mockListWorkflows.mockReturnValue([
|
|
264
|
-
createWorkflow({
|
|
265
|
-
workflow_id: 'wf-nocturnal-001',
|
|
266
|
-
workflow_type: 'nocturnal',
|
|
267
|
-
state: 'completed',
|
|
268
|
-
created_at: now - (60 * 60 * 1000),
|
|
269
|
-
metadata_json: JSON.stringify({
|
|
270
|
-
snapshot: {
|
|
271
|
-
_dataSource: 'pain_context_fallback',
|
|
272
|
-
stats: { totalToolCalls: 0, totalGateBlocks: 0, failureCount: 0 },
|
|
273
|
-
},
|
|
274
|
-
}),
|
|
275
|
-
}),
|
|
276
|
-
]);
|
|
277
|
-
|
|
278
|
-
const result = await runWorkflowWatchdog(
|
|
279
|
-
{ workspaceDir: '/tmp', stateDir: '/tmp/.state' } as any,
|
|
280
|
-
mockApi,
|
|
281
|
-
mockLogger,
|
|
282
|
-
);
|
|
283
|
-
|
|
284
|
-
expect(result.details).toContainEqual(
|
|
285
|
-
expect.stringContaining('fallback_snapshot: nocturnal workflow wf-nocturnal-001 uses pain-context fallback'),
|
|
286
|
-
);
|
|
287
|
-
expect(result.details).toContainEqual(
|
|
288
|
-
expect.stringContaining('fallback_snapshot_stats: nocturnal workflow wf-nocturnal-001 has empty fallback stats'),
|
|
289
|
-
);
|
|
290
|
-
});
|
|
291
|
-
|
|
292
|
-
it('does not flag fallback_snapshot_stats when nocturnal workflow has real stats', async () => {
|
|
293
|
-
const now = Date.now();
|
|
294
|
-
|
|
295
|
-
mockListWorkflows.mockReturnValue([
|
|
296
|
-
createWorkflow({
|
|
297
|
-
workflow_id: 'wf-nocturnal-002',
|
|
298
|
-
workflow_type: 'nocturnal',
|
|
299
|
-
state: 'completed',
|
|
300
|
-
created_at: now - (60 * 60 * 1000),
|
|
301
|
-
metadata_json: JSON.stringify({
|
|
302
|
-
snapshot: {
|
|
303
|
-
_dataSource: 'pain_context_fallback',
|
|
304
|
-
stats: { totalToolCalls: 5, totalGateBlocks: 2, failureCount: 1 },
|
|
305
|
-
},
|
|
306
|
-
}),
|
|
307
|
-
}),
|
|
308
|
-
]);
|
|
309
|
-
|
|
310
|
-
const result = await runWorkflowWatchdog(
|
|
311
|
-
{ workspaceDir: '/tmp', stateDir: '/tmp/.state' } as any,
|
|
312
|
-
mockApi,
|
|
313
|
-
mockLogger,
|
|
314
|
-
);
|
|
315
|
-
|
|
316
|
-
expect(result.details).toContainEqual(
|
|
317
|
-
expect.stringContaining('fallback_snapshot: nocturnal workflow wf-nocturnal-002 uses pain-context fallback'),
|
|
318
|
-
);
|
|
319
|
-
expect(result.details).not.toContainEqual(
|
|
320
|
-
expect.stringContaining('fallback_snapshot_stats'),
|
|
321
|
-
);
|
|
322
|
-
});
|
|
323
|
-
});
|
|
324
|
-
|
|
325
257
|
// ── General behavior ───────────────────────────────────────────────────
|
|
326
258
|
|
|
327
259
|
describe('general behavior', () => {
|
|
@@ -345,28 +277,5 @@ describe('runWorkflowWatchdog', () => {
|
|
|
345
277
|
expect(result.anomalies).toBe(0);
|
|
346
278
|
expect(result.details).toHaveLength(0);
|
|
347
279
|
});
|
|
348
|
-
|
|
349
|
-
it('handles malformed metadata_json gracefully', async () => {
|
|
350
|
-
const now = Date.now();
|
|
351
|
-
|
|
352
|
-
mockListWorkflows.mockReturnValue([
|
|
353
|
-
createWorkflow({
|
|
354
|
-
workflow_id: 'wf-malformed-001',
|
|
355
|
-
workflow_type: 'nocturnal',
|
|
356
|
-
state: 'completed',
|
|
357
|
-
created_at: now - (60 * 60 * 1000),
|
|
358
|
-
metadata_json: 'not valid json {{{',
|
|
359
|
-
}),
|
|
360
|
-
]);
|
|
361
|
-
|
|
362
|
-
const result = await runWorkflowWatchdog(
|
|
363
|
-
{ workspaceDir: '/tmp', stateDir: '/tmp/.state' } as any,
|
|
364
|
-
mockApi,
|
|
365
|
-
mockLogger,
|
|
366
|
-
);
|
|
367
|
-
|
|
368
|
-
expect(result.anomalies).toBe(1);
|
|
369
|
-
expect(result.details.some((d: string) => d.includes('malformed_metadata'))).toBe(true);
|
|
370
|
-
});
|
|
371
280
|
});
|
|
372
281
|
});
|
|
@@ -36,7 +36,9 @@ function cleanup(filePath: string): void {
|
|
|
36
36
|
try {
|
|
37
37
|
const dir = path.dirname(filePath);
|
|
38
38
|
fs.rmSync(dir, { recursive: true, force: true });
|
|
39
|
-
} catch {
|
|
39
|
+
} catch {
|
|
40
|
+
// expected on some platforms — cleanup is best-effort
|
|
41
|
+
}
|
|
40
42
|
}
|
|
41
43
|
|
|
42
44
|
function getLockPath(filePath: string): string {
|
|
@@ -357,8 +359,8 @@ describe('File Lock', () => {
|
|
|
357
359
|
const elapsed = Date.now() - start;
|
|
358
360
|
const avgMs = elapsed / iterations;
|
|
359
361
|
|
|
360
|
-
// 平均每次锁操作应该 <
|
|
361
|
-
expect(avgMs).toBeLessThan(
|
|
362
|
+
// 平均每次锁操作应该 < 50ms (宽松阈值避免 CI/满负载 flaky)
|
|
363
|
+
expect(avgMs).toBeLessThan(50);
|
|
362
364
|
});
|
|
363
365
|
});
|
|
364
366
|
});
|
|
@@ -0,0 +1,52 @@
|
|
|
1
|
+
import { describe, test, expect } from 'vitest';
|
|
2
|
+
import { extractAgentIdFromSessionKey } from '../../src/utils/session-key';
|
|
3
|
+
|
|
4
|
+
describe('extractAgentIdFromSessionKey', () => {
|
|
5
|
+
test('returns undefined for undefined input', () => {
|
|
6
|
+
expect(extractAgentIdFromSessionKey(undefined)).toBeUndefined();
|
|
7
|
+
});
|
|
8
|
+
|
|
9
|
+
test('returns undefined for empty string', () => {
|
|
10
|
+
expect(extractAgentIdFromSessionKey('')).toBeUndefined();
|
|
11
|
+
});
|
|
12
|
+
|
|
13
|
+
test('returns agentId from 3-part key (agent:{id}:{type}:{uuid})', () => {
|
|
14
|
+
expect(extractAgentIdFromSessionKey('agent:main:session:abc-123')).toBe('main');
|
|
15
|
+
});
|
|
16
|
+
|
|
17
|
+
test('returns agentId from 2-part key (agent:{id}:{uuid})', () => {
|
|
18
|
+
expect(extractAgentIdFromSessionKey('agent:worker-1:def-456')).toBe('worker-1');
|
|
19
|
+
});
|
|
20
|
+
|
|
21
|
+
test('returns undefined for non-matching format', () => {
|
|
22
|
+
expect(extractAgentIdFromSessionKey('user:main:session:abc')).toBeUndefined();
|
|
23
|
+
expect(extractAgentIdFromSessionKey('session:abc-123')).toBeUndefined();
|
|
24
|
+
expect(extractAgentIdFromSessionKey('random-string')).toBeUndefined();
|
|
25
|
+
});
|
|
26
|
+
|
|
27
|
+
test('trims whitespace from agentId', () => {
|
|
28
|
+
expect(extractAgentIdFromSessionKey('agent: main :session:abc')).toBe('main');
|
|
29
|
+
});
|
|
30
|
+
|
|
31
|
+
test('returns undefined when agentId is whitespace-only', () => {
|
|
32
|
+
expect(extractAgentIdFromSessionKey('agent: :session:abc')).toBeUndefined();
|
|
33
|
+
});
|
|
34
|
+
|
|
35
|
+
test('handles agentId with special characters', () => {
|
|
36
|
+
expect(extractAgentIdFromSessionKey('agent:my-agent_v2:session:abc')).toBe('my-agent_v2');
|
|
37
|
+
});
|
|
38
|
+
|
|
39
|
+
test('returns undefined for whitespace-only agentId', () => {
|
|
40
|
+
// String.trim() removes ASCII whitespace (\\t, \\n, \\r, space) AND fullwidth space \\u3000 from edges
|
|
41
|
+
expect(extractAgentIdFromSessionKey('agent:\t:session:abc')).toBeUndefined(); // tab → empty after trim
|
|
42
|
+
expect(extractAgentIdFromSessionKey('agent:\r:session:abc')).toBeUndefined(); // CR → empty after trim
|
|
43
|
+
expect(extractAgentIdFromSessionKey('agent:\u3000:session:abc')).toBeUndefined(); // fullwidth space trimmed → empty
|
|
44
|
+
});
|
|
45
|
+
|
|
46
|
+
test('handles mixed whitespace within agentId parts', () => {
|
|
47
|
+
// Tab is internal (not at trim edge), so 'a\tb'.trim() → 'a\tb' (tab preserved in middle)
|
|
48
|
+
expect(extractAgentIdFromSessionKey('agent:a\tb:session:abc')).toBe('a\tb');
|
|
49
|
+
// CR\\n is internal, not at edge, so 'a\r\nb'.trim() → 'a\r\nb'
|
|
50
|
+
expect(extractAgentIdFromSessionKey('agent:a\r\nb:session:abc')).toBe('a\r\nb');
|
|
51
|
+
});
|
|
52
|
+
});
|
|
@@ -1,7 +1,8 @@
|
|
|
1
|
-
import { describe, expect, it } from 'vitest';
|
|
1
|
+
import { describe, expect, it, vi, beforeEach, afterEach, afterAll } from 'vitest';
|
|
2
2
|
import {
|
|
3
3
|
getSubagentRuntimeAvailability,
|
|
4
4
|
isSubagentRuntimeAvailable,
|
|
5
|
+
getAvailableSubagentRuntime,
|
|
5
6
|
} from '../../src/utils/subagent-probe.js';
|
|
6
7
|
|
|
7
8
|
describe('subagent-probe', () => {
|
|
@@ -30,3 +31,49 @@ describe('subagent-probe', () => {
|
|
|
30
31
|
});
|
|
31
32
|
});
|
|
32
33
|
});
|
|
34
|
+
|
|
35
|
+
describe('getAvailableSubagentRuntime', () => {
|
|
36
|
+
const validRuntime = { run: () => Promise.resolve({ runId: 'run-1' }) };
|
|
37
|
+
|
|
38
|
+
it('returns the passed subagent when it is available', () => {
|
|
39
|
+
expect(getAvailableSubagentRuntime(validRuntime)).toBe(validRuntime);
|
|
40
|
+
});
|
|
41
|
+
|
|
42
|
+
it('returns undefined when passed undefined and no global gateway exists', () => {
|
|
43
|
+
expect(getAvailableSubagentRuntime(undefined)).toBeUndefined();
|
|
44
|
+
});
|
|
45
|
+
|
|
46
|
+
it('returns undefined when passed unavailable subagent and no global gateway', () => {
|
|
47
|
+
expect(getAvailableSubagentRuntime({} as any)).toBeUndefined();
|
|
48
|
+
});
|
|
49
|
+
|
|
50
|
+
describe('with global gateway fallback', () => {
|
|
51
|
+
const symbol = Symbol.for('openclaw.plugin.gatewaySubagentRuntime');
|
|
52
|
+
|
|
53
|
+
beforeEach(() => {
|
|
54
|
+
(globalThis as any)[symbol] = { subagent: validRuntime };
|
|
55
|
+
});
|
|
56
|
+
|
|
57
|
+
afterEach(() => {
|
|
58
|
+
delete (globalThis as any)[symbol];
|
|
59
|
+
});
|
|
60
|
+
|
|
61
|
+
afterAll(() => {
|
|
62
|
+
// Safety net: ensure cleanup even if a test crashes before afterEach
|
|
63
|
+
delete (globalThis as any)[symbol];
|
|
64
|
+
});
|
|
65
|
+
|
|
66
|
+
it('falls back to global gateway when passed subagent is unavailable', () => {
|
|
67
|
+
expect(getAvailableSubagentRuntime(undefined)).toBe(validRuntime);
|
|
68
|
+
});
|
|
69
|
+
|
|
70
|
+
it('falls back to global gateway when passed subagent has no run', () => {
|
|
71
|
+
expect(getAvailableSubagentRuntime({} as any)).toBe(validRuntime);
|
|
72
|
+
});
|
|
73
|
+
|
|
74
|
+
it('prefers passed subagent over global gateway when both available', () => {
|
|
75
|
+
const localRuntime = { run: () => Promise.resolve({ runId: 'local' }) };
|
|
76
|
+
expect(getAvailableSubagentRuntime(localRuntime)).toBe(localRuntime);
|
|
77
|
+
});
|
|
78
|
+
});
|
|
79
|
+
});
|
package/vitest.config.ts
CHANGED
|
@@ -23,18 +23,11 @@ const integrationTests = [
|
|
|
23
23
|
// Core DB tests
|
|
24
24
|
'tests/core/control-ui-db.test.ts',
|
|
25
25
|
'tests/core/evolution-logger.test.ts',
|
|
26
|
-
'tests/core/nocturnal-e2e.test.ts',
|
|
27
|
-
'tests/core/nocturnal-trajectory-extractor.test.ts',
|
|
28
26
|
'tests/core/replay-engine.test.ts',
|
|
29
27
|
'tests/core/trajectory.test.ts',
|
|
30
28
|
'tests/core/workspace-context.test.ts',
|
|
31
29
|
// Service tests with DB dependencies
|
|
32
|
-
'tests/service/nocturnal-service-code-candidate.test.ts',
|
|
33
|
-
'tests/service/nocturnal-target-selector.test.ts',
|
|
34
|
-
'tests/service/evolution-worker.nocturnal.test.ts',
|
|
35
30
|
'tests/service/evolution-worker.timeout.test.ts',
|
|
36
|
-
'tests/service/data-endpoints-regression.test.ts',
|
|
37
|
-
'tests/service/control-ui-query-service.test.ts',
|
|
38
31
|
'tests/service/keyword-optimization-service.test.ts',
|
|
39
32
|
// Hook tests with DB dependencies
|
|
40
33
|
'tests/hooks/subagent.test.ts',
|
|
@@ -59,10 +52,10 @@ export default defineConfig({
|
|
|
59
52
|
reporter: ['text', 'html'],
|
|
60
53
|
exclude: ['tests/**'],
|
|
61
54
|
thresholds: {
|
|
62
|
-
lines:
|
|
63
|
-
functions:
|
|
64
|
-
branches:
|
|
65
|
-
statements:
|
|
55
|
+
lines: 58,
|
|
56
|
+
functions: 65,
|
|
57
|
+
branches: 45,
|
|
58
|
+
statements: 57,
|
|
66
59
|
},
|
|
67
60
|
},
|
|
68
61
|
},
|
|
@@ -1,157 +0,0 @@
|
|
|
1
|
-
# Architecture
|
|
2
|
-
|
|
3
|
-
**Analysis Date:** 2026-04-15
|
|
4
|
-
|
|
5
|
-
## Pattern Overview
|
|
6
|
-
|
|
7
|
-
**Overall:** Event-driven plugin architecture with hook-based interception
|
|
8
|
-
|
|
9
|
-
**Key Characteristics:**
|
|
10
|
-
- OpenClaw plugin framework with hook-based integration
|
|
11
|
-
- Background worker services for async evolution processing
|
|
12
|
-
- SQLite-based trajectory and state persistence
|
|
13
|
-
- Multi-layer security gates (GFI gate, empathy engine, pain tracking)
|
|
14
|
-
- Workflow managers for complex subagent orchestration
|
|
15
|
-
|
|
16
|
-
## Layers
|
|
17
|
-
|
|
18
|
-
**Plugin Entry Point:**
|
|
19
|
-
- Purpose: Initialize plugin, register hooks, commands, tools, and services
|
|
20
|
-
- Location: `src/index.ts`
|
|
21
|
-
- Contains: Plugin registration, hook handlers, command registration
|
|
22
|
-
- Depends on: OpenClaw SDK, all core modules
|
|
23
|
-
|
|
24
|
-
**Hooks Layer:**
|
|
25
|
-
- Purpose: Intercept and modify OpenClaw agent behavior
|
|
26
|
-
- Location: `src/hooks/`
|
|
27
|
-
- Contains: `prompt.ts` (before_prompt_build), `gate.ts` (before_tool_call), `pain.ts` (after_tool_call), `llm.ts` (llm_output), `lifecycle.ts` (before_reset, compaction), `subagent.ts` (subagent lifecycle)
|
|
28
|
-
- Depends on: Core services, workspace context
|
|
29
|
-
- Used by: OpenClaw event system
|
|
30
|
-
|
|
31
|
-
**Core Services:**
|
|
32
|
-
- Purpose: Business logic for evolution, pain tracking, trajectory, nocturnal training
|
|
33
|
-
- Location: `src/core/` and `src/service/`
|
|
34
|
-
- Contains: `evolution-engine.ts`, `trajectory.ts`, `nocturnal-trinity.ts`, `pain.ts`, `training-program.ts`, `pd-task-service.ts`
|
|
35
|
-
- Depends on: Database, workspace context, config
|
|
36
|
-
|
|
37
|
-
**Command Handlers:**
|
|
38
|
-
- Purpose: Implement slash commands (e.g., `/pd-init`, `/pd-status`, `/pd-nocturnal-review`)
|
|
39
|
-
- Location: `src/commands/`
|
|
40
|
-
- Contains: 20+ command implementations
|
|
41
|
-
- Depends on: Core services, workspace context
|
|
42
|
-
|
|
43
|
-
**Workflow Managers (Subagent Workflow):**
|
|
44
|
-
- Purpose: Orchestrate complex subagent workflows
|
|
45
|
-
- Location: `src/service/subagent-workflow/`
|
|
46
|
-
- Contains: `nocturnal-workflow-manager.ts`, `deep-reflect-workflow-manager.ts`, `empathy-observer-workflow-manager.ts`, `correction-observer-workflow-manager.ts`
|
|
47
|
-
- Depends on: Evolution worker, core services
|
|
48
|
-
|
|
49
|
-
**Database Layer:**
|
|
50
|
-
- Purpose: Persist trajectory data, evolution state, workflow state
|
|
51
|
-
- Location: `src/core/schema/` (migrations), `src/service/central-database.ts`
|
|
52
|
-
- Contains: SQLite schema, migration runner, query services
|
|
53
|
-
- Depends on: better-sqlite3
|
|
54
|
-
|
|
55
|
-
**UI Layer:**
|
|
56
|
-
- Purpose: React-based plugin UI for monitoring and control
|
|
57
|
-
- Location: `ui/src/`
|
|
58
|
-
- Contains: Pages (Overview, Evolution, Feedback, GateMonitor, Samples, ThinkingModels), components (Shell, ProtectedRoute), context (auth, theme)
|
|
59
|
-
- Depends on: React, React Router, lucide-react
|
|
60
|
-
|
|
61
|
-
**Utils:**
|
|
62
|
-
- Purpose: Shared utilities (I/O, logging, retry, hashing, file locking)
|
|
63
|
-
- Location: `src/utils/`
|
|
64
|
-
- Contains: `io.ts` (atomic writes), `plugin-logger.ts`, `retry.ts`, `hashing.ts`, `file-lock.ts`
|
|
65
|
-
|
|
66
|
-
## Data Flow
|
|
67
|
-
|
|
68
|
-
**Agent Execution Flow:**
|
|
69
|
-
1. OpenClaw fires `before_prompt_build` hook
|
|
70
|
-
2. `hooks/prompt.ts` builds context injection (principles, thinking OS, focus, reflection log)
|
|
71
|
-
3. OpenClaw generates response
|
|
72
|
-
4. `hooks/llm.ts` analyzes LLM output for signals
|
|
73
|
-
5. User triggers tool call
|
|
74
|
-
6. `hooks/gate.ts` intercepts `before_tool_call` - evaluates risk, may block
|
|
75
|
-
7. Tool executes
|
|
76
|
-
8. `hooks/pain.ts` intercepts `after_tool_call` - tracks pain signals, empathy penalties
|
|
77
|
-
|
|
78
|
-
**Evolution Flow:**
|
|
79
|
-
1. `EvolutionWorkerService` polls `pain_candidates.json` periodically
|
|
80
|
-
2. For each candidate, `evolution-engine.ts` evaluates and derives improvements
|
|
81
|
-
3. `trajectory.ts` records behavior patterns
|
|
82
|
-
4. Nocturnal training (`nocturnal-trinity.ts`) synthesizes improvements into rule updates
|
|
83
|
-
5. `principle-tree-ledger.ts` manages principle lifecycle
|
|
84
|
-
|
|
85
|
-
**Nocturnal Training Flow:**
|
|
86
|
-
1. Candidate scoring via `nocturnal-candidate-scoring.ts`
|
|
87
|
-
2. Target selection via `nocturnal-target-selector.ts`
|
|
88
|
-
3. Rule implementation validation via `nocturnal-rule-implementation-validator.ts`
|
|
89
|
-
4. Promotion via `promotion-gate.ts`
|
|
90
|
-
|
|
91
|
-
## Key Abstractions
|
|
92
|
-
|
|
93
|
-
**WorkspaceContext:**
|
|
94
|
-
- Purpose: Encapsulates all state and services for a single workspace
|
|
95
|
-
- Examples: `src/core/workspace-context.ts`
|
|
96
|
-
- Pattern: Factory method `WorkspaceContext.fromHookContext()`
|
|
97
|
-
|
|
98
|
-
**EvolutionEngine:**
|
|
99
|
-
- Purpose: Core evolution processing logic
|
|
100
|
-
- Examples: `src/core/evolution-engine.ts`
|
|
101
|
-
- Pattern: Reducer pattern with typed actions
|
|
102
|
-
|
|
103
|
-
**NocturnalTrinity:**
|
|
104
|
-
- Purpose: Three-phase nocturnal training (dataset, training, evaluation)
|
|
105
|
-
- Examples: `src/core/nocturnal-trinity.ts`
|
|
106
|
-
- Pattern: Phase orchestration with contract validation
|
|
107
|
-
|
|
108
|
-
**PainConfig:**
|
|
109
|
-
- Purpose: Plugin configuration management
|
|
110
|
-
- Examples: `src/core/config.ts`
|
|
111
|
-
- Pattern: Singleton per workspace with file persistence
|
|
112
|
-
|
|
113
|
-
**RuleHost:**
|
|
114
|
-
- Purpose: Secure rule execution environment
|
|
115
|
-
- Examples: `src/core/rule-host.ts`
|
|
116
|
-
- Pattern: Sandboxed evaluation with permission checks
|
|
117
|
-
|
|
118
|
-
## Entry Points
|
|
119
|
-
|
|
120
|
-
**Plugin Entry:**
|
|
121
|
-
- Location: `src/index.ts`
|
|
122
|
-
- Triggers: OpenClaw loads plugin
|
|
123
|
-
- Responsibilities: Register all hooks, commands, tools, services; initialize workspace
|
|
124
|
-
|
|
125
|
-
**Command Entry:**
|
|
126
|
-
- Location: `src/commands/*.ts`
|
|
127
|
-
- Triggers: User invokes slash command (e.g., `/pd-init`)
|
|
128
|
-
- Responsibilities: Validate input, delegate to core services, return formatted result
|
|
129
|
-
|
|
130
|
-
**Service Entry:**
|
|
131
|
-
- Location: `src/service/evolution-worker.ts`
|
|
132
|
-
- Triggers: `before_prompt_build` fires (starts background worker)
|
|
133
|
-
- Responsibilities: Process evolution queue, track pain signals, trigger training
|
|
134
|
-
|
|
135
|
-
## Error Handling
|
|
136
|
-
|
|
137
|
-
**Strategy:** Graceful degradation with logging
|
|
138
|
-
|
|
139
|
-
**Patterns:**
|
|
140
|
-
- Try-catch blocks in all hook handlers with error logging
|
|
141
|
-
- `SystemLogger.log()` for critical errors
|
|
142
|
-
- Workspace context error recording via `eventLog.recordHookExecution()`
|
|
143
|
-
- Non-critical errors caught silently (trajectory collection)
|
|
144
|
-
|
|
145
|
-
## Cross-Cutting Concerns
|
|
146
|
-
|
|
147
|
-
**Logging:** `src/utils/plugin-logger.ts` - OpenClaw logger abstraction
|
|
148
|
-
|
|
149
|
-
**Validation:** Schema validation via `@sinclair/typebox` for config and event types
|
|
150
|
-
|
|
151
|
-
**Authentication:** OpenClaw session-based, agent ID extracted from session key
|
|
152
|
-
|
|
153
|
-
**I/O Safety:** Atomic file writes via `atomicWriteFileSync()` in `src/utils/io.ts`
|
|
154
|
-
|
|
155
|
-
---
|
|
156
|
-
|
|
157
|
-
*Architecture analysis: 2026-04-15*
|
|
@@ -1,145 +0,0 @@
|
|
|
1
|
-
# Codebase Concerns
|
|
2
|
-
|
|
3
|
-
**Analysis Date:** 2026-04-15
|
|
4
|
-
|
|
5
|
-
## Tech Debt
|
|
6
|
-
|
|
7
|
-
**Large Monolithic Files:**
|
|
8
|
-
- Issue: `evolution-worker.ts` is 2689 lines, `nocturnal-trinity.ts` is 2429 lines. These exceed reasonable single-file thresholds and make debugging/profiling difficult.
|
|
9
|
-
- Files: `src/service/evolution-worker.ts`, `src/core/nocturnal-trinity.ts`
|
|
10
|
-
- Impact: Hard to trace bugs, no granular profiling, high risk of regression on modification
|
|
11
|
-
- Fix approach: Break into smaller focused modules (e.g., queue-processor.ts, workflow-watchdog.ts, sleep-cycle.ts)
|
|
12
|
-
|
|
13
|
-
**Type Safety Workarounds:**
|
|
14
|
-
- Issue: Extensive use of `as any`, `as unknown`, and double casts (`as unknown as`) throughout the codebase
|
|
15
|
-
- Files: `src/hooks/prompt.ts`, `src/hooks/subagent.ts`, `src/service/evolution-worker.ts`, `src/commands/promote-impl.ts`, `src/commands/rollback.ts`, `src/commands/pain.ts`
|
|
16
|
-
- Impact: Type errors are silenced rather than fixed, runtime type mismatches can go undetected
|
|
17
|
-
- Fix approach: Define proper shared type interfaces, use discriminated unions
|
|
18
|
-
|
|
19
|
-
**Busy-Wait Retry Loops:**
|
|
20
|
-
- Issue: `src/utils/io.ts` uses busy-wait spin loops (`while (Date.now() < end)`) for Windows file lock retries
|
|
21
|
-
- Files: `src/utils/io.ts` (lines 32-33)
|
|
22
|
-
- Impact: Consumes CPU while waiting; fails to yield to event loop
|
|
23
|
-
- Fix approach: Use `setTimeout` delay or `fs.promises` with proper async retry
|
|
24
|
-
|
|
25
|
-
**Unhandled Promise Rejections:**
|
|
26
|
-
- Issue: Comments in `evolution-worker.ts` (line 182) reference unhandled rejections leaving workflows in limbo. Pattern of catch blocks that re-throw or log but don't always propagate.
|
|
27
|
-
- Files: `src/service/evolution-worker.ts`
|
|
28
|
-
- Impact: Workflows stuck in inconsistent state, silent failures
|
|
29
|
-
- Fix approach: Ensure all async operations have proper error handlers; use `process.on('unhandledRejection')` logging
|
|
30
|
-
|
|
31
|
-
**TODO Comments Not Addressed:**
|
|
32
|
-
- Issue: One active TODO in `src/hooks/bash-risk.ts:18` — "Extract types from gate.ts related to bash risk analysis"
|
|
33
|
-
- Files: `src/hooks/bash-risk.ts`
|
|
34
|
-
|
|
35
|
-
## Known Bugs
|
|
36
|
-
|
|
37
|
-
**Stale Active Workflows (#185):**
|
|
38
|
-
- Symptoms: Workflows marked 'active' but subagent never responds, blocking queue processing
|
|
39
|
-
- Files: `src/service/evolution-worker.ts` (runWorkflowWatchdog)
|
|
40
|
-
- Trigger: Subagent crash or network failure during workflow execution
|
|
41
|
-
- Workaround: Watchdog marks them as 'terminal_error' after 2x TTL
|
|
42
|
-
|
|
43
|
-
**Orphaned Sessions (#188):**
|
|
44
|
-
- Symptoms: Child session cleanup fails when subagent runtime unavailable
|
|
45
|
-
- Files: `src/service/evolution-worker.ts` (cleanup path)
|
|
46
|
-
- Trigger: Gateway-safe fallback fails
|
|
47
|
-
- Workaround: Manual cleanup required
|
|
48
|
-
|
|
49
|
-
**Sleep Reflection Timeout Recovery (#214, #219):**
|
|
50
|
-
- Symptoms: `sleep_reflection` tasks stuck in 'in_progress' after worker crash
|
|
51
|
-
- Files: `src/service/evolution-worker.ts` (lines 1122-1198)
|
|
52
|
-
- Trigger: Worker crashes after claiming task but before writing result
|
|
53
|
-
- Fix: Timeout recovery logic reclaims stuck tasks after `task_timeout_ms`
|
|
54
|
-
|
|
55
|
-
## Security Considerations
|
|
56
|
-
|
|
57
|
-
**Credential Detection in Logs:**
|
|
58
|
-
- Risk: Sensitive data (passwords, tokens, api_keys) may leak into event logs or trajectory data
|
|
59
|
-
- Files: `src/hooks/trajectory-collector.ts`, `src/core/nocturnal-arbiter.ts`, `src/core/nocturnal-compliance.ts`
|
|
60
|
-
- Current mitigation: `SENSITIVE_KEY_PATTERN` regex filters known patterns
|
|
61
|
-
- Recommendations: Extend pattern to cover more formats; add redaction before any async write
|
|
62
|
-
|
|
63
|
-
**Gateway Token Auth:**
|
|
64
|
-
- Risk: HTTP route in `principles-console-route.ts` uses Bearer token auth
|
|
65
|
-
- Files: `src/http/principles-console-route.ts`
|
|
66
|
-
- Current mitigation: Token comparison with configured value
|
|
67
|
-
- Recommendations: Use constant-time comparison to prevent timing attacks
|
|
68
|
-
|
|
69
|
-
**No eval() or Dynamic Code Execution:**
|
|
70
|
-
- Status: Clean — no `eval()`, `new Function()`, or `dangerouslySetInnerHTML` found in codebase
|
|
71
|
-
|
|
72
|
-
## Performance Bottlenecks
|
|
73
|
-
|
|
74
|
-
**Session Persistence Timer Per Session:**
|
|
75
|
-
- Problem: `session-tracker.ts` creates a `setTimeout` per session for delayed persistence writes
|
|
76
|
-
- Files: `src/core/session-tracker.ts`
|
|
77
|
-
- Cause: Timer per workspace/session scales poorly with many concurrent sessions
|
|
78
|
-
- Improvement path: Use a single periodic sweep for all dirty sessions
|
|
79
|
-
|
|
80
|
-
**Event Log Buffer Flush:**
|
|
81
|
-
- Problem: 20-event buffer or 30-second flush interval — events can be lost on crash
|
|
82
|
-
- Files: `src/core/event-log.ts`
|
|
83
|
-
- Cause: Trade-off between I/O frequency and durability
|
|
84
|
-
- Improvement path: Flush immediately on critical events (hook failures, errors)
|
|
85
|
-
|
|
86
|
-
**Evolution Queue File Read on Every Cycle:**
|
|
87
|
-
- Problem: `evolution-worker.ts` reads and parses the entire queue JSON file on each heartbeat
|
|
88
|
-
- Files: `src/service/evolution-worker.ts` (queue loading at lines 1085-1110)
|
|
89
|
-
- Cause: Full file read/parse despite incremental changes
|
|
90
|
-
- Improvement path: Use SQLite or incremental updates
|
|
91
|
-
|
|
92
|
-
**Focus History Compression Timestamp:**
|
|
93
|
-
- Problem: `focus-history.ts` writes `Date.now().toString()` on every compression
|
|
94
|
-
- Files: `src/core/focus-history.ts` (line 962)
|
|
95
|
-
- Impact: File modified on every compress even if content unchanged
|
|
96
|
-
|
|
97
|
-
## Fragile Areas
|
|
98
|
-
|
|
99
|
-
**Workflow Store Queue Migration:**
|
|
100
|
-
- Files: `src/service/evolution-worker.ts` (migrateQueueToV2), `src/service/subagent-workflow/workflow-store.ts`
|
|
101
|
-
- Why fragile: Legacy queue format detection via type guards, migration happens on every cycle
|
|
102
|
-
- Safe modification: Add version field, run migrations once at startup not per cycle
|
|
103
|
-
|
|
104
|
-
**JSON.parse Without Try-Catch on Queue Items:**
|
|
105
|
-
- Files: `src/service/evolution-worker.ts` (line 1148: `JSON.parse(failureEvent.payload_json)`)
|
|
106
|
-
- Why fragile: Payload may be malformed, parse throws and is caught broadly
|
|
107
|
-
- Safe modification: Validate JSON structure before parse
|
|
108
|
-
|
|
109
|
-
**Nocturnal Trinity Runtime Adapter:**
|
|
110
|
-
- Files: `src/core/nocturnal-trinity.ts` (TrinityRuntimeAdapter)
|
|
111
|
-
- Why fragile: Uses `api.runtime.agent.runEmbeddedPiAgent()` which has specific requirements (provider/model must be explicit)
|
|
112
|
-
- Safe modification: Ensure all trinity calls pass explicit provider/model
|
|
113
|
-
|
|
114
|
-
## Dependencies at Risk
|
|
115
|
-
|
|
116
|
-
**better-sqlite3 (^12.9.0):**
|
|
117
|
-
- Risk: Native module requiring platform-specific rebuilds; may break on Node.js major version upgrades
|
|
118
|
-
- Impact: Database operations fail, session/trajectory storage breaks
|
|
119
|
-
- Migration plan: Consider `sql.js` (pure JS) or `node:sqlite` (built-in) for portability
|
|
120
|
-
|
|
121
|
-
**@sinclair/typebox (^0.34.48):**
|
|
122
|
-
- Risk: Used for runtime schema validation; newer versions may change behavior
|
|
123
|
-
- Impact: Validation mismatches could allow invalid data through
|
|
124
|
-
|
|
125
|
-
## Test Coverage Gaps
|
|
126
|
-
|
|
127
|
-
**Untested Service Layer:**
|
|
128
|
-
- What's not tested: `evolution-worker.ts` (2689 lines), `nocturnal-service.ts` (1584 lines)
|
|
129
|
-
- Files: `src/service/evolution-worker.ts`, `src/service/nocturnal-service.ts`
|
|
130
|
-
- Risk: High — service layer contains critical business logic
|
|
131
|
-
- Priority: High
|
|
132
|
-
|
|
133
|
-
**Untested Workflow Managers:**
|
|
134
|
-
- What's not tested: `empathy-observer-workflow-manager.ts`, `deep-reflect-workflow-manager.ts`, `correction-observer-workflow-manager.ts`
|
|
135
|
-
- Files: `src/service/subagent-workflow/`
|
|
136
|
-
- Risk: Workflow spawning and result handling is untested
|
|
137
|
-
|
|
138
|
-
**No Integration Tests for Queue Processing:**
|
|
139
|
-
- What's not tested: Queue enqueue/dequeue cycle, migration path, error recovery
|
|
140
|
-
- Files: `src/service/evolution-worker.ts` (queue operations)
|
|
141
|
-
- Risk: Queue corruption or migration bugs go undetected
|
|
142
|
-
|
|
143
|
-
---
|
|
144
|
-
|
|
145
|
-
*Concerns audit: 2026-04-15*
|