Source: Z4nzu/hackingtool @ 01a51bb

How It Works

Hackingtool is a menu-driven Python CLI that aggregates 185+ security and pentesting tools into a unified terminal interface. It does not implement any security functionality itself — instead, it provides a categorized browsing experience that wraps installation (git clone, pip install, go install, apt-get) and execution of third-party tools. The user navigates through a hierarchy: main menu → category → tool → action (Install / Run / Update / Open Folder).

The framework is built on two base classes: HackingTool (a single tool definition) and HackingToolsCollection (a category containing multiple tools). Each tool is a declarative class with class-level attributes — TITLE, DESCRIPTION, INSTALL_COMMANDS, RUN_COMMANDS, PROJECT_URL — plus optional metadata for OS support, language requirements, and archival status. The base class provides all the plumbing: install detection, smart updates, install-all batch mode, and iterative menu loops.

The v2.0 rewrite (current version) added search (/query), tag-based filtering (t), task-based recommendations (r), OS-aware menu filtering, and install-status indicators (✔/✘). The only runtime Python dependency is rich — everything else is optional and per-tool.

Architecture

hackingtool.py        ← Entry point; main menu loop, search, tags, recommend
core.py               ← HackingTool + HackingToolsCollection base classes
constants.py          ← Version, paths, theme constants
config.py             ← JSON config loader (~/.hackingtool/config.json)
os_detect.py          ← OS/distro/package-manager detection (module-level singleton)
install.py            ← System installer (requires root)
install.sh            ← One-liner curl|bash installer
tools/
  <category>.py       ← One file per category, containing tool class definitions
  others/             ← Sub-category for miscellaneous tools
LayerResponsibility
hackingtool.pyMenu rendering, user interaction, search/tag/recommend
core.pyBase classes, install/run/update logic, menu loops
tools/*.pyDeclarative tool definitions (~3,300 lines total across 20+ files)
os_detect.pyPlatform detection (Linux distro, macOS, WSL, package manager)
config.pyPersistent user config (tools directory, preferences)

The architecture is flat and simple. There is no plugin system, no dynamic loading, and no network layer. Every tool is a hardcoded class instantiation imported at the top of hackingtool.py.

The Spine

The execution flow is:

  1. hackingtool.py::main() — Python 3.10 guard, OS check, ensure ~/.hackingtool/tools/ exists
  2. interact_menu() — Infinite loop: render banner + category grid, parse input
  3. Main menu dispatch — Number → all_tools[n].show_options(), /query → search, t → tags, r → recommend, q → quit
  4. HackingToolsCollection.show_options() — Filter tools by OS/archived status, render tool table, parse choice
  5. HackingTool.show_options() — Show Install/Run/Update/Open Folder options
  6. HackingTool.install() or HackingTool.run() — Execute shell commands via os.system() or subprocess.run()

The menu system uses iterative while True loops with return for back-navigation — deliberately avoiding recursion to prevent stack growth (noted explicitly in source comments).

Key Patterns

Declarative tool definitions. Most tools require zero custom code — they just set class attributes:

class Nuclei(HackingTool):
    TITLE = "Nuclei (Vulnerability Scanner)"
    DESCRIPTION = "Fast, template-based vulnerability scanner..."
    REQUIRES_GO = True
    INSTALL_COMMANDS = [
        "go install -v github.com/projectdiscovery/nuclei/v3/cmd/nuclei@latest",
        "nuclei -update-templates",
    ]
    RUN_COMMANDS = ["nuclei -h"]
    PROJECT_URL = "https://github.com/projectdiscovery/nuclei"

Shell command execution via os.system(). The base class install() and run() methods pass commands to os.system() for INSTALL_COMMANDS and RUN_COMMANDS defined as simple strings. Tools with custom run() overrides use subprocess.run() with cwd= to avoid CWD corruption — a deliberate fix from earlier versions that used os.chdir().

OS-aware filtering. HackingToolsCollection._active_tools() filters by SUPPORTED_OS against the detected platform. Linux-only tools (wireless attacks, many DDoS tools) are hidden on macOS. WSL detection warns about wireless incompatibility.

Smart install detection. HackingTool.is_installed checks shutil.which() for the binary, then falls back to checking if a git clone target directory exists. This powers the ✔/✘ status indicators.

Tag auto-derivation. Tags are both manually set (TAGS = ["osint"]) and auto-derived from tool titles/descriptions via regex rules in _get_all_tags().

Non-Obvious Details

Command injection surface

The base install() and run() methods pass INSTALL_COMMANDS and RUN_COMMANDS to os.system(). Since these are hardcoded strings (not user input), the risk is contained. However, some tools’ custom run() methods use Prompt.ask() for user input and pass it to subprocess.run() — newer tools use list form, but the pattern is inconsistent across older tool definitions.

Bug fix history is visible in code comments

The codebase contains comments like # Bug 3 fix, # Bug 4 fix, # Vuln 1 fix — indicating active security hardening. Notable fixes include replacing os.system("cd foo; cmd") with subprocess.run(cwd=), removing sudo su from install commands, and switching from os.system(string_concat) to subprocess.run([list]) to prevent command injection.

README is auto-generated

generate_readme.py imports AllTools from hackingtool.py and programmatically generates the README tables from tool definitions. This means the README stays in sync with the code.

The 73k stars do not reflect code quality. The actual application logic is ~1,200 lines of Python (core.py + hackingtool.py), with the remaining ~3,300 lines being declarative tool definitions. The project’s value is primarily curation — organizing well-known tools into a browsable menu.

All external tools are installed at runtime into ~/.hackingtool/tools/. The install commands git clone and build into this directory. There is no sandboxing — tools are installed with full system privileges (many require sudo).

Assessment

Strengths:

  • Clean OOP design with two base classes that handle all plumbing
  • OS-aware menu filtering prevents showing Linux-only tools on macOS
  • Smart update detection across install methods (git pull, pip —upgrade, go install)
  • Active archival system marks dead/unmaintained tools (e.g., Python 2-only tools)
  • Only dependency is rich — everything else is optional
  • The v2.0 rewrite is genuinely well-structured compared to typical “script kid” tools

Concerns:

  • Curatorial wrapper, not a tool. Hackingtool adds no security capability — it’s a menu for running other tools. Each wrapped tool must be installed and maintained separately.
  • No error handling for failed installs. os.system() return codes are ignored in the base install() method. Failed dependency installations silently continue.
  • Inconsistent execution patterns. Some tools use os.system(), others subprocess.run() with shell=False, others with shell=True. No validation of user inputs before passing to subprocesses in older tool definitions.
  • No isolation or dependency management for wrapped tools. All git clone targets share the same directory. Python tools may conflict with each other or the host system.
  • DDoS tools included. Despite “for authorized testing only” disclaimers, the inclusion of multiple DDoS attack tools with trivial interfaces (enter URL, press enter) lowers the barrier to misuse.

Recommendations:

  • For security professionals: install individual tools directly — the wrapper adds no functionality you can’t get with apt install or pip install
  • For learners: useful as a catalog of security tools, but understand each tool independently before using it
  • For developers: the OOP framework in core.py is a clean pattern for building CLI launchers — the declarative tool definition approach is genuinely elegant