<?php

namespace App\Http\Controllers\Frontend\TopUp\Traits;

use App\Models\PwPromoUsage;
use App\Models\User;

trait PaymentServiceTrait
{
    /**
     * Validate common payment request data
     */
    protected function validatePaymentRequest($user, $settings, $amount)
    {
        // Check if service is active
        if (! $settings || ! $settings->is_active) {
            return [
                'valid' => false,
                'error' => 'Service is currently not available.',
            ];
        }

        // Check if user has phone number
        if (empty($user->mobilenumber)) {
            return [
                'valid' => false,
                'error' => 'Please update your phone number in Profile Settings before making a payment.',
            ];
        }

        // Check minimum amount
        if ($amount < $settings->min_amount) {
            return [
                'valid' => false,
                'error' => 'Minimum amount is Rp '.number_format($settings->min_amount),
            ];
        }

        // Check maximum amount
        if ($amount > $settings->max_amount) {
            return [
                'valid' => false,
                'error' => 'Maximum amount is Rp '.number_format($settings->max_amount),
            ];
        }

        return ['valid' => true];
    }

    /**
     * Prepare common payment data
     */
    protected function preparePaymentData($request, $user, $settings)
    {
        $selectedRole = $this->verifyCharacterOwnership($user->ID, $request->character_id);
        if (! $selectedRole) {
            return [
                'success' => false,
                'error' => 'Invalid character selected.',
            ];
        }

        $factionData = $this->getFactionBonus($request->character_id);

        $goldRate = $settings->gold_rate;

        $promoResult = $this->processPromoCode($request->promo_code, $request->amount, $user->ID, $goldRate);

        $autoPromoResult = $this->getAutoPromo($request->amount, $user->ID, $goldRate);
        $autoPromoBonusGold = $autoPromoResult ? $autoPromoResult['bonus_gold'] : 0;

        $baseGoldForStreamer = floor($request->amount / $goldRate);
        $streamerResult = $this->processStreamerCode($request->streamer_code, $baseGoldForStreamer);

        $goldAmount = $this->calculateGoldAmount(
            $request->amount,
            $goldRate,
            $factionData['bonus_percentage'],
            $promoResult['bonus_gold'] + $autoPromoBonusGold,
            $streamerResult['bonus_gold']
        );

        return [
            'success' => true,
            'selectedRole' => $selectedRole,
            'factionData' => $factionData,
            'promoResult' => $promoResult,
            'autoPromoResult' => $autoPromoResult,
            'streamerResult' => $streamerResult,
            'goldAmount' => $goldAmount,
        ];
    }

    /**
     * Build product name with promo info
     */
    protected function buildProductName($goldAmount, $promoResult)
    {
        $productName = 'Gold Top Up - '.$goldAmount.' Gold';
        if ($promoResult['promo'] && $promoResult['discount'] > 0) {
            $productName .= ' (Promo: '.$promoResult['promo']->code.')';
        }

        return $productName;
    }

    /**
     * Record promo usage
     */
    protected function recordPromoUsage($promoResult, $userId)
    {
        if ($promoResult['promo']) {
            PwPromoUsage::create([
                'promo_id' => $promoResult['promo']->id,
                'user_id' => $userId,
                'discount_amount' => $promoResult['discount'],
            ]);

            $promoResult['promo']->increment('usage_count');
        }
    }

    protected function recordAutoPromoUsage($autoPromoResult, $userId)
    {
        if ($autoPromoResult && $autoPromoResult['promo']) {
            PwPromoUsage::create([
                'promo_id' => $autoPromoResult['promo']->id,
                'user_id' => $userId,
                'discount_amount' => 0,
            ]);

            $autoPromoResult['promo']->increment('usage_count');
        }
    }

    /**
     * Handle successful payment - add gold and process streamer rewards
     */
    protected function handlePaymentSuccess($transaction, $goldRate = null)
    {
        $user = User::find($transaction->user_id);
        if ($user) {
            $user->gold = ($user->gold ?? 0) + $transaction->gold_amount;
            $user->save();
        }

        // Process streamer reward
        if ($transaction->streamer_code && $goldRate) {
            $this->processStreamerReward(
                $transaction->streamer_code,
                $transaction->amount,
                $goldRate
            );
        }

        return $user;
    }

    /**
     * Log payment calculation details
     */
    protected function logPaymentCalculation($characterId, $factionData, $amount, $goldRate, $promoResult, $streamerResult, $goldAmount, $autoPromoResult = null)
    {
        \Log::info('Gold calculation', [
            'character_id' => $characterId,
            'faction_id' => $factionData['faction_id'],
            'faction_bonus_percentage' => $factionData['bonus_percentage'],
            'amount' => $amount,
            'gold_rate' => $goldRate,
            'promo_bonus_gold' => $promoResult['bonus_gold'],
            'auto_promo_bonus_gold' => $autoPromoResult ? $autoPromoResult['bonus_gold'] : 0,
            'streamer_bonus_gold' => $streamerResult['bonus_gold'],
            'total_gold' => $goldAmount,
        ]);
    }
}
