from django.conf import settings
from django.http import HttpResponseNotFound, HttpResponseRedirect, QueryDict
from django.urls import reverse


class RedirectMiddleware:
    def __init__(self, get_response):
        self.get_response = get_response

        self.redirect_ipv4 = settings.IP_REDIRECT_HOST["ipv4"]
        self.redirect_ipv6 = settings.IP_REDIRECT_HOST["ipv6"]
        self.redirect_both = (
            settings.IP_REDIRECT_HOST["both"]
            if self.redirect_ipv4 and self.redirect_ipv6
            else ""
        )

        self.disallowed_paths = set(["/favicon.ico", "/robots.txt"])

    def __call__(self, request):
        host = request.get_host()

        if self.redirect_both and host == self.redirect_both:
            if request.path in self.disallowed_paths:
                return HttpResponseNotFound()

            q = QueryDict(mutable=True)
            q.appendlist("next", self.build_url(request, self.redirect_ipv6))
            return HttpResponseRedirect(
                f"{self.build_url(request, self.redirect_ipv4)}?{q.urlencode()}"
            )

        if (
            self.redirect_ipv4
            and host == self.redirect_ipv4
            and request.path != reverse("remote_ip")
        ):
            if request.path in self.disallowed_paths:
                return HttpResponseNotFound()

            return HttpResponseRedirect(self.build_url(request, self.redirect_ipv4))

        if (
            self.redirect_ipv6
            and host == self.redirect_ipv6
            and request.path != reverse("remote_ip")
        ):
            if request.path in self.disallowed_paths:
                return HttpResponseNotFound()

            return HttpResponseRedirect(self.build_url(request, self.redirect_ipv6))

        return self.get_response(request)

    def build_url(self, request, redirect_host):
        return f"http{'s' if request.is_secure() else ''}://{redirect_host}{reverse('remote_ip')}"
