import { ReloadOutlined, SearchOutlined } from '@ant-design/icons'
import { useQuery } from '@tanstack/react-query'
import {
  Alert,
  Button,
  Card,
  Col,
  Form,
  Row,
  Select,
  Space,
  Statistic,
  Table,
  Tag,
  Typography,
} from 'antd'
import type { TableColumnsType } from 'antd'
import { useState } from 'react'

import { AdminRangePicker } from '@/components/admin/AdminDatePicker'
import PageHeader from '@/components/admin/PageHeader'
import dayjs from '@/lib/dayjs'
import { fetchAdminFinanceSummary, fetchAdminFinanceTransactions } from '@/services/admin'
import type {
  AdminFinanceChannelDailyItem,
  AdminFinanceDailyItem,
  AdminFinanceTransaction,
} from '@/types/admin/finance'
import { ADMIN_DEFAULT_PAGE_SIZE, buildAdminTablePagination } from '@/utils/admin-pagination'
import { formatAdminDateTime } from '@/utils/admin-time'
import { formatMoney } from './panels/shared'

type FinanceFilterForm = { dateRange?: unknown }

const CATEGORY_OPTIONS = [
  { value: '', label: '全部账目' },
  { value: 'order_paid', label: '订单收款' },
  { value: 'order_refund', label: '订单退款' },
  { value: 'worker_reward', label: '打手报酬' },
  { value: 'withdraw_paid', label: '打手提现' },
  { value: 'recharge', label: '打手充值' },
  { value: 'worker_recovery', label: '打手资金回收' },
  { value: 'after_sales_refund', label: '售后追缴退还' },
]

export default function AdminFinancePage() {
  const [form] = Form.useForm<FinanceFilterForm>()
  const [filters, setFilters] = useState({ dateFrom: '', dateTo: '' })
  const [category, setCategory] = useState('')
  const [channel, setChannel] = useState('')
  const [channelSummaryFilter, setChannelSummaryFilter] = useState('')
  const [page, setPage] = useState(1)
  const [pageSize, setPageSize] = useState(ADMIN_DEFAULT_PAGE_SIZE)

  const summaryQuery = useQuery({
    queryKey: ['admin-finance-summary', filters],
    queryFn: () => fetchAdminFinanceSummary(filters),
  })
  const transactionsQuery = useQuery({
    queryKey: ['admin-finance-transactions', filters, category, page, pageSize],
    queryFn: () =>
      fetchAdminFinanceTransactions({
        ...filters,
        category: category || undefined,
        channel: channel || undefined,
        page,
        pageSize,
      }),
  })
  const overview = summaryQuery.data?.data.overview
  const daily = summaryQuery.data?.data.daily || []
  const channelDaily = (summaryQuery.data?.data.channelDaily || []).filter(
    (item) => !channelSummaryFilter || item.channel === channelSummaryFilter,
  )
  const transactionData = transactionsQuery.data?.data

  function applyFilters(values: FinanceFilterForm) {
    const range = Array.isArray(values.dateRange) ? values.dateRange : []
    const dateFrom =
      range[0] && dayjs(range[0]).isValid() ? dayjs(range[0]).format('YYYY-MM-DD HH:mm:ss') : ''
    const dateTo =
      range[1] && dayjs(range[1]).isValid()
        ? dayjs(range[1]).second(59).format('YYYY-MM-DD HH:mm:ss')
        : ''
    setPage(1)
    setFilters({ dateFrom, dateTo })
  }

  function resetFilters() {
    form.resetFields()
    setCategory('')
    setChannel('')
    setChannelSummaryFilter('')
    setPage(1)
    setFilters({ dateFrom: '', dateTo: '' })
  }

  const dailyColumns: TableColumnsType<AdminFinanceDailyItem> = [
    { title: '日期', dataIndex: 'date', width: 120 },
    { title: '支付订单', dataIndex: 'paidOrderCount', width: 100 },
    { title: '收款', dataIndex: 'paidAmount', render: formatMoney },
    { title: '退款', dataIndex: 'refundAmount', render: formatMoney },
    { title: '打手报酬', dataIndex: 'workerRewardAmount', render: formatMoney },
    { title: '已提现', dataIndex: 'withdrawAmount', render: formatMoney },
    { title: '充值入账', dataIndex: 'rechargeAmount', render: formatMoney },
    { title: '售后退还', dataIndex: 'afterSalesRefundAmount', render: formatMoney },
    {
      title: '净现金流',
      dataIndex: 'netCashFlow',
      render: (value: number) => (
        <Typography.Text type={value >= 0 ? 'success' : 'danger'}>
          {formatMoney(value)}
        </Typography.Text>
      ),
    },
  ]

  const transactionColumns: TableColumnsType<AdminFinanceTransaction> = [
    {
      title: '发生时间',
      dataIndex: 'occurredAt',
      width: 180,
      render: (value) => formatAdminDateTime(value),
    },
    {
      title: '类型',
      dataIndex: 'label',
      width: 150,
      render: (value: string, row) => (
        <Tag color={row.direction === 'in' ? 'green' : 'orange'}>{value}</Tag>
      ),
    },
    { title: '渠道', dataIndex: 'channel', width: 150 },
    {
      title: '金额',
      dataIndex: 'amount',
      width: 140,
      render: (value: number, row) => (
        <Typography.Text type={row.direction === 'in' ? 'success' : 'danger'}>
          {row.direction === 'in' ? '+' : '-'}
          {formatMoney(value)}
        </Typography.Text>
      ),
    },
    { title: '来源编号', dataIndex: 'sourceId', width: 110 },
    {
      title: '关联单号/渠道',
      dataIndex: 'referenceNo',
      render: (value: string) => value || '-',
    },
  ]

  return (
    <section className="page-stack">
      <PageHeader title="财务" description="按日期查看订单收款、退款、打手结算和平台现金流。" />

      <Card>
        <Form<FinanceFilterForm>
          form={form}
          layout="inline"
          className="filter-form"
          onFinish={applyFilters}
        >
          <Form.Item name="dateRange" label="账务日期">
            <AdminRangePicker showTime={{ format: 'HH:mm' }} format="YYYY-MM-DD HH:mm" />
          </Form.Item>
          <Form.Item>
            <Space>
              <Button type="primary" icon={<SearchOutlined />} htmlType="submit">
                查询
              </Button>
              <Button onClick={resetFilters}>重置</Button>
            </Space>
          </Form.Item>
        </Form>
      </Card>

      {summaryQuery.error ? (
        <Alert
          type="error"
          showIcon
          message={
            summaryQuery.error instanceof Error ? summaryQuery.error.message : '读取财务汇总失败'
          }
        />
      ) : null}

      <Row gutter={[16, 16]}>
        <FinanceStatistic title="订单收款" value={overview?.paidAmount || 0} />
        <FinanceStatistic title="订单退款" value={overview?.refundAmount || 0} />
        <FinanceStatistic title="打手报酬" value={overview?.workerRewardAmount || 0} />
        <FinanceStatistic title="已确认提现" value={overview?.withdrawAmount || 0} />
        <FinanceStatistic title="净现金流" value={overview?.netCashFlow || 0} />
        <FinanceStatistic title="待提现" value={overview?.pendingWithdrawAmount || 0} />
      </Row>

      <Card
        title="每日账目"
        extra={
          <Button
            icon={<ReloadOutlined />}
            loading={summaryQuery.isFetching}
            onClick={() => void summaryQuery.refetch()}
          >
            刷新
          </Button>
        }
      >
        <Table<AdminFinanceDailyItem>
          rowKey="date"
          loading={summaryQuery.isLoading}
          dataSource={daily}
          columns={dailyColumns}
          pagination={false}
          scroll={{ x: 1080 }}
        />
      </Card>

      <Card
        title="渠道日报"
        extra={
          <Space wrap>
            <Select
              allowClear
              value={channelSummaryFilter || undefined}
              placeholder="全部渠道"
              style={{ width: 180 }}
              options={Array.from(
                new Set((summaryQuery.data?.data.channelDaily || []).map((item) => item.channel)),
              ).map((value) => ({ value, label: value }))}
              onChange={(value) => setChannelSummaryFilter(value || '')}
            />
            <Typography.Text type="secondary">按日期、渠道和账目类型汇总</Typography.Text>
          </Space>
        }
      >
        <Table<AdminFinanceChannelDailyItem>
          rowKey={(row) => `${row.date}-${row.channel}-${row.category}`}
          loading={summaryQuery.isLoading}
          dataSource={channelDaily}
          pagination={false}
          columns={[
            { title: '日期', dataIndex: 'date', width: 120 },
            { title: '渠道', dataIndex: 'channel', width: 180 },
            { title: '账目类型', dataIndex: 'category', width: 150, render: formatFinanceCategory },
            { title: '笔数', dataIndex: 'count', width: 90 },
            { title: '金额', dataIndex: 'amount', render: formatMoney },
          ]}
          scroll={{ x: 760 }}
        />
      </Card>

      <Card
        title="资金明细"
        extra={
          <Space wrap>
            <Select
              value={category}
              options={CATEGORY_OPTIONS}
              style={{ width: 160 }}
              onChange={(value) => {
                setCategory(value)
                setPage(1)
              }}
            />
            <Select
              allowClear
              value={channel || undefined}
              placeholder="全部渠道"
              style={{ width: 180 }}
              options={Array.from(
                new Set((summaryQuery.data?.data.channelDaily || []).map((item) => item.channel)),
              ).map((value) => ({ value, label: value }))}
              onChange={(value) => {
                setChannel(value || '')
                setPage(1)
              }}
            />
            <Button
              icon={<ReloadOutlined />}
              loading={transactionsQuery.isFetching}
              onClick={() => void transactionsQuery.refetch()}
            >
              刷新
            </Button>
          </Space>
        }
      >
        <Table<AdminFinanceTransaction>
          rowKey={(row) => `${row.category}-${row.sourceId}-${row.occurredAt}`}
          loading={transactionsQuery.isLoading}
          dataSource={transactionData?.items || []}
          columns={transactionColumns}
          pagination={buildAdminTablePagination({
            current: transactionData?.pagination.page || page,
            pageSize: transactionData?.pagination.pageSize || pageSize,
            total: transactionData?.pagination.total || 0,
            onChange: (nextPage, nextPageSize) => {
              setPage(nextPage)
              setPageSize(nextPageSize)
            },
          })}
          scroll={{ x: 780 }}
        />
      </Card>
    </section>
  )
}

function formatFinanceCategory(value: string) {
  return CATEGORY_OPTIONS.find((item) => item.value === value)?.label || value || '-'
}

function FinanceStatistic({ title, value }: { title: string; value: number }) {
  return (
    <Col xs={24} sm={12} xl={8}>
      <Card>
        <Statistic title={title} value={formatMoney(value)} />
      </Card>
    </Col>
  )
}
