<?php

namespace App\Http\Controllers;

use Illuminate\Http\Request;
use App\Models\Client;
use App\Models\CustomAccount;
use App\Models\Setting;
use Illuminate\Support\Facades\Auth;
use Barryvdh\DomPDF\Facade\Pdf;

class ClientController extends Controller
{
    /**
     * Display a listing of clients.
     */
    public function index(Request $request)
    {
        $search = $request->input('search');
        $tab = $request->input('tab', 'clients');
        $perPage = preg_match('/Mobile|Android|iPhone/i', request()->header('User-Agent')) ? 10 : 20;

        if ($tab === 'custom') {
            $customAccounts = CustomAccount::when($search, function ($query, $search) {
                $query->where('name', 'like', "%{$search}%")
                      ->orWhere('email', 'like', "%{$search}%")
                      ->orWhere('account_type', 'like', "%{$search}%");
            })->latest()->paginate($perPage)->withQueryString();
            $clients = collect();
        } else {
            $clients = Client::when($search, function ($query, $search) {
                $query->where('first_name', 'like', "%{$search}%")
                      ->orWhere('last_name', 'like', "%{$search}%")
                      ->orWhere('email', 'like', "%{$search}%")
                      ->orWhere('phone', 'like', "%{$search}%")
                      ->orWhere('mobile', 'like', "%{$search}%")
                      ->orWhere('company_name', 'like', "%{$search}%");
            })->latest()->paginate($perPage)->withQueryString();
            $customAccounts = collect();
        }

        try {
            $currencySymbol = Setting::where('key', 'currency_symbol')->value('value') ?? '£';
        } catch (\Exception $e) {
            $currencySymbol = '£';
        }

        return view('clients.index', compact('clients', 'customAccounts', 'search', 'tab', 'currencySymbol'));
    }

    /**
     * Show the form for creating a new client.
     */
    public function create()
    {
        if (Auth::user()->isAccountant()) {
            return redirect()->route('clients.index')->with('error', 'Accountants cannot create client profiles.');
        }
        return view('clients.create');
    }

    /**
     * Store a newly created client in storage.
     */
    public function store(Request $request)
    {
        if (Auth::user()->isAccountant()) {
            return redirect()->route('clients.index')->with('error', 'Accountants cannot create client profiles.');
        }

        $recordType = $request->input('record_type', 'client');

        if ($recordType === 'custom') {
            $request->validate([
                'custom_account_name' => 'required|string|max:255',
                'custom_account_email' => 'nullable|email|max:255',
                'custom_account_type' => 'required|string|max:255',
                'custom_account_notes' => 'nullable|string',
                'custom_account_opening_balance' => 'nullable|numeric',
            ]);

            CustomAccount::create([
                'name' => $request->input('custom_account_name'),
                'email' => $request->input('custom_account_email'),
                'account_type' => $request->input('custom_account_type'),
                'notes' => $request->input('custom_account_notes'),
                'opening_balance' => $request->input('custom_account_opening_balance', 0.00),
                'created_by' => Auth::id(),
                'updated_by' => Auth::id(),
            ]);

            return redirect()->route('clients.index', ['tab' => 'custom'])->with('success', 'Custom account created successfully!');
        }

        $request->validate([
            'title' => 'required|string',
            'first_name' => 'required|string|max:255',
            'last_name' => 'required|string|max:255',
            'email' => 'nullable|email|max:255',
            'phone' => 'nullable|string|max:50',
            'mobile' => 'nullable|string|max:50',
            'company_name' => 'nullable|string|max:255',
            'company_vat' => 'nullable|string|max:100',
            'address_line1' => 'nullable|string|max:255',
            'address_line2' => 'nullable|string|max:255',
            'city' => 'nullable|string|max:100',
            'state' => 'nullable|string|max:100',
            'postcode' => 'nullable|string|max:20',
            'country' => 'nullable|string|max:2',
            'opening_balance' => 'nullable|numeric',
            'internal_notes' => 'nullable|string',
        ]);

        $clientData = $request->only([
            'title', 'first_name', 'last_name', 'email', 'phone', 'mobile',
            'company_name', 'company_vat', 'address_line1', 'address_line2',
            'city', 'state', 'postcode', 'country', 'opening_balance', 'internal_notes'
        ]);
        $clientData['created_by'] = Auth::id();
        $clientData['updated_by'] = Auth::id();

        Client::create($clientData);

        return redirect()->route('clients.index')->with('success', 'Client profile created successfully!');
    }

    /**
     * Display the specified client profile.
     */
    public function show(Client $client)
    {
        $client->load([
            'cashIns.paymentMethod', 'cashIns.paymentType', 'cashIns.bankAccount',
            'cashOuts.paymentMethod', 'cashOuts.paymentType', 'cashOuts.bankAccount',
            'deals', 'consignments.expenses', 'consignments.cashOuts',
            'buyerConsignments', 'sellerConsignments'
        ]);

        try {
            $currencySymbol = Setting::where('key', 'currency_symbol')->value('value') ?? '£';
        } catch (\Exception $e) {
            $currencySymbol = '£';
        }

        $totalCashIn = $client->cashIns->where('payment_status', 'paid')->sum('amount');
        $totalCashOut = $client->cashOuts->where('payment_status', 'paid')->sum('amount');
        $totalDeals = $client->deals->sum('deal_value');
        
        $totalProjectCostShares = 0;
        foreach ($client->consignments as $consignment) {
            if ($consignment->investor_share_type === 'fixed') {
                $totalProjectCostShares += $consignment->investor_share_value;
            } else {
                $projectOutflows = $consignment->cashOuts->where('payment_status', 'paid')->sum('amount') 
                                   + $consignment->expenses->sum('amount');
                $totalProjectCostShares += $projectOutflows * ($consignment->investor_share_value / 100);
            }
        }

        $openingBalance = $client->opening_balance ?? 0.00;
        $balance = $openingBalance + $totalDeals + $totalProjectCostShares - $totalCashIn + $totalCashOut;

        return view('clients.show', compact(
            'client', 'totalCashIn', 'totalCashOut', 'totalDeals', 
            'totalProjectCostShares', 'openingBalance', 'balance', 'currencySymbol'
        ));
    }

    /**
     * Show the form for editing the client.
     */
    public function edit(Client $client)
    {
        if (Auth::user()->isAccountant()) {
            return redirect()->route('clients.index')->with('error', 'Accountants cannot edit client profiles.');
        }
        return view('clients.edit', compact('client'));
    }

    /**
     * Update the specified client profile in storage.
     */
    public function update(Request $request, Client $client)
    {
        if (Auth::user()->isAccountant()) {
            return redirect()->route('clients.index')->with('error', 'Accountants cannot edit client profiles.');
        }

        $request->validate([
            'title' => 'required|string',
            'first_name' => 'required|string|max:255',
            'last_name' => 'required|string|max:255',
            'email' => 'nullable|email|max:255',
            'phone' => 'nullable|string|max:50',
            'mobile' => 'nullable|string|max:50',
            'company_name' => 'nullable|string|max:255',
            'company_vat' => 'nullable|string|max:100',
            'address_line1' => 'nullable|string|max:255',
            'address_line2' => 'nullable|string|max:255',
            'city' => 'nullable|string|max:100',
            'state' => 'nullable|string|max:100',
            'postcode' => 'nullable|string|max:20',
            'country' => 'nullable|string|max:2',
            'opening_balance' => 'nullable|numeric',
            'internal_notes' => 'nullable|string',
        ]);

        $clientData = $request->only([
            'title', 'first_name', 'last_name', 'email', 'phone', 'mobile',
            'company_name', 'company_vat', 'address_line1', 'address_line2',
            'city', 'state', 'postcode', 'country', 'opening_balance', 'internal_notes'
        ]);
        $clientData['updated_by'] = Auth::id();

        $client->update($clientData);

        return redirect()->route('clients.show', $client->id)->with('success', 'Client profile updated successfully!');
    }

    /**
     * Remove the specified client from storage.
     */
    public function destroy(Client $client)
    {
        if (Auth::user()->isAccountant()) {
            return redirect()->route('clients.index')->with('error', 'Accountants cannot delete client profiles.');
        }

        $client->delete();

        return redirect()->route('clients.index')->with('success', 'Client profile permanently deleted.');
    }

    /**
     * Download client ledger statement as PDF.
     */
    public function downloadLedgerPdf(Client $client)
    {
        $client->load([
            'cashIns.paymentMethod', 'cashIns.paymentType',
            'cashOuts.paymentMethod', 'cashOuts.paymentType',
            'deals', 'consignments.expenses', 'consignments.cashOuts'
        ]);

        try {
            $currencySymbol = Setting::where('key', 'currency_symbol')->value('value') ?? '£';
            $businessName = Setting::where('key', 'business_name')->value('value') ?? 'My Business';
        } catch (\Exception $e) {
            $currencySymbol = '£';
            $businessName = 'My Business';
        }

        $totalCashIn = $client->cashIns->where('payment_status', 'paid')->sum('amount');
        $totalCashOut = $client->cashOuts->where('payment_status', 'paid')->sum('amount');
        $totalDeals = $client->deals->sum('deal_value');
        
        $totalProjectCostShares = 0;
        foreach ($client->consignments as $consignment) {
            if ($consignment->investor_share_type === 'fixed') {
                $totalProjectCostShares += $consignment->investor_share_value;
            } else {
                $projectOutflows = $consignment->cashOuts->where('payment_status', 'paid')->sum('amount') 
                                   + $consignment->expenses->sum('amount');
                $totalProjectCostShares += $projectOutflows * ($consignment->investor_share_value / 100);
            }
        }

        $openingBalance = $client->opening_balance ?? 0.00;
        $balance = $openingBalance + $totalDeals + $totalProjectCostShares - $totalCashIn + $totalCashOut;

        $pdf = Pdf::loadView('reports.templates.client_ledger', compact(
            'client', 'totalCashIn', 'totalCashOut', 'totalDeals', 'totalProjectCostShares', 'openingBalance', 'balance', 'currencySymbol', 'businessName'
        ));

        return $pdf->download("Client_Ledger_" . str_replace(' ', '_', $client->first_name . '_' . $client->last_name) . ".pdf");
    }
}
