<?php

namespace App\Http\Controllers;

use App\Models\PurchaseOrder;
use App\Models\UtilityFee;
use Illuminate\Http\Request;
use Inertia\Inertia;
use Illuminate\Support\Carbon;
use Illuminate\Pagination\LengthAwarePaginator;

class AccountingReportController extends Controller
{
    public function index(Request $request)
    {
        $dateStart = $request->input('date_start', Carbon::now()->toDateString());
        $dateEnd = $request->input('date_end', Carbon::now()->toDateString());

        // 1. Get Purchase Orders (Completed or Received that are ready for accounting)
        $purchaseOrders = PurchaseOrder::with(['vendor'])
            ->whereIn('status', ['received', 'completed'])
            ->whereBetween('created_at', [$dateStart . ' 00:00:00', $dateEnd . ' 23:59:59'])
            ->get()
            ->map(function ($po) {
                return [
                    'id' => 'PO-' . $po->id,
                    'date' => Carbon::parse($po->created_at)->timezone(config('app.timezone'))->toDateString(),
                    'source' => '採購單',
                    'category' => '進貨支出',
                    'item' => $po->vendor->name ?? '未知廠商',
                    'reference' => $po->code,
                    'invoice_number' => $po->invoice_number,
                    'amount' => $po->grand_total,
                ];
            });

        // 2. Get Utility Fees
        $utilityFees = UtilityFee::whereBetween('transaction_date', [$dateStart, $dateEnd])
            ->get()
            ->map(function ($fee) {
                return [
                    'id' => 'UF-' . $fee->id,
                    'date' => $fee->transaction_date->format('Y-m-d'),
                    'source' => '公共事業費',
                    'category' => $fee->category,
                    'item' => $fee->description ?: $fee->category,
                    'reference' => '-',
                    'invoice_number' => $fee->invoice_number,
                    'amount' => $fee->amount,
                ];
            });

        // Combine and Sort
        $allRecords = $purchaseOrders->concat($utilityFees)
            ->sortByDesc('date')
            ->values();

        // 3. Manual Pagination
        $perPage = $request->input('per_page', 10);
        $page = $request->input('page', 1);
        $offset = ($page - 1) * $perPage;

        $paginatedRecords = new LengthAwarePaginator(
            $allRecords->slice($offset, $perPage)->values(),
            $allRecords->count(),
            $perPage,
            $page,
            ['path' => $request->url(), 'query' => $request->query()]
        );

        $summary = [
            'total_amount' => $allRecords->sum('amount'),
            'purchase_total' => $purchaseOrders->sum('amount'),
            'utility_total' => $utilityFees->sum('amount'),
            'record_count' => $allRecords->count(),
        ];

        return Inertia::render('Accounting/Report', [
            'records' => $paginatedRecords,
            'summary' => $summary,
            'filters' => [
                'date_start' => $dateStart,
                'date_end' => $dateEnd,
                'per_page' => (int)$perPage,
            ],
        ]);
    }

    public function export(Request $request)
    {
        $dateStart = $request->input('date_start', Carbon::now()->toDateString());
        $dateEnd = $request->input('date_end', Carbon::now()->toDateString());
        $selectedIdsParam = $request->input('selected_ids');

        $purchaseOrdersQuery = PurchaseOrder::with(['vendor'])
            ->whereIn('status', ['received', 'completed']);
        
        $utilityFeesQuery = UtilityFee::query();

        if ($selectedIdsParam) {
            $ids = explode(',', $selectedIdsParam);
            $poIds = [];
            $ufIds = [];
            foreach ($ids as $id) {
                if (str_starts_with($id, 'PO-')) {
                    $poIds[] = substr($id, 3);
                } elseif (str_starts_with($id, 'UF-')) {
                    $ufIds[] = substr($id, 3);
                }
            }
            $purchaseOrders = $purchaseOrdersQuery->whereIn('id', $poIds)->get();
            $utilityFees = $utilityFeesQuery->whereIn('id', $ufIds)->get();
        } else {
            $purchaseOrders = $purchaseOrdersQuery
                ->whereBetween('created_at', [$dateStart . ' 00:00:00', $dateEnd . ' 23:59:59'])
                ->get();
            $utilityFees = $utilityFeesQuery
                ->whereBetween('transaction_date', [$dateStart, $dateEnd])
                ->get();
        }

        $allRecords = collect();

        foreach ($purchaseOrders as $po) {
            $allRecords->push([
                Carbon::parse($po->created_at)->toDateString(),
                '採購單',
                '進貨支出',
                $po->vendor->name ?? '',
                $po->code,
                $po->invoice_number,
                (float)$po->grand_total,
            ]);
        }

        foreach ($utilityFees as $fee) {
            $allRecords->push([
                Carbon::parse($fee->transaction_date)->toDateString(),
                '公共事業費',
                $fee->category,
                $fee->description,
                '-',
                $fee->invoice_number,
                (float)$fee->amount,
            ]);
        }

        $allRecords = $allRecords->sortByDesc(0);

        $filename = "accounting_report_{$dateStart}_{$dateEnd}.csv";
        $headers = [
            'Content-Type' => 'text/csv; charset=UTF-8',
            'Content-Disposition' => "attachment; filename=\"{$filename}\"",
        ];

        $callback = function () use ($allRecords) {
            $file = fopen('php://output', 'w');
            // BOM for Excel compatibility with UTF-8
            fprintf($file, chr(0xEF).chr(0xBB).chr(0xBF));
            
            fputcsv($file, ['日期', '來源', '類別', '項目', '參考單號', '發票號碼', '金額']);

            foreach ($allRecords as $row) {
                fputcsv($file, $row);
            }
            fclose($file);
        };

        return response()->stream($callback, 200, $headers);
    }
}
