"use client";

import { useEffect, useRef, useState } from "react";
import { useRouter } from "next/navigation";

import {
  consumeSubscriptionExitUrl,
  consumeSubscriptionExplicitExitUrl,
} from "@/lib/navigation/subscription_exit";
import {
  clearPendingPaymentOrder,
  getPendingPaymentOrderForType,
} from "@/lib/payment/pending_payment_order";
import {
  usePaymentDispatch,
  usePaymentState,
} from "@/stores/payment/payment-context";
import { useUserDispatch } from "@/stores/user/user-context";

import type { SubscriptionType } from "./subscription-screen.helpers";

export interface UseSubscriptionPaymentFlowInput {
  subscriptionType: SubscriptionType;
  shouldResumePendingOrder: boolean;
  returnTo: "chat" | null;
}

export function useSubscriptionPaymentFlow({
  subscriptionType,
  shouldResumePendingOrder,
  returnTo,
}: UseSubscriptionPaymentFlowInput) {
  const router = useRouter();
  const userDispatch = useUserDispatch();
  const payment = usePaymentState();
  const paymentDispatch = usePaymentDispatch();
  const refreshedPaidOrderRef = useRef<string | null>(null);
  const resumedPendingOrderRef = useRef<string | null>(null);
  const successDialogShownOrderRef = useRef<string | null>(null);
  const [showPaymentSuccessDialog, setShowPaymentSuccessDialog] =
    useState(false);

  useEffect(() => {
    if (payment.status === "idle") {
      paymentDispatch({ type: "PaymentInit" });
    }
  }, [payment.status, paymentDispatch]);

  useEffect(() => {
    if (!payment.isPaid || !payment.currentOrderId) return;
    if (refreshedPaidOrderRef.current === payment.currentOrderId) return;
    refreshedPaidOrderRef.current = payment.currentOrderId;
    userDispatch({ type: "UserFetch" });
  }, [payment.currentOrderId, payment.isPaid, userDispatch]);

  useEffect(() => {
    if (!payment.isPaid || !payment.currentOrderId) return;
    if (successDialogShownOrderRef.current === payment.currentOrderId) return;

    successDialogShownOrderRef.current = payment.currentOrderId;
    setShowPaymentSuccessDialog(true);
  }, [payment.currentOrderId, payment.isPaid]);

  useEffect(() => {
    const canInspectPendingOrder =
      payment.status === "ready" ||
      (!shouldResumePendingOrder &&
        (payment.isPollingOrder ||
          payment.isPaid ||
          payment.status === "failed"));
    if (!canInspectPendingOrder) return;

    let cancelled = false;

    const handlePendingOrder = async () => {
      const result = await getPendingPaymentOrderForType(subscriptionType);
      if (cancelled || !result.success || result.data === null) return;

      if (!shouldResumePendingOrder) {
        await clearPendingPaymentOrder();
        if (
          payment.currentOrderId === result.data.orderId &&
          (payment.isPollingOrder ||
            payment.isPaid ||
            payment.status === "failed")
        ) {
          paymentDispatch({ type: "PaymentReset" });
        }
        return;
      }

      if (payment.currentOrderId === result.data.orderId) return;
      if (resumedPendingOrderRef.current === result.data.orderId) return;

      resumedPendingOrderRef.current = result.data.orderId;
      paymentDispatch({
        type: "PaymentReturned",
        orderId: result.data.orderId,
        createdAt: result.data.createdAt,
      });
    };

    void handlePendingOrder();
    return () => {
      cancelled = true;
    };
  }, [
    payment.currentOrderId,
    payment.isPaid,
    payment.isPollingOrder,
    payment.status,
    paymentDispatch,
    shouldResumePendingOrder,
    subscriptionType,
  ]);

  useEffect(() => {
    if (!payment.currentOrderId) return;
    if (!payment.isPaid && payment.status !== "failed") return;

    void clearPendingPaymentOrder();
  }, [payment.currentOrderId, payment.isPaid, payment.status]);

  const handleBackClick = () => {
    router.replace(consumeSubscriptionExitUrl(returnTo));
  };

  const handlePaymentSuccessClose = () => {
    setShowPaymentSuccessDialog(false);
    paymentDispatch({ type: "PaymentReset" });
    const pendingExitUrl = consumeSubscriptionExplicitExitUrl();
    if (pendingExitUrl) {
      router.replace(pendingExitUrl);
      return;
    }
    if (returnTo === "chat") {
      router.replace(consumeSubscriptionExitUrl(returnTo));
    }
  };

  return {
    payment,
    paymentDispatch,
    showPaymentSuccessDialog,
    handleBackClick,
    handlePaymentSuccessClose,
  };
}
