import { type ChangeEvent, type FormEvent, useId, useState } from 'react';

import Alert from '@mui/material/Alert';
import { Button, Stack, TextField } from '@mui/material';

import { leadsApi, type LeadCreatePayload } from '../../../api/index.ts';
import { ApiError } from '../../../api/httpClient.ts';

type FeedbackFormFields = {
  fullName: string;
  email: string;
  phone: string;
};

type FeedbackFormErrors = Record<keyof FeedbackFormFields, string | null>;

const defaultFormState: FeedbackFormFields = {
  fullName: '',
  email: '',
  phone: '',
};

const createDefaultErrors = (): FeedbackFormErrors => ({
  fullName: null,
  email: null,
  phone: null,
});

export const FeedbackForm = () => {
  const formInstanceId = useId();
  const [form, setForm] = useState<FeedbackFormFields>(defaultFormState);
  const [errors, setErrors] = useState<FeedbackFormErrors>(createDefaultErrors());
  const [alert, setAlert] = useState<{ type: 'success' | 'error'; message: string } | null>(null);
  const [isSubmitting, setIsSubmitting] = useState(false);

  const handleChange = (event: ChangeEvent<HTMLInputElement>) => {
    const { name, value } = event.target;
    setForm((prev) => ({
      ...prev,
      [name]: value,
    }));
    setErrors((prev) => ({
      ...prev,
      [name]: null,
    }));
  };

  const validate = () => {
    const nextErrors = createDefaultErrors();
    let isValid = true;

    if (!form.fullName.trim()) {
      nextErrors.fullName = 'Укажите ваше имя';
      isValid = false;
    }

    if (!form.email.trim()) {
      nextErrors.email = 'Введите email';
      isValid = false;
    } else if (!/^[\w.+-]+@[\w.-]+\.[A-Za-z]{2,}$/.test(form.email.trim())) {
      nextErrors.email = 'Введите корректный email';
      isValid = false;
    }

    if (form.phone.trim() && form.phone.trim().length < 5) {
      nextErrors.phone = 'Введите телефон полностью';
      isValid = false;
    }

    setErrors(nextErrors);
    return isValid;
  };

  const handleSubmit = async (event: FormEvent<HTMLFormElement>) => {
    event.preventDefault();
    setAlert(null);

    if (!validate()) {
      setAlert({ type: 'error', message: 'Пожалуйста, проверьте правильность заполнения формы.' });
      return;
    }

    setIsSubmitting(true);

    const normalizedPhone = form.phone.trim();
    const payload: LeadCreatePayload = {
      fullName: form.fullName.trim(),
      email: form.email.trim(),
      ...(normalizedPhone ? { phone: normalizedPhone } : {}),
    };

    try {
      await leadsApi.create(payload);
      setAlert({ type: 'success', message: 'Спасибо! Мы свяжемся с вами в ближайшее время.' });
      setForm(defaultFormState);
      setErrors(createDefaultErrors());
    } catch (err) {
      const message =
        err instanceof ApiError ? err.message || 'Не удалось отправить заявку. Попробуйте ещё раз.' : 'Не удалось отправить заявку. Попробуйте ещё раз.';
      setAlert({ type: 'error', message });
    } finally {
      setIsSubmitting(false);
    }
  };

  return (
    <Stack component="form" onSubmit={handleSubmit} noValidate sx={{ alignItems: 'center', width: { xs: '100%', sm: '70%' } }} spacing={1.5}>
      {alert && <Alert severity={alert.type}>{alert.message}</Alert>}
      <TextField
        id={`${formInstanceId}-fullName`}
        name="fullName"
        size="small"
        variant="outlined"
        placeholder="Иванов Иван"
        value={form.fullName}
        onChange={handleChange}
        error={Boolean(errors.fullName)}
        helperText={errors.fullName}
        fullWidth
        autoComplete="name"
      />
      <Stack useFlexGap sx={{ alignItems: 'center', width: { xs: '100%' }, flexDirection: 'row' }} spacing={1}>
        <TextField
          id={`${formInstanceId}-email`}
          name="email"
          size="small"
          variant="outlined"
          placeholder="email@example.com"
          value={form.email}
          onChange={handleChange}
          error={Boolean(errors.email)}
          helperText={errors.email}
          fullWidth
          autoComplete="email"
        />
        <TextField
          id={`${formInstanceId}-phone`}
          name="phone"
          size="small"
          variant="outlined"
          placeholder="+7 999 123 45 67"
          value={form.phone}
          onChange={handleChange}
          error={Boolean(errors.phone)}
          helperText={errors.phone}
          fullWidth
          autoComplete="tel"
          inputProps={{ inputMode: 'tel' }}
        />
      </Stack>
      <Button type="submit" variant="outlined" color="info" size="small" disabled={isSubmitting}>
        {isSubmitting ? 'Отправляем...' : 'Оставить заявку'}
      </Button>
    </Stack>
  );
};
