from django.contrib import admin
from django.http import HttpRequest
from django.http.response import HttpResponse
from retailers.models import Transaction, Wallet
from settings.models import Operator
from .models import (
    Commission,
    DistributorTransfer,
    SuperDistributorTransfer,
    SuperDistributors,
    Distributors,
    DistributorWallet,
    WalletTransaction,
)
import random
import string
from django.contrib.auth.models import User
from django.contrib.auth.models import Group
from helper import calculate_percentage_commission

# Register your models here.


def checkUserRoleExists(userRole, roles):
    rslt = False

    for role in roles:
        if str(role).lower() == str(userRole).lower():
            rslt = True
            break

    return rslt


class DistributorsInline(admin.StackedInline):
    model = Distributors
    extra = 0


def generate_random_number():
    # Generate a random 4-digit number
    random_number = random.randint(1000, 9999)
    return random_number

def generate_random_string(length):
    # Define the character set from which to generate the string
    characters = (
        string.ascii_letters + string.digits
    )  # You can include other characters if needed

    # Generate the random string of specified length
    random_string = "".join(random.choice(characters) for _ in range(length))

    return random_string


class SuperDistributorsAdmin(admin.ModelAdmin):
    inlines = [DistributorsInline]
    list_display = ["name", "code", "mobile"]

    search_fields = [
        "name",
        "code",
        "mobile",
        "email",
    ]
    actions = ["reset_commission","reset_code"]

    def reset_code(self, request, queryset):
        for obj in queryset:
            obj.code = generate_random_number()
            obj.save()
    

    def reset_commission(self, request, queryset):
        ops = Operator.objects.filter(is_active=True)

        for obj in queryset:
            for dt in ops:
                Commission.objects.filter(super_distributor=obj, operator=dt).update(
                    receive_commission=dt.forward_commission,
                    forward_commission=dt.distributor_commission,
                    percentage=0,
                )

    def get_queryset(self, request):
        qs = super().get_queryset(request)

        if request.user.is_superuser:
            return qs
        roles = request.user.groups.all()
        if checkUserRoleExists("Super Distributor", roles):
            return qs.filter(super_distributor__user=request.user)
        elif checkUserRoleExists("Distributor", roles):
            return qs.filter(distributor__user=request.user)

    def initCommissions(self, obj):
        ops = Operator.objects.filter(is_active=True)

        for dt in ops:
            Commission.objects.create(
                source=1,
                super_distributor=obj,
                operator=dt,
                receive_commission=dt.forward_commission,
                forward_commission=dt.distributor_commission,
                percentage=0,
            )
        DistributorWallet.objects.create(source=1, super_distributor=obj, amount=0)

    def delete_queryset(self, request, queryset):
        for obj in queryset:
            if obj.user:
                User.objects.filter(id=obj.user.id).delete()

        return super().delete_queryset(request, queryset)

    def delete_model(self, request, obj):
        if obj.user:
            User.objects.filter(id=obj.user.id).delete()
        return super().delete_model(request, obj)

    def response_add(self, request, obj):
        try:
            self.initCommissions(obj)

            username = obj.mobile

            # group = Group.objects.get(name="Waiter")
            user = None
            if obj.password != "" and obj.password != "NA":
                user = User.objects.create_user(
                    username,
                    obj.email,
                    obj.password,
                )
            else:
                user = User.objects.create_user(
                    username, obj.email, "@123Welcome", is_staff=True
                )

            if user:
                if len(str(obj.name).split(" ")) > 1:
                    user.first_name = str(obj.name).split(" ")[0]
                    user.last_name = str(obj.name).split(" ")[1]
                else:
                    user.first_name = obj.name
                    user.last_name = ""

                user.is_staff = True
                user.is_active = True
                user.date_joined = obj.created_on
                user.save()

                groups = Group.objects.filter(name="Super Distributor")
                if len(groups) > 0:
                    group = groups[0]
                    user.groups.add(group)
                    group.user_set.add(user)

                obj.user = user
                obj.save()
            return super().response_add(request, obj)
        except Exception as error:
            print(error)

    def save_model(self, request, obj, form, change):
        if not change:
            obj.code = generate_random_number()
            obj.created_by = request.user

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


class DistributorsAdmin(admin.ModelAdmin):
    # inlines = [RetailerInline]
    list_filter = ["super_distributor"]
    list_display = ["name", "code", "mobile", "wallet_balance", "super_distributor"]
    exclude = []

    actions = ["reset_commission","reset_code"]

    def reset_code(self, request, queryset):
        for obj in queryset:
            obj.code = generate_random_number()
            obj.save()

    

    def reset_commission(self, request, queryset):
        for obj in queryset:
            if obj.super_distributor:
                cms = Commission.objects.filter(super_distributor=obj.super_distributor)

                for dt in cms:
                    Commission.objects.filter(
                        distributor=obj, operator=dt.operator
                    ).update(
                        receive_commission=dt.forward_commission,
                        forward_commission=dt.operator.retailer_commission,
                        percentage=0,
                    )

    search_fields = [
        "name",
        "code",
        "mobile",
        "email",
    ]

    def wallet_balance(self, obj):
        wlt = DistributorWallet.objects.get(distributor=obj)
        return wlt.amount

    def get_exclude(self, request, obj):
        exs = super().get_exclude(request, obj)

        if request.user.is_superuser:
            return exs
        roles = request.user.groups.all()
        if checkUserRoleExists("Super Distributor", roles):
            return ["super_distributor", "user", "password"]
        elif checkUserRoleExists("Distributor", roles):
            return ["super_distributor", "user"]

    def get_list_filter(self, request):
        lst = super().get_list_filter(request)
        if request.user.is_superuser:
            return lst
        return []

    def get_queryset(self, request):
        qs = super().get_queryset(request)

        if request.user.is_superuser:
            return qs
        roles = request.user.groups.all()
        if checkUserRoleExists("Super Distributor", roles):
            return qs.filter(super_distributor__user=request.user)
        elif checkUserRoleExists("Distributor", roles):
            return qs.filter(distributor__user=request.user)

    def initCommissions(self, obj):
        ops = Commission.objects.filter(super_distributor=obj.super_distributor)

        for dt in ops:
            Commission.objects.create(
                source=2,
                distributor=obj,
                operator=dt.operator,
                receive_commission=dt.forward_commission,
                forward_commission=dt.operator.retailer_commission,
                percentage=0,
            )

        DistributorWallet.objects.create(source=2, distributor=obj, amount=0)

    def delete_queryset(self, request, queryset):
        for obj in queryset:
            if obj.user:
                User.objects.filter(id=obj.user.id).delete()

        return super().delete_queryset(request, queryset)

    def delete_model(self, request, obj):
        if obj.user:
            User.objects.filter(id=obj.user.id).delete()
        return super().delete_model(request, obj)

    def response_add(self, request, obj):
        try:
            self.initCommissions(obj)

            username = obj.mobile

            user = None
            if obj.password != "" and obj.password != "NA":
                user = User.objects.create_user(
                    username,
                    obj.email,
                    obj.password,
                )
            else:
                user = User.objects.create_user(
                    username, obj.email, "@123Welcome", is_staff=True
                )

            if user:
                if len(str(obj.name).split(" ")) > 1:
                    user.first_name = str(obj.name).split(" ")[0]
                    user.last_name = str(obj.name).split(" ")[1]
                else:
                    user.first_name = obj.name
                    user.last_name = ""

                user.is_staff = True
                user.is_active = True
                user.date_joined = obj.created_on
                user.save()
                groups = Group.objects.filter(name="Distributor")
                if len(groups) > 0:
                    group = groups[0]
                    user.groups.add(group)
                    group.user_set.add(user)

                obj.user = user
                obj.save()
            return super().response_add(request, obj)
        except Exception as error:
            print(error)

    def save_model(self, request, obj, form, change):
        if not change:
            if not request.user.is_superuser:
                su = SuperDistributors.objects.get(user=request.user)
                obj.super_distributor = su
                obj.password = "@24Welcome"

            obj.code = generate_random_number()
            obj.created_by = request.user
        return super().save_model(request, obj, form, change)


class CommissionAdmin(admin.ModelAdmin):

    list_filter = ["source", "super_distributor", "distributor", "operator"]
    list_display = [
        "source",
        "super_distributor",
        "distributor",
        "operator",
        "receive_commission",
        "forward_commission",
    ]

    def get_list_filter(self, request):
        lst = super().get_list_filter(request)
        if request.user.is_superuser:
            return lst
        return ["operator"]

    def get_queryset(self, request):
        qs = super().get_queryset(request)

        if request.user.is_superuser:
            return qs
        roles = request.user.groups.all()
        if checkUserRoleExists("Super Distributor", roles):
            return qs.filter(super_distributor__user=request.user)
        elif checkUserRoleExists("Distributor", roles):
            return qs.filter(distributor__user=request.user)
        else:
            return []

    def save_model(self, request, obj, form, change):
        try:
            percentage = calculate_percentage_commission(
                obj.forward_commission, obj.receive_commission
            )
            obj.percentage = percentage
            obj.save()
            return super().save_model(request, obj, form, change)
        except Exception as error:
            print(error)


class DistributorWalletAdmin(admin.ModelAdmin):

    list_filter = ["source", "super_distributor", "distributor"]
    list_display = [
        "source",
        "super_distributor",
        "distributor",
        "amount",
    ]

    def get_list_filter(self, request):
        lst = super().get_list_filter(request)
        if request.user.is_superuser:
            return lst
        return []

    def get_queryset(self, request):
        qs = super().get_queryset(request)

        if request.user.is_superuser:
            return qs
        roles = request.user.groups.all()
        if checkUserRoleExists("Super Distributor", roles):
            return qs.filter(super_distributor__user=request.user)
        elif checkUserRoleExists("Distributor", roles):
            return qs.filter(distributor__user=request.user)
        else:
            return []


class WalletTransactionAdmin(admin.ModelAdmin):

    list_filter = ["wallet"]
    list_display = [
        "wallet",
        "amount",
        "type",
        "cumulative",
    ]

    def get_list_filter(self, request):
        lst = super().get_list_filter(request)
        if request.user.is_superuser:
            return lst
        return []

    def get_queryset(self, request):
        qs = super().get_queryset(request)

        if request.user.is_superuser:
            return qs
        roles = request.user.groups.all()
        if checkUserRoleExists("Super Distributor", roles):
            return qs.filter(wallet__super_distributor__user=request.user)
        elif checkUserRoleExists("Distributor", roles):
            return qs.filter(wallet__distributor__user=request.user)
        else:
            return []


class DistributorTransferAdmin(admin.ModelAdmin):

    list_display = ["distributor", "retailer", "amount", "created_on"]

    exclude = []
    class Media:
        js = (
            "js/jquery/jquery.min.js",
            "lib/helper.js",
            "lib/admin_dis_transfer.js",
        )
    def response_add(self, request, obj):

        swlt = DistributorWallet.objects.get(distributor=obj.distributor)
        if float(swlt.amount) >= float(obj.amount):
            swlt.amount = float(swlt.amount) - float(obj.amount)
            WalletTransaction.objects.create(
                wallet=swlt, amount=obj.amount, type=2, cumulative=swlt.amount
            )

            wlt = Wallet.objects.get(retailer=obj.retailer)
            wlt.amount = float(wlt.amount) + float(obj.amount)
            order_id = "".join(random.choices("0123456789", k=10))
            Transaction.objects.create(
                order_id=order_id,
                tnx_id=order_id,
                source=1,
                retailer=obj.retailer,
                status=1,
                remark="From Distributor",
                amount=obj.amount,
                deduction_amount=obj.amount,
                transaction_type=1,
            )

            swlt.save()
            wlt.save()
        else:
            obj.delete()

        return super().response_add(request, obj)

    def get_exclude(self, request, obj):
        exs = super().get_exclude(request, obj)

        if request.user.is_superuser:
            return exs
        roles = request.user.groups.all()
        if checkUserRoleExists("Distributor", roles):
            return ["distributor"]

    def get_queryset(self, request):
        qs = super().get_queryset(request)

        if request.user.is_superuser:
            return qs
        roles = request.user.groups.all()
        if checkUserRoleExists("Distributor", roles):
            return qs.filter(distributor__user=request.user)

    def save_model(self, request, obj, form, change):
        if not change:
            if not request.user.is_superuser:
                dis = Distributors.objects.get(user=request.user)
                obj.distributor = dis

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


class SuperDistributorTransferAdmin(admin.ModelAdmin):

    list_display = ["super_distributor", "distributor", "amount", "created_on"]

    exclude = []
    class Media:
        js = (
            "js/jquery/jquery.min.js",
            "lib/helper.js",
            "lib/admin_sdis_transfer.js",
        )
        
    def get_exclude(self, request, obj):
        exs = super().get_exclude(request, obj)

        if request.user.is_superuser:
            return exs
        roles = request.user.groups.all()
        if checkUserRoleExists("Super Distributor", roles):
            return ["super_distributor"]

    def get_queryset(self, request):
        qs = super().get_queryset(request)

        if request.user.is_superuser:
            return qs
        roles = request.user.groups.all()
        if checkUserRoleExists("Super Distributor", roles):
            return qs.filter(super_distributor__user=request.user)

    def response_add(self, request, obj):

        swlt = DistributorWallet.objects.get(super_distributor=obj.super_distributor)
        if float(swlt.amount) >= float(obj.amount):
            swlt.amount = float(swlt.amount) - float(obj.amount)
            WalletTransaction.objects.create(
                wallet=swlt, amount=obj.amount, type=2, cumulative=swlt.amount
            )

            wlt = DistributorWallet.objects.get(distributor=obj.distributor)
            wlt.amount = float(wlt.amount) + float(obj.amount)
            WalletTransaction.objects.create(
                wallet=wlt, amount=obj.amount, type=1, cumulative=wlt.amount
            )

            swlt.save()
            wlt.save()
        else:
            obj.delete()

        return super().response_add(request, obj)

    def save_model(self, request, obj, form, change):
        if not change:
            if not request.user.is_superuser:
                sd = SuperDistributors.objects.get(user=request.user)
                obj.super_distributor = sd

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


admin.site.register(SuperDistributors, SuperDistributorsAdmin)
admin.site.register(Distributors, DistributorsAdmin)
admin.site.register(Commission, CommissionAdmin)
admin.site.register(DistributorWallet, DistributorWalletAdmin)
admin.site.register(WalletTransaction, WalletTransactionAdmin)
admin.site.register(DistributorTransfer, DistributorTransferAdmin)
admin.site.register(SuperDistributorTransfer, SuperDistributorTransferAdmin)
