"""obol compliance - compliance status, reports, profiles, regulations."""
from obol.cli._base import (
    get_api, handle_api_error, output, table, compliance_bar, error, add_format_arg,
    CHAR_CHECK, CHAR_CROSS, CHAR_PARTIAL, CHAR_WARNING, CHAR_HLINE,
)


@handle_api_error
def cmd_compliance(args):
    api = get_api()
    fmt = getattr(args, "format", "text")

    sub = getattr(args, "compliance_cmd", None)

    if sub == "profile":
        _cmd_profile(api, args, fmt)
    elif sub == "regulations":
        _cmd_regulations(api, args, fmt)
    elif sub == "report":
        _cmd_report(api, args, fmt)
    elif sub == "recompute":
        result = api.recompute_compliance()
        if fmt == "json":
            output(result, fmt="json")
        else:
            print(f"Recomputed. Score: {result.get('overall_score', 0):.1%}")
            print(f"Requirements: {result.get('total_requirements', 0)}")
            print(f"Gaps: {result.get('gaps', 0)}")
    else:
        # Default: status
        _cmd_status(api, args, fmt)


def _cmd_status(api, args, fmt):
    data = api.get_compliance_status()

    if fmt == "json":
        output(data, fmt="json")
        return

    if not data.get("compliance_enabled"):
        print("Compliance not configured.")
        print("Run: obol compliance profile --industry <X> --jurisdictions US EU")
        return

    score = data.get("overall_score")
    stale = " (stale - run 'obol compliance recompute')" if data.get("stale") else ""

    print(f"Overall Compliance: {compliance_bar(score)}{stale}")
    print(f"Total Gaps: {data.get('gaps', 0)}")
    print()

    regs = data.get("regulations", [])
    if regs:
        rows = []
        for reg in regs:
            s = reg.get("score")
            score_str = f"{s:.0%}" if s is not None else "pending"
            rows.append([
                reg.get("slug", "?"),
                reg.get("name", "?"),
                score_str,
                reg.get("gaps", 0),
                reg.get("requirement_count", 0),
                CHAR_WARNING if reg.get("stale") else CHAR_CHECK,
            ])
        table(
            ["Slug", "Regulation", "Score", "Gaps", "Reqs", "Fresh"],
            rows,
            max_widths={0: 20, 1: 30},
        )

    tier = data.get("tier") or data.get("plan")
    if tier in (None, "free", "solo") or not data.get("compliance_enabled"):
        print()
        print("  Note: Full compliance reports and detailed analysis require Team tier.")
        print("  Upgrade at: https://obol.grayowlresearch.com/dashboard")


def _cmd_profile(api, args, fmt):
    if args.industry:
        # Set profile
        result = api.set_compliance_profile(args.industry, args.jurisdictions or [])
        if fmt == "json":
            output(result, fmt="json")
        else:
            print(f"Profile set: {result.get('industry')} in {result.get('jurisdictions')}")
            print(f"Compliance enabled: {result.get('compliance_enabled')}")
            print(f"Mapped regulations: {result.get('mapped_regulations')}")
    else:
        # Get profile
        result = api.get_compliance_profile()
        if fmt == "json":
            output(result, fmt="json")
        else:
            if result.get("industry"):
                print(f"Industry:      {result['industry']}")
                print(f"Jurisdictions: {', '.join(result.get('jurisdictions', []))}")
                print(f"Enabled:       {result.get('compliance_enabled')}")
                print(f"Regulations:   {result.get('mapped_regulations')}")
            else:
                print("No compliance profile set.")
                print("Run: obol compliance profile --industry healthcare --jurisdictions US EU")


def _cmd_regulations(api, args, fmt):
    slug = getattr(args, "slug", None)

    if slug:
        data = api.get_regulation(slug)
        if fmt == "json":
            output(data, fmt="json")
            return

        print(f"{data['name']} ({data['slug']})")
        print(f"  Authority:    {data['authority']}")
        print(f"  Jurisdiction: {data['jurisdiction']}")
        print(f"  Industries:   {', '.join(data.get('industries', []))}")
        print(f"  Version:      {data['version']}")
        if data.get("source_url"):
            print(f"  Source:       {data['source_url']}")
        print()

        reqs = data.get("requirements", [])
        if reqs:
            rows = []
            for r in reqs:
                rows.append([
                    r["code"],
                    r["title"],
                    r["category"],
                    r["severity"],
                    f"{r['weight']:.1f}",
                ])
            table(
                ["Code", "Title", "Category", "Severity", "Weight"],
                rows,
                max_widths={1: 40},
            )
    else:
        data = api.list_regulations()

        if fmt == "json":
            output(data, fmt="json")
            return

        if not data:
            print("No regulations available.")
            return

        rows = []
        for reg in data:
            rows.append([
                reg["slug"],
                reg["name"],
                reg["jurisdiction"],
                ", ".join(reg.get("industries", [])),
                reg.get("requirement_count", 0),
            ])

        table(
            ["Slug", "Name", "Jurisdiction", "Industries", "Reqs"],
            rows,
            max_widths={0: 20, 1: 25, 3: 30},
        )


def _cmd_report(api, args, fmt):
    slug = getattr(args, "regulation", None)
    try:
        data = api.get_compliance_report(slug=slug)
    except Exception as e:
        if "tier" in str(e).lower() or "upgrade" in str(e).lower() or "403" in str(e):
            print()
            print("  Full compliance reports require Team tier ($149/mo).")
            print("  Your current plan: Free/Solo")
            print()
            print("  Upgrade at: https://obol.grayowlresearch.com/dashboard -> Settings -> Billing")
            print()
            return
        raise

    if fmt == "json":
        output(data, fmt="json")
        return

    if "error" in data:
        if "tier" in data["error"].lower() or "upgrade" in data["error"].lower():
            print()
            print("  Full compliance reports require Team tier ($149/mo).")
            print("  Your current plan: Free/Solo")
            print()
            print("  Upgrade at: https://obol.grayowlresearch.com/dashboard -> Settings -> Billing")
            print()
            return
        error(data["error"])

    print("=" * 60)
    print(f"  COMPLIANCE REPORT - {data.get('org_name', 'Unknown')}")
    print(f"  Generated: {data.get('generated_at', '-')}")
    print("=" * 60)

    if "overall_score" in data:
        print(f"\n  Overall Score: {compliance_bar(data['overall_score'])}")
        print(f"  Requirements:  {data.get('total_requirements', 0)}")
        print(f"  Gaps:          {data.get('total_gaps', 0)}")

    for reg in data.get("regulations", []):
        print(f"\n{CHAR_HLINE * 60}")
        score = reg.get("score", 0)
        status = reg.get("status", "unknown")
        print(f"  {reg.get('name', reg.get('slug', '?'))}")
        print(f"  Score: {compliance_bar(score)}  Status: {status}")
        print()

        reqs = reg.get("requirements", [])
        if reqs:
            rows = []
            for r in reqs:
                status_icon = {"met": CHAR_CHECK, "partially_met": CHAR_PARTIAL, "not_met": CHAR_CROSS}.get(
                    r.get("status", ""), "?"
                )
                rows.append([
                    status_icon,
                    r.get("code", ""),
                    r.get("title", ""),
                    f"{r.get('score', 0):.0%}",
                    r.get("severity", ""),
                ])
            table(["", "Code", "Requirement", "Score", "Severity"], rows, max_widths={2: 35})

    recs = data.get("recommendations", [])
    if recs:
        print(f"\n{CHAR_HLINE * 60}")
        print("  RECOMMENDATIONS")
        print()
        for i, rec in enumerate(recs, 1):
            priority = rec.get("priority", "medium").upper()
            print(f"  {i}. [{priority}] {rec.get('regulation', '')} {rec.get('requirement', '')}")
            print(f"     {rec.get('title', '')}")
            print(f"     → {rec.get('action', '')}")
            print()


def setup_parser(subparsers):
    """Add compliance subparser."""
    parser = subparsers.add_parser("compliance", help="Compliance management")
    parser.set_defaults(func=cmd_compliance, compliance_cmd=None)
    add_format_arg(parser)

    sub = parser.add_subparsers(dest="compliance_cmd")

    sub.add_parser("status", help="Compliance status overview")

    prof = sub.add_parser("profile", help="Get/set compliance profile")
    prof.add_argument("--industry", help="Industry (e.g. healthcare, finance)")
    prof.add_argument("--jurisdictions", nargs="+", help="Jurisdictions (e.g. US EU)")

    regs = sub.add_parser("regulations", help="List/view regulations")
    regs.add_argument("slug", nargs="?", help="Regulation slug for details")

    report = sub.add_parser("report", help="Generate compliance report")
    report.add_argument("--regulation", help="Single regulation slug")

    sub.add_parser("recompute", help="Force compliance recomputation")
