import {
  Button,
  Form,
  Input,
  InputNumber,
  Popconfirm,
  Space,
  Table,
  Switch
} from 'antd'
import { ColumnsType } from 'antd/lib/table'
import React, { useState } from 'react'

import {
  createCreditRiskLevel,
  deleteCreditRiskLevel,
  updateCreditRiskLevel,
  updateCreditRiskLevelCostQuota,
  useListAllCreditRiskLevel
} from 'apiClient/api'
import {
  FormsCostQuota,
  FormsCreditRiskLevel,
  FormsCreditRiskLevelInputBody
} from 'apiClient/api/interface'
import ModalForm from 'components/ModalForm'
import { ListToolBar } from 'components/Table'
import { toFixed } from 'utils/number'

type CostQuotaInput = FormsCostQuota & {
  unlimited?: boolean
}

const isUnlimited = (limit?: string) => {
  if (limit === '-1') {
    return true
  }
  return false
}

const CostQuotaForm: React.FC<
  React.PropsWithChildren<{
    onComplete?: () => {}
    initValues?: CostQuotaInput
    trigger?: React.ReactElement
    riskLevelID: string
  }>
> = ({ onComplete, initValues, trigger, riskLevelID }) => {
  const [visible, setVisible] = useState(false)
  const [unlimited, setUnlimited] = useState(initValues?.unlimited || false)

  const handleSubmit = async (data: CostQuotaInput) => {
    await updateCreditRiskLevelCostQuota(riskLevelID, {
      cost_quota_limit: data.unlimited
        ? '-1'
        : toFixed(data.cost_quota_limit || '0')
    })
    onComplete?.()
    setVisible(false)
  }

  const Trigger = trigger ? (
    React.cloneElement(trigger, {
      onClick: () => {
        setVisible(true)
      }
    })
  ) : (
    <Button type="link" onClick={() => setVisible(true)}>
      Update Quota
    </Button>
  )

  const getFields = () => {
    return (
      <>
        <Form.Item label="Unlimited" name="unlimited" valuePropName="checked">
          <Switch
            checkedChildren="Yes"
            unCheckedChildren="No"
            onChange={(value) => setUnlimited(value)}
          />
        </Form.Item>
        <Form.Item
          name="cost_quota_limit"
          label="Quota Limit"
          rules={[
            ({ getFieldValue }) => ({
              validator(rule, value: number) {
                if (!unlimited) {
                  if (value <= 0) {
                    return Promise.reject(
                      new Error('Limit should be greater than 0')
                    )
                  }
                  if (!value) {
                    return Promise.reject(new Error('Required'))
                  }
                }
                return Promise.resolve()
              }
            })
          ]}
        >
          <InputNumber<string>
            disabled={unlimited}
            min="0"
            step="0.01"
            style={{ display: 'inline-block', width: '90%' }}
          ></InputNumber>
        </Form.Item>
      </>
    )
  }

  return (
    <div>
      {Trigger}
      <ModalForm
        initValues={{ ...initValues }}
        name="risk-level-form"
        title={'Update Quota'}
        visible={visible}
        onSubmit={handleSubmit}
        getFields={getFields}
        onCancel={() => setVisible(false)}
      ></ModalForm>
    </div>
  )
}

const RiskLevelForm: React.FC<
  React.PropsWithChildren<{
    onComplete?: () => {}
    initValues?: FormsCreditRiskLevel
    type: 'add' | 'edit'
    trigger?: React.ReactElement
    title?: string
  }>
> = ({
  onComplete,
  initValues,
  type = 'add',
  trigger,
  title = 'New Risk Level'
}) => {
  const [visible, setVisible] = useState(false)

  const handleSubmit = async (data: FormsCreditRiskLevelInputBody) => {
    if (type === 'add') {
      await createCreditRiskLevel(data)
    } else {
      await updateCreditRiskLevel(
        initValues?.credit_risk_level_id.toString() || '',
        {
          ...data
        }
      )
    }
    onComplete?.()
    setVisible(false)
  }

  const Trigger = trigger ? (
    React.cloneElement(trigger, {
      onClick: () => {
        setVisible(true)
      }
    })
  ) : (
    <Button type="primary" onClick={() => setVisible(true)}>
      New Risk Level
    </Button>
  )

  const getFields = () => {
    return (
      <>
        <Form.Item
          name="credit_risk_level_name"
          label="Name"
          rules={[{ required: true, message: 'required' }]}
        >
          <Input></Input>
        </Form.Item>
      </>
    )
  }

  return (
    <div>
      {Trigger}
      <ModalForm
        initValues={initValues}
        name="risk-level-form"
        title={title}
        visible={visible}
        onSubmit={handleSubmit}
        getFields={getFields}
        onCancel={() => setVisible(false)}
      ></ModalForm>
    </div>
  )
}

export const RiskLevelPanel = () => {
  const { data, refetch, isLoading, isRefetching } = useListAllCreditRiskLevel({
    query: {
      refetchInterval: 2 * 60 * 1000
    }
  })

  const handleDelete = async (levelId: number) => {
    await deleteCreditRiskLevel(levelId.toString())
    refetch()
  }

  const columns: ColumnsType<FormsCreditRiskLevel> = [
    {
      title: 'Risk Level ID',
      dataIndex: 'credit_risk_level_id'
    },
    {
      title: 'Name',
      dataIndex: 'credit_risk_level_name'
    },
    {
      title: 'Risk Cost Quota',
      dataIndex: 'action',
      render: (_: any, record: FormsCreditRiskLevel) => {
        const limit = record.cost_quota?.cost_quota_limit
        return isUnlimited(limit) ? 'Unlimited' : limit
      }
    },
    {
      title: 'Action',
      dataIndex: 'action',
      render: (_: any, record: FormsCreditRiskLevel) => {
        return (
          <Space size="middle">
            <RiskLevelForm
              trigger={<a>Update Name</a>}
              type="edit"
              initValues={record}
              title="Update Risk Level"
              onComplete={refetch}
            ></RiskLevelForm>
            <CostQuotaForm
              onComplete={refetch}
              riskLevelID={record.credit_risk_level_id.toString()}
              initValues={{
                ...record.cost_quota,
                unlimited: isUnlimited(record.cost_quota?.cost_quota_limit)
              }}
            ></CostQuotaForm>
            <Popconfirm
              title="Sure to delete?"
              onConfirm={() => handleDelete(record.credit_risk_level_id)}
            >
              <Button type="link" danger>
                Delete
              </Button>
            </Popconfirm>
          </Space>
        )
      }
    }
  ]
  return (
    <div>
      <ListToolBar
        reload={async () => {
          await refetch()
        }}
        actions={[<RiskLevelForm onComplete={refetch} type="add" />]}
      ></ListToolBar>
      <Table
        columns={columns}
        loading={isLoading || isRefetching}
        dataSource={data?.data}
        rowKey="credit_risk_level_id"
      ></Table>
    </div>
  )
}
