SupportTicketController.php 4.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132
  1. <?php
  2. namespace App\Http\Controllers;
  3. use App\Services\SupportTicketService;
  4. use App\Http\Requests\SupportTicketRequest;
  5. use App\Http\Resources\SupportTicketResource;
  6. use Illuminate\Http\JsonResponse;
  7. class SupportTicketController extends Controller
  8. {
  9. public function __construct(
  10. protected SupportTicketService $service,
  11. ) {}
  12. public function index(): JsonResponse
  13. {
  14. $user = auth()->user();
  15. $query = \App\Models\SupportTicket::query()
  16. ->with(['applicantUnit', 'targetUnit'])
  17. ->orderBy('created_at', 'desc');
  18. if (!$this->isMatriz($user)) {
  19. $unitId = $user->units()->first()?->id;
  20. $query->visibleToUnit($unitId);
  21. }
  22. return $this->successResponse(
  23. payload: SupportTicketResource::collection($query->get())
  24. );
  25. }
  26. public function store(SupportTicketRequest $request): JsonResponse
  27. {
  28. $data = $request->validated();
  29. $user = auth()->user();
  30. $isMatriz = $this->isMatriz($user);
  31. $data['origin'] = $isMatriz ? 'matriz' : 'unit';
  32. $data['applicant_user_id'] = $user->id;
  33. $data['responsable_user_id'] = $user->id;
  34. $data['applicant_unit_id'] = $isMatriz ? null : $user->units()->first()?->id;
  35. $data['status'] = 'in_progress';
  36. // Broadcast: Matriz para todas as unidades
  37. if ($isMatriz && ($data['scope'] ?? null) === 'all') {
  38. $batchId = (string) \Illuminate\Support\Str::uuid();
  39. $unitIds = \App\Models\Unit::query()->pluck('id');
  40. $created = [];
  41. foreach ($unitIds as $unitId) {
  42. $created[] = $this->service->create(array_merge($data, [
  43. 'target_unit_id' => $unitId,
  44. 'batch_id' => $batchId,
  45. ]));
  46. }
  47. return $this->successResponse(
  48. payload: SupportTicketResource::collection($created),
  49. message: __('messages.created'),
  50. code: 201
  51. );
  52. }
  53. // Resolução de target_unit_id por cenário
  54. if ($isMatriz) {
  55. if (($data['scope'] ?? null) === 'internal') {
  56. $data['target_unit_id'] = null;
  57. }
  58. // scope='specific' → target_unit_id já veio do request
  59. } else {
  60. // Franchisee
  61. $data['target_unit_id'] = (($data['scope'] ?? null) === 'internal')
  62. ? $user->units()->first()?->id
  63. : null; // 'specific' do Franchisee = "para Matriz"
  64. }
  65. $item = $this->service->create($data);
  66. return $this->successResponse(
  67. payload: new SupportTicketResource($item),
  68. message: __('messages.created'),
  69. code: 201
  70. );
  71. }
  72. public function show(int $id): JsonResponse
  73. {
  74. $item = $this->service->findById($id);
  75. return $this->successResponse(payload: new SupportTicketResource($item));
  76. }
  77. public function update(SupportTicketRequest $request, int $id): JsonResponse
  78. {
  79. $user = auth()->user();
  80. $item = $this->service->findById($id);
  81. if (!$this->canManage($user, $item)) {
  82. return $this->errorResponse(message: __('messages.unauthorized'), code: 403);
  83. }
  84. $item = $this->service->update($id, $request->validated());
  85. return $this->successResponse(payload: new SupportTicketResource($item), message: __('messages.updated'));
  86. }
  87. public function destroy(int $id): JsonResponse
  88. {
  89. $user = auth()->user();
  90. $item = $this->service->findById($id);
  91. if (!$this->canManage($user, $item)) {
  92. return $this->errorResponse(message: __('messages.unauthorized'), code: 403);
  93. }
  94. $this->service->delete($id);
  95. return $this->successResponse(message: __('messages.deleted'), code: 204);
  96. }
  97. private function isMatriz(\App\Models\User $user): bool
  98. {
  99. return $user->user_type === 'ADMIN';
  100. }
  101. private function canManage(\App\Models\User $user, \App\Models\SupportTicket $ticket): bool
  102. {
  103. if ($this->isMatriz($user)) {
  104. return true;
  105. }
  106. // Franchisee só pode gerenciar tickets internos que ela mesma criou
  107. return $ticket->origin === 'unit'
  108. && $ticket->scope === 'internal'
  109. && $ticket->applicant_unit_id === $user->units()->first()?->id;
  110. }
  111. }