import {
  addTicket,
  deleteTicket,
  getListMaster,
  getTicketsOfUser,
} from '@/api/Admin'
import { DataTablePagination } from '@/components/DataTable/DataTable'
import { Xdelete, create } from '@/rtk/helpers/CRUD'
import { get } from '@/rtk/helpers/apiService'
import {
  Badge,
  Box,
  Button,
  Dialog,
  Group,
  HoverCard,
  Modal,
  Select,
  Text,
  Textarea,
} from '@mantine/core'
import { DateInput } from '@mantine/dates'
import { useForm } from '@mantine/form'
import { notifications } from '@mantine/notifications'
import { IconTrash } from '@tabler/icons-react'
import moment from 'moment'
import { useEffect, useState } from 'react'
import classes from './Tickets.module.css'

type TTickets = {
  id: number
  start_period: string
  end_period: string
  type: string
  start_date: Date
  end_date: Date
  reason: string
}

type TListTickets = {
  data: User[]
}

interface User {
  id: number
  name: string
  email: string
  email_verified_at: string | null
  permission: string
  remember_token: string | null
  created_at: string | null
  updated_at: string | null
}

interface DataReason {
  id: number
  c_code: string
  c_name: string
}

interface DataTimeType {
  id: number
  c_code: string
  c_name: string
}

interface FilterInfo {
  key: string
  name: string
  type: string
}

const Tickets = () => {
  const [listTickets, setListTiskets] = useState<TListTickets>({
    data: [],
  })
  const [action, setAction] = useState('')
  const [item, setItem] = useState({ id: 0 })
  const [activeBtn, setActiveBtn] = useState(false)
  const [disableBtn, setDisableBtn] = useState(false)

  const [dataTimeType, setDataTimeType] = useState<DataTimeType[]>([])
  const [dataReason, setDataReason] = useState<DataReason[]>([])

  const getListMasterByType = async (type: string) => {
    try {
      const params = {
        type: type,
      }
      const res = await get(getListMaster, params)
      if (res.status) {
        return res.data
      }
    } catch (error: any) {
      notifications.show({
        title: 'Error',
        message: error.message ?? error,
        color: 'red',
      })
    }
    return []
  }

  useEffect(() => {
    const fetchData = async () => {
      const resultTimeType = await getListMasterByType('TIME_TYPE')
      setDataTimeType(
        resultTimeType.filter((item: DataTimeType) => item.c_code !== 'ALL'),
      )

      const resultReason = await getListMasterByType('REASON')
      setDataReason(resultReason)
    }

    fetchData()
  }, [])

  const columns = [
    {
      name: 'id',
      size: '3%',
      header: 'ID',
    },
    {
      name: 'user_name',
      size: '17%',
      header: 'User',
    },
    {
      name: 'start_date',
      size: '26%',
      header: 'Time',
      render: (row: any) => {
        return (
          <Text fz={'sm'}>
            {row.startPeriodName}
            {' ('}
            {moment(row.start_date).format('DD/MM/YYYY')}
            {')'} - {row.endPeriodName}
            {' ('}
            {moment(row.end_date).format('DD/MM/YYYY')}
            {')'}
          </Text>
        )
      },
    },
    {
      name: 'typeReasonName',
      size: '10%',
      header: 'Reason',
    },
    {
      name: 'reason',
      size: '15%',
      header: 'Notes',
      render: (row: any) => {
        return (
          <HoverCard width={280} shadow="md">
            <HoverCard.Target>
              <Text fz={'sm'}>
                {row.reason !== null &&
                row.reason !== '' &&
                row.reason.length > 25
                  ? row.reason.slice(0, 25) + '...'
                  : row.reason}
              </Text>
            </HoverCard.Target>
            <HoverCard.Dropdown>
              <Textarea size="sm" autosize>
                {row.reason}
              </Textarea>
            </HoverCard.Dropdown>
          </HoverCard>
        )
      },
    },
    {
      name: 'status',
      size: '5%',
      header: 'Status',
      render: (row: any) => {
        switch (row.status) {
          case 'WAITING':
            return <Badge color="blue">Waiting</Badge>
          case 'CONFIRMED':
            return <Badge color="green">Confirmed</Badge>
          case 'REFUSED':
            return <Badge color="red">Refused</Badge>
          default:
            return null
        }
      },
    },
    {
      name: 'admin_note',
      size: '15%',
      header: 'Admin Notes',
      render: (row: any) => {
        return (
          <HoverCard width={280} shadow="md">
            <HoverCard.Target>
              <Text fz={'sm'}>
                {row.admin_note !== null &&
                row.admin_note !== '' &&
                row.admin_note.length > 25
                  ? row.admin_note.slice(0, 25) + '...'
                  : row.admin_note}
              </Text>
            </HoverCard.Target>
            <HoverCard.Dropdown>
              <Textarea size="sm" autosize>
                {row.admin_note}
              </Textarea>
            </HoverCard.Dropdown>
          </HoverCard>
        )
      },
    },
    {
      name: 'updated_by',
      size: '10%',
      header: 'Updated By',
    },
    {
      name: '#',
      size: '5%',
      header: 'Action',
      render: (row: any) => {
        return row.status === 'WAITING' ? (
          <Box className={classes.optionIcon}>
            <IconTrash
              className={classes.deleteIcon}
              onClick={() => {
                setAction('delete')
                setItem(row)
              }}
              width={20}
              height={20}
            />
          </Box>
        ) : null
      },
    },
  ]

  const filterInfo: FilterInfo[] = []

  const getAllTickets = async () => {
    try {
      const searchParams = new URLSearchParams(window.location.search)
      const params = {}

      for (const [key, value] of searchParams.entries()) {
        if (key === 'page' && value === '') {
          Object.assign(params, { [`${key}`]: 1 })
        } else {
          Object.assign(params, { [`${key}`]: value })
        }
      }

      const res = await get(getTicketsOfUser, params)
      if (res.status) {
        setListTiskets(res)
      }
    } catch (error: any) {
      notifications.show({
        title: 'Error',
        message: error.message ?? error,
        color: 'red',
      })
    }
  }

  const handleCreate = async (values: TTickets) => {
    try {
      const res = await create(
        addTicket,
        {
          // time_string: moment(values.time_string).format('YYYY-MM-DD HH:mm:ss'),
          start_date: moment(values.start_date).format('YYYY-MM-DD'),
          start_period: values.start_period,
          end_date: moment(values.end_date).format('YYYY-MM-DD'),
          end_period: values.end_period,
          type: values.type,
          reason: values.reason,
        },
        getAllTickets,
      )
      if (res === true) {
        setAction('')
        form.reset()
      }
    } catch (error) {
      console.log(error)
    }
  }

  const handleDelete = async (id: number) => {
    try {
      await Xdelete(deleteTicket, { ticket_id: id }, getAllTickets)
    } catch (error) {
      console.log(error)
    }
  }

  useEffect(() => {
    getAllTickets()
  }, [])

  const form = useForm({
    initialValues: {
      id: 0,
      start_date: new Date(),
      start_period: '',
      end_date: new Date(),
      end_period: '',
      type: '',
      reason: '',
    },
  })

  return (
    <div>
      <div className={classes.title}>
        <h3>
          Tickets
        </h3>
        <Button
          m={5}
          onClick={() => {
            setAction('add')
            form.reset()
          }}
        >
          + Add
        </Button>
      </div>
      <Box p={20}>
        {listTickets.data.length > 0 && (
          <DataTablePagination
            filterInfo={filterInfo}
            data={listTickets}
            columns={columns}
            searchInput
            size=""
          />
        )}
      </Box>
      {/* Add/Edit User modal */}
      <Modal
        opened={action === 'add' || action === 'edit'}
        onClose={() => {
          setAction('')
          form.reset()
        }}
        title={
          <Text pl={'sm'} fw={700} fz={'lg'}>
            {action === 'add' && 'Add Ticket'}
          </Text>
        }
      >
        <form
          onSubmit={form.onSubmit(async (values) => {
            setDisableBtn(true)
            action === 'add' && (await handleCreate(values))
            setDisableBtn(false)
          })}
        >
          <Box pl={'md'} pr={'md'}>
            <Box display={'flex'}>
              <Box style={{ display: 'flex', flexFlow: 'column' }} w={'40%'}>
                <DateInput
                  required
                  mb={'md'}
                  label={'From Date'}
                  value={new Date(form.values.start_date)}
                  valueFormat="DD/MM/YYYY"
                  onChange={(e) => form.setFieldValue('start_date', e!)}
                ></DateInput>

                <Select
                  required
                  mb={'md'}
                  label={'Start Period'}
                  data={dataTimeType.map((item) => {
                    return { value: item.c_code.toString(), label: item.c_name }
                  })}
                  value={form.values.start_period}
                  error={form.errors.start_period}
                  onChange={(e) => form.setFieldValue('start_period', e!)}
                />

                <Select
                  required
                  mb={'md'}
                  searchable
                  label="Type"
                  data={dataReason.map((user) => ({
                    value: user.c_code.toString(),
                    label: user.c_name,
                  }))}
                  value={form.values.type}
                  error={form.errors.type}
                  onChange={(e) => form.setFieldValue('type', e!)}
                />
              </Box>
              <Box
                style={{ display: 'flex', flexFlow: 'column' }}
                w={'20%'}
              ></Box>
              <Box style={{ display: 'flex', flexFlow: 'column' }} w={'40%'}>
                <DateInput
                  required
                  mb={'md'}
                  label={'End Date'}
                  value={new Date(form.values.end_date)}
                  valueFormat="DD/MM/YYYY"
                  onChange={(e) => form.setFieldValue('end_date', e!)}
                ></DateInput>
                <Select
                  required
                  mb={'md'}
                  label={'End Period'}
                  data={dataTimeType.map((item) => {
                    return { value: item.c_code.toString(), label: item.c_name }
                  })}
                  value={form.values.end_period}
                  error={form.errors.end_period}
                  onChange={(e) => form.setFieldValue('end_period', e!)}
                />
              </Box>
            </Box>

            <Textarea
              label="Reason"
              required
              value={form.values.reason}
              onChange={(e) => form.setFieldValue('reason', e.target.value)}
            />
            <Box ta={'center'}>
              {action === 'add' && (
                <Button
                  mt={'lg'}
                  bg={'green'}
                  type="submit"
                  disabled={disableBtn}
                >
                  Create
                </Button>
              )}
            </Box>
          </Box>
        </form>
      </Modal>

      <Dialog
        className={classes.dialog}
        opened={action === 'delete'}
        withCloseButton
        onClose={() => setAction('')}
        size="lg"
        radius="md"
        position={{ top: 30, right: 10 }}
      >
        <Text className={classes.dialogText} size="sm" mb="xs" fw={500}>
          Do you want to delete this record?
          <Group justify="center" m={10}>
            <Button
              disabled={activeBtn}
              fw={700}
              size="xs"
              variant="light"
              onClick={async () => {
                setActiveBtn(true)
                await handleDelete(item.id)
                setActiveBtn(false)
                setAction('')
              }}
            >
              Yes
            </Button>
            <Button
              fw={700}
              size="xs"
              variant="light"
              onClick={() => setAction('')}
            >
              Cancel
            </Button>
          </Group>
        </Text>
      </Dialog>
    </div>
  )
}

export default Tickets
