SubPulse-CLI (subpulse)
SubPulse-CLI is a high-throughput, non-blocking DNS resolution engine and infrastructure health auditor engineered in Python. It evaluates organizational domain perimeters, discovers active subdomains, isolates wildcard DNS zones, and identifies dangling CNAME takeover vulnerabilities without thread-pool overhead.
🎯 Primary Use Cases
- External Attack Surface Management: Rapidly discover active subdomains, forgotten staging environments, and shadow-IT infrastructure across corporate root domains.
- Subdomain Takeover Auditing: Detect dangling CNAME records pointing to decommissioned or unclaimed third-party cloud assets (AWS S3, GitHub Pages, Heroku, Azure, CloudFront).
- Wildcard DNS Suppression: Identify wildcard DNS configurations upfront using high-entropy probes, filtering out false-positive resolution storms.
- CI/CD & DevSecOps Perimeter Checks: Run lightweight DNS health audits inside automated security testing pipelines to detect domain misconfigurations.
🏛️ Architectural Overview
Traditional DNS enumeration utilities rely on synchronous OS resolver calls (socket.getaddrinfo() / gethostbyname()) wrapped in heavy thread pools. When querying thousands of potential subdomains, thread context-switching overhead and OS blocking timeouts degrade throughput.
SubPulse-CLI bypasses this limitation using asynchronous socket multiplexing powered by aiodns and c-ares.
[CLI Entrypoint: subpulse <target>]
│
▼
[Wordlist & Resolver Loader] <── (Embedded Defaults or Custom Wordlist)
│
▼
[Wildcard Pre-flight Probe] <── (High-Entropy Random Subdomain)
│
▼
[Async Event Loop Initiated]
│
┌──────────────┼──────────────┐
▼ ▼ ▼
[Worker Task] [Worker Task] [Worker Task] <── Managed concurrently via aiodns & Semaphore
│ │ │
└──────────────┼──────────────┘
▼
[Takeover Heuristics & Resolver]
│
┌──────────────┴──────────────┐
▼ ▼
[Colorama ANSI UI] [RFC JSON Report]
Key Technical Advantages
- Non-Blocking C-Ares Event Multiplexing: Leverages asynchronous UDP/TCP DNS sockets, enabling thousands of concurrent queries on a single Python thread.
- Entropy-Based Wildcard Suppression: Pre-scans domains with randomized probe records to identify wildcard catch-all configurations and isolate responder IP addresses.
- Dangling CNAME Takeover Heuristics: Matches canonical records against 16+ cloud vendor signatures and validates secondary resolution to catch orphaned pointer states (
NXDOMAIN). - Socket Saturation Control: Gated with
asyncio.Semaphoreto prevent OS file descriptor exhaustion while maximizing network throughput.
🚀 Installation & Setup
Option A: Global System Installation via PyPI (Recommended)
Install subpulse directly from PyPI into an isolated global environment:
# Using pipx (Recommended for isolated CLI binaries)
pipx install subpulse
# Or using standard pip
pip install subpulse
Option B: Local Virtual Environment from Source
# 1. Clone the repository
git clone https://github.com/dhruvrathod68/SubPulse-CLI.git
cd SubPulse-CLI
# 2. Create and activate a virtual environment
# On Linux / macOS / Kali:
python3 -m venv venv
source venv/bin/activate
# On Windows PowerShell:
python -m venv venv
.\venv\Scripts\Activate.ps1
# 3. Install in editable mode
pip install -e .
🔄 Updating SubPulse-CLI
To update your globally installed version to the latest release:
# If installed via pipx
pipx upgrade subpulse
# If installed via pip
pip install --upgrade subpulse
# If cloned from Git source
git pull origin main
pip install -e .
💻 Usage & Command Reference
usage: subpulse [-h] [-t TARGET_OPT] [-w WORDLIST] [-r RESOLVERS] [-c CONCURRENCY] [--timeout TIMEOUT] [-o OUTPUT] [TARGET]
positional arguments:
TARGET Target base domain to enumerate (e.g. github.com, example.com).
options:
-h, --help Show this help message and exit.
-t, --target Target base domain (flag format).
-w, --wordlist Path to custom subdomain prefix wordlist file.
-r, --resolvers Comma-separated custom DNS resolvers (e.g. 1.1.1.1,8.8.8.8).
-c, --concurrency Maximum concurrent asynchronous DNS queries (default: 50).
--timeout Query timeout in seconds per DNS request (default: 2.0).
-o, --output File path to export structured JSON telemetry report.
Example Commands
# 1. Basic Subdomain Enumeration (Default Wordlist)
subpulse github.com
# 2. Custom Wordlist with Specific Upstream Resolvers & Concurrency
subpulse target.com -w custom_subs.txt -r 1.1.1.1,8.8.8.8 -c 100
# 3. Comprehensive Audit with JSON Telemetry Export
subpulse target.com -c 40 --timeout 1.5 -o scan_report.json
🛠️ Customizing & Extending Wordlists
You can supply custom subdomain lists without altering Python source code. By default, SubPulse-CLI ships with 50 high-value standard infrastructure prefixes (api, dev, staging, admin, vpn, auth, portal, cloud, etc.).
Adding Custom Subdomain Wordlists
Create a plain-text file (e.g., custom_subdomains.txt) with one prefix per line:
api-internal
k8s-node01
auth-stage
vault-cluster
gateway-proxy
Execute your audit with your custom list:
subpulse target.com -w custom_subdomains.txt
📊 Telemetry Output Schema
When -o or --output is supplied, SubPulse-CLI exports a structured JSON report:
{
"target": "github.com",
"timestamp_utc": "2026-08-31T12:00:00Z",
"duration_seconds": 0.045,
"wildcard_detected": false,
"wildcard_ips": [],
"summary": {
"total_queried": 50,
"resolved": 12,
"takeover_candidates": 0
},
"results": [
{
"fqdn": "api.github.com",
"status": "RESOLVED",
"records": [
"20.207.73.85"
],
"cname": null,
"is_wildcard": false,
"takeover_risk": false,
"takeover_service": null,
"latency_ms": 5.52,
"error": null
},
{
"fqdn": "remote.github.com",
"status": "RESOLVED",
"records": [],
"cname": "remote.github.net",
"is_wildcard": false,
"takeover_risk": false,
"takeover_service": null,
"latency_ms": 5.44,
"error": null
}
]
}
Telemetry Field Definitions
| Field | Type | Description |
|---|---|---|
target |
string |
Base domain audited during enumeration. |
timestamp_utc |
string (ISO-8601) |
Audit initiation timestamp in UTC. |
duration_seconds |
float |
Total wall-clock time consumed by the DNS worker pool. |
wildcard_detected |
boolean |
True if pre-flight entropy probe resolved to wildcard records. |
wildcard_ips |
array of strings |
Set of IP addresses returned by wildcard responses. |
summary |
object |
Aggregate counts (total_queried, resolved, takeover_candidates). |
results[].fqdn |
string |
Fully Qualified Domain Name tested. |
results[].status |
string |
Query status (RESOLVED, NXDOMAIN, TIMEOUT, ERROR). |
results[].records |
array of strings |
Resolved 'A' or 'AAAA' record IP addresses. |
results[].cname |
string / null |
Canonical Name alias target if present. |
results[].is_wildcard |
boolean |
True if resolved IPs match the wildcard suppression set. |
results[].takeover_risk |
boolean |
True if CNAME points to an unclaimed/orphaned cloud service. |
results[].takeover_service |
string / null |
Identified cloud vendor signature (e.g. "GitHub Pages"). |
results[].latency_ms |
float |
Round-trip DNS query time in milliseconds. |
results[].error |
string / null |
Resolver error code if query failed. |
📂 Project Directory Structure
SubPulse-CLI/
├── wordlists/
│ └── subdomains_default.txt # Standard Subdomain Discovery Wordlist
├── venv/ # Python Virtual Environment (git-ignored)
├── .gitignore # Repository Exclusion Rules
├── LICENSE # MIT License (2026 Dhruv Rathod)
├── MANIFEST.in # Source Distribution Packaging Manifest
├── main.py # Core Asynchronous DNS Engine & Orchestrator
├── requirements.txt # Pinned Dependencies Manifest
├── setup.py # Setuptools Packaging Manifest & Console Scripts
└── README.md # Enterprise Open-Source Documentation
🗺️ Roadmap & Upcoming Features
- Multitype Record Sweeping: Concurrent auditing of MX, TXT, AAAA, and SRV records per subdomain.
- AXFR Zone Transfer Auditing: Automated detection of open DNS zone transfer misconfigurations on authoritative nameservers.
- Certificate Transparency (CT) Stream Ingestion: Passive real-time subdomain discovery via crt.sh log streaming.
- Multi-Format Reporting: Native export to CSV, Markdown summary tables, and SARIF formats.
🤝 Contributing & Issue Reporting
Contributions, bug reports, and cloud takeover signature additions are welcome!
Reporting Issues
If you encounter false classifications, resolver exceptions, or socket leaks, please open an issue on the GitHub Issue Tracker.
Submitting Pull Requests
- Fork the repository.
- Create a feature branch (
git checkout -b feature/AddCloudSignatures). - Commit your changes with clear messages (
git commit -m 'feat: add S3 bucket takeover heuristic'). - Push to your branch (
git push origin feature/AddCloudSignatures). - Open a Pull Request detailing your modifications.
⚖️ License & Attribution
Distributed under the MIT License. See LICENSE for full details.
- Author: Dhruv Rathod
- Year: 2026
Metadata
Release files for subpulse 0.1.0
For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.
Source distribution (sdist)
| File | Size | Uploaded | |
|---|---|---|---|
| subpulse-0.1.0.tar.gz | 17.2 kB | Details |
Built distribution (wheel)
| File | Interpreter | ABI | Platform | Reset |
|---|---|---|---|---|
| subpulse-0.1.0-py3-none-any.whl | Python 3 | none | any | Details |
Total release size: 29.5 kB
Release files / subpulse-0.1.0.tar.gz
| Download URL | subpulse-0.1.0.tar.gz |
|---|---|
| Size | 17.2 kB |
| Tags | Source |
|
SHA-256 checksum How to use checksums |
c81825a7e1ef8c4e91940469a1f9a2d84434493e38da7275c6b5d6669bd7cab7
|
|
BLAKE2b-256 checksum How to use checksums |
587ebde7a045d5959acf1c5c449cadd400153b0320e99d49ab3581259933868b
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
No |
| Uploaded via |
twine/7.0.0 CPython/3.14.3
|
Release files / subpulse-0.1.0-py3-none-any.whl
| Download URL | subpulse-0.1.0-py3-none-any.whl |
|---|---|
| Size | 12.2 kB |
| Tags | Python 3 |
|
SHA-256 checksum How to use checksums |
555f9c78bf11e4279dcaa8083702f0ed24e72531671c84c7dc88d59ade3abc5e
|
|
BLAKE2b-256 checksum How to use checksums |
bb29c8671c63ddb767c8adad75794911c1cf82b4770f5bca1fad177a48851b09
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
No |
| Uploaded via |
twine/7.0.0 CPython/3.14.3
|