import React, { useMemo, useState } from 'react'

import { Flex, Input, Select, Space, TextInput } from '@mantine/core'
import { useId } from '@mantine/hooks'
import { IconSearch } from '@tabler/icons-react'
import dayjs from 'dayjs'

import DatePicker from '~/components/DatePicker'
import { useQueryParams } from '~/hooks/use-query-params'
import { historicalEventTelemetry } from '~/telemetry/event-center'

import { SeveritySelect } from '../shared/components/SeveritySelect'
import { Severity } from '../shared/types'
import { HistoryTable } from './HistoryTable/HistoryTable'
import { useLoadmore } from './HistoryTable/useLoadmore'

const HistoryEventPage: React.FC = () => {
  const { queryParams, setQueryParams } = useQueryParams({
    name: '',
    from: DEFAULT_RELATIVE_TIMERANGE,
    to: 'now',
    severity: Severity.Info
  })
  const { from, to } = getTimeRangeValue(queryParams.from, queryParams.to)
  const { dataList, loading, partial, loadmore } = useLoadmore({
    name: queryParams.name,
    severity: queryParams.severity,
    from,
    to
  })
  const [name, setName] = useState(queryParams.name)

  return (
    <>
      <Flex>
        <TextInput
          label='Event Name'
          placeholder='Search Event Name'
          rightSection={<IconSearch size={14} color='gray' />}
          disabled={loading}
          value={name}
          onChange={(e) => setName(e.currentTarget.value || '')}
          onKeyPress={(e) => {
            if (e.code === 'Enter') {
              setQueryParams({ name: e.currentTarget.value })
              loadmore(true)
              historicalEventTelemetry.searchEvent(e.currentTarget.value)
            }
          }}
        />
        <Space w='md' />
        <SeveritySelect
          value={queryParams.severity}
          onChange={(v) => {
            setQueryParams({ severity: v })
            loadmore(true)
            historicalEventTelemetry.changeSeverity(v as any)
          }}
        />
        <Space w='md' />
        <TimeRange
          loading={loading}
          from={queryParams.from}
          to={queryParams.to}
          onChange={(from, to) => {
            setQueryParams({ from, to })
            loadmore(true)
            historicalEventTelemetry.changeTimeRange(from, to)
          }}
        />
      </Flex>

      <Space h='xl' />

      <HistoryTable
        data={dataList}
        loading={loading}
        partial={partial}
        loadmore={loadmore}
      />
    </>
  )
}

const DEFAULT_RELATIVE_TIMERANGE = `${30 * 24 * 60 * 60}`

const TIMERANGE_SELECTIONS: { value: string; label: string }[] = [
  { value: DEFAULT_RELATIVE_TIMERANGE, label: 'Last 30 days' },
  { value: 'absolute', label: 'Absolute' }
]

const TimeRange = ({
  loading,
  from,
  to,
  onChange
}: {
  loading: boolean
  from: string
  to: string
  onChange: (from: string, to: string) => void
}) => {
  const id = useId()
  const isRelative = to === 'now'
  const selectionValue = isRelative ? from : 'absolute'
  const dayjsRange = useMemo<[dayjs.Dayjs, dayjs.Dayjs]>(() => {
    const _from = dayjs(parseInt(from) * 1000)
    const _to = dayjs(parseInt(to) * 1000)
    return [_from, _to]
  }, [from, to])

  return (
    <>
      <Select
        label='Time Range'
        disabled={loading}
        data={TIMERANGE_SELECTIONS}
        value={selectionValue}
        onChange={(v) => {
          if (v === 'absolute') {
            const { from, to } = getTimeRangeValue(
              DEFAULT_RELATIVE_TIMERANGE,
              'now'
            )
            onChange(from, to)
          } else {
            onChange(v!, 'now')
          }
        }}
      />
      {!isRelative && (
        <>
          <Space w='md' />
          <Input.Wrapper
            id={id}
            label='Absolute Range'
            className='flex flex-col'
          >
            <DatePicker.RangePicker
              showTime={{ format: 'HH:mm' }}
              format='YYYY-MM-DD HH:mm'
              className='rounded-[8px] h-9 border-[#ced4da]'
              disabled={loading}
              value={dayjsRange}
              allowClear={false}
              onChange={(v) => {
                const unixValue = v?.map((d) => `${d?.unix()}`)!
                onChange(unixValue[0], unixValue[1])
              }}
            />
          </Input.Wrapper>
        </>
      )}
    </>
  )
}

const getTimeRangeValue = (from: string, to: string) => {
  const isRelative = to === 'now'
  const fromInt = parseInt(from)
  const toValue = isRelative ? Date.now() / 1000 : parseInt(to)
  const fromValue = isRelative ? toValue - fromInt : fromInt
  return {
    from: fromValue.toFixed(0),
    to: toValue.toFixed(0)
  }
}

export default HistoryEventPage
