<?php

namespace App\Http\Controllers\Api\V1;

use App\Http\Controllers\Controller;
use App\Services\TempBillService;
use App\Models\Order;
use Illuminate\Http\Request;
use Illuminate\Http\JsonResponse;

class TempBillController extends Controller
{
    protected $tempBillService;

    public function __construct(TempBillService $tempBillService)
    {
        $this->tempBillService = $tempBillService;
    }

    /**
     * List all temp bills for current branch
     */
    public function index(Request $request): JsonResponse
    {
        $branchId = $request->input('branch_id') ?? $request->user()->branch_id;

        if (!$branchId) {
            return response()->json(['message' => 'Branch ID is required'], 400);
        }

        $tempBills = Order::tempBills()
            ->where('branch_id', $branchId)
            ->with(['items.product', 'user'])
            ->latest()
            ->get();

        return response()->json(['data' => $tempBills]);
    }

    /**
     * Create new temp bill
     */
    public function store(Request $request): JsonResponse
    {
        $validated = $request->validate([
            'branch_id' => 'required|exists:branches,id',
            'order_type' => 'required|in:dine_in,takeaway,delivery',
            'table_number' => 'nullable|integer',
            'customer_name' => 'nullable|string|max:255',
            'customer_phone' => 'nullable|string|max:20',
            'tax_amount' => 'nullable|numeric|min:0',
            'tax_rate' => 'nullable|numeric|min:0',
            'items' => 'required|array|min:1',
            'items.*.product_id' => 'required|exists:products,id',
            'items.*.product_name' => 'required|string|max:255',
            'items.*.quantity' => 'required|integer|min:1',
            'items.*.unit_price' => 'required|numeric|min:0',
            'items.*.selected_options' => 'nullable|array',
            'items.*.selected_inner_options' => 'nullable|array',
        ]);

        try {
            $tempBill = $this->tempBillService->createTempBill($validated);

            return response()->json([
                'message' => 'Temp bill created successfully',
                'data' => $tempBill,
            ], 201);
        } catch (\Exception $e) {
            return response()->json([
                'message' => 'Failed to create temp bill',
                'error' => $e->getMessage()
            ], 500);
        }
    }

    /**
     * Show temp bill details
     */
    public function show($id): JsonResponse
    {
        $order = Order::with(['items.product', 'payments', 'modifications.user'])
            ->findOrFail($id);

        return response()->json(['data' => $order]);
    }

    /**
     * Add item to temp bill
     */
    public function addItem(Request $request, $id): JsonResponse
    {
        $order = Order::findOrFail($id);

        $validated = $request->validate([
            'product_id' => 'required|exists:products,id',
            'product_name' => 'required|string|max:255',
            'quantity' => 'required|integer|min:1',
            'unit_price' => 'required|numeric|min:0',
            'selected_options' => 'nullable|array',
            'selected_inner_options' => 'nullable|array',
        ]);

        try {
            $item = $this->tempBillService->addItemToTempBill($order, $validated);

            return response()->json([
                'message' => 'Item added successfully',
                'data' => $order->fresh(['items.product']),
            ]);
        } catch (\Exception $e) {
            return response()->json([
                'message' => 'Failed to add item',
                'error' => $e->getMessage()
            ], 400);
        }
    }

    /**
     * Remove item from temp bill
     */
    public function removeItem($id, $itemId): JsonResponse
    {
        $order = Order::findOrFail($id);

        try {
            $this->tempBillService->removeItemFromTempBill($order, $itemId);

            return response()->json([
                'message' => 'Item removed successfully',
                'data' => $order->fresh(['items.product']),
            ]);
        } catch (\Exception $e) {
            return response()->json([
                'message' => 'Failed to remove item',
                'error' => $e->getMessage()
            ], 400);
        }
    }

    /**
     * Update item quantity
     */
    public function updateItem(Request $request, $id, $itemId): JsonResponse
    {
        $order = Order::findOrFail($id);

        $validated = $request->validate([
            'quantity' => 'required|integer|min:1',
        ]);

        try {
            $item = $this->tempBillService->updateItemQuantity(
                $order,
                $itemId,
                $validated['quantity']
            );

            return response()->json([
                'message' => 'Item updated successfully',
                'data' => $order->fresh(['items.product']),
            ]);
        } catch (\Exception $e) {
            return response()->json([
                'message' => 'Failed to update item',
                'error' => $e->getMessage()
            ], 400);
        }
    }

    /**
     * Lock bill for payment
     */
    public function lockForPayment($id): JsonResponse
    {
        $order = Order::findOrFail($id);

        try {
            $order = $this->tempBillService->lockForPayment($order);

            return response()->json([
                'message' => 'Bill locked for payment',
                'data' => $order,
            ]);
        } catch (\Exception $e) {
            return response()->json([
                'message' => 'Failed to lock bill',
                'error' => $e->getMessage()
            ], 400);
        }
    }

    /**
     * Cancel temp bill
     */
    public function cancel(Request $request, $id): JsonResponse
    {
        $order = Order::findOrFail($id);

        $validated = $request->validate([
            'reason' => 'nullable|string|max:500',
        ]);

        try {
            $order = $this->tempBillService->cancelTempBill($order, $validated['reason'] ?? null);

            return response()->json([
                'message' => 'Temp bill cancelled',
                'data' => $order,
            ]);
        } catch (\Exception $e) {
            return response()->json([
                'message' => 'Failed to cancel bill',
                'error' => $e->getMessage()
            ], 400);
        }
    }

    /**
     * Get modification history
     */
    public function getModifications($id): JsonResponse
    {
        $order = Order::findOrFail($id);

        $modifications = $order->modifications()
            ->with('user:id,name')
            ->orderBy('created_at', 'desc')
            ->get();

        return response()->json(['data' => $modifications]);
    }
}
