'use client';

import Image from 'next/image';
import { useState, useEffect, useCallback } from 'react';
import {
  ShieldCheck,
  ShieldOff,
  Loader2,
  AlertCircle,
  KeyRound,
  Smartphone,
  Copy,
  Check,
} from 'lucide-react';
import { Card, CardContent, CardHeader, CardTitle, CardDescription } from '@/components/ui/card';
import { Button } from '@/components/ui/button';
import { Input } from '@/components/ui/input';
import { Label } from '@/components/ui/label';

interface MfaStatus {
  mfaEnabled: boolean;
  methods: string[];
  recoveryCodesRemaining: number;
}

interface TotpSetupData {
  otpauthUri: string;
  qrDataUrl: string;
  recoveryCodes: string[];
}

interface LinkedProvider {
  provider: string;
  email: string;
  linkedAt?: string;
}

function getToken(): string | null {
  return typeof window !== 'undefined' ? localStorage.getItem('admin_access_token') : null;
}

function authHeaders(): Record<string, string> {
  const t = getToken();
  return t ? { Authorization: `Bearer ${t}` } : {};
}

function formatProviderName(provider: string): string {
  return provider
    .split(/[-_\s]+/)
    .filter(Boolean)
    .map(part => part.charAt(0).toUpperCase() + part.slice(1))
    .join(' ');
}

export default function SecuritySettingsPage() {
  const [status, setStatus] = useState<MfaStatus | null>(null);
  const [loading, setLoading] = useState(true);
  const [error, setError] = useState('');

  // TOTP setup flow
  const [setupData, setSetupData] = useState<TotpSetupData | null>(null);
  const [verifyCode, setVerifyCode] = useState('');
  const [setupLoading, setSetupLoading] = useState(false);
  const [copied, setCopied] = useState(false);
  const [providers, setProviders] = useState<LinkedProvider[]>([]);

  const fetchStatus = useCallback(async () => {
    try {
      const res = await fetch('/api/auth/mfa/status', { headers: authHeaders() });
      if (res.ok) {
        setStatus(await res.json());
      }
    } catch {
      setError('Failed to load MFA status');
    } finally {
      setLoading(false);
    }
  }, []);

  useEffect(() => {
    fetchStatus();
  }, [fetchStatus]);

  useEffect(() => {
    let cancelled = false;
    async function fetchProviders() {
      try {
        const res = await fetch('/api/auth/providers', { headers: authHeaders() });
        if (!res.ok) return;
        const data = (await res.json()) as LinkedProvider[];
        if (!cancelled) setProviders(Array.isArray(data) ? data : []);
      } catch {
        // Provider linking is optional; keep MFA settings usable if unavailable.
      }
    }
    fetchProviders();
    return () => {
      cancelled = true;
    };
  }, []);

  const handleUnlinkProvider = async (provider: string) => {
    setError('');
    try {
      const res = await fetch(`/api/auth/providers/${provider}`, {
        method: 'DELETE',
        headers: authHeaders(),
      });
      if (!res.ok) {
        const data = await res.json().catch(() => ({}));
        setError(data.error || 'Failed to unlink provider');
        return;
      }
      setProviders(prev => prev.filter(p => p.provider !== provider));
    } catch {
      setError('Service unavailable');
    }
  };

  const handleSetupTotp = async () => {
    setSetupLoading(true);
    setError('');
    try {
      const res = await fetch('/api/auth/mfa/totp/setup', {
        method: 'POST',
        headers: { ...authHeaders(), 'Content-Type': 'application/json' },
      });
      const data = await res.json();
      if (!res.ok) {
        setError(data.error || 'TOTP setup failed');
        return;
      }
      setSetupData(data);
    } catch {
      setError('Service unavailable');
    } finally {
      setSetupLoading(false);
    }
  };

  const handleVerifySetup = async () => {
    setSetupLoading(true);
    setError('');
    try {
      const res = await fetch('/api/auth/mfa/totp/verify-setup', {
        method: 'POST',
        headers: { ...authHeaders(), 'Content-Type': 'application/json' },
        body: JSON.stringify({ code: verifyCode }),
      });
      const data = await res.json();
      if (!res.ok) {
        setError(data.error || 'Verification failed');
        return;
      }
      setSetupData(null);
      setVerifyCode('');
      await fetchStatus();
    } catch {
      setError('Service unavailable');
    } finally {
      setSetupLoading(false);
    }
  };

  const handleDisableMfa = async () => {
    if (!confirm('Are you sure you want to disable two-factor authentication?')) return;
    setSetupLoading(true);
    setError('');
    try {
      const res = await fetch('/api/auth/mfa/disable', {
        method: 'DELETE',
        headers: authHeaders(),
      });
      if (!res.ok) {
        const data = await res.json();
        setError(data.error || 'Failed to disable MFA');
        return;
      }
      await fetchStatus();
    } catch {
      setError('Service unavailable');
    } finally {
      setSetupLoading(false);
    }
  };

  const copyRecoveryCodes = () => {
    if (setupData?.recoveryCodes) {
      navigator.clipboard.writeText(setupData.recoveryCodes.join('\n'));
      setCopied(true);
      setTimeout(() => setCopied(false), 2000);
    }
  };

  if (loading) {
    return (
      <div className="flex items-center justify-center py-12">
        <Loader2 className="h-8 w-8 animate-spin text-muted-foreground" />
      </div>
    );
  }

  return (
    <div className="space-y-6">
      <div>
        <h1 className="text-2xl font-bold tracking-tight">Security Settings</h1>
        <p className="text-muted-foreground">
          Manage two-factor authentication and account security
        </p>
      </div>

      {error && (
        <div className="flex items-center gap-2 rounded-md bg-destructive/10 p-3 text-sm text-destructive">
          <AlertCircle className="h-4 w-4 shrink-0" />
          {error}
        </div>
      )}

      {/* MFA Status Card */}
      <Card>
        <CardHeader>
          <div className="flex items-center gap-3">
            {status?.mfaEnabled ? (
              <ShieldCheck className="h-6 w-6 text-green-600" />
            ) : (
              <ShieldOff className="h-6 w-6 text-amber-500" />
            )}
            <div>
              <CardTitle>Two-Factor Authentication</CardTitle>
              <CardDescription>
                {status?.mfaEnabled
                  ? `Enabled — ${status.methods.join(', ')} · ${status.recoveryCodesRemaining} recovery codes remaining`
                  : 'Not enabled — add an extra layer of security to your account'}
              </CardDescription>
            </div>
          </div>
        </CardHeader>
        <CardContent>
          {!status?.mfaEnabled && !setupData && (
            <Button onClick={handleSetupTotp} disabled={setupLoading}>
              {setupLoading && <Loader2 className="mr-2 h-4 w-4 animate-spin" />}
              <KeyRound className="mr-2 h-4 w-4" />
              Set up authenticator app
            </Button>
          )}

          {status?.mfaEnabled && (
            <Button variant="destructive" onClick={handleDisableMfa} disabled={setupLoading}>
              {setupLoading && <Loader2 className="mr-2 h-4 w-4 animate-spin" />}
              Disable two-factor authentication
            </Button>
          )}
        </CardContent>
      </Card>

      {/* TOTP Setup Flow */}
      {setupData && (
        <Card>
          <CardHeader>
            <CardTitle className="flex items-center gap-2">
              <Smartphone className="h-5 w-5" />
              Set up authenticator
            </CardTitle>
            <CardDescription>
              Scan this QR code with your authenticator app (Google Authenticator, Authy, 1Password,
              etc.)
            </CardDescription>
          </CardHeader>
          <CardContent className="space-y-6">
            {/* QR Code */}
            <div className="flex justify-center">
              {setupData.qrDataUrl ? (
                <Image
                  src={setupData.qrDataUrl}
                  alt="TOTP QR Code"
                  width={192}
                  height={192}
                  unoptimized
                  className="h-48 w-48 rounded-lg border"
                />
              ) : (
                <div className="flex h-48 w-48 items-center justify-center rounded-lg border bg-muted text-xs text-muted-foreground">
                  QR code unavailable
                </div>
              )}
            </div>

            {/* Manual entry URI */}
            <div className="space-y-1">
              <Label className="text-xs text-muted-foreground">Manual entry key</Label>
              <code className="block break-all rounded bg-muted p-2 text-xs">
                {setupData.otpauthUri}
              </code>
            </div>

            {/* Verify code */}
            <div className="space-y-2">
              <Label htmlFor="verify-code">Enter the 6-digit code from your app</Label>
              <div className="flex gap-2">
                <Input
                  id="verify-code"
                  type="text"
                  inputMode="numeric"
                  placeholder="000000"
                  value={verifyCode}
                  onChange={e => setVerifyCode(e.target.value)}
                  maxLength={6}
                  className="max-w-[160px] text-center font-mono text-lg tracking-widest"
                />
                <Button
                  onClick={handleVerifySetup}
                  disabled={setupLoading || verifyCode.length < 6}
                >
                  {setupLoading && <Loader2 className="mr-2 h-4 w-4 animate-spin" />}
                  Verify & Enable
                </Button>
              </div>
            </div>

            {/* Recovery codes */}
            {setupData.recoveryCodes.length > 0 && (
              <div className="space-y-2">
                <div className="flex items-center justify-between">
                  <Label className="text-sm font-medium">Recovery Codes</Label>
                  <Button variant="ghost" size="sm" onClick={copyRecoveryCodes}>
                    {copied ? (
                      <Check className="mr-1 h-3 w-3" />
                    ) : (
                      <Copy className="mr-1 h-3 w-3" />
                    )}
                    {copied ? 'Copied' : 'Copy all'}
                  </Button>
                </div>
                <p className="text-xs text-muted-foreground">
                  Save these codes in a safe place. Each code can only be used once.
                </p>
                <div className="grid grid-cols-2 gap-1 rounded-lg border bg-muted p-3">
                  {setupData.recoveryCodes.map((code, i) => (
                    <code key={i} className="text-xs font-mono">
                      {code}
                    </code>
                  ))}
                </div>
              </div>
            )}

            <Button
              variant="ghost"
              onClick={() => {
                setSetupData(null);
                setVerifyCode('');
              }}
            >
              Cancel
            </Button>
          </CardContent>
        </Card>
      )}

      <Card>
        <CardHeader>
          <CardTitle>Linked sign-in providers</CardTitle>
          <CardDescription>Connect OAuth providers that can be used to sign in.</CardDescription>
        </CardHeader>
        <CardContent className="space-y-4">
          {providers.length > 0 ? (
            <div className="space-y-3">
              {providers.map(provider => (
                <div
                  key={provider.provider}
                  className="flex items-center justify-between rounded-lg border p-3"
                >
                  <div>
                    <div className="font-medium">{formatProviderName(provider.provider)}</div>
                    <div className="text-sm text-muted-foreground">{provider.email}</div>
                  </div>
                  <Button
                    variant="outline"
                    size="sm"
                    onClick={() => handleUnlinkProvider(provider.provider)}
                  >
                    Unlink
                  </Button>
                </div>
              ))}
            </div>
          ) : (
            <div className="flex items-center justify-between rounded-lg border p-3">
              <div>
                <div className="font-medium">No linked providers</div>
                <div className="text-sm text-muted-foreground">
                  Link a provider such as Google to enable another sign-in method.
                </div>
              </div>
              <Button variant="outline" size="sm">
                Link provider
              </Button>
            </div>
          )}
        </CardContent>
      </Card>
    </div>
  );
}
