from rest_framework import viewsets, mixins, status
from rest_framework.decorators import action
from rest_framework.response import Response
from django.template import loader

from drf_spectacular.utils import extend_schema, extend_schema_view, OpenApiResponse, OpenApiParameter, OpenApiTypes

from configuration.models import SiteConfiguration

from .models import ZasilkovnaShipment, ZasilkovnaPacket
from .serializers import (
        ZasilkovnaShipmentSerializer,
        ZasilkovnaPacketSerializer,
        TrackingURLSerializer,
)

# -- SHIPMENT --

@extend_schema_view(
    list=extend_schema(
        tags=["zasilkovna"],
        summary="Hromadný shipment",
        description="Returns a paginated list of Packeta (Zásilkovna) shipments.",
        responses=ZasilkovnaShipmentSerializer,
    ),
    retrieve=extend_schema(
        tags=["zasilkovna"],
        summary="Detail hromadné zásilky",
        description="Returns detail for a single shipment.",
        responses=ZasilkovnaShipmentSerializer,
    ),
)
class ZasilkovnaShipmentViewSet(mixins.ListModelMixin, mixins.RetrieveModelMixin, viewsets.GenericViewSet,):
    queryset = ZasilkovnaShipment.objects.all().order_by("-created_at")
    serializer_class = ZasilkovnaShipmentSerializer





# -- PACKET --

@extend_schema_view(
    retrieve=extend_schema(
        tags=["zasilkovna"],
        summary="Packet",
        description="#TODO: Popis endpointu",
        responses={200: ZasilkovnaPacketSerializer},
    )
)
class ZasilkovnaPacketViewSet(mixins.RetrieveModelMixin, viewsets.GenericViewSet):
    queryset = ZasilkovnaPacket.objects.all()
    serializer_class = ZasilkovnaPacketSerializer

    @extend_schema(
        tags=["zasilkovna"],
        summary="Get public tracking URL",
        description="Returns the public Zásilkovna tracking URL derived from the packet's barcode.",
        responses=OpenApiResponse(response=TrackingURLSerializer),
        parameters=[
            OpenApiParameter(name="id", location=OpenApiParameter.PATH, description="Packet ID", required=True, type=int),
        ],
        request=None,
    )
    @action(detail=True, methods=["get"], url_path="tracking-url")
    def tracking_url(self, request, pk=None):
        packet: ZasilkovnaPacket = self.get_object()
        data = {
            "barcode": packet.barcode,
            "tracking_url": packet.get_tracking_url(),
        }
        return Response(data)


    #HOTOVO
    @extend_schema(
        tags=["zasilkovna"],
        summary="Order shipping",
        description=(
            "Objedná přepravu přes API Packety,"
            "podle existujicího objektu, kde je od uživatele uložený id od místa poslání."
        ),
        request=None,
        responses=OpenApiResponse(response=ZasilkovnaPacketSerializer),
        parameters=[
            OpenApiParameter(name="id", location=OpenApiParameter.PATH, description="Packet ID", required=True, type=int),
        ],
    )
    @action(detail=True, methods=["patch"], url_path="order-shipping")
    def order_shipping(self, request, pk=None):
        packet: ZasilkovnaPacket = self.get_object()
        packet.order_shipping()
        serializer = self.get_serializer(packet)
        return Response(serializer.data, status=status.HTTP_200_OK)


    #HOTOVO
    @extend_schema(
        tags=["zasilkovna"],
        summary="Cancel packet",
        description=(
            "Cancels the packet through the Packeta API and updates its state to CANCELED. "
            "No request body is required."
        ),
        request=None,
        responses=OpenApiResponse(response=ZasilkovnaPacketSerializer),
        parameters=[
            OpenApiParameter(name="id", location=OpenApiParameter.PATH, description="Packet ID", required=True, type=int),
        ],
    )
    @action(detail=True, methods=["patch"], url_path="cancel")
    def cancel(self, request, pk=None):
        packet: ZasilkovnaPacket = self.get_object()
        packet.cancel_packet()
        serializer = self.get_serializer(packet)
        return Response(serializer.data, status=status.HTTP_200_OK)
    

    #TODO: dodělat/domluvit se
    @extend_schema(
        tags=["zasilkovna"],
        summary="Get widget for user, to select pickup point.",
        description=(
            "Returns HTML widget for user to select pickup point. "
            "No request body is required."
        ),
        request=None,
        responses={200: OpenApiResponse(response=TrackingURLSerializer)},
    )
    @action(detail=True, methods=["get"], url_path="pickup-point-widget")
    def pickup_point_widget(self, request):

        #https://configurator.widget.packeta.com/cs

        widget_html = loader.render_to_string(
            "zasilkovna/pickup_point_widget.html",
            {
                "api_key": SiteConfiguration.get_solo().zasilkovna_widget_api_key,
            }
        )

        return Response({"widget_html": widget_html})