from django.contrib.auth import authenticate
from django.utils import timezone
from datetime import timedelta
import random

from rest_framework import serializers
from rest_framework_simplejwt.tokens import RefreshToken
from .models import *
from decimal import Decimal

from django.core.mail import send_mail
from django.conf import settings
# =========================================================
# COMMON HELPERS
# =========================================================

def generate_otp():
    return str(random.randint(100000, 999999))


def get_tokens_for_user(user):
    refresh = RefreshToken.for_user(user)
    return {
        'refresh': str(refresh),
        'access': str(refresh.access_token),
    }


# =========================================================
# USER / PROFILE SERIALIZERS
# =========================================================

class UserProfileSerializer(serializers.ModelSerializer):
    class Meta:
        model = User
        fields = [
            'id',
            'full_name',
            'email',
            'phone',
            'role',
            'profile_image',
            'gender',
            'date_of_birth',
            'is_email_verified',
            'is_phone_verified',
        ]


# =========================================================
# AUTH SERIALIZERS
# =========================================================

class RegisterSerializer(serializers.ModelSerializer):
    password = serializers.CharField(write_only=True, min_length=6)
    confirm_password = serializers.CharField(write_only=True, min_length=6)

    class Meta:
        model = User
        fields = [
            'full_name',
            'email',
            'phone',
            'password',
            'confirm_password',
            'gender',
            'date_of_birth',
        ]

    def validate(self, attrs):
        if attrs['password'] != attrs['confirm_password']:
            raise serializers.ValidationError({
                'confirm_password': 'Password and confirm password must match.'
            })

        if User.objects.filter(email=attrs['email']).exists():
            raise serializers.ValidationError({
                'email': 'This email is already registered.'
            })

        if User.objects.filter(phone=attrs['phone']).exists():
            raise serializers.ValidationError({
                'phone': 'This phone number is already registered.'
            })

        return attrs

    def create(self, validated_data):
        validated_data.pop('confirm_password')

        user = User.objects.create_user(
            email=validated_data['email'],
            phone=validated_data['phone'],
            full_name=validated_data['full_name'],
            password=validated_data['password'],
            gender=validated_data.get('gender'),
            date_of_birth=validated_data.get('date_of_birth'),
        )

        otp_code = generate_otp()

        OTPVerification.objects.create(
            user=user,
            email_or_phone=user.email,
            otp_code=otp_code,
            otp_type='signup',
            expires_at=timezone.now() + timedelta(minutes=10),
        )

        return user


class LoginSerializer(serializers.Serializer):
    email = serializers.EmailField()
    password = serializers.CharField(write_only=True)

    def validate(self, attrs):
        email = attrs.get('email')
        password = attrs.get('password')

        user = authenticate(username=email, password=password)

        if not user:
            raise serializers.ValidationError({
                'email': 'Invalid email or password.'
            })

        if not user.is_active:
            raise serializers.ValidationError({
                'email': 'Your account is inactive.'
            })

        attrs['user'] = user
        return attrs


# class ForgotPasswordSerializer(serializers.Serializer):
#     email = serializers.EmailField()

#     def validate(self, attrs):
#         email = attrs.get('email')

#         try:
#             user = User.objects.get(email=email, is_deleted=False)
#         except User.DoesNotExist:
#             raise serializers.ValidationError({
#                 'email': 'No account found with this email.'
#             })

#         attrs['user'] = user
#         return attrs

#     def save(self):
#         user = self.validated_data['user']
#         otp_code = generate_otp()

#         OTPVerification.objects.create(
#             user=user,
#             email_or_phone=user.email,
#             otp_code=otp_code,
#             otp_type='forgot_password',
#             expires_at=timezone.now() + timedelta(minutes=10),
#         )

#         return {
#             'user': user,
#             'otp_code': otp_code,
#         }

class ForgotPasswordSerializer(serializers.Serializer):
    email = serializers.EmailField()

    def validate(self, attrs):
        email = attrs.get('email')

        try:
            user = User.objects.get(email=email, is_deleted=False)
        except User.DoesNotExist:
            raise serializers.ValidationError({
                'email': 'No account found with this email.'
            })

        attrs['user'] = user
        return attrs

    def save(self):
        user = self.validated_data['user']
        otp_code = generate_otp()

        OTPVerification.objects.create(
            user=user,
            email_or_phone=user.email,
            otp_code=otp_code,
            otp_type='forgot_password',
            expires_at=timezone.now() + timedelta(minutes=10),
        )

        subject = "NC-ECOM Password Reset OTP"

        message = (
            f"Dear {user.full_name or 'Customer'},\n\n"
            f"Your password reset OTP is: {otp_code}\n\n"
            f"This OTP is valid for 10 minutes.\n\n"
            f"If you did not request this, please ignore this email.\n\n"
            f"Regards,\n"
            f"NC-ECOM Team"
        )

        send_mail(
            subject=subject,
            message=message,
            from_email=settings.DEFAULT_FROM_EMAIL,
            recipient_list=[user.email],
            fail_silently=False,
        )

        return {
            'user': user,
        }

class ResetPasswordSerializer(serializers.Serializer):
    email = serializers.EmailField()
    otp_code = serializers.CharField(max_length=10)
    new_password = serializers.CharField(write_only=True, min_length=6)
    confirm_password = serializers.CharField(write_only=True, min_length=6)

    def validate(self, attrs):
        email = attrs.get('email')
        otp_code = attrs.get('otp_code')
        new_password = attrs.get('new_password')
        confirm_password = attrs.get('confirm_password')

        if new_password != confirm_password:
            raise serializers.ValidationError({
                'confirm_password': 'Password and confirm password must match.'
            })

        try:
            user = User.objects.get(email=email, is_deleted=False)
        except User.DoesNotExist:
            raise serializers.ValidationError({
                'email': 'No account found with this email.'
            })

        try:
            otp_record = OTPVerification.objects.filter(
                user=user,
                email_or_phone=email,
                otp_code=otp_code,
                otp_type='forgot_password',
                is_used=False,
                is_deleted=False
            ).latest('created_at')
        except OTPVerification.DoesNotExist:
            raise serializers.ValidationError({
                'otp_code': 'Invalid OTP.'
            })

        if otp_record.is_expired():
            raise serializers.ValidationError({
                'otp_code': 'OTP has expired.'
            })

        attrs['user'] = user
        attrs['otp_record'] = otp_record
        return attrs

    def save(self):
        user = self.validated_data['user']
        otp_record = self.validated_data['otp_record']
        new_password = self.validated_data['new_password']

        user.set_password(new_password)
        user.save()

        otp_record.is_used = True
        otp_record.save()

        return user
    
    
    
    
    
# =========================================================
# CATEGORY / PRODUCT SERIALIZERS
# =========================================================

class CategorySerializer(serializers.ModelSerializer):
    class Meta:
        model = Category
        fields = [
            'id',
            'name',
            'slug',
            'image',
            'banner_image',
            'description',
            'show_on_home',
        ]


class BrandSerializer(serializers.ModelSerializer):
    class Meta:
        model = Brand
        fields = '__all__'


class ProductImageSerializer(serializers.ModelSerializer):
    class Meta:
        model = ProductImage
        fields = [
            'id',
            'image',
            'alt_text',
            'sort_order',
            'is_primary',
        ]


class ProductSpecificationSerializer(serializers.ModelSerializer):
    class Meta:
        model = ProductSpecification
        fields = [
            'id',
            'title',
            'value',
            'sort_order',
        ]


class ProductHighlightSerializer(serializers.ModelSerializer):
    class Meta:
        model = ProductHighlight
        fields = [
            'id',
            'title',
            'sort_order',
        ]


class ProductListSerializer(serializers.ModelSerializer):
    category = CategorySerializer(read_only=True)
    brand = BrandSerializer(read_only=True)
    discount_percentage = serializers.ReadOnlyField()
    in_stock = serializers.ReadOnlyField()

    class Meta:
        model = Product
        fields = [
            'id',
            'name',
            'slug',
            'sku',
            'short_description',
            'category',
            'brand',
            'price',
            'old_price',
            'discount_percentage',
            'stock_quantity',
            'in_stock',
            'rating_avg',
            'review_count',
            'thumbnail',
            'is_featured',
            'is_best_selling',
            'is_trending',
            'created_at',
        ]


class ProductDetailSerializer(serializers.ModelSerializer):
    category = CategorySerializer(read_only=True)
    brand = BrandSerializer(read_only=True)
    discount_percentage = serializers.ReadOnlyField()
    in_stock = serializers.ReadOnlyField()
    product_images = ProductImageSerializer(many=True, read_only=True)
    specifications = ProductSpecificationSerializer(many=True, read_only=True)
    highlights = ProductHighlightSerializer(many=True, read_only=True)

    class Meta:
        model = Product
        fields = [
            'id',
            'name',
            'slug',
            'sku',
            'short_description',
            'description',
            'category',
            'brand',
            'price',
            'old_price',
            'discount_percentage',
            'stock_quantity',
            'in_stock',
            'rating_avg',
            'review_count',
            'thumbnail',
            'product_images',
            'specifications',
            'highlights',
            'is_featured',
            'is_best_selling',
            'is_trending',
            'is_returnable',
            'is_cod_available',
            'warranty_text',
            'min_order_quantity',
            'max_order_quantity',
            'created_at',
        ]


class BannerSerializer(serializers.ModelSerializer):
    class Meta:
        model = Banner
        fields = '__all__'
 
        
        
        
        
# =========================================================
# WISHLIST SERIALIZERS
# =========================================================

class WishlistToggleSerializer(serializers.Serializer):
    product_id = serializers.IntegerField()

    def validate_product_id(self, value):
        if not Product.objects.filter(id=value, is_active=True, is_deleted=False).exists():
            raise serializers.ValidationError('Product not found.')
        return value


class WishlistItemSerializer(serializers.ModelSerializer):
    product = ProductListSerializer(read_only=True)

    class Meta:
        model = WishlistItem
        fields = [
            'id',
            'product',
            'created_at',
        ]


# =========================================================
# CART SERIALIZERS
# =========================================================

class CartAddSerializer(serializers.Serializer):
    product_id = serializers.IntegerField()
    quantity = serializers.IntegerField(min_value=1, default=1)

    def validate(self, attrs):
        product_id = attrs.get('product_id')
        quantity = attrs.get('quantity')

        try:
            product = Product.objects.get(
                id=product_id,
                is_active=True,
                is_deleted=False
            )
        except Product.DoesNotExist:
            raise serializers.ValidationError({
                'product_id': 'Product not found.'
            })

        if product.stock_quantity < quantity:
            raise serializers.ValidationError({
                'quantity': 'Requested quantity is not available in stock.'
            })

        attrs['product'] = product
        return attrs


class CartItemUpdateSerializer(serializers.Serializer):
    quantity = serializers.IntegerField(min_value=1)

    def validate_quantity(self, value):
        return value


class CartItemSerializer(serializers.ModelSerializer):
    product = ProductListSerializer(read_only=True)
    total_price = serializers.ReadOnlyField()

    class Meta:
        model = CartItem
        fields = [
            'id',
            'product',
            'quantity',
            'price_at_time',
            'total_price',
            'created_at',
        ]


class CartSerializer(serializers.ModelSerializer):
    cart_items = CartItemSerializer(many=True, read_only=True)
    subtotal = serializers.ReadOnlyField()
    total_items = serializers.ReadOnlyField()

    class Meta:
        model = Cart
        fields = [
            'id',
            'total_items',
            'subtotal',
            'cart_items',
            'created_at',
        ]


# =========================================================
# ADDRESS SERIALIZERS
# =========================================================

class AddressSerializer(serializers.ModelSerializer):
    class Meta:
        model = Address
        fields = [
            'id',
            'full_name',
            'phone',
            'alternate_phone',
            'address_line_1',
            'address_line_2',
            'landmark',
            'city',
            'state',
            'country',
            'postal_code',
            'address_type',
            'is_default',
            'created_at',
        ]

    def create(self, validated_data):
        user = self.context['request'].user

        if validated_data.get('is_default', False):
            Address.objects.filter(
                user=user,
                is_default=True
            ).update(is_default=False)

        return Address.objects.create(user=user, **validated_data)

    def update(self, instance, validated_data):
        if validated_data.get('is_default', False):
            Address.objects.filter(
                user=instance.user,
                is_default=True
            ).exclude(id=instance.id).update(is_default=False)

        for attr, value in validated_data.items():
            setattr(instance, attr, value)

        instance.save()
        return instance
    
    
    
    
    
    
# =========================================================
# COUPON / CHECKOUT / ORDER SERIALIZERS
# =========================================================

class CouponValidateSerializer(serializers.Serializer):
    code = serializers.CharField(max_length=50)


class CheckoutReviewSerializer(serializers.Serializer):
    address_id = serializers.IntegerField()
    coupon_code = serializers.CharField(max_length=50, required=False, allow_blank=True)
    payment_method = serializers.ChoiceField(choices=['razorpay', 'cod'], default='razorpay')


class OrderItemSerializer(serializers.ModelSerializer):
    product = serializers.SerializerMethodField()

    class Meta:
        model = OrderItem
        fields = [
            'id',
            'product',
            'quantity',
            'unit_price',
            'total_price',
        ]

    def get_product(self, obj):
        product = obj.product

        if not product:
            return None

        return {
            "id": product.id,
            "name": product.name,
            "thumbnail": product.thumbnail.url if product.thumbnail else "",
            "price": str(product.price),
        }


 


class OrderListSerializer(serializers.ModelSerializer):
    products = OrderItemSerializer(source='order_items', many=True, read_only=True)
    has_invoice = serializers.SerializerMethodField()
    invoice_number = serializers.SerializerMethodField()

    class Meta:
        model = Order
        fields = '__all__'
        # fields = [
        #     'id',
        #     'order_number',
        #     'status',
        #     'total_amount',
        #     'payment_method',
        #     'address',
        #     'placed_at',
        #     'products',  # 🔥 MOST IMPORTANT
        #     'has_invoice',
        #     'invoice_number',
        # ]

    def get_has_invoice(self, obj):
        return hasattr(obj, 'invoice_document')

    def get_invoice_number(self, obj):
        if hasattr(obj, 'invoice_document'):
            return obj.invoice_document.invoice_number
        return None


class OrderTrackingEventSerializer(serializers.ModelSerializer):

    class Meta:
        model = OrderTrackingEvent

        fields = [
            "id",
            "status",
            "title",
            "description",
            "location",
            "event_time",
            "metadata",
        ]

class OrderDetailSerializer(serializers.ModelSerializer):
    order_items = OrderItemSerializer(many=True, read_only=True)
    address = AddressSerializer(read_only=True)
    invoice = serializers.SerializerMethodField()
    shipment = serializers.SerializerMethodField()
    tracking_events = serializers.SerializerMethodField()
#     tracking_events = OrderTrackingEventSerializer(
#     many=True,
#     read_only=True,
# )
    
    def get_tracking_events(self, obj):
        events = obj.tracking_events.filter(
            is_customer_visible=True,
            is_active=True,
            is_deleted=False,
        )

        return OrderTrackingEventSerializer(
            events,
            many=True,
        ).data

    class Meta:
        model = Order
        fields = '__all__'


    def get_invoice(self, obj):
        if hasattr(obj, 'invoice_document'):
            return InvoiceDocumentSerializer(
                obj.invoice_document,
                context=self.context,
            ).data
        return None
    def get_shipment(self, obj):

        if hasattr(obj, "shipment"):

            return ShipmentSerializer(
                obj.shipment,
                context=self.context,
            ).data

        return None



class ShipmentSerializer(serializers.ModelSerializer):
    order_number = serializers.CharField(
    source="order.order_number",
    read_only=True,
)
    customer_name = serializers.CharField(
    source="order.address.full_name",
    read_only=True,
)

    class Meta:

        model = Shipment

        fields = [
            "id",
            "courier_name",
            "tracking_number",
            "awb_number",
            "shipment_status",
            "estimated_delivery_date",
            "shipped_at",
            "delivered_at",
            "metadata",
            "order_number",
            "customer_name",
        ]


class ShipmentUpdateSerializer(serializers.Serializer):

    shipment_status = serializers.CharField()

    courier_name = serializers.CharField(
        required=False,
        allow_blank=True,
    )

    tracking_number = serializers.CharField(
        required=False,
        allow_blank=True,
    )

    awb_number = serializers.CharField(
        required=False,
        allow_blank=True,
    )

    estimated_delivery_date = serializers.DateTimeField(
        required=False,
    )        
class RazorpayOrderCreateSerializer(serializers.Serializer):
    address_id = serializers.IntegerField()
    coupon_code = serializers.CharField(
        max_length=50,
        required=False,
        allow_blank=True
    )


class VerifyPaymentSerializer(serializers.Serializer):

    address_id = serializers.IntegerField()

    coupon_code = serializers.CharField(
        max_length=50,
        required=False,
        allow_blank=True
    )

    gateway_order_id = serializers.CharField()

    gateway_payment_id = serializers.CharField()

    gateway_signature = serializers.CharField()



class PaymentStatusUpdateSerializer(serializers.Serializer):
    order_id = serializers.IntegerField()
    payment_status = serializers.ChoiceField(choices=['paid', 'failed', 'pending'])
    gateway_order_id = serializers.CharField(required=False, allow_blank=True)
    gateway_payment_id = serializers.CharField(required=False, allow_blank=True)
    gateway_signature = serializers.CharField(required=False, allow_blank=True)
    failure_reason = serializers.CharField(required=False, allow_blank=True)
    
    
    
    
# =========================================================
# REVIEW SERIALIZERS
# =========================================================
# serializers/product_mini_serializer.py  (या same file में ऊपर add कर सकते हो)

class ProductMiniSerializer(serializers.ModelSerializer):
    class Meta:
        model = Product
        fields = ['id', 'name', 'thumbnail']
        
class ProductReviewImageSerializer(serializers.ModelSerializer):
    class Meta:
        model = ProductReviewImage
        fields = [
            'id',
            'image',
        ]


class ProductReviewSerializer(serializers.ModelSerializer):
    user_name = serializers.CharField(source='user.full_name', read_only=True)
    review_images = ProductReviewImageSerializer(many=True, read_only=True)

    # 🔥 MAIN FIX — nested product object
    product = ProductMiniSerializer(read_only=True)

    class Meta:
        model = ProductReview
        fields = [
            'id',
            'user_name',
            'product',  # 🔥 FIXED
            'rating',
            'review_text',
            'is_verified_purchase',
            'created_at',
            'review_images',
        ]


 

class ReviewCreateSerializer(serializers.Serializer):
    product_id = serializers.IntegerField()
    rating = serializers.IntegerField(min_value=1, max_value=5)
    review_text = serializers.CharField(required=False, allow_blank=True)

    def validate_product_id(self, value):
        if not Product.objects.filter(
            id=value,
            is_active=True,
            is_deleted=False
        ).exists():
            raise serializers.ValidationError('Product not found.')
        return value


# =========================================================
# RETURN SERIALIZERS
# =========================================================

class ReturnRequestCreateSerializer(serializers.Serializer):
    order_id = serializers.IntegerField()
    order_item_id = serializers.IntegerField()
    reason = serializers.CharField(max_length=255)
    details = serializers.CharField(required=False, allow_blank=True)

    def validate(self, attrs):
        request = self.context['request']
        order_id = attrs.get('order_id')
        order_item_id = attrs.get('order_item_id')

        order = Order.objects.filter(
            id=order_id,
            user=request.user,
            is_active=True,
            is_deleted=False
        ).first()

        if not order:
            raise serializers.ValidationError({
                'order_id': 'Order not found.'
            })

        order_item = OrderItem.objects.filter(
            id=order_item_id,
            order=order
        ).first()

        if not order_item:
            raise serializers.ValidationError({
                'order_item_id': 'Order item not found.'
            })

        if order_item.product and not order_item.product.is_returnable:
            raise serializers.ValidationError({
                'order_item_id': 'This product is not returnable.'
            })

        attrs['order'] = order
        attrs['order_item'] = order_item
        return attrs


class ReturnRequestSerializer(serializers.ModelSerializer):
    product_name = serializers.CharField(source='order_item.product_name', read_only=True)
    order_number = serializers.CharField(source='order.order_number', read_only=True)
    product_image = serializers.CharField(
        source='order_item.product.thumbnail',
        read_only=True,
    )
    class Meta:
        model = ReturnRequest
        fields = [
            'id',
            'request_number',
            'order_number',
            'product_name',
            'reason',
            'details',
            'status',
            'refund_amount',
            'requested_at',
            'resolved_at',
            'created_at',
            'product_image',
        ]


# =========================================================
# SUPPORT SERIALIZERS
# =========================================================

class SupportTicketCreateSerializer(serializers.Serializer):
    category = serializers.ChoiceField(choices=[
        'order_issue',
        'payment_issue',
        'refund_issue',
        'technical_support',
        'other',
    ])
    title = serializers.CharField(max_length=200)
    description = serializers.CharField()
    priority = serializers.ChoiceField(choices=['low', 'medium', 'high'], default='medium')


class SupportTicketMessageSerializer(serializers.ModelSerializer):
    class Meta:
        model = SupportTicketMessage
        fields = [
            'id',
            'sender_type',
            'message',
            'attachment',
            'created_at',
        ]


class SupportTicketSerializer(serializers.ModelSerializer):
    messages = SupportTicketMessageSerializer(many=True, read_only=True)

    class Meta:
        model = SupportTicket
        fields = [
            'id',
            'ticket_number',
            'category',
            'title',
            'description',
            'status',
            'priority',
            'created_at',
            'messages',
        ]


# =========================================================
# SERVICE REQUEST SERIALIZERS
# =========================================================

class ServiceRequestCreateSerializer(serializers.Serializer):
    device_type = serializers.ChoiceField(choices=[
        'laptop',
        'desktop',
        'printer',
        'networking',
        'display',
        'other',
    ])
    title = serializers.CharField(max_length=200)
    description = serializers.CharField()
    warranty_status = serializers.ChoiceField(choices=[
        'in_warranty',
        'out_of_warranty',
        'unknown',
    ], default='unknown')


class ServiceRequestSerializer(serializers.ModelSerializer):
    class Meta:
        model = ServiceRequest
        fields = [
            'id',
            'request_number',
            'device_type',
            'title',
            'description',
            'status',
            'warranty_status',
            'created_at',
        ]
        
        
        
        
# =========================================================
# CMS / NOTIFICATION / SEARCH / RECENTLY VIEWED SERIALIZERS
# =========================================================

class CMSPageSerializer(serializers.ModelSerializer):
    class Meta:
        model = CMSPage
        fields = [
            'id',
            'title',
            'slug',
            'subtitle',
            'content',
            'page_type',
            'last_updated_label',
            'created_at',
            'updated_at',
        ]


class NotificationSerializer(serializers.ModelSerializer):
    class Meta:
        model = Notification
        fields = [
            'id',
            'title',
            'message',
            'notification_type',
            'is_read',
            'read_at',
            'created_at',
        ]


class RecentSearchCreateSerializer(serializers.Serializer):
    keyword = serializers.CharField(max_length=255)

    def validate_keyword(self, value):
        value = value.strip()
        if not value:
            raise serializers.ValidationError('Keyword is required.')
        return value


class RecentSearchSerializer(serializers.ModelSerializer):
    class Meta:
        model = RecentSearch
        fields = [
            'id',
            'keyword',
            'created_at',
        ]


class RecentlyViewedTrackSerializer(serializers.Serializer):
    product_id = serializers.IntegerField()

    def validate_product_id(self, value):
        if not Product.objects.filter(id=value, is_active=True, is_deleted=False).exists():
            raise serializers.ValidationError('Product not found.')
        return value


class RecentlyViewedSerializer(serializers.ModelSerializer):
    product = ProductListSerializer(read_only=True)

    class Meta:
        model = RecentlyViewed
        fields = [
            'id',
            'product',
            'viewed_at',
        ]
        
        
        
class ReviewImageUploadSerializer(serializers.Serializer):
    review_id = serializers.IntegerField()
    images = serializers.ListField(
        child=serializers.ImageField(),
        allow_empty=False
    )
    
class ProfileUpdateSerializer(serializers.ModelSerializer):
    class Meta:
        model = User
        fields = [
            'full_name',
            'email',
            'phone',
            'gender',
            'date_of_birth',
            'profile_image',
        ]
        
        
        
# =========================================================
# CASHBACK / REWARD SERIALIZERS
# =========================================================

class CashbackRuleSerializer(serializers.ModelSerializer):
    class Meta:
        model = CashbackRule
        fields = [
            'id',
            'title',
            'description',
            'rule_type',
            'threshold_amount',
            'reward_amount',
            'cumulative_days',
            'credit_on_status',
            'show_progress_hint',
            'progress_message',
            'start_date',
            'end_date',
        ]


class CashbackWalletSerializer(serializers.ModelSerializer):
    class Meta:
        model = CashbackWallet
        fields = [
            'id',
            'available_balance',
            'locked_balance',
            'total_earned',
            'total_redeemed',
            'total_expired',
            'created_at',
        ]


class CashbackTransactionSerializer(serializers.ModelSerializer):
    rule_title = serializers.CharField(source='rule.title', read_only=True)
    order_number = serializers.CharField(source='order.order_number', read_only=True)

    class Meta:
        model = CashbackTransaction
        fields = [
            'id',
            'transaction_type',
            'source_type',
            'amount',
            'balance_after_transaction',
            'remark',
            'expires_at',
            'created_at',
            'rule_title',
            'order_number',
        ]


class CashbackPreviewSerializer(serializers.Serializer):
    cart_amount = serializers.DecimalField(max_digits=12, decimal_places=2)


class CashbackOrderTriggerSerializer(serializers.Serializer):
    order_id = serializers.IntegerField()
    
    
    
    
class OrderStatusUpdateSerializer(serializers.Serializer):
    order_id = serializers.IntegerField()
    status = serializers.ChoiceField(choices=[
        'pending',
        'confirmed',
        'processing',
        'shipped',
        'delivered',
        'cancelled',
    ])
    
    
    
    # =========================================================
# INVOICE SERIALIZERS
# =========================================================

class InvoiceDocumentSerializer(serializers.ModelSerializer):
    invoice_url = serializers.SerializerMethodField()

    class Meta:
        model = InvoiceDocument
        fields = [
            'id',
            'invoice_number',
            'file_name',
            'invoice_url',
            'email_sent',
            'emailed_at',
            'created_at',
        ]

    def get_invoice_url(self, obj):
        request = self.context.get('request')
        if obj.pdf_file:
            if request:
                return request.build_absolute_uri(obj.pdf_file.url)
            return obj.pdf_file.url
        return None
    
    
# =========================================================
# SAVED PAYMENT SERIALIZERS
# =========================================================

class SavedPaymentMethodSerializer(serializers.ModelSerializer):

    class Meta:
        model = SavedPaymentMethod

        fields = [
            'id',
            'payment_type',
            'title',
            'subtitle',
            'provider',
            'token_reference',
            'is_default',
            'created_at',
        ]

        read_only_fields = [
            'id',
            'created_at',
        ]

    def create(self, validated_data):

        user = self.context['request'].user

        if validated_data.get('is_default', False):

            SavedPaymentMethod.objects.filter(
                user=user,
                is_default=True
            ).update(is_default=False)

        return SavedPaymentMethod.objects.create(
            user=user,
            **validated_data
        )

    def update(self, instance, validated_data):

        if validated_data.get('is_default', False):

            SavedPaymentMethod.objects.filter(
                user=instance.user,
                is_default=True
            ).exclude(id=instance.id).update(is_default=False)

        return super().update(instance, validated_data)