label('Selesaikan Kerjasama') ->icon(Heroicon::OutlinedCheckBadge) ->color('success') ->requiresConfirmation() ->modalHeading(fn () => CheerfulNotification::getByKey('cooperation.complete_title')) ->modalDescription(fn () => CheerfulNotification::getByKey('cooperation.complete_desc')) ->action(function (Cooperation $record): void { // Check for any pending payments first (globally for this cooperation) $hasPendingPayments = $record->payments() ->where('cooperation_payments.status', ApprovalStatus::PENDING) ->exists(); if ($hasPendingPayments) { CheerfulNotification::danger( CheerfulNotification::getByKey('cooperation.payment_pending'), CheerfulNotification::getByKey('cooperation.payment_pending_desc') )->send(); $this->halt(); return; } // 1. Media whose proposal was accepted $acceptedMedia = $record->cooperationMedia()->accepted()->get(); if ($acceptedMedia->isEmpty()) { CheerfulNotification::danger( CheerfulNotification::getByKey('cooperation.media_empty'), CheerfulNotification::getByKey('cooperation.media_empty_desc') )->send(); return; } // 2. Filter media that have at least one accepted report $mediaWithObligation = $acceptedMedia->filter(function ($media) use ($record) { return $record->reports() ->whereHas('mediaTaskAssignment.partnerMedia', fn ($q) => $q->where('partner_media.id', $media->partner_media_id)) ->accepted() ->exists(); }); // 3. Of those media, verify they all have an ACCEPTED payment $unpaidMedia = $mediaWithObligation->filter(function ($media) { return ! $media->payment()->accepted()->exists(); }); if ($unpaidMedia->isNotEmpty()) { CheerfulNotification::danger( CheerfulNotification::getByKey('cooperation.payment_unfulfilled'), CheerfulNotification::getByKey('cooperation.payment_unfulfilled_desc') )->send(); $this->halt(); return; } // Calculate total payment from all accepted media payments // This will count all accepted payments, even if they didn't have reports (unlikely but possible) $totalPayment = $record->payments()->accepted()->sum('amount'); $record->update([ 'payment_amount' => $totalPayment, 'completed_at' => now(), 'status' => CooperationStatus::COMPLETED, ]); CheerfulNotification::success( CheerfulNotification::getByKey('cooperation.completed_success'), CheerfulNotification::getByKey('cooperation.completed_desc') )->send(); }) ->visible(function (Cooperation $record): bool { return auth()->user()->hasRole([RoleEnum::ADMINISTRATOR->value, RoleEnum::DEVELOPER->value]) && $record->status === CooperationStatus::PAYMENT; }); } }