#!/usr/bin/env python3
"""Print a compact inventory of Flux Kustomization resources."""

from __future__ import annotations

import argparse
from pathlib import Path
from typing import Any

import yaml


def _iter_docs(path: Path) -> list[dict[str, Any]]:
    docs: list[dict[str, Any]] = []
    for raw in yaml.safe_load_all(path.read_text(encoding="utf-8")):
        if isinstance(raw, dict):
            docs.append(raw)
    return docs


def _is_flux_kustomization(doc: dict[str, Any]) -> bool:
    return (
        doc.get("kind") == "Kustomization"
        and str(doc.get("apiVersion") or "").startswith("kustomize.toolkit.fluxcd.io/")
    )


def _depends_on(spec: dict[str, Any]) -> str:
    names = []
    for dep in spec.get("dependsOn") or []:
        if isinstance(dep, dict) and dep.get("name"):
            names.append(str(dep["name"]))
    return ",".join(names)


def _row(doc: dict[str, Any], path: Path) -> dict[str, str]:
    metadata = doc.get("metadata") or {}
    spec = doc.get("spec") or {}
    annotations = metadata.get("annotations") or {}
    return {
        "name": str(metadata.get("name") or ""),
        "path": str(spec.get("path") or ""),
        "namespace": str(spec.get("targetNamespace") or ""),
        "depends": _depends_on(spec),
        "prune": str(spec.get("prune", "")),
        "wait": str(spec.get("wait", "")),
        "suspend": str(spec.get("suspend", False)),
        "reason": str(annotations.get("atlas.bstein.dev/suspend-reason") or ""),
        "file": str(path),
    }


def build_inventory(root: Path) -> list[dict[str, str]]:
    rows: list[dict[str, str]] = []
    for path in sorted(root.rglob("*.yaml")):
        for doc in _iter_docs(path):
            if _is_flux_kustomization(doc):
                rows.append(_row(doc, path))
    return sorted(rows, key=lambda item: item["name"])


def _print_table(rows: list[dict[str, str]]) -> None:
    columns = ["name", "path", "namespace", "depends", "prune", "wait", "suspend", "reason"]
    widths = {
        column: max([len(column), *[len(row[column]) for row in rows]]) for column in columns
    }
    header = "  ".join(column.ljust(widths[column]) for column in columns)
    print(header)
    print("  ".join("-" * widths[column] for column in columns))
    for row in rows:
        print("  ".join(row[column].ljust(widths[column]) for column in columns))


def main() -> int:
    parser = argparse.ArgumentParser(description=__doc__)
    parser.add_argument("root", nargs="?", default="clusters/atlas/flux-system")
    args = parser.parse_args()

    rows = build_inventory(Path(args.root))
    _print_table(rows)
    return 0


if __name__ == "__main__":
    raise SystemExit(main())
