# apps/shares/management/commands/payment_tracking_report.py
from django.core.management.base import BaseCommand
from django.db.models import Sum, Count, Q, F
from django.utils import timezone
from datetime import timedelta
from tabulate import tabulate

from apps.shares.models import ShareSubscription, SharePayment, ShareType
from apps.members.models import Member


class Command(BaseCommand):
    help = "Génère un rapport détaillé du suivi des paiements de parts sociales"

    def add_arguments(self, parser):
        parser.add_argument(
            "--member-id", type=int, help="ID du membre pour un rapport individuel"
        )
        parser.add_argument(
            "--period",
            type=int,
            default=30,
            help="Période en jours pour le rapport (défaut: 30 jours)",
        )
        parser.add_argument(
            "--export",
            choices=["csv", "json"],
            help="Exporter le rapport au format CSV ou JSON",
        )

    def handle(self, *args, **options):
        self.stdout.write(
            self.style.SUCCESS("🔍 RAPPORT DE SUIVI DES PAIEMENTS DE PARTS SOCIALES")
        )
        self.stdout.write("=" * 70)

        period_days = options["period"]
        start_date = timezone.now().date() - timedelta(days=period_days)

        if options["member_id"]:
            self.member_report(options["member_id"])
        else:
            self.global_report(start_date, period_days)

        if options["export"]:
            self.export_data(options["export"], start_date)

    def global_report(self, start_date, period_days):
        """Rapport global sur tous les membres"""

        # 1. STATISTIQUES GÉNÉRALES
        self.stdout.write(f"\n📊 STATISTIQUES GÉNÉRALES (derniers {period_days} jours)")
        self.stdout.write("-" * 50)

        total_subscriptions = ShareSubscription.objects.count()
        total_payments = SharePayment.objects.filter(
            created_at__date__gte=start_date
        ).count()
        recent_payments_amount = (
            SharePayment.objects.filter(created_at__date__gte=start_date).aggregate(
                total=Sum("financial_transaction__amount")
            )["total"]
            or 0
        )

        stats_table = [
            ["Total souscriptions", total_subscriptions],
            ["Paiements récents", total_payments],
            ["Montant payé récemment", f"{recent_payments_amount:,.0f} FCFA"],
        ]

        print(tabulate(stats_table, headers=["Métrique", "Valeur"], tablefmt="grid"))

        # 2. ÉTAT DES SOUSCRIPTIONS PAR STATUT
        self.stdout.write(f"\n📈 RÉPARTITION PAR STATUT DE PAIEMENT")
        self.stdout.write("-" * 50)

        subscriptions = ShareSubscription.objects.all()
        fully_paid = [s for s in subscriptions if s.is_fully_paid]
        partially_paid = [
            s for s in subscriptions if s.paid_quantity > 0 and not s.is_fully_paid
        ]
        not_paid = [s for s in subscriptions if s.paid_quantity == 0]

        status_table = [
            [
                "Entièrement payées",
                len(fully_paid),
                f"{len(fully_paid)/total_subscriptions*100:.1f}%",
            ],
            [
                "Partiellement payées",
                len(partially_paid),
                f"{len(partially_paid)/total_subscriptions*100:.1f}%",
            ],
            [
                "Non payées",
                len(not_paid),
                f"{len(not_paid)/total_subscriptions*100:.1f}%",
            ],
        ]

        print(
            tabulate(status_table, headers=["Statut", "Nombre", "%"], tablefmt="grid")
        )

        # 3. TOP 10 DES MEMBRES AVEC LE PLUS DE PAIEMENTS
        self.stdout.write(f"\n🏆 TOP 10 MEMBRES - ACTIVITÉ DE PAIEMENT")
        self.stdout.write("-" * 50)

        top_members = (
            SharePayment.objects.filter(created_at__date__gte=start_date)
            .values(
                "subscription__member__user__first_name",
                "subscription__member__user__last_name",
                "subscription__member__membership_number",
            )
            .annotate(
                total_payments=Count("id"),
                total_amount=Sum("financial_transaction__amount"),
            )
            .order_by("-total_amount")[:10]
        )

        if top_members:
            members_table = []
            for member in top_members:
                name = f"{member['subscription__member__user__first_name']} {member['subscription__member__user__last_name']}"
                members_table.append(
                    [
                        name.strip(),
                        member["subscription__member__membership_number"] or "N/A",
                        member["total_payments"],
                        f"{member['total_amount']:,.0f} FCFA",
                    ]
                )

            print(
                tabulate(
                    members_table,
                    headers=["Membre", "N° Adhérent", "Nb Paiements", "Montant Total"],
                    tablefmt="grid",
                )
            )

        # 4. ACTIVITÉ PAR TYPE DE PART
        self.stdout.write(f"\n📋 ACTIVITÉ PAR TYPE DE PART")
        self.stdout.write("-" * 50)

        share_types_activity = (
            SharePayment.objects.filter(created_at__date__gte=start_date)
            .values(
                "subscription__share_type__name",
                "subscription__share_type__nominal_value",
            )
            .annotate(
                total_payments=Count("id"),
                total_quantity=Sum("paid_quantity"),
                total_amount=Sum("financial_transaction__amount"),
            )
            .order_by("-total_amount")
        )

        if share_types_activity:
            types_table = []
            for share_type in share_types_activity:
                types_table.append(
                    [
                        share_type["subscription__share_type__name"],
                        f"{share_type['subscription__share_type__nominal_value']:,.0f} FCFA",
                        share_type["total_payments"],
                        share_type["total_quantity"],
                        f"{share_type['total_amount']:,.0f} FCFA",
                    ]
                )

            print(
                tabulate(
                    types_table,
                    headers=[
                        "Type de Part",
                        "Valeur Nominale",
                        "Nb Paiements",
                        "Quantité",
                        "Montant Total",
                    ],
                    tablefmt="grid",
                )
            )

    def member_report(self, member_id):
        """Rapport détaillé pour un membre spécifique"""
        try:
            member = Member.objects.get(id=member_id)
        except Member.DoesNotExist:
            self.stdout.write(
                self.style.ERROR(f"Membre avec ID {member_id} introuvable")
            )
            return

        self.stdout.write(f"\n👤 RAPPORT DÉTAILLÉ - MEMBRE {member_id}")
        self.stdout.write("-" * 50)

        user = member.user
        self.stdout.write(f"Nom: {user.first_name} {user.last_name}")
        self.stdout.write(f"Email: {user.email}")
        self.stdout.write(f'N° Adhérent: {member.membership_number or "N/A"}')

        # Souscriptions du membre
        subscriptions = ShareSubscription.objects.filter(member=member)

        self.stdout.write(f"\n📋 SOUSCRIPTIONS ({subscriptions.count()})")
        self.stdout.write("-" * 30)

        subs_table = []
        total_subscribed_amount = 0
        total_paid_amount = 0

        for sub in subscriptions:
            subscribed_amount = sub.subscribed_quantity * sub.share_type.nominal_value
            paid_amount = sub.paid_quantity * sub.share_type.nominal_value
            remaining_amount = subscribed_amount - paid_amount

            total_subscribed_amount += subscribed_amount
            total_paid_amount += paid_amount

            status = (
                "✅ Payé"
                if sub.is_fully_paid
                else ("🔶 Partiel" if sub.paid_quantity > 0 else "❌ Non payé")
            )

            subs_table.append(
                [
                    f"#{sub.id}",
                    sub.share_type.name,
                    f"{sub.subscribed_quantity}/{sub.paid_quantity}",
                    f"{subscribed_amount:,.0f}",
                    f"{paid_amount:,.0f}",
                    f"{remaining_amount:,.0f}",
                    status,
                ]
            )

        print(
            tabulate(
                subs_table,
                headers=[
                    "ID",
                    "Type",
                    "Parts (S/P)",
                    "Souscrit",
                    "Payé",
                    "Restant",
                    "Statut",
                ],
                tablefmt="grid",
            )
        )

        # Historique des paiements
        payments = SharePayment.objects.filter(subscription__member=member).order_by(
            "-created_at"
        )

        self.stdout.write(f"\n💰 HISTORIQUE DES PAIEMENTS ({payments.count()})")
        self.stdout.write("-" * 30)

        if payments:
            payments_table = []
            for payment in payments[:20]:  # Derniers 20 paiements
                payments_table.append(
                    [
                        payment.created_at.strftime("%d/%m/%Y"),
                        f"#{payment.subscription.id}",
                        payment.subscription.share_type.name,
                        payment.paid_quantity,
                        f"{payment.amount_paid:,.0f} FCFA",
                        f"TXN-{payment.financial_transaction.id}",
                    ]
                )

            print(
                tabulate(
                    payments_table,
                    headers=[
                        "Date",
                        "Souscription",
                        "Type",
                        "Quantité",
                        "Montant",
                        "Transaction",
                    ],
                    tablefmt="grid",
                )
            )

        # Résumé financier
        self.stdout.write(f"\n💼 RÉSUMÉ FINANCIER")
        self.stdout.write("-" * 20)

        summary_table = [
            ["Montant total souscrit", f"{total_subscribed_amount:,.0f} FCFA"],
            ["Montant total payé", f"{total_paid_amount:,.0f} FCFA"],
            [
                "Montant restant à payer",
                f"{total_subscribed_amount - total_paid_amount:,.0f} FCFA",
            ],
            [
                "Taux de libération",
                f"{(total_paid_amount/total_subscribed_amount*100) if total_subscribed_amount > 0 else 0:.1f}%",
            ],
        ]

        print(tabulate(summary_table, headers=["Métrique", "Valeur"], tablefmt="grid"))

    def export_data(self, format_type, start_date):
        """Exporte les données au format demandé"""
        if format_type == "csv":
            import csv
            from django.http import HttpResponse

            filename = f"payment_tracking_report_{timezone.now().date()}.csv"
            self.stdout.write(f"\n📁 Export CSV: {filename}")

            # Ici, vous pourriez implémenter l'export CSV complet

        elif format_type == "json":
            import json

            filename = f"payment_tracking_report_{timezone.now().date()}.json"
            self.stdout.write(f"\n📁 Export JSON: {filename}")

            # Ici, vous pourriez implémenter l'export JSON complet
