#!/usr/bin/env python3 from __future__ import annotations import json import subprocess import sys from pathlib import Path ROOT = Path(__file__).resolve().parents[2] def run_git(repo: Path, *args: str) -> str: result = subprocess.run( ["git", "-C", str(repo), *args], check=False, text=True, stdout=subprocess.PIPE, stderr=subprocess.PIPE, ) if result.returncode != 0: return f"git error: {result.stderr.strip()}" return result.stdout.strip() def main() -> int: manifest = json.loads((ROOT / "repositories.json").read_text()) parent = Path(manifest["default_parent"]) rows: list[tuple[str, str, str, str]] = [] for entry in manifest["repositories"]: repo = parent / entry["path"] if not repo.exists(): rows.append((entry["name"], entry["category"], "missing", "")) continue branch = run_git(repo, "symbolic-ref", "--quiet", "--short", "HEAD") or "(detached)" status = run_git(repo, "status", "--short") state = "dirty" if status else "clean" rows.append((entry["name"], entry["category"], branch, state)) name_width = max(len(row[0]) for row in rows) category_width = max(len(row[1]) for row in rows) for name, category, branch, state in rows: print(f"{name:<{name_width}} {category:<{category_width}} {branch:<24} {state}") return 0 if __name__ == "__main__": sys.exit(main())