"use client"

import type React from "react"
import { useEffect, useRef, useState } from "react"
import { useFormik } from "formik"
import { candidatesApi } from "@/shared/api/endpoints/hr/candidates"
import { Grid, Stack, Box, IconButton, Snackbar, Alert, InputAdornment, List, ListItem, ListItemIcon, ListItemText, Typography } from "@mui/material"
import { FontAwesomeIcon } from "@fortawesome/react-fontawesome"
import { faPaperclip, faExclamationCircle } from "@fortawesome/free-solid-svg-icons"
import { type ICandidature, CandidatureStatut } from "@/shared/types/candidature"
import { type ModeType, TableType, type TableColumn } from "@/shared/types/common"
import FormField from "@/shared/components/form/form-field"
import { StyledTextField } from "@/shared/theme/css"
import { useResponsive } from "@/hooks"
import { getCandidatureFields } from "../../utils/form-fields-formulaire"
import { getCandidatureFieldsForStatus } from "@/shared/sections/rh/recrutement/candidatures/utils/candidature-field-constants"
import FormContainer from "@/layouts/form/form-container"
import EditExportButtons from "@/shared/components/form/edit-export-buttons"
import CustomTooltip from "@/shared/components/tooltips/tooltip-custom"
import { AddButton } from "@/shared/components/table/styles"
import ActionButtons from "@/shared/components/form/buttons-action"
import CandidatureDateField from "./candidature-date-field"
import ConditionalComponent from "@/shared/components/table/ConditionalComponent"
import SendEmailModal from "../send-email-modal"
import { createCandidatureSchema } from "../../utils/candidature-schema"
import { useCandidatesStore } from "@/shared/api/stores/hr-service/candidatesStore"
import { LocalizationProvider } from '@mui/x-date-pickers/LocalizationProvider'
import { AdapterDayjs } from '@mui/x-date-pickers/AdapterDayjs'
import 'dayjs/locale/fr'
import dayjs from 'dayjs'

// Configure dayjs to use French locale
dayjs.locale('fr')

interface CandidatureFormProps {
  candidature: ICandidature
  mode: ModeType
  onSave: (candidature: ICandidature) => Promise<void> | void
  onClose: (forceClose: boolean) => void;
  onEdit?: (candidature: ICandidature) => void
  onStatusChange?: (row: ICandidature, newStatus: string, field: keyof ICandidature, reason?: string) => void
  tableHead: TableColumn[]
  updateTabContent: (tabId: string, newContent: ICandidature) => void
  tabId: string
  useBackend?: boolean; // Feature flag for backend integration
  currentTab?: string; // Current tab identifier
}

export default function CandidatureDetailsForm({
  candidature,
  mode,
  onSave,
  onClose,
  onEdit,
  onStatusChange,
  tableHead,
  updateTabContent,
  tabId,
  useBackend = false,
  currentTab,
}: CandidatureFormProps) {
  const documentFileInputRef = useRef<HTMLInputElement>(null)
  const contratDocumentFileInputRef = useRef<HTMLInputElement>(null)
  const isBetweenSmAndLg = useResponsive("between", "sm", "lg")

  const [isEmailModalOpen, setIsEmailModalOpen] = useState(false)
  const [emailSubject, setEmailSubject] = useState("")
  const [emailMessage, setEmailMessage] = useState("")
  const [notification, setNotification] = useState({
    open: false,
    message: "",
    severity: "info" as "success" | "info" | "warning" | "error",
  })

  const isViewMode = mode === "view"
  const isEditMode = mode === "edit"
  const isNewMode = mode === "add"

  const isStatusChangeDisabled = currentTab === "rdvSemaine" || currentTab === "absentRdv"
  const { departments, departmentsLoading, fetchDepartments, fetchRdvSemaineCandidates, fetchAbsentCandidates, fetchCandidatesByStatus } = useCandidatesStore()
  useEffect(() => {
    fetchDepartments()
  }, [fetchDepartments])

  const [emailExists, setEmailExists] = useState(false)
  const emailCheckTimeoutRef = useRef<number | null>(null)

  const formik = useFormik<ICandidature>({
    initialValues: candidature,
    validationSchema: createCandidatureSchema(candidature.type === "Candidature sédentaire"),
    enableReinitialize: true,
    onSubmit: async (values) => {
      const statusRequiresRedirection =
        values.statut === CandidatureStatut.Retenu ||
        values.statut === CandidatureStatut.Refuse ||
        values.statut === CandidatureStatut.Blackliste ||
        values.statut === CandidatureStatut.Valide ||
        values.statut === CandidatureStatut.Absent

      if (values.statut === CandidatureStatut.Valide && !values.contrat) {
        values.contrat = "non signé"
      }

      await onSave(values)

      if (!isNewMode && values.dateHeureRdvAgence && useBackend) {
        try {
          const candidateType = values.type === "Candidature chauffeur" ? 'DRIVER' : 'SEDENTARY';
          await Promise.all([
            fetchRdvSemaineCandidates(candidateType),
            fetchAbsentCandidates(candidateType),
            fetchCandidatesByStatus('RETAINED', candidateType)
          ]);
        } catch (error) {
          console.error('Erreur lors du rafraîchissement des listes:', error);
        }
      }

      if (isNewMode) {
        setNotification({
          open: true,
          message: "Candidat créé avec succès",
          severity: "success",
        })
        setTimeout(() => onClose(true), 500);
        return;
      }

      setNotification({
        open: true,
        message: "Candidat mis à jour avec succès",
        severity: "success",
      })
      setTimeout(() => onClose(true), 500);
    },

  })
  useEffect(() => {
    const email = formik.values.email
    if (!isNewMode) {
      setEmailExists(false)
      return
    }
    if (emailCheckTimeoutRef.current) {
      window.clearTimeout(emailCheckTimeoutRef.current)
    }
    if (!email) {
      setEmailExists(false)
      formik.setFieldError('email', undefined as unknown as string)
      return
    }
    const timeoutId = window.setTimeout(async () => {
      try {
        const exists = await candidatesApi.checkEmailExists(email)
        setEmailExists(!!exists)
        if (exists) {
          formik.setFieldError('email', 'Un candidat avec cet email existe déjà')
        } else {
          if (formik.errors.email === 'Un candidat avec cet email existe déjà') {
            formik.setFieldError('email', undefined as unknown as string)
          }
        }
      } catch { }
    }, 400)
    emailCheckTimeoutRef.current = timeoutId
    return () => {
      if (emailCheckTimeoutRef.current) {
        window.clearTimeout(emailCheckTimeoutRef.current)
      }
    }
  }, [formik.values.email, isNewMode])

  useEffect(() => {
    if (updateTabContent && tabId && mode !== "view") {
      updateTabContent(tabId, formik.values)
    }
  }, [formik.values, updateTabContent, tabId, mode])

  const isSedentaire = formik.values.type === "Candidature sédentaire"
  const candidatureFields = getCandidatureFields(isSedentaire)

  const handleStatusChange = (name: string, value: any) => {
    const newStatus = value as CandidatureStatut
    const updatedValues = { ...formik.values, [name]: newStatus }

    if (
      (newStatus === CandidatureStatut.Retenu || newStatus === CandidatureStatut.Valide) &&
      !formik.values.dateHeureRdvAgence
    ) {
      const tomorrow = new Date()
      tomorrow.setDate(tomorrow.getDate() + 1)
      tomorrow.setHours(10, 0, 0, 0)

      const dateString = tomorrow.toISOString().slice(0, 16)
      updatedValues.dateHeureRdvAgence = dateString
    }

    if ((newStatus === CandidatureStatut.Valide || newStatus === CandidatureStatut.Retenu) && !formik.values.contrat) {
      updatedValues.contrat = "non signé"
    }

    if (newStatus === CandidatureStatut.Valide && !formik.values.email_pro) {
      if (formik.values.email) {
        const emailParts = formik.values.email.split("@")
        if (emailParts.length > 1) {
          updatedValues.email_pro = emailParts[0] + "@votreentreprise.com"
        }
      } else if (formik.values.nom && formik.values.prenom) {
        const normalizedPrenom = formik.values.prenom
          .toLowerCase()
          .normalize("NFD")
          .replace(/[\u0300-\u036f]/g, "")
        const normalizedNom = formik.values.nom
          .toLowerCase()
          .normalize("NFD")
          .replace(/[\u0300-\u036f]/g, "")
        updatedValues.email_pro = `${normalizedPrenom}.${normalizedNom}@votreentreprise.com`
      }
    }

    if (
      (newStatus === CandidatureStatut.Refuse || newStatus === CandidatureStatut.Blackliste) &&
      !formik.values.raisonRefus
    ) {
      updatedValues.raisonRefus = ""
    }

    Object.keys(updatedValues).forEach((key) => {
      formik.setFieldValue(key, updatedValues[key as keyof ICandidature])
    })

    if (onStatusChange && useBackend) {
      onStatusChange(formik.values, newStatus, 'statut');
    }
  }

  const handleDocumentUpload = (e: React.ChangeEvent<HTMLInputElement>) => {
    const file = e.target.files?.[0]
    if (file) {
      formik.setFieldValue("document", file.name)
    }
  }

  const handleContratDocumentUpload = (e: React.ChangeEvent<HTMLInputElement>) => {
    const file = e.target.files?.[0]
    if (file) {
      formik.setFieldValue("contrat_document", file.name)
    }
  }

  const handleDocumentIconClick = () => {
    if (!isViewMode) {
      documentFileInputRef.current?.click()
    }
  }

  const handleContratDocumentIconClick = () => {
    if (!isViewMode) {
      contratDocumentFileInputRef.current?.click()
    }
  }

  const handleOpenEmailModal = () => setIsEmailModalOpen(true)
  const handleCloseEmailModal = () => {
    setIsEmailModalOpen(false)
    setEmailSubject("")
    setEmailMessage("")
  }

  const handleSendEmail = (subject: string, message: string) => {
    setNotification({
      open: true,
      message: "Email envoyé avec succès",
      severity: "success"
    })

    handleCloseEmailModal()
  }

  const handleCloseNotification = () => {
    setNotification({ ...notification, open: false })
  }

  const handleEditClick = () => {
    if (onEdit) {
      onEdit(candidature)
    }
  }

  return (
    <FormContainer
      titre={isNewMode ? "Nouvelle candidature" : `Candidature - ${formik.values.nom} ${formik.values.prenom}`}
    >
      <Stack flexGrow={0} direction="row" alignItems="center" justifyContent="flex-end" gap="8px" pb={1}>
        <ConditionalComponent isValid={isViewMode}>
          <EditExportButtons
            onEdit={handleEditClick}
            onExport={() => void 0}
            tooltipTitle={TableType.Candidature}
            dataRow={candidature}
            tableHead={tableHead}
          />
        </ConditionalComponent>
        <ConditionalComponent isValid={formik.values.statut === CandidatureStatut.ATraiter && isViewMode}>
          <Box
            sx={{
              borderLeft: 1,
              height: 30,
              borderColor: (theme) => theme.palette.text.disabled,
              mx: 1,
              mb: 1,
            }}
          />
        </ConditionalComponent>
        <ConditionalComponent isValid={formik.values.statut === CandidatureStatut.ATraiter}>
          <CustomTooltip arrow title="Envoyer un email">
            <AddButton color="primary" variant="contained" onClick={handleOpenEmailModal} sx={{ mr: 1, mb: 1 }}>
              Envoyer un email
            </AddButton>
          </CustomTooltip>
        </ConditionalComponent>
      </Stack>


      <LocalizationProvider 
        dateAdapter={AdapterDayjs}
        adapterLocale="fr"
      >
        <form onSubmit={formik.handleSubmit}>
          <Grid container spacing={3}>
          {candidatureFields
            .filter((field) => {
              const allowedFields = getCandidatureFieldsForStatus(
                formik.values.statut,
                isSedentaire
              );

              if (allowedFields.length > 0) {
                return allowedFields.includes(field.name);
              }

              if (field.showWhen) {
                return field.showWhen(formik.values);
              }

              return true;
            })
            .map((field) => {
              if (field.name === "departement") {
                const departmentField = {
                  ...field,
                  options: departments.map(dept => ({
                    value: dept.name,
                    label: dept.name
                  }))
                }
                return (
                  <Grid item xs={12} md={6} key={field.name}>
                    <FormField
                      field={departmentField}
                      value={formik.values[field.name] || ""}
                      formData={formik.values}
                      onChange={(name, value) => formik.setFieldValue(name, value)}
                      error={
                        formik.touched[field.name] && formik.errors[field.name]
                          ? (formik.errors[field.name] as string)
                          : undefined
                      }
                      onBlur={formik.handleBlur}
                      isReadOnly={isViewMode}
                      disabled={departmentsLoading}
                    />
                  </Grid>
                )
              }

              // Handle date fields with custom component to avoid dayjs validation issues
              if (field.name === "dateAppelRappel" || field.name === "dateCandidature") {
                return (
                  <Grid item xs={12} md={6} key={field.name}>
                    <CandidatureDateField
                      field={field}
                      value={formik.values[field.name] || ""}
                      onChange={(name, value) => formik.setFieldValue(name, value)}
                      error={
                        formik.touched[field.name] && formik.errors[field.name]
                          ? (formik.errors[field.name] as string)
                          : undefined
                      }
                      onBlur={formik.handleBlur}
                      isReadOnly={isViewMode}
                    />
                  </Grid>
                )
              }

              if (field.name === "dateHeureRdvAgence" && formik.values.statut === CandidatureStatut.Absent) {
                const modifiedField = { ...field, label: "Replanifier un RDV" }
                return (
                  <Grid item xs={12} md={6} key={field.name}>
                    <CandidatureDateField
                      field={modifiedField}
                      value={formik.values[field.name] || ""}
                      onChange={(name, value) => formik.setFieldValue(name, value)}
                      error={
                        formik.touched[field.name] && formik.errors[field.name]
                          ? (formik.errors[field.name] as string)
                          : undefined
                      }
                      onBlur={formik.handleBlur}
                      isReadOnly={isViewMode}
                    />
                  </Grid>
                )
              }

              if (field.name === "dateHeureRdvAgence" && formik.values.statut === CandidatureStatut.Retenu) {
                const modifiedField = { ...field, label: "Planifier un RDV" }
                return (
                  <Grid item xs={12} md={6} key={field.name}>
                    <CandidatureDateField
                      field={modifiedField}
                      value={formik.values[field.name] || ""}
                      onChange={(name, value) => {
                        formik.setFieldValue(name, value)
                        if (value) {
                          const updatedCandidature = { ...formik.values, [name]: value }
                          updateTabContent(tabId, updatedCandidature)
                        }
                      }}
                      error={
                        formik.touched[field.name] && formik.errors[field.name]
                          ? (formik.errors[field.name] as string)
                          : undefined
                      }
                      onBlur={formik.handleBlur}
                      isReadOnly={isViewMode}
                    />
                  </Grid>
                )
              }

              if (
                field.name === "raisonRefus" &&
                (formik.values.statut === CandidatureStatut.Refuse ||
                  formik.values.statut === CandidatureStatut.Blackliste)
              ) {
                const modifiedField = { ...field, label: "Raison", required: true }
                return (
                  <Grid item xs={12} md={6} key={field.name}>
                    <FormField
                      field={modifiedField}
                      value={formik.values[field.name] || ""}
                      formData={formik.values}
                      onChange={(name, value) => formik.setFieldValue(name, value)}
                      error={
                        formik.touched[field.name] && formik.errors[field.name]
                          ? (formik.errors[field.name] as string)
                          : undefined
                      }
                      onBlur={formik.handleBlur}
                      isReadOnly={isViewMode}
                    />
                  </Grid>
                )
              }


              if (field.name === "statut") {
                const statusField = {
                  ...field,
                  disabled: isStatusChangeDisabled
                }
                return (
                  <Grid item xs={12} md={6} key={field.name}>
                    <FormField
                      field={statusField}
                      value={formik.values[field.name] || ""}
                      formData={formik.values}
                      onChange={(name, value) =>
                        field.name === "statut" ? handleStatusChange(name, value) : formik.setFieldValue(name, value)
                      }
                      error={
                        formik.touched[field.name] && formik.errors[field.name]
                          ? (formik.errors[field.name] as string)
                          : undefined
                      }
                      onBlur={formik.handleBlur}
                      isReadOnly={isViewMode || isStatusChangeDisabled} // Disabled in both RDV sections
                    />
                  </Grid>
                )
              }

              if (field.name === "document") {
                return (
                  <Grid item xs={12} md={6} key={field.name}>
                    <StyledTextField
                      isSmallScreen={isBetweenSmAndLg}
                      fullWidth
                      name={field.name}
                      InputLabelProps={{
                        shrink: true,
                      }}
                      value={formik.values[field.name] || ""}
                      onChange={formik.handleChange}
                      onBlur={formik.handleBlur}
                      label={field.label}
                      placeholder="Cliquez pour importer un document"
                      InputProps={{
                        readOnly: isViewMode,
                        endAdornment: (
                          <InputAdornment position="end">
                            <CustomTooltip arrow title="Importer un document">
                              <IconButton
                                onClick={handleDocumentIconClick}
                                disabled={isViewMode}
                                size="small"
                                color="primary"
                              >
                                <FontAwesomeIcon icon={faPaperclip} />
                              </IconButton>
                            </CustomTooltip>
                          </InputAdornment>
                        ),
                      }}
                    />
                  </Grid>
                )
              }

              if (field.name === "contrat_document") {
                return (
                  <Grid item xs={12} md={6} key={field.name}>
                    <StyledTextField
                      isSmallScreen={isBetweenSmAndLg}
                      fullWidth
                      name={field.name}
                      InputLabelProps={{
                        shrink: true,
                      }}
                      value={formik.values[field.name] || ""}
                      onChange={formik.handleChange}
                      onBlur={formik.handleBlur}
                      label={field.label}
                      placeholder="Cliquez pour importer le contrat"
                      InputProps={{
                        readOnly: isViewMode,
                        endAdornment: (
                          <InputAdornment position="end">
                            <CustomTooltip arrow title="Importer le contrat">
                              <IconButton
                                onClick={handleContratDocumentIconClick}
                                disabled={isViewMode}
                                size="small"
                                color="primary"
                              >
                                <FontAwesomeIcon icon={faPaperclip} />
                              </IconButton>
                            </CustomTooltip>
                          </InputAdornment>
                        ),
                      }}
                    />
                  </Grid>
                )
              }

              return (
                <Grid item xs={12} md={6} key={field.name}>
                  <FormField
                    field={field}
                    value={formik.values[field.name] || ""}
                    formData={formik.values}
                    onChange={(name, value) =>
                      field.name === "statut" ? handleStatusChange(name, value) : formik.setFieldValue(name, value)
                    }
                    error={
                      formik.touched[field.name] && formik.errors[field.name] ?
                        field.name === "address" ? (formik.errors.address as { address?: string })?.address
                          :
                          String(formik.errors[field.name])
                        : undefined
                    }
                    onBlur={formik.handleBlur}
                    isReadOnly={isViewMode}
                    disabled={field.name === "sourceCandidat" && mode !== "add"}
                  />
                </Grid>
              )
            })}
          <Grid item xs={12}>
            <ConditionalComponent isValid={!isViewMode}>
              <ActionButtons onSave={formik.submitForm} onCancel={() => onClose(false)} mode={mode} disabled={isNewMode && emailExists} />
            </ConditionalComponent>
          </Grid>
        </Grid>
        </form>
      </LocalizationProvider>

      <input
        type="file"
        ref={documentFileInputRef}
        style={{ display: "none" }}
        onChange={handleDocumentUpload}
        accept=".pdf,.doc,.docx,.jpg,.jpeg,.png"
      />
      <input
        type="file"
        ref={contratDocumentFileInputRef}
        style={{ display: "none" }}
        onChange={handleContratDocumentUpload}
        accept=".pdf,.doc,.docx,.jpg,.jpeg,.png"
      />

      <SendEmailModal
        open={isEmailModalOpen}
        onClose={handleCloseEmailModal}
        candidature={formik.values}
        onSend={handleSendEmail}
        useBackend={useBackend}
      />

      <Snackbar
        open={notification.open}
        autoHideDuration={6000}
        onClose={handleCloseNotification}
        anchorOrigin={{ vertical: "top", horizontal: "center" }}
      >
        <Alert onClose={handleCloseNotification} severity={notification.severity} sx={{ width: "100%" }}>
          {notification.message}
        </Alert>
      </Snackbar>
    </FormContainer>
  )
}
