package dev.lions.user.manager.resource;

import dev.lions.user.manager.dto.role.RoleAssignmentDTO;
import dev.lions.user.manager.dto.role.RoleDTO;
import dev.lions.user.manager.enums.role.TypeRole;
import dev.lions.user.manager.service.RoleService;
import jakarta.annotation.security.RolesAllowed;
import jakarta.inject.Inject;
import jakarta.validation.Valid;
import jakarta.validation.constraints.NotBlank;
import jakarta.validation.constraints.NotNull;
import jakarta.ws.rs.*;
import jakarta.ws.rs.core.MediaType;
import jakarta.ws.rs.core.Response;
import lombok.extern.slf4j.Slf4j;
import org.eclipse.microprofile.openapi.annotations.Operation;
import org.eclipse.microprofile.openapi.annotations.media.Content;
import org.eclipse.microprofile.openapi.annotations.media.Schema;
import org.eclipse.microprofile.openapi.annotations.parameters.Parameter;
import org.eclipse.microprofile.openapi.annotations.responses.APIResponse;
import org.eclipse.microprofile.openapi.annotations.responses.APIResponses;
import org.eclipse.microprofile.openapi.annotations.tags.Tag;

import java.util.List;
import java.util.Optional;

/**
 * REST Resource pour la gestion des rôles Keycloak
 * Endpoints pour les rôles realm, rôles client, et attributions
 */
@Path("/api/roles")
@Produces(MediaType.APPLICATION_JSON)
@Consumes(MediaType.APPLICATION_JSON)
@Tag(name = "Roles", description = "Gestion des rôles Keycloak (realm et client)")
@Slf4j
public class RoleResource {

    @Inject
    RoleService roleService;

    // ==================== Endpoints Realm Roles ====================

    @POST
    @Path("/realm")
    @Operation(summary = "Créer un rôle realm", description = "Crée un nouveau rôle au niveau du realm")
    @APIResponses({
        @APIResponse(responseCode = "201", description = "Rôle créé",
            content = @Content(schema = @Schema(implementation = RoleDTO.class))),
        @APIResponse(responseCode = "400", description = "Données invalides"),
        @APIResponse(responseCode = "409", description = "Rôle existe déjà"),
        @APIResponse(responseCode = "500", description = "Erreur serveur")
    })
    @RolesAllowed({"admin", "role_manager"})
    public Response createRealmRole(
        @Valid @NotNull RoleDTO roleDTO,
        @QueryParam("realm") @NotBlank String realmName
    ) {
        log.info("POST /api/roles/realm - Création du rôle realm: {} dans le realm: {}",
                 roleDTO.getName(), realmName);

        try {
            RoleDTO createdRole = roleService.createRealmRole(roleDTO, realmName);
            return Response.status(Response.Status.CREATED).entity(createdRole).build();
        } catch (IllegalArgumentException e) {
            log.warn("Données invalides lors de la création du rôle: {}", e.getMessage());
            return Response.status(Response.Status.CONFLICT)
                .entity(new ErrorResponse(e.getMessage()))
                .build();
        } catch (Exception e) {
            log.error("Erreur lors de la création du rôle realm", e);
            return Response.status(Response.Status.INTERNAL_SERVER_ERROR)
                .entity(new ErrorResponse(e.getMessage()))
                .build();
        }
    }

    @GET
    @Path("/realm/{roleName}")
    @Operation(summary = "Récupérer un rôle realm par nom", description = "Récupère les détails d'un rôle realm")
    @APIResponses({
        @APIResponse(responseCode = "200", description = "Rôle trouvé",
            content = @Content(schema = @Schema(implementation = RoleDTO.class))),
        @APIResponse(responseCode = "404", description = "Rôle non trouvé"),
        @APIResponse(responseCode = "500", description = "Erreur serveur")
    })
    @RolesAllowed({"admin", "role_manager", "role_viewer"})
    public Response getRealmRole(
        @Parameter(description = "Nom du rôle") @PathParam("roleName") @NotBlank String roleName,
        @Parameter(description = "Nom du realm") @QueryParam("realm") @NotBlank String realmName
    ) {
        log.info("GET /api/roles/realm/{} - realm: {}", roleName, realmName);

        try {
            return roleService.getRoleByName(roleName, realmName, dev.lions.user.manager.enums.role.TypeRole.REALM_ROLE, null)
                .map(role -> Response.ok(role).build())
                .orElse(Response.status(Response.Status.NOT_FOUND)
                    .entity(new ErrorResponse("Rôle non trouvé"))
                    .build());
        } catch (Exception e) {
            log.error("Erreur lors de la récupération du rôle realm {}", roleName, e);
            return Response.status(Response.Status.INTERNAL_SERVER_ERROR)
                .entity(new ErrorResponse(e.getMessage()))
                .build();
        }
    }

    @GET
    @Path("/realm")
    @Operation(summary = "Lister tous les rôles realm", description = "Liste tous les rôles du realm")
    @APIResponses({
        @APIResponse(responseCode = "200", description = "Liste des rôles"),
        @APIResponse(responseCode = "400", description = "Realm invalide ou inexistant"),
        @APIResponse(responseCode = "500", description = "Erreur serveur")
    })
    @RolesAllowed({"admin", "role_manager", "role_viewer"})
    public Response getAllRealmRoles(
        @QueryParam("realm") @NotBlank String realmName
    ) {
        log.info("GET /api/roles/realm - realm: {}", realmName);

        try {
            List<RoleDTO> roles = roleService.getAllRealmRoles(realmName);
            return Response.ok(roles).build();
        } catch (IllegalArgumentException e) {
            log.warn("Realm invalide ou inexistant: {}", e.getMessage());
            return Response.status(Response.Status.BAD_REQUEST)
                .entity(new ErrorResponse(e.getMessage()))
                .build();
        } catch (Exception e) {
            log.error("Erreur lors de la récupération des rôles realm", e);
            return Response.status(Response.Status.INTERNAL_SERVER_ERROR)
                .entity(new ErrorResponse(e.getMessage()))
                .build();
        }
    }

    @PUT
    @Path("/realm/{roleName}")
    @Operation(summary = "Mettre à jour un rôle realm", description = "Met à jour les informations d'un rôle realm")
    @APIResponses({
        @APIResponse(responseCode = "200", description = "Rôle mis à jour",
            content = @Content(schema = @Schema(implementation = RoleDTO.class))),
        @APIResponse(responseCode = "404", description = "Rôle non trouvé"),
        @APIResponse(responseCode = "500", description = "Erreur serveur")
    })
    @RolesAllowed({"admin", "role_manager"})
    public Response updateRealmRole(
        @PathParam("roleName") @NotBlank String roleName,
        @Valid @NotNull RoleDTO roleDTO,
        @QueryParam("realm") @NotBlank String realmName
    ) {
        log.info("PUT /api/roles/realm/{} - realm: {}", roleName, realmName);

        try {
            // Récupérer l'ID du rôle par son nom
            Optional<RoleDTO> existingRole = roleService.getRoleByName(roleName, realmName, 
                dev.lions.user.manager.enums.role.TypeRole.REALM_ROLE, null);
            if (existingRole.isEmpty()) {
                return Response.status(Response.Status.NOT_FOUND)
                    .entity(new ErrorResponse("Rôle non trouvé"))
                    .build();
            }
            
            RoleDTO updatedRole = roleService.updateRole(existingRole.get().getId(), roleDTO, realmName,
                dev.lions.user.manager.enums.role.TypeRole.REALM_ROLE, null);
            return Response.ok(updatedRole).build();
        } catch (Exception e) {
            log.error("Erreur lors de la mise à jour du rôle realm {}", roleName, e);
            return Response.status(Response.Status.INTERNAL_SERVER_ERROR)
                .entity(new ErrorResponse(e.getMessage()))
                .build();
        }
    }

    @DELETE
    @Path("/realm/{roleName}")
    @Operation(summary = "Supprimer un rôle realm", description = "Supprime un rôle realm")
    @APIResponses({
        @APIResponse(responseCode = "204", description = "Rôle supprimé"),
        @APIResponse(responseCode = "404", description = "Rôle non trouvé"),
        @APIResponse(responseCode = "500", description = "Erreur serveur")
    })
    @RolesAllowed({"admin"})
    public Response deleteRealmRole(
        @PathParam("roleName") @NotBlank String roleName,
        @QueryParam("realm") @NotBlank String realmName
    ) {
        log.info("DELETE /api/roles/realm/{} - realm: {}", roleName, realmName);

        try {
            // Récupérer l'ID du rôle par son nom
            Optional<RoleDTO> existingRole = roleService.getRoleByName(roleName, realmName,
                dev.lions.user.manager.enums.role.TypeRole.REALM_ROLE, null);
            if (existingRole.isEmpty()) {
                return Response.status(Response.Status.NOT_FOUND)
                    .entity(new ErrorResponse("Rôle non trouvé"))
                    .build();
            }
            
            roleService.deleteRole(existingRole.get().getId(), realmName,
                dev.lions.user.manager.enums.role.TypeRole.REALM_ROLE, null);
            return Response.noContent().build();
        } catch (Exception e) {
            log.error("Erreur lors de la suppression du rôle realm {}", roleName, e);
            return Response.status(Response.Status.INTERNAL_SERVER_ERROR)
                .entity(new ErrorResponse(e.getMessage()))
                .build();
        }
    }

    // ==================== Endpoints Client Roles ====================

    @POST
    @Path("/client/{clientId}")
    @Operation(summary = "Créer un rôle client", description = "Crée un nouveau rôle pour un client spécifique")
    @APIResponses({
        @APIResponse(responseCode = "201", description = "Rôle créé",
            content = @Content(schema = @Schema(implementation = RoleDTO.class))),
        @APIResponse(responseCode = "400", description = "Données invalides"),
        @APIResponse(responseCode = "409", description = "Rôle existe déjà"),
        @APIResponse(responseCode = "500", description = "Erreur serveur")
    })
    @RolesAllowed({"admin", "role_manager"})
    public Response createClientRole(
        @PathParam("clientId") @NotBlank String clientId,
        @Valid @NotNull RoleDTO roleDTO,
        @QueryParam("realm") @NotBlank String realmName
    ) {
        log.info("POST /api/roles/client/{} - Création du rôle client dans le realm: {}",
                 clientId, realmName);

        try {
            RoleDTO createdRole = roleService.createClientRole(roleDTO, realmName, clientId);
            return Response.status(Response.Status.CREATED).entity(createdRole).build();
        } catch (IllegalArgumentException e) {
            log.warn("Données invalides lors de la création du rôle client: {}", e.getMessage());
            return Response.status(Response.Status.CONFLICT)
                .entity(new ErrorResponse(e.getMessage()))
                .build();
        } catch (Exception e) {
            log.error("Erreur lors de la création du rôle client", e);
            return Response.status(Response.Status.INTERNAL_SERVER_ERROR)
                .entity(new ErrorResponse(e.getMessage()))
                .build();
        }
    }

    @GET
    @Path("/client/{clientId}/{roleName}")
    @Operation(summary = "Récupérer un rôle client par nom", description = "Récupère les détails d'un rôle client")
    @APIResponses({
        @APIResponse(responseCode = "200", description = "Rôle trouvé",
            content = @Content(schema = @Schema(implementation = RoleDTO.class))),
        @APIResponse(responseCode = "404", description = "Rôle non trouvé"),
        @APIResponse(responseCode = "500", description = "Erreur serveur")
    })
    @RolesAllowed({"admin", "role_manager", "role_viewer"})
    public Response getClientRole(
        @PathParam("clientId") @NotBlank String clientId,
        @PathParam("roleName") @NotBlank String roleName,
        @QueryParam("realm") @NotBlank String realmName
    ) {
        log.info("GET /api/roles/client/{}/{} - realm: {}", clientId, roleName, realmName);

        try {
            return roleService.getRoleByName(roleName, realmName, 
                dev.lions.user.manager.enums.role.TypeRole.CLIENT_ROLE, clientId)
                .map(role -> Response.ok(role).build())
                .orElse(Response.status(Response.Status.NOT_FOUND)
                    .entity(new ErrorResponse("Rôle client non trouvé"))
                    .build());
        } catch (Exception e) {
            log.error("Erreur lors de la récupération du rôle client {}/{}", clientId, roleName, e);
            return Response.status(Response.Status.INTERNAL_SERVER_ERROR)
                .entity(new ErrorResponse(e.getMessage()))
                .build();
        }
    }

    @GET
    @Path("/client/{clientId}")
    @Operation(summary = "Lister tous les rôles d'un client", description = "Liste tous les rôles d'un client spécifique")
    @APIResponses({
        @APIResponse(responseCode = "200", description = "Liste des rôles"),
        @APIResponse(responseCode = "500", description = "Erreur serveur")
    })
    @RolesAllowed({"admin", "role_manager", "role_viewer"})
    public Response getAllClientRoles(
        @PathParam("clientId") @NotBlank String clientId,
        @QueryParam("realm") @NotBlank String realmName
    ) {
        log.info("GET /api/roles/client/{} - realm: {}", clientId, realmName);

        try {
            List<RoleDTO> roles = roleService.getAllClientRoles(realmName, clientId);
            return Response.ok(roles).build();
        } catch (Exception e) {
            log.error("Erreur lors de la récupération des rôles du client {}", clientId, e);
            return Response.status(Response.Status.INTERNAL_SERVER_ERROR)
                .entity(new ErrorResponse(e.getMessage()))
                .build();
        }
    }

    @DELETE
    @Path("/client/{clientId}/{roleName}")
    @Operation(summary = "Supprimer un rôle client", description = "Supprime un rôle d'un client")
    @APIResponses({
        @APIResponse(responseCode = "204", description = "Rôle supprimé"),
        @APIResponse(responseCode = "404", description = "Rôle non trouvé"),
        @APIResponse(responseCode = "500", description = "Erreur serveur")
    })
    @RolesAllowed({"admin"})
    public Response deleteClientRole(
        @PathParam("clientId") @NotBlank String clientId,
        @PathParam("roleName") @NotBlank String roleName,
        @QueryParam("realm") @NotBlank String realmName
    ) {
        log.info("DELETE /api/roles/client/{}/{} - realm: {}", clientId, roleName, realmName);

        try {
            // Récupérer l'ID du rôle par son nom
            Optional<RoleDTO> existingRole = roleService.getRoleByName(roleName, realmName,
                dev.lions.user.manager.enums.role.TypeRole.CLIENT_ROLE, clientId);
            if (existingRole.isEmpty()) {
                return Response.status(Response.Status.NOT_FOUND)
                    .entity(new ErrorResponse("Rôle client non trouvé"))
                    .build();
            }
            
            roleService.deleteRole(existingRole.get().getId(), realmName,
                dev.lions.user.manager.enums.role.TypeRole.CLIENT_ROLE, clientId);
            return Response.noContent().build();
        } catch (Exception e) {
            log.error("Erreur lors de la suppression du rôle client {}/{}", clientId, roleName, e);
            return Response.status(Response.Status.INTERNAL_SERVER_ERROR)
                .entity(new ErrorResponse(e.getMessage()))
                .build();
        }
    }

    // ==================== Endpoints Attribution de rôles ====================

    @POST
    @Path("/assign/realm/{userId}")
    @Operation(summary = "Attribuer des rôles realm à un utilisateur", description = "Assigne un ou plusieurs rôles realm à un utilisateur")
    @APIResponses({
        @APIResponse(responseCode = "204", description = "Rôles attribués"),
        @APIResponse(responseCode = "404", description = "Utilisateur ou rôle non trouvé"),
        @APIResponse(responseCode = "500", description = "Erreur serveur")
    })
    @RolesAllowed({"admin", "role_manager"})
    public Response assignRealmRoles(
        @PathParam("userId") @NotBlank String userId,
        @QueryParam("realm") @NotBlank String realmName,
        @NotNull RoleAssignmentRequest request
    ) {
        log.info("POST /api/roles/assign/realm/{} - Attribution de {} rôles", userId, request.roleNames.size());

        try {
            RoleAssignmentDTO assignment = RoleAssignmentDTO.builder()
                .userId(userId)
                .roleNames(request.roleNames)
                .typeRole(TypeRole.REALM_ROLE)
                .realmName(realmName)
                .build();
            roleService.assignRolesToUser(assignment);
            return Response.noContent().build();
        } catch (Exception e) {
            log.error("Erreur lors de l'attribution des rôles realm à l'utilisateur {}", userId, e);
            return Response.status(Response.Status.INTERNAL_SERVER_ERROR)
                .entity(new ErrorResponse(e.getMessage()))
                .build();
        }
    }

    @POST
    @Path("/revoke/realm/{userId}")
    @Operation(summary = "Révoquer des rôles realm d'un utilisateur", description = "Révoque un ou plusieurs rôles realm d'un utilisateur")
    @APIResponses({
        @APIResponse(responseCode = "204", description = "Rôles révoqués"),
        @APIResponse(responseCode = "404", description = "Utilisateur ou rôle non trouvé"),
        @APIResponse(responseCode = "500", description = "Erreur serveur")
    })
    @RolesAllowed({"admin", "role_manager"})
    public Response revokeRealmRoles(
        @PathParam("userId") @NotBlank String userId,
        @QueryParam("realm") @NotBlank String realmName,
        @NotNull RoleAssignmentRequest request
    ) {
        log.info("POST /api/roles/revoke/realm/{} - Révocation de {} rôles", userId, request.roleNames.size());

        try {
            RoleAssignmentDTO assignment = RoleAssignmentDTO.builder()
                .userId(userId)
                .roleNames(request.roleNames)
                .typeRole(TypeRole.REALM_ROLE)
                .realmName(realmName)
                .build();
            roleService.revokeRolesFromUser(assignment);
            return Response.noContent().build();
        } catch (Exception e) {
            log.error("Erreur lors de la révocation des rôles realm de l'utilisateur {}", userId, e);
            return Response.status(Response.Status.INTERNAL_SERVER_ERROR)
                .entity(new ErrorResponse(e.getMessage()))
                .build();
        }
    }

    @POST
    @Path("/assign/client/{clientId}/{userId}")
    @Operation(summary = "Attribuer des rôles client à un utilisateur", description = "Assigne un ou plusieurs rôles client à un utilisateur")
    @APIResponses({
        @APIResponse(responseCode = "204", description = "Rôles attribués"),
        @APIResponse(responseCode = "404", description = "Utilisateur, client ou rôle non trouvé"),
        @APIResponse(responseCode = "500", description = "Erreur serveur")
    })
    @RolesAllowed({"admin", "role_manager"})
    public Response assignClientRoles(
        @PathParam("clientId") @NotBlank String clientId,
        @PathParam("userId") @NotBlank String userId,
        @QueryParam("realm") @NotBlank String realmName,
        @NotNull RoleAssignmentRequest request
    ) {
        log.info("POST /api/roles/assign/client/{}/{} - Attribution de {} rôles client",
                 clientId, userId, request.roleNames.size());

        try {
            RoleAssignmentDTO assignment = RoleAssignmentDTO.builder()
                .userId(userId)
                .roleNames(request.roleNames)
                .typeRole(TypeRole.CLIENT_ROLE)
                .realmName(realmName)
                .clientName(clientId)
                .build();
            roleService.assignRolesToUser(assignment);
            return Response.noContent().build();
        } catch (Exception e) {
            log.error("Erreur lors de l'attribution des rôles client à l'utilisateur {}", userId, e);
            return Response.status(Response.Status.INTERNAL_SERVER_ERROR)
                .entity(new ErrorResponse(e.getMessage()))
                .build();
        }
    }

    @GET
    @Path("/user/realm/{userId}")
    @Operation(summary = "Récupérer les rôles realm d'un utilisateur", description = "Liste tous les rôles realm d'un utilisateur")
    @APIResponses({
        @APIResponse(responseCode = "200", description = "Liste des rôles"),
        @APIResponse(responseCode = "500", description = "Erreur serveur")
    })
    @RolesAllowed({"admin", "role_manager", "role_viewer"})
    public Response getUserRealmRoles(
        @PathParam("userId") @NotBlank String userId,
        @QueryParam("realm") @NotBlank String realmName
    ) {
        log.info("GET /api/roles/user/realm/{} - realm: {}", userId, realmName);

        try {
            List<RoleDTO> roles = roleService.getUserRealmRoles(userId, realmName);
            return Response.ok(roles).build();
        } catch (Exception e) {
            log.error("Erreur lors de la récupération des rôles realm de l'utilisateur {}", userId, e);
            return Response.status(Response.Status.INTERNAL_SERVER_ERROR)
                .entity(new ErrorResponse(e.getMessage()))
                .build();
        }
    }

    @GET
    @Path("/user/client/{clientId}/{userId}")
    @Operation(summary = "Récupérer les rôles client d'un utilisateur", description = "Liste tous les rôles client d'un utilisateur")
    @APIResponses({
        @APIResponse(responseCode = "200", description = "Liste des rôles"),
        @APIResponse(responseCode = "500", description = "Erreur serveur")
    })
    @RolesAllowed({"admin", "role_manager", "role_viewer"})
    public Response getUserClientRoles(
        @PathParam("clientId") @NotBlank String clientId,
        @PathParam("userId") @NotBlank String userId,
        @QueryParam("realm") @NotBlank String realmName
    ) {
        log.info("GET /api/roles/user/client/{}/{} - realm: {}", clientId, userId, realmName);

        try {
            List<RoleDTO> roles = roleService.getUserClientRoles(userId, clientId, realmName);
            return Response.ok(roles).build();
        } catch (Exception e) {
            log.error("Erreur lors de la récupération des rôles client de l'utilisateur {}", userId, e);
            return Response.status(Response.Status.INTERNAL_SERVER_ERROR)
                .entity(new ErrorResponse(e.getMessage()))
                .build();
        }
    }

    // ==================== Endpoints Rôles composites ====================

    @POST
    @Path("/composite/{roleName}/add")
    @Operation(summary = "Ajouter des rôles composites", description = "Ajoute des rôles composites à un rôle")
    @APIResponses({
        @APIResponse(responseCode = "204", description = "Composites ajoutés"),
        @APIResponse(responseCode = "404", description = "Rôle non trouvé"),
        @APIResponse(responseCode = "500", description = "Erreur serveur")
    })
    @RolesAllowed({"admin", "role_manager"})
    public Response addComposites(
        @PathParam("roleName") @NotBlank String roleName,
        @QueryParam("realm") @NotBlank String realmName,
        @NotNull RoleAssignmentRequest request
    ) {
        log.info("POST /api/roles/composite/{}/add - Ajout de {} composites", roleName, request.roleNames.size());

        try {
            // Récupérer l'ID du rôle parent par son nom
            Optional<RoleDTO> parentRole = roleService.getRoleByName(roleName, realmName, TypeRole.REALM_ROLE, null);
            if (parentRole.isEmpty()) {
                return Response.status(Response.Status.NOT_FOUND)
                    .entity(new ErrorResponse("Rôle parent non trouvé"))
                    .build();
            }
            
            // Convertir les noms de rôles en IDs
            List<String> childRoleIds = request.roleNames.stream()
                .map(name -> {
                    Optional<RoleDTO> role = roleService.getRoleByName(name, realmName, TypeRole.REALM_ROLE, null);
                    return role.map(RoleDTO::getId).orElse(null);
                })
                .filter(id -> id != null)
                .collect(java.util.stream.Collectors.toList());
            
            roleService.addCompositeRoles(parentRole.get().getId(), childRoleIds, realmName, TypeRole.REALM_ROLE, null);
            return Response.noContent().build();
        } catch (Exception e) {
            log.error("Erreur lors de l'ajout des composites au rôle {}", roleName, e);
            return Response.status(Response.Status.INTERNAL_SERVER_ERROR)
                .entity(new ErrorResponse(e.getMessage()))
                .build();
        }
    }

    @GET
    @Path("/composite/{roleName}")
    @Operation(summary = "Récupérer les rôles composites", description = "Liste tous les rôles composites d'un rôle")
    @APIResponses({
        @APIResponse(responseCode = "200", description = "Liste des composites"),
        @APIResponse(responseCode = "500", description = "Erreur serveur")
    })
    @RolesAllowed({"admin", "role_manager", "role_viewer"})
    public Response getComposites(
        @PathParam("roleName") @NotBlank String roleName,
        @QueryParam("realm") @NotBlank String realmName
    ) {
        log.info("GET /api/roles/composite/{} - realm: {}", roleName, realmName);

        try {
            // Récupérer l'ID du rôle par son nom
            Optional<RoleDTO> role = roleService.getRoleByName(roleName, realmName, TypeRole.REALM_ROLE, null);
            if (role.isEmpty()) {
                return Response.status(Response.Status.NOT_FOUND)
                    .entity(new ErrorResponse("Rôle non trouvé"))
                    .build();
            }
            
            List<RoleDTO> composites = roleService.getCompositeRoles(role.get().getId(), realmName, TypeRole.REALM_ROLE, null);
            return Response.ok(composites).build();
        } catch (Exception e) {
            log.error("Erreur lors de la récupération des composites du rôle {}", roleName, e);
            return Response.status(Response.Status.INTERNAL_SERVER_ERROR)
                .entity(new ErrorResponse(e.getMessage()))
                .build();
        }
    }

    // ==================== DTOs internes ====================

    @Schema(description = "Requête d'attribution/révocation de rôles")
    public static class RoleAssignmentRequest {
        @Schema(description = "Liste des noms de rôles", required = true)
        public List<String> roleNames;
    }

    @Schema(description = "Réponse d'erreur")
    public static class ErrorResponse {
        @Schema(description = "Message d'erreur")
        public String message;

        public ErrorResponse(String message) {
            this.message = message;
        }
    }
}
