<?php

namespace App\Http\Controllers\Api;

use App\Http\Requests\Role\StoreRoleRequest;
use App\Http\Requests\Role\UpdateRoleRequest;
use App\Http\Resources\RoleResource;
use App\Models\Role;
use Illuminate\Http\Request;
use Illuminate\Http\Resources\Json\AnonymousResourceCollection;
use Illuminate\Support\Facades\DB;
use Illuminate\Support\Str;

class RoleController extends ApiController
{
    public function index(Request $request): AnonymousResourceCollection
    {
        $roles = Role::query()
            ->where('company_id', $this->currentCompanyId($request))
            ->with(['permissions'])
            ->get();

        return RoleResource::collection($roles);
    }

    public function store(StoreRoleRequest $request): RoleResource
    {
        return DB::transaction(function () use ($request) {
            $role = Role::create([
                ...$request->safe()->except(['permission_ids']),
                'company_id' => $this->currentCompanyId($request),
                'slug' => Str::slug($request->string('name')),
            ]);

            if ($request->has('permission_ids')) {
                $role->permissions()->sync($request->input('permission_ids'));
            }

            return new RoleResource($role->load('permissions'));
        });
    }

    public function show(Request $request, Role $role): RoleResource
    {
        $this->ensureCompanyScoped($role, $this->currentCompanyId($request));

        return new RoleResource($role->load('permissions'));
    }

    public function update(UpdateRoleRequest $request, Role $role): RoleResource
    {
        $this->ensureCompanyScoped($role, $this->currentCompanyId($request));

        return DB::transaction(function () use ($request, $role) {
            $role->update($request->safe()->except(['permission_ids']));

            if ($request->has('permission_ids')) {
                $role->permissions()->sync($request->input('permission_ids'));
            }

            return new RoleResource($role->load('permissions'));
        });
    }

    public function destroy(Request $request, Role $role): \Illuminate\Http\JsonResponse
    {
        $this->ensureCompanyScoped($role, $this->currentCompanyId($request));

        if ($role->users()->exists()) {
            return response()->json([
                'message' => 'Role cannot be deleted while it has assigned users.'
            ], 422);
        }

        $role->delete();

        return response()->json(['message' => 'Role deleted successfully']);
    }
}
