Skills-4-SE design-smell-detector
Identify design quality issues in code including high coupling, low cohesion, God classes, long methods, and other code smells. Use when: (1) Reviewing code architecture and design quality, (2) Identifying refactoring opportunities, (3) Detecting God classes or classes with too many responsibilities, (4) Finding high coupling or low cohesion issues, (5) Analyzing code maintainability and technical debt. Detects coupling smells, cohesion problems, complexity issues, size violations, and encapsulation problems with actionable refactoring suggestions.
git clone https://github.com/ArabelaTso/Skills-4-SE
T=$(mktemp -d) && git clone --depth=1 https://github.com/ArabelaTso/Skills-4-SE "$T" && mkdir -p ~/.claude/skills && cp -r "$T/skills/design-smell-detector" ~/.claude/skills/arabelatso-skills-4-se-design-smell-detector && rm -rf "$T"
skills/design-smell-detector/SKILL.mdDesign Smell Detector
Identify and address design quality issues in code through automated smell detection and refactoring guidance.
Quick Start
Detect Design Smells
# Analyze a single file python scripts/detect_smells.py src/app.py # Analyze entire directory python scripts/detect_smells.py src/ # Output as JSON python scripts/detect_smells.py src/ --format json
Example Output
Found 5 design smell(s): 1 critical, 3 major, 1 minor CRITICAL ISSUES: 🔴 src/services.py:45 - God Class Class 'UserManager' has 25 methods (threshold: 20) 💡 Split into multiple smaller, focused classes MAJOR ISSUES: 🟠 src/models.py:120 - Low Cohesion Class 'Order' has low cohesion (score: 0.25) 💡 Group related methods/attributes or split class 🟠 src/utils.py:89 - Long Method Method 'process_order' has 67 lines (threshold: 50) 💡 Extract smaller methods or refactor
Design Smells Detected
Coupling Smells
High Coupling: Too many dependencies
- Module imports > 20
- Constructor dependencies > 10
- Changes cascade across classes
Feature Envy: Method uses other class more than own
- External access > internal access
- Method should move to envied class
Inappropriate Intimacy: Classes too tightly coupled
- Accessing private fields of other classes
- Excessive use of getters/setters
Cohesion Smells
Low Cohesion: Class members unrelated
- LCOM (Lack of Cohesion) > 0.7
- Methods don't share instance variables
- Class has multiple responsibilities
God Class: Class knows/does too much
- Methods > 20
- Attributes > 15
- Lines of code > 500
Complexity Smells
High Cyclomatic Complexity: Too many decision points
- Complexity > 10
- Deeply nested conditionals
- Many if/else, loops
Long Method: Method too long
- Lines of code > 50
- Multiple responsibilities
- Hard to understand
Size Smells
Long Parameter List: Too many parameters
- Parameters > 5
- Related parameters not grouped
- Method signature hard to understand
Large Module: Module too large
- Classes > 20
- Lines of code > 1000
- Multiple responsibilities
Encapsulation Smells
Data Class: Only data, no behavior
- Only getters/setters
- No business logic
- Missing encapsulation
Exposed Internal State: Implementation details exposed
- Public mutable fields
- Returns references to internal collections
- Breaks encapsulation
Detection Workflow
1. Run Detection
Analyze codebase for design smells:
python scripts/detect_smells.py src/
2. Review Results
Examine detected smells by severity:
- Critical: God classes, severe coupling issues
- Major: Low cohesion, long methods, high complexity
- Minor: Long parameter lists, feature envy
3. Prioritize Refactoring
Focus on:
- Critical issues first
- Frequently changed code
- High-impact, low-effort improvements
4. Apply Refactoring
Use refactoring strategies based on smell type.
See refactoring_strategies.md for detailed solutions.
5. Verify Improvements
Re-run detection to measure progress:
python scripts/detect_smells.py src/
Compare metrics before/after.
Common Design Smells
God Class
Symptoms:
- Too many methods (>20)
- Too many attributes (>15)
- Low cohesion
- Multiple responsibilities
Example:
# ❌ God Class class Application: # 30+ methods handling: # - User management # - Order processing # - Payment handling # - Reporting # - Email notifications # - File operations pass
Refactoring:
# ✅ Split by responsibility class UserManager: pass class OrderProcessor: pass class PaymentHandler: pass class ReportGenerator: pass
High Coupling
Symptoms:
- Too many imports (>20)
- Too many constructor dependencies
- Changes cascade across classes
Example:
# ❌ High coupling class UserService: def __init__(self): self.db = Database() self.cache = Cache() self.logger = Logger() self.validator = Validator() self.email = EmailService() self.sms = SMSService() # ... many more
Refactoring:
# ✅ Dependency injection class UserService: def __init__(self, db, logger, notifier): self.db = db self.logger = logger self.notifier = notifier # Abstraction
Low Cohesion
Symptoms:
- Methods don't share attributes
- Class does unrelated things
- LCOM score > 0.7
Example:
# ❌ Low cohesion class UserManager: def create_user(self): pass def send_email(self): pass def log_activity(self): pass def calculate_discount(self): pass
Refactoring:
# ✅ High cohesion - focused classes class UserRepository: def create_user(self): pass class EmailService: def send_email(self): pass class ActivityLogger: def log_activity(self): pass
Long Method
Symptoms:
- Method > 50 lines
- Multiple responsibilities
- Hard to understand
Example:
# ❌ Long method (100+ lines) def process_order(order): # Validate (20 lines) # Calculate price (15 lines) # Save to DB (10 lines) # Send email (20 lines) # Update stats (10 lines) # Log activity (15 lines) pass
Refactoring:
# ✅ Extract methods def process_order(order): validate_order(order) total = calculate_total(order) save_order(order, total) send_confirmation(order) update_statistics() log_activity(order)
Refactoring Strategies
Reduce Coupling
Dependency Injection:
# Inject dependencies instead of creating them class OrderService: def __init__(self, db, logger): self.db = db self.logger = logger
Interface Abstraction:
# Depend on abstractions, not implementations from abc import ABC, abstractmethod class PaymentGateway(ABC): @abstractmethod def charge(self, amount): pass class PaymentProcessor: def __init__(self, gateway: PaymentGateway): self.gateway = gateway
Improve Cohesion
Extract Class:
# Split into focused classes class User: # User data and behavior class UserRepository: # Database operations class EmailService: # Email operations
Move Method:
# Move method to appropriate class class Account: def get_formatted_balance(self): # Moved from reporter return f"${self.balance:.2f}"
Reduce Complexity
Extract Method:
# Break complex method into smaller ones def process_order(order): validate_order(order) calculate_total(order) save_order(order)
Replace Conditional with Polymorphism:
# Use inheritance instead of conditionals class Customer: def calculate_price(self, base_price): return base_price class PremiumCustomer(Customer): def calculate_price(self, base_price): return base_price * 0.9
For comprehensive refactoring strategies, see refactoring_strategies.md.
Metrics and Thresholds
Detection Thresholds
| Smell | Metric | Threshold |
|---|---|---|
| God Class | Methods | > 20 |
| God Class | Attributes | > 15 |
| God Class | LOC | > 500 |
| High Coupling | Imports | > 20 |
| Low Cohesion | LCOM | > 0.7 |
| Long Method | LOC | > 50 |
| High Complexity | Cyclomatic | > 10 |
| Long Parameter List | Parameters | > 5 |
Key Metrics
LCOM (Lack of Cohesion of Methods):
- Measures how methods share instance variables
- Range: 0.0 (high cohesion) to 1.0 (low cohesion)
- Lower is better
Cyclomatic Complexity:
- Number of linearly independent paths
- Each if/while/for adds 1
- Lower is better (< 10)
Fan-out (Coupling):
- Number of dependencies
- Lower is better (< 10)
Design Smell Catalog
For complete descriptions, examples, and solutions for all design smells, see smell_catalog.md.
Includes:
- Coupling Smells: High coupling, Feature Envy, Inappropriate Intimacy
- Cohesion Smells: Low cohesion, God Class
- Complexity Smells: High complexity, Long Method
- Size Smells: Long Parameter List, Large Module
- Encapsulation Smells: Data Class, Exposed Internal State
Best Practices
1. Detect Regularly
Integrate into workflow:
# Pre-commit hook python scripts/detect_smells.py src/ # CI/CD pipeline make check-design-smells
2. Track Metrics Over Time
Monitor trends:
Sprint 1: 15 God classes, 45 long methods Sprint 2: 12 God classes, 38 long methods Sprint 3: 8 God classes, 25 long methods
3. Prioritize Strategically
Focus on:
- Code changed frequently
- Critical business logic
- High-impact areas
4. Refactor Incrementally
- Small, safe changes
- Run tests after each change
- Commit frequently
5. Measure Improvements
Before/after metrics:
Before: LCOM = 0.85 (low cohesion) After: LCOM = 0.25 (high cohesion)
Common Scenarios
Scenario 1: Legacy Codebase Modernization
Goal: Identify technical debt in legacy system
Approach:
- Run smell detection on entire codebase
- Generate metrics report
- Identify top 10 worst files
- Create refactoring backlog
- Tackle incrementally
Scenario 2: Code Review Enhancement
Goal: Automated design quality checks in PR reviews
Approach:
- Add smell detection to CI pipeline
- Fail build if critical smells introduced
- Report metrics in PR comments
- Require fixes before merge
Scenario 3: Architecture Assessment
Goal: Evaluate system architecture quality
Approach:
- Detect coupling and cohesion issues
- Identify God classes and large modules
- Analyze dependency structure
- Recommend architectural improvements
Integration with Development Workflow
Pre-commit Hook
#!/bin/bash # .git/hooks/pre-commit python scripts/detect_smells.py src/ if [ $? -ne 0 ]; then echo "Critical design smells detected. Commit aborted." exit 1 fi
CI/CD Pipeline
# .github/workflows/quality.yml name: Design Quality Check on: [push, pull_request] jobs: check-smells: runs-on: ubuntu-latest steps: - uses: actions/checkout@v3 - name: Detect design smells run: python scripts/detect_smells.py src/ - name: Upload report uses: actions/upload-artifact@v3 with: name: smell-report path: smell-report.json
IDE Integration
Most IDEs support similar analysis through plugins:
- PyCharm: Built-in inspections for coupling/cohesion
- VS Code: Python linting extensions
- SonarLint: Real-time smell detection
Troubleshooting
False Positives
Problem: Legitimate design flagged as smell
Solution:
- Understand context and constraints
- Consider if threshold should be adjusted
- Document reasons for exception
Overwhelming Results
Problem: Too many smells to address
Solution:
- Filter by severity (critical first)
- Focus on frequently changed code
- Set incremental goals
Refactoring Breaks Tests
Problem: Tests fail after refactoring
Solution:
- Ensure comprehensive test coverage first
- Refactor incrementally
- Run tests after each small change
Reference Documentation
Design Smell Catalog
See smell_catalog.md for:
- Complete smell definitions
- Detection criteria and thresholds
- Code examples (before/after)
- Metrics explanations (LCOM, cyclomatic complexity, fan-out)
- All coupling, cohesion, complexity, size, and encapsulation smells
Refactoring Strategies
See refactoring_strategies.md for:
- Coupling reduction strategies (DI, interfaces, facades)
- Cohesion improvement (extract class, move method)
- Complexity reduction (extract method, polymorphism)
- Size reduction (split classes, parameter objects)
- Encapsulation improvement
- Refactoring workflow and best practices
- Anti-patterns to avoid
- Success metrics