'use client';
import React, {
  useEffect,
  useMemo,
  useState,
  useTransition,
  type ReactNode
} from 'react';
import { Loader2, MailPlus, UserMinus, Users } from 'lucide-react';
import { toast } from 'sonner';
import clsx from 'clsx';
import { Card, CardContent, CardHeader, CardTitle } from '@/components/ui/card';
import { Badge } from '@/components/ui/badge';
import { Button } from '@/components/ui/button';
import { Input } from '@/components/ui/input';
import {
  Select,
  SelectContent,
  SelectItem,
  SelectTrigger,
  SelectValue
} from '@/components/ui/select';
import { Separator } from '@/components/ui/separator';
import { Skeleton } from '@/components/ui/skeleton';
import { organization as organizationClient } from '@/lib/auth/auth-client';
import { api } from '@/lib/trpc/client';

type OrganizationDashboardResponse = {
  organization: {
    id: string;
    name: string;
    contactName: string | null;
    address: string | null;
    postalCode: string | null;
    city: string | null;
    cvr: string | null;
  };
  role: string;
  members: Array<{
    id: string;
    role: string;
    createdAt: string | null;
    user: {
      id: string;
      name: string | null;
      email: string | null;
      image: string | null;
    };
  }>;
  invitations: Array<{
    id: string;
    email: string;
    role: string;
    status: string;
    expiresAt: string | null;
    invitedBy: string | null;
  }>;
  subscription: {
    id: string;
    plan: string;
    status: string;
    seats: number;
    referenceId: string | null;
    cancelAtPeriodEnd: boolean | null;
    periodStart: string | null;
    periodEnd: string | null;
    trialStart: string | null;
    trialEnd: string | null;
    canceledAt: string | null;
    metadata: Record<string, unknown> | null;
  } | null;
  seatUsage: {
    used: number;
    pending: number;
    capacity: number;
  };
};

const STATUS_LABELS: Record<string, string> = {
  active: 'Aktiv',
  trialing: 'Prøveperiode',
  canceled: 'Afmeldt',
  incomplete: 'Ufuldstændig',
  past_due: 'Forfalden',
  unpaid: 'Ubetalt'
};

function formatPlanName(plan: string | null | undefined) {
  const normalized = (plan || '').toLowerCase();
  switch (normalized) {
    case 'business-monthly':
      return 'Erhverv (Månedligt)';
    case 'business-annual':
      return 'Erhverv (Årligt)';
    case 'plus':
      return 'Plus (Månedligt)';
    case 'plus-annual':
      return 'Plus (Årligt)';
    case 'basis':
      return 'Basis (Månedligt)';
    case 'basis-annual':
      return 'Basis (Årligt)';
    default:
      return plan || 'Ukendt';
  }
}

function formatDate(value: string | null | undefined) {
  if (!value) {
    return 'Ukendt';
  }

  const date = new Date(value);
  if (Number.isNaN(date.getTime())) {
    return 'Ukendt';
  }

  return date.toLocaleDateString('da-DK', {
    year: 'numeric',
    month: 'long',
    day: 'numeric'
  });
}

function ProfileSection({
  title,
  children,
  contentClassName
}: {
  title: string;
  children: ReactNode;
  contentClassName?: string;
}) {
  const contentClasses = contentClassName
    ? clsx('w-full', contentClassName)
    : 'flex w-full flex-col gap-5';

  return (
    <section className='mx-auto w-full max-w-[1362px] grow p-3 md:px-8 md:py-4 xl:border-x'>
      <div className='flex flex-col xl:flex-row'>
        <div className='shrink-0 xl:w-68'>
          <h2 className='mb-4 text-xl leading-none font-bold text-[#CBCBCB] md:text-3xl'>
            {title}
          </h2>
        </div>
        <div className={contentClasses}>{children}</div>
      </div>
      <Separator className='mt-7' />
    </section>
  );
}

export function OrganizationManagement() {
  const [loading, setLoading] = useState(true);
  const [data, setData] = useState<OrganizationDashboardResponse | null>(null);
  const [error, setError] = useState<string | null>(null);
  const [refreshing, startTransition] = useTransition();
  const [seatTarget, setSeatTarget] = useState<number>(1);
  const [seatSubmitting, setSeatSubmitting] = useState(false);
  const [inviteEmail, setInviteEmail] = useState('');
  const [inviteRole, setInviteRole] = useState<'member' | 'admin'>('member');
  const [inviteSubmitting, setInviteSubmitting] = useState(false);
  const [revokingInvitationId, setRevokingInvitationId] = useState<
    string | null
  >(null);
  const [removingMemberId, setRemovingMemberId] = useState<string | null>(null);

  const adjustSeatsMutation = api.payment.subscription.adjustSeats.useMutation(
    {}
  );

  const organizationId = data?.organization.id ?? null;

  const isManager = useMemo(() => {
    const role = data?.role || '';
    return role === 'owner' || role === 'admin';
  }, [data?.role]);

  const seatsRemaining = useMemo(() => {
    if (!data?.subscription) {
      return 0;
    }
    return Math.max(
      0,
      data.subscription.seats - (data.seatUsage.used + data.seatUsage.pending)
    );
  }, [data]);

  const fetchData = async (showLoader = true) => {
    if (showLoader) {
      setLoading(true);
      setError(null);
    }

    try {
      const response = await fetch('/api/organization/dashboard', {
        method: 'GET',
        credentials: 'include',
        cache: 'no-store'
      });

      if (!response.ok) {
        const payload = await response.json().catch(() => ({}));
        throw new Error(payload?.error || 'Kunne ikke hente organisationsdata');
      }

      const payload = (await response.json()) as {
        data: OrganizationDashboardResponse;
      };
      setData(payload.data);
      if (payload.data.subscription?.seats) {
        setSeatTarget(payload.data.subscription.seats);
      } else {
        setSeatTarget(payload.data.seatUsage.capacity);
      }

      if (payload.data.organization?.id) {
        await organizationClient
          .setActive({
            organizationId: payload.data.organization.id
          })
          .catch(() => undefined);
      }
    } catch (err) {
      console.error('[Organization Dashboard] Failed to fetch data', err);
      setError(
        err instanceof Error
          ? err.message
          : 'Kunne ikke hente organisationsdata. Prøv igen senere.'
      );
    } finally {
      if (showLoader) {
        setLoading(false);
      }
    }
  };

  useEffect(() => {
    fetchData(true);
  }, []);

  const refresh = () => {
    startTransition(() => {
      fetchData(false);
    });
  };

  const handleSeatSubmit = async (event: React.FormEvent<HTMLFormElement>) => {
    event.preventDefault();

    if (!data?.subscription || !organizationId) {
      toast.error('Ingen aktiv erhvervsabonnement fundet.');
      return;
    }

    if (seatTarget === data.subscription.seats) {
      toast.message('Antallet af pladser er uændret.');
      return;
    }

    if (seatTarget < data.seatUsage.used) {
      toast.error(
        `Der er allerede ${data.seatUsage.used} medlemmer. Du kan ikke sætte pladser lavere end dette.`
      );
      return;
    }

    try {
      setSeatSubmitting(true);

      const response = await adjustSeatsMutation.mutateAsync({
        organizationId,
        seats: seatTarget,
        successUrl: `${window.location.origin}/profile/organization?checkout=success`,
        cancelUrl: `${window.location.origin}/profile/organization`
      });

      const redirectUrl = response.url;

      if (redirectUrl) {
        window.location.href = redirectUrl;
        return;
      }

      throw new Error('Manglede betalingslink fra Stripe.');
    } catch (err) {
      console.error('[Organization Dashboard] Seat update failed', err);
      toast.error(
        err instanceof Error
          ? err.message
          : 'Kunne ikke opdatere antallet af pladser. Prøv igen.'
      );
    } finally {
      setSeatSubmitting(false);
    }
  };

  const handleInvite = async () => {
    if (!organizationId) {
      toast.error('Ingen organisation valgt.');
      return;
    }
    if (!inviteEmail.trim()) {
      toast.error('Angiv en emailadresse.');
      return;
    }

    if (!data?.subscription) {
      toast.error(
        'Du skal have et aktivt erhvervsabonnement for at invitere medlemmer.'
      );
      return;
    }

    if (data?.subscription && seatsRemaining <= 0) {
      toast.error(
        'Alle pladser er optaget eller reserveret. Opgrader pladser for at invitere flere medlemmer.'
      );
      return;
    }

    try {
      setInviteSubmitting(true);
      const response = await fetch('/api/organization/invitations', {
        method: 'POST',
        headers: { 'Content-Type': 'application/json' },
        body: JSON.stringify({
          organizationId,
          email: inviteEmail.trim(),
          role: inviteRole
        })
      });

      const payload = await response.json().catch(() => ({}));

      if (!response.ok) {
        throw new Error(payload?.error || 'Kunne ikke sende invitation');
      }

      toast.success('Invitation sendt');
      setInviteEmail('');
      refresh();
    } catch (err) {
      console.error('[Organization Dashboard] Invitation failed', err);
      toast.error(
        err instanceof Error
          ? err.message
          : 'Kunne ikke sende invitation. Prøv igen senere.'
      );
    } finally {
      setInviteSubmitting(false);
    }
  };

  const handleRevokeInvitation = async (invitationId: string) => {
    try {
      setRevokingInvitationId(invitationId);
      const result = organizationClient.cancelInvitation(
        {
          invitationId
        },
        {
          throw: true
        }
      );

      await toast.promise(result, {
        loading: 'Tilbagekalder invitation...',
        success: () => {
          refresh();
          return 'Invitation tilbagekaldt';
        },
        error: (error: { error?: { message?: string } }) =>
          error?.error?.message || 'Kunne ikke tilbagekalde invitation'
      });
    } finally {
      setRevokingInvitationId(null);
    }
  };

  const handleRemoveMember = async (
    memberId: string,
    memberName?: string | null
  ) => {
    if (!organizationId) {
      toast.error('Ingen organisation valgt.');
      return;
    }

    try {
      setRemovingMemberId(memberId);
      const result = organizationClient.removeMember(
        {
          memberIdOrEmail: memberId
        },
        {
          throw: true
        }
      );

      await toast.promise(result, {
        loading: 'Fjerner medlem...',
        success: () => {
          refresh();
          return `${memberName || 'Medlem'} er fjernet`;
        },
        error: (error: { error?: { message?: string } }) =>
          error?.error?.message || 'Kunne ikke fjerne medlem'
      });
    } finally {
      setRemovingMemberId(null);
    }
  };

  if (loading) {
    return (
      <>
        <ProfileSection title='organisation'>
          <Card className='w-full rounded-none border-0 bg-neutral-50 font-serif shadow-none'>
            <CardHeader>
              <Skeleton className='h-6 w-48' />
            </CardHeader>
            <CardContent className='space-y-4'>
              <Skeleton className='h-4 w-full' />
              <Skeleton className='h-4 w-full' />
              <Skeleton className='h-4 w-3/4' />
              <Skeleton className='h-4 w-2/3' />
            </CardContent>
          </Card>
        </ProfileSection>
        <ProfileSection title='invitationer'>
          <Card className='w-full rounded-none border-0 bg-neutral-50 font-serif shadow-none'>
            <CardHeader>
              <Skeleton className='h-6 w-36' />
            </CardHeader>
            <CardContent className='space-y-3'>
              <Skeleton className='h-4 w-3/4' />
              <Skeleton className='h-4 w-1/2' />
            </CardContent>
          </Card>
        </ProfileSection>
      </>
    );
  }

  if (error) {
    return (
      <ProfileSection title='organisation'>
        <Card className='w-full rounded-none border-0 bg-neutral-50 font-serif shadow-none'>
          <CardHeader>
            <CardTitle>Organisation</CardTitle>
          </CardHeader>
          <CardContent>
            <p className='text-destructive'>{error}</p>
            <Button className='mt-4' onClick={() => fetchData(true)}>
              Prøv igen
            </Button>
          </CardContent>
        </Card>
      </ProfileSection>
    );
  }

  if (!data) {
    return null;
  }

  const subscription = data.subscription;
  const seatCapacity = subscription?.seats ?? data.seatUsage.capacity;
  const seatUsageLabel = `${data.seatUsage.used} af ${seatCapacity} pladser i brug`;

  return (
    <>
      <ProfileSection title='organisation'>
        <Card className='w-full gap-3 rounded-none border-0 bg-neutral-50 font-serif shadow-none'>
          <CardHeader className='flex flex-col gap-2 md:flex-row md:items-center md:justify-between'>
            <div>
              <CardTitle>Organisation</CardTitle>
              <p className='text-muted-foreground text-sm'>
                Administrer virksomhedsabonnement og teammedlemmer
              </p>
            </div>
            <Badge variant='secondary'>{data.role}</Badge>
          </CardHeader>
          <CardContent className='space-y-4'>
            <div className='grid gap-4 md:grid-cols-2'>
              <div className='space-y-1'>
                <p className='text-muted-foreground text-sm'>Virksomhed</p>
                <p className='text-lg font-semibold'>
                  {data.organization.name}
                </p>
                {data.organization.cvr && (
                  <p className='text-muted-foreground text-sm'>
                    CVR: {data.organization.cvr}
                  </p>
                )}
              </div>
              <div className='space-y-1'>
                <p className='text-muted-foreground text-sm'>Kontakt</p>
                <p className='text-sm'>
                  {data.organization.contactName || 'Ikke angivet'}
                </p>
                <p className='text-muted-foreground text-sm'>
                  {[
                    data.organization.address,
                    data.organization.postalCode,
                    data.organization.city
                  ]
                    .filter(Boolean)
                    .join(', ') || 'Ingen adresse angivet'}
                </p>
              </div>
            </div>

            <Separator />

            {subscription ? (
              <div className='space-y-4'>
                <div className='flex flex-col gap-2 md:flex-row md:items-center md:justify-between'>
                  <div>
                    <p className='text-muted-foreground text-sm'>Abonnement</p>
                    <p className='text-lg font-semibold'>
                      {formatPlanName(subscription.plan)}
                    </p>
                  </div>
                  <div className='flex items-center gap-2'>
                    <Badge
                      variant={
                        subscription.status === 'active'
                          ? 'default'
                          : 'secondary'
                      }
                    >
                      {STATUS_LABELS[subscription.status] ||
                        subscription.status}
                    </Badge>
                    {subscription.cancelAtPeriodEnd ? (
                      <Badge variant='destructive'>Opsagt</Badge>
                    ) : null}
                  </div>
                </div>
                <div className='rounded-md border border-dashed p-4'>
                  <div className='flex items-center gap-2 text-sm font-medium'>
                    <Users className='h-4 w-4' />
                    <span>{seatUsageLabel}</span>
                  </div>
                  {data.seatUsage.pending > 0 && (
                    <p className='text-muted-foreground mt-1 text-xs'>
                      {data.seatUsage.pending} invitation(er) afventer accept
                    </p>
                  )}
                  <p className='text-muted-foreground mt-2 text-xs'>
                    Næste fakturering: {formatDate(subscription.periodEnd)}
                  </p>
                </div>

                {isManager && (
                  <form
                    onSubmit={handleSeatSubmit}
                    className='bg-muted/30 flex flex-col gap-3 rounded-md border p-4 md:flex-row md:items-end'
                  >
                    <div className='flex-1'>
                      <label className='mb-1 block text-sm font-medium'>
                        Antal pladser
                      </label>
                      <Input
                        type='number'
                        min={data.seatUsage.used}
                        value={seatTarget}
                        onChange={(event) =>
                          setSeatTarget(
                            Number.parseInt(event.target.value || '0', 10)
                          )
                        }
                      />
                      <p className='text-muted-foreground mt-1 text-xs'>
                        Minimum {data.seatUsage.used}. Inkluderer eksisterende
                        medlemmer.
                      </p>
                    </div>
                    <Button
                      type='submit'
                      disabled={
                        seatSubmitting || seatTarget < data.seatUsage.used
                      }
                    >
                      {seatSubmitting ? (
                        <>
                          <Loader2 className='mr-2 h-4 w-4 animate-spin' />
                          Starter betaling...
                        </>
                      ) : (
                        'Opdater pladser'
                      )}
                    </Button>
                  </form>
                )}
              </div>
            ) : (
              <div className='text-muted-foreground rounded-md border border-dashed p-4 text-sm'>
                Ingen aktiv erhvervsplan fundet. Køb et abonnement for at
                administrere teamet.
              </div>
            )}
          </CardContent>
        </Card>

        <Card className='w-full gap-3 rounded-none border-0 bg-neutral-50 font-serif shadow-none'>
          <CardHeader className='flex flex-col gap-2 md:flex-row md:items-center md:justify-between'>
            <CardTitle>Medlemmer</CardTitle>
            {refreshing && (
              <Loader2 className='text-muted-foreground h-4 w-4 animate-spin' />
            )}
          </CardHeader>
          <CardContent className='space-y-4'>
            {data.members.length === 0 ? (
              <p className='text-muted-foreground text-sm'>
                Ingen medlemmer fundet.
              </p>
            ) : (
              <div className='space-y-3'>
                {data.members.map((memberRecord) => (
                  <div
                    key={memberRecord.id}
                    className='flex flex-col gap-2 rounded-md border p-4 md:flex-row md:items-center md:justify-between'
                  >
                    <div>
                      <p className='font-medium'>
                        {memberRecord.user.name ||
                          memberRecord.user.email ||
                          'Ukendt bruger'}
                      </p>
                      <p className='text-muted-foreground text-sm'>
                        {memberRecord.user.email ?? 'Ingen email'}
                      </p>
                      <p className='text-muted-foreground mt-1 text-xs'>
                        Rolle: {memberRecord.role}
                      </p>
                    </div>
                    {isManager && memberRecord.role !== 'owner' && (
                      <Button
                        variant='outline'
                        size='sm'
                        className={clsx(
                          'w-full md:w-auto',
                          removingMemberId === memberRecord.id && 'opacity-80'
                        )}
                        disabled={removingMemberId === memberRecord.id}
                        onClick={() =>
                          handleRemoveMember(
                            memberRecord.id,
                            memberRecord.user.name
                          )
                        }
                      >
                        {removingMemberId === memberRecord.id ? (
                          <>
                            <Loader2 className='mr-2 h-4 w-4 animate-spin' />
                            Fjerner...
                          </>
                        ) : (
                          <>
                            <UserMinus className='mr-2 h-4 w-4' />
                            Fjern medlem
                          </>
                        )}
                      </Button>
                    )}
                  </div>
                ))}
              </div>
            )}
          </CardContent>
        </Card>
      </ProfileSection>

      <ProfileSection title='invitationer'>
        <Card className='w-full gap-3 rounded-none border-0 bg-neutral-50 font-serif shadow-none'>
          <CardHeader>
            <CardTitle>Invitationer</CardTitle>
          </CardHeader>
          <CardContent className='space-y-4'>
            {data.invitations.length === 0 ? (
              <p className='text-muted-foreground text-sm'>
                Ingen aktive invitationer.
              </p>
            ) : (
              <div className='space-y-3'>
                {data.invitations.map((invitation) => (
                  <div
                    key={invitation.id}
                    className='flex flex-col gap-2 rounded-md border p-4 md:flex-row md:items-center md:justify-between'
                  >
                    <div>
                      <p className='font-medium'>{invitation.email}</p>
                      <p className='text-muted-foreground text-sm'>
                        Rolle: {invitation.role}
                      </p>
                      <p className='text-muted-foreground mt-1 text-xs'>
                        Status: {invitation.status}
                        {invitation.expiresAt
                          ? ` · Udløber ${formatDate(invitation.expiresAt)}`
                          : ''}
                      </p>
                    </div>
                    {isManager && invitation.status === 'pending' && (
                      <Button
                        variant='outline'
                        size='sm'
                        className={clsx(
                          'w-full md:w-auto',
                          revokingInvitationId === invitation.id && 'opacity-80'
                        )}
                        disabled={revokingInvitationId === invitation.id}
                        onClick={() => handleRevokeInvitation(invitation.id)}
                      >
                        {revokingInvitationId === invitation.id ? (
                          <>
                            <Loader2 className='mr-2 h-4 w-4 animate-spin' />
                            Tilbagekalder...
                          </>
                        ) : (
                          'Tilbagekald'
                        )}
                      </Button>
                    )}
                  </div>
                ))}
              </div>
            )}

            {isManager && (
              <div className='bg-muted/30 space-y-3 rounded-md border p-4'>
                <div className='flex items-center gap-2 text-sm font-medium'>
                  <MailPlus className='h-4 w-4' />
                  <span>Inviter nyt medlem</span>
                </div>
                <div className='grid gap-3 md:grid-cols-[1fr_minmax(150px,200px)_auto]'>
                  <Input
                    type='email'
                    placeholder='brugernavn@virksomhed.dk'
                    value={inviteEmail}
                    onChange={(event) => setInviteEmail(event.target.value)}
                  />
                  <Select
                    value={inviteRole}
                    onValueChange={(value) =>
                      setInviteRole(value as 'member' | 'admin')
                    }
                  >
                    <SelectTrigger>
                      <SelectValue placeholder='Vælg rolle' />
                    </SelectTrigger>
                    <SelectContent>
                      <SelectItem value='member'>Medlem</SelectItem>
                      <SelectItem value='admin'>Administrator</SelectItem>
                    </SelectContent>
                  </Select>
                  <Button
                    type='button'
                    onClick={handleInvite}
                    disabled={inviteSubmitting}
                  >
                    {inviteSubmitting ? (
                      <>
                        <Loader2 className='mr-2 h-4 w-4 animate-spin' />
                        Sender...
                      </>
                    ) : (
                      'Send invitation'
                    )}
                  </Button>
                </div>
                {data.subscription && (
                  <p
                    className={clsx(
                      'text-xs',
                      seatsRemaining > 0
                        ? 'text-muted-foreground'
                        : 'text-destructive'
                    )}
                  >
                    Tilgængelige pladser: {seatsRemaining}
                  </p>
                )}
              </div>
            )}
          </CardContent>
        </Card>
      </ProfileSection>
    </>
  );
}
