<?php

namespace Modules\WMSInventoryCore\App\Http\Controllers;

use App\ApiClasses\Error;
use App\ApiClasses\Success;
use App\Http\Controllers\Controller;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\DB;
use Illuminate\Support\Facades\Log;
use Modules\SystemCore\App\Models\CoreProduct;
use Modules\WMSInventoryCore\App\Http\Requests\StoreUnitRequest;
use Modules\WMSInventoryCore\App\Http\Requests\UpdateUnitRequest;
use Modules\WMSInventoryCore\App\Models\Unit;
use Yajra\DataTables\Facades\DataTables;

class UnitController extends Controller
{
    public function index()
    {
        $this->authorize('wmsinventory.view-units');

        return view('wmsinventorycore::units.index');
    }

    public function getDataAjax(Request $request)
    {
        $this->authorize('wmsinventory.view-units');
        $units = Unit::query();

        return DataTables::of($units)
            ->addColumn('actions', function ($unit) {
                $actions = [];

                if (auth()->user()->can('wmsinventory.edit-unit')) {
                    $actions[] = [
                        'label' => __('Edit'),
                        'icon' => 'bx bx-edit',
                        'class' => 'edit-record',
                        'data' => [
                            'id' => $unit->id,
                            'name' => $unit->name,
                            'code' => $unit->code,
                            'description' => $unit->description ?? '',
                            'bs-toggle' => 'offcanvas',
                            'bs-target' => '#offcanvasEditUnit',
                        ],
                    ];
                }

                if (auth()->user()->can('wmsinventory.delete-unit')) {
                    $actions[] = [
                        'label' => __('Delete'),
                        'icon' => 'bx bx-trash',
                        'class' => 'delete-record text-danger',
                        'data-id' => $unit->id,
                    ];
                }

                return view('components.datatable-actions', [
                    'id' => $unit->id,
                    'actions' => $actions,
                ])->render();
            })
            ->rawColumns(['actions'])
            ->make(true);
    }

    public function store(StoreUnitRequest $request)
    {
        try {
            DB::transaction(function () use ($request) {
                Unit::create([
                    'name' => $request->name,
                    'code' => $request->code,
                    'description' => $request->description,
                    'created_by_id' => auth()->id(),
                    'updated_by_id' => auth()->id(),
                ]);
            });

            return Success::response(__('Unit has been created successfully'));
        } catch (\Exception $e) {
            Log::error('Failed to create unit: '.$e->getMessage());

            return Error::response(__('Failed to create unit'));
        }
    }

    public function update(UpdateUnitRequest $request, $id)
    {
        try {
            $unit = Unit::findOrFail($id);

            DB::transaction(function () use ($request, $unit) {
                $unit->update([
                    'name' => $request->name,
                    'code' => $request->code,
                    'description' => $request->description,
                    'updated_by_id' => auth()->id(),
                ]);
            });

            return Success::response(__('Unit has been updated successfully'));
        } catch (\Exception $e) {
            Log::error('Failed to update unit: '.$e->getMessage());

            return Error::response(__('Failed to update unit'));
        }
    }

    public function destroy($id)
    {
        $this->authorize('wmsinventory.delete-unit');

        try {
            /** @var Unit $unit */
            $unit = Unit::findOrFail($id);

            // Check if any products use this unit as their unit of measure
            $productsUsingUnit = CoreProduct::where('unit_of_measure', $unit->name)
                ->orWhere('unit_of_measure', $unit->code)
                ->count();

            if ($productsUsingUnit > 0) {
                return Error::response(__('Cannot delete unit with existing products'));
            }

            DB::transaction(function () use ($unit) {
                $unit->delete();
            });

            return Success::response(__('Unit has been deleted successfully'));
        } catch (\Exception $e) {
            Log::error('Failed to delete unit: '.$e->getMessage());

            return Error::response(__('Failed to delete unit'));
        }
    }
}
