import React, { useState, useEffect } from 'react';
import { X, Plus, Trash2, Calendar, DollarSign, FileText, Building2, Loader2 } from 'lucide-react';
import groupBookingService from '../../bookings/services/groupBookingService';
import roomService, { Room } from '../../rooms/services/roomService';
import { toast } from 'react-toastify';
import { useFormatCurrency } from '../../payments/hooks/useFormatCurrency';
import DatePicker from 'react-datepicker';
import 'react-datepicker/dist/react-datepicker.css';

interface RoomBlock {
  room_type_id: number;
  num_rooms: number;
  rate_per_room: number;
}

interface CreateGroupBookingModalProps {
  isOpen: boolean;
  onClose: () => void;
  onSuccess: () => void;
}

const CreateGroupBookingModal: React.FC<CreateGroupBookingModalProps> = ({
  isOpen,
  onClose,
  onSuccess,
}) => {
  const { formatCurrency } = useFormatCurrency();
  const [loading, setLoading] = useState(false);
  const [loadingRoomTypes, setLoadingRoomTypes] = useState(false);
  
  // Form state
  const [checkInDate, setCheckInDate] = useState<Date | null>(null);
  const [checkOutDate, setCheckOutDate] = useState<Date | null>(null);
  const [groupName, setGroupName] = useState('');
  const [groupType, setGroupType] = useState('');
  const [roomBlocks, setRoomBlocks] = useState<RoomBlock[]>([]);
  const [paymentOption, setPaymentOption] = useState<'coordinator_pays_all' | 'individual_payments' | 'split_payment'>('coordinator_pays_all');
  const [depositRequired, setDepositRequired] = useState(false);
  const [depositPercentage, setDepositPercentage] = useState<number>(20);
  const [specialRequests, setSpecialRequests] = useState('');
  const [notes, setNotes] = useState('');
  const [cancellationPolicy, setCancellationPolicy] = useState('');
  const [cancellationDeadline, setCancellationDeadline] = useState<Date | null>(null);
  const [cancellationPenaltyPercentage, setCancellationPenaltyPercentage] = useState<number>(0);
  const [groupDiscountPercentage, setGroupDiscountPercentage] = useState<number | undefined>(undefined);
  
  // Room types
  const [roomTypes, setRoomTypes] = useState<Array<{ id: number; name: string; base_price: number }>>([]);
  useState<Room[]>([]);
  
  // Pricing summary
  const [pricingSummary, setPricingSummary] = useState<{
    originalTotal: number;
    discountAmount: number;
    totalPrice: number;
    discountPercentage: number;
  } | null>(null);

  // Fetch room types
  useEffect(() => {
    const fetchRoomTypes = async () => {
      try {
        setLoadingRoomTypes(true);
        const response = await roomService.getRooms({ limit: 100, page: 1 });
        const uniqueRoomTypes = new Map<number, { id: number; name: string; base_price: number }>();
        
        response.data.rooms.forEach((room: Room) => {
          if (room.room_type && !uniqueRoomTypes.has(room.room_type.id)) {
            uniqueRoomTypes.set(room.room_type.id, {
              id: room.room_type.id,
              name: room.room_type.name,
              base_price: room.room_type.base_price,
            });
          }
        });
        
        // Fetch additional pages if needed
        if (response.data.pagination && response.data.pagination.totalPages > 1) {
          const totalPages = response.data.pagination.totalPages;
          for (let page = 2; page <= totalPages; page++) {
            try {
              const pageResponse = await roomService.getRooms({ limit: 100, page });
              pageResponse.data.rooms.forEach((room: Room) => {
                if (room.room_type && !uniqueRoomTypes.has(room.room_type.id)) {
                  uniqueRoomTypes.set(room.room_type.id, {
                    id: room.room_type.id,
                    name: room.room_type.name,
                    base_price: room.room_type.base_price,
                  });
                }
              });
            } catch (err) {
              console.error(`Failed to fetch page ${page}:`, err);
            }
          }
        }
        
        setRoomTypes(Array.from(uniqueRoomTypes.values()));
      } catch (error: unknown) {
        console.error('Error fetching room types:', error);
        toast.error('Failed to load room types');
      } finally {
        setLoadingRoomTypes(false);
      }
    };

    if (isOpen) {
      fetchRoomTypes();
    }
  }, [isOpen]);

  // Calculate pricing when room blocks or dates change
  useEffect(() => {
    if (roomBlocks.length > 0 && checkInDate && checkOutDate) {
      calculatePricing();
    } else {
      setPricingSummary(null);
    }
  // eslint-disable-next-line react-hooks/exhaustive-deps
  }, [roomBlocks, checkInDate, checkOutDate, groupDiscountPercentage]);

  const calculatePricing = () => {
    if (!checkInDate || !checkOutDate || roomBlocks.length === 0) return;

    const nights = Math.ceil((checkOutDate.getTime() - checkInDate.getTime()) / (1000 * 60 * 60 * 24));
    if (nights <= 0) return;

    let originalTotal = 0;
    roomBlocks.forEach(block => {
      originalTotal += block.rate_per_room * block.num_rooms * nights;
    });

    // Calculate discount
    const totalRooms = roomBlocks.reduce((sum, block) => sum + block.num_rooms, 0);
    let discountPercentage = groupDiscountPercentage;
    
    if (discountPercentage === undefined) {
      // Auto-calculate based on room count
      if (totalRooms >= 20) {
        discountPercentage = 15;
      } else if (totalRooms >= 10) {
        discountPercentage = 10;
      } else if (totalRooms >= 5) {
        discountPercentage = 5;
      } else {
        discountPercentage = 0;
      }
    }

    const discountAmount = originalTotal * (discountPercentage / 100);
    const totalPrice = originalTotal - discountAmount;

    setPricingSummary({
      originalTotal,
      discountAmount,
      totalPrice,
      discountPercentage,
    });
  };

  const addRoomBlock = () => {
    if (roomTypes.length === 0) {
      toast.error('Please wait for room types to load');
      return;
    }
    
    const firstRoomType = roomTypes[0];
    setRoomBlocks([
      ...roomBlocks,
      {
        room_type_id: firstRoomType.id,
        num_rooms: 1,
        rate_per_room: firstRoomType.base_price,
      },
    ]);
  };

  const removeRoomBlock = (index: number) => {
    setRoomBlocks(roomBlocks.filter((_, i) => i !== index));
  };

  const updateRoomBlock = (index: number, field: keyof RoomBlock, value: number) => {
    const updated = [...roomBlocks];
    updated[index] = { ...updated[index], [field]: value };
    
    // Auto-fill rate if room type changes
    if (field === 'room_type_id') {
      const roomType = roomTypes.find(rt => rt.id === value);
      if (roomType) {
        updated[index].rate_per_room = roomType.base_price;
      }
    }
    
    setRoomBlocks(updated);
  };

  const handleSubmit = async (e: React.FormEvent) => {
    e.preventDefault();

    if (!checkInDate || !checkOutDate) {
      toast.error('Please select check-in and check-out dates');
      return;
    }

    if (checkInDate >= checkOutDate) {
      toast.error('Check-out date must be after check-in date');
      return;
    }

    if (roomBlocks.length === 0) {
      toast.error('Please add at least one room block');
      return;
    }

    if (roomBlocks.some(block => block.num_rooms <= 0)) {
      toast.error('Number of rooms must be greater than 0');
      return;
    }

    try {
      setLoading(true);

      const bookingData = {
        check_in_date: checkInDate.toISOString(),
        check_out_date: checkOutDate.toISOString(),
        room_blocks: roomBlocks,
        group_name: groupName || undefined,
        group_type: groupType || undefined,
        payment_option: paymentOption,
        deposit_required: depositRequired,
        deposit_percentage: depositRequired ? depositPercentage : undefined,
        special_requests: specialRequests || undefined,
        notes: notes || undefined,
        cancellation_policy: cancellationPolicy || undefined,
        cancellation_deadline: cancellationDeadline ? cancellationDeadline.toISOString() : undefined,
        cancellation_penalty_percentage: cancellationPenaltyPercentage > 0 ? cancellationPenaltyPercentage : undefined,
        group_discount_percentage: groupDiscountPercentage,
      };

      await groupBookingService.createGroupBooking(bookingData);
      toast.success('Group booking created successfully!');
      handleClose();
      onSuccess();
    } catch (error: unknown) {
      toast.error(getUserFriendlyError(error) || getUserFriendlyError(error) || 'Failed to create group booking');
    } finally {
      setLoading(false);
    }
  };

  const handleClose = () => {
    setCheckInDate(null);
    setCheckOutDate(null);
    setGroupName('');
    setGroupType('');
    setRoomBlocks([]);
    setPaymentOption('coordinator_pays_all');
    setDepositRequired(false);
    setDepositPercentage(20);
    setSpecialRequests('');
    setNotes('');
    setCancellationPolicy('');
    setCancellationDeadline(null);
    setCancellationPenaltyPercentage(0);
    setGroupDiscountPercentage(undefined);
    setPricingSummary(null);
    onClose();
  };

  if (!isOpen) return null;

  return (
    <div className="fixed inset-0 bg-black bg-opacity-50 flex items-center justify-center z-50 p-4">
      <div className="bg-white rounded-lg max-w-4xl w-full max-h-[90vh] overflow-y-auto">
        <div className="sticky top-0 bg-white border-b border-gray-200 px-6 py-4 flex justify-between items-center">
          <h2 className="text-2xl font-bold text-gray-900">Create Group Booking</h2>
          <button
            onClick={handleClose}
            className="text-gray-400 hover:text-gray-600"
          >
            <X className="w-6 h-6" />
          </button>
        </div>

        <form onSubmit={handleSubmit} className="p-6 space-y-6">
          {/* Dates */}
          <div className="grid grid-cols-2 gap-4">
            <div>
              <label className="block text-sm font-medium text-gray-700 mb-2">
                <Calendar className="w-4 h-4 inline mr-2" />
                Check-in Date
              </label>
              <DatePicker
                selected={checkInDate}
                onChange={(date) => setCheckInDate(date)}
                selectsStart
                startDate={checkInDate}
                endDate={checkOutDate}
                minDate={new Date()}
                className="w-full px-4 py-2 border border-gray-300 rounded-lg focus:ring-2 focus:ring-blue-500 focus:border-transparent"
                dateFormat="yyyy-MM-dd"
                required
              />
            </div>
            <div>
              <label className="block text-sm font-medium text-gray-700 mb-2">
                <Calendar className="w-4 h-4 inline mr-2" />
                Check-out Date
              </label>
              <DatePicker
                selected={checkOutDate}
                onChange={(date) => setCheckOutDate(date)}
                selectsEnd
                startDate={checkInDate}
                endDate={checkOutDate}
                minDate={checkInDate || new Date()}
                className="w-full px-4 py-2 border border-gray-300 rounded-lg focus:ring-2 focus:ring-blue-500 focus:border-transparent"
                dateFormat="yyyy-MM-dd"
                required
              />
            </div>
          </div>

          {/* Group Information */}
          <div className="grid grid-cols-2 gap-4">
            <div>
              <label className="block text-sm font-medium text-gray-700 mb-2">
                Group Name
              </label>
              <input
                type="text"
                value={groupName}
                onChange={(e) => setGroupName(e.target.value)}
                placeholder="e.g., Corporate Retreat 2024"
                className="w-full px-4 py-2 border border-gray-300 rounded-lg focus:ring-2 focus:ring-blue-500 focus:border-transparent"
              />
            </div>
            <div>
              <label className="block text-sm font-medium text-gray-700 mb-2">
                Group Type
              </label>
              <select
                value={groupType}
                onChange={(e) => setGroupType(e.target.value)}
                className="w-full px-4 py-2 border border-gray-300 rounded-lg focus:ring-2 focus:ring-blue-500 focus:border-transparent"
              >
                <option value="">Select type...</option>
                <option value="corporate">Corporate</option>
                <option value="wedding">Wedding</option>
                <option value="conference">Conference</option>
                <option value="tour">Tour Group</option>
                <option value="family">Family Reunion</option>
                <option value="other">Other</option>
              </select>
            </div>
          </div>

          {/* Room Blocks */}
          <div>
            <div className="flex justify-between items-center mb-4">
              <label className="block text-sm font-medium text-gray-700">
                <Building2 className="w-4 h-4 inline mr-2" />
                Room Blocks
              </label>
              <button
                type="button"
                onClick={addRoomBlock}
                className="flex items-center gap-2 px-4 py-2 bg-blue-600 text-white rounded-lg hover:bg-blue-700"
              >
                <Plus className="w-4 h-4" />
                Add Room Block
              </button>
            </div>

            {loadingRoomTypes ? (
              <div className="text-center py-8">
                <Loader2 className="w-6 h-6 animate-spin mx-auto text-gray-400" />
                <p className="text-gray-500 mt-2">Loading room types...</p>
              </div>
            ) : roomBlocks.length === 0 ? (
              <div className="text-center py-8 border-2 border-dashed border-gray-300 rounded-lg">
                <p className="text-gray-500">No room blocks added. Click "Add Room Block" to get started.</p>
              </div>
            ) : (
              <div className="space-y-4">
                {roomBlocks.map((block, index) => (
                  <div key={index} className="border border-gray-200 rounded-lg p-4">
                    <div className="flex justify-between items-start mb-4">
                      <h4 className="font-medium text-gray-900">Room Block {index + 1}</h4>
                      <button
                        type="button"
                        onClick={() => removeRoomBlock(index)}
                        className="text-red-600 hover:text-red-800"
                      >
                        <Trash2 className="w-4 h-4" />
                      </button>
                    </div>
                    <div className="grid grid-cols-3 gap-4">
                      <div>
                        <label className="block text-sm font-medium text-gray-700 mb-2">
                          Room Type
                        </label>
                        <select
                          value={block.room_type_id}
                          onChange={(e) => updateRoomBlock(index, 'room_type_id', Number(e.target.value))}
                          className="w-full px-4 py-2 border border-gray-300 rounded-lg focus:ring-2 focus:ring-blue-500 focus:border-transparent"
                          required
                        >
                          {roomTypes.map((rt) => (
                            <option key={rt.id} value={rt.id}>
                              {rt.name} - {formatCurrency(rt.base_price)}/night
                            </option>
                          ))}
                        </select>
                      </div>
                      <div>
                        <label className="block text-sm font-medium text-gray-700 mb-2">
                          Number of Rooms
                        </label>
                        <input
                          type="number"
                          min="1"
                          value={block.num_rooms}
                          onChange={(e) => updateRoomBlock(index, 'num_rooms', Number(e.target.value))}
                          className="w-full px-4 py-2 border border-gray-300 rounded-lg focus:ring-2 focus:ring-blue-500 focus:border-transparent"
                          required
                        />
                      </div>
                      <div>
                        <label className="block text-sm font-medium text-gray-700 mb-2">
                          Rate per Room (per night)
                        </label>
                        <input
                          type="number"
                          min="0"
                          step="0.01"
                          value={block.rate_per_room}
                          onChange={(e) => updateRoomBlock(index, 'rate_per_room', Number(e.target.value))}
                          className="w-full px-4 py-2 border border-gray-300 rounded-lg focus:ring-2 focus:ring-blue-500 focus:border-transparent"
                          required
                        />
                      </div>
                    </div>
                  </div>
                ))}
              </div>
            )}
          </div>

          {/* Pricing Summary */}
          {pricingSummary && (
            <div className="bg-gray-50 border border-gray-200 rounded-lg p-4">
              <h3 className="font-semibold text-gray-900 mb-3">Pricing Summary</h3>
              <div className="space-y-2">
                <div className="flex justify-between">
                  <span className="text-gray-600">Original Total:</span>
                  <span className="text-gray-900">{formatCurrency(pricingSummary.originalTotal)}</span>
                </div>
                {pricingSummary.discountPercentage > 0 && (
                  <div className="flex justify-between text-green-600">
                    <span>Group Discount ({pricingSummary.discountPercentage}%):</span>
                    <span>-{formatCurrency(pricingSummary.discountAmount)}</span>
                  </div>
                )}
                <div className="flex justify-between font-semibold text-lg border-t border-gray-300 pt-2">
                  <span>Total Price:</span>
                  <span>{formatCurrency(pricingSummary.totalPrice)}</span>
                </div>
              </div>
              <div className="mt-3">
                <label className="block text-sm font-medium text-gray-700 mb-2">
                  Custom Discount Percentage (optional)
                </label>
                <input
                  type="number"
                  min="0"
                  max="100"
                  value={groupDiscountPercentage || ''}
                  onChange={(e) => setGroupDiscountPercentage(e.target.value ? Number(e.target.value) : undefined)}
                  placeholder="Auto-calculated"
                  className="w-full px-4 py-2 border border-gray-300 rounded-lg focus:ring-2 focus:ring-blue-500 focus:border-transparent"
                />
                <p className="text-xs text-gray-500 mt-1">
                  Leave empty for automatic discount based on room count
                </p>
              </div>
            </div>
          )}

          {/* Payment Options */}
          <div>
            <label className="block text-sm font-medium text-gray-700 mb-2">
              <DollarSign className="w-4 h-4 inline mr-2" />
              Payment Option
            </label>
            <select
              value={paymentOption}
              onChange={(e) => setPaymentOption(e.target.value as 'coordinator_pays_all' | 'individual_payments' | 'split_payment')}
              className="w-full px-4 py-2 border border-gray-300 rounded-lg focus:ring-2 focus:ring-blue-500 focus:border-transparent"
            >
              <option value="coordinator_pays_all">Coordinator Pays All</option>
              <option value="individual_payments">Individual Payments</option>
              <option value="split_payment">Split Payment</option>
            </select>
          </div>

          {/* Deposit */}
          <div className="flex items-center gap-4">
            <input
              type="checkbox"
              id="depositRequired"
              checked={depositRequired}
              onChange={(e) => setDepositRequired(e.target.checked)}
              className="w-4 h-4 text-blue-600 border-gray-300 rounded focus:ring-blue-500"
            />
            <label htmlFor="depositRequired" className="text-sm font-medium text-gray-700">
              Deposit Required
            </label>
            {depositRequired && (
              <div className="flex items-center gap-2">
                <input
                  type="number"
                  min="0"
                  max="100"
                  value={depositPercentage}
                  onChange={(e) => setDepositPercentage(Number(e.target.value))}
                  className="w-20 px-3 py-1 border border-gray-300 rounded-lg focus:ring-2 focus:ring-blue-500 focus:border-transparent"
                />
                <span className="text-sm text-gray-600">%</span>
              </div>
            )}
          </div>

          {/* Cancellation Policy */}
          <div>
            <label className="block text-sm font-medium text-gray-700 mb-2">
              <FileText className="w-4 h-4 inline mr-2" />
              Cancellation Policy
            </label>
            <textarea
              value={cancellationPolicy}
              onChange={(e) => setCancellationPolicy(e.target.value)}
              rows={3}
              placeholder="Enter cancellation policy details..."
              className="w-full px-4 py-2 border border-gray-300 rounded-lg focus:ring-2 focus:ring-blue-500 focus:border-transparent"
            />
            <div className="grid grid-cols-2 gap-4 mt-2">
              <div>
                <label className="block text-sm font-medium text-gray-700 mb-2">
                  Cancellation Deadline
                </label>
                <DatePicker
                  selected={cancellationDeadline}
                  onChange={(date) => setCancellationDeadline(date)}
                  className="w-full px-4 py-2 border border-gray-300 rounded-lg focus:ring-2 focus:ring-blue-500 focus:border-transparent"
                  dateFormat="yyyy-MM-dd"
                />
              </div>
              <div>
                <label className="block text-sm font-medium text-gray-700 mb-2">
                  Cancellation Penalty (%)
                </label>
                <input
                  type="number"
                  min="0"
                  max="100"
                  value={cancellationPenaltyPercentage}
                  onChange={(e) => setCancellationPenaltyPercentage(Number(e.target.value))}
                  className="w-full px-4 py-2 border border-gray-300 rounded-lg focus:ring-2 focus:ring-blue-500 focus:border-transparent"
                />
              </div>
            </div>
          </div>

          {/* Special Requests & Notes */}
          <div className="grid grid-cols-2 gap-4">
            <div>
              <label className="block text-sm font-medium text-gray-700 mb-2">
                Special Requests
              </label>
              <textarea
                value={specialRequests}
                onChange={(e) => setSpecialRequests(e.target.value)}
                rows={3}
                placeholder="Any special requests..."
                className="w-full px-4 py-2 border border-gray-300 rounded-lg focus:ring-2 focus:ring-blue-500 focus:border-transparent"
              />
            </div>
            <div>
              <label className="block text-sm font-medium text-gray-700 mb-2">
                Notes
              </label>
              <textarea
                value={notes}
                onChange={(e) => setNotes(e.target.value)}
                rows={3}
                placeholder="Internal notes..."
                className="w-full px-4 py-2 border border-gray-300 rounded-lg focus:ring-2 focus:ring-blue-500 focus:border-transparent"
              />
            </div>
          </div>

          {/* Actions */}
          <div className="flex justify-end gap-4 pt-4 border-t border-gray-200">
            <button
              type="button"
              onClick={handleClose}
              className="px-6 py-2 border border-gray-300 rounded-lg text-gray-700 hover:bg-gray-50"
            >
              Cancel
            </button>
            <button
              type="submit"
              disabled={loading || roomBlocks.length === 0}
              className="px-6 py-2 bg-blue-600 text-white rounded-lg hover:bg-blue-700 disabled:opacity-50 disabled:cursor-not-allowed flex items-center gap-2"
            >
              {loading ? (
                <>
                  <Loader2 className="w-4 h-4 animate-spin" />
                  Creating...
                </>
              ) : (
                'Create Group Booking'
              )}
            </button>
          </div>
        </form>
      </div>
    </div>
  );
};

export default CreateGroupBookingModal;

