{"id":51359583,"url":"https://github.com/danyalkhattak/pawpy","last_synced_at":"2026-07-05T00:00:43.992Z","repository":{"id":368214137,"uuid":"1284058120","full_name":"Danyalkhattak/pawpy","owner":"Danyalkhattak","description":"The Most Powerful Wordlist Generator for OSINT, Pentesting, and Security Research","archived":false,"fork":false,"pushed_at":"2026-06-30T04:05:17.000Z","size":64,"stargazers_count":0,"open_issues_count":0,"forks_count":0,"subscribers_count":0,"default_branch":"main","last_synced_at":"2026-07-02T22:29:10.603Z","etag":null,"topics":["blue-team","cli","cybersecurity","dictionary-generator","fastapi","osint","password-cracking","password-generator","pentesting","python","red-team","security","wordlist","wordlist-generator"],"latest_commit_sha":null,"homepage":"https://pypi.org/project/pawpy-cli","language":"Python","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/Danyalkhattak.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null,"notice":null,"maintainers":null,"copyright":null,"agents":null,"dco":null,"cla":null}},"created_at":"2026-06-29T13:38:00.000Z","updated_at":"2026-06-30T04:05:21.000Z","dependencies_parsed_at":null,"dependency_job_id":null,"html_url":"https://github.com/Danyalkhattak/pawpy","commit_stats":null,"previous_names":["danyalkhattak/pawpy"],"tags_count":2,"template":false,"template_full_name":null,"purl":"pkg:github/Danyalkhattak/pawpy","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Danyalkhattak%2Fpawpy","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Danyalkhattak%2Fpawpy/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Danyalkhattak%2Fpawpy/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Danyalkhattak%2Fpawpy/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/Danyalkhattak","download_url":"https://codeload.github.com/Danyalkhattak/pawpy/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Danyalkhattak%2Fpawpy/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":35104115,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-05-26T15:22:16.424Z","status":"online","status_checked_at":"2026-07-03T02:00:05.635Z","response_time":110,"last_error":null,"robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":true,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["blue-team","cli","cybersecurity","dictionary-generator","fastapi","osint","password-cracking","password-generator","pentesting","python","red-team","security","wordlist","wordlist-generator"],"created_at":"2026-07-02T22:05:10.033Z","updated_at":"2026-07-03T23:01:08.128Z","avatar_url":"https://github.com/Danyalkhattak.png","language":"Python","funding_links":[],"categories":[],"sub_categories":[],"readme":"# Pawpy\n\n**The Most Powerful Wordlist Generator**\n\n\u003cp align=\"center\"\u003e\n  \u003cimg src=\"https://img.shields.io/badge/version-1.0.1-blue\" alt=\"Version\" /\u003e\n  \u003cimg src=\"https://img.shields.io/badge/python-3.8+-green\" alt=\"Python\" /\u003e\n  \u003cimg src=\"https://img.shields.io/badge/license-MIT-orange\" alt=\"License\" /\u003e\n  \u003cimg src=\"https://img.shields.io/badge/purpose-educational%20%7C%20authorised%20testing-red\" alt=\"Purpose\" /\u003e\n\u003c/p\u003e\n\n---\n\n## ⚠️ Ethical Use Only\n\nPawpy is designed **exclusively** for authorised security testing, password audits, and educational purposes. Unauthorised use against systems or accounts you do not own or have explicit permission to test is **illegal and unethical**. By using this tool, you confirm you have proper authorisation.\n\n---\n\n## Table of Contents\n\n- [Overview](#overview)\n- [Features](#features)\n- [Installation](#installation)\n- [Quick Start](#quick-start)\n- [CLI Reference](#cli-reference)\n- [Profile Format](#profile-format)\n- [Mutation Engine](#mutation-engine)\n- [Scoring \u0026 Filtering](#scoring--filtering)\n- [API \u0026 Dashboard](#api--dashboard)\n- [OSINT Plugins](#osint-plugins)\n- [Project Structure](#project-structure)\n- [Development](#development)\n- [License](#license)\n\n---\n\n## Overview\n\nPawpy is an open-source, terminal-based wordlist generator a powerful mutation engine, Markov chain blending, hashcat rule-file support, hybrid mask attacks, and a built-in web dashboard. It transforms target profile information into comprehensive, policy-compliant password candidate lists suitable for authorised penetration testing and security research.\n\nThe tool follows a modular pipeline architecture: profile data flows through successive mutation stages (leet-speak, mangle rules, date permutations, keyboard walks, Markov blending, custom templates, hashcat rules, hybrid masks) before optional scoring and policy filtering produces the final deduplicated, sorted wordlist.\n\n---\n\n## Features\n\n### Core\n\n| Feature | Description |\n|---------|-------------|\n| **Interactive Profiling** | Questionnaire for collecting target information |\n| **JSON Import** | Load single or multi-target profiles from JSON files |\n| **Multi-Target Cross-Referencing** | Merge multiple profiles for cross-referenced word generation |\n| **OSINT Plugin System** | Auto-discovery and execution of OSINT plugins from `profile/plugins/` |\n| **Embedded Top 10K Passwords** | Ships with common passwords; auto-updatable from SecLists |\n\n### Mutation Engine\n\n| Mutation | Description |\n|----------|-------------|\n| **Leet Speak** | 3 substitution levels (basic, extended, aggressive) with combinatorial expansion |\n| **Date Permutations** | 20+ variants per date: DDMM, MMDD, YYYY, YY, with separator combinations |\n| **Common Mangle Rules** | Capitalise, upper, lower, reverse, swapcase, append/prepend digits \u0026 symbols |\n| **Hashcat Rule Engine** | Full parser for hashcat/John-style `.rule` files (l, u, c, r, $X, ^X, sXY, iNX, oNX, d, p, z, [N, ]N) |\n| **Static Keyboard Walks** | 25+ built-in classic patterns (qwerty, asdf, zxcvbn, 1qaz2wsx, ...) |\n| **Dynamic Keyboard Walks** | BFS-generated walks on QWERTY adjacency graph up to configurable length |\n| **Two-Word Combinations** | All pairs of base words with 8 separator variants and case combinations |\n| **Year-Word Blends** | Append/prepend years (1990–current) and two-digit years to all base words |\n| **Markov Blending** | Character-level Markov chain (order 1–4) trained on corpus + profile words |\n| **Custom Templates** | Pattern engine: `[FirstName][Year][!]` with token resolution and combinatorial expansion |\n| **Hybrid Mask Attacks** | Simulates hashcat `-a 6` (word + right mask) and `-a 7` (left mask + word) |\n\n### Scoring \u0026 Filtering\n\n| Feature | Description |\n|---------|-------------|\n| **zxcvbn Scoring** | Optional strength-based pruning (scores 0–4) to remove trivially weak candidates |\n| **Policy Filtering** | Enforce minimum length, uppercase, lowercase, digit, and special character requirements |\n\n### API \u0026 Dashboard\n\n| Feature | Description |\n|---------|-------------|\n| **REST API** | FastAPI endpoint (`POST /generate`) accepting profile JSON, returning download URL |\n| **Web Dashboard** | Browser-based UI with real-time WebSocket progress logging |\n\n### Performance\n\n| Feature | Description |\n|---------|-------------|\n| **Multi-Process** | Configurable worker count via `-t` / `--threads` |\n| **GPU Acceleration** | Optional CuPy-based GPU rule application (graceful fallback to CPU) |\n| **External Merge Sort** | Billion-scale sorting with k-way heap merge for very large wordlists |\n\n### Modes\n\n| Mode | Flag | Behaviour |\n|------|------|----------|\n| **Normal** | *(default)* | All standard mutations |\n| **Lite** | `--lite` | Skips two-word combos, Markov, large hybrid, dynamic keyboard walks |\n| **Extreme** | `--extreme` | Enables year blends, Markov, dynamic keyboard walks, all heavy mutations |\n\n---\n\n## Installation\n\n### From PyPI (recommended)\n\n```bash\npip install pawpy-cli\n```\n\n### From Source\n\n```bash\ngit clone https://github.com/Danyalkhattak/pawpy.git\ncd pawpy\npip install -r requirements.txt\npip install -e .\n```\n\n### Optional Dependencies\n\n```bash\n# API \u0026 Dashboard\npip install fastapi uvicorn websockets\n\n# GPU acceleration (requires CUDA)\npip install cupy-cuda11x   # or cupy-cuda12x depending on your CUDA version\n\n# Password strength scoring\npip install zxcvbn\n\n# All optional\npip install -e \".[all]\"\n```\n\n---\n\n## Quick Start\n\n### Interactive Mode\n\n```bash\npawpy\n```\n\nThis launches the questionnaire. Answer the prompts (blank answers are fine) and Pawpy generates a wordlist to `pawpy_wordlist.txt`.\n\n### From JSON Profile\n\n```bash\npawpy -j profile.json -o wordlist.txt\n```\n\n### Multi-Target Mode\n\n```bash\npawpy --multi targets.json --extreme\n```\n\n### With Hashcat Rules\n\n```bash\npawpy -j profile.json --rules best64.rule\n```\n\n### Hybrid Mask Attack\n\n```bash\npawpy -j profile.json --hybrid-right ?d?d?d\n```\n\n### With Scoring \u0026 Policy Filter\n\n```bash\npawpy -j profile.json --min-strength 2 --min-length 8 --require-upper --require-digit\n```\n\n### Update Common Passwords\n\n```bash\npawpy update-passwords\n```\n\n### Start API Server\n\n```bash\npawpy api\n# Server runs at http://127.0.0.1:8000\n```\n\n### Launch Dashboard\n\n```bash\npawpy dashboard\n# Dashboard runs at http://127.0.0.1:8080\n```\n\n---\n\n## CLI Reference\n\n```\nusage: pawpy [-h] [-o FILE] [-j FILE] [--multi FILE] [--rules FILE]\n               [--template TMPL] [--hybrid-left MASK] [--hybrid-right MASK]\n               [--markov] [--markov-order N] [--markov-count N]\n               [--min-strength N] [--min-length N]\n               [--require-upper] [--require-lower] [--require-digit]\n               [--require-special] [--lite] [--extreme]\n               [--gpu] [-t N] [-v] [--verbose]\n\nOptions:\n  -o, --output FILE         Output file (default: pawpy_wordlist.txt)\n  -j, --import-json FILE    Import single profile from JSON\n  --multi FILE              Import multiple profiles from JSON array\n  --rules FILE              Load hashcat rule file\n  --template TEMPLATE       Custom pattern template (repeatable)\n  --hybrid-left MASK        Left mask for hybrid attack (?l?d)\n  --hybrid-right MASK       Right mask for hybrid attack (?d?d?d)\n  --markov                  Enable Markov chain blending\n  --markov-order N          Markov chain order (default: 2)\n  --markov-count N          Number of Markov words (default: 5000)\n  --min-strength N          Minimum zxcvbn score (0-4)\n  --min-length N            Minimum password length\n  --require-upper           Require uppercase letter\n  --require-lower           Require lowercase letter\n  --require-digit           Require digit\n  --require-special         Require special character\n  --lite                    Fast mode (skip heavy combos)\n  --extreme                 Enable all heavy mutations\n  --gpu                     Use GPU acceleration if available\n  -t, --threads N           Worker process count (default: CPU count)\n  -v, --version             Show version\n  --verbose                 Enable debug logging\n\nSub-commands:\n  update-passwords          Download latest common passwords from SecLists\n  api                       Start REST API server\n  dashboard                 Launch web dashboard\n```\n\n---\n\n## Profile Format\n\n### Single Profile (JSON)\n\n```json\n{\n  \"firstname\": \"John\",\n  \"lastname\": \"Doe\",\n  \"nickname\": \"Johnny\",\n  \"birthdate\": \"01011990\",\n  \"partner\": \"Jane\",\n  \"partner_nick\": \"Janey\",\n  \"partner_bdate\": \"02021992\",\n  \"pet\": \"Rex\",\n  \"company\": \"Acme\",\n  \"hometown\": \"Metropolis\",\n  \"favourite_color\": \"blue\",\n  \"children\": [\"Alice\", \"Bob\"],\n  \"keywords\": [\"guitar\", \"hiking\"]\n}\n```\n\n### Multi-Target Profile (JSON Array)\n\n```json\n[\n  { \"firstname\": \"John\", \"lastname\": \"Doe\", \"pet\": \"Rex\" },\n  { \"firstname\": \"Jane\", \"lastname\": \"Doe\", \"pet\": \"Buddy\" }\n]\n```\n\nWhen using `--multi`, Pawpy merges all profiles into a unified cross-referenced profile. This means base words from all targets are combined, enabling the mutation engine to generate cross-target combinations (e.g., John's first name paired with Jane's pet name).\n\n---\n\n## Mutation Engine\n\nThe mutation pipeline processes base words through multiple stages in sequence:\n\n```\nBase Words\n    │\n    ├── Leet Speak (3 levels)\n    ├── Common Mangle Rules (capitalize, reverse, append/prepend)\n    ├── Date Permutations (20+ variants per date)\n    ├── Hashcat Rules (if --rules provided)\n    ├── Custom Templates (if --template provided)\n    ├── Keyboard Walks (static + optional dynamic)\n    ├── Markov Blending (if --markov)\n    ├── Year-Word Blends (if not --lite)\n    ├── Two-Word Combinations (if not --lite)\n    ├── Hybrid Masks (if --hybrid-left/right)\n    └── Top 10K Common Passwords\n    │\n    ▼\nScoring \u0026 Policy Filtering\n    │\n    ▼\nDeduplication \u0026 Sort → Final Wordlist\n```\n\n### Leet Speak Levels\n\n| Level | Substitutions |\n|-------|---------------|\n| 1 (Basic) | a→@, e→3, i→1, o→0, s→$, t→7 |\n| 2 (Extended) | + i→!, s→5 |\n| 3 (Aggressive) | + a→4, l→1, b→8, g→9, h→# |\n\n### Hashcat Rule Support\n\nSupported rule commands:\n\n| Rule | Description | Example |\n|------|-------------|--------|\n| `l` | Lowercase all | `hello` → `hello` |\n| `u` | Uppercase all | `hello` → `HELLO` |\n| `c` | Capitalise first | `hello` → `Hello` |\n| `s` | Swap case | `Hello` → `hELLO` |\n| `r` | Reverse | `hello` → `olleh` |\n| `d` | Duplicate whole word | `hi` → `hihi` |\n| `p` | Duplicate first char | `hi` → `hhi` |\n| `z` | Duplicate last char | `hi` → `hii` |\n| `$X` | Append char X | `$!` → `pass!` |\n| `^X` | Prepend char X | `^1` → `1pass` |\n| `[N` | Keep first N chars | `[3` → `pas` |\n| `]N` | Keep last N chars | `]3` → `ssw` |\n| `iNX` | Insert char X at pos N | `i2X` → `paXssword` |\n| `oNX` | Overwrite char at pos N with X | `o0X` → `Xassword` |\n| `'XY` | Replace all X with Y | `'a@` → `p@ssword` |\n\n### Template Tokens\n\n| Token | Resolves To |\n|-------|-------------|\n| `[FirstName]` | First name (original, Capitalised, UPPER, lower) |\n| `[LastName]` | Last name |\n| `[Nickname]` | Nickname |\n| `[Pet]` | Pet name |\n| `[Company]` | Company name |\n| `[Color]` / `[Favourite_Color]` | Favourite colour |\n| `[Partner]` | Partner's first name |\n| `[Child]` / `[Children]` | Children's names |\n| `[Keyword]` / `[Keywords]` | Keywords / interests |\n| `[Year]` | 1986–current year |\n| `[Year2]` | Two-digit years |\n| `[Date]` | Birthdate from profile |\n| `[Digit]` | 0–9 |\n| `[Special]` | !@#$%^\u0026*?._- |\n| `[Upper]` | A–Z |\n| `[Lower]` | a–z |\n| `[Sep]` | Separators: _ - . @ # (empty) |\n| `[123]` | 123, 1234, 12345, !@#, 1q2w3e |\n\nExample: `[FirstName][Sep][Year]` with profile `firstname=John` generates:\n`john_2024`, `john-2024`, `john.2024`, `John_2024`, `john@2024`, etc.\n\n---\n\n## Scoring \u0026 Filtering\n\n### zxcvbn Strength Scoring\n\nWhen `--min-strength N` is provided (requires `zxcvbn` package), each candidate is scored on a 0–4 scale:\n\n| Score | Strength | Description |\n|-------|----------|-------------|\n| 0 | Very Weak | Trivially guessable (e.g., `123456`) |\n| 1 | Weak | Easily guessable (e.g., `password1`) |\n| 2 | Fair | Moderately guessable |\n| 3 | Strong | Uncommon but not resistant to targeted attacks |\n| 4 | Very Strong | Highly resistant to cracking |\n\nCandidates scoring below the threshold are pruned. This reduces wordlist size by removing trivially weak entries while keeping genuinely strong candidates.\n\n### Policy Filtering\n\nCombine policy flags to enforce password complexity requirements:\n\n```bash\n# At least 8 chars, one uppercase, one digit\npawpy -j profile.json --min-length 8 --require-upper --require-digit\n\n# Complex: 10+ chars, mixed case, digit, special\npawpy -j profile.json --min-length 10 --require-upper --require-lower \\\n    --require-digit --require-special\n```\n\n---\n\n## API \u0026 Dashboard\n\n### REST API\n\nStart the API server:\n\n```bash\npawpy api\n```\n\nEndpoints:\n\n| Method | Path | Description |\n|--------|------|-------------|\n| GET | `/` | Health check |\n| POST | `/generate` | Generate wordlist (multipart: profile JSON file + options) |\n| GET | `/download/{job_id}` | Download generated wordlist |\n| GET | `/jobs` | List all generation jobs |\n\nExample with `curl`:\n\n```bash\ncurl -X POST http://127.0.0.1:8000/generate \\\n  -F \"profile=@target.json\" \\\n  -F \"output=my_wordlist.txt\" \\\n  -F \"extreme=true\"\n```\n\n### Web Dashboard\n\n```bash\npawpy dashboard\n# Open http://127.0.0.1:8080 in your browser\n```\n\nThe dashboard provides a dark-themed web interface where you can:\n\n- Upload a profile JSON file\n- Select generation mode (Normal / Lite / Extreme)\n- Toggle Markov blending and zxcvbn scoring\n- Monitor real-time generation progress via WebSocket\n- Download the resulting wordlist\n\n---\n\n## OSINT Plugins\n\nPawpy includes a plugin system that auto-discovers Python modules in `pawpy/profile/plugins/`. Each plugin must define a `collect(profile: dict) -\u003e dict` function that enriches the profile dict with OSINT-derived data.\n\n### Creating a Plugin\n\nCreate a new `.py` file in `pawpy/profile/plugins/`:\n\n```python\n# pawpy/profile/plugins/my_plugin.py\n\nfrom typing import Any, Dict\n\n\ndef collect(profile: Dict[str, Any]) -\u003e Dict[str, Any]:\n    \"\"\"Enrich profile with OSINT data.\"\"\"\n    # Your OSINT logic here\n    # e.g., look up public social media profiles,\n    # check for breached credentials (with consent), etc.\n    \n    if profile.get(\"firstname\"):\n        keywords = profile.get(\"keywords\", [])\n        if isinstance(keywords, str):\n            keywords = [keywords]\n        # Add OSINT-discovered keywords\n        keywords.append(\"discovered_keyword\")\n        profile[\"keywords\"] = keywords\n    \n    return profile\n```\n\n### Important Rules for Plugin Authors\n\n- **Respect rate-limiting** and terms of service of any external APIs or websites.\n- **Only use OSINT data for authorised security testing.**\n- **Follow responsible disclosure** practices.\n- Handle exceptions gracefully so plugin failures don't crash the pipeline.\n\n---\n\n## Project Structure\n\n```\npawpy/\n├── pawpy/\n│   ├── __init__.py              # Package version and metadata\n│   ├── __main__.py              # python -m pawpy entry point\n│   ├── cli.py                   # Full CLI with argparse\n│   ├── config.py                # PawpyConfig dataclass\n│   ├── utils.py                 # Banner, logging, dedup, progress\n│   ├── profile/\n│   │   ├── __init__.py\n│   │   ├── base.py              # ProfileCollector (interactive + JSON)\n│   │   ├── multi.py             # Multi-target cross-referencing\n│   │   └── plugins/\n│   │       ├── __init__.py      # Plugin discovery and loader\n│   │       └── example.py       # Example no-op plugin template\n│   ├── mutations/\n│   │   ├── __init__.py\n│   │   ├── leet.py              # Leet-speak (3 levels, combinatorial)\n│   │   ├── dates.py             # Date permutations (20+ variants)\n│   │   ├── mangle.py            # Common rules + hashcat rule engine\n│   │   ├── markov.py            # Markov chain training \u0026 generation\n│   │   ├── keyboard.py          # Static + dynamic keyboard walks\n│   │   └── templates.py         # Custom pattern template engine\n│   ├── generator/\n│   │   ├── __init__.py\n│   │   ├── core.py              # Main 15-stage pipeline orchestrator\n│   │   ├── hybrid.py            # Hybrid mask attacks (hashcat -a 6/7)\n│   │   ├── sorter.py            # Billion-scale external merge sort\n│   │   └── gpu.py               # Optional CuPy GPU acceleration\n│   ├── scoring/\n│   │   ├── __init__.py\n│   │   └── scorer.py            # zxcvbn-based strength pruning\n│   ├── filters/\n│   │   ├── __init__.py\n│   │   └── policy.py            # Password complexity policy filter\n│   ├── api/\n│   │   ├── __init__.py\n│   │   ├── rest.py              # FastAPI REST endpoints\n│   │   └── dashboard.py         # WebSocket web dashboard\n│   └── data/\n│       ├── __init__.py\n│       ├── common_passwords.py  # Embedded top 100 + SecLists loader\n│       └── updater.py           # Auto-update from SecLists\n├── tests/\n│   ├── __init__.py\n│   ├── test_leet.py\n│   ├── test_dates.py\n│   ├── test_mangle.py\n│   ├── test_markov.py\n│   ├── test_keyboard.py\n│   ├── test_templates.py\n│   ├── test_profile.py\n│   ├── test_hybrid.py\n│   └── test_policy.py\n├── .github/\n│   └── workflows/\n│       └── lint.yml             # CI: flake8 + black + isort\n├── requirements.txt\n├── setup.py\n└── README.md\n```\n\n---\n\n## Development\n\n### Setup\n\n```bash\ngit clone https://github.com/Danyalkhattak/pawpy.git\ncd pawpy\npip install -e \".[all]\"\npip install pytest\n```\n\n### Running Tests\n\n```bash\npytest tests/ -v\n```\n\n### Code Quality\n\n```bash\n# Lint\nflake8 pawpy/\n\n# Format\nblack pawpy/\nisort pawpy/\n\n# All checks (also run by CI)\nflake8 pawpy/ \u0026\u0026 black --check pawpy/ \u0026\u0026 isort --check-only pawpy/\n```\n\n### Adding a New Mutation\n\nCreate a new `.py` file in `pawpy/mutations/` with a function that takes a list of words and returns a list of mutated candidates:\n\n```python\n# pawpy/mutations/my_mutation.py\n\ndef my_mutation(word: str) -\u003e list[str]:\n    \"\"\"Apply custom mutation to a word.\"\"\"\n return [word + \"_custom\", word.upper() + \"123\"]\n```\n\nThen import and call it in `pawpy/generator/core.py` within the `PipelineOrchestrator.run()` method.\n\n---\n\n## Architecture \u0026 Data Flow\n\n```\nUser Input (CLI / JSON / API)\n         │\n         ▼\n┌─────────────────────┐\n│  Profile Collection  │  Interactive / JSON / OSINT Plugins\n└──────────┬──────────┘\n           │\n           ▼\n┌─────────────────────┐\n│  Base Word Extract   │  All text fields → lowercase, deduplicated\n│  + Date Extraction   │\n└──────────┬──────────┘\n           │\n           ▼\n┌──────────────────────────────────────────┐\n│           Mutation Pipeline               │\n│  ┌──────────┐ ┌──────────┐ ┌───────────┐  │\n│  │  Leet    │ │  Mangle  │ │  Dates    │  │\n│  └──────────┘ └──────────┘ └───────────┘  │\n│  ┌──────────┐ ┌──────────┐ ┌───────────┐  │\n│  │ Keyboard │ │  Markov  │ │ Templates │  │\n│  └──────────┘ └──────────┘ └───────────┘  │\n│  ┌──────────┐ ┌──────────┐ ┌───────────┐  │\n│  │  Hybrid  │ │  Rules   │ │  Combos   │  │\n│  └──────────┘ └──────────┘ └───────────┘  │\n└────────────────────┬─────────────────────┘\n                     │\n                     ▼\n┌──────────────────────────────────────────┐\n│         Scoring \u0026 Filtering              │\n│  zxcvbn strength  │  Policy compliance   │\n└────────────────────┬─────────────────────┘\n                     │\n                     ▼\n┌──────────────────────────────────────────┐\n│         Sort + Deduplicate                │\n│  (in-memory or external merge sort)      │\n└────────────────────┬─────────────────────┘\n                     │\n                     ▼\n              Final Wordlist File\n```\n\n---\n\n## Performance Notes\n\n- **Throughput**: On an 8-core CPU, the system targets ≥10 million passwords/minute for basic mutations.\n- **Memory**: By default, stays under 2 GB RAM. For very large generation jobs, the external merge sorter handles disk-backed processing.\n- **Output**: Written sequentially for optimal I/O. Sorted chunks are merge-sorted efficiently.\n- **GPU**: Optional CuPy acceleration for rule application. Falls back gracefully to CPU if CuPy is not installed.\n\n---\n\n## License\n\nMIT License. See [LICENSE](LICENSE) for details.\n\n---\n\n## Acknowledgements\n\n- [CUPP](https://github.com/Mebus/cupp) – Original inspiration for interactive profiling\n- [Hashcat](https://hashcat.net/wiki/doku.php?id=rule_based_attack) – Rule engine format\n- [SecLists](https://github.com/danielmiessler/SecLists) – Common password data source\n- [zxcvbn](https://github.com/dropbox/zxcvbn) – Password strength estimation\n- [Rich](https://github.com/Textualize/rich) – Beautiful terminal output\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fdanyalkhattak%2Fpawpy","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fdanyalkhattak%2Fpawpy","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fdanyalkhattak%2Fpawpy/lists"}