from django.shortcuts import render, redirect, get_object_or_404,HttpResponse
from django.core.paginator import Paginator, EmptyPage, PageNotAnInteger
from .models import ProductCategory,Product,OtherImage,SerialNumber
from django.contrib import messages
from django.utils import timezone
from django.contrib.auth.decorators import login_required
from django.core.exceptions import ValidationError
import re
from django.core.mail import EmailMessage
from django.db.models import Q,OuterRef, Subquery
from django.http.response import JsonResponse
from myobconnect.views import refresh_token
from myobconnect.models import MyobModel
from quotation.models import Invoice
from django.conf import settings
import json
import requests
from customer.models import Customer
# from quotation.models import Order_Item

from quotation.models import GST,Discount,Quotation, QuotationItem,QuotationVersion, Customer,Supplier, Product,Invoice,InvoiceItem,SerialNumber,InvoicePdf,Customer_Payment,Order,Order_Item,User,Technician_Assigned_Order_Item,Technician_Comment,Supplier_Bill

from supplier.models import Supplier
from service.models import Heading

from django.db.models import Count

from product.models import ProductSpecificationPDF, ProductManualPDF

from leads.models import Lead,ProductSpecificationPDFSent,ProductUserManualPDFSent
import os
from dotenv import load_dotenv, find_dotenv
load_dotenv(find_dotenv())
from django.db import transaction
myob_expense_account = os.environ.get('MYOB_ExpenseAccount')
myob_cost_of_sales_account = os.environ.get('MYOB_CostOfSalesAccount')
myob_income_account = os.environ.get('MYOB_IncomeAccount')
myob_asset_account = os.environ.get('MYOB_AssetAccount')
myob_tax_code = os.environ.get('MYOB_TaxCode')
from django.template.loader import render_to_string

# def send_product_pdfs(request, customer_id):
#     if request.method != "POST":
#         return redirect('leads:list')

#     customer = Lead.objects.get(id=customer_id)
#     # products = customer.product_objects.prefetch_related('specification_pdfs', 'manual_pdfs')
#     products = (
#     Product.objects
#     .filter(deleted_at__isnull=True)
#     .select_related('category')  # needed for category__category_name ordering
#     .prefetch_related('specification_pdfs', 'manual_pdfs')
#     .order_by('category__category_name')
#     )
#     selected_products = []
#     is_spec=[]
#     is_user_manual=[]
#     for product in products:
#         send_spec = request.POST.get(f"send_spec_{product.id}")
#         send_manual = request.POST.get(f"send_manual_{product.id}")
#         is_product=0
        
#         if send_spec:
#             for i, spec_pdf in enumerate(product.specification_pdfs.all(), start=1):
#                 if spec_pdf.file and os.path.exists(spec_pdf.file.path):
#                     is_product=1
                    
#         if send_manual:
#             for i, manual_pdf in enumerate(product.manual_pdfs.all(), start=1):
#                 if manual_pdf.file and os.path.exists(manual_pdf.file.path):
#                     is_product=1
                        
#         if is_product == 1:
#             selected_products.append(f"{product.product_name}")
#     subject = f"EXCITECH Australia - Product Specification"
#     template_data = {'lead': customer,'selected_products':selected_products}
#     message = render_to_string('pages/leads/productdetailsemail.html', template_data)
#     from_email = settings.FROM_EMAIL
#     recipient_email = 'kiran@beedev.co.in' #lead.email 
#     cc_email = ['kiran@beedev.co.in'] #settings.ADMIN_EMAIL_CC_PO # settings.ADMIN_EMAIL
#     email = EmailMessage(subject, message, from_email, [recipient_email],cc_email)
#     for product in products:
#         send_spec = request.POST.get(f"send_spec_{product.id}")
#         send_manual = request.POST.get(f"send_manual_{product.id}")
        
        
#         if send_spec:
#             for i, spec_pdf in enumerate(product.specification_pdfs.all(), start=1):
#                 if spec_pdf.file and os.path.exists(spec_pdf.file.path):
#                     with open(spec_pdf.file.path, "rb") as f:
#                         new_name = f"{product.product_name}_Spec_{i}.pdf"
#                         email.attach(new_name, f.read(), "application/pdf")
#                         if product.id not in is_spec:
#                             is_spec.append(product.id)
#                     # selected_products.append(f"{product.product_name} - Spec ({new_name})")

    
#         if send_manual:
#             for i, manual_pdf in enumerate(product.manual_pdfs.all(), start=1):
#                 if manual_pdf.file and os.path.exists(manual_pdf.file.path):
#                     with open(manual_pdf.file.path, "rb") as f:
#                         new_name = f"{product.product_name}_Manual_{i}.pdf"
#                         email.attach(new_name, f.read(), "application/pdf")
#                         if product.id not in is_user_manual:
#                             is_user_manual.append(product.id)
#                         # selected_products.append(f"{product.product_name} - Manual ({new_name})")
                        
#         # if is_product == 1:
#         #     selected_products.append(f"{product.product_name}")
    
#     # dd(attachments)
#     if not selected_products:
#         messages.error(request, "No Products selected to send.")
#         return redirect('leads:list')
    
#     # dd(selected_products)
#     if is_user_manual:
#         is_user_manual_objs = [
#             ProductUserManualPDFSent(product_id=product_id, lead_id=customer_id)
#             for product_id in is_user_manual
#         ]
#         ProductUserManualPDFSent.objects.bulk_create(is_user_manual_objs)
#     if is_spec:
#         is_spec_objs = [
#             ProductSpecificationPDFSent(product_id=product_idss, lead_id=customer_id)
#             for product_idss in is_spec
#         ]
#         ProductSpecificationPDFSent.objects.bulk_create(is_spec_objs)
#     if email:
        
#         # for file_path in attachments:   # attachments = list of file paths
#         #     email.attach_file(file_path)
#         email.content_subtype = 'html'
#         email.send(fail_silently=False)
#     messages.success(request, 'Mail Sent Successfully.')
#     return redirect('leads:list')
   
from django.db import transaction

def send_product_pdfs(request, customer_id):
    if request.method != "POST":
        return redirect('leads:list')

    customer = Lead.objects.get(id=customer_id)

    products = (
        Product.objects
        .filter(deleted_at__isnull=True)
        .select_related('category')
        .prefetch_related('specification_pdfs', 'manual_pdfs')
        .order_by('category__category_name')
    )

    selected_products = []
    is_spec = set()
    is_user_manual = set()

    email = EmailMessage(
        subject="EXCITECH Australia - Product Specification",
        body="",
        from_email=settings.FROM_EMAIL,
        to=['hari@beedev.co.in'],
        cc=['kiran@beedev.co.in']
    )

    for product in products:
        send_spec = request.POST.get(f"send_spec_{product.id}")
        send_manual = request.POST.get(f"send_manual_{product.id}")

        is_product = False

        if send_spec:
            for i, spec_pdf in enumerate(product.specification_pdfs.all(), start=1):
                if spec_pdf.file and os.path.exists(spec_pdf.file.path):
                    is_product = True
                    with open(spec_pdf.file.path, "rb") as f:
                        email.attach(
                            f"{product.product_name}_Spec_{i}.pdf",
                            f.read(),
                            "application/pdf"
                        )
                    is_spec.add(product.id)

        if send_manual:
            for i, manual_pdf in enumerate(product.manual_pdfs.all(), start=1):
                if manual_pdf.file and os.path.exists(manual_pdf.file.path):
                    is_product = True
                    with open(manual_pdf.file.path, "rb") as f:
                        email.attach(
                            f"{product.product_name}_Manual_{i}.pdf",
                            f.read(),
                            "application/pdf"
                        )
                    is_user_manual.add(product.id)

        if is_product:
            selected_products.append(product.product_name)

    if not selected_products:
        messages.error(request, "No Products selected to send.")
        return redirect('leads:list')

    message = render_to_string(
        'pages/leads/productdetailsemail.html',
        {'lead': customer, 'selected_products': selected_products}
    )
    email.body = message
    email.content_subtype = 'html'

    # ✅ Atomic DB section
    try:
        with transaction.atomic():
            if is_user_manual:
                ProductUserManualPDFSent.objects.bulk_create([
                    ProductUserManualPDFSent(product_id=pid, lead_id=customer_id)
                    for pid in is_user_manual
                ])

            if is_spec:
                ProductSpecificationPDFSent.objects.bulk_create([
                    ProductSpecificationPDFSent(product_id=pid, lead_id=customer_id)
                    for pid in is_spec
                ])
    except Exception as e:
        messages.error(request, f"DB Error: {str(e)}")
        return redirect('leads:list')

    # ✅ Email AFTER DB commit
    email.send(fail_silently=False)

    messages.success(request, "Mail Sent Successfully.")
    return redirect('leads:list')

def listproducttobill(request):
    order_item= Order_Item.objects.filter(serial_number__isnull=True)
    ord= order_item.values('product__id','product__product_name', 'product__sku','serial_number').annotate(qty=Count('id')).distinct()
    #dd(ord)
    for or1 in ord:
        sr=SerialNumber.objects.filter(product__id=or1['product__id'],customer=None).count()
        or1['serial_number_qty']=sr
        or1['reuiredbilledqty']=or1['qty']-sr
    # dd(ord)
    return HttpResponse('here')
def getProducts(request):
    refresh_token(request)
    myobdata = MyobModel.objects.first()
    api_url = f"https://ar2.api.myob.com/accountright/{settings.COMPANY_FILE_ID}/Inventory/Item//?$filter=Number eq 'E3-1836 LOAD-UNLOAD-LABEL RL'"

    headers = {
        'Authorization': f'Bearer {myobdata.access_token}',
        'x-myobapi-key': settings.MYOB_CLIENT_ID,
        'x-myobapi-version': 'v2',
        'Content-Type': 'application/json',
        'Accept-Encoding': 'gzip,deflate'
    }
    response = requests.get(api_url, headers=headers)
    print("Response:", response.status_code, response.content)
    # /?$filter=Type eq 'Personal'
    return HttpResponse('here')
    
@login_required
def request_trade_products(request):
    products = Product.objects.filter(
        is_product=1,
        is_converted_from_trade=False,
        deleted_at__isnull=True
    )
    return render(request,'pages/product/trade_products.html',{'products':products})

def sync_myob_product_row(request,product_id):

    refresh_token(request)
    myobdata = MyobModel.objects.first()
    if not myobdata:
        messages.error(request,'Please First create Access Code')
        return redirect('/myob/initiate-connection')
   
    api_url = f"https://ar2.api.myob.com/accountright/{settings.COMPANY_FILE_ID}/Inventory/Item/"

    headers = {
        'Authorization': f'Bearer {myobdata.access_token}',
        'x-myobapi-key': settings.MYOB_CLIENT_ID,
        'x-myobapi-version': 'v2',
        'Content-Type': 'application/json',
        'Accept-Encoding': 'gzip,deflate'
    }

    product = Product.objects.get(id=product_id)

    # product = Product.objects.get(id=17)

    product_data=   {
            "Number":product.sku,
                "Name":f'{product.product_name}',
            "IsActive": True,
            "IsBought" : True,
            "IsSold" : True,
            "IsInventoried" : False,
            "ExpenseAccount" :  {
                        "UID": myob_expense_account},
            "Description": product.product_description[:255],
            
            "CostOfSalesAccount" : {
                "UID" : myob_cost_of_sales_account,
                            },
            "IncomeAccount": {
                    "UID": myob_income_account,
                },

            "AssetAccount" : {
                        "UID" : myob_asset_account,
                        },


            "BuyingDetails": {
                "BaseSellingPrice" :float(product.product_price),
                "ItemsPerBuyingUnit" : 1,
                "TaxCode": {
                    "UID": myob_tax_code,
                }
            },
            "SellingDetails": {
                "BaseSellingPrice" : float(product.product_price),
                "ItemsPerBuyingUnit" : 1,
                "TaxCode": {
                    "UID": myob_tax_code,
                }
            }
        }
    product_json = json.dumps(product_data)
    response = requests.post(api_url, data=product_json, headers=headers)
    print("-------------------dk--------------------")
    print("Response:", response.status_code, response.content)
    print(response)
    print('2222')
    print(request.headers)
    print("--------------------")

    data=response.headers
   
    if response.status_code == 201:
        location = data['Location']
        if location:
            parts = location.split('/')
            uid = parts[-1]
            # product.myob_location = location
            product.uid = uid
            product.save()
        messages.success(request, 'Product successfully Sync With Myob.')
        return redirect('product:list_product')
    else:
        messages.error(request, 'Product Already to Sync With Myob.')
        return redirect('product:list_product')
    


@login_required
def sync_myob_product(request):

    refresh_token(request)
    myobdata = MyobModel.objects.first()
    if not myobdata:
        messages.error(request,'Please First create Access Code')
        return redirect('/myob/initiate-connection')
   
    api_url = f"https://ar2.api.myob.com/accountright/{settings.COMPANY_FILE_ID}/Inventory/Item/"

    headers = {
        'Authorization': f'Bearer {myobdata.access_token}',
        'x-myobapi-key': settings.MYOB_CLIENT_ID,
        'x-myobapi-version': 'v2',
        'Content-Type': 'application/json',
        'Accept-Encoding': 'gzip,deflate'
    }

    products = Product.objects.filter(uid=None)[:2]
    
    for product in products:
        # product = Product.objects.get(id=17)
        print("@@@@@@@@@@@@@")
        print(product)
    
       
       
        product_data=   {
                "Number":product.sku,
                "Name": f'{product.product_name}',
                "IsActive": True,
                "IsBought" : True,
                "IsSold" : True,
                "IsInventoried" : False,
                "ExpenseAccount" :  {
                            "UID": myob_expense_account},
                "Description": product.product_description[:255],
                
                "CostOfSalesAccount" : {
                    "UID" : myob_cost_of_sales_account,
                                },
                "IncomeAccount": {
                        "UID": myob_income_account,
                    },

                "AssetAccount" : {
                            "UID" : myob_asset_account,
                            },


                "BuyingDetails": {
                    "BaseSellingPrice" :float(product.product_price),
                    "ItemsPerBuyingUnit" : 1,
                    "TaxCode": {
                        "UID": myob_tax_code,
                    }
                },
                "SellingDetails": {
                    "BaseSellingPrice" : float(product.product_price),
                    "ItemsPerBuyingUnit" : 1,
                    "TaxCode": {
                        "UID": myob_tax_code,
                    }
                }
            }
        product_json = json.dumps(product_data)
        response = requests.post(api_url, data=product_json, headers=headers)
        print("-------------------dk--------------------")
        print("Response:", response.status_code, response.content)
        print(response)
        print('2222')
        print(request.headers)
        print("--------------------")
    
        data=response.headers
       
        if response.status_code == 201:
            location = data['Location']
            if location:
                parts = location.split('/')
                uid = parts[-1]
                # product.myob_location = location
                product.uid = uid
                product.save()
            messages.success(request, 'Product successfully Sync With Myob.')
            return redirect('product:list_product')
            messages.error(request, 'Product Already to Sync With Myob.')
            return redirect('product:list_product')
    return  HttpResponse('All records are successfully synch with myob')
# def get_product(request):
#     product = Product.objects.get(id=1)
#     # other_images = OtherImage.objects.filter(product__in=product) 
#     return render(request,'pages/product/get_product.html', {'product': product})

def product_details(request,id):
    product = Product.objects.get(id=id)
    # dd(product)
    print(product.product_description)
    return render(request,'pages/product/product_details.html',{'product':product})

@login_required
def list_category(request):
    category_name = request.GET.get('category_name')
    status = request.GET.get('status')


    
    product_categories = ProductCategory.objects.filter(deleted_at__isnull=True )

    if category_name:
        category_name = request.GET.get('category_name').strip()
        product_categories = product_categories.filter(
            Q(category_name__icontains=category_name) or
            Q(is_active=status) 
        )
    if status:
        product_categories = product_categories.filter(is_active=status)


    total_records = product_categories.count()
    show_pagination = total_records > settings.PAGE_RECORDS


    if show_pagination: 
        
        
        page = request.GET.get('page', 1)
        paginator = Paginator(product_categories, settings.PAGE_RECORDS)  # Show 10 categories per page
        try:
            product_categories = paginator.page(page)
        except PageNotAnInteger:
            product_categories = paginator.page(1)
        except EmptyPage:
            product_categories = paginator.page(paginator.num_pages)
        
    return render(request,'pages/category/list.html',{'categories': product_categories})



@login_required
def create_category(request):
    context={}
    if request.method == 'POST':
        form = request.POST
        category_name = request.POST.get('category_name')
        
        
        is_active= request.POST.get('is_active')
        
        
        if is_active is None:
           is_active = False
        else:
            is_active = True


        allow_price_edit =request.POST.get('allow_price_edit')
        if allow_price_edit is None:
           allow_price_edit = False
        else:
            allow_price_edit = True
        
        #pattern = r"^[A-Za-z]+$"
        
    
        #if not re.match(pattern, category_name):
           # messages.error(request, 'Category Name Should Contain Only Letters.')
           # context['form'] = form
           # return render(request,'pages/category/create.html',context)
            
        if not category_name:
            messages.error(request, 'Please Enter Category Name.')
            context['form'] = form
            return render(request,'pages/category/create.html',context)

        if ProductCategory.objects.filter(category_name=category_name).exists():
            messages.error(request, 'Category Name Already Exist.')
            context['form'] = form
            return render(request,'pages/category/create.html',context)
        
        product_category = ProductCategory(category_name=category_name,is_active=is_active,allow_price_edit=allow_price_edit,created_by=request.user)
        product_category.save()
        messages.success(request, 'Category Added Successfully.')
        return redirect('product:list_category')
    context['form'] = {}
    return render(request,'pages/category/create.html',context)

@login_required    
def edit_category(request,id):
    
    product_category = get_object_or_404(ProductCategory, id=id)
    if request.method == 'POST':
        
        
              
        is_active= request.POST.get('is_active')
        
        if is_active is None:
           is_active = False
        else:
            is_active = True

        allow_price_edit =request.POST.get('allow_price_edit')
        if allow_price_edit is None:
           allow_price_edit = False
        else:
            allow_price_edit = True

    
        category_name = request.POST.get('category_name')
        product_category.category_name = category_name
        product_category.is_active=is_active
        product_category.allow_price_edit=allow_price_edit
        product_category.updated_by = request.user
        product_category.updated_at = timezone.now()
        product_category.save()
        messages.success(request, 'Category Updated Successfully.')
        return redirect('product:list_category')
    return render(request,'pages/category/edit.html',{'product_category': product_category})
 
 
@login_required  
def delete_category(request, id):
    product_category = ProductCategory.objects.get(id=id)
    print(product_category,"ddd")
    product_category.deleted_by = request.user 
    product_category.soft_delete()
    messages.success(request, 'Category Deleted Successfully.')
    return redirect('product:list_category')

@login_required
def list_product(request):
    product_id = request.GET.get('product_id')
    sku = request.GET.get('sku')
    category = request.GET.get('category')
    # status = request.GET.get('status')
    categories = ProductCategory.objects.filter(is_active=True)
    allproducts = Product.objects.filter(deleted_at__isnull=True ).order_by('category__category_name')
    products = Product.objects.filter(deleted_at__isnull=True ).order_by('category__category_name')
    other_images = OtherImage.objects.filter(product__in=products)
    # Apply additional filters based on user input
    if product_id:
        product_id=product_id.strip()
        products = products.filter(
            Q(id__icontains=product_id) or
            Q(sku__icontains=sku) or
            Q(category__category_name__icontains=category) 
        )
    # if supplier_name:
    #     supplier = supplier.filter(supplier_name__icontains=supplier_name)

    if sku:
        sku=sku.strip()
        products = products.filter(sku__icontains=sku)

    if category:
        category=category.strip()
        products = products.filter(category__id__icontains=category)
    total_records = products.count()
    show_pagination = total_records > settings.PAGE_RECORDS
    if show_pagination: 
        page = request.GET.get('page', 1)
        # items_per_page = 10  # Adjust as needed
        paginator = Paginator(products, settings.PAGE_RECORDS)
    
        try:
            products = paginator.page(page)
        except PageNotAnInteger:
            products = paginator.page(1)
        except EmptyPage:
            products = paginator.page(paginator.num_pages)
    return render(request,'pages/product/list.html', {'products': products,'allproducts':allproducts,'categories':categories,'other_images':other_images})

@login_required
def create_product(request):
    categories = ProductCategory.objects.filter(is_active=True)
    check_lists=Heading.objects.all()
    context = {'categories': categories}
    if request.method == 'POST':
        
        form = request.POST
      
        try:
            sku = request.POST['sku']
            product_type = request.POST['product_type']
            category_id = request.POST['category']
            product_name = request.POST['product_name']
            product_description = request.POST['product_description']
            product_specification_contents = request.POST['product_specification_contents']
            product_image_main = request.FILES.get('product_image_main')
            
            product_price = request.POST['product_price']
            specification_pdf = request.FILES.get('specification_pdf')
            
            # selected_heading_ids  = request.POST.getlist('check_list')

            # print(selected_heading_ids )
            is_active= request.POST.get('is_active')
          
        
            if is_active == 'Inactive':
               is_active = False
            else:
                is_active = True
            

            if Product.objects.filter(product_name=product_name).exists():
                messages.error(request, 'Product Name Already Exist')
                context['form'] = form
                return render(request,'pages/product/create.html',context)
            
            
            if not product_image_main:
                messages.error(request,"Please Select Main Image")
                context['form'] = form
                return render(request,'pages/product/create.html',context)
                
                

            if Product.objects.filter(sku=sku).exists():
                messages.error(request,"Product SKU Already Exist.")
                context['form'] = form
                return render(request,'pages/product/create.html',context)
        
            product = Product.objects.create(
                sku=sku,
                product_type=product_type,
                category_id=category_id,
                product_name=product_name,
                product_description= product_description ,
                product_specification_contents=product_specification_contents,
                product_image_main=product_image_main,
            
                product_price=product_price,
                specification_pdf=specification_pdf,
                is_active=is_active,
                
                created_by=request.user
            )
            # product.selected_heading.clear()
            # product.selected_heading.add(*selected_heading_ids)
            if request.FILES.get('product_details_pdf'):
                product.product_details_pdf = request.FILES['product_details_pdf']
            product.save()
            
            # -------- MULTIPLE SPECIFICATION PDF --------
            MAX_PDFS = 5
            spec_files = request.FILES.getlist('product_specification_pdf')
            existing_count = ProductSpecificationPDF.objects.filter(
                product=product,
                deleted_at__isnull=True
            ).count()
            
            if existing_count + len(spec_files) > MAX_PDFS:
                messages.error(request, "You can upload maximum 5 specification PDFs.")
                return redirect(request.META.get('HTTP_REFERER'))

            for f in spec_files:
                ProductSpecificationPDF.objects.create(
                    product=product,
                    file=f,
                    created_by=request.user
                )
            
            # -------- MULTIPLE MANUAL PDF --------
            manual_files = request.FILES.getlist('product_manual_pdf')
            existing_manual = ProductManualPDF.objects.filter(
                product=product,
                deleted_at__isnull=True
            ).count()
            
            if existing_manual + len(manual_files) > MAX_PDFS:
                messages.error(request, "You can upload maximum 5 manual PDFs.")
                return redirect(request.META.get('HTTP_REFERER'))
            
            for f in manual_files:
                ProductManualPDF.objects.create(
                    product=product,
                    file=f,
                    created_by=request.user
                )

                
            other_images = request.FILES.getlist('other_images')
            for image in other_images:
                OtherImage.objects.create(product=product, other_images=image)


            refresh_token(request)
            myobdata = MyobModel.objects.first()
            if not myobdata:
                messages.error(request,'Please First create Access Code')
                return redirect('/myob/initiate-connection')
            api_url = f"https://ar2.api.myob.com/accountright/{settings.COMPANY_FILE_ID}/Inventory/Item/"
            headers = {
                'Authorization': f'Bearer {myobdata.access_token}',
                'x-myobapi-key': settings.MYOB_CLIENT_ID,
                'x-myobapi-version': 'v2',
                'Content-Type': 'application/json',
                'Accept-Encoding': 'gzip,deflate'
            }
            product = Product.objects.latest('id')
            product_data=   {
                    "Number":product.sku,
                    "Name": f'{product.product_name}',
                    "IsActive": True,
                    "IsBought" : True,
                    "IsSold" : True,
                    "IsInventoried" : False,
                    "ExpenseAccount" :  {
                             "UID": myob_expense_account},
                    "Description": product.product_description[:255],
                   
                    "CostOfSalesAccount" : {
                        "UID" : myob_cost_of_sales_account,
                                    },
                    "IncomeAccount": {
                            "UID":  myob_income_account,
                        },

                    "AssetAccount" : {
                                "UID" : myob_asset_account,
                                },
                    "BuyingDetails": {
                        "BaseSellingPrice" :float(product.product_price),
                        "ItemsPerBuyingUnit" : 1,
                        "TaxCode": {
                            "UID": myob_tax_code,
                        }
                    },
                    "SellingDetails": {
                        "BaseSellingPrice" : float(product.product_price),
                        "ItemsPerBuyingUnit" : 1,
                        "TaxCode": {
                            "UID": myob_tax_code,
                        }
                    }
                }
            product_json = json.dumps(product_data)
            response = requests.post(api_url, data=product_json, headers=headers)
            print("-------------------dk--------------------")
            print("Response:", response.status_code, response.content)
            print(response)
            print('2222')
            print(request.headers)
            print("--------------------")
            data=response.headers
            if response.status_code == 201:
                location = data['Location']
                if location:
                    parts = location.split('/')
                    uid = parts[-1]
                    # product.myob_location = location
                    product.uid = uid
                    product.save()
                messages.success(request, 'Product Added Successfully.')
                return redirect('product:list_product')
            else:
                messages.success(request, 'Failed to Add to Myob Product.')
                return redirect('product:list_product')

        except ValidationError as validation_error:
            context = {'categories': categories, 'validation_error': validation_error}
            context['form'] = form
            return render(request, 'product_temp/create_product.html', context)
    else:
        context = {'categories': categories,'check_lists':check_lists}
        context['form'] = {}
        return render(request,'pages/product/create.html',context)

@login_required       
def delete_spec_pdf(request, id):
    pdf = get_object_or_404(ProductSpecificationPDF, id=id)
    pdf.deleted_at = timezone.now()
    pdf.deleted_by = request.user
    pdf.save()
    messages.success(request, "Specification PDF deleted successfully.")
    return redirect(request.META.get('HTTP_REFERER'))

@login_required   
def delete_manual_pdf(request, id):
    pdf = get_object_or_404(ProductManualPDF, id=id)
    pdf.deleted_at = timezone.now()
    pdf.deleted_by = request.user
    pdf.save()
    messages.success(request, "Manual PDF deleted successfully.")
    return redirect(request.META.get('HTTP_REFERER'))

        
@login_required   
def delete_product_other_image(request,id):
    OtherImage.objects.filter(id=id).delete()
    return JsonResponse({'success':True})

expense_account_uid = getattr(settings, 'MYOB_ExpenseAccount', None)
@login_required   
def edit_product(request,id):
    product = get_object_or_404(Product,id=id)
    spec_pdfs = product.specification_pdfs.filter(deleted_at__isnull=True)
    manual_pdfs = product.manual_pdfs.filter(deleted_at__isnull=True)
    categories = ProductCategory.objects.filter(is_active=True)
    check_lists=Heading.objects.all()
    if request.method == 'POST':
        # Extract form data
        #dd(request.POST)
        refresh_token(request)
   
        myobdata = MyobModel.objects.first()
        if not myobdata:
            messages.error(request,'Please First create Access Code')
            return redirect('/myob/initiate-connection')
        UID=product.uid
        api_url = f"https://ar2.api.myob.com/accountright/{settings.COMPANY_FILE_ID}/Inventory/Item/{UID}"
        sku = request.POST['sku']
        product_type = request.POST['product_type']
        category_id = request.POST['category']
        product_name = request.POST['product_name']
        product_description = request.POST['product_description']
        product_specification_contents = request.POST['product_specification_contents']
        # selected_heading_ids  = request.POST.getlist('check_list')
        product_image_main = request.FILES.get('product_image_main')
        # print(selected_heading_ids )
        is_active= request.POST.get('is_active')
        if is_active == 'Inactive':
           is_active = False
        else:
            is_active = True
            
        if not product_image_main:
            if product.product_image_main == None:
                messages.error(request,"Please Select Main Image")
                context = {'product': product, 'categories': categories}
                return render(request,'pages/product/edit.html',context)
        if  Product.objects.filter(sku=sku).exclude(id=id).exists():
            messages.error(request, 'Product SKU Already Exist.')
            return render(request,'pages/product/edit.html',{'product':product,'categories':categories})
        if  product_image_main:
            product.product_image_main = product_image_main 
                
        product_price = request.POST['product_price']
        specification_pdf = request.FILES.get('specification_pdf')
        
        # Update the product instance
             
        
        product.sku = sku
        product.product_type = product_type
        product.category_id = category_id
        product.product_name = product_name
        product.product_description = product_description
        product.product_specification_contents = product_specification_contents
        product.product_price = product_price
        product.specification_pdf = specification_pdf
        product.is_active=is_active
        product.is_converted_from_trade=True
        product.updated_by=request.user
        # product.selected_heading.clear()
        # product.selected_heading.add(*selected_heading_ids)
        if request.FILES.get('product_details_pdf'):
            product.product_details_pdf = request.FILES['product_details_pdf']
        product.save()
        
        # -------- MULTIPLE SPECIFICATION PDF --------
        spec_files = request.FILES.getlist('product_specification_pdf')
        for f in spec_files:
            ProductSpecificationPDF.objects.create(
                product=product,
                file=f,
                created_by=request.user
            )
        
        # -------- MULTIPLE MANUAL PDF --------
        manual_files = request.FILES.getlist('product_manual_pdf')
        for f in manual_files:
            ProductManualPDF.objects.create(
                product=product,
                file=f,
                created_by=request.user
            )

        # product.save()
        print('saved')
        # Handle other images
        other_images = request.FILES.getlist('other_images')
        # dd(other_images)
        for image in other_images:
            try:
                other_image = OtherImage.objects.create(product=product, other_images=image)
                print(f'Successfully created: {other_image}')
                # OtherImage.save();
            except Exception as e:
                print(f'Error: {e}')
        # dd(other_images)
        headers = {
            'Authorization': f'Bearer {myobdata.access_token}',
            'x-myobapi-key': settings.MYOB_CLIENT_ID,
            'x-myobapi-version': 'v2',
            'Content-Type': 'application/json',
            'Accept-Encoding': 'gzip,deflate'
        }

        if UID:
            response = requests.get(api_url, headers=headers)
            response_json = response.json()
            print(response_json)
            current_row_version = response_json.get('RowVersion')
            product_data=   {
                    "UID":product.uid,
                    "Number":product.sku,
                    "Name": f'{product.product_name}',
                    "IsActive": True,
                    "IsBought" : True,
                    "IsSold" : True,
                    "IsInventoried" : False,
                  
                    "Description": product.product_description[:255],
                    "RowVersion":current_row_version,
                   
                    "ExpenseAccount" :  {
                             "UID": myob_expense_account,
                             },
                    "Description": product.product_description[:255],
                   
                    "CostOfSalesAccount" : {
                        "UID" : myob_cost_of_sales_account,
                                    },
                    "IncomeAccount": {
                            "UID": myob_income_account,
                        },

                    "AssetAccount" : {
                                "UID" :  myob_asset_account,
                                },


                    "BuyingDetails": {
                        "BaseSellingPrice" :float(product.product_price),
                        "ItemsPerBuyingUnit" : 1,
                        "TaxCode": {
                            "UID":  myob_tax_code,
                        }
                    },
                    "SellingDetails": {
                        "BaseSellingPrice" : float(product.product_price),
                        "ItemsPerBuyingUnit" : 1,
                        "TaxCode": {
                            "UID":  myob_tax_code,
                        }
                    }
                }
        
            product_json = json.dumps(product_data)
            response = requests.put(api_url, data=product_json, headers=headers)

            print("-------------------dk--------------------")
            print("Response:", response.status_code, response.content)
            print(response)
            print('2222')
            print(request.headers)
            print("--------------------")

            data=response.headers
            if response.status_code == 200:
                location = data['Location']
                if location:
                    parts = location.split('/')
                    uid = parts[-1]
                    # product.myob_location = location
                    product.uid = uid
                    product.save()
                    messages.success(request, 'Product Updated Successfully.')
                    return redirect('product:list_product')
                else:
                    messages.error(request, 'Failed To Update Product.')
                    return redirect('product:list_product')
            else:
                messages.success(request, 'Product Updated Successfully.')
                return redirect('product:list_product')
        else:
            refresh_token(request)
            myobdata = MyobModel.objects.first()
            if not myobdata:
                messages.error(request,'Please First create Access Code')
                return redirect('/myob/initiate-connection')
            api_url = f"https://ar2.api.myob.com/accountright/{settings.COMPANY_FILE_ID}/Inventory/Item/"
            headers = {
                'Authorization': f'Bearer {myobdata.access_token}',
                'x-myobapi-key': settings.MYOB_CLIENT_ID,
                'x-myobapi-version': 'v2',
                'Content-Type': 'application/json',
                'Accept-Encoding': 'gzip,deflate'
            }
            product_data=   {
                    "Number":product.sku,
                    "Name": f'{product.product_name}',
                    "IsActive": True,
                    "IsBought" : True,
                    "IsSold" : True,
                    "IsInventoried" : False,
                    "ExpenseAccount" :  {
                             "UID": myob_expense_account},
                    "Description": product.product_description[:255],
                   
                    "CostOfSalesAccount" : {
                        "UID" : myob_cost_of_sales_account,
                                    },
                    "IncomeAccount": {
                            "UID":  myob_income_account,
                        },

                    "AssetAccount" : {
                                "UID" : myob_asset_account,
                                },
                    "BuyingDetails": {
                        "BaseSellingPrice" :float(product.product_price),
                        "ItemsPerBuyingUnit" : 1,
                        "TaxCode": {
                            "UID": myob_tax_code,
                        }
                    },
                    "SellingDetails": {
                        "BaseSellingPrice" : float(product.product_price),
                        "ItemsPerBuyingUnit" : 1,
                        "TaxCode": {
                            "UID": myob_tax_code,
                        }
                    }
                }
            product_json = json.dumps(product_data)
            response = requests.post(api_url, data=product_json, headers=headers)
            print("-------------------dk--------------------")
            print("Response:", response.status_code, response.content)
            print(response)
            print('2222')
            print(request.headers)
            print("--------------------")
            data=response.headers
            if response.status_code == 201:
                location = data['Location']
                if location:
                    parts = location.split('/')
                    uid = parts[-1]
                    # product.myob_location = location
                    product.uid = uid
                    product.save()
                messages.success(request, 'Product Updated Successfully.')
                return redirect('product:list_product')
            else:
                messages.success(request, 'Failed to Add Product to Myob .')
                return redirect('product:list_product')
                
    return render(request,'pages/product/edit.html',{'product': product, 'categories': categories,'check_lists':check_lists,'spec_pdfs': spec_pdfs,'manual_pdfs': manual_pdfs})



@login_required
def delete_product(request, id):
    product = Product.objects.get(id=id)
    product.deleted_by = request.user  
    product.soft_delete()
    messages.success(request, 'Product Deleted Successfully.')
    return redirect('product:list_product')
   



def create_serialnumber(request):
    context={}
    products = Product.objects.filter(is_active=True,deleted_at__isnull=True).order_by('category__category_name')
    if request.method == 'POST':
        form = request.POST
        is_active= request.POST.get('is_active')
        if is_active is None:
           is_active = False
        else:
            is_active = True
        serial_numbers = request.POST.getlist('serial_number[]', []) 
        print(serial_numbers)
        product_id = request.POST.get('product')
        for serial_number in serial_numbers:
            if SerialNumber.objects.filter(serial_number=serial_number):
                messages.error(request, 'Serial Number Already Exists.')
                context = {'products': products,}
                context['form'] = form
                return render(request, 'pages/serialnumber/create.html', context)
            serial_number_obj = SerialNumber(
                serial_number=serial_number,
                product_id=product_id,
                status=1,
                tracking_status=SerialNumber.ARRIVED,
                is_active=is_active
            )
            serial_number_obj.created_by = request.user
            serial_number_obj.save()
        messages.success(request, 'Serial Number Added Successfully.')
        return redirect('product:list_serialnumber')
    context = {'products': products}
    context['form'] = {}
    return render(request, 'pages/serialnumber/create.html', context)

@login_required
def list_serialnumber(request):
    serial_number = request.GET.get('serial_number')
    product_id = request.GET.get('product_id')
    customer_name = request.GET.get('customer_name')
    supplier_name = request.GET.get('supplier_name')
    sku = request.GET.get('sku')
    category_name = request.GET.get('category_name')
    status = request.GET.get('status')
    tracking_status = request.GET.get('tracking_status')
    products = Product.objects.filter(is_active=True,is_product=0,deleted_at__isnull=True ).order_by('category__category_name')
    serialnumbers = SerialNumber.objects.filter(deleted_at__isnull=True).order_by('customer','-created_at')  
    
    # Apply additional filters based on user input
    if serial_number:
        serialnumbers = serialnumbers.filter(
            Q(serial_number__icontains=serial_number) or
            Q(product__product_name__icontains=product_name) or
            Q(customer__first_name__icontains=customer_name) or
            Q(customer__last_name__icontains=customer_name) or
            Q(customer__company_name__icontains=customer_name)or
            Q(supplier__first_name__icontains=supplier_name) or
            Q(supplier__last_name__icontains=supplier_name) or
            Q(supplier__company_name__icontains=supplier_name)or
            Q(category_name__icontains=category_name)or
            Q(status=status)or
            Q(tracking_status=tracking_status)
        ).order_by('customer','-created_at')  
        
    if product_id:
        # product_name = product_name.strip() if product_name else ''
        # sku = sku.strip() if sku else ''
        serialnumbers = serialnumbers.filter(
            Q(product__id=product_id) 
        ).order_by('customer', '-created_at')
    # if product_name:
    #     product_name=product_name.strip()
    #     serialnumbers = serialnumbers.filter(
    #          Q(product__product_name__icontains=product_name) or
    #         Q(product__sku__icontains=product_name)
    #         ).order_by('customer','-created_at')  
        #     product__product_name__icontains=product_name)
        # serialnumbers = serialnumbers.filter(product__sku__icontains=product_name)

    if customer_name:
        serialnumbers = serialnumbers.filter(customer__id=customer_name).order_by('customer','-created_at')  
    if supplier_name:
        serialnumbers = serialnumbers.filter(supplier__id=supplier_name).order_by('supplier','-created_at')  
    if category_name:
        serialnumbers = serialnumbers.filter(pcategory_name__icontains=category_name).order_by('customer','created_at') 
    if status:
        status=int('0' + status)  # 0-open,1-allocated,2-unallocated
        if status==3 : #3-open
            serialnumbers = serialnumbers.filter(serial_number ='',customer__isnull=True)
        elif status==1: #1-allocated
            serialnumbers = serialnumbers.filter(serial_number__isnull=False,customer__isnull=False)
        elif status==2: #2-unallocated
            # serialnumbers = serialnumbers.include(serial_number__isnull=True).include(serial_number__exact='')
            serialnumbers = serialnumbers.filter(customer__isnull=True,serial_number__gt='',serial_number__isnull=False)
    if tracking_status:
        if(int(tracking_status) <= 3):
            serialnumbers = serialnumbers.filter(tracking_status__icontains=tracking_status).order_by('customer','created_at') 
        else:
            if(int(tracking_status) == 5):
                serialnumberstrack = [
                    sn for sn in serialnumbers
                    if sn.get_order_item_inprogress
                ]
                ids = [sn.id for sn in serialnumberstrack]
    
            elif(int(tracking_status) == 7):
                serialnumberstrack = [
                    sn for sn in serialnumbers
                    if sn.get_order_item_installed 
                ]
                ids = [sn.id for sn in serialnumberstrack]
                print(ids)
            else:
                serialnumberstrack = [
                    sn for sn in serialnumbers
                    if sn.get_order_item and sn.get_order_item != None and str(sn.get_order_item.status) == str(tracking_status)
                ]
                ids = [sn.id for sn in serialnumberstrack]
    
            if ids:
                serialnumbers = serialnumbers.filter(id__in=ids)
            else:
                serialnumbers = serialnumbers.none()
            print(serialnumberstrack)
            # serialnumbers = serialnumbers.filter(tracking_status__icontains=tracking_status).order_by('customer','created_at')
    customers = Customer.objects.filter(is_active=True)
    suppliers = Supplier.objects.filter(is_active=True)
    total_records = serialnumbers.count()
    show_pagination = total_records > settings.PAGE_RECORDS
    if show_pagination: 
        page = request.GET.get('page', 1)
        paginator = Paginator(serialnumbers, settings.PAGE_RECORDS)  # Show 10 serial numbers per page
        try:
            serialnumbers = paginator.page(page)
        except PageNotAnInteger:
            serialnumbers = paginator.page(1)
        except EmptyPage:
            serialnumbers = paginator.page(paginator.num_pages)
    order_items = Order_Item.objects.filter(serial_number__isnull=True,is_trade = 0)
    for sn in serialnumbers:
        if sn.bill:
            cost_map = sn.bill.get_landed_cost_map()
            sn.landed_cost = cost_map.get(sn.product_id, 0)
        else:
            sn.landed_cost = 0
    serialnumbersUnallocatedlist = SerialNumber.objects.filter(deleted_at__isnull=True,customer__isnull=True,invoice__isnull=True,serial_number__isnull=False,status=1) 
    # dd(serialnumbersUnallocatedlist)
    return render(request, 'pages/serialnumber/list.html', {'serialnumbersUnallocatedlist':serialnumbersUnallocatedlist,'serialnumbers': serialnumbers,'customers':customers,'order_items':order_items,'suppliers':suppliers,'products':products})

@login_required
def list_serialnumber_arrival_today(request):
    serial_number = request.GET.get('serial_number')
    product_id = request.GET.get('product_id')
    customer_name = request.GET.get('customer_name')
    supplier_name = request.GET.get('supplier_name')
    sku = request.GET.get('sku')
    category_name = request.GET.get('category_name')
    status = request.GET.get('status')
    products=Product.objects.filter(deleted_at__isnull=True ).order_by('category__category_name')
    serialnumbers = SerialNumber.objects.filter(deleted_at__isnull=True).order_by('customer','-created_at')  
    # Apply additional filters based on user input
    if serial_number:
        serialnumbers = serialnumbers.filter(
            Q(serial_number__icontains=serial_number) or
            Q(product__product_name__icontains=product_name) or
            Q(customer__first_name__icontains=customer_name) or
            Q(customer__last_name__icontains=customer_name) or
            Q(customer__company_name__icontains=customer_name)or
            Q(supplier__first_name__icontains=supplier_name) or
            Q(supplier__last_name__icontains=supplier_name) or
            Q(supplier__company_name__icontains=supplier_name)or
            Q(category_name__icontains=category_name)or
            Q(is_active=status)
        ).order_by('customer','-created_at')  
        
    if product_id:
        # product_name = product_name.strip() if product_name else ''
        # sku = sku.strip() if sku else ''
        serialnumbers = serialnumbers.filter(
            Q(product__id=product_id) 
        ).order_by('customer', '-created_at')
    # if product_name:
    #     product_name=product_name.strip()
    #     serialnumbers = serialnumbers.filter(
    #          Q(product__product_name__icontains=product_name) or
    #         Q(product__sku__icontains=product_name)
    #         ).order_by('customer','-created_at')  
        #     product__product_name__icontains=product_name)
        # serialnumbers = serialnumbers.filter(product__sku__icontains=product_name)

    if customer_name:
        serialnumbers = serialnumbers.filter(customer__id=customer_name).order_by('customer','-created_at')  
    if supplier_name:
        serialnumbers = serialnumbers.filter(supplier__id=supplier_name).order_by('supplier','-created_at')  
    if category_name:
        serialnumbers = serialnumbers.filter(pcategory_name__icontains=category_name).order_by('customer','created_at') 
    if status:
        status=int('0' + status)  # 0-open,1-allocated,2-unallocated
        if status==3 : #3-open
            serialnumbers = serialnumbers.filter(serial_number ='',customer__isnull=True)
        elif status==1: #1-allocated
            serialnumbers = serialnumbers.filter(serial_number__isnull=False,customer__isnull=False)
        elif status==2: #2-unallocated
            # serialnumbers = serialnumbers.include(serial_number__isnull=True).include(serial_number__exact='')
            serialnumbers = serialnumbers.filter(customer__isnull=True,serial_number__gt='',serial_number__isnull=False)
    customers = Customer.objects.filter(is_active=True)
    suppliers = Supplier.objects.filter(is_active=True)
    total_records = serialnumbers.count()
    show_pagination = total_records > settings.PAGE_RECORDS
    if show_pagination: 
        page = request.GET.get('page', 1)
        paginator = Paginator(serialnumbers, settings.PAGE_RECORDS)  # Show 10 serial numbers per page
        try:
            serialnumbers = paginator.page(page)
        except PageNotAnInteger:
            serialnumbers = paginator.page(1)
        except EmptyPage:
            serialnumbers = paginator.page(paginator.num_pages)
    order_items = Order_Item.objects.filter(serial_number__isnull=True)
    return render(request, 'pages/serialnumber/list.html', {'serialnumbers': serialnumbers,'customers':customers,'order_items':order_items,'suppliers':suppliers,'products':products})


def edit_serialnumber(request, id):
    #dd(id)
    serialnumber=SerialNumber.objects.get(id=id)
    products=Product.objects.filter(deleted_at__isnull=True ).order_by('category__category_name')
    invoices=Invoice.objects.filter(invoice_items__product=serialnumber.product,invoice_items__is_trade_product=0)
    order_items = Order_Item.objects.filter(serial_number__isnull=True,is_trade=0)
    if request.method == 'POST':
        product_id= request.POST.get('product')
     
        product=Product.objects.get(id=product_id) 
   
        serial_number = request.POST.get('serial_number')

        serialnumber.product=product
        is_active= request.POST.get('is_active')
        
        order_item_Id = request.POST.get('order_item')
        if serial_number :
            if SerialNumber.objects.filter(serial_number=serial_number,deleted_at__isnull=True).exclude(pk=id):
               messages.error(request, 'Serial Number Already Exists.')
               return redirect('product:edit_serialnumber' ,id )

        orderitem = Order_Item.objects.filter(serial_number=serialnumber).first()
        if orderitem:
            print("deepak 1")
            orderitem.serial_number = None
            orderitem.updated_by = request.user
            orderitem.save()

            # Update serial number attributes
            serialnumber.status = SerialNumber.UNALLOCATED
            serialnumber.invoice = None 
            serialnumber.customer = None  
            serialnumber.updated_by = request.user
            serialnumber.serial_number=serial_number
            serialnumber.save()
            print(order_item_Id)
            if order_item_Id:
                new_order_item = get_object_or_404(Order_Item, id=order_item_Id)
                # serialnumber=SerialNumber.objects.get(serial_number=serial_number)
                new_order_item.serial_number = serialnumber
                new_order_item.updated_by = request.user
                
                new_order_item.save()
                serialnumber.invoice = new_order_item.order.invoice
                serialnumber.customer = new_order_item.order.invoice.customer
                serialnumber.status = SerialNumber.ALLOCATED
            else:
                #new_order_item = get_object_or_404(Order_Item, id=order_item_Id)
                # serialnumber=SerialNumber.objects.get(serial_number=serial_number)
                orderitem.serial_number = None
                orderitem.updated_by = request.user
                orderitem.save()
                serialnumber.invoice = None
                serialnumber.customer = None
                serialnumber.status = SerialNumber.UNALLOCATED

            # Update serial number status and related fields
            
            serialnumber.updated_by = request.user
            serialnumber.save()
            if new_order_item:
                new_order_item.status=serialnumber.tracking_status
                new_order_item.save()
            messages.success(request, 'Serial Number Reallocated Successfully.')
            return redirect('product:list_serialnumber')
        else:
            print("rahul")
            order_item_Id = request.POST.get('order_item')
            
            serialnumber.serial_number=serial_number
            serialnumber.status = SerialNumber.UNALLOCATED
            serialnumber.save()
            # serialnumber=SerialNumber.objects.get(serial_number=serial_number)
            
          
            # Update new order item's serial_number
            if order_item_Id:
                new_order_item = get_object_or_404(Order_Item, id=order_item_Id)
                new_order_item.serial_number = serialnumber
               
                new_order_item.updated_by = request.user
                new_order_item.save()
                serialnumber.status = SerialNumber.ALLOCATED
                serialnumber.invoice = new_order_item.order.invoice
                serialnumber.customer = new_order_item.order.invoice.customer
                serialnumber.save()
                new_order_item.status=serialnumber.tracking_status
                new_order_item.save()

            # Update serial number status and related fields
           
            serialnumber.updated_by = request.user
            serialnumber.save()
           
            messages.success(request, 'Serial Number Updated Successfully.')
        return redirect('product:list_serialnumber')
    
        if is_active is None:
           is_active = False
        else:
            is_active = True
        serialnumber.is_active = is_active
        serialnumber.updated_by = request.user
        if  serial_number and serial_number.strip(): 
            # dd('here')
            serialnumber.serial_number=serial_number
            if serialnumber.status == 0:
                serialnumber.status=1
        else:
            # dd('out')
            serialnumber.serial_number = None
        serialnumber.save()
        messages.success(request, 'Serial Number Updated Successfully.')
        return redirect('product:list_serialnumber')
    return render(request, 'pages/serialnumber/edit.html', {'serialnumber': serialnumber,'products':products,'invoices':invoices,'order_items':order_items})
    
    
@login_required
def reallocate_serial_number(request, id):
    if request.method == 'POST':
        try:
            serial_number = SerialNumber.objects.get(id=id)
            orderitem = Order_Item.objects.filter(serial_number=serial_number).first()

            if orderitem:
                
                print("deepak")
                # Update existing order item's serial_number
                orderitem.serial_number = None
                orderitem.updated_by = request.user
                orderitem.save()

                # Update serial number attributes
                if serial_number.serial_number != ' ' and serial_number.serial_number != None:
                    serial_number.status = SerialNumber.UNALLOCATED
                else:
                    serial_number.status = 3
                serial_number.invoice = None 
                serial_number.customer = None  
                serial_number.updated_by = request.user
                serial_number.save()

                order_item_Id = request.POST.get('order_item')
                new_order_item = get_object_or_404(Order_Item, id=order_item_Id)

                # Update new order item's serial_number
                new_order_item.serial_number = serial_number
                new_order_item.status=serial_number.tracking_status
                new_order_item.updated_by = request.user
                new_order_item.save()

                # Update serial number status and related fields
                serial_number.status = SerialNumber.ALLOCATED
                serial_number.invoice = new_order_item.order.invoice
                serial_number.customer = new_order_item.order.invoice.customer
                serial_number.updated_by = request.user
                serial_number.save()

                messages.success(request, 'Serial Number Reallocated Successfully.')
                return redirect('product:list_serialnumber')
            else:
                print("rahul")
                order_item_Id = request.POST.get('order_item')
                new_order_item = get_object_or_404(Order_Item, id=order_item_Id)

                # Update new order item's serial_number
                new_order_item.serial_number = serial_number
                new_order_item.status=serial_number.tracking_status
                new_order_item.updated_by = request.user
                new_order_item.save()

                # Update serial number status and related fields
                serial_number.status = SerialNumber.ALLOCATED
                serial_number.invoice = new_order_item.order.invoice
                serial_number.customer = new_order_item.order.invoice.customer
                serial_number.updated_by = request.user
                serial_number.save()

                messages.success(request, 'Serial Number Allocated Successfully.')
                return redirect('product:list_serialnumber')
        except SerialNumber.DoesNotExist:
            messages.error(request, 'Serial Number not found.')
        except Order_Item.DoesNotExist:
            messages.error(request, 'Order Item not found.')

    return redirect('product:list_serialnumber')
@login_required
def release_serial_number(request, id):
    # print(request.POST)
    # dd('here')
    if request.method == 'POST':
        try:
            serial_number = SerialNumber.objects.get(id=id)
            orderitem = Order_Item.objects.filter(serial_number=serial_number).first()

                
            print("deepak")
            # Update existing order item's serial_number
            orderitem.serial_number = None
            orderitem.status = 0
            orderitem.updated_by = request.user
            orderitem.save()

            # Update serial number attributes
            if serial_number.serial_number != ' ' and serial_number.serial_number != None:
                serial_number.status = SerialNumber.UNALLOCATED
            else:
                serial_number.status = 3
            serial_number.invoice = None 
            serial_number.customer = None  
            serial_number.updated_by = request.user
            serial_number.save()
            messages.success(request, 'Serial Number Released Successfully.')
            return redirect('product:list_serialnumber')
           
        except SerialNumber.DoesNotExist:
            messages.error(request, 'Serial Number not found.')
        except Order_Item.DoesNotExist:
            messages.error(request, 'Order Item not found.')

    return redirect('product:list_serialnumber')

@login_required
def reattach_serial_number(request, id):
    
    if request.method == 'POST':
        try:
            serial_number = SerialNumber.objects.get(id=id)
            orderitem = Order_Item.objects.filter(serial_number=serial_number).first()
            print(request.POST,serial_number,orderitem)
            # dd('here')
            # Update existing order item's serial_number
            # orderitem.serial_number = None
            # orderitem.status = 0
            # orderitem.updated_by = request.user
            # orderitem.save()

            # Update serial number attributes
            if serial_number.serial_number != ' ' and serial_number.serial_number != None:
                serial_number.status = SerialNumber.UNALLOCATED
            else:
                serial_number.status = 3
            serial_number.invoice = None 
            serial_number.customer = None  
            serial_number.tracking_status= 3
            serial_number.updated_by = request.user
            serial_number.save()

            serial_numbernew = SerialNumber.objects.get(id=request.POST.get('serial_number_id'))
            orderitem.serial_number = serial_numbernew
            # orderitem.status = 3
            orderitem.updated_by = request.user
            orderitem.save()
            
            serial_numbernew.status = 2
            serial_numbernew.tracking_status= orderitem.status
            serial_numbernew.invoice = orderitem.order.invoice 
            serial_numbernew.customer = orderitem.order.invoice.customer  
            serial_numbernew.updated_by = request.user
            serial_numbernew.save()

            # serial_number.status = SerialNumber.ALLOCATED
            # serial_number.invoice = new_order_item.order.invoice
            # serial_number.customer = new_order_item.order.invoice.customer
            # serial_number.updated_by = request.user
            # serial_number.save()

            messages.success(request, 'Serial Number Re-Attached Successfully.')
            return redirect('product:list_serialnumber')
           
        except SerialNumber.DoesNotExist:
            messages.error(request, 'Serial Number not found.')
        except Order_Item.DoesNotExist:
            messages.error(request, 'Order Item not found.')

    return redirect('product:list_serialnumber')
def delete_serialnumber(request, id):
    serialnumber = get_object_or_404(SerialNumber, id=id)
    serialnumber.deleted_by=request.user
    serialnumber.soft_delete()
    
    messages.success(request, 'Serial Number Deleted Successfully.')
    return redirect('product:list_serialnumber')
    

