mirror of
https://github.com/SuperClaude-Org/SuperClaude_Framework.git
synced 2025-12-29 16:16:08 +00:00
feat: Enhanced Framework-Hooks with comprehensive testing and validation
- Update compression engine with improved YAML handling and error recovery - Add comprehensive test suite with 10 test files covering edge cases - Enhance hook system with better MCP intelligence and pattern detection - Improve documentation with detailed configuration guides - Add learned patterns for project optimization - Strengthen notification and session lifecycle hooks 🤖 Generated with [Claude Code](https://claude.ai/code) Co-Authored-By: Claude <noreply@anthropic.com>
This commit is contained in:
@@ -54,8 +54,10 @@ class NotificationHook:
|
||||
self.mcp_intelligence = MCPIntelligence()
|
||||
self.compression_engine = CompressionEngine()
|
||||
|
||||
# Initialize learning engine
|
||||
cache_dir = Path("cache")
|
||||
# Initialize learning engine with installation directory cache
|
||||
import os
|
||||
cache_dir = Path(os.path.expanduser("~/.claude/cache"))
|
||||
cache_dir.mkdir(parents=True, exist_ok=True)
|
||||
self.learning_engine = LearningEngine(cache_dir)
|
||||
|
||||
# Load notification configuration
|
||||
|
||||
@@ -54,8 +54,10 @@ class PostToolUseHook:
|
||||
self.mcp_intelligence = MCPIntelligence()
|
||||
self.compression_engine = CompressionEngine()
|
||||
|
||||
# Initialize learning engine
|
||||
cache_dir = Path("cache")
|
||||
# Initialize learning engine with installation directory cache
|
||||
import os
|
||||
cache_dir = Path(os.path.expanduser("~/.claude/cache"))
|
||||
cache_dir.mkdir(parents=True, exist_ok=True)
|
||||
self.learning_engine = LearningEngine(cache_dir)
|
||||
|
||||
# Load hook-specific configuration from SuperClaude config
|
||||
|
||||
@@ -56,8 +56,10 @@ class PreCompactHook:
|
||||
self.mcp_intelligence = MCPIntelligence()
|
||||
self.compression_engine = CompressionEngine()
|
||||
|
||||
# Initialize learning engine
|
||||
cache_dir = Path("cache")
|
||||
# Initialize learning engine with installation directory cache
|
||||
import os
|
||||
cache_dir = Path(os.path.expanduser("~/.claude/cache"))
|
||||
cache_dir.mkdir(parents=True, exist_ok=True)
|
||||
self.learning_engine = LearningEngine(cache_dir)
|
||||
|
||||
# Load hook-specific configuration from SuperClaude config
|
||||
@@ -318,7 +320,7 @@ class PreCompactHook:
|
||||
content_type = metadata.get('content_type', '')
|
||||
file_path = metadata.get('file_path', '')
|
||||
|
||||
if any(pattern in file_path for pattern in ['/SuperClaude/', '/.claude/', 'framework']):
|
||||
if any(pattern in file_path for pattern in ['/.claude/', 'framework']):
|
||||
framework_score += 3
|
||||
|
||||
if any(pattern in content_type for pattern in user_indicators):
|
||||
|
||||
@@ -54,8 +54,10 @@ class PreToolUseHook:
|
||||
self.mcp_intelligence = MCPIntelligence()
|
||||
self.compression_engine = CompressionEngine()
|
||||
|
||||
# Initialize learning engine
|
||||
cache_dir = Path("cache")
|
||||
# Initialize learning engine with installation directory cache
|
||||
import os
|
||||
cache_dir = Path(os.path.expanduser("~/.claude/cache"))
|
||||
cache_dir.mkdir(parents=True, exist_ok=True)
|
||||
self.learning_engine = LearningEngine(cache_dir)
|
||||
|
||||
# Load hook-specific configuration from SuperClaude config
|
||||
|
||||
@@ -46,15 +46,20 @@ class SessionStartHook:
|
||||
def __init__(self):
|
||||
start_time = time.time()
|
||||
|
||||
# Initialize core components
|
||||
# Initialize only essential components immediately
|
||||
self.framework_logic = FrameworkLogic()
|
||||
self.pattern_detector = PatternDetector()
|
||||
self.mcp_intelligence = MCPIntelligence()
|
||||
self.compression_engine = CompressionEngine()
|
||||
|
||||
# Initialize learning engine with cache directory
|
||||
cache_dir = Path("cache")
|
||||
self.learning_engine = LearningEngine(cache_dir)
|
||||
# Lazy-load other components to improve performance
|
||||
self._pattern_detector = None
|
||||
self._mcp_intelligence = None
|
||||
self._compression_engine = None
|
||||
self._learning_engine = None
|
||||
|
||||
# Use installation directory for cache
|
||||
import os
|
||||
cache_dir = Path(os.path.expanduser("~/.claude/cache"))
|
||||
cache_dir.mkdir(parents=True, exist_ok=True)
|
||||
self._cache_dir = cache_dir
|
||||
|
||||
# Load hook-specific configuration from SuperClaude config
|
||||
self.hook_config = config_loader.get_hook_config('session_start')
|
||||
@@ -69,6 +74,34 @@ class SessionStartHook:
|
||||
# Performance tracking using configuration
|
||||
self.initialization_time = (time.time() - start_time) * 1000
|
||||
self.performance_target_ms = config_loader.get_hook_config('session_start', 'performance_target_ms', 50)
|
||||
|
||||
@property
|
||||
def pattern_detector(self):
|
||||
"""Lazy-load pattern detector to improve initialization performance."""
|
||||
if self._pattern_detector is None:
|
||||
self._pattern_detector = PatternDetector()
|
||||
return self._pattern_detector
|
||||
|
||||
@property
|
||||
def mcp_intelligence(self):
|
||||
"""Lazy-load MCP intelligence to improve initialization performance."""
|
||||
if self._mcp_intelligence is None:
|
||||
self._mcp_intelligence = MCPIntelligence()
|
||||
return self._mcp_intelligence
|
||||
|
||||
@property
|
||||
def compression_engine(self):
|
||||
"""Lazy-load compression engine to improve initialization performance."""
|
||||
if self._compression_engine is None:
|
||||
self._compression_engine = CompressionEngine()
|
||||
return self._compression_engine
|
||||
|
||||
@property
|
||||
def learning_engine(self):
|
||||
"""Lazy-load learning engine to improve initialization performance."""
|
||||
if self._learning_engine is None:
|
||||
self._learning_engine = LearningEngine(self._cache_dir)
|
||||
return self._learning_engine
|
||||
|
||||
def initialize_session(self, session_context: dict) -> dict:
|
||||
"""
|
||||
|
||||
@@ -239,7 +239,6 @@ class CompressionEngine:
|
||||
|
||||
# Framework content - complete exclusion
|
||||
framework_patterns = [
|
||||
'/SuperClaude/SuperClaude/',
|
||||
'~/.claude/',
|
||||
'.claude/',
|
||||
'SuperClaude/',
|
||||
|
||||
@@ -475,4 +475,86 @@ class MCPIntelligence:
|
||||
efficiency_ratio = metrics.get('efficiency_ratio', 1.0)
|
||||
efficiency_scores.append(min(efficiency_ratio, 2.0)) # Cap at 200% efficiency
|
||||
|
||||
return sum(efficiency_scores) / len(efficiency_scores) if efficiency_scores else 1.0
|
||||
return sum(efficiency_scores) / len(efficiency_scores) if efficiency_scores else 1.0
|
||||
|
||||
def select_optimal_server(self, tool_name: str, context: Dict[str, Any]) -> str:
|
||||
"""
|
||||
Select the most appropriate MCP server for a given tool and context.
|
||||
|
||||
Args:
|
||||
tool_name: Name of the tool to be executed
|
||||
context: Context information for intelligent selection
|
||||
|
||||
Returns:
|
||||
Name of the optimal server for the tool
|
||||
"""
|
||||
# Map common tools to server capabilities
|
||||
tool_server_mapping = {
|
||||
'read_file': 'morphllm',
|
||||
'write_file': 'morphllm',
|
||||
'edit_file': 'morphllm',
|
||||
'analyze_architecture': 'sequential',
|
||||
'complex_reasoning': 'sequential',
|
||||
'debug_analysis': 'sequential',
|
||||
'create_component': 'magic',
|
||||
'ui_component': 'magic',
|
||||
'design_system': 'magic',
|
||||
'browser_test': 'playwright',
|
||||
'e2e_test': 'playwright',
|
||||
'performance_test': 'playwright',
|
||||
'get_documentation': 'context7',
|
||||
'library_docs': 'context7',
|
||||
'framework_patterns': 'context7',
|
||||
'semantic_analysis': 'serena',
|
||||
'project_context': 'serena',
|
||||
'memory_management': 'serena'
|
||||
}
|
||||
|
||||
# Primary server selection based on tool
|
||||
primary_server = tool_server_mapping.get(tool_name)
|
||||
|
||||
if primary_server:
|
||||
return primary_server
|
||||
|
||||
# Context-based selection for unknown tools
|
||||
if context.get('complexity', 'low') == 'high':
|
||||
return 'sequential'
|
||||
elif context.get('type') == 'ui':
|
||||
return 'magic'
|
||||
elif context.get('type') == 'browser':
|
||||
return 'playwright'
|
||||
elif context.get('file_count', 1) > 10:
|
||||
return 'serena'
|
||||
else:
|
||||
return 'morphllm' # Default fallback
|
||||
|
||||
def get_fallback_server(self, tool_name: str, context: Dict[str, Any]) -> str:
|
||||
"""
|
||||
Get fallback server when primary server fails.
|
||||
|
||||
Args:
|
||||
tool_name: Name of the tool
|
||||
context: Context information
|
||||
|
||||
Returns:
|
||||
Name of the fallback server
|
||||
"""
|
||||
primary_server = self.select_optimal_server(tool_name, context)
|
||||
|
||||
# Define fallback chains
|
||||
fallback_chains = {
|
||||
'sequential': 'serena',
|
||||
'serena': 'morphllm',
|
||||
'morphllm': 'context7',
|
||||
'magic': 'morphllm',
|
||||
'playwright': 'sequential',
|
||||
'context7': 'morphllm'
|
||||
}
|
||||
|
||||
fallback = fallback_chains.get(primary_server, 'morphllm')
|
||||
|
||||
# Avoid circular fallback
|
||||
if fallback == primary_server:
|
||||
return 'morphllm'
|
||||
|
||||
return fallback
|
||||
@@ -292,4 +292,6 @@ class UnifiedConfigLoader:
|
||||
|
||||
|
||||
# Global instance for shared use across hooks
|
||||
config_loader = UnifiedConfigLoader(".")
|
||||
# Use Claude installation directory instead of current working directory
|
||||
import os
|
||||
config_loader = UnifiedConfigLoader(os.path.expanduser("~/.claude"))
|
||||
@@ -55,8 +55,10 @@ class StopHook:
|
||||
self.mcp_intelligence = MCPIntelligence()
|
||||
self.compression_engine = CompressionEngine()
|
||||
|
||||
# Initialize learning engine
|
||||
cache_dir = Path("cache")
|
||||
# Initialize learning engine with installation directory cache
|
||||
import os
|
||||
cache_dir = Path(os.path.expanduser("~/.claude/cache"))
|
||||
cache_dir.mkdir(parents=True, exist_ok=True)
|
||||
self.learning_engine = LearningEngine(cache_dir)
|
||||
|
||||
# Load hook-specific configuration from SuperClaude config
|
||||
@@ -508,7 +510,8 @@ class StopHook:
|
||||
persistence_result['compression_ratio'] = compression_result.compression_ratio
|
||||
|
||||
# Simulate saving (real implementation would use actual storage)
|
||||
cache_dir = Path("cache")
|
||||
cache_dir = Path(os.path.expanduser("~/.claude/cache"))
|
||||
cache_dir.mkdir(parents=True, exist_ok=True)
|
||||
session_file = cache_dir / f"session_{context['session_id']}.json"
|
||||
|
||||
with open(session_file, 'w') as f:
|
||||
|
||||
@@ -55,8 +55,10 @@ class SubagentStopHook:
|
||||
self.mcp_intelligence = MCPIntelligence()
|
||||
self.compression_engine = CompressionEngine()
|
||||
|
||||
# Initialize learning engine
|
||||
cache_dir = Path("cache")
|
||||
# Initialize learning engine with installation directory cache
|
||||
import os
|
||||
cache_dir = Path(os.path.expanduser("~/.claude/cache"))
|
||||
cache_dir.mkdir(parents=True, exist_ok=True)
|
||||
self.learning_engine = LearningEngine(cache_dir)
|
||||
|
||||
# Load task management configuration
|
||||
|
||||
Reference in New Issue
Block a user