Skip to main content

Advanced Frappe hooks analyzer and conflict detector

Project description

🔍 HookX

Advanced Frappe hooks analyzer and conflict detector for multi-app environments

PyPI version Python Support License: MIT PyPI Downloads

HookX is a high-performance Python library and CLI tool designed to analyze, inspect, and report on hooks in Frappe applications. It provides complete visibility into hooks.py files across apps, detects conflicts and overlapping methods, and generates comprehensive reports for developers, teams, and CI/CD pipelines.

🚀 Key Features

  • 🔍 Comprehensive Hook Scanning - Analyzes all hook types including doc_events, method overrides, scheduler events, and custom hooks
  • ⚡ Ultra-Fast Performance - Optimized with parallel processing, intelligent caching, and performance monitoring
  • 🎯 Intelligent Conflict Detection - Detects overlapping hooks with severity classification (Critical, High, Medium, Low)
  • 📊 Multiple Output Formats - Rich terminal tables, JSON, CSV, HTML, and Markdown reports
  • 🔄 CI/CD Integration - Built-in support for automated testing and deployment pipelines
  • 🎨 Rich Terminal UI - Beautiful, colored output with progress indicators and detailed formatting
  • 🏗️ App Hierarchy Awareness - Understands Frappe app load order and priority for accurate conflict resolution

📦 Installation

From PyPI (Recommended)

pip install hookx

From Source

git clone https://github.com/thisissharath/hookx.git
cd hookx
pip install -e .

Development Installation

git clone https://github.com/thisissharath/hookx.git
cd hookx
pip install -e ".[dev]"

🛠️ Quick Start

Command Line Usage

# Scan entire Frappe bench
hookx scan /path/to/frappe-bench

# Scan specific site with app load order
hookx scan /path/to/frappe-bench/sites/mysite

# Scan single app
hookx scan /path/to/frappe-bench/apps/erpnext

# Export results for CI/CD
hookx export /path/to/bench results.json --fail-on-critical

# Quick conflict check
hookx check /path/to/bench --exit-code

# Validate hooks syntax
hookx validate /path/to/app

Python API Usage

from hookx import HookX

# Initialize scanner
scanner = HookX()

# Full comprehensive scan with all details
report = scanner.full_scan_report("/path/to/frappe-bench", save_to="report.json")
print(f"Found {report['summary']['total_conflicts']} conflicts")

# Quick scan for fast checks
quick = scanner.quick_scan("/path/to/frappe-bench")
print(f"Status: {quick['status']}, Critical: {quick['critical_conflicts']}")

# Export for CI/CD
scanner.export_for_ci("/path/to/bench", "ci-report.json")

📋 Command Reference

hookx scan - Comprehensive Hook Analysis

Performs detailed analysis of hooks across Frappe apps with conflict detection.

hookx scan [PATH] [OPTIONS]

# Basic usage
hookx scan /home/frappe/frappe-bench
hookx scan /home/frappe/frappe-bench/sites/production
hookx scan /home/frappe/frappe-bench/apps/erpnext

# Output formats
hookx scan /path/to/bench --format json
hookx scan /path/to/bench --format csv --output report.csv
hookx scan /path/to/bench --format html --output report.html

# Filtering and options
hookx scan /path/to/bench --min-severity high
hookx scan /path/to/bench --site production --strict
hookx scan /path/to/bench --max-workers 8 --no-cache

Options:

  • --site, -s: Site name for app load order (when scanning bench)
  • --format, -f: Output format (table, json, csv, html, markdown)
  • --output, -o: Output file path
  • --min-severity: Minimum severity level (critical, high, medium, low, info)
  • --strict: Treat all conflicts as high severity
  • --no-cache: Disable caching for fresh results
  • --max-workers: Maximum worker threads for parallel processing

hookx check - Quick Conflict Detection

Fast conflict checking for CI/CD pipelines and automated validation.

hookx check [PATH] [OPTIONS]

# Basic conflict check
hookx check /path/to/bench

# CI/CD integration
hookx check /path/to/bench --exit-code
hookx check /path/to/bench --critical-only --quiet

# Exit codes:
# 0 - No conflicts found
# 1 - Conflicts found
# 2 - Error during scanning

Options:

  • --exit-code: Exit with non-zero code if conflicts found
  • --critical-only: Only check for critical conflicts
  • --strict: Treat all conflicts as critical
  • --quiet, -q: Suppress output, only return exit code

hookx validate - Syntax Validation

Validates hooks.py files for syntax errors and common issues.

hookx validate [PATH] [OPTIONS]

# Validate single file
hookx validate /path/to/app/hooks.py

# Validate app directory
hookx validate /path/to/app

# Validate entire bench
hookx validate /path/to/bench

# Auto-fix common issues
hookx validate /path/to/app --fix

Options:

  • --fix: Attempt to fix common syntax issues

hookx export - CI/CD Integration

Export structured reports for external tools and automated processing.

hookx export [PATH] [OUTPUT_FILE] [OPTIONS]

# Basic export
hookx export /path/to/bench results.json
hookx export /path/to/bench report.csv --format csv

# CI/CD integration
hookx export /path/to/bench ci-report.json --fail-on-critical
hookx export /path/to/bench results.json --site production --fail-on-conflicts

Options:

  • --format, -f: Export format (json, csv)
  • --site, -s: Site name for app load order
  • --fail-on-conflicts: Exit with code 1 if any conflicts found
  • --fail-on-critical: Exit with code 1 only if critical conflicts found

hookx info - System Information

Display version information and manage caches.

hookx info [OPTIONS]

# Show version
hookx info

# Clear caches
hookx info --clear-cache

# Show performance stats
hookx info --show-stats

📊 Supported Hook Types

HookX analyzes all Frappe hook types:

  • Doc Events - before_save, after_insert, on_submit, on_cancel, etc.
  • Method Overrides - override_whitelisted_methods, override_doctype_class
  • Scheduler Events - all, hourly, daily, weekly, monthly, cron
  • Website Hooks - website_route_rules, website_redirects
  • Boot Session - boot_session
  • Jinja Filters - jinja
  • Fixtures - fixtures
  • Custom Hooks - Any custom hook definitions

🎯 Conflict Detection

HookX uses sophisticated algorithms to detect various types of conflicts:

Severity Levels

  • 🔴 Critical - Will cause runtime errors (method overrides, class overrides)
  • 🟠 High - Likely to cause issues (doc events, route conflicts)
  • 🟡 Medium - May cause unexpected behavior (scheduler conflicts)
  • 🔵 Low - Informational (jinja filters, fixtures)
  • 🟢 Info - Just informational

Conflict Types

  • Method Override Conflicts - Multiple apps overriding the same method
  • DocType Class Conflicts - Multiple apps overriding the same DocType class
  • Doc Event Overlaps - Multiple handlers for the same DocType event
  • Route Conflicts - Conflicting website route rules
  • Scheduler Overlaps - Duplicate scheduler event definitions

📊 Output Formats

Terminal Table (Default)

Rich, colored tables with icons and formatting for immediate visual feedback.

JSON Export

{
  "scan_info": {
    "scan_id": "abc123",
    "timestamp": "2024-01-15T10:30:00",
    "scan_path": "/path/to/bench",
    "scan_type": "bench",
    "duration": 2.45
  },
  "summary": {
    "total_apps": 15,
    "total_hooks": 342,
    "total_conflicts": 3,
    "has_critical_conflicts": true
  },
  "conflicts": [
    {
      "severity": "critical",
      "hook_type": "override_whitelisted_methods",
      "description": "Multiple apps override get_item_details method",
      "affected_apps": ["erpnext", "custom_app"],
      "resolution_hint": "Consolidate method overrides into single app"
    }
  ]
}

CSV Export

Structured data suitable for spreadsheets and data analysis tools.

HTML Report

Professional reports with styling, perfect for documentation and sharing.

Markdown

Documentation-friendly format for README files and wikis.

🚀 CI/CD Integration

GitHub Actions

name: Hook Conflict Check
on: [push, pull_request]

jobs:
  check-hooks:
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v3
      - name: Setup Python
        uses: actions/setup-python@v4
        with:
          python-version: '3.11'
      
      - name: Install HookX
        run: pip install hookx
      
      - name: Check for hook conflicts
        run: hookx check . --exit-code --critical-only
      
      - name: Generate report
        if: always()
        run: hookx export . hook-report.json
      
      - name: Upload report
        if: always()
        uses: actions/upload-artifact@v3
        with:
          name: hook-analysis
          path: hook-report.json

GitLab CI

hook-analysis:
  stage: test
  image: python:3.11
  script:
    - pip install hookx
    - hookx check . --exit-code --critical-only
    - hookx export . hook-report.json
  artifacts:
    reports:
      junit: hook-report.json
    when: always

🏗️ Python API

Basic Usage

from hookx import HookX

# Initialize with options
scanner = HookX(
    max_workers=8,           # Parallel processing threads
    enable_cache=True,       # Intelligent caching
    strict_mode=False,       # Treat all conflicts as high severity
    console_output=True      # Rich terminal output
)

# Comprehensive scan
result = scanner.scan("/path/to/bench")
print(f"Found {result.total_conflicts} conflicts")

# Quick status check
has_conflicts = scanner.check_conflicts_only("/path/to/bench")
has_critical = scanner.has_critical_conflicts("/path/to/bench")

Preset Functions

# Full comprehensive report with auto-save
report = scanner.full_scan_report(
    "/path/to/bench", 
    save_to="detailed_report.json"
)

# Quick summary for dashboards
summary = scanner.quick_scan("/path/to/bench")
print(f"Status: {summary['status']}")
print(f"Critical conflicts: {summary['critical_conflicts']}")

Advanced Usage

# Scan specific components
bench_result = scanner.scan_bench("/path/to/bench")
site_result = scanner.scan_site("/path/to/site")
app_result = scanner.scan_app("/path/to/app")

# Validate hooks syntax
issues = scanner.validate_hooks("/path/to/app/hooks.py")
if issues:
    print("Validation issues found:", issues)

# Export for CI/CD
should_fail = scanner.export_for_ci(
    "/path/to/bench", 
    "ci-report.json"
)
exit(1 if should_fail else 0)

🔧 Configuration

Performance Tuning

# High-performance configuration
scanner = HookX(
    max_workers=16,          # More parallel threads
    enable_cache=True,       # Enable caching
    console_output=False     # Disable rich output for speed
)

# Memory-optimized configuration
scanner = HookX(
    max_workers=4,           # Fewer threads
    enable_cache=False,      # Disable caching
    strict_mode=True         # Strict conflict detection
)

CLI Performance Options

# High performance scanning
hookx scan /path/to/bench --max-workers 16 --no-cache

# Memory-optimized scanning
hookx scan /path/to/bench --max-workers 2

🐛 Troubleshooting

Common Issues

Issue: "No hooks.py found"

# Ensure you're scanning the correct path
hookx validate /path/to/app  # Check if app structure is correct

Issue: "Permission denied"

# Check file permissions
ls -la /path/to/hooks.py
chmod +r /path/to/hooks.py

Issue: "Import errors in hooks.py"

# Validate syntax first
hookx validate /path/to/app --fix

Performance Issues

Large bench scanning is slow:

# Use more workers and enable caching
hookx scan /path/to/bench --max-workers 8

Memory usage is high:

# Reduce workers and disable caching
hookx scan /path/to/bench --max-workers 2 --no-cache

Debug Mode

# Enable verbose logging
import logging
logging.basicConfig(level=logging.DEBUG)

scanner = HookX()
result = scanner.scan("/path/to/bench")

🤝 Contributing

We welcome contributions! Please see our Contributing Guide for details.

Development Setup

# Clone repository
git clone https://github.com/thisissharath/hookx.git
cd hookx

# Install in development mode
pip install -e ".[dev]"

# Run tests
pytest

# Run linting
black hookx/
flake8 hookx/
mypy hookx/

📚 Documentation

🐛 Bug Reports & Feature Requests

Please use GitHub Issues to report bugs or request features.

📄 License

This project is licensed under the MIT License - see the LICENSE file for details.

🙏 Acknowledgments

  • Built for the Frappe Framework community
  • Inspired by the need for better multi-app conflict detection
  • Thanks to all contributors and users providing feedback

Made with ❤️ by Sharath Kumar for the Frappe community

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

hookx-1.0.0.tar.gz (47.8 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

hookx-1.0.0-py3-none-any.whl (46.5 kB view details)

Uploaded Python 3

File details

Details for the file hookx-1.0.0.tar.gz.

File metadata

  • Download URL: hookx-1.0.0.tar.gz
  • Upload date:
  • Size: 47.8 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.2.0 CPython/3.13.7

File hashes

Hashes for hookx-1.0.0.tar.gz
Algorithm Hash digest
SHA256 fb06f56d67860934e5dea005a5d62445a34dc4159c09f3e66aef1864fac4ba4d
MD5 0da6a2fee4e4f816d50768bc9a7ea73b
BLAKE2b-256 28027e547a527b3a58d492078c193de7621d6799defdc4f745d435ec01ab05cf

See more details on using hashes here.

File details

Details for the file hookx-1.0.0-py3-none-any.whl.

File metadata

  • Download URL: hookx-1.0.0-py3-none-any.whl
  • Upload date:
  • Size: 46.5 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.2.0 CPython/3.13.7

File hashes

Hashes for hookx-1.0.0-py3-none-any.whl
Algorithm Hash digest
SHA256 c817b4797faf7a3f318facdb4e7f0f4c9fb135df3a2565b3d05ceb549d3157cd
MD5 777a38062961dff565d4b683b87ab055
BLAKE2b-256 5e8f6dbc7a4787504af88897ba436705af5d981a299c6512dd8836e1487ac847

See more details on using hashes here.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page