<?php

namespace App\Actions\Payments;

use App\Enums\PaymentProofReviewStatus;
use App\Enums\PaymentStatus;
use App\Enums\RegistrationStatus;
use App\Events\PaymentProofReviewed;
use App\Models\EventPaymentProof;
use App\Models\User;
use App\Services\AuditLogger;
use App\Services\RegistrationStatusService;
use Illuminate\Support\Facades\DB;
use InvalidArgumentException;

class ConfirmPaymentAction
{
    public function __construct(
        private RegistrationStatusService $registrationStatus,
        private AuditLogger $auditLogger,
    ) {}

    public function execute(EventPaymentProof $proof, User $admin, ?string $notes = null): EventPaymentProof
    {
        return DB::transaction(function () use ($proof, $admin, $notes) {
            if ($proof->review_status !== PaymentProofReviewStatus::Pending) {
                throw new InvalidArgumentException(__('events.errors.invalid_status'));
            }

            $registration = $proof->eventRegistration;

            $proof->update([
                'review_status' => PaymentProofReviewStatus::Approved,
                'reviewed_by' => $admin->id,
                'reviewed_at' => now(),
            ]);

            $oldStatus = $registration->status;

            $this->registrationStatus->record(
                $registration,
                RegistrationStatus::Confirmed,
                $oldStatus,
                $admin,
                $notes ?? 'Payment confirmed',
            );

            $registration->update([
                'payment_status' => PaymentStatus::Confirmed,
                'confirmed_at' => now(),
                'reviewed_by' => $admin->id,
                'reviewed_at' => now(),
            ]);

            $this->auditLogger->log('payment.confirmed', $proof, null, ['review_status' => PaymentProofReviewStatus::Approved->value]);

            event(new PaymentProofReviewed(
                proof: $proof->fresh(['eventRegistration.event', 'eventRegistration.user']),
                action: PaymentProofReviewed::ACTION_CONFIRMED,
            ));

            return $proof->fresh(['eventRegistration.event', 'manualPaymentMethod']);
        });
    }
}
