claude-flow 2.0.0-alpha.66 → 2.0.0-alpha.68
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.claude/cache/agent-pool.json +33 -0
- package/.claude/cache/memory-optimization.json +19 -0
- package/.claude/cache/neural-optimization.json +25 -0
- package/.claude/cache/optimized-hooks.json +19 -0
- package/.claude/cache/parallel-processing.json +26 -0
- package/.claude/optimized-settings.json +270 -0
- package/.claude/settings-backup.json +186 -0
- package/.claude/settings-enhanced.json +278 -0
- package/.claude/settings-fixed.json +186 -0
- package/.claude/settings.json +105 -8
- package/CHANGELOG.md +38 -0
- package/bin/claude-flow +1 -1
- package/dist/cli/simple-commands/hive-mind.js +1 -1
- package/dist/cli/simple-commands/hive-mind.js.map +1 -1
- package/dist/cli/simple-commands/hooks.js +6 -4
- package/dist/cli/simple-commands/hooks.js.map +1 -1
- package/dist/providers/anthropic-provider.d.ts +27 -0
- package/dist/providers/anthropic-provider.d.ts.map +1 -0
- package/dist/providers/anthropic-provider.js +247 -0
- package/dist/providers/anthropic-provider.js.map +1 -0
- package/dist/providers/base-provider.d.ts +134 -0
- package/dist/providers/base-provider.d.ts.map +1 -0
- package/dist/providers/base-provider.js +407 -0
- package/dist/providers/base-provider.js.map +1 -0
- package/dist/providers/cohere-provider.d.ts +28 -0
- package/dist/providers/cohere-provider.d.ts.map +1 -0
- package/dist/providers/cohere-provider.js +407 -0
- package/dist/providers/cohere-provider.js.map +1 -0
- package/dist/providers/google-provider.d.ts +23 -0
- package/dist/providers/google-provider.d.ts.map +1 -0
- package/dist/providers/google-provider.js +362 -0
- package/dist/providers/google-provider.js.map +1 -0
- package/dist/providers/index.d.ts +14 -0
- package/dist/providers/index.d.ts.map +1 -0
- package/dist/providers/index.js +18 -0
- package/dist/providers/index.js.map +1 -0
- package/dist/providers/ollama-provider.d.ts +23 -0
- package/dist/providers/ollama-provider.d.ts.map +1 -0
- package/dist/providers/ollama-provider.js +374 -0
- package/dist/providers/ollama-provider.js.map +1 -0
- package/dist/providers/openai-provider.d.ts +23 -0
- package/dist/providers/openai-provider.d.ts.map +1 -0
- package/dist/providers/openai-provider.js +349 -0
- package/dist/providers/openai-provider.js.map +1 -0
- package/dist/providers/provider-manager.d.ts +139 -0
- package/dist/providers/provider-manager.d.ts.map +1 -0
- package/dist/providers/provider-manager.js +513 -0
- package/dist/providers/provider-manager.js.map +1 -0
- package/dist/providers/types.d.ts +356 -0
- package/dist/providers/types.d.ts.map +1 -0
- package/dist/providers/types.js +61 -0
- package/dist/providers/types.js.map +1 -0
- package/dist/providers/utils.d.ts +37 -0
- package/dist/providers/utils.d.ts.map +1 -0
- package/dist/providers/utils.js +322 -0
- package/dist/providers/utils.js.map +1 -0
- package/dist/services/agentic-flow-hooks/hook-manager.d.ts +70 -0
- package/dist/services/agentic-flow-hooks/hook-manager.d.ts.map +1 -0
- package/dist/services/agentic-flow-hooks/hook-manager.js +512 -0
- package/dist/services/agentic-flow-hooks/hook-manager.js.map +1 -0
- package/dist/services/agentic-flow-hooks/index.d.ts +36 -0
- package/dist/services/agentic-flow-hooks/index.d.ts.map +1 -0
- package/dist/services/agentic-flow-hooks/index.js +325 -0
- package/dist/services/agentic-flow-hooks/index.js.map +1 -0
- package/dist/services/agentic-flow-hooks/llm-hooks.d.ts +33 -0
- package/dist/services/agentic-flow-hooks/llm-hooks.d.ts.map +1 -0
- package/dist/services/agentic-flow-hooks/llm-hooks.js +415 -0
- package/dist/services/agentic-flow-hooks/llm-hooks.js.map +1 -0
- package/dist/services/agentic-flow-hooks/memory-hooks.d.ts +45 -0
- package/dist/services/agentic-flow-hooks/memory-hooks.d.ts.map +1 -0
- package/dist/services/agentic-flow-hooks/memory-hooks.js +532 -0
- package/dist/services/agentic-flow-hooks/memory-hooks.js.map +1 -0
- package/dist/services/agentic-flow-hooks/neural-hooks.d.ts +39 -0
- package/dist/services/agentic-flow-hooks/neural-hooks.d.ts.map +1 -0
- package/dist/services/agentic-flow-hooks/neural-hooks.js +561 -0
- package/dist/services/agentic-flow-hooks/neural-hooks.js.map +1 -0
- package/dist/services/agentic-flow-hooks/performance-hooks.d.ts +33 -0
- package/dist/services/agentic-flow-hooks/performance-hooks.d.ts.map +1 -0
- package/dist/services/agentic-flow-hooks/performance-hooks.js +621 -0
- package/dist/services/agentic-flow-hooks/performance-hooks.js.map +1 -0
- package/dist/services/agentic-flow-hooks/types.d.ts +379 -0
- package/dist/services/agentic-flow-hooks/types.d.ts.map +1 -0
- package/dist/services/agentic-flow-hooks/types.js +8 -0
- package/dist/services/agentic-flow-hooks/types.js.map +1 -0
- package/dist/services/agentic-flow-hooks/workflow-hooks.d.ts +39 -0
- package/dist/services/agentic-flow-hooks/workflow-hooks.d.ts.map +1 -0
- package/dist/services/agentic-flow-hooks/workflow-hooks.js +742 -0
- package/dist/services/agentic-flow-hooks/workflow-hooks.js.map +1 -0
- package/package.json +1 -1
- package/scripts/optimize-performance.js +400 -0
- package/scripts/performance-monitor.js +263 -0
- package/src/cli/help-text.js +1 -1
- package/src/cli/simple-cli.js +1 -1
- package/src/cli/simple-commands/hive-mind.js +1 -1
- package/src/providers/anthropic-provider.ts +282 -0
- package/src/providers/base-provider.ts +560 -0
- package/src/providers/cohere-provider.ts +521 -0
- package/src/providers/google-provider.ts +477 -0
- package/src/providers/index.ts +21 -0
- package/src/providers/ollama-provider.ts +489 -0
- package/src/providers/openai-provider.ts +476 -0
- package/src/providers/provider-manager.ts +654 -0
- package/src/providers/types.ts +531 -0
- package/src/providers/utils.ts +376 -0
- package/src/services/agentic-flow-hooks/hook-manager.ts +701 -0
- package/src/services/agentic-flow-hooks/index.ts +386 -0
- package/src/services/agentic-flow-hooks/llm-hooks.ts +557 -0
- package/src/services/agentic-flow-hooks/memory-hooks.ts +710 -0
- package/src/services/agentic-flow-hooks/neural-hooks.ts +758 -0
- package/src/services/agentic-flow-hooks/performance-hooks.ts +827 -0
- package/src/services/agentic-flow-hooks/types.ts +503 -0
- package/src/services/agentic-flow-hooks/workflow-hooks.ts +1026 -0
|
@@ -0,0 +1,827 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Performance optimization hooks for agentic-flow
|
|
3
|
+
*
|
|
4
|
+
* Tracks metrics, identifies bottlenecks, and provides
|
|
5
|
+
* optimization suggestions based on provider performance.
|
|
6
|
+
*/
|
|
7
|
+
|
|
8
|
+
import { agenticHookManager } from './hook-manager.js';
|
|
9
|
+
import type {
|
|
10
|
+
AgenticHookContext,
|
|
11
|
+
HookHandlerResult,
|
|
12
|
+
PerformanceHookPayload,
|
|
13
|
+
PerformanceMetric,
|
|
14
|
+
BottleneckAnalysis,
|
|
15
|
+
OptimizationSuggestion,
|
|
16
|
+
SideEffect,
|
|
17
|
+
} from './types.js';
|
|
18
|
+
|
|
19
|
+
// ===== Performance Metric Hook =====
|
|
20
|
+
|
|
21
|
+
export const performanceMetricHook = {
|
|
22
|
+
id: 'agentic-performance-metric',
|
|
23
|
+
type: 'performance-metric' as const,
|
|
24
|
+
priority: 100,
|
|
25
|
+
handler: async (
|
|
26
|
+
payload: PerformanceHookPayload,
|
|
27
|
+
context: AgenticHookContext
|
|
28
|
+
): Promise<HookHandlerResult> => {
|
|
29
|
+
const { metric, value, unit, threshold } = payload;
|
|
30
|
+
|
|
31
|
+
const sideEffects: SideEffect[] = [];
|
|
32
|
+
|
|
33
|
+
// Store metric
|
|
34
|
+
const metricData: PerformanceMetric = {
|
|
35
|
+
name: metric,
|
|
36
|
+
value,
|
|
37
|
+
unit,
|
|
38
|
+
timestamp: Date.now(),
|
|
39
|
+
tags: extractTags(payload.context),
|
|
40
|
+
};
|
|
41
|
+
|
|
42
|
+
context.performance.metrics.set(metric, metricData);
|
|
43
|
+
|
|
44
|
+
// Check threshold violations
|
|
45
|
+
if (threshold !== undefined) {
|
|
46
|
+
const violated = checkThreshold(value, threshold, payload.context);
|
|
47
|
+
|
|
48
|
+
if (violated) {
|
|
49
|
+
sideEffects.push({
|
|
50
|
+
type: 'notification',
|
|
51
|
+
action: 'emit',
|
|
52
|
+
data: {
|
|
53
|
+
event: 'performance:threshold:violated',
|
|
54
|
+
data: {
|
|
55
|
+
metric,
|
|
56
|
+
value,
|
|
57
|
+
threshold,
|
|
58
|
+
unit,
|
|
59
|
+
},
|
|
60
|
+
},
|
|
61
|
+
});
|
|
62
|
+
|
|
63
|
+
// Generate optimization suggestion
|
|
64
|
+
const suggestion = await generateOptimizationSuggestion(
|
|
65
|
+
metric,
|
|
66
|
+
value,
|
|
67
|
+
threshold,
|
|
68
|
+
context
|
|
69
|
+
);
|
|
70
|
+
|
|
71
|
+
if (suggestion) {
|
|
72
|
+
context.performance.optimizations.push(suggestion);
|
|
73
|
+
sideEffects.push({
|
|
74
|
+
type: 'log',
|
|
75
|
+
action: 'write',
|
|
76
|
+
data: {
|
|
77
|
+
level: 'info',
|
|
78
|
+
message: 'Optimization suggestion generated',
|
|
79
|
+
data: suggestion,
|
|
80
|
+
},
|
|
81
|
+
});
|
|
82
|
+
}
|
|
83
|
+
}
|
|
84
|
+
}
|
|
85
|
+
|
|
86
|
+
// Update rolling averages
|
|
87
|
+
await updateRollingAverages(metric, value, context);
|
|
88
|
+
|
|
89
|
+
// Detect anomalies
|
|
90
|
+
const anomaly = await detectAnomaly(metric, value, context);
|
|
91
|
+
if (anomaly) {
|
|
92
|
+
sideEffects.push({
|
|
93
|
+
type: 'notification',
|
|
94
|
+
action: 'emit',
|
|
95
|
+
data: {
|
|
96
|
+
event: 'performance:anomaly:detected',
|
|
97
|
+
data: { metric, value, anomaly },
|
|
98
|
+
},
|
|
99
|
+
});
|
|
100
|
+
}
|
|
101
|
+
|
|
102
|
+
return {
|
|
103
|
+
continue: true,
|
|
104
|
+
sideEffects,
|
|
105
|
+
};
|
|
106
|
+
},
|
|
107
|
+
};
|
|
108
|
+
|
|
109
|
+
// ===== Performance Bottleneck Hook =====
|
|
110
|
+
|
|
111
|
+
export const performanceBottleneckHook = {
|
|
112
|
+
id: 'agentic-performance-bottleneck',
|
|
113
|
+
type: 'performance-bottleneck' as const,
|
|
114
|
+
priority: 90,
|
|
115
|
+
handler: async (
|
|
116
|
+
payload: PerformanceHookPayload,
|
|
117
|
+
context: AgenticHookContext
|
|
118
|
+
): Promise<HookHandlerResult> => {
|
|
119
|
+
const { bottleneck } = payload;
|
|
120
|
+
|
|
121
|
+
if (!bottleneck) {
|
|
122
|
+
return { continue: true };
|
|
123
|
+
}
|
|
124
|
+
|
|
125
|
+
const sideEffects: SideEffect[] = [];
|
|
126
|
+
|
|
127
|
+
// Analyze bottleneck severity
|
|
128
|
+
const analysis: BottleneckAnalysis = {
|
|
129
|
+
component: bottleneck.location,
|
|
130
|
+
severity: mapSeverity(bottleneck.severity),
|
|
131
|
+
impact: bottleneck.severity / 10, // Normalize to 0-1
|
|
132
|
+
suggestions: bottleneck.suggestions,
|
|
133
|
+
};
|
|
134
|
+
|
|
135
|
+
context.performance.bottlenecks.push(analysis);
|
|
136
|
+
|
|
137
|
+
// Store for historical analysis
|
|
138
|
+
sideEffects.push({
|
|
139
|
+
type: 'memory',
|
|
140
|
+
action: 'store',
|
|
141
|
+
data: {
|
|
142
|
+
key: `bottleneck:${analysis.component}:${Date.now()}`,
|
|
143
|
+
value: analysis,
|
|
144
|
+
ttl: 86400, // 24 hours
|
|
145
|
+
},
|
|
146
|
+
});
|
|
147
|
+
|
|
148
|
+
// Check for recurring bottlenecks
|
|
149
|
+
const recurrence = await checkBottleneckRecurrence(
|
|
150
|
+
analysis.component,
|
|
151
|
+
context
|
|
152
|
+
);
|
|
153
|
+
|
|
154
|
+
if (recurrence.count > 3) {
|
|
155
|
+
// Recurring bottleneck - escalate
|
|
156
|
+
sideEffects.push({
|
|
157
|
+
type: 'notification',
|
|
158
|
+
action: 'emit',
|
|
159
|
+
data: {
|
|
160
|
+
event: 'performance:bottleneck:recurring',
|
|
161
|
+
data: {
|
|
162
|
+
component: analysis.component,
|
|
163
|
+
occurrences: recurrence.count,
|
|
164
|
+
timespan: recurrence.timespan,
|
|
165
|
+
},
|
|
166
|
+
},
|
|
167
|
+
});
|
|
168
|
+
|
|
169
|
+
// Generate advanced optimization
|
|
170
|
+
const optimization = await generateAdvancedOptimization(
|
|
171
|
+
analysis,
|
|
172
|
+
recurrence,
|
|
173
|
+
context
|
|
174
|
+
);
|
|
175
|
+
|
|
176
|
+
if (optimization) {
|
|
177
|
+
context.performance.optimizations.push(optimization);
|
|
178
|
+
}
|
|
179
|
+
}
|
|
180
|
+
|
|
181
|
+
// Correlate with other metrics
|
|
182
|
+
const correlations = await findMetricCorrelations(
|
|
183
|
+
analysis.component,
|
|
184
|
+
context
|
|
185
|
+
);
|
|
186
|
+
|
|
187
|
+
if (correlations.length > 0) {
|
|
188
|
+
sideEffects.push({
|
|
189
|
+
type: 'log',
|
|
190
|
+
action: 'write',
|
|
191
|
+
data: {
|
|
192
|
+
level: 'info',
|
|
193
|
+
message: 'Bottleneck correlations found',
|
|
194
|
+
data: { bottleneck: analysis, correlations },
|
|
195
|
+
},
|
|
196
|
+
});
|
|
197
|
+
}
|
|
198
|
+
|
|
199
|
+
return {
|
|
200
|
+
continue: true,
|
|
201
|
+
sideEffects,
|
|
202
|
+
};
|
|
203
|
+
},
|
|
204
|
+
};
|
|
205
|
+
|
|
206
|
+
// ===== Performance Optimization Hook =====
|
|
207
|
+
|
|
208
|
+
export const performanceOptimizationHook = {
|
|
209
|
+
id: 'agentic-performance-optimization',
|
|
210
|
+
type: 'performance-optimization' as const,
|
|
211
|
+
priority: 80,
|
|
212
|
+
handler: async (
|
|
213
|
+
payload: PerformanceHookPayload,
|
|
214
|
+
context: AgenticHookContext
|
|
215
|
+
): Promise<HookHandlerResult> => {
|
|
216
|
+
const { optimization } = payload;
|
|
217
|
+
|
|
218
|
+
if (!optimization) {
|
|
219
|
+
return { continue: true };
|
|
220
|
+
}
|
|
221
|
+
|
|
222
|
+
const sideEffects: SideEffect[] = [];
|
|
223
|
+
|
|
224
|
+
// Validate optimization
|
|
225
|
+
const validation = await validateOptimization(optimization, context);
|
|
226
|
+
if (!validation.valid) {
|
|
227
|
+
sideEffects.push({
|
|
228
|
+
type: 'log',
|
|
229
|
+
action: 'write',
|
|
230
|
+
data: {
|
|
231
|
+
level: 'warning',
|
|
232
|
+
message: 'Optimization validation failed',
|
|
233
|
+
data: { optimization, validation },
|
|
234
|
+
},
|
|
235
|
+
});
|
|
236
|
+
return { continue: true, sideEffects };
|
|
237
|
+
}
|
|
238
|
+
|
|
239
|
+
// Simulate optimization impact
|
|
240
|
+
const simulation = await simulateOptimization(optimization, context);
|
|
241
|
+
|
|
242
|
+
if (simulation.expectedImprovement < 0.1) {
|
|
243
|
+
// Low impact - skip
|
|
244
|
+
return { continue: true };
|
|
245
|
+
}
|
|
246
|
+
|
|
247
|
+
// Store optimization recommendation
|
|
248
|
+
const recommendation = {
|
|
249
|
+
optimization,
|
|
250
|
+
simulation,
|
|
251
|
+
timestamp: Date.now(),
|
|
252
|
+
autoApply: optimization.applied && simulation.risk === 'low',
|
|
253
|
+
};
|
|
254
|
+
|
|
255
|
+
sideEffects.push({
|
|
256
|
+
type: 'memory',
|
|
257
|
+
action: 'store',
|
|
258
|
+
data: {
|
|
259
|
+
key: `optimization:${optimization.type}:${Date.now()}`,
|
|
260
|
+
value: recommendation,
|
|
261
|
+
ttl: 604800, // 7 days
|
|
262
|
+
},
|
|
263
|
+
});
|
|
264
|
+
|
|
265
|
+
// Auto-apply low-risk optimizations
|
|
266
|
+
if (recommendation.autoApply) {
|
|
267
|
+
await applyOptimization(optimization, context);
|
|
268
|
+
|
|
269
|
+
sideEffects.push({
|
|
270
|
+
type: 'notification',
|
|
271
|
+
action: 'emit',
|
|
272
|
+
data: {
|
|
273
|
+
event: 'performance:optimization:applied',
|
|
274
|
+
data: { optimization, automatic: true },
|
|
275
|
+
},
|
|
276
|
+
});
|
|
277
|
+
} else {
|
|
278
|
+
// Queue for manual review
|
|
279
|
+
sideEffects.push({
|
|
280
|
+
type: 'notification',
|
|
281
|
+
action: 'emit',
|
|
282
|
+
data: {
|
|
283
|
+
event: 'performance:optimization:suggested',
|
|
284
|
+
data: { optimization, simulation },
|
|
285
|
+
},
|
|
286
|
+
});
|
|
287
|
+
}
|
|
288
|
+
|
|
289
|
+
return {
|
|
290
|
+
continue: true,
|
|
291
|
+
sideEffects,
|
|
292
|
+
};
|
|
293
|
+
},
|
|
294
|
+
};
|
|
295
|
+
|
|
296
|
+
// ===== Performance Threshold Hook =====
|
|
297
|
+
|
|
298
|
+
export const performanceThresholdHook = {
|
|
299
|
+
id: 'agentic-performance-threshold',
|
|
300
|
+
type: 'performance-threshold' as const,
|
|
301
|
+
priority: 95,
|
|
302
|
+
handler: async (
|
|
303
|
+
payload: PerformanceHookPayload,
|
|
304
|
+
context: AgenticHookContext
|
|
305
|
+
): Promise<HookHandlerResult> => {
|
|
306
|
+
const { metric, value, threshold } = payload;
|
|
307
|
+
|
|
308
|
+
if (threshold === undefined) {
|
|
309
|
+
return { continue: true };
|
|
310
|
+
}
|
|
311
|
+
|
|
312
|
+
const sideEffects: SideEffect[] = [];
|
|
313
|
+
|
|
314
|
+
// Dynamic threshold adjustment
|
|
315
|
+
const historicalData = await getMetricHistory(metric, context);
|
|
316
|
+
const adjustedThreshold = calculateDynamicThreshold(
|
|
317
|
+
threshold,
|
|
318
|
+
historicalData
|
|
319
|
+
);
|
|
320
|
+
|
|
321
|
+
if (adjustedThreshold !== threshold) {
|
|
322
|
+
sideEffects.push({
|
|
323
|
+
type: 'log',
|
|
324
|
+
action: 'write',
|
|
325
|
+
data: {
|
|
326
|
+
level: 'info',
|
|
327
|
+
message: 'Threshold dynamically adjusted',
|
|
328
|
+
data: {
|
|
329
|
+
metric,
|
|
330
|
+
original: threshold,
|
|
331
|
+
adjusted: adjustedThreshold,
|
|
332
|
+
},
|
|
333
|
+
},
|
|
334
|
+
});
|
|
335
|
+
}
|
|
336
|
+
|
|
337
|
+
// Predict threshold violations
|
|
338
|
+
const prediction = await predictThresholdViolation(
|
|
339
|
+
metric,
|
|
340
|
+
value,
|
|
341
|
+
adjustedThreshold,
|
|
342
|
+
historicalData
|
|
343
|
+
);
|
|
344
|
+
|
|
345
|
+
if (prediction.willViolate && prediction.confidence > 0.7) {
|
|
346
|
+
sideEffects.push({
|
|
347
|
+
type: 'notification',
|
|
348
|
+
action: 'emit',
|
|
349
|
+
data: {
|
|
350
|
+
event: 'performance:threshold:predicted',
|
|
351
|
+
data: {
|
|
352
|
+
metric,
|
|
353
|
+
currentValue: value,
|
|
354
|
+
threshold: adjustedThreshold,
|
|
355
|
+
predictedTime: prediction.timeToViolation,
|
|
356
|
+
confidence: prediction.confidence,
|
|
357
|
+
},
|
|
358
|
+
},
|
|
359
|
+
});
|
|
360
|
+
|
|
361
|
+
// Proactive optimization
|
|
362
|
+
const proactiveOpt = await generateProactiveOptimization(
|
|
363
|
+
metric,
|
|
364
|
+
prediction,
|
|
365
|
+
context
|
|
366
|
+
);
|
|
367
|
+
|
|
368
|
+
if (proactiveOpt) {
|
|
369
|
+
context.performance.optimizations.push(proactiveOpt);
|
|
370
|
+
}
|
|
371
|
+
}
|
|
372
|
+
|
|
373
|
+
return {
|
|
374
|
+
continue: true,
|
|
375
|
+
sideEffects,
|
|
376
|
+
};
|
|
377
|
+
},
|
|
378
|
+
};
|
|
379
|
+
|
|
380
|
+
// ===== Helper Functions =====
|
|
381
|
+
|
|
382
|
+
function extractTags(context: Record<string, any>): string[] {
|
|
383
|
+
const tags: string[] = [];
|
|
384
|
+
|
|
385
|
+
if (context.provider) tags.push(`provider:${context.provider}`);
|
|
386
|
+
if (context.model) tags.push(`model:${context.model}`);
|
|
387
|
+
if (context.operation) tags.push(`op:${context.operation}`);
|
|
388
|
+
if (context.component) tags.push(`component:${context.component}`);
|
|
389
|
+
|
|
390
|
+
return tags;
|
|
391
|
+
}
|
|
392
|
+
|
|
393
|
+
function checkThreshold(
|
|
394
|
+
value: number,
|
|
395
|
+
threshold: number,
|
|
396
|
+
context: Record<string, any>
|
|
397
|
+
): boolean {
|
|
398
|
+
// Check if threshold is violated based on context
|
|
399
|
+
const operator = context.thresholdOperator || 'gt';
|
|
400
|
+
|
|
401
|
+
switch (operator) {
|
|
402
|
+
case 'gt': return value > threshold;
|
|
403
|
+
case 'gte': return value >= threshold;
|
|
404
|
+
case 'lt': return value < threshold;
|
|
405
|
+
case 'lte': return value <= threshold;
|
|
406
|
+
case 'eq': return value === threshold;
|
|
407
|
+
case 'ne': return value !== threshold;
|
|
408
|
+
default: return value > threshold;
|
|
409
|
+
}
|
|
410
|
+
}
|
|
411
|
+
|
|
412
|
+
async function generateOptimizationSuggestion(
|
|
413
|
+
metric: string,
|
|
414
|
+
value: number,
|
|
415
|
+
threshold: number,
|
|
416
|
+
context: AgenticHookContext
|
|
417
|
+
): Promise<OptimizationSuggestion | null> {
|
|
418
|
+
// Generate optimization based on metric type
|
|
419
|
+
const metricType = getMetricType(metric);
|
|
420
|
+
|
|
421
|
+
switch (metricType) {
|
|
422
|
+
case 'latency':
|
|
423
|
+
if (value > threshold * 2) {
|
|
424
|
+
return {
|
|
425
|
+
type: 'cache',
|
|
426
|
+
target: metric,
|
|
427
|
+
expectedImprovement: 50,
|
|
428
|
+
implementation: 'Enable response caching for frequently accessed data',
|
|
429
|
+
risk: 'low',
|
|
430
|
+
};
|
|
431
|
+
} else if (value > threshold * 1.5) {
|
|
432
|
+
return {
|
|
433
|
+
type: 'parallel',
|
|
434
|
+
target: metric,
|
|
435
|
+
expectedImprovement: 30,
|
|
436
|
+
implementation: 'Parallelize independent operations',
|
|
437
|
+
risk: 'medium',
|
|
438
|
+
};
|
|
439
|
+
}
|
|
440
|
+
break;
|
|
441
|
+
|
|
442
|
+
case 'throughput':
|
|
443
|
+
if (value < threshold * 0.5) {
|
|
444
|
+
return {
|
|
445
|
+
type: 'batch',
|
|
446
|
+
target: metric,
|
|
447
|
+
expectedImprovement: 40,
|
|
448
|
+
implementation: 'Batch similar requests together',
|
|
449
|
+
risk: 'low',
|
|
450
|
+
};
|
|
451
|
+
}
|
|
452
|
+
break;
|
|
453
|
+
|
|
454
|
+
case 'memory':
|
|
455
|
+
if (value > threshold * 0.9) {
|
|
456
|
+
return {
|
|
457
|
+
type: 'resource',
|
|
458
|
+
target: metric,
|
|
459
|
+
expectedImprovement: 20,
|
|
460
|
+
implementation: 'Implement memory pooling and recycling',
|
|
461
|
+
risk: 'medium',
|
|
462
|
+
};
|
|
463
|
+
}
|
|
464
|
+
break;
|
|
465
|
+
}
|
|
466
|
+
|
|
467
|
+
return null;
|
|
468
|
+
}
|
|
469
|
+
|
|
470
|
+
async function updateRollingAverages(
|
|
471
|
+
metric: string,
|
|
472
|
+
value: number,
|
|
473
|
+
context: AgenticHookContext
|
|
474
|
+
): Promise<void> {
|
|
475
|
+
const avgKey = `avg:${metric}`;
|
|
476
|
+
const history = await context.memory.cache.get(avgKey) || [];
|
|
477
|
+
|
|
478
|
+
history.push({ value, timestamp: Date.now() });
|
|
479
|
+
|
|
480
|
+
// Keep last 1000 values
|
|
481
|
+
if (history.length > 1000) {
|
|
482
|
+
history.shift();
|
|
483
|
+
}
|
|
484
|
+
|
|
485
|
+
await context.memory.cache.set(avgKey, history);
|
|
486
|
+
}
|
|
487
|
+
|
|
488
|
+
async function detectAnomaly(
|
|
489
|
+
metric: string,
|
|
490
|
+
value: number,
|
|
491
|
+
context: AgenticHookContext
|
|
492
|
+
): Promise<any | null> {
|
|
493
|
+
const avgKey = `avg:${metric}`;
|
|
494
|
+
const history = await context.memory.cache.get(avgKey) || [];
|
|
495
|
+
|
|
496
|
+
if (history.length < 100) {
|
|
497
|
+
return null; // Not enough data
|
|
498
|
+
}
|
|
499
|
+
|
|
500
|
+
// Calculate statistics
|
|
501
|
+
const values = history.map((h: any) => h.value);
|
|
502
|
+
const mean = values.reduce((a: number, b: number) => a + b, 0) / values.length;
|
|
503
|
+
const variance = values.reduce((a: number, b: number) =>
|
|
504
|
+
a + Math.pow(b - mean, 2), 0
|
|
505
|
+
) / values.length;
|
|
506
|
+
const stdDev = Math.sqrt(variance);
|
|
507
|
+
|
|
508
|
+
// Check if value is anomalous (> 3 standard deviations)
|
|
509
|
+
const zScore = Math.abs((value - mean) / stdDev);
|
|
510
|
+
|
|
511
|
+
if (zScore > 3) {
|
|
512
|
+
return {
|
|
513
|
+
type: 'statistical',
|
|
514
|
+
zScore,
|
|
515
|
+
mean,
|
|
516
|
+
stdDev,
|
|
517
|
+
severity: zScore > 5 ? 'high' : 'medium',
|
|
518
|
+
};
|
|
519
|
+
}
|
|
520
|
+
|
|
521
|
+
return null;
|
|
522
|
+
}
|
|
523
|
+
|
|
524
|
+
function mapSeverity(severity: number): BottleneckAnalysis['severity'] {
|
|
525
|
+
if (severity >= 8) return 'critical';
|
|
526
|
+
if (severity >= 6) return 'high';
|
|
527
|
+
if (severity >= 4) return 'medium';
|
|
528
|
+
return 'low';
|
|
529
|
+
}
|
|
530
|
+
|
|
531
|
+
async function checkBottleneckRecurrence(
|
|
532
|
+
component: string,
|
|
533
|
+
context: AgenticHookContext
|
|
534
|
+
): Promise<{ count: number; timespan: number }> {
|
|
535
|
+
const historyKey = `bottleneck:history:${component}`;
|
|
536
|
+
const history = await context.memory.cache.get(historyKey) || [];
|
|
537
|
+
|
|
538
|
+
const now = Date.now();
|
|
539
|
+
const dayAgo = now - 86400000;
|
|
540
|
+
|
|
541
|
+
// Count occurrences in last 24 hours
|
|
542
|
+
const recentOccurrences = history.filter((h: any) =>
|
|
543
|
+
h.timestamp > dayAgo
|
|
544
|
+
);
|
|
545
|
+
|
|
546
|
+
return {
|
|
547
|
+
count: recentOccurrences.length,
|
|
548
|
+
timespan: 86400000, // 24 hours in ms
|
|
549
|
+
};
|
|
550
|
+
}
|
|
551
|
+
|
|
552
|
+
async function generateAdvancedOptimization(
|
|
553
|
+
bottleneck: BottleneckAnalysis,
|
|
554
|
+
recurrence: { count: number; timespan: number },
|
|
555
|
+
context: AgenticHookContext
|
|
556
|
+
): Promise<OptimizationSuggestion | null> {
|
|
557
|
+
// Generate advanced optimization for recurring bottlenecks
|
|
558
|
+
if (bottleneck.severity === 'critical' && recurrence.count > 5) {
|
|
559
|
+
return {
|
|
560
|
+
type: 'algorithm',
|
|
561
|
+
target: bottleneck.component,
|
|
562
|
+
expectedImprovement: 60,
|
|
563
|
+
implementation: `Redesign ${bottleneck.component} algorithm for better scalability`,
|
|
564
|
+
risk: 'high',
|
|
565
|
+
};
|
|
566
|
+
}
|
|
567
|
+
|
|
568
|
+
if (bottleneck.severity === 'high' && recurrence.count > 3) {
|
|
569
|
+
return {
|
|
570
|
+
type: 'cache',
|
|
571
|
+
target: bottleneck.component,
|
|
572
|
+
expectedImprovement: 40,
|
|
573
|
+
implementation: `Implement distributed caching for ${bottleneck.component}`,
|
|
574
|
+
risk: 'medium',
|
|
575
|
+
};
|
|
576
|
+
}
|
|
577
|
+
|
|
578
|
+
return null;
|
|
579
|
+
}
|
|
580
|
+
|
|
581
|
+
async function findMetricCorrelations(
|
|
582
|
+
component: string,
|
|
583
|
+
context: AgenticHookContext
|
|
584
|
+
): Promise<Array<{ metric: string; correlation: number }>> {
|
|
585
|
+
const correlations: Array<{ metric: string; correlation: number }> = [];
|
|
586
|
+
|
|
587
|
+
// Check correlations with other metrics
|
|
588
|
+
for (const [metric, data] of context.performance.metrics) {
|
|
589
|
+
if (data.tags.includes(`component:${component}`)) {
|
|
590
|
+
// Simple correlation check
|
|
591
|
+
correlations.push({
|
|
592
|
+
metric: data.name,
|
|
593
|
+
correlation: 0.7, // Placeholder
|
|
594
|
+
});
|
|
595
|
+
}
|
|
596
|
+
}
|
|
597
|
+
|
|
598
|
+
return correlations;
|
|
599
|
+
}
|
|
600
|
+
|
|
601
|
+
async function validateOptimization(
|
|
602
|
+
optimization: any,
|
|
603
|
+
context: AgenticHookContext
|
|
604
|
+
): Promise<{ valid: boolean; reason?: string }> {
|
|
605
|
+
// Validate optimization is safe to apply
|
|
606
|
+
if (!optimization.type || !optimization.details) {
|
|
607
|
+
return {
|
|
608
|
+
valid: false,
|
|
609
|
+
reason: 'Missing required optimization fields',
|
|
610
|
+
};
|
|
611
|
+
}
|
|
612
|
+
|
|
613
|
+
// Check risk level
|
|
614
|
+
if (optimization.details === 'high' && !context.metadata.allowHighRisk) {
|
|
615
|
+
return {
|
|
616
|
+
valid: false,
|
|
617
|
+
reason: 'High-risk optimizations not allowed',
|
|
618
|
+
};
|
|
619
|
+
}
|
|
620
|
+
|
|
621
|
+
return { valid: true };
|
|
622
|
+
}
|
|
623
|
+
|
|
624
|
+
async function simulateOptimization(
|
|
625
|
+
optimization: any,
|
|
626
|
+
context: AgenticHookContext
|
|
627
|
+
): Promise<any> {
|
|
628
|
+
// Simulate optimization impact
|
|
629
|
+
const baseline = await getBaselineMetrics(optimization.type, context);
|
|
630
|
+
|
|
631
|
+
const simulation = {
|
|
632
|
+
expectedImprovement: optimization.improvement || 0.2,
|
|
633
|
+
risk: calculateRisk(optimization),
|
|
634
|
+
affectedMetrics: identifyAffectedMetrics(optimization),
|
|
635
|
+
rollbackPlan: generateRollbackPlan(optimization),
|
|
636
|
+
};
|
|
637
|
+
|
|
638
|
+
return simulation;
|
|
639
|
+
}
|
|
640
|
+
|
|
641
|
+
async function applyOptimization(
|
|
642
|
+
optimization: any,
|
|
643
|
+
context: AgenticHookContext
|
|
644
|
+
): Promise<void> {
|
|
645
|
+
// Apply optimization
|
|
646
|
+
// Placeholder implementation
|
|
647
|
+
const timestamp = Date.now();
|
|
648
|
+
|
|
649
|
+
// Store optimization application
|
|
650
|
+
await context.memory.cache.set(
|
|
651
|
+
`applied:${optimization.type}:${timestamp}`,
|
|
652
|
+
{
|
|
653
|
+
optimization,
|
|
654
|
+
appliedAt: timestamp,
|
|
655
|
+
appliedBy: 'automatic',
|
|
656
|
+
}
|
|
657
|
+
);
|
|
658
|
+
}
|
|
659
|
+
|
|
660
|
+
async function getMetricHistory(
|
|
661
|
+
metric: string,
|
|
662
|
+
context: AgenticHookContext
|
|
663
|
+
): Promise<any[]> {
|
|
664
|
+
const historyKey = `history:${metric}`;
|
|
665
|
+
return await context.memory.cache.get(historyKey) || [];
|
|
666
|
+
}
|
|
667
|
+
|
|
668
|
+
function calculateDynamicThreshold(
|
|
669
|
+
baseThreshold: number,
|
|
670
|
+
historicalData: any[]
|
|
671
|
+
): number {
|
|
672
|
+
if (historicalData.length < 50) {
|
|
673
|
+
return baseThreshold; // Not enough data
|
|
674
|
+
}
|
|
675
|
+
|
|
676
|
+
// Calculate percentile-based threshold
|
|
677
|
+
const values = historicalData
|
|
678
|
+
.map(d => d.value)
|
|
679
|
+
.sort((a, b) => a - b);
|
|
680
|
+
|
|
681
|
+
const p95 = values[Math.floor(values.length * 0.95)];
|
|
682
|
+
|
|
683
|
+
// Adjust threshold based on historical performance
|
|
684
|
+
return Math.max(baseThreshold, p95 * 1.1);
|
|
685
|
+
}
|
|
686
|
+
|
|
687
|
+
async function predictThresholdViolation(
|
|
688
|
+
metric: string,
|
|
689
|
+
currentValue: number,
|
|
690
|
+
threshold: number,
|
|
691
|
+
historicalData: any[]
|
|
692
|
+
): Promise<any> {
|
|
693
|
+
if (historicalData.length < 10) {
|
|
694
|
+
return {
|
|
695
|
+
willViolate: false,
|
|
696
|
+
confidence: 0,
|
|
697
|
+
};
|
|
698
|
+
}
|
|
699
|
+
|
|
700
|
+
// Simple linear trend prediction
|
|
701
|
+
const recentValues = historicalData.slice(-10).map(d => d.value);
|
|
702
|
+
const trend = calculateTrend(recentValues);
|
|
703
|
+
|
|
704
|
+
if (trend > 0 && currentValue > threshold * 0.8) {
|
|
705
|
+
const timeToViolation = (threshold - currentValue) / trend;
|
|
706
|
+
|
|
707
|
+
return {
|
|
708
|
+
willViolate: true,
|
|
709
|
+
timeToViolation,
|
|
710
|
+
confidence: Math.min(trend * 10, 0.9),
|
|
711
|
+
};
|
|
712
|
+
}
|
|
713
|
+
|
|
714
|
+
return {
|
|
715
|
+
willViolate: false,
|
|
716
|
+
confidence: 0,
|
|
717
|
+
};
|
|
718
|
+
}
|
|
719
|
+
|
|
720
|
+
async function generateProactiveOptimization(
|
|
721
|
+
metric: string,
|
|
722
|
+
prediction: any,
|
|
723
|
+
context: AgenticHookContext
|
|
724
|
+
): Promise<OptimizationSuggestion | null> {
|
|
725
|
+
// Generate proactive optimization to prevent violation
|
|
726
|
+
const metricType = getMetricType(metric);
|
|
727
|
+
|
|
728
|
+
if (metricType === 'latency' && prediction.timeToViolation < 300000) {
|
|
729
|
+
return {
|
|
730
|
+
type: 'cache',
|
|
731
|
+
target: metric,
|
|
732
|
+
expectedImprovement: 30,
|
|
733
|
+
implementation: 'Preemptively cache high-latency operations',
|
|
734
|
+
risk: 'low',
|
|
735
|
+
};
|
|
736
|
+
}
|
|
737
|
+
|
|
738
|
+
return null;
|
|
739
|
+
}
|
|
740
|
+
|
|
741
|
+
function getMetricType(metric: string): string {
|
|
742
|
+
if (metric.includes('latency')) return 'latency';
|
|
743
|
+
if (metric.includes('throughput')) return 'throughput';
|
|
744
|
+
if (metric.includes('memory')) return 'memory';
|
|
745
|
+
if (metric.includes('cpu')) return 'cpu';
|
|
746
|
+
return 'unknown';
|
|
747
|
+
}
|
|
748
|
+
|
|
749
|
+
async function getBaselineMetrics(
|
|
750
|
+
type: string,
|
|
751
|
+
context: AgenticHookContext
|
|
752
|
+
): Promise<any> {
|
|
753
|
+
// Get baseline metrics for comparison
|
|
754
|
+
// Placeholder implementation
|
|
755
|
+
return {};
|
|
756
|
+
}
|
|
757
|
+
|
|
758
|
+
function calculateRisk(optimization: any): string {
|
|
759
|
+
// Calculate optimization risk level
|
|
760
|
+
if (optimization.type === 'algorithm') return 'high';
|
|
761
|
+
if (optimization.type === 'architecture') return 'high';
|
|
762
|
+
if (optimization.type === 'cache') return 'low';
|
|
763
|
+
if (optimization.type === 'batch') return 'low';
|
|
764
|
+
return 'medium';
|
|
765
|
+
}
|
|
766
|
+
|
|
767
|
+
function identifyAffectedMetrics(optimization: any): string[] {
|
|
768
|
+
// Identify metrics affected by optimization
|
|
769
|
+
const affected: string[] = [];
|
|
770
|
+
|
|
771
|
+
switch (optimization.type) {
|
|
772
|
+
case 'cache':
|
|
773
|
+
affected.push('latency', 'memory_usage');
|
|
774
|
+
break;
|
|
775
|
+
case 'parallel':
|
|
776
|
+
affected.push('latency', 'cpu_usage', 'throughput');
|
|
777
|
+
break;
|
|
778
|
+
case 'batch':
|
|
779
|
+
affected.push('throughput', 'latency');
|
|
780
|
+
break;
|
|
781
|
+
case 'algorithm':
|
|
782
|
+
affected.push('latency', 'cpu_usage', 'memory_usage');
|
|
783
|
+
break;
|
|
784
|
+
}
|
|
785
|
+
|
|
786
|
+
return affected;
|
|
787
|
+
}
|
|
788
|
+
|
|
789
|
+
function generateRollbackPlan(optimization: any): any {
|
|
790
|
+
// Generate rollback plan
|
|
791
|
+
return {
|
|
792
|
+
steps: [
|
|
793
|
+
'Capture current metrics',
|
|
794
|
+
'Apply optimization',
|
|
795
|
+
'Monitor for 5 minutes',
|
|
796
|
+
'Rollback if metrics degrade',
|
|
797
|
+
],
|
|
798
|
+
triggers: {
|
|
799
|
+
errorRate: 0.05,
|
|
800
|
+
latencyIncrease: 1.5,
|
|
801
|
+
},
|
|
802
|
+
};
|
|
803
|
+
}
|
|
804
|
+
|
|
805
|
+
function calculateTrend(values: number[]): number {
|
|
806
|
+
if (values.length < 2) return 0;
|
|
807
|
+
|
|
808
|
+
// Simple linear regression
|
|
809
|
+
const n = values.length;
|
|
810
|
+
const sumX = values.reduce((a, _, i) => a + i, 0);
|
|
811
|
+
const sumY = values.reduce((a, b) => a + b, 0);
|
|
812
|
+
const sumXY = values.reduce((a, b, i) => a + i * b, 0);
|
|
813
|
+
const sumX2 = values.reduce((a, _, i) => a + i * i, 0);
|
|
814
|
+
|
|
815
|
+
const slope = (n * sumXY - sumX * sumY) / (n * sumX2 - sumX * sumX);
|
|
816
|
+
|
|
817
|
+
return slope;
|
|
818
|
+
}
|
|
819
|
+
|
|
820
|
+
// ===== Register Hooks =====
|
|
821
|
+
|
|
822
|
+
export function registerPerformanceHooks(): void {
|
|
823
|
+
agenticHookManager.register(performanceMetricHook);
|
|
824
|
+
agenticHookManager.register(performanceBottleneckHook);
|
|
825
|
+
agenticHookManager.register(performanceOptimizationHook);
|
|
826
|
+
agenticHookManager.register(performanceThresholdHook);
|
|
827
|
+
}
|