'use client';

import * as React from 'react';
import { useEffect, useMemo, useState } from 'react';
import { useMutation } from '@tanstack/react-query';
import { toast } from 'sonner';
import { Icons } from '@/components/icons';
import { Button } from '@/components/ui/button';
import { Select, SelectContent, SelectItem, SelectTrigger, SelectValue } from '@/components/ui/select';
import {
  Sheet,
  SheetContent,
  SheetDescription,
  SheetFooter,
  SheetHeader,
  SheetTitle
} from '@/components/ui/sheet';
import { useAppForm, useFormFields } from '@/components/ui/tanstack-form';
import { createLeadMutation, updateLeadMutation } from '../api/mutations';
import type { LeadReferenceData, LeadSummary } from '../api/types';
import { leadSchema } from '../schemas/lead.schema';

type LeadFormValues = {
  branchId: string | null;
  customerId: string | null;
  contactId: string | null;
  description: string | null;
  projectName: string | null;
  projectLocation: string | null;
  productType: string | null;
  priority: string | null;
  estimatedValue: number | null;
  awarenessId: string | null;
  status: string;
  followupStatus: string | null;
  lostReason: string | null;
  outcome: 'open' | 'won' | 'lost';
  ownerMarketingUserId: string | null;
};

function toDefaultValues(lead: LeadSummary | undefined, referenceData: LeadReferenceData): LeadFormValues {
  return {
    branchId: lead?.branchId ?? referenceData.branches[0]?.id ?? null,
    customerId: lead?.customerId ?? null,
    contactId: lead?.contactId ?? null,
    description: lead?.description ?? null,
    projectName: lead?.projectName ?? null,
    projectLocation: lead?.projectLocation ?? null,
    productType: lead?.productType ?? referenceData.productTypes[0]?.id ?? null,
    priority: lead?.priority ?? referenceData.priorities[0]?.id ?? null,
    estimatedValue: lead?.estimatedValue ?? null,
    awarenessId: lead?.awarenessId ?? referenceData.awarenesses[0]?.id ?? null,
    status: lead?.status ?? referenceData.statuses[0]?.id ?? '',
    followupStatus: lead?.followupStatus ?? null,
    lostReason: lead?.lostReason ?? null,
    outcome: (lead?.outcome as 'open' | 'won' | 'lost' | undefined) ?? 'open',
    ownerMarketingUserId: lead?.ownerMarketingUserId ?? null
  };
}

export function LeadForm({
  open,
  onOpenChange,
  referenceData,
  lead
}: {
  open: boolean;
  onOpenChange: (open: boolean) => void;
  referenceData: LeadReferenceData;
  lead?: LeadSummary;
}) {
  const isEdit = Boolean(lead);
  const defaultValues = useMemo(() => toDefaultValues(lead, referenceData), [lead, referenceData]);
  const [selectedCustomerId, setSelectedCustomerId] = useState(defaultValues.customerId ?? '');
  const { FormTextField, FormTextareaField, FormSelectField, FormCurrencyField } =
    useFormFields<LeadFormValues>();

  const createMutation = useMutation({
    ...createLeadMutation,
    onSuccess: () => {
      toast.success('สร้างลีดสำเร็จ');
      onOpenChange(false);
    },
    onError: (error) => {
      toast.error(error instanceof Error ? error.message : 'ไม่สามารถสร้างลีดได้');
    }
  });

  const updateMutation = useMutation({
    ...updateLeadMutation,
    onSuccess: () => {
      toast.success('อัปเดตลีดสำเร็จ');
      onOpenChange(false);
    },
    onError: (error) => {
      toast.error(error instanceof Error ? error.message : 'ไม่สามารถอัปเดตลีดได้');
    }
  });

  const contactsForCustomer = referenceData.contacts.filter(
    (contact) => contact.customerId === selectedCustomerId
  );

  const form = useAppForm({
    defaultValues,
    onSubmit: async ({ value }) => {
      const payload = {
        ...value,
        branchId: value.branchId || null,
        customerId: value.customerId || null,
        contactId: value.contactId || null,
        description: value.description || null,
        projectName: value.projectName || null,
        projectLocation: value.projectLocation || null,
        productType: value.productType || null,
        priority: value.priority || null,
        estimatedValue: value.estimatedValue ?? null,
        awarenessId: value.awarenessId || null,
        followupStatus: value.followupStatus || null,
        lostReason: value.lostReason || null,
        ownerMarketingUserId: value.ownerMarketingUserId || null
      };

      if (isEdit && lead) {
        await updateMutation.mutateAsync({ id: lead.id, values: payload });
        return;
      }

      await createMutation.mutateAsync(payload);
    }
  });

  useEffect(() => {
    if (!open) return;

    form.reset(defaultValues);
    setSelectedCustomerId(defaultValues.customerId ?? '');
  }, [defaultValues, form, open]);

  return (
    <Sheet open={open} onOpenChange={onOpenChange}>
      <SheetContent className='flex w-full flex-col sm:max-w-3xl'>
        <SheetHeader>
          <SheetTitle>{isEdit ? 'แก้ไขลีด' : 'สร้างลีด'}</SheetTitle>
          <SheetDescription>บันทึกข้อมูลลีดของฝ่ายการตลาดก่อนส่งต่อให้ฝ่ายขาย</SheetDescription>
        </SheetHeader>

        <div className='flex-1 overflow-auto'>
          <form.AppForm>
            <form.Form id='lead-form' className='grid gap-4 md:grid-cols-2'>
              <form.AppField
                name='customerId'
                children={(field) => (
                  <field.FieldSet>
                    <field.Field>
                      <field.FieldLabel>ลูกค้า</field.FieldLabel>
                      <Select
                        value={field.state.value ?? ''}
                        onValueChange={(nextValue) => {
                          field.handleChange(nextValue === '__none__' ? null : nextValue);
                          field.handleBlur();
                          setSelectedCustomerId(nextValue === '__none__' ? '' : nextValue);
                          form.setFieldValue('contactId', null);
                        }}
                      >
                        <SelectTrigger aria-label='ลูกค้า'>
                          <SelectValue placeholder='เลือกลูกค้า' />
                        </SelectTrigger>
                        <SelectContent>
                          <SelectItem value='__none__'>ไม่เลือก</SelectItem>
                          {referenceData.customers.map((customer) => (
                            <SelectItem key={customer.id} value={customer.id}>
                              {customer.name} ({customer.code})
                            </SelectItem>
                          ))}
                        </SelectContent>
                      </Select>
                    </field.Field>
                    <field.FieldError />
                  </field.FieldSet>
                )}
              />

              <form.AppField
                name='contactId'
                children={(field) => (
                  <field.FieldSet>
                    <field.Field>
                      <field.FieldLabel>ผู้ติดต่อ</field.FieldLabel>
                      <Select
                        value={field.state.value ?? '__none__'}
                        onValueChange={(nextValue) => {
                          field.handleChange(nextValue === '__none__' ? null : nextValue);
                          field.handleBlur();
                        }}
                      >
                        <SelectTrigger aria-label='ผู้ติดต่อ'>
                          <SelectValue placeholder='เลือกผู้ติดต่อ' />
                        </SelectTrigger>
                        <SelectContent>
                          <SelectItem value='__none__'>ไม่เลือก</SelectItem>
                          {contactsForCustomer.map((contact) => (
                            <SelectItem key={contact.id} value={contact.id}>
                              {contact.name}
                              {contact.isPrimary ? ' (หลัก)' : ''}
                            </SelectItem>
                          ))}
                        </SelectContent>
                      </Select>
                    </field.Field>
                    <field.FieldError />
                  </field.FieldSet>
                )}
              />

              <FormTextField name='projectName' label='Project Name' />
              <FormTextField name='projectLocation' label='Project Location' />
              <FormTextareaField name='description' label='Description' className='md:col-span-2' />

              <FormSelectField
                name='branchId'
                label='สาขา'
                options={referenceData.branches.map((branch) => ({
                  value: branch.id,
                  label: branch.name
                }))}
              />
              <FormSelectField
                name='productType'
                label='Product Type'
                options={referenceData.productTypes.map((item) => ({
                  value: item.id,
                  label: item.label
                }))}
              />
              <FormSelectField
                name='priority'
                label='Priority'
                options={referenceData.priorities.map((item) => ({
                  value: item.id,
                  label: item.label
                }))}
              />
              <FormCurrencyField name='estimatedValue' label='Estimated Value' currencyLabel='THB' />
              <FormSelectField
                name='awarenessId'
                label='Awareness'
                options={referenceData.awarenesses.map((item) => ({
                  value: item.id,
                  label: item.label
                }))}
              />
              <FormSelectField
                name='status'
                label='Status'
                options={referenceData.statuses.map((item) => ({
                  value: item.id,
                  label: item.label
                }))}
              />
              <FormSelectField
                name='followupStatus'
                label='Follow-up Status'
                options={referenceData.followupStatuses.map((item) => ({
                  value: item.id,
                  label: item.label
                }))}
              />
              <FormSelectField
                name='lostReason'
                label='Lost Reason'
                options={referenceData.lostReasons.map((item) => ({
                  value: item.id,
                  label: item.label
                }))}
              />
              <FormSelectField
                name='ownerMarketingUserId'
                label='Marketing Owner'
                options={referenceData.assignableUsers.map((user) => ({
                  value: user.id,
                  label: user.name
                }))}
              />
            </form.Form>
          </form.AppForm>
        </div>

        <SheetFooter>
          <Button
            variant='outline'
            onClick={() => onOpenChange(false)}
            disabled={createMutation.isPending || updateMutation.isPending}
          >
            ยกเลิก
          </Button>
          <Button
            type='submit'
            form='lead-form'
            isLoading={createMutation.isPending || updateMutation.isPending}
          >
            <Icons.add className='mr-2 h-4 w-4' />
            {isEdit ? 'อัปเดตลีด' : 'สร้างลีด'}
          </Button>
        </SheetFooter>
      </SheetContent>
    </Sheet>
  );
}

export function LeadFormTrigger({ referenceData }: { referenceData: LeadReferenceData }) {
  const [open, setOpen] = React.useState(false);

  return (
    <>
      <Button onClick={() => setOpen(true)}>
        <Icons.add className='mr-2 h-4 w-4' />
        เพิ่มลีด
      </Button>
      <LeadForm open={open} onOpenChange={setOpen} referenceData={referenceData} />
    </>
  );
}
