import React, { useState, useEffect } from 'react'; import { useParams, useNavigate, Link } from 'react-router-dom'; import { CheckCircle, Home, ListOrdered, Calendar, Users, CreditCard, MapPin, Mail, Phone, User, FileText, Building2, AlertCircle, Copy, Check, Loader2, } from 'lucide-react'; import { toast } from 'react-toastify'; import { getBookingById, generateQRCode, type Booking, } from '../../services/api/bookingService'; import { confirmBankTransfer } from '../../services/api/paymentService'; import Loading from '../../components/common/Loading'; const BookingSuccessPage: React.FC = () => { const { id } = useParams<{ id: string }>(); const navigate = useNavigate(); const [booking, setBooking] = useState( null ); const [loading, setLoading] = useState(true); const [error, setError] = useState(null); const [copiedBookingNumber, setCopiedBookingNumber] = useState(false); const [uploadingReceipt, setUploadingReceipt] = useState(false); const [receiptUploaded, setReceiptUploaded] = useState(false); const [selectedFile, setSelectedFile] = useState(null); const [previewUrl, setPreviewUrl] = useState(null); useEffect(() => { if (id) { fetchBookingDetails(Number(id)); } }, [id]); const fetchBookingDetails = async (bookingId: number) => { try { setLoading(true); setError(null); const response = await getBookingById(bookingId); if ( response.success && response.data?.booking ) { const bookingData = response.data.booking; setBooking(bookingData); // Redirect to deposit payment page if required and not yet paid if ( bookingData.requires_deposit && !bookingData.deposit_paid ) { navigate(`/deposit-payment/${bookingId}`, { replace: true }); return; } } else { throw new Error( 'Không thể tải thông tin đặt phòng' ); } } catch (err: any) { console.error('Error fetching booking:', err); const message = err.response?.data?.message || 'Không thể tải thông tin đặt phòng'; setError(message); toast.error(message); } finally { setLoading(false); } }; const formatDate = (dateString: string) => { return new Date(dateString).toLocaleDateString('en-US', { weekday: 'long', year: 'numeric', month: 'long', day: 'numeric', }); }; const formatPrice = (price: number) => { return new Intl.NumberFormat('en-US', { style: 'currency', currency: 'VND', }).format(price); }; const getStatusColor = (status: string) => { switch (status) { case 'confirmed': return 'bg-green-100 text-green-800'; case 'pending': return 'bg-yellow-100 text-yellow-800'; case 'cancelled': return 'bg-red-100 text-red-800'; case 'checked_in': return 'bg-blue-100 text-blue-800'; case 'checked_out': return 'bg-gray-100 text-gray-800'; default: return 'bg-gray-100 text-gray-800'; } }; const getStatusText = (status: string) => { switch (status) { case 'confirmed': return 'Đã xác nhận'; case 'pending': return 'Chờ xác nhận'; case 'cancelled': return 'Đã hủy'; case 'checked_in': return 'Đã nhận phòng'; case 'checked_out': return 'Đã trả phòng'; default: return status; } }; const copyBookingNumber = async () => { if (!booking?.booking_number) return; try { await navigator.clipboard.writeText( booking.booking_number ); setCopiedBookingNumber(true); toast.success('Đã sao chép mã đặt phòng'); setTimeout(() => setCopiedBookingNumber(false), 2000); } catch (err) { toast.error('Không thể sao chép'); } }; const handleFileSelect = ( e: React.ChangeEvent ) => { const file = e.target.files?.[0]; if (!file) return; // Validate file type if (!file.type.startsWith('image/')) { toast.error('Vui lòng chọn file ảnh'); return; } // Validate file size (max 5MB) if (file.size > 5 * 1024 * 1024) { toast.error('Kích thước ảnh không được vượt quá 5MB'); return; } setSelectedFile(file); // Create preview const reader = new FileReader(); reader.onloadend = () => { setPreviewUrl(reader.result as string); }; reader.readAsDataURL(file); }; const handleUploadReceipt = async () => { if (!selectedFile || !booking) return; try { setUploadingReceipt(true); // Generate transaction ID based on booking number const transactionId = `TXN-${booking.booking_number}-${Date.now()}`; const response = await confirmBankTransfer( booking.id, transactionId, selectedFile ); if (response.success) { toast.success( '✅ Đã gửi xác nhận thanh toán thành công! ' + 'Chúng tôi sẽ xác nhận trong thời gian sớm nhất.' ); setReceiptUploaded(true); // Update booking payment status locally setBooking((prev) => prev ? { ...prev, payment_status: 'paid', status: prev.status === 'pending' ? 'confirmed' : prev.status } : null ); } else { throw new Error( response.message || 'Không thể xác nhận thanh toán' ); } } catch (err: any) { console.error('Error uploading receipt:', err); const message = err.response?.data?.message || 'Không thể gửi xác nhận thanh toán. ' + 'Vui lòng thử lại.'; toast.error(message); } finally { setUploadingReceipt(false); } }; const qrCodeUrl = booking ? generateQRCode( booking.booking_number, booking.total_price ) : null; if (loading) { return ; } if (error || !booking) { return (

{error || 'Không tìm thấy đặt phòng'}

); } const room = booking.room; const roomType = room?.room_type; return (
{/* Success Header */}

Đặt phòng thành công!

Cảm ơn bạn đã đặt phòng tại khách sạn của chúng tôi

{/* Booking Number */}
Mã đặt phòng: {booking.booking_number}
{/* Status Badge */}
{getStatusText(booking.status)}
{/* Booking Details */}

Chi tiết đặt phòng

{/* Room Information */} {roomType && (
{roomType.images?.[0] && ( {roomType.name} )}

{roomType.name}

{room && (

Phòng {room.room_number} - Tầng {room.floor}

)}

{formatPrice(roomType.base_price)}/đêm

)} {/* Dates */}

Ngày nhận phòng

{formatDate(booking.check_in_date)}

Ngày trả phòng

{formatDate(booking.check_out_date)}

{/* Guest Count */}

Số người

{booking.guest_count} người

{/* Notes */} {booking.notes && (

Ghi chú

{booking.notes}

)} {/* Payment Method */}

Phương thức thanh toán

{booking.payment_method === 'cash' ? '💵 Thanh toán tại chỗ' : '🏦 Chuyển khoản ngân hàng'}

{/* Total Price */}
Tổng thanh toán {formatPrice(booking.total_price)}
{/* Guest Information */} {booking.guest_info && (

Thông tin khách hàng

Họ và tên

{booking.guest_info.full_name}

Email

{booking.guest_info.email}

Số điện thoại

{booking.guest_info.phone}

)} {/* Bank Transfer Instructions */} {booking.payment_method === 'bank_transfer' && (

Hướng dẫn chuyển khoản

Vui lòng chuyển khoản theo thông tin sau:

{/* Bank Info */}

Ngân hàng: Vietcombank (VCB)

Số tài khoản: 0123456789

Chủ tài khoản: KHACH SAN ABC

Số tiền:{' '} {formatPrice(booking.total_price)}

Nội dung:{' '} {booking.booking_number}

{/* QR Code */} {qrCodeUrl && (

Quét mã QR để chuyển khoản

QR Code

Mã QR đã bao gồm đầy đủ thông tin

)}

💡 Lưu ý: Vui lòng ghi đúng mã đặt phòng vào nội dung chuyển khoản để chúng tôi có thể xác nhận thanh toán của bạn.

{/* Upload Receipt Section */} {!receiptUploaded ? (

📎 Xác nhận thanh toán

Sau khi chuyển khoản, vui lòng tải lên ảnh biên lai để chúng tôi xác nhận nhanh hơn.

{/* File Input */}
{/* Upload Button */} {selectedFile && ( )}
) : (

Payment confirmation sent

We will confirm your order as soon as possible.

)}
)} {/* Important Notice */}

⚠️ Important Notice:

  • Please bring your ID card when checking in
  • Check-in time: 14:00 / Check-out time: 12:00
  • If you cancel the booking, 20% of the total order value will be charged
  • {booking.payment_method === 'bank_transfer' && (
  • Please transfer within 24 hours to secure your room
  • )}
{/* Action Buttons */}
Xem đơn của tôi Về trang chủ
); }; export default BookingSuccessPage;