@extends('layouts.app') @section('title', 'Booking') @section('content') @php $passengersVisaData = ($passengers ?? collect())->map(function($p) { $rate = $p->booking?->currencyRate?->rate ?? app(\App\Services\CurrencyRateService::class)->getRateForDate($p->booking?->created_at)?->rate ?? 0; return [ 'id' => $p->id, 'booking_id' => $p->booking_id, 'rate' => $rate, 'visa' => $p->visaSubmission ? [ 'id' => $p->visaSubmission->id, 'agent_id' => $p->visaSubmission->visa_agent_id, 'agent' => $p->visaSubmission?->visaAgent?->name ?? '', 'visa_number' => $p->visaSubmission?->visa_number ?? '', 'selling_price' => (float)($p->visaSubmission?->visaSellingPrice?->selling_price ?? 0), 'agent_commission' => (float)($p->visaSubmission?->agent_commission ?? 0), 'net_visa_cost' => (float)($p->visaSubmission?->net_visa_cost ?? 0), 'additional_cost' => (float)($p->visaSubmission?->additional_cost ?? 0), 'remarks' => $p->visaSubmission?->remarks ?? '', 'final_cost' => (float)($p->visaSubmission?->final_cost ?? 0), 'commission_agent_id' => $p->visaSubmission?->commission_agent_id, 'commission_agent' => $p->visaSubmission?->commissionAgent?->name ?? '', 'status' => $p->visaSubmission->status?->value ?? 'pending', ] : null, ]; })->values(); $packagesList = \App\Models\Package::select('id', 'package_name') ->get() ->unique('package_name') ->values(); $flightDateRanges = []; $today = (int) now()->format('d'); $currentThird = $today <= 10 ? 1 : ($today <= 20 ? 2 : 3); $months = [ ['offset' => 0, 'startPart' => $currentThird], ['offset' => 1, 'startPart' => 1], ['offset' => 2, 'startPart' => 1], ['offset' => 3, 'startPart' => 1], ]; foreach ($months as $m) { if (count($flightDateRanges) >= 9) break; $month = now()->copy()->addMonths($m['offset'])->startOfMonth(); $lastDay = (int) $month->copy()->endOfMonth()->format('d'); $label = $month->format('M'); $parts = [ 1 => ['start' => $month->format('Y-m-01'), 'end' => $month->format('Y-m-10'), 'label' => "{$label} 1–10"], 2 => ['start' => $month->format('Y-m-11'), 'end' => $month->format('Y-m-20'), 'label' => "{$label} 11–20"], 3 => ['start' => $month->format('Y-m-21'), 'end' => $month->copy()->endOfMonth()->format('Y-m-d'), 'label' => "{$label} 21–{$lastDay}"], ]; for ($p = $m['startPart']; $p <= 3; $p++) { if (count($flightDateRanges) >= 9) break; $flightDateRanges[] = array_merge(['id' => count($flightDateRanges) + 1], $parts[$p]); } } $airlinesList = \App\Models\Airline::with('travelClasses')->get()->map(fn($a) => [ 'id' => $a->id, 'name' => $a->name, 'class_ids' => $a->travelClasses->pluck('id'), ])->values(); $classesList = \App\Models\TravelClass::all()->map(fn($c) => [ 'id' => $c->id, 'name' => $c->name, ])->values(); $activeFares = \App\Models\TicketFare::where('is_active', true)->with([ 'route.fromCity', 'route.toCity', 'route.returnCity', 'route.multiSegments.fromCity', 'route.multiSegments.toCity', 'airline', 'airlineClass.class', 'groupTicket', ])->get(); $inactiveFareIds = \App\Models\Passenger::whereNotNull('ticket_fare_id') ->whereHas('ticketFare', fn($q) => $q->where('is_active', false)) ->pluck('ticket_fare_id') ->unique(); $inactiveFares = \App\Models\TicketFare::whereIn('id', $inactiveFareIds)->with([ 'route.fromCity', 'route.toCity', 'route.returnCity', 'route.multiSegments.fromCity', 'route.multiSegments.toCity', 'airline', 'airlineClass.class', 'groupTicket', ])->get(); $ticketFaresList = $activeFares->merge($inactiveFares)->map(fn($fare) => [ 'id' => $fare->id, 'route' => match($fare->route->route_type?->value) { 'multi_city' => $fare->route->multiSegments->map(fn($s) => ($s->fromCity?->code ?? '?') . '-' . ($s->toCity?->code ?? '?'))->implode(', '), 'round' => ($fare->route->fromCity?->code ?? '?') . '-' . ($fare->route->toCity?->code ?? '?') . '-' . ($fare->route->returnCity?->code ?? '?'), default => ($fare->route->fromCity?->code ?? '?') . '-' . ($fare->route->toCity?->code ?? '?'), }, 'airline' => $fare->airline->name, 'airline_class' => $fare->airlineClass->class?->name ?? '', 'ticket_type' => $fare->ticket_type?->value ?? 'regular', 'route_id' => $fare->route_id, 'airline_id' => $fare->airline_id, 'airline_classes_id' => $fare->airline_classes_id, 'route_type' => $fare->route->route_type?->value, 'flight_type' => $fare->route->flight_type?->value, 'group_ticket_id' => $fare->groupTicket?->id ?? null, 'pnr' => $fare->groupTicket?->pnr ?? '', 'ticket_qty' => $fare->groupTicket?->ticket_qty ?? null, 'is_refundable' => $fare->groupTicket?->is_refundable ?? null, 'is_exchangable' => $fare->groupTicket?->is_exchangable ?? null, 'selling_fare' => (float)($fare->selling_fare ?? 0), 'net_fare' => (float)($fare->net_fare ?? 0), 'offer_price' => $fare->ticket_type?->value === 'offer' ? (float)($fare->offer_price ?? 0) : null, 'child_fare_percentage' => (float)($fare->child_fare_percentage ?? 70), 'infant_fare_percentage' => (float)($fare->infant_fare_percentage ?? 30), 'is_active' => $fare->is_active, ])->values(); $passengersTicketData = ($passengers ?? collect())->map(fn($p) => [ 'id' => $p->id, 'booking_id' => $p->booking_id, 'booking_date' => $p->booking?->created_at?->format('Y-m-d') ?? '', 'invoice_no' => $p->booking?->invoice_id ?? '', 'passenger_name' => trim($p->first_name . ' ' . $p->last_name), 'passport' => $p->passport_no ?? '', 'route' => $p->route_display ?? '', 'airline' => $p->ticketFare?->airline?->name ?? $p->booking?->package?->ticketFare?->airline?->name ?? '', 'travel_class' => $p->ticketFare?->airlineClass?->class?->name ?? $p->booking?->package?->ticketFare?->airlineClass?->class?->name ?? '', 'passenger_type' => $p->passenger_type?->value ?? 'adult', 'mobile_no' => $p->mobile_no ?? '', 'guardian' => '', 'is_ticket_held' => (bool)($p->is_ticket_held ?? false), 'ticket_status' => $p->ticket_status?->value ?? null, 'due' => $p->booking?->invoice?->balance ?? 0, 'required_flight_date' => $p->flight_date_from?->format('Y-m-d') ?? '', 'actual_flight_date' => $p->actual_flight_date?->format('Y-m-d') ?? '', 'fingerprint_location' => $p->booking?->fingerprint_location?->value ?? 'None', 'fingerprint_status' => $p->fingerprintDetail?->status?->value ?? null, 'status' => $p->status?->name ?? 'None', 'is_cancelled' => $p->booking?->is_cancelled ?? false, 'documents' => [], 'passenger_data' => null, 'ticket_fare' => $p->ticketFare ? [ 'ticket_type' => $p->ticketFare->ticket_type?->value ?? 'regular', 'route_type' => match($p->ticketFare?->route?->route_type?->value) { 'oneway_inbound' => 'One Way-Inbound', 'oneway_outbound' => 'One Way-Outbound', 'round' => 'Round', 'multi_city' => 'Multi City', default => '', }, 'flight_type' => match($p->ticketFare?->route?->flight_type?->value) { 'direct' => 'Direct', 'transit' => 'Transit', default => '', }, 'group_ticket_id' => $p->ticketFare->groupTicket?->id ?? null, 'inbound_date' => $p->ticketFare->groupTicket?->inbound_date ?? '', 'outbound_date' => $p->ticketFare->groupTicket?->outbound_date ?? '', 'pnr' => $p->ticketFare->groupTicket?->pnr ?? '', 'ticket_number' => '', 'date' => '', 'ticket_agent' => '', 'ticket_fare_id' => $p->ticketFare->id, 'airline_id' => $p->ticketFare->airline_id, 'airline_classes_id' => $p->ticketFare->airline_classes_id, 'route_id' => $p->ticketFare->route_id, 'selling_fare' => (float)($p->ticketFare->selling_fare ?? 0), 'net_fare' => (float)($p->ticketFare->net_fare ?? 0), 'child_fare_percentage' => (float)($p->ticketFare->child_fare_percentage ?? 70), 'infant_fare_percentage' => (float)($p->ticketFare->infant_fare_percentage ?? 30), 'offer_price' => $p->ticketFare->ticket_type?->value === 'offer' ? (float)($p->ticketFare->offer_price ?? 0) : null, 'with_offer' => (bool)($p->ticketFare->ticket_type?->value === 'offer'), 'refundable' => false, 'non_refundable' => false, 'non_exchangeable' => false, 'baggage_inbound' => '', 'baggage_outbound' => '', 'outbound_pending' => false, 'issue_type' => null, 'issued_ticket_id' => null, 'baggage_allowances' => $p->ticketFare?->baggageAllowances->map(fn($b) => [ 'passenger_type' => $b->passenger_type, 'travel_direction' => $b->travel_direction, 'allowance' => $b->allowance, ]) ?? [], ] : null, 'latest_issued_ticket' => ($lit = $p->latestIssuedTicket) ? [ 'id' => $lit->id, 'ticket_number' => $lit->ticket_number ?? '', 'pnr' => $lit->pnr ?? '', 'ticket_agent_id' => $lit->ticket_agent_id, 'ticket_agent_name' => $lit->ticketAgent?->name ?? '', 'ticket_fare_id' => $lit->ticket_fare_id, 'group_ticket_id' => $lit->group_ticket_id, 'issued_date' => $lit->issued_date?->format('Y-m-d') ?? '', 'inbound_date' => $lit->inbound_date?->format('Y-m-d') ?? '', 'outbound_date' => $lit->outbound_date?->format('Y-m-d') ?? '', 'selling_fare' => (float)($lit->selling_fare ?? 0), 'net_fare' => (float)($lit->net_fare ?? 0), 'offer_price' => (float)($lit->offer_price ?? 0), 'is_refundable' => $lit->is_refundable ?? false, 'is_exchangeable' => $lit->is_exchangeable ?? false, 'baggage_inbound' => $lit->baggage_inbound ?? '', 'baggage_outbound' => $lit->baggage_outbound ?? '', 'outbound_pending' => $lit->outbound_pending ?? false, 'issue_type' => $lit->issue_type, 'status' => $lit->status, 'airline' => $lit->ticketFare?->airline?->name ?? '', 'travel_class' => $lit->ticketFare?->airlineClass?->class?->name ?? '', 'route' => $lit->ticketFare?->route ? ($lit->ticketFare->route->fromCity?->code . '-' . $lit->ticketFare->route->toCity?->code) : '', 'route_type' => $lit->ticketFare?->route?->route_type?->value, ] : null, ])->values(); @endphp
@php $canCreateBooking = auth()->user()->roles->pluck('name')->intersect(['Super Admin', 'Co Admin', 'Branch Manager', 'Branch Staff', 'Auditor', 'Visa Admin', 'Visa Staff', 'Ticket Admin', 'Ticket Staff', 'Fingerprint Admin', 'Fingerprint Staff', 'Delivery Staff'])->isNotEmpty(); $canViewFinancialColumns = auth()->user()->roles->pluck('name')->intersect(['Super Admin', 'Co Admin', 'Auditor'])->isNotEmpty(); $canViewVisaColumns = auth()->user()->roles->pluck('name')->intersect(['Super Admin', 'Co Admin', 'Visa Admin', 'Visa Staff'])->isNotEmpty(); $canViewTicketFareColumn = auth()->user()->roles->pluck('name')->intersect(['Super Admin', 'Co Admin', 'Ticket Admin', 'Ticket Staff'])->isNotEmpty(); $canViewTicketAgentColumn = auth()->user()->roles->pluck('name')->intersect(['Super Admin', 'Co Admin', 'Ticket Admin', 'Ticket Staff'])->isNotEmpty(); $canEditInline = auth()->user()->roles->pluck('name')->intersect(['Super Admin', 'Co Admin', 'Delivery Staff'])->isNotEmpty(); $canEditFingerprintLocation = auth()->user()->roles->pluck('name')->intersect(['Super Admin', 'Co Admin', 'Fingerprint Admin', 'Delivery Staff'])->isNotEmpty(); $canDeleteBooking = auth()->user()->roles->pluck('name')->intersect(['Super Admin'])->isNotEmpty(); $canViewActionColumn = true; $canViewPassengerIndex = true; @endphp

Booking

@if($canCreateBooking) Add Booking @endif
@if(session('success'))
{{ session('success') }}
@endif @if(session('error'))
{{ session('error') }}
@endif
@if($canViewPassengerIndex)@endif
@unless(auth()->user()->branch_id) @endunless Total Booking - {{ $totalBookingCount }} Total Passenger - {{ $totalBookingPassengerCount }}
@if($canViewActionColumn)@endif @forelse($bookings as $booking) @php $bookingCurrencyRate = $booking->currencyRate?->rate ?? ($currencyRateService?->getRateForDate($booking->created_at)?->rate ?? ($currencyRateService?->getFirstRate()?->rate ?? 0)); @endphp @if($canViewActionColumn) @endif @empty @endforelse
Invoice ID Booking Date Customer Mobile Passengers Fingerprint Location Booking Branch Fingerprint Branch District Package Total Paid Due StatusActions
{{ $booking->invoice_id ?? '—' }} {{ $booking->created_at->format('Y-m-d') }} {{ $booking->customer->name ?? 'N/A' }} {{ $booking->customer->mobile_no ?? 'N/A' }} {{ $booking->passengers->count() }} @if($canEditFingerprintLocation && !(auth()->user()->hasRole('Fingerprint Admin') && ($booking->fingerprint_location?->value ?? 'office') === 'home')) @else {{ ucfirst($booking->fingerprint_location?->value ?? 'Office') }} @endif {{ $booking->bookingBranch->name ?? '—' }} {{ $booking->fingerprintBranch->name ?? '—' }} {{ $booking->district->name ?? 'N/A' }} {{ $booking->package->package_name ?? 'N/A' }} @currency($booking->invoice?->total_amount ?? 0, 2, $bookingCurrencyRate) @currency($booking->invoice?->paid_amount ?? 0, 2, $bookingCurrencyRate) @currency($booking->invoice?->balance ?? 0, 2, $bookingCurrencyRate) @if($booking->is_cancelled) @php $cb = $booking->cancelledBooking; @endphp @if($cb && $cb->status->value === 'cancellation processing') Cancellation Processing @else Cancelled @endif @else Active @endif View @if(!$booking->is_cancelled && (auth()->user()->hasRole('Super Admin') || auth()->user()->hasRole('Co Admin'))) @endif @if($canDeleteBooking)
@csrf @method('DELETE')
@endif
No bookings found
{{ $bookings->links() }}
@if($canViewPassengerIndex)
@if($canFilterByVisaAgent)
@endif @if($canFilterByTicketAgent)
@endif
@unless(auth()->user()->branch_id)
@endunless
Total Passenger - {{ $totalPassengerCount }} Total Package - @currency($totalPackageValue, 2, null, $totalPackageBdt) Total Due - @currency($totalDue, 2, null, $totalDueBdt)
@if($canViewFinancialColumns)@endif @if($canViewFinancialColumns)@endif @if($canViewFinancialColumns)@endif @if($canViewVisaColumns)@endif @if($canViewVisaColumns)@endif @if($canViewTicketFareColumn)@endif @if($canViewTicketAgentColumn)@endif @php $lastBookingId = null; @endphp @forelse($passengers as $passenger) @php $isFirstRow = ($lastBookingId !== $passenger->booking_id); $lastBookingId = $passenger->booking_id; $ticketFare = $passenger->ticketFare; $baseFare = $ticketFare?->ticket_type?->value === 'offer' ? ($ticketFare->offer_price ?? $ticketFare->selling_fare ?? $ticketFare->net_fare ?? 0) : ($ticketFare?->selling_fare ?? $ticketFare?->net_fare ?? 0); $passengerTypeVal = $passenger->passenger_type?->value; $fareAmount = match($passengerTypeVal) { 'child' => $baseFare * ($ticketFare?->child_fare_percentage ?? 70) / 100, 'infant' => $baseFare * ($ticketFare?->infant_fare_percentage ?? 30) / 100, default => $baseFare, }; $route = $passenger->ticketFare?->route ?? $passenger->booking?->package?->ticketFare?->route; $routeDisplay = '—'; if ($route) { $routeType = $route->route_type?->value; if ($routeType === 'multi_city') { $routeDisplay = $route->multiSegments->map(fn($s) => ($s->fromCity?->code ?? '?') . '-' . ($s->toCity?->code ?? '?'))->implode(', '); } elseif ($routeType === 'round') { $routeDisplay = ($route->fromCity?->code ?? '?') . '-' . ($route->toCity?->code ?? '?') . '-' . ($route->returnCity?->code ?? '?'); } else { $routeDisplay = ($route->fromCity?->code ?? '?') . ' → ' . ($route->toCity?->code ?? '?'); } } @endphp @php $passBookingRate = $passenger->booking?->currencyRate?->rate ?? ($currencyRateService?->getRateForDate($passenger->booking?->created_at)?->rate ?? ($currencyRateService?->getFirstRate()?->rate ?? 0)); @endphp @if($canViewFinancialColumns)@endif @if($canViewFinancialColumns)@endif @if($canViewFinancialColumns)@endif @if($canViewVisaColumns) @endif @if($canViewTicketFareColumn) @endif @if($canViewTicketAgentColumn)@endif @empty @endforelse
Booking Date Invoice ID Customer PAX QTY Mobile Name Current status Passport No Route Required Flight Date Actual Flight Date Return Date PackagePackage ValueTotal CostMarkup (Profit)Due Stay DurationVisaVisa AgentVisa StatusTicket FareTicket AgentTicket Status Fingerprint Status Remarks Actions
{{ $passenger->booking?->created_at?->format('d M Y') ?? '—' }} {{ $passenger->booking?->invoice_id ?? '—' }} {{ $passenger->booking->customer->name ?? 'N/A' }} {{ $isFirstRow ? ($passenger->booking?->pax_qty ?? '—') : '' }}
{{ $passenger->booking?->customer?->mobile_no ?? '—' }}
{{ $passenger->mobile_no ?? '—' }}
{{ trim($passenger->first_name . ' ' . $passenger->last_name) ?: '—' }} @if($canEditInline) @else {{ $passenger->status?->name ?? $passenger->computed_status ?? 'None' }} @endif {{ $passenger->passport_no ?? '—' }} {{ $routeDisplay }} {{ $passenger->flight_date_from?->format('d M Y') . ' → ' . $passenger->flight_date_to?->format('d M Y') ?? '—' }} {{ $passenger->allIssuedTickets->sortByDesc('created_at')->first(fn($t) => $t->inbound_date)?->inbound_date?->format('d M Y') ?? 'N/A' }} {{ $passenger->allIssuedTickets->sortByDesc('created_at')->first(fn($t) => $t->outbound_date)?->outbound_date?->format('d M Y') ?? 'N/A' }} {{ $passenger->booking?->package?->package_name ?? '—' }}@if($passenger->package_value)@currency($passenger->package_value, 2, $passBookingRate)@else—@endif@if($isFirstRow)@if($passenger->booking?->invoice)
Total: @currency($passenger->booking->invoice->total_amount, 2, $passBookingRate)
Due: @currency($passenger->booking->invoice->balance, 2, $passBookingRate)
@else—@endif @endif
{{ $passenger->stay_duration ?? '—' }}
@if($fareAmount > 0)@currency($fareAmount, 2, $passBookingRate)@else—@endif
@php $detail = $passenger->fingerprintDetail; $rawStatus = $detail?->status?->value; $displayStatus = $rawStatus; if ($rawStatus === 'approved') { $allDetails = $detail->fingerprint?->fingerprintDetails; $allApproved = $allDetails && $allDetails->every(fn($d) => $d->status->value === 'approved'); if (!$allApproved) { $displayStatus = 'Partially Approved'; } $approvedDate = $detail->approvedLog?->created_at ?? $detail->updated_at; } elseif ($rawStatus === 'done') { $displayStatus = 'Pending Pax Completion'; } @endphp @if($displayStatus)
{{ $displayStatus === 'Partially Approved' ? 'Partially Approved' : ($rawStatus === 'done' ? 'Pending Pax Completion' : ucfirst($rawStatus)) }} @if($rawStatus === 'approved' && $approvedDate) {{ $approvedDate->format('d|m|y') }} @endif
@else @endif
{{ $passenger->booking?->remarks ?? '—' }}
View @if($passenger->documents_count > 0) Download @else Download @endif @if($passenger->booking->documents->isNotEmpty() || ($passenger->booking->customer && $passenger->booking->customer->documents->isNotEmpty())) Download All @else Download All @endif
No passengers found
{{ $passengers->links() }}
@endif {{-- Visa Submit Modal --}}

Visa Submit

{{-- Visa Issue Modal --}}

Visa Issue

{{-- Visa Edit Modal --}}

Edit Visa

{{-- Visa Re-Submit Modal --}}

Visa Re-Submit

{{-- Visa Cancel Modal --}}

Cancel Visa

{{-- Ticket Fare Modal --}}
@include('partials.route-form-modal') @include('partials.airline-form-modal') @include('partials.class-form-modal') {{-- Cancellation Initiation Modal --}}

Cancel Booking

{{-- Financial Summary --}}
Total Paid

Total Cost

Balance

{{-- Cost Breakdown --}}

Costs Incurred

Fingerprint:
Visa:
Ticket:
Total Cost:
{{-- Branch & Service Charge --}}
{{-- Refund Amount --}}
Refund Amount:

Refund = Total Paid − Total Cost − Service Charge

{{-- Actions --}}
@endsection