#!/usr/bin/env python3
"""
recon_notebook_seed.py - Chapter 3 Lab 1: Python recon utility seed.

This file mirrors the code shown in section 3.2 of the book.
It is the starting point for the 03_python_recon.ipynb notebook exercise.

Run on your own domains or localhost only.
"""

import argparse
import socket
import json
import requests


def recon(host: str) -> dict:
    """Perform a basic recon on host: resolve IP, HTTP status, Server header."""
    info: dict = {"host": host}
    try:
        info["ip"] = socket.gethostbyname(host)
        # verify=True is the default and must stay on
        r = requests.get(f"https://{host}", timeout=5)
        info["status"] = r.status_code
        info["server"] = r.headers.get("Server", "unknown")
    except (socket.gaierror, requests.RequestException) as exc:
        # Contained error - not a raw traceback
        info["error"] = str(exc)
    return info


def recon_dns(host: str) -> dict:
    """Extend recon with A/MX/NS lookups using dnspython (pip install dnspython)."""
    import dns.resolver  # type: ignore

    info = recon(host)
    for rtype in ("A", "MX", "NS"):
        try:
            answers = dns.resolver.resolve(host, rtype)
            info[rtype] = [str(r) for r in answers]
        except Exception as exc:
            info[f"{rtype}_error"] = str(exc)
    return info


if __name__ == "__main__":
    ap = argparse.ArgumentParser(
        description="Minimal recon helper - Section 3.2 lab seed"
    )
    ap.add_argument("host", help="Hostname to recon (must be yours or a lab target)")
    ap.add_argument(
        "--json",
        dest="as_json",
        action="store_true",
        help="Emit results as JSON (Lab 1 extension exercise)",
    )
    ap.add_argument(
        "--dns",
        action="store_true",
        help="Include DNS record lookups (requires dnspython)",
    )
    args = ap.parse_args()

    result = recon_dns(args.host) if args.dns else recon(args.host)

    if args.as_json:
        print(json.dumps(result, indent=2))
    else:
        print(result)
