Commit 619abe30 authored by Mahmoud Aglan's avatar Mahmoud Aglan

Add payment status column to group participants list

Shows "مدفوع" (green) or "لم يدفع" (red) per participant.
Row is highlighted red if participant has unpaid/overdue invoices
or their enrollment billing date is past without payment.
Co-Authored-By: 's avatarClaude Opus 4.6 <noreply@anthropic.com>
parent 63cd6d25
...@@ -4,6 +4,9 @@ ...@@ -4,6 +4,9 @@
use App\Domain\Attendance\Enums\AttendanceStatus; use App\Domain\Attendance\Enums\AttendanceStatus;
use App\Domain\Attendance\Models\AttendanceRecord; use App\Domain\Attendance\Models\AttendanceRecord;
use App\Domain\Financial\Enums\InvoiceStatus;
use App\Domain\Financial\Models\Invoice;
use App\Domain\Participant\Models\Participant;
use App\Domain\Scheduling\Models\Assignment; use App\Domain\Scheduling\Models\Assignment;
use App\Domain\Training\Enums\SessionStatus; use App\Domain\Training\Enums\SessionStatus;
use App\Domain\Training\Models\Enrollment; use App\Domain\Training\Models\Enrollment;
...@@ -94,6 +97,28 @@ public function render() ...@@ -94,6 +97,28 @@ public function render()
->orderBy('enrollment_date') ->orderBy('enrollment_date')
->get(); ->get();
// Payment status per participant: has unpaid/overdue invoices this month?
$participantIds = $activeEnrollments->pluck('participant_id')->toArray();
$unpaidParticipantIds = [];
if ($participantIds) {
$unpaidParticipantIds = Invoice::where('billable_type', Participant::class)
->whereIn('billable_id', $participantIds)
->whereIn('status', [InvoiceStatus::Sent, InvoiceStatus::Overdue, InvoiceStatus::PartiallyPaid])
->where('due_amount', '>', 0)
->whereNull('deleted_at')
->pluck('billable_id')
->unique()
->toArray();
}
// Also flag enrollments where next_billing_date is past and payment_status != paid
$overdueEnrollmentParticipantIds = $activeEnrollments
->filter(fn ($e) => $e->next_billing_date && $e->next_billing_date->isPast() && ($e->payment_status?->value ?? $e->payment_status) !== 'paid')
->pluck('participant_id')
->toArray();
$notPaidParticipantIds = array_unique(array_merge($unpaidParticipantIds, $overdueEnrollmentParticipantIds));
// All enrollments count (any status) // All enrollments count (any status)
$totalEnrollments = Enrollment::where('training_group_id', $this->group->id) $totalEnrollments = Enrollment::where('training_group_id', $this->group->id)
->whereNotIn('status', ['cancelled']) ->whereNotIn('status', ['cancelled'])
...@@ -180,6 +205,7 @@ public function render() ...@@ -180,6 +205,7 @@ public function render()
return view('livewire.groups.group-show', [ return view('livewire.groups.group-show', [
'activeEnrollments' => $activeEnrollments, 'activeEnrollments' => $activeEnrollments,
'notPaidParticipantIds' => $notPaidParticipantIds,
'totalEnrollments' => $totalEnrollments, 'totalEnrollments' => $totalEnrollments,
'recentSessions' => $recentSessions, 'recentSessions' => $recentSessions,
'upcomingSessions' => $upcomingSessions, 'upcomingSessions' => $upcomingSessions,
......
...@@ -394,13 +394,15 @@ class="px-4 py-2 bg-indigo-600 text-white rounded-lg hover:bg-indigo-700 text-sm ...@@ -394,13 +394,15 @@ class="px-4 py-2 bg-indigo-600 text-white rounded-lg hover:bg-indigo-700 text-sm
<tr> <tr>
<th class="px-4 py-3 text-start font-medium text-gray-600">{{ __('المشترك') }}</th> <th class="px-4 py-3 text-start font-medium text-gray-600">{{ __('المشترك') }}</th>
<th class="px-4 py-3 text-start font-medium text-gray-600">{{ __('تاريخ التسجيل') }}</th> <th class="px-4 py-3 text-start font-medium text-gray-600">{{ __('تاريخ التسجيل') }}</th>
<th class="px-4 py-3 text-center font-medium text-gray-600">{{ __('الدفع') }}</th>
<th class="px-4 py-3 text-center font-medium text-gray-600">{{ __('الحالة') }}</th> <th class="px-4 py-3 text-center font-medium text-gray-600">{{ __('الحالة') }}</th>
<th class="px-4 py-3 text-center font-medium text-gray-600">{{ __('نسبة الحضور') }}</th> <th class="px-4 py-3 text-center font-medium text-gray-600">{{ __('نسبة الحضور') }}</th>
</tr> </tr>
</thead> </thead>
<tbody class="divide-y divide-gray-100"> <tbody class="divide-y divide-gray-100">
@foreach($activeEnrollments as $enrollment) @foreach($activeEnrollments as $enrollment)
<tr class="hover:bg-gray-50 transition"> @php $isUnpaid = in_array($enrollment->participant_id, $notPaidParticipantIds); @endphp
<tr class="{{ $isUnpaid ? 'bg-red-50 hover:bg-red-100' : 'hover:bg-gray-50' }} transition">
<td class="px-4 py-3"> <td class="px-4 py-3">
<div class="flex items-center gap-3"> <div class="flex items-center gap-3">
<div class="w-8 h-8 rounded-full bg-blue-100 flex items-center justify-center flex-shrink-0"> <div class="w-8 h-8 rounded-full bg-blue-100 flex items-center justify-center flex-shrink-0">
...@@ -428,6 +430,17 @@ class="text-sm font-medium text-blue-600 hover:text-blue-800 hover:underline"> ...@@ -428,6 +430,17 @@ class="text-sm font-medium text-blue-600 hover:text-blue-800 hover:underline">
<td class="px-4 py-3 text-gray-600" dir="ltr"> <td class="px-4 py-3 text-gray-600" dir="ltr">
{{ $enrollment->enrollment_date?->format('Y-m-d') ?? '—' }} {{ $enrollment->enrollment_date?->format('Y-m-d') ?? '—' }}
</td> </td>
<td class="px-4 py-3 text-center">
@if($isUnpaid)
<span class="px-2 py-0.5 text-xs bg-red-100 text-red-700 font-bold rounded-full">
{{ __('لم يدفع') }}
</span>
@else
<span class="px-2 py-0.5 text-xs bg-green-100 text-green-700 rounded-full">
{{ __('مدفوع') }}
</span>
@endif
</td>
<td class="px-4 py-3 text-center"> <td class="px-4 py-3 text-center">
<span class="px-2 py-0.5 text-xs bg-green-100 text-green-700 rounded-full"> <span class="px-2 py-0.5 text-xs bg-green-100 text-green-700 rounded-full">
{{ __('نشط') }} {{ __('نشط') }}
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment