<?php

namespace App\Http\Controllers\Api;

use App\Http\Controllers\Controller;
use App\Models\Purchase;
use App\Models\PurchaseReturn;
use App\Services\ActivityLogger;
use App\Services\NotificationService;
use App\Services\PurchaseReturnService;
use Illuminate\Http\Request;
use Illuminate\Validation\Rule;

class PurchaseReturnController extends Controller
{
    public function __construct(
        protected PurchaseReturnService $purchaseReturnService
    ) {}

    public function index(Request $request)
    {
        $this->authorize('view-purchase-returns');

        $query = PurchaseReturn::with(['purchase', 'supplier', 'user', 'items.product'])
            ->orderBy('created_at', 'desc');

        if ($request->filled('status')) {
            $query->where('status', $request->status);
        }

        if ($request->filled('supplier_id')) {
            $query->where('supplier_id', $request->supplier_id);
        }

        if ($request->filled('start_date')) {
            $query->whereDate('created_at', '>=', $request->start_date);
        }

        if ($request->filled('end_date')) {
            $query->whereDate('created_at', '<=', $request->end_date);
        }

        if ($request->filled('search')) {
            $search = $request->search;
            $query->where(function ($q) use ($search) {
                $q->where('return_number', 'like', "%{$search}%")
                  ->orWhereHas('supplier', fn ($q2) => $q2->where('name', 'like', "%{$search}%"))
                  ->orWhereHas('purchase', fn ($q2) => $q2->where('purchase_number', 'like', "%{$search}%"));
            });
        }

        $returns = $query->paginate(min((int) $request->input('per_page', 15), 100));

        return response()->json($returns);
    }

    public function store(Request $request)
    {
        $this->authorize('create-purchase-returns');

        $orgId = app('current_organization_id');

        $validated = $request->validate([
            'purchase_id'              => ['required', Rule::exists('purchases', 'id')->where('organization_id', $orgId)],
            'reason'                   => 'required|string|max:1000',
            'notes'                    => 'nullable|string',
            'items'                    => 'required|array|min:1',
            'items.*.purchase_item_id' => 'required|integer',
            'items.*.quantity'         => 'required|integer|min:1',
            'items.*.reason'           => 'nullable|string',
        ]);

        try {
            $purchaseReturn = $this->purchaseReturnService->create($validated, $request->user());

            ActivityLogger::log(
                'purchase_return_created',
                "Purchase return {$purchaseReturn->return_number} created for PO #{$purchaseReturn->purchase->purchase_number}",
                $purchaseReturn
            );

            return response()->json(['data' => $purchaseReturn->load('items.product', 'supplier', 'purchase', 'user')], 201);
        } catch (\Exception $e) {
            return response()->json(['message' => $e->getMessage()], 422);
        }
    }

    public function show(PurchaseReturn $purchaseReturn)
    {
        $this->authorize('view-purchase-returns');

        return response()->json([
            'data' => $purchaseReturn->load('items.product', 'supplier', 'purchase', 'user'),
        ]);
    }

    public function complete(PurchaseReturn $purchaseReturn, Request $request)
    {
        $this->authorize('manage-purchase-returns');

        try {
            $purchaseReturn = $this->purchaseReturnService->complete($purchaseReturn);

            $orgId    = app('current_organization_id');
            $branchId = app()->bound('current_branch_id') ? app('current_branch_id') : null;
            $supplier = $purchaseReturn->supplier?->name ?? 'Unknown Supplier';

            NotificationService::notifyRoles(
                $orgId,
                $branchId,
                ['super-admin', 'admin', 'org-owner'],
                'purchase_return_completed',
                "Purchase Return Completed — {$purchaseReturn->return_number}",
                "Return of goods to {$supplier} has been completed. Inventory deducted by " . number_format((float) $purchaseReturn->total_amount, 2),
                ['purchase_return_id' => $purchaseReturn->id]
            );

            ActivityLogger::log(
                'purchase_return_completed',
                "Purchase return {$purchaseReturn->return_number} completed — inventory deducted",
                $purchaseReturn
            );

            return response()->json([
                'message' => 'Purchase return completed and inventory updated.',
                'data'    => $purchaseReturn->load('items.product', 'supplier', 'purchase', 'user'),
            ]);
        } catch (\Exception $e) {
            return response()->json(['message' => $e->getMessage()], 422);
        }
    }

    public function cancel(PurchaseReturn $purchaseReturn)
    {
        $this->authorize('manage-purchase-returns');

        try {
            $purchaseReturn = $this->purchaseReturnService->cancel($purchaseReturn);

            ActivityLogger::log(
                'purchase_return_cancelled',
                "Purchase return {$purchaseReturn->return_number} cancelled",
                $purchaseReturn
            );

            return response()->json([
                'message' => 'Purchase return cancelled.',
                'data'    => $purchaseReturn,
            ]);
        } catch (\Exception $e) {
            return response()->json(['message' => $e->getMessage()], 422);
        }
    }
}
