import { useState, useMemo, useEffect, useCallback, CSSProperties } from 'react';
import { Card, Row, Col, Statistic, Table, Button, Input, Select, DatePicker, Modal, Descriptions, Form, Typography, message, Space, Tag } from 'antd';
import { ArrowLeftOutlined } from '@ant-design/icons';
import { request } from '../api/client';
import { useNavigate } from 'react-router-dom';
import { ROUTES } from '../router/routes.constant';

type ReservationStatus = 'PENDING' | 'READY' | 'FULFILLED' | 'CANCELLED' | 'EXPIRED';

interface ReservationResponse {
  id: string;
  book_id: string;
  member_id: string;
  reservation_date: string;
  expiry_date: string | null;
  queue_position: number;
  status: ReservationStatus;
  notified_date: string | null;
  created_at: string;
  updated_at: string;
}

interface BookDetail {
  id: string;
  title: string;
  isbn: string | null;
}

interface MemberDetail {
  id: string;
  user_id: string;
  membership_number: string;
}

interface ReservationDetailResponse {
  id: string;
  book: BookDetail;
  member: MemberDetail;
  reservation_date: string;
  expiry_date: string | null;
  queue_position: number;
  status: ReservationStatus;
  notified_date: string | null;
  created_at: string;
  updated_at: string;
}

interface PaginationState {
  current: number;
  pageSize: number;
  total: number;
}

export default function ReservationsListPage() {
  const [messageApi, contextHolder] = message.useMessage();
  const navigate = useNavigate();
  const [form] = Form.useForm();

  const [reservations, setReservations] = useState<ReservationResponse[]>([]);
  const [loading, setLoading] = useState<boolean>(false);
  const [filterStatus, setFilterStatus] = useState<string>('');
  const [searchBook, setSearchBook] = useState<string>('');
  const [searchMember, setSearchMember] = useState<string>('');
  const [dateRange, setDateRange] = useState<[string, string] | []>([]);
  const [pagination, setPagination] = useState<PaginationState>({
    current: 1,
    pageSize: 20,
    total: 0,
  });
  const [detailModalVisible, setDetailModalVisible] = useState<boolean>(false);
  const [cancelModalVisible, setCancelModalVisible] = useState<boolean>(false);
  const [selectedReservation, setSelectedReservation] = useState<ReservationDetailResponse | null>(null);
  const [totalActive, setTotalActive] = useState<number>(0);
  const [readyForPickup, setReadyForPickup] = useState<number>(0);
  const [expiredToday, setExpiredToday] = useState<number>(0);

  const fetchReservations = useCallback(async () => {
    setLoading(true);
    try {
      const queryParams: Record<string, string | number> = {
        limit: pagination.pageSize,
        offset: (pagination.current - 1) * pagination.pageSize,
      };
      if (filterStatus) {
        queryParams.reservation_status = filterStatus;
      }
      if (searchBook) {
        queryParams.book_id = searchBook;
      }
      if (searchMember) {
        queryParams.member_id = searchMember;
      }

      const result = await request<ReservationResponse[]>({
        method: 'GET',
        path: '/circulation/reservations',
        query: queryParams,
      });

      setReservations(result.data);
      setPagination((prev) => ({ ...prev, total: result.data.length }));

      const activeCount = result.data.filter((r) => r.status === 'PENDING' || r.status === 'READY').length;
      const readyCount = result.data.filter((r) => r.status === 'READY').length;
      const expiredCount = result.data.filter((r) => {
        if (r.expiry_date) {
          const today = new Date().toISOString().split('T')[0];
          return r.expiry_date.split('T')[0] === today && r.status === 'EXPIRED';
        }
        return false;
      }).length;

      setTotalActive(activeCount);
      setReadyForPickup(readyCount);
      setExpiredToday(expiredCount);
    } catch (error) {
      messageApi.error('Failed to load reservations');
    } finally {
      setLoading(false);
    }
  }, [pagination.current, pagination.pageSize, filterStatus, searchBook, searchMember, messageApi]);

  useEffect(() => {
    fetchReservations();
  }, [fetchReservations]);

  const viewDetails = useCallback(async (record: ReservationResponse) => {
    setSelectedReservation({ ...record, book: { id: '', title: '', isbn: null }, member: { id: '', user_id: '', membership_number: '' } } as ReservationDetailResponse);
    setDetailModalVisible(true);
    try {
      const result = await request<ReservationDetailResponse>({
        method: 'GET',
        path: '/circulation/reservations/{reservation_id}/details',
        pathParams: { reservation_id: record.id },
      });
      setSelectedReservation(result.data);
    } catch (error) {
      messageApi.error('Failed to load reservation details');
    }
  }, [messageApi]);

  const openCancelModal = useCallback((record: ReservationResponse) => {
    setSelectedReservation({ ...record, book: { id: '', title: '', isbn: null }, member: { id: '', user_id: '', membership_number: '' } } as ReservationDetailResponse);
    setCancelModalVisible(true);
  }, []);

  const confirmCancelReservation = useCallback(async () => {
    if (!selectedReservation) return;

    try {
      await form.validateFields();
      await request<ReservationResponse>({
        method: 'POST',
        path: '/circulation/reservations/{reservation_id}/cancel',
        pathParams: { reservation_id: selectedReservation.id },
      });
      messageApi.success('Reservation cancelled successfully');
      setCancelModalVisible(false);
      form.resetFields();
      fetchReservations();
    } catch (error) {
      messageApi.error('Failed to cancel reservation');
    }
  }, [selectedReservation, form, messageApi, fetchReservations]);

  const processPickup = useCallback((record: ReservationResponse) => {
    Modal.confirm({
      title: 'Process Pickup',
      content: 'Are you sure you want to process pickup for this reservation?',
      onOk: () => {
        navigate(ROUTES.CIRCULATION_CHECKOUT);
      },
    });
  }, [navigate]);

  const navigateToDashboard = useCallback(() => {
    navigate(ROUTES.LIBRARIAN_DASHBOARD);
  }, [navigate]);

  const closeDetailModal = useCallback(() => {
    setDetailModalVisible(false);
    setSelectedReservation(null);
  }, []);

  const closeCancelModal = useCallback(() => {
    setCancelModalVisible(false);
    form.resetFields();
  }, [form]);

  const handleStatusFilterChange = useCallback((value: string) => {
    setFilterStatus(value || '');
    setPagination((prev) => ({ ...prev, current: 1 }));
  }, []);

  const handleBookSearchChange = useCallback((e: React.ChangeEvent<HTMLInputElement>) => {
    setSearchBook(e.target.value);
    setPagination((prev) => ({ ...prev, current: 1 }));
  }, []);

  const handleMemberSearchChange = useCallback((e: React.ChangeEvent<HTMLInputElement>) => {
    setSearchMember(e.target.value);
    setPagination((prev) => ({ ...prev, current: 1 }));
  }, []);

  const handleTableChange = useCallback((paginationConfig: { current?: number; pageSize?: number }) => {
    setPagination((prev) => ({
      ...prev,
      current: paginationConfig.current || prev.current,
      pageSize: paginationConfig.pageSize || prev.pageSize,
    }));
  }, []);

  const getStatusColor = (status: ReservationStatus): string => {
    const colorMap: Record<ReservationStatus, string> = {
      PENDING: 'blue',
      READY: 'green',
      FULFILLED: 'cyan',
      CANCELLED: 'default',
      EXPIRED: 'red',
    };
    return colorMap[status];
  };

  const columns = useMemo(() => [
    {
      title: 'Reservation ID',
      dataIndex: 'id',
      key: 'id',
      width: 120,
      ellipsis: true,
    },
    {
      title: 'Book',
      dataIndex: 'book_id',
      key: 'book_id',
    },
    {
      title: 'Member',
      dataIndex: 'member_id',
      key: 'member_id',
    },
    {
      title: 'Reservation Date',
      dataIndex: 'reservation_date',
      key: 'reservation_date',
      sorter: true,
      render: (date: string) => date ? new Date(date).toLocaleDateString() : '-',
    },
    {
      title: 'Queue Position',
      dataIndex: 'queue_position',
      key: 'queue_position',
      width: 100,
      align: 'center' as const,
    },
    {
      title: 'Status',
      dataIndex: 'status',
      key: 'status',
      width: 140,
      render: (status: ReservationStatus) => (
        <Tag color={getStatusColor(status)}>{status}</Tag>
      ),
    },
    {
      title: 'Expiry Date',
      dataIndex: 'expiry_date',
      key: 'expiry_date',
      render: (date: string | null) => date ? new Date(date).toLocaleDateString() : '-',
    },
    {
      title: 'Actions',
      key: 'actions',
      width: 220,
      fixed: 'right' as const,
      render: (_: unknown, record: ReservationResponse) => (
        <Space size="small">
          <Button type="link" size="small" onClick={() => viewDetails(record)}>
            View Details
          </Button>
          <Button type="link" size="small" danger onClick={() => openCancelModal(record)}>
            Cancel
          </Button>
          {record.status === 'READY' && (
            <Button type="link" size="small" onClick={() => processPickup(record)}>
              Process Pickup
            </Button>
          )}
        </Space>
      ),
    },
  ], [viewDetails, openCancelModal, processPickup]);

  const rootStyle: CSSProperties = {
    minHeight: '100vh',
    height: '100%',
    width: '100%',
    display: 'flex',
    flexDirection: 'column',
    padding: '24px',
    background: '#f5f5f5',
  };

  return (
    <div style={rootStyle}>
      {contextHolder}
      <div style={{ display: 'flex', justifyContent: 'space-between', alignItems: 'center', marginBottom: '24px' }}>
        <div style={{ display: 'flex', alignItems: 'center', gap: '12px' }}>
          <Button type="text" icon={<ArrowLeftOutlined />} onClick={navigateToDashboard}>
            Back to Dashboard
          </Button>
          <Typography.Title level={3} style={{ margin: 0 }}>
            Reservations Management
          </Typography.Title>
        </div>
      </div>

      <Row gutter={[16, 16]} style={{ marginBottom: '24px' }}>
        <Col xs={24} sm={8}>
          <Card size="small">
            <Statistic
              title="Total Active Reservations"
              value={totalActive}
              valueStyle={{ color: '#1677ff' }}
            />
          </Card>
        </Col>
        <Col xs={24} sm={8}>
          <Card size="small">
            <Statistic
              title="Ready for Pickup"
              value={readyForPickup}
              valueStyle={{ color: '#52c41a' }}
            />
          </Card>
        </Col>
        <Col xs={24} sm={8}>
          <Card size="small">
            <Statistic
              title="Expired Today"
              value={expiredToday}
              valueStyle={{ color: '#ff4d4f' }}
            />
          </Card>
        </Col>
      </Row>

      <Card size="small" style={{ marginBottom: '16px' }}>
        <Row gutter={[16, 16]} align="middle">
          <Col xs={24} sm={12} md={6}>
            <Select
              placeholder="Filter by status"
              allowClear
              value={filterStatus || undefined}
              onChange={handleStatusFilterChange}
              style={{ width: '100%' }}
              options={[
                { label: 'Pending', value: 'PENDING' },
                { label: 'Ready', value: 'READY' },
                { label: 'Fulfilled', value: 'FULFILLED' },
                { label: 'Cancelled', value: 'CANCELLED' },
                { label: 'Expired', value: 'EXPIRED' },
              ]}
            />
          </Col>
          <Col xs={24} sm={12} md={6}>
            <Input.Search
              placeholder="Search by book title or ID"
              allowClear
              value={searchBook}
              onChange={handleBookSearchChange}
            />
          </Col>
          <Col xs={24} sm={12} md={6}>
            <Input.Search
              placeholder="Search by member name or ID"
              allowClear
              value={searchMember}
              onChange={handleMemberSearchChange}
            />
          </Col>
          <Col xs={24} sm={12} md={6}>
            <DatePicker.RangePicker
              style={{ width: '100%' }}
              placeholder={['Start Date', 'End Date']}
            />
          </Col>
        </Row>
      </Card>

      <Card bodyStyle={{ padding: 0 }}>
        <Table
          rowKey="id"
          dataSource={reservations}
          columns={columns}
          loading={loading}
          pagination={{
            current: pagination.current,
            pageSize: pagination.pageSize,
            total: pagination.total,
            showSizeChanger: true,
            showTotal: (total) => `Total ${total} items`,
          }}
          onChange={handleTableChange}
        />
      </Card>

      <Modal
        title="Reservation Details"
        open={detailModalVisible}
        onCancel={closeDetailModal}
        footer={null}
        width={640}
      >
        {selectedReservation && (
          <Descriptions bordered column={2}>
            <Descriptions.Item label="Reservation ID" span={2}>
              {selectedReservation.id}
            </Descriptions.Item>
            <Descriptions.Item label="Status" span={2}>
              <Tag color={getStatusColor(selectedReservation.status)}>
                {selectedReservation.status}
              </Tag>
            </Descriptions.Item>
            <Descriptions.Item label="Book" span={2}>
              {selectedReservation.book?.title || selectedReservation.book_id}
            </Descriptions.Item>
            <Descriptions.Item label="Member" span={2}>
              {selectedReservation.member?.membership_number || selectedReservation.member_id}
            </Descriptions.Item>
            <Descriptions.Item label="Reservation Date">
              {selectedReservation.reservation_date ? new Date(selectedReservation.reservation_date).toLocaleString() : '-'}
            </Descriptions.Item>
            <Descriptions.Item label="Expiry Date">
              {selectedReservation.expiry_date ? new Date(selectedReservation.expiry_date).toLocaleString() : '-'}
            </Descriptions.Item>
            <Descriptions.Item label="Queue Position">
              {selectedReservation.queue_position}
            </Descriptions.Item>
            <Descriptions.Item label="Notified Date">
              {selectedReservation.notified_date ? new Date(selectedReservation.notified_date).toLocaleString() : '-'}
            </Descriptions.Item>
            <Descriptions.Item label="Created At">
              {selectedReservation.created_at ? new Date(selectedReservation.created_at).toLocaleString() : '-'}
            </Descriptions.Item>
            <Descriptions.Item label="Updated At">
              {selectedReservation.updated_at ? new Date(selectedReservation.updated_at).toLocaleString() : '-'}
            </Descriptions.Item>
          </Descriptions>
        )}
      </Modal>

      <Modal
        title="Cancel Reservation"
        open={cancelModalVisible}
        onCancel={closeCancelModal}
        onOk={confirmCancelReservation}
        okText="Confirm Cancel"
        okButtonProps={{ danger: true }}
        width={480}
      >
        <Form form={form} layout="vertical">
          <Form.Item
            label="Cancellation Reason"
            name="reason"
            rules={[{ required: true, message: 'Please provide a reason for cancellation' }]}
          >
            <Input.TextArea
              rows={4}
              placeholder="Enter reason for cancelling this reservation..."
            />
          </Form.Item>
        </Form>
      </Modal>
    </div>
  );
}