diff --git a/src/repocat/cli/review.py b/src/repocat/cli/review.py index 20639c5..0182e7f 100644 --- a/src/repocat/cli/review.py +++ b/src/repocat/cli/review.py @@ -1,19 +1,15 @@ -from typer import Typer, confirm, prompt +from typer import Typer from rich.console import Console -from rich.table import Table -from pathlib import Path -import shutil -from datetime import datetime -import typer from rich.prompt import Prompt, Confirm +from datetime import datetime +import shutil +import typer -from repocat.cli.move import move_command from repocat.config import load_config -from repocat.models.config import RepoCategory +from repocat.models.catalog import RepoCatalogState +from repocat.cli.move import move_command from repocat.cli.archive import archive_repo -from repocat.cli.clean import get_dir_size, is_git_dirty, is_git_unpushed - app = Typer() console = Console() @@ -23,48 +19,39 @@ def review(): """ Führt interaktiv durch alle Repositories im Review-Ordner. """ - config = load_config() - base = config.base_dir + catalog = RepoCatalogState.from_config(load_config()) - archive_cat = next((c for c in config.categories if c.is_archive), None) + archive_cat = next((c for c in catalog.categories if c.config.is_archive), None) if not archive_cat: console.print("[red]Keine Archiv-Kategorie in der Konfiguration gefunden.[/]") raise typer.Exit(1) - archive_path = base / archive_cat.subdir - archive_path.mkdir(parents=True, exist_ok=True) - - review_cat = next((c for c in config.categories if c.name == "review"), None) + review_cat = catalog.get_category("review") if not review_cat: console.print("[red]Kein 'review'-Eintrag in der Konfiguration gefunden.[/]") raise typer.Exit(1) - review_path = base / review_cat.subdir - if not review_path.exists(): - console.print(f"[yellow]Hinweis:[/] Kein review-Ordner vorhanden unter {review_path}") - return - - repos = [p for p in review_path.iterdir() if p.is_dir()] - if not repos: + if not review_cat.repos: console.print("[green]✓ Keine Repositories im Review-Ordner.[/]") return - for repo in sorted(repos): + for repo in sorted(review_cat.repos, key=lambda r: r.name): console.rule(f"[bold cyan]{repo.name}") - age_days = (datetime.now() - datetime.fromtimestamp(repo.stat().st_mtime)).days - size_mb = get_dir_size(repo) / 1024 / 1024 + console.print(f"[bold]Alter:[/] {repo.age_days} Tage") + console.print(f"[bold]Größe:[/] {repo.size_mb:.1f} MB") - status = [] - if is_git_dirty(repo): - status.append("uncommitted") - if is_git_unpushed(repo): - status.append("unpushed") - if not status: - status.append("clean") + if repo.git: + status = [] + if repo.git.dirty: + status.append("uncommitted") + if repo.git.unpushed: + status.append("unpushed") + if not status: + status.append("clean") + else: + status = ["kein Git"] - console.print(f"[bold]Alter:[/] {age_days} Tage") - console.print(f"[bold]Größe:[/] {size_mb:.1f} MB") console.print(f"[bold]Git:[/] {', '.join(status)}") while True: @@ -81,17 +68,17 @@ def review(): raise typer.Exit() elif action in ("d", "delete"): if Confirm.ask(f"Bist du sicher, dass du [red]{repo.name}[/] löschen willst?"): - shutil.rmtree(repo) + shutil.rmtree(repo.path) console.print(f"[red]✓ Gelöscht:[/] {repo.name}") break elif action in ("m", "move"): - target_categories = [c.name for c in config.categories if c.name != "review" and not c.is_archive] + target_categories = [c.config.name for c in catalog.categories if c.config.name != "review" and not c.config.is_archive] target = Prompt.ask("Zielkategorie", choices=target_categories) move_command(source=f"review/{repo.name}", target=target) break elif action in ("a", "archive"): try: - archive_file = archive_repo(repo, archive_path, dry_run=False) + archive_file = archive_repo(repo.path, archive_cat.path, dry_run=False) console.print(f"[green]✓ Archiviert:[/] {archive_file.name}") break except Exception as e: @@ -99,4 +86,4 @@ def review(): else: console.print("[yellow]Ungültige Eingabe. Gültig sind: m, d, s, q[/]") - console.print("[green]✓ Review abgeschlossen.[/]") + console.print("[green]✓ Review abgeschlossen.[/]") \ No newline at end of file