﻿"use client";

import { useState, useEffect } from "react";
import { useRouter } from "next/navigation";
import { useForm } from "react-hook-form";
import { zodResolver } from "@hookform/resolvers/zod";
import { loginSchema, type LoginInput } from "@/lib/validations/auth";
import { Button } from "@/components/ui/button";
import { Input } from "@/components/ui/input";
import { Label } from "@/components/ui/label";
import { useToastEnhanced } from "@/hooks/use-toast-enhanced";
import { Loader2, Mail, Lock, Eye, EyeOff } from "lucide-react";
import { loginAction } from "@/features/auth/actions/auth-api-actions";
import {
  clientRateLimit,
  clearClientRateLimit,
} from "@/core/security/rate-limit";
import {
  generateClientCsrfToken,
  verifyClientCsrfToken,
} from "@/core/security/client-csrf";
import {
  detectUserRole,
  getDashboardRoute,
  getSessionKey,
  roleNeedsCookie,
} from "@/lib/utils/role-detection";
import { storeToken } from "@/core/api/client/axios-client";

export function LoginForm() {
  const [isLoading, setIsLoading] = useState(false);
  const [showPassword, setShowPassword] = useState(false);
  const [csrfToken, setCsrfToken] = useState<string>("");
  const toast = useToastEnhanced();
  const router = useRouter();

  useEffect(() => {
    setCsrfToken(generateClientCsrfToken());
  }, []);

  const {
    register,
    handleSubmit,
    formState: { errors },
  } = useForm<LoginInput>({
    resolver: zodResolver(loginSchema),
  });

  const onSubmit = async (data: LoginInput) => {
    console.log("\n[Login Form] ðŸš€ Form submission started", {
      email: data.email,
      timestamp: new Date().toISOString(),
    });

    console.log("[Login Form] Verifying CSRF token");
    if (!verifyClientCsrfToken(csrfToken)) {
      console.log("[Login Form] âŒ CSRF token validation failed");
      toast.error({
        title: "Security error",
        description: "Please refresh the page and try again",
      });
      return;
    }
    console.log("[Login Form] âœ… CSRF token valid");

    console.log("[Login Form] Checking rate limit");
    const rateCheck = clientRateLimit("login_attempt", 5, 60000);
    if (!rateCheck.allowed) {
      const waitTime = Math.ceil(rateCheck.resetIn / 1000);
      console.log("[Login Form] âŒ Rate limit exceeded", { waitTime });
      toast.error({
        title: "Too many attempts",
        description: `Please wait ${waitTime} seconds before trying again`,
      });
      return;
    }
    console.log("[Login Form] âœ… Rate limit check passed");

    setIsLoading(true);

    try {
      console.log("[Login Form] Calling backend API via loginAction");

      // Call server action which handles backend API authentication
      const result = await loginAction({
        email: data.email,
        password: data.password,
      });

      console.log("[Login Form] API response received", {
        success: result.success,
        hasUser: !!result.user,
        hasToken: !!result.token,
      });

      if (!result.success) {
        console.log("[Login Form] âŒ Login failed:", result.error);
        throw new Error(result.error || "Login failed");
      }

      if (!result.user) {
        console.log("[Login Form] âŒ No user data in response");
        throw new Error("Invalid response from server");
      }

      console.log("[Login Form] âœ… User authenticated via API", {
        email: result.user.email,
        name: result.user.name,
      });

      // Store token in localStorage for client-side axios requests
      if (result.token) {
        console.log(
          "[Login Form] Storing token in localStorage for client-side API calls"
        );
        storeToken(result.token);
      } else {
        console.warn(
          "[Login Form] âš ï¸ No token returned from API to store in localStorage"
        );
      }

      clearClientRateLimit("login_attempt");

      // Detect user role from API response
      const detectedRole = detectUserRole({
        email: result.user.email,
        status: result.user.status,
        name: result.user.name,
      });

      console.log("[Login Form] âœ… Role detected:", detectedRole);

      // Create session data from API response with detected role
      const sessionData = {
        email: result.user.email,
        name: result.user.name,
        role: detectedRole,
        loginTime: new Date().toISOString(),
      };
      console.log("[Login Form] Session data created with role", sessionData);

      // Store session based on role
      const sessionKey = getSessionKey(detectedRole);
      console.log(`[Login Form] Storing ${detectedRole} session`);
      sessionStorage.setItem(sessionKey, JSON.stringify(sessionData));

      // Set cookie if role requires it (admin, agent, hotel)
      if (roleNeedsCookie(detectedRole)) {
        const cookieValue = encodeURIComponent(JSON.stringify(sessionData));
        document.cookie = `${sessionKey}=${cookieValue}; path=/; max-age=86400; SameSite=Strict${window.location.protocol === "https:" ? "; Secure" : ""}`;
        console.log(`[Login Form] ${detectedRole} cookie set`, {
          cookieValue: cookieValue.substring(0, 50) + "...",
        });
      }

      // Dispatch session update event for customer
      if (detectedRole === "customer") {
        window.dispatchEvent(new Event("sessionUpdate"));
      }

      // Get appropriate welcome message
      const welcomeTitle =
        detectedRole === "admin"
          ? "Welcome back, Admin!"
          : `Welcome back, ${result.user.name}!`;

      const welcomeDesc =
        detectedRole === "customer"
          ? "You have successfully logged in."
          : "Redirecting to dashboard...";

      toast.success({
        title: welcomeTitle,
        description: welcomeDesc,
      });

      // Get dashboard route based on role
      const dashboardRoute = getDashboardRoute(detectedRole);
      console.log(`[Login Form] ðŸŽ‰ Redirecting to ${dashboardRoute}`);
      router.push(dashboardRoute);
    } catch (error) {
      console.log("[Login Form] âŒ Login error:", error);
      toast.error({
        title: "Login failed",
        description:
          error instanceof Error
            ? error.message
            : "Please check your credentials",
      });
    } finally {
      console.log("[Login Form] Login process completed\n");
      setIsLoading(false);
    }
  };

  return (
    <form onSubmit={handleSubmit(onSubmit)} className="space-y-4">
      <input type="hidden" name="csrf_token" value={csrfToken} />

      <div className="space-y-2">
        <Label htmlFor="login-email">Email address</Label>
        <div className="relative">
          <Mail
            className="absolute left-3 top-1/2 -translate-y-1/2 h-4 w-4 text-muted-foreground"
            aria-hidden="true"
          />
          <Input
            id="login-email"
            type="email"
            placeholder="your@email.com"
            autoComplete="email"
            disabled={isLoading}
            className="pl-10"
            aria-invalid={errors.email ? "true" : "false"}
            aria-describedby={errors.email ? "login-email-error" : undefined}
            {...register("email")}
          />
        </div>
        {errors.email && (
          <p
            id="login-email-error"
            className="text-sm text-destructive"
            role="alert"
          >
            {errors.email.message}
          </p>
        )}
      </div>

      <div className="space-y-2">
        <Label htmlFor="login-password">Password</Label>
        <div className="relative">
          <Lock
            className="absolute left-3 top-1/2 -translate-y-1/2 h-4 w-4 text-muted-foreground"
            aria-hidden="true"
          />
          <Input
            id="login-password"
            type={showPassword ? "text" : "password"}
            placeholder="Enter your password"
            autoComplete="current-password"
            disabled={isLoading}
            className="pl-10 pr-10"
            aria-invalid={errors.password ? "true" : "false"}
            aria-describedby={
              errors.password ? "login-password-error" : undefined
            }
            {...register("password")}
          />
          <Button
            type="button"
            variant="ghost"
            size="sm"
            className="absolute right-1 top-1/2 -translate-y-1/2 h-8 w-8 p-0"
            onClick={() => setShowPassword(!showPassword)}
            aria-label={showPassword ? "Hide password" : "Show password"}
          >
            {showPassword ? (
              <EyeOff className="h-4 w-4" aria-hidden="true" />
            ) : (
              <Eye className="h-4 w-4" aria-hidden="true" />
            )}
          </Button>
        </div>
        {errors.password && (
          <p
            id="login-password-error"
            className="text-sm text-destructive"
            role="alert"
          >
            {errors.password.message}
          </p>
        )}
      </div>

      <Button
        type="submit"
        className="w-full"
        size="lg"
        disabled={isLoading}
        aria-label="Sign in to your account"
      >
        {isLoading && (
          <Loader2 className="mr-2 h-4 w-4 animate-spin" aria-hidden="true" />
        )}
        {isLoading ? "Signing in..." : "Sign In"}
      </Button>
    </form>
  );
}
