"""
Django admin configuration for wallet app.
"""
from django.contrib import admin
from django.core.exceptions import ValidationError
from django.utils import timezone
from .models import Wallet, Transaction, WithdrawalRequest


@admin.register(Wallet)
class WalletAdmin(admin.ModelAdmin):
    """
    Admin configuration for Wallet model.
    """
    list_display = ('user', 'balance', 'total_deposits', 'total_withdrawals', 'total_earnings', 'referral_earnings', 'created_at')
    search_fields = ('user__username', 'user__email')
    readonly_fields = ('created_at', 'updated_at')


@admin.register(Transaction)
class TransactionAdmin(admin.ModelAdmin):
    """
    Admin configuration for Transaction model.
    """
    list_display = ('wallet', 'transaction_type', 'amount', 'status', 'reference_id', 'created_at')
    list_filter = ('transaction_type', 'status')
    search_fields = ('wallet__user__username', 'reference_id')
    readonly_fields = ('created_at',)
    list_editable = ('status',)


@admin.register(WithdrawalRequest)
class WithdrawalRequestAdmin(admin.ModelAdmin):
    """
    Admin configuration for withdrawal requests.
    """
    list_display = (
        'wallet',
        'amount',
        'method',
        'status',
        'reviewed_by',
        'created_at',
    )
    list_filter = ('status', 'method')
    search_fields = ('wallet__user__username', 'destination_details', 'transaction__reference_id')
    readonly_fields = ('transaction', 'reviewed_by', 'reviewed_at', 'created_at', 'updated_at')
    list_editable = ('status',)

    def save_model(self, request, obj, form, change):
        if change:
            old_obj = WithdrawalRequest.objects.get(pk=obj.pk)
            review_time = timezone.now()

            if obj.status == 'APPROVED' and old_obj.status != 'APPROVED':
                wallet = obj.wallet
                if wallet.balance < obj.amount:
                    raise ValidationError('This wallet no longer has enough balance to approve the withdrawal.')

                wallet.balance -= obj.amount
                wallet.total_withdrawals += obj.amount
                wallet.save()

                obj.reviewed_by = request.user
                obj.reviewed_at = review_time

                if obj.transaction:
                    obj.transaction.status = 'COMPLETED'
                    obj.transaction.completed_at = review_time
                    obj.transaction.save()

            elif old_obj.status == 'APPROVED' and obj.status != 'APPROVED':
                wallet = obj.wallet
                wallet.balance += obj.amount
                if wallet.total_withdrawals >= obj.amount:
                    wallet.total_withdrawals -= obj.amount
                else:
                    wallet.total_withdrawals = 0
                wallet.save()

                obj.reviewed_by = request.user
                obj.reviewed_at = review_time

                if obj.transaction:
                    obj.transaction.status = 'FAILED' if obj.status == 'REJECTED' else 'PENDING'
                    obj.transaction.completed_at = review_time if obj.status == 'REJECTED' else None
                    obj.transaction.save()

            elif obj.status == 'REJECTED' and old_obj.status != 'REJECTED':
                obj.reviewed_by = request.user
                obj.reviewed_at = review_time

                if obj.transaction:
                    obj.transaction.status = 'FAILED'
                    obj.transaction.completed_at = review_time
                    obj.transaction.save()

            elif obj.status == 'PENDING' and old_obj.status != 'PENDING':
                obj.reviewed_by = request.user
                obj.reviewed_at = review_time

                if obj.transaction:
                    obj.transaction.status = 'PENDING'
                    obj.transaction.completed_at = None
                    obj.transaction.save()

        super().save_model(request, obj, form, change)
