<?php

namespace App\Http\Controllers;

use App\Interfaces\LocationRepositoryInterface;
use App\Interfaces\ManufactureRepositoryInterface;
use App\Interfaces\TypeunitRepositoryInterface;
use App\Interfaces\UnitRepositoryInterface;
use App\Models\UnitType;
use Illuminate\Http\Request;
use PermissionHelper;
use Yajra\DataTables\DataTables;
use Illuminate\Database\QueryException;

class UnitController extends Controller
{
    /**
     * Display a listing of the resource.
     */
    protected $unitrepository;
    protected $unittypee;
    protected $manufacture;
    protected $locationrepository;

    public function __construct(UnitRepositoryInterface $unitrepository, TypeunitRepositoryInterface $unittype, ManufactureRepositoryInterface $manufacture, LocationRepositoryInterface $locationrepository)
    {
        $this->unitrepository = $unitrepository;
        $this->unittypee = $unittype;
        $this->manufacture = $manufacture;
        $this->locationrepository = $locationrepository;
    }

    public function index()
    {
        $data = $this->unitrepository->datatable();
        $unittype = $this->unittypee->all();
        $manufacture = $this->manufacture->all();
        $locations = $this->locationrepository->all();
        $canCreate = PermissionHelper::hasPermission("units")->create;

        if (request()->ajax()) {
            return $this->datatable($data);
        }

        return view('parts.unit.index', ['canCreate' => $canCreate, 'unittype' => $unittype, 'manufacture' => $manufacture, 'locations' => $locations]);
    }

    /**
     * Show the form for creating a new resource.
     */
    public function create()
    {
        //
    }

    /**
     * Store a newly created resource in storage.
     */
    public function store(Request $request)
    {
        $validated = $request->validate([
            'unit_code' => 'required|string|max:50|unique:units,unit_code',
            'unit_type_id' => 'required|exists:type_units,id',
            'manufacture_id' => 'required|exists:manufactures,id',
            'location_id' => 'required|exists:locations,id',
            'type_unit' => 'required|string|max:50',
            'production_year' => 'required|string|size:4|regex:/^[0-9]{4}$/',
            'serial_number_unit' => 'required|string|max:50',
            'serial_number_chassis' => 'required|string|max:50',
        ]);

        try {

            $validated["type_id"] = $validated["unit_type_id"];
            unset($validated["unit_type_id"]);
            $validated["unit_type"] = $validated["type_unit"];
            unset($validated["type_unit"]);
            $this->unitrepository->create($validated);

            return response()->json([
                'status' => 'success',
                'message' => 'Unit berhasil ditambahkan.'
            ]);
        } catch (\Exception $e) {
            return response()->json([
                'status' => 'error',
                'message' => 'Gagal menambahkan unit: ' . $e->getMessage()
            ], 500);
        }
    }

    /**
     * Display the specified resource.
     */
    public function show(string $id)
    {
        //
    }

    /**
     * Show the form for editing the specified resource.
     */
    public function edit(string $id)
    {
        //
    }

    /**
     * Update the specified resource in storage.
     */
    public function update(Request $request, string $id)
    {
        $validated = $request->validate([
            'unit_code' => 'required|string|max:50|unique:units,unit_code,' . $id,
            'unit_type_id' => 'required|exists:type_units,id',
            'manufacture_id' => 'required|exists:manufactures,id',
            'location_id' => 'required|exists:locations,id',
            'type_unit' => 'required|string|max:50',
            'production_year' => 'required|string|size:4|regex:/^[0-9]{4}$/',
            'serial_number_unit' => 'required|string|max:50',
            'serial_number_chassis' => 'required|string|max:50',
        ]);

        try {
            $validated["type_id"] = $validated["unit_type_id"];
            unset($validated["unit_type_id"]);
            $validated["unit_type"] = $validated["type_unit"];
            unset($validated["type_unit"]);
            $this->unitrepository->update($id, $validated);

            return response()->json([
                'status' => 'success',
                'message' => 'Unit berhasil diperbarui.'
            ]);
        } catch (\Exception $e) {
            return response()->json([
                'status' => 'error',
                'message' => 'Gagal memperbarui unit: ' . $e->getMessage()
            ], 500);
        }
    }

    /**
     * Remove the specified resource from storage.
     */
    public function destroy(string $id)
    {
        try {
            $this->unitrepository->delete($id);

            return response()->json([
                'success' => true,
                'message' => 'Unit berhasil dihapus!'
            ]);
        } catch (QueryException $e) {
            if ($e->getCode() == '23000') {
                return response()->json([
                    'success' => false,
                    'message' => 'Gagal menghapus Unit karena masih digunakan di data lain.'
                ], 400);
            }

            return response()->json([
                'success' => false,
                'message' => 'Terjadi kesalahan saat menghapus oli.'
            ], 500);
        }
    }

    public function datatable($data)
    {
        return DataTables::of($data)
            ->addIndexColumn()
            ->addColumn('action', function ($row) {
                $canEdit = PermissionHelper::hasPermission("units")->update;
                $canDelete = PermissionHelper::hasPermission("units")->delete;

                if (!$canEdit && !$canDelete) {
                    return "<span class='text-muted fst-italic'>Only View</span>";
                }

                $actionBtn = "<div class='d-flex gap-2'>";
                $actionBtn .= $canEdit ? '<a href="javascript:void(0)" class="edit btn btn-warning btn-sm"
                              data-id="' . $row->id . '"
                              data-unit_code="' . $row->unit_code . '"
                              data-unit_type_id="' . $row->type_id . '"
                              data-manufacture_id="' . $row->manufacture_id . '"
                              data-location_id="' . $row->location_id . '"
                              data-type_unit="' . $row->unit_type . '"
                              data-production_year="' . $row->production_year . '"
                              data-serial_number_unit="' . $row->serial_number_unit . '"
                              data-serial_number_chassis="' . $row->serial_number_chassis . '"
                              data-hours_meter="' . $row->hours_meter . '"
                              ><i class="fa fa-pencil"></i></a> ' : "";
                $actionBtn .= $canDelete ? '<a href="javascript:void(0)" class="delete btn btn-danger btn-sm" data-id="' . $row->id . '"><i class="fa fa-trash"></i></a>' : "";
                $actionBtn .= "</div>";
                return $actionBtn;
            })
            ->addColumn("unit_type", function ($row) {
                return $row->unittype->name ?? "-";
            })
            ->addColumn("manufacture", function ($row) {
                return $row->manufacture->name ?? "-";
            })
            ->addColumn("location", function ($row) {
                return $row->location->name ?? "-";
            })
            ->filterColumn('location', function ($query, $keyword) {
                $query->whereHas('location', fn($q) => $q->where('name', 'like', "%{$keyword}%"));
            })
            ->orderColumn('location', function ($query, $order) {
                $query->join('locations', 'locations.id', '=', 'units.location_id')
                    ->orderBy('locations.name', $order);
            })
            ->filterColumn('unit_type', function ($query, $keyword) {
                $query->whereHas('unittype', fn($q) => $q->where('name', 'like', "%{$keyword}%"));
            })
            ->orderColumn('unit_type', function ($query, $order) {
                $query->join('type_units', 'type_units.id', '=', 'units.type_id')
                    ->orderBy('type_units.name', $order);
            })
            ->rawColumns(['action'])
            ->make(true);
    }
}
