from rest_framework.views import APIView
from rest_framework.response import Response
from rest_framework import status
from rest_framework.pagination import PageNumberPagination
from rest_framework.exceptions import ValidationError, NotFound
from drf_yasg.utils import swagger_auto_schema
from django.shortcuts import get_object_or_404
from django.template.loader import render_to_string
from django.core.mail import send_mail
from django.conf import settings
from rest_framework.permissions import IsAuthenticated

from api.property_api.agent.models.agent import Agent
from api.property_api.agent.serializer.agent_serializer import AgentSerializer, PropertyWithAgentSerializer
from api.property_api.agent.serializer.agent_profile_modification_serializer import AgentPartialUpdateSerializer


from rest_framework.permissions import IsAuthenticated
from rest_framework.parsers import MultiPartParser, FormParser

from api.property_api.property.models.property import Property

class AgentPublicListAPIView(APIView):
    """Public endpoint to list all agents for website users"""
    
    def get(self, request):
        agents = Agent.objects.filter(is_active=True)
        country = request.query_params.get('country')
        if country:
            agents = agents.filter(country__id=country)
        paginator = PageNumberPagination()
        result_page = paginator.paginate_queryset(agents, request)
        serializer = AgentSerializer(result_page, many=True,context={"request": request})
        return paginator.get_paginated_response(serializer.data)


class AgentListCreateAPIView(APIView):
    permission_classes = [IsAuthenticated]
    parser_classes = [MultiPartParser, FormParser]
    
    @swagger_auto_schema(request_body=AgentSerializer,consumes=["multipart/form-data"])
    def post(self, request):
        serializer = AgentSerializer(data=request.data,context={"request": request})
        serializer.is_valid(raise_exception=True)

        agent = serializer.save()
        user = agent.agent_user

        # 🔐 Generate OTP
        token = user.create_verification_token()

        subject = "Verify Your Panjabiz Agent Account"

        text_message = f"""
        Hello {agent.name},

        Your verification code is:

        {token}

        This code will expire in 5 minutes.

        If you did not request this, ignore this email.

        — discovercafe Team
        """

        html_message = render_to_string(
            "emails/verification_email.html",
            {
                "name": agent.name,
                "token": token
            }
        )

        send_mail(
            subject=subject,
            message=text_message,
            from_email=settings.DEFAULT_FROM_EMAIL,
            recipient_list=[user.email],
            html_message=html_message,
            fail_silently=False
        )

        return Response({
            "message": "Agent registered successfully. Please verify your email."
        }, status=status.HTTP_201_CREATED)

    def get(self, request):
        search = request.query_params.get('search')
        country = request.query_params.get('country')
        user = request.user

        agents = Agent.objects.all()

        if country:
            agents = agents.filter(country__id=country)

        if search:
            agents = agents.filter(name__icontains=search)

        if user.role == 'client' or user.role == 'agent':
            agents = agents.filter(created_by=user)

        paginator = PageNumberPagination()
        result_page = paginator.paginate_queryset(agents, request)
        serializer = AgentSerializer(
            result_page,
            many=True,
            context={"request": request}
        )
        return paginator.get_paginated_response(serializer.data)



class AgentDetailAPIView(APIView):
    parser_classes = [MultiPartParser, FormParser]

    @swagger_auto_schema(
    request_body=AgentPartialUpdateSerializer,
    operation_description="Partially update agent",
    consumes=["multipart/form-data"]
)
    def patch(self, request, pk):
        agent = get_object_or_404(Agent, pk=pk)
        serializer = AgentPartialUpdateSerializer(agent, data=request.data,partial=True,context={'request': request})
        serializer.is_valid(raise_exception=True)
        serializer.save()
        return Response({"success": "Agent updated successfully"}, status=status.HTTP_200_OK)

    def get(self, request, pk):
        agent = get_object_or_404(Agent, pk=pk)
        serializer = AgentSerializer(agent,context={'request': request})
        return Response(serializer.data)

    def delete(self, request, pk):
        agent = get_object_or_404(Agent, pk=pk)
        
        user = agent.agent_user
        
        agent.delete()
        
        if user:
            user.delete()
        
        return Response({"success": "Agent and associated user deleted successfully"}, status=status.HTTP_200_OK)
    
class AgentDropdownListAPIView(APIView):
    """Public endpoint to list all agents for website users"""

    def get(self, request):
        agents = Agent.objects.filter(is_active=True)

        serializer = AgentSerializer(
            agents,
            many=True,
            context={"request": request}
        )

        return Response(
            {
                "count": agents.count(),
                "results": serializer.data
            },
            status=status.HTTP_200_OK
        )
    
class AgentDropdownUserBasedListAPIView(APIView):
        def get(self, request):
            search = request.query_params.get('search')
            user = request.user

            agents = Agent.objects.all()

            if search:
                agents = agents.filter(name__icontains=search)

            if user.role == 'client' or user.role == 'agent':
                agents = agents.filter(created_by=user)

            # paginator = PageNumberPagination()
            # result_page = paginator.paginate_queryset(agents, request)
            serializer = AgentSerializer(
                agents,
                many=True,
                context={"request": request}
            )
            return Response(serializer.data, status=status.HTTP_200_OK)
        



class PropertyWithAgentDetailAPIView(APIView):
    """
    API endpoint to get property details by ID with agent information
    """
    permission_classes = [IsAuthenticated]
    @swagger_auto_schema(responses={200: PropertyWithAgentSerializer()})
    def get(self, request, pk):
        """
        Retrieve property details with agent information by property ID
        
        Args:
            pk (int): Property ID
            
        Returns:
            Property object with complete agent details
        """
        try:
            property_obj = get_object_or_404(
                Property.objects.select_related(
                    'country', 'city', 'state', 'agent', 'category_type', 'created_by'
                ).prefetch_related('property', 'media'),
                pk=pk,
                is_active=True
            )
            
            serializer = PropertyWithAgentSerializer(property_obj, context={'request': request})
            return Response(
                {
                    'success': True,
                    'data': serializer.data
                },
                status=status.HTTP_200_OK
            )
        except Exception as e:
            return Response(
                {
                    'success': False,
                    'message': str(e)
                },
                status=status.HTTP_400_BAD_REQUEST
            )