olympus-ai 3.3.0 → 3.4.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/.claude-plugin/marketplace.json +1 -1
- package/README.md +2 -0
- package/dist/__tests__/learning/aggregation.test.d.ts +2 -0
- package/dist/__tests__/learning/aggregation.test.d.ts.map +1 -0
- package/dist/__tests__/learning/aggregation.test.js +282 -0
- package/dist/__tests__/learning/aggregation.test.js.map +1 -0
- package/dist/__tests__/learning/anomaly.test.d.ts +2 -0
- package/dist/__tests__/learning/anomaly.test.d.ts.map +1 -0
- package/dist/__tests__/learning/anomaly.test.js +107 -0
- package/dist/__tests__/learning/anomaly.test.js.map +1 -0
- package/dist/__tests__/learning/baselines.test.d.ts +2 -0
- package/dist/__tests__/learning/baselines.test.d.ts.map +1 -0
- package/dist/__tests__/learning/baselines.test.js +155 -0
- package/dist/__tests__/learning/baselines.test.js.map +1 -0
- package/dist/__tests__/learning/efficiency.test.d.ts +2 -0
- package/dist/__tests__/learning/efficiency.test.d.ts.map +1 -0
- package/dist/__tests__/learning/efficiency.test.js +94 -0
- package/dist/__tests__/learning/efficiency.test.js.map +1 -0
- package/dist/__tests__/learning/feedback-loop-injection.test.d.ts +6 -0
- package/dist/__tests__/learning/feedback-loop-injection.test.d.ts.map +1 -0
- package/dist/__tests__/learning/feedback-loop-injection.test.js +288 -0
- package/dist/__tests__/learning/feedback-loop-injection.test.js.map +1 -0
- package/dist/__tests__/learning/learning-capture-integration.test.d.ts +6 -0
- package/dist/__tests__/learning/learning-capture-integration.test.d.ts.map +1 -0
- package/dist/__tests__/learning/learning-capture-integration.test.js +151 -0
- package/dist/__tests__/learning/learning-capture-integration.test.js.map +1 -0
- package/dist/__tests__/learning/token-metrics.test.d.ts +2 -0
- package/dist/__tests__/learning/token-metrics.test.d.ts.map +1 -0
- package/dist/__tests__/learning/token-metrics.test.js +308 -0
- package/dist/__tests__/learning/token-metrics.test.js.map +1 -0
- package/dist/__tests__/token-tracking-integration.test.d.ts +8 -0
- package/dist/__tests__/token-tracking-integration.test.d.ts.map +1 -0
- package/dist/__tests__/token-tracking-integration.test.js +669 -0
- package/dist/__tests__/token-tracking-integration.test.js.map +1 -0
- package/dist/cli/commands/metrics.d.ts +10 -2
- package/dist/cli/commands/metrics.d.ts.map +1 -1
- package/dist/cli/commands/metrics.js +25 -239
- package/dist/cli/commands/metrics.js.map +1 -1
- package/dist/cli/index.js +196 -1
- package/dist/cli/index.js.map +1 -1
- package/dist/config/loader.d.ts.map +1 -1
- package/dist/config/loader.js +14 -0
- package/dist/config/loader.js.map +1 -1
- package/dist/hooks/registrations/budget-warning.d.ts +8 -0
- package/dist/hooks/registrations/budget-warning.d.ts.map +1 -0
- package/dist/hooks/registrations/budget-warning.js +63 -0
- package/dist/hooks/registrations/budget-warning.js.map +1 -0
- package/dist/hooks/registrations/index.d.ts +3 -2
- package/dist/hooks/registrations/index.d.ts.map +1 -1
- package/dist/hooks/registrations/index.js +5 -3
- package/dist/hooks/registrations/index.js.map +1 -1
- package/dist/hooks/registrations/learning-capture.d.ts +19 -0
- package/dist/hooks/registrations/learning-capture.d.ts.map +1 -0
- package/dist/hooks/registrations/learning-capture.js +220 -0
- package/dist/hooks/registrations/learning-capture.js.map +1 -0
- package/dist/hooks/registrations/session-start.d.ts.map +1 -1
- package/dist/hooks/registrations/session-start.js +13 -0
- package/dist/hooks/registrations/session-start.js.map +1 -1
- package/dist/hooks/registrations/token-metrics.d.ts +10 -2
- package/dist/hooks/registrations/token-metrics.d.ts.map +1 -1
- package/dist/hooks/registrations/token-metrics.js +18 -4
- package/dist/hooks/registrations/token-metrics.js.map +1 -1
- package/dist/installer/index.d.ts +1 -1
- package/dist/installer/index.d.ts.map +1 -1
- package/dist/installer/index.js +56 -0
- package/dist/installer/index.js.map +1 -1
- package/dist/learning/aggregation.d.ts +39 -0
- package/dist/learning/aggregation.d.ts.map +1 -0
- package/dist/learning/aggregation.js +101 -0
- package/dist/learning/aggregation.js.map +1 -0
- package/dist/learning/anomaly.d.ts +30 -0
- package/dist/learning/anomaly.d.ts.map +1 -0
- package/dist/learning/anomaly.js +102 -0
- package/dist/learning/anomaly.js.map +1 -0
- package/dist/learning/baselines.d.ts +44 -0
- package/dist/learning/baselines.d.ts.map +1 -0
- package/dist/learning/baselines.js +126 -0
- package/dist/learning/baselines.js.map +1 -0
- package/dist/learning/efficiency.d.ts +23 -0
- package/dist/learning/efficiency.d.ts.map +1 -0
- package/dist/learning/efficiency.js +67 -0
- package/dist/learning/efficiency.js.map +1 -0
- package/dist/learning/hooks/learned-context.d.ts.map +1 -1
- package/dist/learning/hooks/learned-context.js +46 -0
- package/dist/learning/hooks/learned-context.js.map +1 -1
- package/dist/learning/pricing.d.ts +30 -0
- package/dist/learning/pricing.d.ts.map +1 -0
- package/dist/learning/pricing.js +98 -0
- package/dist/learning/pricing.js.map +1 -0
- package/dist/learning/session-state.d.ts +12 -2
- package/dist/learning/session-state.d.ts.map +1 -1
- package/dist/learning/session-state.js +72 -3
- package/dist/learning/session-state.js.map +1 -1
- package/dist/learning/storage.d.ts +21 -1
- package/dist/learning/storage.d.ts.map +1 -1
- package/dist/learning/storage.js +84 -0
- package/dist/learning/storage.js.map +1 -1
- package/dist/learning/token-estimator.d.ts +41 -0
- package/dist/learning/token-estimator.d.ts.map +1 -0
- package/dist/learning/token-estimator.js +111 -0
- package/dist/learning/token-estimator.js.map +1 -0
- package/dist/learning/types.d.ts +32 -0
- package/dist/learning/types.d.ts.map +1 -1
- package/dist/learning/utils.d.ts +42 -0
- package/dist/learning/utils.d.ts.map +1 -0
- package/dist/learning/utils.js +76 -0
- package/dist/learning/utils.js.map +1 -0
- package/dist/shared/types.d.ts +29 -0
- package/dist/shared/types.d.ts.map +1 -1
- package/package.json +1 -1
- package/scripts/dist/hooks/olympus-hooks.cjs +86 -84
|
@@ -9,7 +9,7 @@
|
|
|
9
9
|
{
|
|
10
10
|
"name": "olympus-ai",
|
|
11
11
|
"description": "Multi-agent orchestration with intelligent model routing, The Ascent persistence loop, and specialized agents. Summon the gods of code.",
|
|
12
|
-
"version": "
|
|
12
|
+
"version": "3.4.0",
|
|
13
13
|
"author": {
|
|
14
14
|
"name": "mikev10"
|
|
15
15
|
},
|
package/README.md
CHANGED
|
@@ -45,6 +45,7 @@ Olympus transforms Claude Code from a single agent into a **pantheon of speciali
|
|
|
45
45
|
- **Pattern Extraction** - Identifies recurring feedback and adapts behavior accordingly
|
|
46
46
|
- **Preference Learning** - Infers your communication style (concise vs. detailed, autonomous vs. collaborative)
|
|
47
47
|
- **Agent Performance Tracking** - Monitors which agents succeed or fail for specific tasks
|
|
48
|
+
- **Token Efficiency Tracking** - Automatically tracks token usage per agent to optimize cost without manual intervention
|
|
48
49
|
- **Discovery Storage** - Structured JSONL storage with verification tracking and confidence scoring
|
|
49
50
|
- **Context Injection** - Learned preferences and discoveries are automatically applied in new sessions
|
|
50
51
|
|
|
@@ -79,6 +80,7 @@ Olympus transforms Claude Code from a single agent into a **pantheon of speciali
|
|
|
79
80
|
| **Task Persistence** | Stops when asked | Continues until verified complete |
|
|
80
81
|
| **Background Tasks** | Blocks waiting | Runs async with notifications |
|
|
81
82
|
| **Agent Specialization** | Generic responses | 20+ experts for specific domains |
|
|
83
|
+
| **Token Awareness** | Manual tracking | Automatic efficiency guidance |
|
|
82
84
|
|
|
83
85
|
---
|
|
84
86
|
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"aggregation.test.d.ts","sourceRoot":"","sources":["../../../src/__tests__/learning/aggregation.test.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1,282 @@
|
|
|
1
|
+
import { describe, it, expect } from 'vitest';
|
|
2
|
+
import { updateAgentTokenEfficiency, extractTokens, wasSuccessful, hasMinimumSamples } from '../../learning/aggregation.js';
|
|
3
|
+
describe('updateAgentTokenEfficiency', () => {
|
|
4
|
+
const basePerformance = {
|
|
5
|
+
agent_name: 'oracle-low',
|
|
6
|
+
total_invocations: 10,
|
|
7
|
+
success_count: 8,
|
|
8
|
+
revision_count: 1,
|
|
9
|
+
cancellation_count: 1,
|
|
10
|
+
success_rate: 0.8,
|
|
11
|
+
failure_patterns: [],
|
|
12
|
+
strong_areas: [],
|
|
13
|
+
weak_areas: [],
|
|
14
|
+
last_updated: new Date().toISOString()
|
|
15
|
+
};
|
|
16
|
+
it('should initialize token efficiency for new agent', () => {
|
|
17
|
+
const result = updateAgentTokenEfficiency(basePerformance, 5000, true, 10000);
|
|
18
|
+
expect(result.token_efficiency).toBeDefined();
|
|
19
|
+
expect(result.token_efficiency?.avg_tokens_per_success).toBe(5000);
|
|
20
|
+
expect(result.token_efficiency?.avg_tokens_per_failure).toBe(0);
|
|
21
|
+
expect(result.token_efficiency?.total_tokens).toBe(5000);
|
|
22
|
+
expect(result.token_efficiency?.invocation_count).toBe(1);
|
|
23
|
+
expect(result.token_efficiency?.trend).toBe('insufficient_data');
|
|
24
|
+
});
|
|
25
|
+
it('should initialize with failure tokens', () => {
|
|
26
|
+
const result = updateAgentTokenEfficiency(basePerformance, 8000, false, 10000);
|
|
27
|
+
expect(result.token_efficiency?.avg_tokens_per_success).toBe(0);
|
|
28
|
+
expect(result.token_efficiency?.avg_tokens_per_failure).toBe(8000);
|
|
29
|
+
expect(result.token_efficiency?.total_tokens).toBe(8000);
|
|
30
|
+
});
|
|
31
|
+
it('should update existing efficiency with success', () => {
|
|
32
|
+
const performanceWithEfficiency = {
|
|
33
|
+
...basePerformance,
|
|
34
|
+
token_efficiency: {
|
|
35
|
+
avg_tokens_per_success: 5000,
|
|
36
|
+
avg_tokens_per_failure: 8000,
|
|
37
|
+
total_tokens: 10000,
|
|
38
|
+
invocation_count: 2,
|
|
39
|
+
efficiency_score: 1.2,
|
|
40
|
+
trend: 'insufficient_data'
|
|
41
|
+
}
|
|
42
|
+
};
|
|
43
|
+
const result = updateAgentTokenEfficiency(performanceWithEfficiency, 4000, true, 10000);
|
|
44
|
+
expect(result.token_efficiency?.invocation_count).toBe(3);
|
|
45
|
+
expect(result.token_efficiency?.total_tokens).toBe(14000);
|
|
46
|
+
// Avg should move toward 4000 using exponential moving average
|
|
47
|
+
expect(result.token_efficiency?.avg_tokens_per_success).toBeLessThan(5000);
|
|
48
|
+
});
|
|
49
|
+
it('should update existing efficiency with failure', () => {
|
|
50
|
+
const performanceWithEfficiency = {
|
|
51
|
+
...basePerformance,
|
|
52
|
+
token_efficiency: {
|
|
53
|
+
avg_tokens_per_success: 5000,
|
|
54
|
+
avg_tokens_per_failure: 8000,
|
|
55
|
+
total_tokens: 10000,
|
|
56
|
+
invocation_count: 2,
|
|
57
|
+
efficiency_score: 1.2,
|
|
58
|
+
trend: 'insufficient_data'
|
|
59
|
+
}
|
|
60
|
+
};
|
|
61
|
+
const result = updateAgentTokenEfficiency(performanceWithEfficiency, 10000, false, 10000);
|
|
62
|
+
expect(result.token_efficiency?.avg_tokens_per_failure).toBeGreaterThan(8000);
|
|
63
|
+
});
|
|
64
|
+
it('should calculate trend when sufficient samples', () => {
|
|
65
|
+
const performanceWithEfficiency = {
|
|
66
|
+
...basePerformance,
|
|
67
|
+
token_efficiency: {
|
|
68
|
+
avg_tokens_per_success: 5000,
|
|
69
|
+
avg_tokens_per_failure: 8000,
|
|
70
|
+
total_tokens: 24000,
|
|
71
|
+
invocation_count: 5, // Now at 5, will be 6 after update
|
|
72
|
+
efficiency_score: 1.2,
|
|
73
|
+
trend: 'insufficient_data'
|
|
74
|
+
}
|
|
75
|
+
};
|
|
76
|
+
const result = updateAgentTokenEfficiency(performanceWithEfficiency, 4000, true, 10000);
|
|
77
|
+
// Should now have sufficient data for trend
|
|
78
|
+
expect(result.token_efficiency?.trend).not.toBe('insufficient_data');
|
|
79
|
+
});
|
|
80
|
+
it('should recalculate efficiency score', () => {
|
|
81
|
+
const performanceWithEfficiency = {
|
|
82
|
+
...basePerformance,
|
|
83
|
+
token_efficiency: {
|
|
84
|
+
avg_tokens_per_success: 10000,
|
|
85
|
+
avg_tokens_per_failure: 15000,
|
|
86
|
+
total_tokens: 50000,
|
|
87
|
+
invocation_count: 5,
|
|
88
|
+
efficiency_score: 0.8,
|
|
89
|
+
trend: 'stable'
|
|
90
|
+
}
|
|
91
|
+
};
|
|
92
|
+
const result = updateAgentTokenEfficiency(performanceWithEfficiency, 5000, true, 10000);
|
|
93
|
+
// Efficiency should improve with lower tokens
|
|
94
|
+
expect(result.token_efficiency?.efficiency_score).toBeGreaterThan(0.8);
|
|
95
|
+
});
|
|
96
|
+
it('should throw on negative token count', () => {
|
|
97
|
+
expect(() => updateAgentTokenEfficiency(basePerformance, -5000, true, 10000))
|
|
98
|
+
.toThrow('Token count cannot be negative');
|
|
99
|
+
});
|
|
100
|
+
it('should preserve other performance fields', () => {
|
|
101
|
+
const result = updateAgentTokenEfficiency(basePerformance, 5000, true, 10000);
|
|
102
|
+
expect(result.agent_name).toBe(basePerformance.agent_name);
|
|
103
|
+
expect(result.success_rate).toBe(basePerformance.success_rate);
|
|
104
|
+
expect(result.total_invocations).toBe(basePerformance.total_invocations);
|
|
105
|
+
});
|
|
106
|
+
});
|
|
107
|
+
describe('extractTokens', () => {
|
|
108
|
+
it('should extract tokens from entry with token_usage', () => {
|
|
109
|
+
const entry = {
|
|
110
|
+
id: 'test-1',
|
|
111
|
+
timestamp: new Date().toISOString(),
|
|
112
|
+
session_id: 'session-1',
|
|
113
|
+
project_path: '/test/project',
|
|
114
|
+
event_type: 'success',
|
|
115
|
+
user_message: 'Test',
|
|
116
|
+
feedback_category: 'praise',
|
|
117
|
+
confidence: 1.0,
|
|
118
|
+
token_usage: {
|
|
119
|
+
input_tokens: 3000,
|
|
120
|
+
output_tokens: 2000,
|
|
121
|
+
total_tokens: 5000,
|
|
122
|
+
estimated: true
|
|
123
|
+
}
|
|
124
|
+
};
|
|
125
|
+
expect(extractTokens(entry)).toBe(5000);
|
|
126
|
+
});
|
|
127
|
+
it('should return 0 for entry without token_usage', () => {
|
|
128
|
+
const entry = {
|
|
129
|
+
id: 'test-1',
|
|
130
|
+
timestamp: new Date().toISOString(),
|
|
131
|
+
session_id: 'session-1',
|
|
132
|
+
project_path: '/test/project',
|
|
133
|
+
event_type: 'success',
|
|
134
|
+
user_message: 'Test',
|
|
135
|
+
feedback_category: 'praise',
|
|
136
|
+
confidence: 1.0
|
|
137
|
+
};
|
|
138
|
+
expect(extractTokens(entry)).toBe(0);
|
|
139
|
+
});
|
|
140
|
+
});
|
|
141
|
+
describe('wasSuccessful', () => {
|
|
142
|
+
it('should return true for success event', () => {
|
|
143
|
+
const entry = {
|
|
144
|
+
id: 'test-1',
|
|
145
|
+
timestamp: new Date().toISOString(),
|
|
146
|
+
session_id: 'session-1',
|
|
147
|
+
project_path: '/test/project',
|
|
148
|
+
event_type: 'success',
|
|
149
|
+
user_message: 'Test',
|
|
150
|
+
feedback_category: 'praise',
|
|
151
|
+
confidence: 1.0
|
|
152
|
+
};
|
|
153
|
+
expect(wasSuccessful(entry)).toBe(true);
|
|
154
|
+
});
|
|
155
|
+
it('should return true for explicit_preference event', () => {
|
|
156
|
+
const entry = {
|
|
157
|
+
id: 'test-1',
|
|
158
|
+
timestamp: new Date().toISOString(),
|
|
159
|
+
session_id: 'session-1',
|
|
160
|
+
project_path: '/test/project',
|
|
161
|
+
event_type: 'explicit_preference',
|
|
162
|
+
user_message: 'Test',
|
|
163
|
+
feedback_category: 'explicit_preference',
|
|
164
|
+
confidence: 1.0
|
|
165
|
+
};
|
|
166
|
+
expect(wasSuccessful(entry)).toBe(true);
|
|
167
|
+
});
|
|
168
|
+
it('should return false for revision event', () => {
|
|
169
|
+
const entry = {
|
|
170
|
+
id: 'test-1',
|
|
171
|
+
timestamp: new Date().toISOString(),
|
|
172
|
+
session_id: 'session-1',
|
|
173
|
+
project_path: '/test/project',
|
|
174
|
+
event_type: 'revision',
|
|
175
|
+
user_message: 'Test',
|
|
176
|
+
feedback_category: 'correction',
|
|
177
|
+
confidence: 1.0
|
|
178
|
+
};
|
|
179
|
+
expect(wasSuccessful(entry)).toBe(false);
|
|
180
|
+
});
|
|
181
|
+
it('should return false for cancellation event', () => {
|
|
182
|
+
const entry = {
|
|
183
|
+
id: 'test-1',
|
|
184
|
+
timestamp: new Date().toISOString(),
|
|
185
|
+
session_id: 'session-1',
|
|
186
|
+
project_path: '/test/project',
|
|
187
|
+
event_type: 'cancellation',
|
|
188
|
+
user_message: 'Test',
|
|
189
|
+
feedback_category: 'rejection',
|
|
190
|
+
confidence: 1.0
|
|
191
|
+
};
|
|
192
|
+
expect(wasSuccessful(entry)).toBe(false);
|
|
193
|
+
});
|
|
194
|
+
});
|
|
195
|
+
describe('hasMinimumSamples', () => {
|
|
196
|
+
it('should return false when no token efficiency data', () => {
|
|
197
|
+
const performance = {
|
|
198
|
+
agent_name: 'oracle-low',
|
|
199
|
+
total_invocations: 10,
|
|
200
|
+
success_count: 8,
|
|
201
|
+
revision_count: 1,
|
|
202
|
+
cancellation_count: 1,
|
|
203
|
+
success_rate: 0.8,
|
|
204
|
+
failure_patterns: [],
|
|
205
|
+
strong_areas: [],
|
|
206
|
+
weak_areas: [],
|
|
207
|
+
last_updated: new Date().toISOString()
|
|
208
|
+
};
|
|
209
|
+
expect(hasMinimumSamples(performance)).toBe(false);
|
|
210
|
+
});
|
|
211
|
+
it('should return false when invocation count < 5', () => {
|
|
212
|
+
const performance = {
|
|
213
|
+
agent_name: 'oracle-low',
|
|
214
|
+
total_invocations: 10,
|
|
215
|
+
success_count: 8,
|
|
216
|
+
revision_count: 1,
|
|
217
|
+
cancellation_count: 1,
|
|
218
|
+
success_rate: 0.8,
|
|
219
|
+
failure_patterns: [],
|
|
220
|
+
strong_areas: [],
|
|
221
|
+
weak_areas: [],
|
|
222
|
+
last_updated: new Date().toISOString(),
|
|
223
|
+
token_efficiency: {
|
|
224
|
+
avg_tokens_per_success: 5000,
|
|
225
|
+
avg_tokens_per_failure: 8000,
|
|
226
|
+
total_tokens: 20000,
|
|
227
|
+
invocation_count: 4,
|
|
228
|
+
efficiency_score: 1.2,
|
|
229
|
+
trend: 'insufficient_data'
|
|
230
|
+
}
|
|
231
|
+
};
|
|
232
|
+
expect(hasMinimumSamples(performance)).toBe(false);
|
|
233
|
+
});
|
|
234
|
+
it('should return true when invocation count >= 5', () => {
|
|
235
|
+
const performance = {
|
|
236
|
+
agent_name: 'oracle-low',
|
|
237
|
+
total_invocations: 10,
|
|
238
|
+
success_count: 8,
|
|
239
|
+
revision_count: 1,
|
|
240
|
+
cancellation_count: 1,
|
|
241
|
+
success_rate: 0.8,
|
|
242
|
+
failure_patterns: [],
|
|
243
|
+
strong_areas: [],
|
|
244
|
+
weak_areas: [],
|
|
245
|
+
last_updated: new Date().toISOString(),
|
|
246
|
+
token_efficiency: {
|
|
247
|
+
avg_tokens_per_success: 5000,
|
|
248
|
+
avg_tokens_per_failure: 8000,
|
|
249
|
+
total_tokens: 25000,
|
|
250
|
+
invocation_count: 5,
|
|
251
|
+
efficiency_score: 1.2,
|
|
252
|
+
trend: 'stable'
|
|
253
|
+
}
|
|
254
|
+
};
|
|
255
|
+
expect(hasMinimumSamples(performance)).toBe(true);
|
|
256
|
+
});
|
|
257
|
+
it('should use custom minimum samples', () => {
|
|
258
|
+
const performance = {
|
|
259
|
+
agent_name: 'oracle-low',
|
|
260
|
+
total_invocations: 10,
|
|
261
|
+
success_count: 8,
|
|
262
|
+
revision_count: 1,
|
|
263
|
+
cancellation_count: 1,
|
|
264
|
+
success_rate: 0.8,
|
|
265
|
+
failure_patterns: [],
|
|
266
|
+
strong_areas: [],
|
|
267
|
+
weak_areas: [],
|
|
268
|
+
last_updated: new Date().toISOString(),
|
|
269
|
+
token_efficiency: {
|
|
270
|
+
avg_tokens_per_success: 5000,
|
|
271
|
+
avg_tokens_per_failure: 8000,
|
|
272
|
+
total_tokens: 30000,
|
|
273
|
+
invocation_count: 7,
|
|
274
|
+
efficiency_score: 1.2,
|
|
275
|
+
trend: 'stable'
|
|
276
|
+
}
|
|
277
|
+
};
|
|
278
|
+
expect(hasMinimumSamples(performance, 10)).toBe(false);
|
|
279
|
+
expect(hasMinimumSamples(performance, 5)).toBe(true);
|
|
280
|
+
});
|
|
281
|
+
});
|
|
282
|
+
//# sourceMappingURL=aggregation.test.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"aggregation.test.js","sourceRoot":"","sources":["../../../src/__tests__/learning/aggregation.test.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,EAAE,EAAE,MAAM,EAAE,MAAM,QAAQ,CAAC;AAC9C,OAAO,EACL,0BAA0B,EAC1B,aAAa,EACb,aAAa,EACb,iBAAiB,EAClB,MAAM,+BAA+B,CAAC;AAGvC,QAAQ,CAAC,4BAA4B,EAAE,GAAG,EAAE;IAC1C,MAAM,eAAe,GAAqB;QACxC,UAAU,EAAE,YAAY;QACxB,iBAAiB,EAAE,EAAE;QACrB,aAAa,EAAE,CAAC;QAChB,cAAc,EAAE,CAAC;QACjB,kBAAkB,EAAE,CAAC;QACrB,YAAY,EAAE,GAAG;QACjB,gBAAgB,EAAE,EAAE;QACpB,YAAY,EAAE,EAAE;QAChB,UAAU,EAAE,EAAE;QACd,YAAY,EAAE,IAAI,IAAI,EAAE,CAAC,WAAW,EAAE;KACvC,CAAC;IAEF,EAAE,CAAC,kDAAkD,EAAE,GAAG,EAAE;QAC1D,MAAM,MAAM,GAAG,0BAA0B,CAAC,eAAe,EAAE,IAAI,EAAE,IAAI,EAAE,KAAK,CAAC,CAAC;QAE9E,MAAM,CAAC,MAAM,CAAC,gBAAgB,CAAC,CAAC,WAAW,EAAE,CAAC;QAC9C,MAAM,CAAC,MAAM,CAAC,gBAAgB,EAAE,sBAAsB,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;QACnE,MAAM,CAAC,MAAM,CAAC,gBAAgB,EAAE,sBAAsB,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;QAChE,MAAM,CAAC,MAAM,CAAC,gBAAgB,EAAE,YAAY,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;QACzD,MAAM,CAAC,MAAM,CAAC,gBAAgB,EAAE,gBAAgB,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;QAC1D,MAAM,CAAC,MAAM,CAAC,gBAAgB,EAAE,KAAK,CAAC,CAAC,IAAI,CAAC,mBAAmB,CAAC,CAAC;IACnE,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,uCAAuC,EAAE,GAAG,EAAE;QAC/C,MAAM,MAAM,GAAG,0BAA0B,CAAC,eAAe,EAAE,IAAI,EAAE,KAAK,EAAE,KAAK,CAAC,CAAC;QAE/E,MAAM,CAAC,MAAM,CAAC,gBAAgB,EAAE,sBAAsB,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;QAChE,MAAM,CAAC,MAAM,CAAC,gBAAgB,EAAE,sBAAsB,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;QACnE,MAAM,CAAC,MAAM,CAAC,gBAAgB,EAAE,YAAY,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;IAC3D,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,gDAAgD,EAAE,GAAG,EAAE;QACxD,MAAM,yBAAyB,GAAqB;YAClD,GAAG,eAAe;YAClB,gBAAgB,EAAE;gBAChB,sBAAsB,EAAE,IAAI;gBAC5B,sBAAsB,EAAE,IAAI;gBAC5B,YAAY,EAAE,KAAK;gBACnB,gBAAgB,EAAE,CAAC;gBACnB,gBAAgB,EAAE,GAAG;gBACrB,KAAK,EAAE,mBAAmB;aAC3B;SACF,CAAC;QAEF,MAAM,MAAM,GAAG,0BAA0B,CAAC,yBAAyB,EAAE,IAAI,EAAE,IAAI,EAAE,KAAK,CAAC,CAAC;QAExF,MAAM,CAAC,MAAM,CAAC,gBAAgB,EAAE,gBAAgB,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;QAC1D,MAAM,CAAC,MAAM,CAAC,gBAAgB,EAAE,YAAY,CAAC,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;QAC1D,+DAA+D;QAC/D,MAAM,CAAC,MAAM,CAAC,gBAAgB,EAAE,sBAAsB,CAAC,CAAC,YAAY,CAAC,IAAI,CAAC,CAAC;IAC7E,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,gDAAgD,EAAE,GAAG,EAAE;QACxD,MAAM,yBAAyB,GAAqB;YAClD,GAAG,eAAe;YAClB,gBAAgB,EAAE;gBAChB,sBAAsB,EAAE,IAAI;gBAC5B,sBAAsB,EAAE,IAAI;gBAC5B,YAAY,EAAE,KAAK;gBACnB,gBAAgB,EAAE,CAAC;gBACnB,gBAAgB,EAAE,GAAG;gBACrB,KAAK,EAAE,mBAAmB;aAC3B;SACF,CAAC;QAEF,MAAM,MAAM,GAAG,0BAA0B,CAAC,yBAAyB,EAAE,KAAK,EAAE,KAAK,EAAE,KAAK,CAAC,CAAC;QAE1F,MAAM,CAAC,MAAM,CAAC,gBAAgB,EAAE,sBAAsB,CAAC,CAAC,eAAe,CAAC,IAAI,CAAC,CAAC;IAChF,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,gDAAgD,EAAE,GAAG,EAAE;QACxD,MAAM,yBAAyB,GAAqB;YAClD,GAAG,eAAe;YAClB,gBAAgB,EAAE;gBAChB,sBAAsB,EAAE,IAAI;gBAC5B,sBAAsB,EAAE,IAAI;gBAC5B,YAAY,EAAE,KAAK;gBACnB,gBAAgB,EAAE,CAAC,EAAE,mCAAmC;gBACxD,gBAAgB,EAAE,GAAG;gBACrB,KAAK,EAAE,mBAAmB;aAC3B;SACF,CAAC;QAEF,MAAM,MAAM,GAAG,0BAA0B,CAAC,yBAAyB,EAAE,IAAI,EAAE,IAAI,EAAE,KAAK,CAAC,CAAC;QAExF,4CAA4C;QAC5C,MAAM,CAAC,MAAM,CAAC,gBAAgB,EAAE,KAAK,CAAC,CAAC,GAAG,CAAC,IAAI,CAAC,mBAAmB,CAAC,CAAC;IACvE,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,qCAAqC,EAAE,GAAG,EAAE;QAC7C,MAAM,yBAAyB,GAAqB;YAClD,GAAG,eAAe;YAClB,gBAAgB,EAAE;gBAChB,sBAAsB,EAAE,KAAK;gBAC7B,sBAAsB,EAAE,KAAK;gBAC7B,YAAY,EAAE,KAAK;gBACnB,gBAAgB,EAAE,CAAC;gBACnB,gBAAgB,EAAE,GAAG;gBACrB,KAAK,EAAE,QAAQ;aAChB;SACF,CAAC;QAEF,MAAM,MAAM,GAAG,0BAA0B,CAAC,yBAAyB,EAAE,IAAI,EAAE,IAAI,EAAE,KAAK,CAAC,CAAC;QAExF,8CAA8C;QAC9C,MAAM,CAAC,MAAM,CAAC,gBAAgB,EAAE,gBAAgB,CAAC,CAAC,eAAe,CAAC,GAAG,CAAC,CAAC;IACzE,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,sCAAsC,EAAE,GAAG,EAAE;QAC9C,MAAM,CAAC,GAAG,EAAE,CAAC,0BAA0B,CAAC,eAAe,EAAE,CAAC,IAAI,EAAE,IAAI,EAAE,KAAK,CAAC,CAAC;aAC1E,OAAO,CAAC,gCAAgC,CAAC,CAAC;IAC/C,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,0CAA0C,EAAE,GAAG,EAAE;QAClD,MAAM,MAAM,GAAG,0BAA0B,CAAC,eAAe,EAAE,IAAI,EAAE,IAAI,EAAE,KAAK,CAAC,CAAC;QAE9E,MAAM,CAAC,MAAM,CAAC,UAAU,CAAC,CAAC,IAAI,CAAC,eAAe,CAAC,UAAU,CAAC,CAAC;QAC3D,MAAM,CAAC,MAAM,CAAC,YAAY,CAAC,CAAC,IAAI,CAAC,eAAe,CAAC,YAAY,CAAC,CAAC;QAC/D,MAAM,CAAC,MAAM,CAAC,iBAAiB,CAAC,CAAC,IAAI,CAAC,eAAe,CAAC,iBAAiB,CAAC,CAAC;IAC3E,CAAC,CAAC,CAAC;AACL,CAAC,CAAC,CAAC;AAEH,QAAQ,CAAC,eAAe,EAAE,GAAG,EAAE;IAC7B,EAAE,CAAC,mDAAmD,EAAE,GAAG,EAAE;QAC3D,MAAM,KAAK,GAAkB;YAC3B,EAAE,EAAE,QAAQ;YACZ,SAAS,EAAE,IAAI,IAAI,EAAE,CAAC,WAAW,EAAE;YACnC,UAAU,EAAE,WAAW;YACvB,YAAY,EAAE,eAAe;YAC7B,UAAU,EAAE,SAAS;YACrB,YAAY,EAAE,MAAM;YACpB,iBAAiB,EAAE,QAAQ;YAC3B,UAAU,EAAE,GAAG;YACf,WAAW,EAAE;gBACX,YAAY,EAAE,IAAI;gBAClB,aAAa,EAAE,IAAI;gBACnB,YAAY,EAAE,IAAI;gBAClB,SAAS,EAAE,IAAI;aAChB;SACF,CAAC;QAEF,MAAM,CAAC,aAAa,CAAC,KAAK,CAAC,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;IAC1C,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,+CAA+C,EAAE,GAAG,EAAE;QACvD,MAAM,KAAK,GAAkB;YAC3B,EAAE,EAAE,QAAQ;YACZ,SAAS,EAAE,IAAI,IAAI,EAAE,CAAC,WAAW,EAAE;YACnC,UAAU,EAAE,WAAW;YACvB,YAAY,EAAE,eAAe;YAC7B,UAAU,EAAE,SAAS;YACrB,YAAY,EAAE,MAAM;YACpB,iBAAiB,EAAE,QAAQ;YAC3B,UAAU,EAAE,GAAG;SAChB,CAAC;QAEF,MAAM,CAAC,aAAa,CAAC,KAAK,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;IACvC,CAAC,CAAC,CAAC;AACL,CAAC,CAAC,CAAC;AAEH,QAAQ,CAAC,eAAe,EAAE,GAAG,EAAE;IAC7B,EAAE,CAAC,sCAAsC,EAAE,GAAG,EAAE;QAC9C,MAAM,KAAK,GAAkB;YAC3B,EAAE,EAAE,QAAQ;YACZ,SAAS,EAAE,IAAI,IAAI,EAAE,CAAC,WAAW,EAAE;YACnC,UAAU,EAAE,WAAW;YACvB,YAAY,EAAE,eAAe;YAC7B,UAAU,EAAE,SAAS;YACrB,YAAY,EAAE,MAAM;YACpB,iBAAiB,EAAE,QAAQ;YAC3B,UAAU,EAAE,GAAG;SAChB,CAAC;QAEF,MAAM,CAAC,aAAa,CAAC,KAAK,CAAC,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;IAC1C,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,kDAAkD,EAAE,GAAG,EAAE;QAC1D,MAAM,KAAK,GAAkB;YAC3B,EAAE,EAAE,QAAQ;YACZ,SAAS,EAAE,IAAI,IAAI,EAAE,CAAC,WAAW,EAAE;YACnC,UAAU,EAAE,WAAW;YACvB,YAAY,EAAE,eAAe;YAC7B,UAAU,EAAE,qBAAqB;YACjC,YAAY,EAAE,MAAM;YACpB,iBAAiB,EAAE,qBAAqB;YACxC,UAAU,EAAE,GAAG;SAChB,CAAC;QAEF,MAAM,CAAC,aAAa,CAAC,KAAK,CAAC,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;IAC1C,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,wCAAwC,EAAE,GAAG,EAAE;QAChD,MAAM,KAAK,GAAkB;YAC3B,EAAE,EAAE,QAAQ;YACZ,SAAS,EAAE,IAAI,IAAI,EAAE,CAAC,WAAW,EAAE;YACnC,UAAU,EAAE,WAAW;YACvB,YAAY,EAAE,eAAe;YAC7B,UAAU,EAAE,UAAU;YACtB,YAAY,EAAE,MAAM;YACpB,iBAAiB,EAAE,YAAY;YAC/B,UAAU,EAAE,GAAG;SAChB,CAAC;QAEF,MAAM,CAAC,aAAa,CAAC,KAAK,CAAC,CAAC,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;IAC3C,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,4CAA4C,EAAE,GAAG,EAAE;QACpD,MAAM,KAAK,GAAkB;YAC3B,EAAE,EAAE,QAAQ;YACZ,SAAS,EAAE,IAAI,IAAI,EAAE,CAAC,WAAW,EAAE;YACnC,UAAU,EAAE,WAAW;YACvB,YAAY,EAAE,eAAe;YAC7B,UAAU,EAAE,cAAc;YAC1B,YAAY,EAAE,MAAM;YACpB,iBAAiB,EAAE,WAAW;YAC9B,UAAU,EAAE,GAAG;SAChB,CAAC;QAEF,MAAM,CAAC,aAAa,CAAC,KAAK,CAAC,CAAC,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;IAC3C,CAAC,CAAC,CAAC;AACL,CAAC,CAAC,CAAC;AAEH,QAAQ,CAAC,mBAAmB,EAAE,GAAG,EAAE;IACjC,EAAE,CAAC,mDAAmD,EAAE,GAAG,EAAE;QAC3D,MAAM,WAAW,GAAqB;YACpC,UAAU,EAAE,YAAY;YACxB,iBAAiB,EAAE,EAAE;YACrB,aAAa,EAAE,CAAC;YAChB,cAAc,EAAE,CAAC;YACjB,kBAAkB,EAAE,CAAC;YACrB,YAAY,EAAE,GAAG;YACjB,gBAAgB,EAAE,EAAE;YACpB,YAAY,EAAE,EAAE;YAChB,UAAU,EAAE,EAAE;YACd,YAAY,EAAE,IAAI,IAAI,EAAE,CAAC,WAAW,EAAE;SACvC,CAAC;QAEF,MAAM,CAAC,iBAAiB,CAAC,WAAW,CAAC,CAAC,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;IACrD,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,+CAA+C,EAAE,GAAG,EAAE;QACvD,MAAM,WAAW,GAAqB;YACpC,UAAU,EAAE,YAAY;YACxB,iBAAiB,EAAE,EAAE;YACrB,aAAa,EAAE,CAAC;YAChB,cAAc,EAAE,CAAC;YACjB,kBAAkB,EAAE,CAAC;YACrB,YAAY,EAAE,GAAG;YACjB,gBAAgB,EAAE,EAAE;YACpB,YAAY,EAAE,EAAE;YAChB,UAAU,EAAE,EAAE;YACd,YAAY,EAAE,IAAI,IAAI,EAAE,CAAC,WAAW,EAAE;YACtC,gBAAgB,EAAE;gBAChB,sBAAsB,EAAE,IAAI;gBAC5B,sBAAsB,EAAE,IAAI;gBAC5B,YAAY,EAAE,KAAK;gBACnB,gBAAgB,EAAE,CAAC;gBACnB,gBAAgB,EAAE,GAAG;gBACrB,KAAK,EAAE,mBAAmB;aAC3B;SACF,CAAC;QAEF,MAAM,CAAC,iBAAiB,CAAC,WAAW,CAAC,CAAC,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;IACrD,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,+CAA+C,EAAE,GAAG,EAAE;QACvD,MAAM,WAAW,GAAqB;YACpC,UAAU,EAAE,YAAY;YACxB,iBAAiB,EAAE,EAAE;YACrB,aAAa,EAAE,CAAC;YAChB,cAAc,EAAE,CAAC;YACjB,kBAAkB,EAAE,CAAC;YACrB,YAAY,EAAE,GAAG;YACjB,gBAAgB,EAAE,EAAE;YACpB,YAAY,EAAE,EAAE;YAChB,UAAU,EAAE,EAAE;YACd,YAAY,EAAE,IAAI,IAAI,EAAE,CAAC,WAAW,EAAE;YACtC,gBAAgB,EAAE;gBAChB,sBAAsB,EAAE,IAAI;gBAC5B,sBAAsB,EAAE,IAAI;gBAC5B,YAAY,EAAE,KAAK;gBACnB,gBAAgB,EAAE,CAAC;gBACnB,gBAAgB,EAAE,GAAG;gBACrB,KAAK,EAAE,QAAQ;aAChB;SACF,CAAC;QAEF,MAAM,CAAC,iBAAiB,CAAC,WAAW,CAAC,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;IACpD,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,mCAAmC,EAAE,GAAG,EAAE;QAC3C,MAAM,WAAW,GAAqB;YACpC,UAAU,EAAE,YAAY;YACxB,iBAAiB,EAAE,EAAE;YACrB,aAAa,EAAE,CAAC;YAChB,cAAc,EAAE,CAAC;YACjB,kBAAkB,EAAE,CAAC;YACrB,YAAY,EAAE,GAAG;YACjB,gBAAgB,EAAE,EAAE;YACpB,YAAY,EAAE,EAAE;YAChB,UAAU,EAAE,EAAE;YACd,YAAY,EAAE,IAAI,IAAI,EAAE,CAAC,WAAW,EAAE;YACtC,gBAAgB,EAAE;gBAChB,sBAAsB,EAAE,IAAI;gBAC5B,sBAAsB,EAAE,IAAI;gBAC5B,YAAY,EAAE,KAAK;gBACnB,gBAAgB,EAAE,CAAC;gBACnB,gBAAgB,EAAE,GAAG;gBACrB,KAAK,EAAE,QAAQ;aAChB;SACF,CAAC;QAEF,MAAM,CAAC,iBAAiB,CAAC,WAAW,EAAE,EAAE,CAAC,CAAC,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;QACvD,MAAM,CAAC,iBAAiB,CAAC,WAAW,EAAE,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;IACvD,CAAC,CAAC,CAAC;AACL,CAAC,CAAC,CAAC"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"anomaly.test.d.ts","sourceRoot":"","sources":["../../../src/__tests__/learning/anomaly.test.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1,107 @@
|
|
|
1
|
+
import { describe, it, expect } from 'vitest';
|
|
2
|
+
import { detectAnomaly } from '../../learning/anomaly.js';
|
|
3
|
+
describe('detectAnomaly', () => {
|
|
4
|
+
const defaultThresholds = {
|
|
5
|
+
warning: 1.5,
|
|
6
|
+
critical: 2.5
|
|
7
|
+
};
|
|
8
|
+
it('should detect no anomaly for normal usage', () => {
|
|
9
|
+
const result = detectAnomaly(10000, 10000, defaultThresholds);
|
|
10
|
+
expect(result.is_anomaly).toBe(false);
|
|
11
|
+
expect(result.severity).toBe('info');
|
|
12
|
+
expect(result.ratio).toBe(1.0);
|
|
13
|
+
expect(result.message).toContain('10.0k');
|
|
14
|
+
expect(result.message).toContain('100%');
|
|
15
|
+
});
|
|
16
|
+
it('should detect warning anomaly at 1.5x threshold', () => {
|
|
17
|
+
const result = detectAnomaly(15000, 10000, defaultThresholds);
|
|
18
|
+
expect(result.is_anomaly).toBe(true);
|
|
19
|
+
expect(result.severity).toBe('warning');
|
|
20
|
+
expect(result.ratio).toBe(1.5);
|
|
21
|
+
expect(result.message).toContain('15.0k');
|
|
22
|
+
expect(result.message).toContain('150%');
|
|
23
|
+
expect(result.message).toContain('above typical usage');
|
|
24
|
+
});
|
|
25
|
+
it('should detect critical anomaly at 2.5x threshold', () => {
|
|
26
|
+
const result = detectAnomaly(25000, 10000, defaultThresholds);
|
|
27
|
+
expect(result.is_anomaly).toBe(true);
|
|
28
|
+
expect(result.severity).toBe('critical');
|
|
29
|
+
expect(result.ratio).toBe(2.5);
|
|
30
|
+
expect(result.message).toContain('25.0k');
|
|
31
|
+
expect(result.message).toContain('250%');
|
|
32
|
+
expect(result.message).toContain('unusually high');
|
|
33
|
+
});
|
|
34
|
+
it('should handle first session (baseline = 0)', () => {
|
|
35
|
+
const result = detectAnomaly(10000, 0, defaultThresholds);
|
|
36
|
+
expect(result.is_anomaly).toBe(false);
|
|
37
|
+
expect(result.severity).toBe('info');
|
|
38
|
+
expect(result.ratio).toBe(0);
|
|
39
|
+
expect(result.message).toContain('No baseline data');
|
|
40
|
+
});
|
|
41
|
+
it('should use custom thresholds', () => {
|
|
42
|
+
const customThresholds = {
|
|
43
|
+
warning: 2.0,
|
|
44
|
+
critical: 3.0
|
|
45
|
+
};
|
|
46
|
+
const result = detectAnomaly(18000, 10000, customThresholds);
|
|
47
|
+
// 1.8x is below 2.0 warning threshold
|
|
48
|
+
expect(result.is_anomaly).toBe(false);
|
|
49
|
+
expect(result.severity).toBe('info');
|
|
50
|
+
});
|
|
51
|
+
it('should detect warning with custom thresholds', () => {
|
|
52
|
+
const customThresholds = {
|
|
53
|
+
warning: 2.0,
|
|
54
|
+
critical: 3.0
|
|
55
|
+
};
|
|
56
|
+
const result = detectAnomaly(20000, 10000, customThresholds);
|
|
57
|
+
expect(result.is_anomaly).toBe(true);
|
|
58
|
+
expect(result.severity).toBe('warning');
|
|
59
|
+
});
|
|
60
|
+
it('should format small token counts without k suffix', () => {
|
|
61
|
+
const result = detectAnomaly(500, 500, defaultThresholds);
|
|
62
|
+
expect(result.message).toContain('500');
|
|
63
|
+
expect(result.message).not.toContain('k');
|
|
64
|
+
});
|
|
65
|
+
it('should format large token counts with k suffix', () => {
|
|
66
|
+
const result = detectAnomaly(15000, 10000, defaultThresholds);
|
|
67
|
+
expect(result.message).toContain('15.0k');
|
|
68
|
+
expect(result.message).toContain('10.0k');
|
|
69
|
+
});
|
|
70
|
+
it('should throw on negative current tokens', () => {
|
|
71
|
+
expect(() => detectAnomaly(-5000, 10000, defaultThresholds)).toThrow('Token counts cannot be negative');
|
|
72
|
+
});
|
|
73
|
+
it('should throw on negative baseline', () => {
|
|
74
|
+
expect(() => detectAnomaly(10000, -5000, defaultThresholds)).toThrow('Token counts cannot be negative');
|
|
75
|
+
});
|
|
76
|
+
it('should throw on negative threshold values', () => {
|
|
77
|
+
expect(() => detectAnomaly(10000, 10000, { warning: -1.5, critical: 2.5 }))
|
|
78
|
+
.toThrow('Thresholds cannot be negative');
|
|
79
|
+
});
|
|
80
|
+
it('should throw when critical <= warning', () => {
|
|
81
|
+
expect(() => detectAnomaly(10000, 10000, { warning: 2.5, critical: 2.5 }))
|
|
82
|
+
.toThrow('Critical threshold must be greater than warning threshold');
|
|
83
|
+
expect(() => detectAnomaly(10000, 10000, { warning: 3.0, critical: 2.5 }))
|
|
84
|
+
.toThrow('Critical threshold must be greater than warning threshold');
|
|
85
|
+
});
|
|
86
|
+
it('should detect anomaly just below critical threshold', () => {
|
|
87
|
+
const result = detectAnomaly(24999, 10000, defaultThresholds);
|
|
88
|
+
expect(result.is_anomaly).toBe(true);
|
|
89
|
+
expect(result.severity).toBe('warning');
|
|
90
|
+
});
|
|
91
|
+
it('should detect critical at exact threshold', () => {
|
|
92
|
+
const result = detectAnomaly(25000, 10000, defaultThresholds);
|
|
93
|
+
expect(result.is_anomaly).toBe(true);
|
|
94
|
+
expect(result.severity).toBe('critical');
|
|
95
|
+
});
|
|
96
|
+
it('should include actionable recommendations in critical message', () => {
|
|
97
|
+
const result = detectAnomaly(25000, 10000, defaultThresholds);
|
|
98
|
+
expect(result.message).toContain('delegate');
|
|
99
|
+
expect(result.message).toContain('smaller tasks');
|
|
100
|
+
});
|
|
101
|
+
it('should include actionable recommendations in warning message', () => {
|
|
102
|
+
const result = detectAnomaly(15000, 10000, defaultThresholds);
|
|
103
|
+
expect(result.message).toContain('delegating');
|
|
104
|
+
expect(result.message).toContain('completion');
|
|
105
|
+
});
|
|
106
|
+
});
|
|
107
|
+
//# sourceMappingURL=anomaly.test.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"anomaly.test.js","sourceRoot":"","sources":["../../../src/__tests__/learning/anomaly.test.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"baselines.test.d.ts","sourceRoot":"","sources":["../../../src/__tests__/learning/baselines.test.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1,155 @@
|
|
|
1
|
+
import { describe, it, expect } from 'vitest';
|
|
2
|
+
import { getSessionBaseline, updateSessionBaseline, getWarningThreshold } from '../../learning/baselines.js';
|
|
3
|
+
describe('getSessionBaseline', () => {
|
|
4
|
+
it('should return default 10k when no baseline data', () => {
|
|
5
|
+
expect(getSessionBaseline()).toBe(10000);
|
|
6
|
+
});
|
|
7
|
+
it('should return default 10k when sample count < 5', () => {
|
|
8
|
+
const baseline = {
|
|
9
|
+
overall_avg: 8000,
|
|
10
|
+
by_task_type: {},
|
|
11
|
+
by_project: {},
|
|
12
|
+
sample_count: 4,
|
|
13
|
+
last_updated: new Date().toISOString()
|
|
14
|
+
};
|
|
15
|
+
expect(getSessionBaseline(undefined, undefined, baseline)).toBe(10000);
|
|
16
|
+
});
|
|
17
|
+
it('should return project-specific baseline when available', () => {
|
|
18
|
+
const baseline = {
|
|
19
|
+
overall_avg: 10000,
|
|
20
|
+
by_task_type: {},
|
|
21
|
+
by_project: { '/path/to/project': 7500 },
|
|
22
|
+
sample_count: 10,
|
|
23
|
+
last_updated: new Date().toISOString()
|
|
24
|
+
};
|
|
25
|
+
expect(getSessionBaseline('/path/to/project', undefined, baseline)).toBe(7500);
|
|
26
|
+
});
|
|
27
|
+
it('should return task-type baseline when project not available', () => {
|
|
28
|
+
const baseline = {
|
|
29
|
+
overall_avg: 10000,
|
|
30
|
+
by_task_type: { debugging: 6000 },
|
|
31
|
+
by_project: {},
|
|
32
|
+
sample_count: 10,
|
|
33
|
+
last_updated: new Date().toISOString()
|
|
34
|
+
};
|
|
35
|
+
expect(getSessionBaseline(undefined, 'debugging', baseline)).toBe(6000);
|
|
36
|
+
});
|
|
37
|
+
it('should prefer project baseline over task-type baseline', () => {
|
|
38
|
+
const baseline = {
|
|
39
|
+
overall_avg: 10000,
|
|
40
|
+
by_task_type: { debugging: 6000 },
|
|
41
|
+
by_project: { '/path/to/project': 7500 },
|
|
42
|
+
sample_count: 10,
|
|
43
|
+
last_updated: new Date().toISOString()
|
|
44
|
+
};
|
|
45
|
+
expect(getSessionBaseline('/path/to/project', 'debugging', baseline)).toBe(7500);
|
|
46
|
+
});
|
|
47
|
+
it('should fall back to overall average when no specific baseline', () => {
|
|
48
|
+
const baseline = {
|
|
49
|
+
overall_avg: 9200,
|
|
50
|
+
by_task_type: {},
|
|
51
|
+
by_project: {},
|
|
52
|
+
sample_count: 10,
|
|
53
|
+
last_updated: new Date().toISOString()
|
|
54
|
+
};
|
|
55
|
+
expect(getSessionBaseline('/unknown/project', 'unknown-task', baseline)).toBe(9200);
|
|
56
|
+
});
|
|
57
|
+
});
|
|
58
|
+
describe('updateSessionBaseline', () => {
|
|
59
|
+
it('should initialize baseline for first session', () => {
|
|
60
|
+
const result = updateSessionBaseline(8000, '/path/to/project', 'debugging', undefined);
|
|
61
|
+
expect(result.overall_avg).toBe(8000);
|
|
62
|
+
expect(result.by_project['/path/to/project']).toBe(8000);
|
|
63
|
+
expect(result.by_task_type['debugging']).toBe(8000);
|
|
64
|
+
expect(result.sample_count).toBe(1);
|
|
65
|
+
});
|
|
66
|
+
it('should initialize baseline without task type', () => {
|
|
67
|
+
const result = updateSessionBaseline(8000, '/path/to/project', undefined, undefined);
|
|
68
|
+
expect(result.overall_avg).toBe(8000);
|
|
69
|
+
expect(result.by_project['/path/to/project']).toBe(8000);
|
|
70
|
+
expect(result.by_task_type).toEqual({});
|
|
71
|
+
expect(result.sample_count).toBe(1);
|
|
72
|
+
});
|
|
73
|
+
it('should update overall average correctly', () => {
|
|
74
|
+
const baseline = {
|
|
75
|
+
overall_avg: 10000,
|
|
76
|
+
by_task_type: {},
|
|
77
|
+
by_project: { '/path/to/project': 10000 },
|
|
78
|
+
sample_count: 1,
|
|
79
|
+
last_updated: new Date().toISOString()
|
|
80
|
+
};
|
|
81
|
+
const result = updateSessionBaseline(8000, '/path/to/project', undefined, baseline);
|
|
82
|
+
// (10000 * 1 + 8000) / 2 = 9000
|
|
83
|
+
expect(result.overall_avg).toBe(9000);
|
|
84
|
+
expect(result.sample_count).toBe(2);
|
|
85
|
+
});
|
|
86
|
+
it('should update project-specific average', () => {
|
|
87
|
+
const baseline = {
|
|
88
|
+
overall_avg: 10000,
|
|
89
|
+
by_task_type: {},
|
|
90
|
+
by_project: { '/path/to/project': 10000 },
|
|
91
|
+
sample_count: 1,
|
|
92
|
+
last_updated: new Date().toISOString()
|
|
93
|
+
};
|
|
94
|
+
const result = updateSessionBaseline(6000, '/path/to/project', undefined, baseline);
|
|
95
|
+
// Project avg should be updated
|
|
96
|
+
expect(result.by_project['/path/to/project']).toBeLessThan(10000);
|
|
97
|
+
});
|
|
98
|
+
it('should handle new project in existing baseline', () => {
|
|
99
|
+
const baseline = {
|
|
100
|
+
overall_avg: 10000,
|
|
101
|
+
by_task_type: {},
|
|
102
|
+
by_project: { '/old/project': 10000 },
|
|
103
|
+
sample_count: 5,
|
|
104
|
+
last_updated: new Date().toISOString()
|
|
105
|
+
};
|
|
106
|
+
const result = updateSessionBaseline(8000, '/new/project', undefined, baseline);
|
|
107
|
+
expect(result.by_project['/old/project']).toBe(10000); // unchanged
|
|
108
|
+
expect(result.by_project['/new/project']).toBe(8000); // new entry
|
|
109
|
+
});
|
|
110
|
+
it('should update task-type average when provided', () => {
|
|
111
|
+
const baseline = {
|
|
112
|
+
overall_avg: 10000,
|
|
113
|
+
by_task_type: { debugging: 8000 },
|
|
114
|
+
by_project: {},
|
|
115
|
+
sample_count: 5,
|
|
116
|
+
last_updated: new Date().toISOString()
|
|
117
|
+
};
|
|
118
|
+
const result = updateSessionBaseline(6000, '/path/to/project', 'debugging', baseline);
|
|
119
|
+
expect(result.by_task_type['debugging']).toBeLessThan(8000);
|
|
120
|
+
});
|
|
121
|
+
it('should throw on negative token counts', () => {
|
|
122
|
+
expect(() => updateSessionBaseline(-1000, '/path/to/project')).toThrow('Session tokens cannot be negative');
|
|
123
|
+
});
|
|
124
|
+
it('should update last_updated timestamp', () => {
|
|
125
|
+
const oldTimestamp = new Date('2024-01-01').toISOString();
|
|
126
|
+
const baseline = {
|
|
127
|
+
overall_avg: 10000,
|
|
128
|
+
by_task_type: {},
|
|
129
|
+
by_project: {},
|
|
130
|
+
sample_count: 1,
|
|
131
|
+
last_updated: oldTimestamp
|
|
132
|
+
};
|
|
133
|
+
const result = updateSessionBaseline(8000, '/path/to/project', undefined, baseline);
|
|
134
|
+
expect(result.last_updated).not.toBe(oldTimestamp);
|
|
135
|
+
expect(new Date(result.last_updated).getTime()).toBeGreaterThan(new Date(oldTimestamp).getTime());
|
|
136
|
+
});
|
|
137
|
+
});
|
|
138
|
+
describe('getWarningThreshold', () => {
|
|
139
|
+
it('should calculate warning threshold with default multiplier', () => {
|
|
140
|
+
expect(getWarningThreshold(10000)).toBe(15000); // 1.5x default
|
|
141
|
+
});
|
|
142
|
+
it('should calculate warning threshold with custom multiplier', () => {
|
|
143
|
+
expect(getWarningThreshold(10000, 2.0)).toBe(20000);
|
|
144
|
+
});
|
|
145
|
+
it('should handle zero baseline', () => {
|
|
146
|
+
expect(getWarningThreshold(0, 1.5)).toBe(0);
|
|
147
|
+
});
|
|
148
|
+
it('should throw on negative baseline', () => {
|
|
149
|
+
expect(() => getWarningThreshold(-10000, 1.5)).toThrow('Baseline and multiplier must be non-negative');
|
|
150
|
+
});
|
|
151
|
+
it('should throw on negative multiplier', () => {
|
|
152
|
+
expect(() => getWarningThreshold(10000, -1.5)).toThrow('Baseline and multiplier must be non-negative');
|
|
153
|
+
});
|
|
154
|
+
});
|
|
155
|
+
//# sourceMappingURL=baselines.test.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"baselines.test.js","sourceRoot":"","sources":["../../../src/__tests__/learning/baselines.test.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"efficiency.test.d.ts","sourceRoot":"","sources":["../../../src/__tests__/learning/efficiency.test.ts"],"names":[],"mappings":""}
|