<?php

namespace Modules\Vrc\Http\Controllers;

use Illuminate\Http\Request;
use Modules\Vrc\Entities\VrcNcr;
use Modules\Vrc\Entities\VrcRepairOrder;
use Modules\Vrc\Entities\VrcTicket;
use Modules\Vrc\Entities\VrcTicketMessage;
use Yajra\DataTables\Facades\DataTables;

class TicketController extends VrcBaseController
{
    public function index()
    {
        $this->guard('vrc.ticket.view');

        if (request()->ajax()) {
            $tickets = VrcTicket::where('business_id', $this->businessId())
                ->select(['id', 'subject', 'status', 'priority', 'category', 'opened_at']);

            $canManage = auth()->user()->can('vrc.ticket.manage');

            return DataTables::of($tickets)
                ->editColumn('subject', fn ($t) => e($t->subject) ?: ('#' . $t->id))
                ->editColumn('status', fn ($t) => '<span class="label label-default">' . e(ucfirst(str_replace('_', ' ', $t->status))) . '</span>')
                ->editColumn('priority', fn ($t) => e(ucfirst((string) $t->priority)))
                ->editColumn('category', fn ($t) => e(ucfirst((string) $t->category)))
                ->editColumn('opened_at', fn ($t) => $t->opened_at ? $t->opened_at->format('Y-m-d H:i') : '—')
                ->addColumn('action', function ($t) use ($canManage) {
                    $btns = '<a href="' . route('vrc.tickets.show', $t->id) . '" class="btn btn-xs btn-primary"><i class="fa fa-folder-open"></i> View</a> ';
                    if ($canManage) {
                        $btns .= '<button data-href="' . route('vrc.tickets.edit', $t->id) . '" class="btn btn-xs btn-info vrc-modal-btn"><i class="fa fa-edit"></i></button> '
                            . '<button data-href="' . route('vrc.tickets.destroy', $t->id) . '" class="btn btn-xs btn-danger vrc-delete"><i class="fa fa-trash"></i></button>';
                    }
                    return $btns;
                })
                ->rawColumns(['status', 'action'])
                ->make(true);
        }

        return view('vrc::tickets.index');
    }

    public function create()
    {
        $this->guard('vrc.ticket.manage');
        return view('vrc::tickets.create', ['statuses' => VrcTicket::STATUSES]);
    }

    public function store(Request $request)
    {
        $this->guard('vrc.ticket.manage');
        $data = $this->rules($request);
        try {
            $data['business_id'] = $this->businessId();
            $data['opened_at'] = now();
            $data['status'] = $data['status'] ?? 'open';
            $data['source'] = 'staff';
            VrcTicket::create($data);
            return $this->ok(__('vrc::lang.added_success'));
        } catch (\Exception $e) {
            \Log::emergency($e->getMessage());
            return $this->fail();
        }
    }

    public function show($id)
    {
        $this->guard('vrc.ticket.view');
        $ticket = VrcTicket::with(['messages', 'vehicle'])
            ->where('business_id', $this->businessId())->findOrFail($id);

        $repairOrder = $ticket->repair_order_id
            ? VrcRepairOrder::where('business_id', $this->businessId())->find($ticket->repair_order_id)
            : null;

        return view('vrc::tickets.show', [
            'ticket'      => $ticket,
            'messages'    => $ticket->messages,
            'statuses'    => VrcTicket::STATUSES,
            'repairOrder' => $repairOrder,
            'vehicle'     => $ticket->vehicle,
        ]);
    }

    public function edit($id)
    {
        $this->guard('vrc.ticket.manage');
        $ticket = VrcTicket::where('business_id', $this->businessId())->findOrFail($id);
        return view('vrc::tickets.edit', ['ticket' => $ticket, 'statuses' => VrcTicket::STATUSES]);
    }

    public function update(Request $request, $id)
    {
        $this->guard('vrc.ticket.manage');
        $data = $this->rules($request);
        try {
            $ticket = VrcTicket::where('business_id', $this->businessId())->findOrFail($id);
            $ticket->update($data);
            return $this->ok(__('vrc::lang.updated_success'));
        } catch (\Exception $e) {
            \Log::emergency($e->getMessage());
            return $this->fail();
        }
    }

    public function destroy($id)
    {
        $this->guard('vrc.ticket.manage');
        try {
            VrcTicket::where('business_id', $this->businessId())->findOrFail($id)->delete();
            return $this->ok(__('vrc::lang.deleted_success'));
        } catch (\Exception $e) {
            \Log::emergency($e->getMessage());
            return $this->fail();
        }
    }

    /** Staff reply on the ticket thread (full-page form, redirect back). */
    public function postMessage(Request $request, $id)
    {
        $this->guard('vrc.ticket.view');
        $ticket = VrcTicket::where('business_id', $this->businessId())->findOrFail($id);
        $request->validate(['body' => 'required|string']);

        try {
            VrcTicketMessage::create([
                'business_id' => $ticket->business_id,
                'ticket_id'   => $ticket->id,
                'author_type' => 'staff',
                'author_id'   => $this->userId(),
                'body'        => $request->input('body'),
                'created_at'  => now(),
            ]);
            return back()->with('status', ['success' => 1, 'msg' => 'Reply added.']);
        } catch (\Exception $e) {
            \Log::emergency($e->getMessage());
            return back()->with('status', ['success' => 0, 'msg' => __('messages.something_went_wrong')]);
        }
    }

    /** Change ticket status (full-page form, redirect back). */
    public function changeStatus(Request $request, $id)
    {
        $this->guard('vrc.ticket.manage');
        $ticket = VrcTicket::where('business_id', $this->businessId())->findOrFail($id);
        $request->validate(['status' => 'required|in:' . implode(',', VrcTicket::STATUSES)]);

        try {
            $new = $request->input('status');
            $old = $ticket->status;
            $ticket->status = $new;
            if (in_array($new, ['resolved', 'closed'], true)) {
                $ticket->resolved_at = now();
            }
            $ticket->save();

            VrcTicketMessage::create([
                'business_id' => $ticket->business_id,
                'ticket_id'   => $ticket->id,
                'author_type' => 'system',
                'author_id'   => $this->userId(),
                'body'        => 'Status changed from ' . str_replace('_', ' ', $old) . ' to ' . str_replace('_', ' ', $new) . '.',
                'created_at'  => now(),
            ]);

            return back()->with('status', ['success' => 1, 'msg' => 'Status updated.']);
        } catch (\Exception $e) {
            \Log::emergency($e->getMessage());
            return back()->with('status', ['success' => 0, 'msg' => __('messages.something_went_wrong')]);
        }
    }

    /** Escalate the ticket into a Non-Conformance Report. */
    public function escalate($id)
    {
        $this->guard('vrc.ticket.manage');
        $ticket = VrcTicket::where('business_id', $this->businessId())->findOrFail($id);

        try {
            $ncr = VrcNcr::create([
                'business_id'     => $ticket->business_id,
                'source'          => 'complaint',
                'title'           => $ticket->subject,
                'description'     => $ticket->description,
                'status'          => 'open',
                'repair_order_id' => $ticket->repair_order_id,
                'ticket_id'       => $ticket->id,
                'raised_by'       => $this->userId(),
                'raised_at'       => now(),
            ]);

            $ticket->ncr_id = $ncr->id;
            $ticket->save();

            return back()->with('status', ['success' => 1, 'msg' => 'Ticket escalated to NCR.']);
        } catch (\Exception $e) {
            \Log::emergency($e->getMessage());
            return back()->with('status', ['success' => 0, 'msg' => __('messages.something_went_wrong')]);
        }
    }

    protected function rules(Request $request): array
    {
        return $this->validate($request, [
            'subject'     => 'required|string|max:191',
            'category'    => 'nullable|in:complaint,query,warranty,feedback,other',
            'priority'    => 'nullable|in:low,normal,high,urgent',
            'status'      => 'nullable|in:' . implode(',', VrcTicket::STATUSES),
            'assigned_to' => 'nullable|string|max:191',
            'description' => 'nullable|string',
        ]);
    }
}
