#!/usr/bin/env python3
"""Push command: scan sessions for report.md, git commit, archive, push."""

import shutil
import subprocess
import sys
from datetime import datetime
from pathlib import Path



def push(project_root: str | None = None) -> int:
    root = Path(project_root).resolve() if project_root else Path.cwd().resolve()
    sessions_dir = root / ".mixer" / "sessions"

    if not sessions_dir.is_dir():
        print("No .mixer/sessions/ directory found.")
        return 1

    # Scan for session folders with report.md
    report_sessions: list[tuple[Path, str]] = []
    for folder in sorted(sessions_dir.iterdir()):
        if not folder.is_dir() or folder.name.startswith("."):
            continue
        report_file = folder / "report.md"
        if not report_file.is_file():
            continue
        message = _extract_commit_message(report_file)
        if message:
            report_sessions.append((folder, message))

    if not report_sessions:
        print("No session folders with report.md found.")
        return 1

    print(f"Found {len(report_sessions)} session(s) with commit messages:")
    for folder, msg in report_sessions:
        subject = msg.splitlines()[0] if msg else "(empty)"
        print(f"  {folder.name}: {subject}")

    # Combine commit messages
    if len(report_sessions) == 1:
        combined_message = report_sessions[0][1]
    else:
        parts = []
        for folder, msg in report_sessions:
            parts.append(f"[{folder.name}]\n{msg}")
        combined_message = "\n\n".join(parts)

    # Git add + commit
    print("\nStaging changes...")
    result = subprocess.run(
        ["git", "add", "."],
        cwd=str(root),
        capture_output=True, text=True,
    )
    if result.returncode != 0:
        print(f"git add failed: {result.stderr}")
        return 1

    # Check if there's anything to commit
    status = subprocess.run(
        ["git", "status", "--porcelain"],
        cwd=str(root),
        capture_output=True, text=True,
    )
    if not status.stdout.strip():
        print("Nothing to commit (working tree clean).")
        return 0

    print("Committing...")
    result = subprocess.run(
        ["git", "commit", "-m", combined_message],
        cwd=str(root),
        capture_output=True, text=True,
    )
    if result.returncode != 0:
        print(f"git commit failed: {result.stderr}")
        return 1
    print(result.stdout.strip())

    # Archive committed sessions
    archive_dir = sessions_dir / "_archived"
    archive_dir.mkdir(parents=True, exist_ok=True)
    timestamp = datetime.now().strftime("%Y%m%d-%H%M%S")
    for folder, _ in report_sessions:
        dest = archive_dir / f"{folder.name}_{timestamp}"
        shutil.move(str(folder), str(dest))
        print(f"  Archived: {folder.name} -> _archived/{dest.name}")

    # Git push
    print("\nPushing...")
    result = subprocess.run(
        ["git", "push"],
        cwd=str(root),
        capture_output=True, text=True,
    )
    if result.returncode != 0:
        print(f"git push failed: {result.stderr}")
        return 1
    print(result.stdout.strip() or "Push complete.")

    return 0


def _extract_commit_message(report_file: Path) -> str:
    """Extract the commit message from a report.md file."""
    body = report_file.read_text()

    # Extract Subject and Body sections
    subject = ""
    body_lines = []
    current_section = None

    for line in body.splitlines():
        stripped = line.strip()
        if stripped.startswith("## Subject"):
            current_section = "subject"
            continue
        elif stripped.startswith("## Body"):
            current_section = "body"
            continue
        elif stripped.startswith("## ") or stripped.startswith("# "):
            current_section = None
            continue

        if current_section == "subject" and stripped:
            subject = stripped
        elif current_section == "body" and stripped:
            body_lines.append(stripped)

    if not subject:
        return ""

    parts = [subject]
    if body_lines:
        parts.append("")
        parts.extend(body_lines)

    return "\n".join(parts)


if __name__ == "__main__":
    project_root = None
    for arg in sys.argv[1:]:
        if arg.startswith("--project_root="):
            project_root = arg.split("=", 1)[1]
    raise SystemExit(push(project_root=project_root))
