"use client";

import { LoadingButton } from "@/components/loading-button";
import { Button } from "@/components/ui/button";
import { Checkbox } from "@/components/ui/checkbox";
import {
  Dialog,
  DialogContent,
  DialogFooter,
  DialogHeader,
  DialogTitle,
} from "@/components/ui/dialog";
import { Input } from "@/components/ui/input";
import { Label } from "@/components/ui/label";
import {
  Select,
  SelectContent,
  SelectItem,
  SelectTrigger,
  SelectValue,
} from "@/components/ui/select";
import {
  Tooltip,
  TooltipContent,
  TooltipTrigger,
} from "@/components/ui/tooltip";
import { VersionSelector } from "@/components/version-selector";
import { useBrowserDownload } from "@/hooks/use-browser-download";
import type { BrowserProfile, ProxySettings } from "@/types";
import { invoke } from "@tauri-apps/api/core";
import { useEffect, useState } from "react";
import { toast } from "sonner";

type BrowserTypeString =
  | "mullvad-browser"
  | "firefox"
  | "firefox-developer"
  | "chromium"
  | "brave"
  | "zen"
  | "tor-browser";

interface CreateProfileDialogProps {
  isOpen: boolean;
  onClose: () => void;
  onCreateProfile: (profileData: {
    name: string;
    browserStr: BrowserTypeString;
    version: string;
    proxy?: ProxySettings;
  }) => Promise<void>;
}

export function CreateProfileDialog({
  isOpen,
  onClose,
  onCreateProfile,
}: CreateProfileDialogProps) {
  const [profileName, setProfileName] = useState("");
  const [selectedBrowser, setSelectedBrowser] =
    useState<BrowserTypeString | null>("mullvad-browser");
  const [selectedVersion, setSelectedVersion] = useState<string | null>(null);
  const [supportedBrowsers, setSupportedBrowsers] = useState<
    BrowserTypeString[]
  >([]);
  const [isCreating, setIsCreating] = useState(false);
  const [existingProfiles, setExistingProfiles] = useState<BrowserProfile[]>(
    [],
  );

  // Proxy settings
  const [proxyEnabled, setProxyEnabled] = useState(false);
  const [proxyType, setProxyType] = useState("http");
  const [proxyHost, setProxyHost] = useState("");
  const [proxyPort, setProxyPort] = useState(8080);

  const {
    availableVersions,
    downloadedVersions,
    isDownloading,
    loadVersions,
    loadDownloadedVersions,
    downloadBrowser,
    isVersionDownloaded,
  } = useBrowserDownload();

  useEffect(() => {
    if (isOpen) {
      void loadSupportedBrowsers();
      void loadExistingProfiles();
    }
  }, [isOpen]);

  useEffect(() => {
    if (isOpen && selectedBrowser) {
      // Reset selected version when browser changes
      setSelectedVersion(null);
      void loadVersions(selectedBrowser);
      void loadDownloadedVersions(selectedBrowser);
    }
  }, [isOpen, selectedBrowser, loadVersions, loadDownloadedVersions]);

  // Set default version when versions are loaded and no version is selected
  useEffect(() => {
    if (availableVersions.length > 0 && selectedBrowser) {
      // Always reset version when browser changes or versions are loaded
      // Find the latest stable version (not alpha/beta)
      const stableVersions = availableVersions.filter((v) => !v.is_alpha);

      if (stableVersions.length > 0) {
        // Select the first stable version (they're already sorted newest first)
        setSelectedVersion(stableVersions[0].tag_name);
      } else if (availableVersions.length > 0) {
        // If no stable version found, select the first available version
        setSelectedVersion(availableVersions[0].tag_name);
      }
    }
  }, [availableVersions, selectedBrowser]);

  const loadSupportedBrowsers = async () => {
    try {
      const browsers = await invoke<BrowserTypeString[]>(
        "get_supported_browsers",
      );
      setSupportedBrowsers(browsers);
      if (browsers.includes("mullvad-browser")) {
        setSelectedBrowser("mullvad-browser");
      } else if (browsers.length > 0) {
        setSelectedBrowser(browsers[0]);
      }
    } catch (error) {
      console.error("Failed to load supported browsers:", error);
    }
  };

  const loadExistingProfiles = async () => {
    try {
      const profiles = await invoke<BrowserProfile[]>("list_browser_profiles");
      setExistingProfiles(profiles);
    } catch (error) {
      console.error("Failed to load existing profiles:", error);
    }
  };

  const handleDownload = async () => {
    if (!selectedBrowser || !selectedVersion) return;
    await downloadBrowser(selectedBrowser, selectedVersion);
  };

  const validateProfileName = (name: string): string | null => {
    const trimmedName = name.trim();

    if (!trimmedName) {
      return "Profile name cannot be empty";
    }

    // Check for duplicate names (case insensitive)
    const isDuplicate = existingProfiles.some(
      (profile) => profile.name.toLowerCase() === trimmedName.toLowerCase(),
    );

    if (isDuplicate) {
      return "A profile with this name already exists";
    }

    return null;
  };

  // Helper to determine if proxy should be disabled for the selected browser
  const isProxyDisabled = selectedBrowser === "tor-browser";

  // Update proxy enabled state when browser changes to tor-browser
  useEffect(() => {
    if (selectedBrowser === "tor-browser" && proxyEnabled) {
      setProxyEnabled(false);
    }
  }, [selectedBrowser, proxyEnabled]);

  const handleCreate = async () => {
    if (!profileName.trim() || !selectedBrowser || !selectedVersion) return;

    // Validate profile name
    const nameError = validateProfileName(profileName);
    if (nameError) {
      toast.error(nameError);
      return;
    }

    setIsCreating(true);
    try {
      const proxy =
        proxyEnabled && !isProxyDisabled
          ? {
              enabled: true,
              proxy_type: proxyType,
              host: proxyHost,
              port: proxyPort,
            }
          : undefined;

      await onCreateProfile({
        name: profileName.trim(),
        browserStr: selectedBrowser,
        version: selectedVersion,
        proxy,
      });

      // Reset form
      setProfileName("");
      setSelectedVersion(null);
      setProxyEnabled(false);
      setProxyHost("");
      setProxyPort(8080);
      onClose();
    } catch (error) {
      console.error("Failed to create profile:", error);
    } finally {
      setIsCreating(false);
    }
  };

  const nameError = profileName.trim()
    ? validateProfileName(profileName)
    : null;
  const canCreate =
    profileName.trim() &&
    selectedBrowser &&
    selectedVersion &&
    isVersionDownloaded(selectedVersion) &&
    (!proxyEnabled || isProxyDisabled || (proxyHost && proxyPort)) &&
    !nameError;

  return (
    <Dialog open={isOpen} onOpenChange={onClose}>
      <DialogContent className="max-w-md">
        <DialogHeader>
          <DialogTitle>Create New Profile</DialogTitle>
        </DialogHeader>

        <div className="grid gap-4 py-4">
          {/* Profile Name */}
          <div className="grid gap-2">
            <Label htmlFor="profile-name">Profile Name</Label>
            <Input
              id="profile-name"
              value={profileName}
              onChange={(e) => {
                setProfileName(e.target.value);
              }}
              placeholder="Enter profile name"
              className={nameError ? "border-red-500" : ""}
            />
            {nameError && <p className="text-sm text-red-600">{nameError}</p>}
          </div>

          {/* Browser Selection */}
          <div className="grid gap-2">
            <Label>Browser</Label>
            <Select
              value={selectedBrowser ?? undefined}
              onValueChange={(value) => {
                setSelectedBrowser(value as BrowserTypeString);
              }}
            >
              <SelectTrigger>
                <SelectValue placeholder="Select browser" />
              </SelectTrigger>
              <SelectContent>
                {supportedBrowsers.map((browser) => (
                  <SelectItem key={browser} value={browser}>
                    {browser
                      .split("-")
                      .map(
                        (word) => word.charAt(0).toUpperCase() + word.slice(1),
                      )
                      .join(" ")}
                  </SelectItem>
                ))}
              </SelectContent>
            </Select>
          </div>

          {/* Version Selection */}
          <div className="grid gap-2">
            <Label>Version</Label>
            <VersionSelector
              selectedVersion={selectedVersion}
              onVersionSelect={setSelectedVersion}
              availableVersions={availableVersions}
              downloadedVersions={downloadedVersions}
              isDownloading={isDownloading}
              onDownload={() => {
                void handleDownload();
              }}
              placeholder="Select version..."
            />
          </div>

          {/* Proxy Settings */}
          <div className="grid gap-4 pt-4 border-t">
            <div className="flex items-center space-x-2">
              {isProxyDisabled ? (
                <Tooltip>
                  <TooltipTrigger asChild>
                    <div className="flex items-center space-x-2 opacity-50">
                      <Checkbox
                        id="proxy-enabled"
                        checked={false}
                        disabled={true}
                      />
                      <Label htmlFor="proxy-enabled" className="text-gray-500">
                        Enable Proxy
                      </Label>
                    </div>
                  </TooltipTrigger>
                  <TooltipContent>
                    <p>
                      Tor Browser has its own built-in proxy system and
                      doesn&apos;t support additional proxy configuration
                    </p>
                  </TooltipContent>
                </Tooltip>
              ) : (
                <>
                  <Checkbox
                    id="proxy-enabled"
                    checked={proxyEnabled}
                    onCheckedChange={(checked) => {
                      setProxyEnabled(checked as boolean);
                    }}
                  />
                  <Label htmlFor="proxy-enabled">Enable Proxy</Label>
                </>
              )}
            </div>

            {proxyEnabled && !isProxyDisabled && (
              <>
                <div className="grid gap-2">
                  <Label>Proxy Type</Label>
                  <Select value={proxyType} onValueChange={setProxyType}>
                    <SelectTrigger>
                      <SelectValue />
                    </SelectTrigger>
                    <SelectContent>
                      {["http", "https", "socks4", "socks5"].map((type) => (
                        <SelectItem key={type} value={type}>
                          {type.toUpperCase()}
                        </SelectItem>
                      ))}
                    </SelectContent>
                  </Select>
                </div>

                <div className="grid gap-2">
                  <Label htmlFor="proxy-host">Host</Label>
                  <Input
                    id="proxy-host"
                    value={proxyHost}
                    onChange={(e) => {
                      setProxyHost(e.target.value);
                    }}
                    placeholder="e.g. 127.0.0.1"
                  />
                </div>

                <div className="grid gap-2">
                  <Label htmlFor="proxy-port">Port</Label>
                  <Input
                    id="proxy-port"
                    type="number"
                    value={proxyPort}
                    onChange={(e) => {
                      setProxyPort(Number.parseInt(e.target.value, 10) || 0);
                    }}
                    placeholder="e.g. 8080"
                    min="1"
                    max="65535"
                  />
                </div>
              </>
            )}
          </div>
        </div>

        <DialogFooter>
          <Button variant="outline" onClick={onClose}>
            Cancel
          </Button>
          <LoadingButton
            isLoading={isCreating}
            onClick={() => void handleCreate()}
            disabled={!canCreate}
          >
            Create Profile
          </LoadingButton>
        </DialogFooter>
      </DialogContent>
    </Dialog>
  );
}
