principles-disciple 1.66.0 → 1.68.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/ADVANCED_CONFIG_ZH.md +0 -4
- package/README.md +0 -11
- package/openclaw.plugin.json +3 -26
- package/package.json +1 -1
- package/scripts/sync-plugin.mjs +113 -28
- package/src/commands/context.ts +6 -14
- package/src/commands/evolution-status.ts +29 -3
- package/src/commands/pain.ts +3 -4
- package/src/config/defaults/runtime.ts +0 -2
- package/src/constants/tools.ts +0 -1
- package/src/core/config.ts +0 -30
- package/src/core/event-log.ts +0 -6
- package/src/hooks/prompt.ts +6 -38
- package/src/hooks/subagent.ts +0 -7
- package/src/index.ts +0 -2
- package/src/service/evolution-worker.ts +0 -13
- package/src/service/runtime-summary-service.ts +94 -15
- package/src/service/subagent-workflow/deep-reflect-workflow-manager.ts +1 -204
- package/src/service/subagent-workflow/index.ts +0 -8
- package/src/service/subagent-workflow/types.ts +0 -11
- package/src/service/subagent-workflow/workflow-manager-base.ts +1 -1
- package/src/tools/critique-prompt.ts +1 -97
- package/src/tools/deep-reflect.ts +1 -337
- package/src/tools/model-index.ts +1 -100
- package/src/types/event-payload.ts +0 -6
- package/src/types/event-types.ts +0 -86
- package/src/types.ts +0 -21
- package/templates/langs/en/core/TOOLS.md +0 -43
- package/templates/langs/zh/core/TOOLS.md +0 -43
- package/templates/pain_settings.json +0 -21
- package/tests/commands/evolution-status.test.ts +288 -0
- package/tests/core/event-log.test.ts +1 -29
- package/tests/service/runtime-summary-service.test.ts +1 -1
|
@@ -1,337 +1 @@
|
|
|
1
|
-
|
|
2
|
-
import type { PluginRuntimeSubagent } from '../service/subagent-workflow/runtime-direct-driver.js';
|
|
3
|
-
import { Type } from '@sinclair/typebox';
|
|
4
|
-
import * as fs from 'fs';
|
|
5
|
-
import { EventLogService } from '../core/event-log.js';
|
|
6
|
-
import { resolvePdPath } from '../core/paths.js';
|
|
7
|
-
import { resolveWorkspaceDirFromApi } from '../core/path-resolver.js';
|
|
8
|
-
import { WorkspaceNotFoundError } from '../config/index.js';
|
|
9
|
-
import {
|
|
10
|
-
DeepReflectWorkflowManager,
|
|
11
|
-
deepReflectWorkflowSpec,
|
|
12
|
-
type DeepReflectTaskInput,
|
|
13
|
-
} from '../service/subagent-workflow/index.js';
|
|
14
|
-
|
|
15
|
-
interface DeepReflectionConfig {
|
|
16
|
-
enabled: boolean;
|
|
17
|
-
mode: 'auto' | 'forced' | 'disabled';
|
|
18
|
-
auto_trigger_conditions: {
|
|
19
|
-
min_tool_calls: number;
|
|
20
|
-
error_rate_threshold: number;
|
|
21
|
-
high_gfi_threshold: number;
|
|
22
|
-
};
|
|
23
|
-
modelsDir?: string;
|
|
24
|
-
timeout_ms?: number;
|
|
25
|
-
}
|
|
26
|
-
|
|
27
|
-
/**
|
|
28
|
-
* Type assertion: OpenClaw SDK subagent -> workflow manager subagent type.
|
|
29
|
-
* Both types are structurally identical but come from different import paths.
|
|
30
|
-
*/
|
|
31
|
-
function toWorkflowSubagent(
|
|
32
|
-
subagent: NonNullable<OpenClawPluginApi['runtime']>['subagent']
|
|
33
|
-
): PluginRuntimeSubagent {
|
|
34
|
-
return subagent as unknown as PluginRuntimeSubagent;
|
|
35
|
-
}
|
|
36
|
-
|
|
37
|
-
const DEFAULT_CONFIG: DeepReflectionConfig = {
|
|
38
|
-
enabled: true,
|
|
39
|
-
mode: 'auto',
|
|
40
|
-
auto_trigger_conditions: {
|
|
41
|
-
min_tool_calls: 5,
|
|
42
|
-
error_rate_threshold: 0.3,
|
|
43
|
-
high_gfi_threshold: 70
|
|
44
|
-
},
|
|
45
|
-
timeout_ms: 60000
|
|
46
|
-
};
|
|
47
|
-
|
|
48
|
-
function safeLog(
|
|
49
|
-
api: OpenClawPluginApi | undefined,
|
|
50
|
-
level: 'info' | 'debug' | 'warn' | 'error',
|
|
51
|
-
message: string
|
|
52
|
-
): void {
|
|
53
|
-
try {
|
|
54
|
-
if (api?.logger && typeof api.logger[level] === 'function') {
|
|
55
|
-
api.logger[level](message);
|
|
56
|
-
}
|
|
57
|
-
} catch {
|
|
58
|
-
// Never recurse on logger failures
|
|
59
|
-
}
|
|
60
|
-
}
|
|
61
|
-
|
|
62
|
-
function loadConfig(workspaceDir: string | undefined, api: OpenClawPluginApi): DeepReflectionConfig {
|
|
63
|
-
if (!workspaceDir) return DEFAULT_CONFIG;
|
|
64
|
-
const configPath = resolvePdPath(workspaceDir, 'PAIN_SETTINGS');
|
|
65
|
-
try {
|
|
66
|
-
if (fs.existsSync(configPath)) {
|
|
67
|
-
const raw = fs.readFileSync(configPath, 'utf-8');
|
|
68
|
-
const settings = JSON.parse(raw);
|
|
69
|
-
return { ...DEFAULT_CONFIG, ...settings.deep_reflection };
|
|
70
|
-
}
|
|
71
|
-
} catch (err) {
|
|
72
|
-
safeLog(api, 'warn', `[DeepReflect] Failed to load config: ${String(err)}`);
|
|
73
|
-
}
|
|
74
|
-
return DEFAULT_CONFIG;
|
|
75
|
-
}
|
|
76
|
-
|
|
77
|
-
function readStringParam(rawParams: Record<string, unknown>, key: string): string | undefined {
|
|
78
|
-
const value = rawParams[key];
|
|
79
|
-
if (typeof value === 'string') return value.trim() || undefined;
|
|
80
|
-
|
|
81
|
-
const snakeKey = key.replace(/([A-Z])/g, '_$1').toLowerCase();
|
|
82
|
-
const snakeValue = rawParams[snakeKey];
|
|
83
|
-
if (typeof snakeValue === 'string') return snakeValue.trim() || undefined;
|
|
84
|
-
|
|
85
|
-
return undefined;
|
|
86
|
-
}
|
|
87
|
-
|
|
88
|
-
function readNumberParam(rawParams: Record<string, unknown>, key: string): number | undefined {
|
|
89
|
-
const value = rawParams[key];
|
|
90
|
-
if (typeof value === 'number') return value;
|
|
91
|
-
|
|
92
|
-
const snakeKey = key.replace(/([A-Z])/g, '_$1').toLowerCase();
|
|
93
|
-
const snakeValue = rawParams[snakeKey];
|
|
94
|
-
if (typeof snakeValue === 'number') return snakeValue;
|
|
95
|
-
|
|
96
|
-
return undefined;
|
|
97
|
-
}
|
|
98
|
-
|
|
99
|
-
export function createDeepReflectTool(api: OpenClawPluginApi) {
|
|
100
|
-
return {
|
|
101
|
-
name: 'deep_reflect',
|
|
102
|
-
description: '执行深层次的元认知反思,分析当前任务的潜在风险、逻辑漏洞或架构改进点。',
|
|
103
|
-
parameters: Type.Object({
|
|
104
|
-
context: Type.String({ description: '需要反思的任务上下文、代码片段或当前遇到的困难。' }),
|
|
105
|
-
depth: Type.Optional(Type.Number({ description: '反思深度 (1-3)。1: 快速扫描, 2: 均衡分析, 3: 彻底解构。默认为 2。', minimum: 1, maximum: 3 })),
|
|
106
|
-
model_id: Type.Optional(Type.String({ description: '可选:强制指定使用的思维模型 ID。' }))
|
|
107
|
-
}),
|
|
108
|
-
|
|
109
|
-
async execute(
|
|
110
|
-
_toolCallId: string,
|
|
111
|
-
rawParams: Record<string, unknown>
|
|
112
|
-
): Promise<{ content: { type: string; text: string }[] }> {
|
|
113
|
-
const context = readStringParam(rawParams, 'context') || '';
|
|
114
|
-
const depth = readNumberParam(rawParams, 'depth') ?? 2;
|
|
115
|
-
const model_id = readStringParam(rawParams, 'model_id');
|
|
116
|
-
|
|
117
|
-
if (!context) {
|
|
118
|
-
return { content: [{ type: 'text', text: '❌ 错误: 必须提供反思上下文 (context)。' }] };
|
|
119
|
-
}
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
const effectiveWorkspaceDir = resolveReflectionWorkspace(api);
|
|
124
|
-
|
|
125
|
-
const config = loadConfig(effectiveWorkspaceDir, api);
|
|
126
|
-
if (config.mode === 'disabled' || !config.enabled) {
|
|
127
|
-
return { content: [{ type: 'text', text: '⏭️ Deep Reflection 已禁用。' }] };
|
|
128
|
-
}
|
|
129
|
-
|
|
130
|
-
if (model_id) {
|
|
131
|
-
safeLog(api, 'warn', `[DeepReflect] The 'model_id' parameter is deprecated. The agent will now auto-select models based on the context index.`);
|
|
132
|
-
}
|
|
133
|
-
|
|
134
|
-
try {
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
return await executeReflectionWorkflow(effectiveWorkspaceDir, config, context, depth, model_id, api);
|
|
138
|
-
} catch (err) {
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
return handleReflectionError(err, context, depth, model_id, effectiveWorkspaceDir, api);
|
|
142
|
-
}
|
|
143
|
-
}
|
|
144
|
-
};
|
|
145
|
-
}
|
|
146
|
-
|
|
147
|
-
/**
|
|
148
|
-
* Resolve workspace directory for deep reflection tool.
|
|
149
|
-
*/
|
|
150
|
-
function resolveReflectionWorkspace(api: OpenClawPluginApi): string {
|
|
151
|
-
// FIX (B): Only use resolveWorkspaceDirFromApi — do not chain through api.config?.workspaceDir
|
|
152
|
-
// which may be stale. Fail-fast if workspace cannot be resolved.
|
|
153
|
-
const dir = resolveWorkspaceDirFromApi(api);
|
|
154
|
-
if (!dir) {
|
|
155
|
-
throw new WorkspaceNotFoundError('deep-reflect: workspace directory could not be resolved via API');
|
|
156
|
-
}
|
|
157
|
-
return dir;
|
|
158
|
-
}
|
|
159
|
-
|
|
160
|
-
/**
|
|
161
|
-
* Execute the deep reflection workflow: start, poll, collect results.
|
|
162
|
-
*/
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
async function executeReflectionWorkflow(
|
|
166
|
-
effectiveWorkspaceDir: string,
|
|
167
|
-
config: DeepReflectionConfig,
|
|
168
|
-
context: string,
|
|
169
|
-
depth: number,
|
|
170
|
-
model_id: string | undefined,
|
|
171
|
-
api: OpenClawPluginApi,
|
|
172
|
-
): Promise<{ content: { type: string; text: string }[] }> {
|
|
173
|
-
const stateDir = resolvePdPath(effectiveWorkspaceDir, 'STATE_DIR');
|
|
174
|
-
const eventLog = EventLogService.get(stateDir, api.logger);
|
|
175
|
-
const parentSessionId = effectiveWorkspaceDir.replace(/[^a-zA-Z0-9_-]/g, '_').substring(0, 64);
|
|
176
|
-
|
|
177
|
-
const manager = new DeepReflectWorkflowManager({
|
|
178
|
-
workspaceDir: effectiveWorkspaceDir,
|
|
179
|
-
logger: api.logger,
|
|
180
|
-
|
|
181
|
-
subagent: toWorkflowSubagent(api.runtime.subagent),
|
|
182
|
-
agentSession: api.runtime.agent?.session,
|
|
183
|
-
});
|
|
184
|
-
|
|
185
|
-
try {
|
|
186
|
-
const taskInput: DeepReflectTaskInput = { context, depth, model_id };
|
|
187
|
-
const handle = await manager.startWorkflow(deepReflectWorkflowSpec, {
|
|
188
|
-
parentSessionId,
|
|
189
|
-
workspaceDir: effectiveWorkspaceDir,
|
|
190
|
-
taskInput,
|
|
191
|
-
});
|
|
192
|
-
|
|
193
|
-
const startTime = Date.now();
|
|
194
|
-
const timeoutMs = config.timeout_ms ?? 60000;
|
|
195
|
-
|
|
196
|
-
|
|
197
|
-
return await pollReflectionCompletion(manager, handle, timeoutMs, startTime, eventLog, effectiveWorkspaceDir, context, model_id, depth);
|
|
198
|
-
} finally {
|
|
199
|
-
manager.dispose();
|
|
200
|
-
}
|
|
201
|
-
}
|
|
202
|
-
|
|
203
|
-
/**
|
|
204
|
-
* Poll the reflection workflow until completion, timeout, or error.
|
|
205
|
-
*/
|
|
206
|
-
|
|
207
|
-
|
|
208
|
-
async function pollReflectionCompletion(
|
|
209
|
-
manager: DeepReflectWorkflowManager,
|
|
210
|
-
handle: { workflowId: string; childSessionKey: string },
|
|
211
|
-
timeoutMs: number,
|
|
212
|
-
startTime: number,
|
|
213
|
-
eventLog: ReturnType<typeof EventLogService.get>,
|
|
214
|
-
workspaceDir: string,
|
|
215
|
-
context: string,
|
|
216
|
-
model_id: string | undefined,
|
|
217
|
-
depth: number,
|
|
218
|
-
): Promise<{ content: { type: string; text: string }[] }> {
|
|
219
|
-
const pollInterval = 500;
|
|
220
|
-
|
|
221
|
-
while (Date.now() - startTime < timeoutMs) {
|
|
222
|
-
await new Promise(resolve => setTimeout(resolve, pollInterval));
|
|
223
|
-
const workflowState = manager.getWorkflowState(handle.workflowId);
|
|
224
|
-
if (!workflowState) break;
|
|
225
|
-
|
|
226
|
-
if (workflowState === 'completed') {
|
|
227
|
-
|
|
228
|
-
|
|
229
|
-
return formatReflectionSuccess(handle, context, depth, model_id, startTime, eventLog, workspaceDir);
|
|
230
|
-
}
|
|
231
|
-
|
|
232
|
-
if (workflowState === 'terminal_error' || workflowState === 'expired') {
|
|
233
|
-
throw new Error(`Deep-reflect workflow failed: ${workflowState}`);
|
|
234
|
-
}
|
|
235
|
-
}
|
|
236
|
-
|
|
237
|
-
return { content: [{ type: 'text', text: '⚠️ 反思任务执行超时。你可以尝试减少上下文长度或增加深度。' }] };
|
|
238
|
-
}
|
|
239
|
-
|
|
240
|
-
/**
|
|
241
|
-
* Format the success response from a completed reflection.
|
|
242
|
-
*/
|
|
243
|
-
|
|
244
|
-
|
|
245
|
-
function formatReflectionSuccess(
|
|
246
|
-
handle: { childSessionKey: string },
|
|
247
|
-
context: string,
|
|
248
|
-
depth: number,
|
|
249
|
-
model_id: string | undefined,
|
|
250
|
-
startTime: number,
|
|
251
|
-
eventLog: ReturnType<typeof EventLogService.get>,
|
|
252
|
-
workspaceDir: string,
|
|
253
|
-
): { content: { type: string; text: string }[] } {
|
|
254
|
-
const reflectionLogPath = resolvePdPath(workspaceDir, 'REFLECTION_LOG');
|
|
255
|
-
let insights = '';
|
|
256
|
-
if (fs.existsSync(reflectionLogPath)) {
|
|
257
|
-
const content = fs.readFileSync(reflectionLogPath, 'utf8');
|
|
258
|
-
const match = /### Insights\n([\s\S]*?)(?=---|$)/.exec(content);
|
|
259
|
-
if (match) insights = match[1].trim();
|
|
260
|
-
}
|
|
261
|
-
|
|
262
|
-
if (eventLog) {
|
|
263
|
-
eventLog.recordDeepReflection(handle.childSessionKey, {
|
|
264
|
-
modelId: model_id || 'auto-select',
|
|
265
|
-
modelSelectionMode: model_id ? 'manual' : 'auto',
|
|
266
|
-
depth,
|
|
267
|
-
contextPreview: context.substring(0, 200),
|
|
268
|
-
resultPreview: insights.substring(0, 300),
|
|
269
|
-
durationMs: Date.now() - startTime,
|
|
270
|
-
passed: true,
|
|
271
|
-
timeout: false,
|
|
272
|
-
});
|
|
273
|
-
}
|
|
274
|
-
|
|
275
|
-
return {
|
|
276
|
-
content: [{
|
|
277
|
-
type: 'text',
|
|
278
|
-
text: `
|
|
279
|
-
# 💎 Deep Reflection Insights
|
|
280
|
-
---
|
|
281
|
-
**Selected Model(s)**: ${model_id || 'auto-select'}
|
|
282
|
-
**Reflection Depth**: ${depth}
|
|
283
|
-
**Analysis Duration**: ${((Date.now() - startTime) / 1000).toFixed(1)}s
|
|
284
|
-
|
|
285
|
-
${insights || '反思完成,详见 REFLECTION_LOG。'}
|
|
286
|
-
|
|
287
|
-
---
|
|
288
|
-
*Generated by Principles Disciple Meta-Cognitive Engine*
|
|
289
|
-
`.trim(),
|
|
290
|
-
}],
|
|
291
|
-
};
|
|
292
|
-
}
|
|
293
|
-
|
|
294
|
-
/**
|
|
295
|
-
* Handle reflection errors and format error response.
|
|
296
|
-
*/
|
|
297
|
-
|
|
298
|
-
|
|
299
|
-
function handleReflectionError(
|
|
300
|
-
err: unknown,
|
|
301
|
-
context: string,
|
|
302
|
-
depth: number,
|
|
303
|
-
model_id: string | undefined,
|
|
304
|
-
workspaceDir: string,
|
|
305
|
-
api: OpenClawPluginApi,
|
|
306
|
-
): { content: { type: string; text: string }[] } {
|
|
307
|
-
const errorMsg = err instanceof Error ? err.message : String(err);
|
|
308
|
-
safeLog(api, 'error', `[DeepReflect] Reflection failed: ${errorMsg}`);
|
|
309
|
-
|
|
310
|
-
const stateDir = resolvePdPath(workspaceDir, 'STATE_DIR');
|
|
311
|
-
const eventLog = EventLogService.get(stateDir, api.logger);
|
|
312
|
-
|
|
313
|
-
if (eventLog) {
|
|
314
|
-
eventLog.recordDeepReflection('deep-reflect-error', {
|
|
315
|
-
modelId: model_id || 'auto-select',
|
|
316
|
-
modelSelectionMode: model_id ? 'manual' : 'auto',
|
|
317
|
-
depth,
|
|
318
|
-
contextPreview: context.substring(0, 200),
|
|
319
|
-
durationMs: 0,
|
|
320
|
-
passed: false,
|
|
321
|
-
timeout: errorMsg.toLowerCase().includes('timeout'),
|
|
322
|
-
error: errorMsg,
|
|
323
|
-
});
|
|
324
|
-
}
|
|
325
|
-
|
|
326
|
-
return { content: [{ type: 'text', text: `❌ 反思执行失败: ${errorMsg}。请检查 API 配置或网络连接。` }] };
|
|
327
|
-
}
|
|
328
|
-
|
|
329
|
-
export const deepReflectTool = {
|
|
330
|
-
name: 'deep_reflect',
|
|
331
|
-
description: '执行深层次的元认知反思,分析当前任务的潜在风险、逻辑漏洞或架构改进点。',
|
|
332
|
-
parameters: Type.Object({
|
|
333
|
-
context: Type.String({ description: '需要反思的任务上下文、代码片段或当前遇到的困难。' }),
|
|
334
|
-
depth: Type.Optional(Type.Number({ description: '反思深度 (1-3)。1: 快速扫描, 2: 均衡分析, 3: 彻底解构。默认为 2。', minimum: 1, maximum: 3 })),
|
|
335
|
-
model_id: Type.Optional(Type.String({ description: '可选:强制指定使用的思维模型 ID。' }))
|
|
336
|
-
}),
|
|
337
|
-
};
|
|
1
|
+
export {};
|
package/src/tools/model-index.ts
CHANGED
|
@@ -1,100 +1 @@
|
|
|
1
|
-
|
|
2
|
-
import * as path from 'path';
|
|
3
|
-
import type { OpenClawPluginApi } from '../openclaw-sdk.js';
|
|
4
|
-
import { WorkspaceContext } from '../core/workspace-context.js';
|
|
5
|
-
|
|
6
|
-
// 安全日志函数
|
|
7
|
-
function safeLog(
|
|
8
|
-
api: OpenClawPluginApi | undefined,
|
|
9
|
-
level: 'info' | 'debug' | 'warn' | 'error',
|
|
10
|
-
message: string
|
|
11
|
-
): void {
|
|
12
|
-
try {
|
|
13
|
-
if (api?.logger && typeof api.logger[level] === 'function') {
|
|
14
|
-
api.logger[level](message);
|
|
15
|
-
}
|
|
16
|
-
} catch {
|
|
17
|
-
// Ignore logging errors
|
|
18
|
-
}
|
|
19
|
-
}
|
|
20
|
-
|
|
21
|
-
/**
|
|
22
|
-
* 默认消息
|
|
23
|
-
*/
|
|
24
|
-
const DEFAULT_MESSAGE = '(暂无扩展思维模型)';
|
|
25
|
-
|
|
26
|
-
/**
|
|
27
|
-
* 索引文件最大大小(字节)
|
|
28
|
-
*/
|
|
29
|
-
const MAX_INDEX_SIZE = 50 * 1024; // 50KB
|
|
30
|
-
|
|
31
|
-
/**
|
|
32
|
-
* 加载自定义配置
|
|
33
|
-
*/
|
|
34
|
-
function loadCustomConfig(wctx: WorkspaceContext): { modelsDir?: string } | undefined {
|
|
35
|
-
try {
|
|
36
|
-
const {config} = wctx;
|
|
37
|
-
const modelsDir = config.get('deep_reflection.modelsDir');
|
|
38
|
-
if (typeof modelsDir === 'string' && modelsDir.trim()) {
|
|
39
|
-
return { modelsDir: modelsDir.trim() };
|
|
40
|
-
}
|
|
41
|
-
} catch {
|
|
42
|
-
// Ignore config errors
|
|
43
|
-
}
|
|
44
|
-
return undefined;
|
|
45
|
-
}
|
|
46
|
-
|
|
47
|
-
/**
|
|
48
|
-
* 加载模型索引并返回格式化后的字符串
|
|
49
|
-
*
|
|
50
|
-
* @param workspaceDir 工作区目录
|
|
51
|
-
* @param api OpenClaw 插件 API
|
|
52
|
-
* @returns 格式化后的模型索引内容或默认消息
|
|
53
|
-
*/
|
|
54
|
-
export function loadModelIndex(
|
|
55
|
-
workspaceDir: string,
|
|
56
|
-
api?: OpenClawPluginApi
|
|
57
|
-
): string {
|
|
58
|
-
if (!workspaceDir) return DEFAULT_MESSAGE;
|
|
59
|
-
|
|
60
|
-
try {
|
|
61
|
-
const wctx = WorkspaceContext.fromHookContext({ workspaceDir });
|
|
62
|
-
const customConfig = loadCustomConfig(wctx);
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
let modelsDir: string;
|
|
67
|
-
if (customConfig?.modelsDir) {
|
|
68
|
-
modelsDir = path.isAbsolute(customConfig.modelsDir)
|
|
69
|
-
? customConfig.modelsDir
|
|
70
|
-
: path.join(workspaceDir, customConfig.modelsDir);
|
|
71
|
-
|
|
72
|
-
// 👈 关键修复:显式输出测试用例期待的 debug 日志
|
|
73
|
-
safeLog(api, 'debug', `[DeepReflect] Using custom models dir: ${modelsDir}`);
|
|
74
|
-
} else {
|
|
75
|
-
modelsDir = wctx.resolve('MODELS_DIR');
|
|
76
|
-
}
|
|
77
|
-
|
|
78
|
-
const indexPath = path.join(modelsDir, '_INDEX.md');
|
|
79
|
-
|
|
80
|
-
if (!fs.existsSync(indexPath)) {
|
|
81
|
-
if (fs.existsSync(modelsDir)) {
|
|
82
|
-
safeLog(api, 'warn', `[DeepReflect] _INDEX.md not found but ${modelsDir.replace(workspaceDir, '')} exists. Please create an index file.`);
|
|
83
|
-
}
|
|
84
|
-
return DEFAULT_MESSAGE;
|
|
85
|
-
}
|
|
86
|
-
|
|
87
|
-
const stats = fs.statSync(indexPath);
|
|
88
|
-
if (stats.size > MAX_INDEX_SIZE) {
|
|
89
|
-
safeLog(api, 'warn', `[DeepReflect] Index file too large (${stats.size} bytes). Max is ${MAX_INDEX_SIZE}.`);
|
|
90
|
-
return DEFAULT_MESSAGE;
|
|
91
|
-
}
|
|
92
|
-
|
|
93
|
-
const content = fs.readFileSync(indexPath, 'utf-8');
|
|
94
|
-
return content.trim() || DEFAULT_MESSAGE;
|
|
95
|
-
|
|
96
|
-
} catch (err) {
|
|
97
|
-
safeLog(api, 'warn', `[DeepReflect] Failed to load model index: ${String(err)}`);
|
|
98
|
-
return DEFAULT_MESSAGE;
|
|
99
|
-
}
|
|
100
|
-
}
|
|
1
|
+
export {};
|
|
@@ -13,7 +13,6 @@ import type {
|
|
|
13
13
|
GateBypassEventData,
|
|
14
14
|
PlanApprovalEventData,
|
|
15
15
|
EvolutionTaskEventData,
|
|
16
|
-
DeepReflectionEventData,
|
|
17
16
|
EmpathyRollbackEventData,
|
|
18
17
|
EventCategory,
|
|
19
18
|
} from './event-types.js';
|
|
@@ -28,7 +27,6 @@ export type EventLogEntry =
|
|
|
28
27
|
| { ts: string; date: string; type: 'gate_bypass'; category: EventCategory; sessionId?: string; workspaceDir?: string; data: GateBypassEventData }
|
|
29
28
|
| { ts: string; date: string; type: 'plan_approval'; category: EventCategory; sessionId?: string; workspaceDir?: string; data: PlanApprovalEventData }
|
|
30
29
|
| { ts: string; date: string; type: 'evolution_task'; category: EventCategory; sessionId?: string; workspaceDir?: string; data: EvolutionTaskEventData }
|
|
31
|
-
| { ts: string; date: string; type: 'deep_reflection'; category: EventCategory; sessionId?: string; workspaceDir?: string; data: DeepReflectionEventData }
|
|
32
30
|
| { ts: string; date: string; type: 'empathy_rollback'; category: EventCategory; sessionId?: string; workspaceDir?: string; data: EmpathyRollbackEventData }
|
|
33
31
|
| { ts: string; date: string; type: 'error'; category: EventCategory; sessionId?: string; workspaceDir?: string; data: Record<string, unknown> }
|
|
34
32
|
| { ts: string; date: string; type: 'warn'; category: EventCategory; sessionId?: string; workspaceDir?: string; data: Record<string, unknown> };
|
|
@@ -71,10 +69,6 @@ export function isEvolutionTaskEventEntry(entry: EventLogEntry): entry is Extrac
|
|
|
71
69
|
return entry.type === 'evolution_task';
|
|
72
70
|
}
|
|
73
71
|
|
|
74
|
-
export function isDeepReflectionEventEntry(entry: EventLogEntry): entry is Extract<EventLogEntry, { type: 'deep_reflection' }> {
|
|
75
|
-
return entry.type === 'deep_reflection';
|
|
76
|
-
}
|
|
77
|
-
|
|
78
72
|
export function isEmpathyRollbackEventEntry(entry: EventLogEntry): entry is Extract<EventLogEntry, { type: 'empathy_rollback' }> {
|
|
79
73
|
return entry.type === 'empathy_rollback';
|
|
80
74
|
}
|
package/src/types/event-types.ts
CHANGED
|
@@ -14,7 +14,6 @@ export type EventType =
|
|
|
14
14
|
| 'gate_bypass'
|
|
15
15
|
| 'plan_approval'
|
|
16
16
|
| 'evolution_task'
|
|
17
|
-
| 'deep_reflection'
|
|
18
17
|
| 'empathy_rollback'
|
|
19
18
|
| 'error'
|
|
20
19
|
| 'warn'
|
|
@@ -154,35 +153,6 @@ export interface EvolutionTaskEventData {
|
|
|
154
153
|
reason: string;
|
|
155
154
|
}
|
|
156
155
|
|
|
157
|
-
export interface DeepReflectionEventData {
|
|
158
|
-
/** 思维模型 ID (T-01 到 T-09),向后兼容 */
|
|
159
|
-
modelId: string;
|
|
160
|
-
/** 模型选择模式:'manual' = 用户指定 model_id,'auto' = 子智能体自动选择 */
|
|
161
|
-
modelSelectionMode: 'manual' | 'auto';
|
|
162
|
-
/** 反思深度 (1-3) */
|
|
163
|
-
depth: number;
|
|
164
|
-
/** 上下文摘要(前 200 字符) */
|
|
165
|
-
contextPreview: string;
|
|
166
|
-
/** 反思结果摘要 */
|
|
167
|
-
resultPreview?: string;
|
|
168
|
-
/** 执行耗时 (ms) */
|
|
169
|
-
durationMs: number;
|
|
170
|
-
/** 是否通过(未发现显著问题) */
|
|
171
|
-
passed: boolean;
|
|
172
|
-
/** 是否超时 */
|
|
173
|
-
timeout: boolean;
|
|
174
|
-
/** 错误信息 */
|
|
175
|
-
error?: string;
|
|
176
|
-
/** 输出长度 */
|
|
177
|
-
outputLength?: number;
|
|
178
|
-
/** 置信度(从输出中提取) */
|
|
179
|
-
confidence?: 'LOW' | 'MEDIUM' | 'HIGH';
|
|
180
|
-
/** 发现的盲点数量 */
|
|
181
|
-
blindSpotsCount?: number;
|
|
182
|
-
/** 发现的风险数量 */
|
|
183
|
-
risksCount?: number;
|
|
184
|
-
}
|
|
185
|
-
|
|
186
156
|
export interface EmpathyRollbackEventData {
|
|
187
157
|
/** Event ID being rolled back */
|
|
188
158
|
eventId: string;
|
|
@@ -438,42 +408,6 @@ export interface HookStats {
|
|
|
438
408
|
totalDurationMs: number;
|
|
439
409
|
}
|
|
440
410
|
|
|
441
|
-
export interface DeepReflectionStats {
|
|
442
|
-
/** 总调用次数 */
|
|
443
|
-
totalCalls: number;
|
|
444
|
-
/** 通过次数(未发现问题) */
|
|
445
|
-
passedCount: number;
|
|
446
|
-
/** 发现问题的次数 */
|
|
447
|
-
issuesFoundCount: number;
|
|
448
|
-
/** 超时次数 */
|
|
449
|
-
timeoutCount: number;
|
|
450
|
-
/** 错误次数 */
|
|
451
|
-
errorCount: number;
|
|
452
|
-
/** 按模型选择模式统计 */
|
|
453
|
-
bySelectionMode: {
|
|
454
|
-
manual: { count: number; avgDurationMs: number; passedCount: number };
|
|
455
|
-
auto: { count: number; avgDurationMs: number; passedCount: number };
|
|
456
|
-
};
|
|
457
|
-
/** 按模型统计(向后兼容,仅记录手动指定的 model_id) */
|
|
458
|
-
byModel: Record<string, {
|
|
459
|
-
count: number;
|
|
460
|
-
avgDurationMs: number;
|
|
461
|
-
passedCount: number;
|
|
462
|
-
}>;
|
|
463
|
-
/** 按深度统计 */
|
|
464
|
-
byDepth: Record<number, number>;
|
|
465
|
-
/** 总耗时 */
|
|
466
|
-
totalDurationMs: number;
|
|
467
|
-
/** 平均耗时 */
|
|
468
|
-
avgDurationMs: number;
|
|
469
|
-
/** 发现的总盲点数 */
|
|
470
|
-
totalBlindSpots: number;
|
|
471
|
-
/** 发现的总风险数 */
|
|
472
|
-
totalRisks: number;
|
|
473
|
-
/** 置信度分布 */
|
|
474
|
-
confidenceDistribution: { LOW: number; MEDIUM: number; HIGH: number };
|
|
475
|
-
}
|
|
476
|
-
|
|
477
411
|
/**
|
|
478
412
|
* Daily aggregated statistics.
|
|
479
413
|
*/
|
|
@@ -504,8 +438,6 @@ export interface DailyStats {
|
|
|
504
438
|
evolution: EvolutionStats;
|
|
505
439
|
/** Hook execution statistics */
|
|
506
440
|
hooks: HookStats;
|
|
507
|
-
/** Deep Reflection statistics */
|
|
508
|
-
deepReflection: DeepReflectionStats;
|
|
509
441
|
}
|
|
510
442
|
|
|
511
443
|
/**
|
|
@@ -611,23 +543,5 @@ export function createEmptyDailyStats(date: string): DailyStats {
|
|
|
611
543
|
errors: 0,
|
|
612
544
|
totalDurationMs: 0,
|
|
613
545
|
},
|
|
614
|
-
deepReflection: {
|
|
615
|
-
totalCalls: 0,
|
|
616
|
-
passedCount: 0,
|
|
617
|
-
issuesFoundCount: 0,
|
|
618
|
-
timeoutCount: 0,
|
|
619
|
-
errorCount: 0,
|
|
620
|
-
bySelectionMode: {
|
|
621
|
-
manual: { count: 0, avgDurationMs: 0, passedCount: 0 },
|
|
622
|
-
auto: { count: 0, avgDurationMs: 0, passedCount: 0 },
|
|
623
|
-
},
|
|
624
|
-
byModel: {},
|
|
625
|
-
byDepth: {},
|
|
626
|
-
totalDurationMs: 0,
|
|
627
|
-
avgDurationMs: 0,
|
|
628
|
-
totalBlindSpots: 0,
|
|
629
|
-
totalRisks: 0,
|
|
630
|
-
confidenceDistribution: { LOW: 0, MEDIUM: 0, HIGH: 0 },
|
|
631
|
-
},
|
|
632
546
|
};
|
|
633
547
|
}
|
package/src/types.ts
CHANGED
|
@@ -31,9 +31,6 @@ export interface ContextInjectionConfig {
|
|
|
31
31
|
/** Project context (CURRENT_FOCUS.md) mode */
|
|
32
32
|
projectFocus: ProjectFocusMode;
|
|
33
33
|
|
|
34
|
-
/** Reflection log - can be toggled */
|
|
35
|
-
reflectionLog: boolean;
|
|
36
|
-
|
|
37
34
|
/** Evolution task context injection settings */
|
|
38
35
|
evolutionContext: EvolutionContextConfig;
|
|
39
36
|
}
|
|
@@ -44,31 +41,13 @@ export interface ContextInjectionConfig {
|
|
|
44
41
|
* - principles: always on (not configurable)
|
|
45
42
|
* - thinkingOs: true (can be turned off)
|
|
46
43
|
* - projectFocus: 'off' (default closed, user can enable)
|
|
47
|
-
* - reflectionLog: true (default on)
|
|
48
44
|
*/
|
|
49
45
|
export const defaultContextConfig: ContextInjectionConfig = {
|
|
50
46
|
thinkingOs: true,
|
|
51
47
|
projectFocus: 'off',
|
|
52
|
-
reflectionLog: true,
|
|
53
48
|
evolutionContext: {
|
|
54
49
|
enabled: true,
|
|
55
50
|
maxMessages: 4,
|
|
56
51
|
maxCharsPerMessage: 200,
|
|
57
52
|
},
|
|
58
53
|
};
|
|
59
|
-
|
|
60
|
-
/**
|
|
61
|
-
* Reflection log entry structure
|
|
62
|
-
*/
|
|
63
|
-
export interface ReflectionLogEntry {
|
|
64
|
-
timestamp: string;
|
|
65
|
-
context: string;
|
|
66
|
-
insights: string;
|
|
67
|
-
modelId?: string;
|
|
68
|
-
depth?: number;
|
|
69
|
-
}
|
|
70
|
-
|
|
71
|
-
/**
|
|
72
|
-
* Reflection log retention configuration
|
|
73
|
-
*/
|
|
74
|
-
export const reflectionLogRetentionDays = 7;
|
|
@@ -6,49 +6,6 @@
|
|
|
6
6
|
- **Tool Preference**: Prefer `rg` (ripgrep) for high-performance search. Never blindly traverse.
|
|
7
7
|
|
|
8
8
|
|
|
9
|
-
## 3. Deep Reflection Tool
|
|
10
|
-
`deep_reflect` is a **Cognitive Analysis Tool** — Performs critical analysis before executing complex tasks to identify blind spots, risks, and alternatives.
|
|
11
|
-
|
|
12
|
-
### When to Call
|
|
13
|
-
- **Complex Tasks**: Planning, design, decision-making, analysis requiring deep thinking
|
|
14
|
-
- **Insufficient Information**: Vague requirements, unclear constraints, missing key information
|
|
15
|
-
- **High-Stakes Decisions**: Important decisions, irreversible actions, broad impact
|
|
16
|
-
- **Uncertainty**: Unsure about the best approach, need multiple perspectives
|
|
17
|
-
|
|
18
|
-
### Use Case Examples
|
|
19
|
-
- Marketing strategy design: Analyze target audience, channel selection, risk mitigation
|
|
20
|
-
- Product feature planning: Evaluate user needs, technical feasibility, resource investment
|
|
21
|
-
- Architecture decisions: Weigh pros and cons, identify potential risks
|
|
22
|
-
- Problem diagnosis: Multi-angle root cause analysis, avoid missing key factors
|
|
23
|
-
|
|
24
|
-
### How to Call
|
|
25
|
-
```
|
|
26
|
-
deep_reflect(
|
|
27
|
-
model_id: "T-01" | "T-02" | ... | "T-09", // T-01 for planning, T-05 for risk analysis
|
|
28
|
-
context: "Describe your plan and concerns...",
|
|
29
|
-
depth: 1 | 2 | 3 // 1=quick, 2=balanced, 3=exhaustive
|
|
30
|
-
)
|
|
31
|
-
```
|
|
32
|
-
|
|
33
|
-
### Thinking Model Selection
|
|
34
|
-
| Model | Name | Best For |
|
|
35
|
-
|-------|------|----------|
|
|
36
|
-
| T-01 | Map Before Territory | Planning, design, understanding systems |
|
|
37
|
-
| T-05 | Negation Before Affirmation | Risk analysis, finding flaws |
|
|
38
|
-
| T-07 | Systems Over Components | Architecture decisions, integration issues |
|
|
39
|
-
|
|
40
|
-
### Output Structure
|
|
41
|
-
Tool returns: Blind Spots → Risk Warnings → Alternative Approaches → Recommendations → Confidence Level
|
|
42
|
-
|
|
43
|
-
**Note**: This is critical feedback. You make the final decision. Consider suggestions seriously, but don't follow blindly.
|
|
44
|
-
|
|
45
|
-
### Benefits
|
|
46
|
-
- Identifies blind spots and missing information
|
|
47
|
-
- Surfaces potential risks and failure modes
|
|
48
|
-
- Provides alternative approaches with trade-off analysis
|
|
49
|
-
- Applies structured thinking models for deeper insight
|
|
50
|
-
|
|
51
|
-
---
|
|
52
9
|
|
|
53
10
|
## 4. Agent Routing Clarification
|
|
54
11
|
|