migrant-web/app/Http/Controllers/Api/SupportTicketController.php
2026-06-08 15:51:51 +05:30

325 lines
11 KiB
PHP

<?php
namespace App\Http\Controllers\Api;
use App\Http\Controllers\Controller;
use App\Models\SupportTicket;
use App\Models\SupportTicketReply;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Validator;
use Illuminate\Support\Facades\DB;
class SupportTicketController extends Controller
{
// ==========================================
// WORKER ENDPOINTS
// ==========================================
public function getTicketsForWorker(Request $request)
{
$worker = $request->attributes->get('worker');
if (!$worker) {
return response()->json(['success' => false, 'message' => 'Unauthorized.'], 401);
}
$tickets = SupportTicket::where('worker_id', $worker->id)
->orderBy('created_at', 'desc')
->get()
->map(function ($ticket) {
return [
'id' => $ticket->id,
'ticket_number' => $ticket->ticket_number,
'subject' => $ticket->subject,
'description' => $ticket->description,
'status' => $ticket->status,
'priority' => $ticket->priority,
'created_at' => $ticket->created_at->toIso8601String(),
];
});
return response()->json([
'success' => true,
'tickets' => $tickets
]);
}
public function createTicketFromWorker(Request $request)
{
$worker = $request->attributes->get('worker');
if (!$worker) {
return response()->json(['success' => false, 'message' => 'Unauthorized.'], 401);
}
$validator = Validator::make($request->all(), [
'subject' => 'required|string|max:255',
'description' => 'required|string',
'priority' => 'nullable|string|in:low,medium,high',
]);
if ($validator->fails()) {
return response()->json([
'success' => false,
'message' => 'Validation error.',
'errors' => $validator->errors()
], 422);
}
$ticket = SupportTicket::create([
'ticket_number' => 'TKT-' . rand(100000, 999999),
'worker_id' => $worker->id,
'subject' => $request->subject,
'description' => $request->description,
'priority' => $request->priority ?? 'medium',
'status' => 'open',
]);
return response()->json([
'success' => true,
'message' => 'Ticket created successfully.',
'ticket' => [
'id' => $ticket->id,
'ticket_number' => $ticket->ticket_number,
'subject' => $ticket->subject,
'description' => $ticket->description,
'status' => $ticket->status,
'priority' => $ticket->priority,
'created_at' => $ticket->created_at->toIso8601String(),
]
], 201);
}
public function replyToTicketFromWorker(Request $request, $id)
{
$worker = $request->attributes->get('worker');
if (!$worker) {
return response()->json(['success' => false, 'message' => 'Unauthorized.'], 401);
}
$ticket = SupportTicket::where('worker_id', $worker->id)->find($id);
if (!$ticket) {
return response()->json(['success' => false, 'message' => 'Ticket not found.'], 404);
}
if ($ticket->status === 'closed') {
return response()->json(['success' => false, 'message' => 'Cannot reply to a closed ticket.'], 422);
}
$validator = Validator::make($request->all(), [
'message' => 'required|string',
]);
if ($validator->fails()) {
return response()->json([
'success' => false,
'message' => 'Validation error.',
'errors' => $validator->errors()
], 422);
}
$reply = SupportTicketReply::create([
'support_ticket_id' => $ticket->id,
'worker_id' => $worker->id,
'message' => $request->message,
]);
if ($ticket->status === 'resolved') {
$ticket->update(['status' => 'open']);
}
return response()->json([
'success' => true,
'message' => 'Reply posted successfully.',
'reply' => [
'id' => $reply->id,
'message' => $reply->message,
'sender_name' => $reply->sender_name,
'created_at' => $reply->created_at->toIso8601String(),
]
], 201);
}
// ==========================================
// EMPLOYER ENDPOINTS
// ==========================================
public function getTicketsForEmployer(Request $request)
{
$employer = $request->attributes->get('employer');
if (!$employer) {
return response()->json(['success' => false, 'message' => 'Unauthorized.'], 401);
}
$tickets = SupportTicket::where('user_id', $employer->id)
->orderBy('created_at', 'desc')
->get()
->map(function ($ticket) {
return [
'id' => $ticket->id,
'ticket_number' => $ticket->ticket_number,
'subject' => $ticket->subject,
'description' => $ticket->description,
'status' => $ticket->status,
'priority' => $ticket->priority,
'created_at' => $ticket->created_at->toIso8601String(),
];
});
return response()->json([
'success' => true,
'tickets' => $tickets
]);
}
public function createTicketFromEmployer(Request $request)
{
$employer = $request->attributes->get('employer');
if (!$employer) {
return response()->json(['success' => false, 'message' => 'Unauthorized.'], 401);
}
$validator = Validator::make($request->all(), [
'subject' => 'required|string|max:255',
'description' => 'required|string',
'priority' => 'nullable|string|in:low,medium,high',
]);
if ($validator->fails()) {
return response()->json([
'success' => false,
'message' => 'Validation error.',
'errors' => $validator->errors()
], 422);
}
$ticket = SupportTicket::create([
'ticket_number' => 'TKT-' . rand(100000, 999999),
'user_id' => $employer->id,
'subject' => $request->subject,
'description' => $request->description,
'priority' => $request->priority ?? 'medium',
'status' => 'open',
]);
return response()->json([
'success' => true,
'message' => 'Ticket created successfully.',
'ticket' => [
'id' => $ticket->id,
'ticket_number' => $ticket->ticket_number,
'subject' => $ticket->subject,
'description' => $ticket->description,
'status' => $ticket->status,
'priority' => $ticket->priority,
'created_at' => $ticket->created_at->toIso8601String(),
]
], 201);
}
public function replyToTicketFromEmployer(Request $request, $id)
{
$employer = $request->attributes->get('employer');
if (!$employer) {
return response()->json(['success' => false, 'message' => 'Unauthorized.'], 401);
}
$ticket = SupportTicket::where('user_id', $employer->id)->find($id);
if (!$ticket) {
return response()->json(['success' => false, 'message' => 'Ticket not found.'], 404);
}
if ($ticket->status === 'closed') {
return response()->json(['success' => false, 'message' => 'Cannot reply to a closed ticket.'], 422);
}
$validator = Validator::make($request->all(), [
'message' => 'required|string',
]);
if ($validator->fails()) {
return response()->json([
'success' => false,
'message' => 'Validation error.',
'errors' => $validator->errors()
], 422);
}
$reply = SupportTicketReply::create([
'support_ticket_id' => $ticket->id,
'user_id' => $employer->id,
'message' => $request->message,
]);
if ($ticket->status === 'resolved') {
$ticket->update(['status' => 'open']);
}
return response()->json([
'success' => true,
'message' => 'Reply posted successfully.',
'reply' => [
'id' => $reply->id,
'message' => $reply->message,
'sender_name' => $reply->sender_name,
'created_at' => $reply->created_at->toIso8601String(),
]
], 201);
}
// ==========================================
// SHARED GET DETAILS
// ==========================================
public function getTicketDetail(Request $request, $id)
{
$worker = $request->attributes->get('worker');
$employer = $request->attributes->get('employer');
if (!$worker && !$employer) {
return response()->json(['success' => false, 'message' => 'Unauthorized.'], 401);
}
$query = SupportTicket::where('id', $id);
if ($worker) {
$query->where('worker_id', $worker->id);
} else {
$query->where('user_id', $employer->id);
}
$ticket = $query->first();
if (!$ticket) {
return response()->json(['success' => false, 'message' => 'Ticket not found.'], 404);
}
$replies = SupportTicketReply::where('support_ticket_id', $ticket->id)
->with(['user', 'worker'])
->orderBy('created_at', 'asc')
->get()
->map(function ($reply) {
return [
'id' => $reply->id,
'message' => $reply->message,
'sender_name' => $reply->sender_name,
'is_admin' => $reply->user && $reply->user->role === 'admin',
'is_developer_response' => (bool)$reply->is_developer_response,
'created_at' => $reply->created_at->toIso8601String(),
];
});
return response()->json([
'success' => true,
'ticket' => [
'id' => $ticket->id,
'ticket_number' => $ticket->ticket_number,
'subject' => $ticket->subject,
'description' => $ticket->description,
'status' => $ticket->status,
'priority' => $ticket->priority,
'created_at' => $ticket->created_at->toIso8601String(),
],
'replies' => $replies
]);
}
}