claude-flow-novice 1.5.17 → 1.5.19

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.
Files changed (24) hide show
  1. package/.claude-flow-novice/dist/config/hooks/post-edit-pipeline.js +1837 -0
  2. package/.claude-flow-novice/dist/src/hooks/communication-integrated-post-edit.js +673 -0
  3. package/.claude-flow-novice/dist/src/hooks/enhanced/experience-adaptation-hooks.js +347 -0
  4. package/.claude-flow-novice/dist/src/hooks/enhanced/personalization-hooks.js +118 -0
  5. package/.claude-flow-novice/dist/src/hooks/enhanced-post-edit-pipeline.js +2044 -0
  6. package/.claude-flow-novice/dist/src/hooks/filter-integration.js +542 -0
  7. package/.claude-flow-novice/dist/src/hooks/guidance-hooks.js +629 -0
  8. package/.claude-flow-novice/dist/src/hooks/index.ts +239 -0
  9. package/.claude-flow-novice/dist/src/hooks/managers/enhanced-hook-manager.js +200 -0
  10. package/.claude-flow-novice/dist/src/hooks/resilient-hook-system.js +812 -0
  11. package/CHANGELOG.md +22 -0
  12. package/config/hooks/post-edit-pipeline.js +30 -0
  13. package/package.json +2 -1
  14. package/src/cli/simple-commands/init/templates/CLAUDE.md +38 -6
  15. package/src/hooks/communication-integrated-post-edit.js +673 -0
  16. package/src/hooks/enhanced/experience-adaptation-hooks.js +347 -0
  17. package/src/hooks/enhanced/personalization-hooks.js +118 -0
  18. package/src/hooks/enhanced-hooks-cli.js +168 -0
  19. package/src/hooks/enhanced-post-edit-pipeline.js +2044 -0
  20. package/src/hooks/filter-integration.js +542 -0
  21. package/src/hooks/guidance-hooks.js +629 -0
  22. package/src/hooks/index.ts +239 -0
  23. package/src/hooks/managers/enhanced-hook-manager.js +200 -0
  24. package/src/hooks/resilient-hook-system.js +812 -0
@@ -0,0 +1,629 @@
1
+ /**
2
+ * Guidance System Hooks Integration
3
+ * Integrates adaptive guidance with the existing hook system
4
+ */
5
+
6
+ const { GuidanceSystem } = require('../guidance');
7
+ const path = require('path');
8
+
9
+ class GuidanceHooks {
10
+ constructor(options = {}) {
11
+ this.guidanceSystem = new GuidanceSystem(options);
12
+ this.isInitialized = false;
13
+ this.sessionContext = {
14
+ currentTask: null,
15
+ commandHistory: [],
16
+ errorCount: 0,
17
+ startTime: Date.now(),
18
+ };
19
+ }
20
+
21
+ /**
22
+ * Initialize guidance hooks
23
+ */
24
+ async initialize() {
25
+ if (this.isInitialized) {
26
+ return true;
27
+ }
28
+
29
+ try {
30
+ const initialized = await this.guidanceSystem.initialize();
31
+ if (initialized) {
32
+ this.isInitialized = true;
33
+ this.setupEventHandlers();
34
+ return true;
35
+ }
36
+ return false;
37
+ } catch (error) {
38
+ console.warn('Guidance hooks initialization failed:', error.message);
39
+ return false;
40
+ }
41
+ }
42
+
43
+ /**
44
+ * Setup event handlers for guidance system
45
+ */
46
+ setupEventHandlers() {
47
+ this.guidanceSystem.on('milestoneAchieved', (data) => {
48
+ this.celebrateMilestone(data);
49
+ });
50
+
51
+ this.guidanceSystem.on('experienceLevelChanged', (data) => {
52
+ this.announceExperienceLevelChange(data);
53
+ });
54
+
55
+ this.guidanceSystem.on('error', (data) => {
56
+ console.warn('Guidance system error:', data.error.message);
57
+ });
58
+ }
59
+
60
+ /**
61
+ * Pre-task hook - provides guidance before task execution
62
+ */
63
+ async preTaskHook(context) {
64
+ await this.initialize();
65
+
66
+ const { command, args, taskDescription, options = {} } = context;
67
+
68
+ try {
69
+ // Update session context
70
+ this.sessionContext.currentTask = {
71
+ command,
72
+ args,
73
+ description: taskDescription,
74
+ startTime: Date.now(),
75
+ };
76
+
77
+ // Get guidance for the command
78
+ const guidance = await this.guidanceSystem.getCommandGuidance(command, args, {
79
+ taskDescription,
80
+ currentFiles: await this.getCurrentProjectFiles(),
81
+ ...context,
82
+ });
83
+
84
+ // Provide guidance based on user's experience level
85
+ if (guidance && this.shouldShowGuidance(guidance, options)) {
86
+ this.displayPreTaskGuidance(guidance, options);
87
+ }
88
+
89
+ // Track command start
90
+ this.sessionContext.commandHistory.push({
91
+ command,
92
+ args,
93
+ startTime: Date.now(),
94
+ status: 'started',
95
+ });
96
+
97
+ return {
98
+ guidance,
99
+ shouldProceed: true,
100
+ modifiedContext: context,
101
+ };
102
+ } catch (error) {
103
+ console.warn('Pre-task guidance failed:', error.message);
104
+ return { shouldProceed: true, modifiedContext: context };
105
+ }
106
+ }
107
+
108
+ /**
109
+ * Post-task hook - learns from task execution and provides follow-up guidance
110
+ */
111
+ async postTaskHook(context) {
112
+ if (!this.isInitialized) {
113
+ return;
114
+ }
115
+
116
+ const { command, args, outcome, error, duration, output } = context;
117
+
118
+ try {
119
+ // Update command history
120
+ const lastCommand =
121
+ this.sessionContext.commandHistory[this.sessionContext.commandHistory.length - 1];
122
+ if (lastCommand && lastCommand.command === command) {
123
+ lastCommand.status = outcome;
124
+ lastCommand.duration = duration;
125
+ lastCommand.error = error;
126
+ lastCommand.endTime = Date.now();
127
+ }
128
+
129
+ // Process command execution for learning
130
+ await this.guidanceSystem.processCommandExecution({
131
+ command,
132
+ outcome,
133
+ timeSpent: duration,
134
+ errorMessages: error ? [error.message] : [],
135
+ guidanceUsed: Boolean(context.guidanceUsed),
136
+ context: {
137
+ args,
138
+ output,
139
+ sessionDuration: Date.now() - this.sessionContext.startTime,
140
+ },
141
+ });
142
+
143
+ // Provide post-execution guidance
144
+ await this.providePostExecutionGuidance(context);
145
+
146
+ // Update error count
147
+ if (outcome === 'failure') {
148
+ this.sessionContext.errorCount++;
149
+ }
150
+ } catch (error) {
151
+ console.warn('Post-task guidance failed:', error.message);
152
+ }
153
+ }
154
+
155
+ /**
156
+ * Pre-edit hook - provides guidance before file modifications
157
+ */
158
+ async preEditHook(context) {
159
+ await this.initialize();
160
+
161
+ const { filePath, operation, content } = context;
162
+
163
+ try {
164
+ // Analyze file context for guidance
165
+ const fileContext = await this.analyzeFileContext(filePath, operation);
166
+
167
+ // Get relevant guidance
168
+ const guidance = await this.guidanceSystem.getGuidance({
169
+ command: 'file-edit',
170
+ taskType: this.inferTaskTypeFromFile(filePath),
171
+ currentFiles: [filePath],
172
+ operation,
173
+ ...fileContext,
174
+ });
175
+
176
+ if (guidance && guidance.adaptive.suggestions?.length > 0) {
177
+ console.log('\nšŸ’” File Edit Guidance:');
178
+ guidance.adaptive.suggestions.forEach((suggestion, index) => {
179
+ if (suggestion.type === 'safety' || suggestion.priority === 'high') {
180
+ console.log(` ${index + 1}. āš ļø ${suggestion.message}`);
181
+ }
182
+ });
183
+ }
184
+
185
+ return {
186
+ guidance,
187
+ shouldProceed: true,
188
+ modifiedContext: context,
189
+ };
190
+ } catch (error) {
191
+ console.warn('Pre-edit guidance failed:', error.message);
192
+ return { shouldProceed: true, modifiedContext: context };
193
+ }
194
+ }
195
+
196
+ /**
197
+ * Post-edit hook - learns from file modifications
198
+ */
199
+ async postEditHook(context) {
200
+ if (!this.isInitialized) {
201
+ return;
202
+ }
203
+
204
+ const { filePath, operation, success, error } = context;
205
+
206
+ try {
207
+ // Track file edit patterns
208
+ await this.guidanceSystem.processCommandExecution({
209
+ command: 'file-edit',
210
+ outcome: success ? 'success' : 'failure',
211
+ timeSpent: context.duration || 0,
212
+ errorMessages: error ? [error.message] : [],
213
+ context: {
214
+ filePath,
215
+ operation,
216
+ fileType: path.extname(filePath),
217
+ },
218
+ });
219
+
220
+ // Provide suggestions for next steps
221
+ if (success) {
222
+ const nextSteps = await this.suggestNextSteps(filePath, operation);
223
+ if (nextSteps.length > 0) {
224
+ console.log('\nšŸ”„ Suggested next steps:');
225
+ nextSteps.forEach((step, index) => {
226
+ console.log(` ${index + 1}. ${step}`);
227
+ });
228
+ }
229
+ }
230
+ } catch (error) {
231
+ console.warn('Post-edit guidance failed:', error.message);
232
+ }
233
+ }
234
+
235
+ /**
236
+ * Session start hook - initializes session context
237
+ */
238
+ async sessionStartHook(context) {
239
+ await this.initialize();
240
+
241
+ const { sessionId, projectPath, user } = context;
242
+
243
+ try {
244
+ // Initialize session context
245
+ this.sessionContext = {
246
+ sessionId,
247
+ projectPath,
248
+ user,
249
+ currentTask: null,
250
+ commandHistory: [],
251
+ errorCount: 0,
252
+ startTime: Date.now(),
253
+ };
254
+
255
+ // Get user status and show welcome guidance
256
+ const userStatus = this.guidanceSystem.getUserStatus();
257
+ if (userStatus) {
258
+ this.showWelcomeGuidance(userStatus);
259
+ }
260
+
261
+ // Get learning recommendations for new session
262
+ const recommendations = this.guidanceSystem.getLearningRecommendations();
263
+ if (recommendations.combined.length > 0) {
264
+ console.log("\nšŸ“š Today's learning suggestions:");
265
+ recommendations.combined.slice(0, 2).forEach((rec, index) => {
266
+ console.log(` ${index + 1}. ${rec.title} (${rec.estimatedTime || '10 min'})`);
267
+ });
268
+ console.log(' Use "claude-flow-novice guidance learn" for more recommendations');
269
+ }
270
+ } catch (error) {
271
+ console.warn('Session start guidance failed:', error.message);
272
+ }
273
+ }
274
+
275
+ /**
276
+ * Session end hook - saves learning data and provides session summary
277
+ */
278
+ async sessionEndHook(context) {
279
+ if (!this.isInitialized) {
280
+ return;
281
+ }
282
+
283
+ const { sessionId, duration, exportMetrics } = context;
284
+
285
+ try {
286
+ // Generate session summary
287
+ const summary = this.generateSessionSummary();
288
+
289
+ if (exportMetrics) {
290
+ console.log('\nšŸ“Š Session Summary:');
291
+ console.log(` Commands executed: ${summary.totalCommands}`);
292
+ console.log(` Success rate: ${summary.successRate}%`);
293
+ console.log(` Session duration: ${this.formatDuration(duration)}`);
294
+
295
+ if (summary.milestonesAchieved > 0) {
296
+ console.log(` šŸ† Milestones achieved: ${summary.milestonesAchieved}`);
297
+ }
298
+
299
+ if (summary.experienceLevelChanged) {
300
+ console.log(` šŸŽ‰ Experience level upgraded to: ${summary.newExperienceLevel}`);
301
+ }
302
+ }
303
+
304
+ // Save guidance data
305
+ await this.guidanceSystem.shutdown();
306
+ } catch (error) {
307
+ console.warn('Session end guidance failed:', error.message);
308
+ }
309
+ }
310
+
311
+ /**
312
+ * Determine if guidance should be shown based on user preferences and context
313
+ */
314
+ shouldShowGuidance(guidance, options) {
315
+ const userStatus = this.guidanceSystem.getUserStatus();
316
+ if (!userStatus) return false;
317
+
318
+ const preferences = userStatus.preferences;
319
+
320
+ // Respect user's guidance preferences
321
+ if (options.quiet || !preferences.showTips) {
322
+ return false;
323
+ }
324
+
325
+ // Always show high-priority guidance
326
+ const hasHighPriority =
327
+ guidance.adaptive?.suggestions?.some((s) => s.priority === 'high') ||
328
+ guidance.adaptive?.warnings?.length > 0;
329
+
330
+ if (hasHighPriority) {
331
+ return true;
332
+ }
333
+
334
+ // Show guidance based on experience level
335
+ const experienceLevel = userStatus.experienceLevel;
336
+ if (experienceLevel === 'novice') {
337
+ return true;
338
+ }
339
+
340
+ if (experienceLevel === 'intermediate' && Math.random() < 0.5) {
341
+ return true;
342
+ }
343
+
344
+ if (experienceLevel === 'expert' && Math.random() < 0.1) {
345
+ return true;
346
+ }
347
+
348
+ return false;
349
+ }
350
+
351
+ /**
352
+ * Display pre-task guidance
353
+ */
354
+ displayPreTaskGuidance(guidance, options) {
355
+ const suggestions = guidance.adaptive?.suggestions || [];
356
+ const warnings = guidance.adaptive?.warnings || [];
357
+
358
+ // Show warnings first
359
+ if (warnings.length > 0) {
360
+ console.log('\nāš ļø Before you proceed:');
361
+ warnings.forEach((warning, index) => {
362
+ console.log(` ${index + 1}. ${warning.message}`);
363
+ });
364
+ }
365
+
366
+ // Show high-priority suggestions
367
+ const highPrioritySuggestions = suggestions.filter((s) => s.priority === 'high');
368
+ if (highPrioritySuggestions.length > 0) {
369
+ console.log('\nšŸ’” Important suggestions:');
370
+ highPrioritySuggestions.forEach((suggestion, index) => {
371
+ console.log(` ${index + 1}. ${suggestion.message}`);
372
+ if (suggestion.action) {
373
+ console.log(` Try: ${suggestion.action}`);
374
+ }
375
+ });
376
+ }
377
+
378
+ // Show recommended agents if available
379
+ if (guidance.context?.recommendedAgents?.length > 0) {
380
+ console.log(`\nšŸ¤– Recommended agents: ${guidance.context.recommendedAgents.join(', ')}`);
381
+ }
382
+ }
383
+
384
+ /**
385
+ * Provide post-execution guidance
386
+ */
387
+ async providePostExecutionGuidance(context) {
388
+ const { command, outcome, error, output } = context;
389
+
390
+ // Success guidance
391
+ if (outcome === 'success') {
392
+ await this.provideSuccessGuidance(command, output);
393
+ }
394
+
395
+ // Error guidance
396
+ if (outcome === 'failure' && error) {
397
+ await this.provideErrorGuidance(command, error);
398
+ }
399
+
400
+ // Suggest optimizations or next steps
401
+ const nextSteps = await this.suggestPostExecutionSteps(command, outcome);
402
+ if (nextSteps.length > 0) {
403
+ console.log('\nšŸ”„ What to do next:');
404
+ nextSteps.slice(0, 2).forEach((step, index) => {
405
+ console.log(` ${index + 1}. ${step}`);
406
+ });
407
+ }
408
+ }
409
+
410
+ /**
411
+ * Provide success guidance
412
+ */
413
+ async provideSuccessGuidance(command, output) {
414
+ const userStatus = this.guidanceSystem.getUserStatus();
415
+ if (!userStatus || userStatus.experienceLevel === 'expert') {
416
+ return;
417
+ }
418
+
419
+ // Congratulate novice users
420
+ if (userStatus.experienceLevel === 'novice' && Math.random() < 0.3) {
421
+ console.log('\nšŸŽ‰ Well done! Command executed successfully.');
422
+ }
423
+
424
+ // Provide learning opportunities
425
+ if (command.includes('swarm-init') && userStatus.experienceLevel === 'novice') {
426
+ console.log('\nšŸ’” Next: Try spawning agents with "claude-flow-novice agent-spawn <type>"');
427
+ }
428
+ }
429
+
430
+ /**
431
+ * Provide error guidance
432
+ */
433
+ async provideErrorGuidance(command, error) {
434
+ const errorMessage = error.message || String(error);
435
+
436
+ // Get contextual error guidance
437
+ const guidance = await this.guidanceSystem.getGuidance({
438
+ command: 'error-recovery',
439
+ taskType: 'debugging',
440
+ errorMessages: [errorMessage],
441
+ currentCommand: command,
442
+ });
443
+
444
+ if (guidance?.adaptive?.suggestions) {
445
+ console.log('\nšŸ”§ Error recovery suggestions:');
446
+ guidance.adaptive.suggestions.slice(0, 2).forEach((suggestion, index) => {
447
+ console.log(` ${index + 1}. ${suggestion.message}`);
448
+ });
449
+ }
450
+
451
+ // Track repeated errors for learning
452
+ this.sessionContext.errorCount++;
453
+ if (this.sessionContext.errorCount >= 3) {
454
+ console.log(
455
+ '\nšŸ’” Tip: Consider using "claude-flow-novice guidance help-with <command>" for detailed guidance',
456
+ );
457
+ }
458
+ }
459
+
460
+ /**
461
+ * Suggest next steps after command execution
462
+ */
463
+ async suggestPostExecutionSteps(command, outcome) {
464
+ const steps = [];
465
+
466
+ if (outcome === 'success') {
467
+ if (command.includes('swarm-init')) {
468
+ steps.push('Spawn specialized agents for your task');
469
+ steps.push('Monitor swarm status with "claude-flow-novice swarm-status"');
470
+ }
471
+
472
+ if (command.includes('agent-spawn')) {
473
+ steps.push('Orchestrate tasks with "claude-flow-novice task-orchestrate"');
474
+ steps.push('Check agent metrics with "claude-flow-novice agent-metrics"');
475
+ }
476
+
477
+ if (command.includes('task-orchestrate')) {
478
+ steps.push('Monitor task progress with "claude-flow-novice task-status"');
479
+ steps.push('Review results when complete');
480
+ }
481
+ }
482
+
483
+ return steps;
484
+ }
485
+
486
+ /**
487
+ * Celebrate milestone achievements
488
+ */
489
+ celebrateMilestone(data) {
490
+ console.log(`\nšŸ† Milestone achieved: ${data.description}!`);
491
+ console.log(` Points earned: ${data.points}`);
492
+
493
+ if (data.unlocks?.length > 0) {
494
+ console.log(` šŸ”“ Unlocked: ${data.unlocks.join(', ')}`);
495
+ }
496
+ }
497
+
498
+ /**
499
+ * Announce experience level changes
500
+ */
501
+ announceExperienceLevelChange(data) {
502
+ console.log(`\nšŸŽ‰ Congratulations! You've advanced to ${data.newLevel} level!`);
503
+
504
+ if (data.newLevel === 'intermediate') {
505
+ console.log(' You now have access to more advanced features.');
506
+ } else if (data.newLevel === 'expert') {
507
+ console.log(" You're now recognized as an expert user!");
508
+ }
509
+ }
510
+
511
+ /**
512
+ * Show welcome guidance for new session
513
+ */
514
+ showWelcomeGuidance(userStatus) {
515
+ const level = userStatus.experienceLevel;
516
+
517
+ if (level === 'novice') {
518
+ console.log("\nšŸ‘‹ Welcome! As a novice user, you'll receive detailed guidance.");
519
+ console.log(' Use "claude-flow-novice guidance help-with <command>" anytime for help.');
520
+ } else if (level === 'intermediate') {
521
+ console.log(
522
+ `\nšŸ‘‹ Welcome back! You're ${Math.round(userStatus.progressToNext * 100)}% of the way to expert level.`,
523
+ );
524
+ } else if (level === 'expert') {
525
+ console.log('\nšŸ‘‹ Welcome back, expert! Guidance is minimal but available on demand.');
526
+ }
527
+ }
528
+
529
+ /**
530
+ * Analyze file context for guidance
531
+ */
532
+ async analyzeFileContext(filePath, operation) {
533
+ const context = {
534
+ fileType: path.extname(filePath),
535
+ isTestFile: filePath.includes('.test.') || filePath.includes('.spec.'),
536
+ isConfigFile: ['package.json', '.eslintrc', 'tsconfig.json'].some((config) =>
537
+ filePath.includes(config),
538
+ ),
539
+ operation,
540
+ };
541
+
542
+ // Add more context based on file analysis
543
+ return context;
544
+ }
545
+
546
+ /**
547
+ * Infer task type from file path
548
+ */
549
+ inferTaskTypeFromFile(filePath) {
550
+ if (filePath.includes('.test.') || filePath.includes('.spec.')) {
551
+ return 'testing';
552
+ }
553
+ if (filePath.includes('package.json') || filePath.includes('config')) {
554
+ return 'configuration';
555
+ }
556
+ if (filePath.includes('.js') || filePath.includes('.ts')) {
557
+ return 'development';
558
+ }
559
+ if (filePath.includes('.md') || filePath.includes('README')) {
560
+ return 'documentation';
561
+ }
562
+ return 'general';
563
+ }
564
+
565
+ /**
566
+ * Get current project files for context
567
+ */
568
+ async getCurrentProjectFiles() {
569
+ // Implementation would scan current directory
570
+ // For now, return placeholder
571
+ return [];
572
+ }
573
+
574
+ /**
575
+ * Suggest next steps after file editing
576
+ */
577
+ async suggestNextSteps(filePath, operation) {
578
+ const steps = [];
579
+
580
+ if (filePath.includes('.test.')) {
581
+ steps.push('Run tests to verify changes');
582
+ steps.push('Check test coverage');
583
+ } else if (filePath.includes('.js') || filePath.includes('.ts')) {
584
+ steps.push('Run linter to check code quality');
585
+ steps.push('Consider writing tests for new functionality');
586
+ }
587
+
588
+ return steps;
589
+ }
590
+
591
+ /**
592
+ * Generate session summary
593
+ */
594
+ generateSessionSummary() {
595
+ const totalCommands = this.sessionContext.commandHistory.length;
596
+ const successfulCommands = this.sessionContext.commandHistory.filter(
597
+ (cmd) => cmd.status === 'success',
598
+ ).length;
599
+
600
+ return {
601
+ totalCommands,
602
+ successfulCommands,
603
+ successRate: totalCommands > 0 ? Math.round((successfulCommands / totalCommands) * 100) : 0,
604
+ errorCount: this.sessionContext.errorCount,
605
+ milestonesAchieved: 0, // Would track during session
606
+ experienceLevelChanged: false, // Would track during session
607
+ newExperienceLevel: null,
608
+ };
609
+ }
610
+
611
+ /**
612
+ * Format duration in human-readable format
613
+ */
614
+ formatDuration(ms) {
615
+ const seconds = Math.floor(ms / 1000);
616
+ const minutes = Math.floor(seconds / 60);
617
+ const hours = Math.floor(minutes / 60);
618
+
619
+ if (hours > 0) {
620
+ return `${hours}h ${minutes % 60}m`;
621
+ } else if (minutes > 0) {
622
+ return `${minutes}m ${seconds % 60}s`;
623
+ } else {
624
+ return `${seconds}s`;
625
+ }
626
+ }
627
+ }
628
+
629
+ module.exports = GuidanceHooks;