@eldrforge/kodrdriv 1.2.131 → 1.2.132

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.
@@ -5,7 +5,7 @@ import { DEFAULT_TO_COMMIT_ALIAS, DEFAULT_MAX_DIFF_BYTES, DEFAULT_EXCLUDED_PATTE
5
5
  import { getCurrentBranch, getDefaultFromRef, safeJsonParse } from '@eldrforge/git-tools';
6
6
  import { create } from '../content/log.js';
7
7
  import { create as create$1, truncateDiffByFiles } from '../content/diff.js';
8
- import { runAgenticRelease, requireTTY, createReleasePrompt, createCompletionWithRetry, getUserChoice, STANDARD_CHOICES, getLLMFeedbackInEditor, editContentInEditor } from '@eldrforge/ai-service';
8
+ import { runAgenticRelease, requireTTY, createReleasePrompt, createCompletionWithRetry, generateReflectionReport, getUserChoice, STANDARD_CHOICES, getLLMFeedbackInEditor, editContentInEditor } from '@eldrforge/ai-service';
9
9
  import { improveContentWithLLM } from '../util/interactive.js';
10
10
  import { toAIConfig } from '../util/aiAdapter.js';
11
11
  import { createStorageAdapter } from '../util/storageAdapter.js';
@@ -88,166 +88,25 @@ Please revise the release notes according to the user's feedback while maintaini
88
88
  };
89
89
  return await improveContentWithLLM(releaseSummary, runConfig, promptConfig, promptContext, outputDirectory, improvementConfig);
90
90
  }
91
- // Helper function to generate self-reflection output for release notes
91
+ // Helper function to generate self-reflection output for release notes using observability module
92
92
  async function generateSelfReflection(agenticResult, outputDirectory, storage, logger) {
93
93
  try {
94
94
  const timestamp = new Date().toISOString().replace(/[:.]/g, '-').split('.')[0];
95
95
  const reflectionPath = getOutputPath(outputDirectory, `agentic-reflection-release-${timestamp}.md`);
96
- // Calculate tool effectiveness metrics
97
- const toolMetrics = agenticResult.toolMetrics || [];
98
- const toolStats = new Map();
99
- for (const metric of toolMetrics){
100
- if (!toolStats.has(metric.name)) {
101
- toolStats.set(metric.name, {
102
- total: 0,
103
- success: 0,
104
- failures: 0,
105
- totalDuration: 0
106
- });
107
- }
108
- const stats = toolStats.get(metric.name);
109
- stats.total++;
110
- stats.totalDuration += metric.duration;
111
- if (metric.success) {
112
- stats.success++;
113
- } else {
114
- stats.failures++;
115
- }
116
- }
117
- // Build reflection document
118
- const sections = [];
119
- sections.push('# Agentic Release Notes - Self-Reflection Report');
120
- sections.push('');
121
- sections.push(`Generated: ${new Date().toISOString()}`);
122
- sections.push('');
123
- sections.push('## Execution Summary');
124
- sections.push('');
125
- sections.push(`- **Iterations**: ${agenticResult.iterations}`);
126
- sections.push(`- **Tool Calls**: ${agenticResult.toolCallsExecuted}`);
127
- sections.push(`- **Unique Tools Used**: ${toolStats.size}`);
128
- sections.push('');
129
- sections.push('## Tool Effectiveness Analysis');
130
- sections.push('');
131
- if (toolStats.size === 0) {
132
- sections.push('*No tools were called during execution.*');
133
- sections.push('');
134
- } else {
135
- sections.push('| Tool | Calls | Success Rate | Avg Duration | Total Time |');
136
- sections.push('|------|-------|--------------|--------------|------------|');
137
- const sortedTools = Array.from(toolStats.entries()).sort((a, b)=>b[1].total - a[1].total);
138
- for (const [toolName, stats] of sortedTools){
139
- const successRate = (stats.success / stats.total * 100).toFixed(1);
140
- const avgDuration = (stats.totalDuration / stats.total).toFixed(0);
141
- const totalTime = stats.totalDuration.toFixed(0);
142
- sections.push(`| ${toolName} | ${stats.total} | ${successRate}% | ${avgDuration}ms | ${totalTime}ms |`);
143
- }
144
- sections.push('');
145
- }
146
- // Tool usage insights
147
- sections.push('## Tool Usage Insights');
148
- sections.push('');
149
- if (toolStats.size > 0) {
150
- const mostUsedTool = Array.from(toolStats.entries()).sort((a, b)=>b[1].total - a[1].total)[0];
151
- sections.push(`- **Most Used Tool**: \`${mostUsedTool[0]}\` (${mostUsedTool[1].total} calls)`);
152
- const slowestTool = Array.from(toolStats.entries()).sort((a, b)=>b[1].totalDuration / b[1].total - a[1].totalDuration / a[1].total)[0];
153
- const slowestAvg = (slowestTool[1].totalDuration / slowestTool[1].total).toFixed(0);
154
- sections.push(`- **Slowest Tool**: \`${slowestTool[0]}\` (${slowestAvg}ms average)`);
155
- const failedTools = Array.from(toolStats.entries()).filter(([_, stats])=>stats.failures > 0);
156
- if (failedTools.length > 0) {
157
- sections.push(`- **Tools with Failures**: ${failedTools.length} tool(s) had at least one failure`);
158
- for (const [toolName, stats] of failedTools){
159
- sections.push(` - \`${toolName}\`: ${stats.failures}/${stats.total} calls failed`);
160
- }
161
- } else {
162
- sections.push('- **Reliability**: All tool calls succeeded ✓');
163
- }
164
- }
165
- sections.push('');
166
- // Execution patterns
167
- sections.push('## Execution Patterns');
168
- sections.push('');
169
- const iterationsPerToolCall = agenticResult.toolCallsExecuted > 0 ? (agenticResult.iterations / agenticResult.toolCallsExecuted).toFixed(2) : 'N/A';
170
- sections.push(`- **Iterations per Tool Call**: ${iterationsPerToolCall}`);
171
- const totalExecutionTime = Array.from(toolStats.values()).reduce((sum, stats)=>sum + stats.totalDuration, 0);
172
- sections.push(`- **Total Tool Execution Time**: ${totalExecutionTime.toFixed(0)}ms`);
173
- if (agenticResult.toolCallsExecuted > 0) {
174
- const avgTimePerCall = (totalExecutionTime / agenticResult.toolCallsExecuted).toFixed(0);
175
- sections.push(`- **Average Time per Tool Call**: ${avgTimePerCall}ms`);
176
- }
177
- sections.push('');
178
- // Recommendations
179
- sections.push('## Recommendations');
180
- sections.push('');
181
- const recommendations = [];
182
- const failedTools = Array.from(toolStats.entries()).filter(([_, stats])=>stats.failures > 0);
183
- if (failedTools.length > 0) {
184
- recommendations.push('- **Tool Reliability**: Some tools failed during execution. Review error messages and consider improving error handling or tool implementation.');
185
- }
186
- const slowTools = Array.from(toolStats.entries()).filter(([_, stats])=>stats.totalDuration / stats.total > 1000);
187
- if (slowTools.length > 0) {
188
- recommendations.push('- **Performance**: Consider optimizing slow tools or caching results to improve execution speed.');
189
- }
190
- if (agenticResult.iterations >= (agenticResult.maxIterations || 30)) {
191
- recommendations.push('- **Max Iterations Reached**: The agent reached maximum iterations. Consider increasing the limit or improving tool efficiency to allow the agent to complete naturally.');
192
- }
193
- const underutilizedTools = Array.from(toolStats.entries()).filter(([_, stats])=>stats.total === 1);
194
- if (underutilizedTools.length > 3) {
195
- recommendations.push('- **Underutilized Tools**: Many tools were called only once. Consider whether all tools are necessary or if the agent needs better guidance on when to use them.');
196
- }
197
- if (agenticResult.toolCallsExecuted === 0) {
198
- recommendations.push('- **No Tools Used**: The agent completed without calling any tools. This might indicate the initial prompt provided sufficient information, or the agent may benefit from more explicit guidance to use tools.');
199
- }
200
- if (recommendations.length === 0) {
201
- sections.push('*No specific recommendations at this time. Execution appears optimal.*');
202
- } else {
203
- for (const rec of recommendations){
204
- sections.push(rec);
205
- }
206
- }
207
- sections.push('');
208
- // Add detailed execution timeline
209
- sections.push('## Detailed Execution Timeline');
210
- sections.push('');
211
- if (toolMetrics.length === 0) {
212
- sections.push('*No tool execution timeline available.*');
213
- } else {
214
- sections.push('| Time | Iteration | Tool | Result | Duration |');
215
- sections.push('|------|-----------|------|--------|----------|');
216
- for (const metric of toolMetrics){
217
- const time = new Date(metric.timestamp).toLocaleTimeString();
218
- const result = metric.success ? '✅ Success' : `❌ ${metric.error || 'Failed'}`;
219
- sections.push(`| ${time} | ${metric.iteration} | ${metric.name} | ${result} | ${metric.duration}ms |`);
220
- }
221
- sections.push('');
222
- }
223
- // Add conversation history
224
- sections.push('## Conversation History');
225
- sections.push('');
226
- sections.push('<details>');
227
- sections.push('<summary>Click to expand full agentic interaction</summary>');
228
- sections.push('');
229
- sections.push('```json');
230
- sections.push(JSON.stringify(agenticResult.conversationHistory, null, 2));
231
- sections.push('```');
232
- sections.push('');
233
- sections.push('</details>');
234
- sections.push('');
235
- // Add generated release notes
236
- sections.push('## Generated Release Notes');
237
- sections.push('');
238
- sections.push('### Title');
239
- sections.push('```');
240
- sections.push(agenticResult.releaseNotes.title);
241
- sections.push('```');
242
- sections.push('');
243
- sections.push('### Body');
244
- sections.push('```markdown');
245
- sections.push(agenticResult.releaseNotes.body);
246
- sections.push('```');
247
- sections.push('');
248
- // Write the reflection file
249
- const reflectionContent = sections.join('\n');
250
- await storage.writeFile(reflectionPath, reflectionContent, 'utf-8');
96
+ // Use new observability reflection generator
97
+ const report = await generateReflectionReport({
98
+ iterations: agenticResult.iterations || 0,
99
+ toolCallsExecuted: agenticResult.toolCallsExecuted || 0,
100
+ maxIterations: agenticResult.maxIterations || 30,
101
+ toolMetrics: agenticResult.toolMetrics || [],
102
+ conversationHistory: agenticResult.conversationHistory || [],
103
+ releaseNotes: agenticResult.releaseNotes,
104
+ logger
105
+ });
106
+ // Save the report
107
+ const storageAdapter = createStorageAdapter();
108
+ const filename = `agentic-reflection-release-${timestamp}.md`;
109
+ await storageAdapter.writeOutput(filename, report);
251
110
  logger.info('');
252
111
  logger.info('═'.repeat(80));
253
112
  logger.info('📊 SELF-REFLECTION REPORT GENERATED');
@@ -256,9 +115,12 @@ async function generateSelfReflection(agenticResult, outputDirectory, storage, l
256
115
  logger.info('📁 Location: %s', reflectionPath);
257
116
  logger.info('');
258
117
  logger.info('📈 Report Summary:');
259
- logger.info(' • %d iterations completed', agenticResult.iterations);
260
- logger.info(' • %d tool calls executed', agenticResult.toolCallsExecuted);
261
- logger.info(' • %d unique tools used', toolStats.size);
118
+ const iterations = agenticResult.iterations || 0;
119
+ const toolCalls = agenticResult.toolCallsExecuted || 0;
120
+ const uniqueTools = new Set((agenticResult.toolMetrics || []).map((m)=>m.name)).size;
121
+ logger.info(` • ${iterations} iterations completed`);
122
+ logger.info(` • ${toolCalls} tool calls executed`);
123
+ logger.info(` • ${uniqueTools} unique tools used`);
262
124
  logger.info('');
263
125
  logger.info('💡 Use this report to:');
264
126
  logger.info(' • Understand which tools were most effective');
@@ -443,7 +305,9 @@ const execute = async (runConfig)=>{
443
305
  logger: aiLogger,
444
306
  openaiReasoning: ((_aiConfig_commands3 = aiConfig.commands) === null || _aiConfig_commands3 === void 0 ? void 0 : (_aiConfig_commands_release3 = _aiConfig_commands3.release) === null || _aiConfig_commands_release3 === void 0 ? void 0 : _aiConfig_commands_release3.reasoning) || aiConfig.reasoning
445
307
  });
446
- logger.info('🔍 Agentic analysis complete: %d iterations, %d tool calls', agenticResult.iterations, agenticResult.toolCallsExecuted);
308
+ const iterations = agenticResult.iterations || 0;
309
+ const toolCalls = agenticResult.toolCallsExecuted || 0;
310
+ logger.info(`🔍 Agentic analysis complete: ${iterations} iterations, ${toolCalls} tool calls`);
447
311
  // Generate self-reflection output if enabled
448
312
  if ((_runConfig_release14 = runConfig.release) === null || _runConfig_release14 === void 0 ? void 0 : _runConfig_release14.selfReflection) {
449
313
  await generateSelfReflection(agenticResult, outputDirectory, storage, logger);