<?php

namespace App\Http\Controllers\Admin;

use App\Http\Controllers\Controller;
use App\Http\Requests\Admin\CurrencyIndexRequest;
use App\Http\Requests\Admin\CurrencyLastUpdateInfoRequest;
use App\Http\Requests\Admin\CurrencyRecordsRequest;
use App\Http\Requests\Admin\CurrencyUpdateRatesRequest;
use App\Http\Requests\Admin\CurrencyUpdateRequest;
use App\Jobs\UpdateCurrencyRates;
use App\Models\Currency;
use App\Models\Setting;
use App\Traits\LogsAdminActivity;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Cache;
use Illuminate\Support\Facades\DB;
use Illuminate\Support\Facades\Log;

class CurrencyController extends Controller
{
    use LogsAdminActivity;

    /**
     * Para birimleri listesi görünümü + PRC-306 üst settings kartları
     */
    public function index(CurrencyIndexRequest $request)
    {
        $currencies = Currency::orderBy('code')->get(['id', 'code', 'name']);
        $settings = [
            'default_currency' => (int) Setting::getValue('default_currency', 1),
            'fx_provider_failover_order' => Setting::getValue('fx_provider_failover_order', 'ecb,open_er_api,open_exchange_rates,fixer'),
        ];
        // PRC-655 — FX credential'ları artık module_settings'te (/admin/currency-providers);
        // bu sayfa yalnız default currency + failover order yönetir.
        return view('admin.currencies.index', compact('currencies', 'settings'));
    }

    /**
     * PRC-306: Üst settings kartlarından save (default_currency + FX driver keys + failover order).
     */
    public function saveSettings(Request $request)
    {
        // PRC-655 — FX credential (fx_*_api_key) yazımı kaldırıldı; credential'lar
        // /admin/currency-providers (module_settings) üzerinden yönetilir. Bu sayfa
        // yalnız default currency + provider failover order yazar.
        $data = $request->validate([
            'default_currency' => 'nullable|integer|min:1|exists:currencies,id',
            'fx_provider_failover_order' => 'nullable|string|max:255',
        ]);

        if (isset($data['default_currency'])) {
            Setting::setValue('default_currency', (int) $data['default_currency']);
        }
        if (isset($data['fx_provider_failover_order'])) {
            Setting::setValue('fx_provider_failover_order', $data['fx_provider_failover_order']);
        }

        \App\Models\Log::create([
            'type' => \App\Models\Log::TYPE_ADMIN,
            'admin_id' => auth('admin')->id(),
            'description' => 'Updated currency + FX provider settings via /admin/settings/currencies',
        ]);

        return redirect()->route('admin.settings.currencies.index')
            ->with('success', __('admin/currencies.settings_saved'));
    }

    /**
     * DataTables için para birimi kayıtları
     */
    public function records(CurrencyRecordsRequest $request)
    {

        $draw = $request->get('draw', 1);
        $start = $request->get('start', 0);
        $length = $request->get('length', 10);
        $rawSearch = $request->get('search', null);
        $searchValue = '';
        if (is_array($rawSearch)) {
            $searchValue = $rawSearch['value'] ?? '';
        } elseif (! is_null($rawSearch)) {
            $searchValue = (string) $rawSearch;
        }

        $query = Currency::query();

        // Temel arama
        if (! empty($searchValue)) {
            $query->where(function ($q) use ($searchValue) {
                $q->where('name', 'like', "%{$searchValue}%")
                    ->orWhere('code', 'like', "%{$searchValue}%")
                    ->orWhere('prefix', 'like', "%{$searchValue}%")
                    ->orWhere('suffix', 'like', "%{$searchValue}%");
            });
        }

        // Toplam kayıt sayısı
        $totalRecords = $query->count();

        // Sıralama
        $query->orderBy('is_default', 'desc');
        $query->orderBy('status', 'desc');

        // Sayfalama
        $records = $query->offset($start)
            ->limit($length)
            ->get();

        return response()->json([
            'draw' => $draw,
            'recordsTotal' => $totalRecords,
            'recordsFiltered' => $totalRecords,
            'data' => $records,
        ]);
    }

    /**
     * Para birimi bilgilerini güncelle
     */
    public function update(CurrencyUpdateRequest $request, Currency $currency)
    {

        try {
            DB::beginTransaction();

            $data = [
                'name' => $request->name,
                'prefix' => $request->prefix,
                'suffix' => $request->suffix,
                'rate' => $request->rate,
                'status' => $request->status,
                'is_default' => $request->filled('is_default') ? $request->is_default : $currency->is_default,
            ];

            // Varsayılan para birimi olarak işaretlenmişse, diğer para birimlerini güncelle
            if ($request->filled('is_default') && $request->is_default) {
                Currency::where('id', '!=', $currency->id)
                    ->where('is_default', true)
                    ->update(['is_default' => false]);
            } elseif ($currency->is_default && $request->filled('is_default') && ! $request->is_default) {
                // Eğer bu kayıt varsayılan ise ve varsayılan olmaktan çıkarılmak isteniyorsa
                // Buna izin verme, en az bir varsayılan para birimi olmalı
                return response()->json([
                    'success' => false,
                    'message' => __('admin/currencies.messages_default_required'),
                ], 422);
            }

            $currency->update($data);

            $this->logUpdated($currency, "Updated currency #{$currency->id} - {$currency->code}");

            DB::commit();

            return response()->json([
                'success' => true,
                'message' => __('admin/currencies.messages_updated'),
                'data' => $currency,
            ]);
        } catch (\Exception $e) {
            DB::rollBack();
            Log::error('Currency update error: '.$e->getMessage());

            return response()->json([
                'success' => false,
                'message' => __('admin/currencies.messages_update_error'),
            ], 500);
        }
    }

    /**
     * Para birimi kurlarını manuel olarak güncelle
     */
    public function updateRates(CurrencyUpdateRatesRequest $request)
    {

        // Job'ı hemen çalıştır
        UpdateCurrencyRates::dispatchSync();

        // Son güncelleme zamanını al
        $lastUpdated = Cache::get('currency_rates_last_updated', null);

        if ($lastUpdated) {
            $message = __('admin/currencies.messages_rates_updated', ['time' => $lastUpdated]);
        } else {
            $message = __('admin/currencies.messages_rates_update_requested');
        }

        return response()->json([
            'success' => true,
            'message' => $message,
            'last_updated' => $lastUpdated,
        ]);
    }

    /**
     * Son kur güncelleme bilgisini getir
     */
    public function getLastUpdateInfo(CurrencyLastUpdateInfoRequest $request)
    {

        // Son güncelleme zamanını al
        $lastUpdated = Cache::get('currency_rates_last_updated', null);

        // Varsayılan para birimini bul
        $defaultCurrency = Currency::where('is_default', true)->first();
        $baseCurrency = $defaultCurrency ? $defaultCurrency->code : null;

        return response()->json([
            'success' => true,
            'last_updated' => $lastUpdated,
            'base_currency' => $baseCurrency,
        ]);
    }
}
