package fr.titionfire.ffsaf.rest; import fr.titionfire.ffsaf.data.model.MembreModel; import fr.titionfire.ffsaf.domain.service.MembreService; import fr.titionfire.ffsaf.rest.data.SimpleMembre; import fr.titionfire.ffsaf.rest.exception.DForbiddenException; import fr.titionfire.ffsaf.rest.exception.DInternalError; import fr.titionfire.ffsaf.rest.from.FullMemberForm; import fr.titionfire.ffsaf.utils.PageResult; import fr.titionfire.ffsaf.utils.SecurityCtx; import fr.titionfire.ffsaf.utils.Utils; import io.smallrye.mutiny.Uni; import io.smallrye.mutiny.unchecked.Unchecked; import jakarta.annotation.security.RolesAllowed; import jakarta.inject.Inject; import jakarta.ws.rs.*; import jakarta.ws.rs.core.MediaType; import org.eclipse.microprofile.config.inject.ConfigProperty; import org.eclipse.microprofile.openapi.annotations.Operation; 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.function.Consumer; @Tag(name = "Membre admin", description = "Gestion des membres (pour les administrateurs)") @Path("api/member") @RolesAllowed({"federation_admin"}) public class MembreAdminEndpoints { @Inject MembreService membreService; @ConfigProperty(name = "upload_dir") String media; @Inject SecurityCtx securityCtx; Consumer checkPerm = Unchecked.consumer(membreModel -> { if (!securityCtx.roleHas("federation_admin") && !securityCtx.isInClubGroup(membreModel.getClub().getId())) throw new DForbiddenException(); }); @GET @Path("/find/admin") @Produces(MediaType.APPLICATION_JSON) @Operation(summary = "Recherche des membres par critères ", description = "Recherche des membres en fonction de " + "critères tels que le nom, le prénom, le club, etc. ") @APIResponses(value = { @APIResponse(responseCode = "200", description = "La liste des membres correspondant aux critères de recherche"), @APIResponse(responseCode = "500", description = "Erreur interne du serveur") }) public Uni> getFindAdmin( @Parameter(description = "Nombre max de résulta (max 50)") @QueryParam("limit") Integer limit, @Parameter(description = "Page à consulter") @QueryParam("page") Integer page, @Parameter(description = "Text à rechercher") @QueryParam("search") String search, @Parameter(description = "Club à filter") @QueryParam("club") String club, @Parameter(description = "Catégorie à filter") @QueryParam("categorie") String categorie, @Parameter(description = "État de la demande de licence: 0 -> sans demande, 1 -> avec demande ou validée, 2 -> toute les demande non validée, 3 -> validée, 4 -> tout, 5 -> demande complete, 6 -> demande incomplete") @QueryParam("licenceRequest") int licenceRequest, @Parameter(description = "État du payment: 0 -> non payer, 1 -> payer, 2 -> tout") @QueryParam("payment") int payment, @Parameter(description = "Ordre") @QueryParam("order") String order) { if (limit == null) limit = 50; if (page == null || page < 1) page = 1; return membreService.searchAdmin(limit, page - 1, search, club, licenceRequest, payment, order, categorie); } @GET @Path("/find/similar") @Produces(MediaType.APPLICATION_JSON) @Operation(hidden = true) public Uni> getSimilar(@QueryParam("fname") String fname, @QueryParam("lname") String lname) { return membreService.getSimilar(fname, lname); } @PUT @Path("{id}") @Produces(MediaType.TEXT_PLAIN) @Consumes(MediaType.MULTIPART_FORM_DATA) @Operation(summary = "Met à jour les informations d'un membre en fonction de son identifiant", description = "Met à " + "jour les informations d'un membre en fonction de son identifiant") @APIResponses(value = { @APIResponse(responseCode = "200", description = "Le membre a été mis à jour avec succès"), @APIResponse(responseCode = "403", description = "Accès refusé"), @APIResponse(responseCode = "404", description = "Le membre n'existe pas"), @APIResponse(responseCode = "500", description = "Erreur interne du serveur") }) public Uni setAdminMembre( @Parameter(description = "Identifiant de membre") @PathParam("id") long id, FullMemberForm input) { return membreService.update(id, input) .invoke(Unchecked.consumer(out -> { if (!out.equals("OK")) throw new DInternalError("Impossible de reconnaitre le fichier: " + out); })).chain(() -> { if (input.getPhoto_data().length > 0) return Uni.createFrom().future(Utils.replacePhoto(id, input.getPhoto_data(), media, "ppMembre" )).invoke(Unchecked.consumer(out -> { if (!out.equals("OK")) throw new DInternalError("Impossible de reconnaitre le fichier: " + out); })); else return Uni.createFrom().nullItem(); }); } @POST @Produces(MediaType.TEXT_PLAIN) @Consumes(MediaType.MULTIPART_FORM_DATA) @Operation(summary = "Ajoute un nouveau membre", description = "Ajoute un nouveau membre avec les informations " + "fournies dans le formulaire") @APIResponses(value = { @APIResponse(responseCode = "200", description = "Le membre a été ajouté avec succès"), @APIResponse(responseCode = "400", description = "Les données envoyées sont invalides"), @APIResponse(responseCode = "500", description = "Erreur interne du serveur") }) public Uni addAdminMembre(FullMemberForm input) { return membreService.add(input) .invoke(Unchecked.consumer(id -> { if (id == null) throw new InternalError("Fail to creat member data"); })).call(id -> { if (input.getPhoto_data().length > 0) return Uni.createFrom().future(Utils.replacePhoto(id, input.getPhoto_data(), media, "ppMembre" )); else return Uni.createFrom().nullItem(); }); } @DELETE @Path("{id}") @Produces(MediaType.TEXT_PLAIN) @Operation(summary = "Supprime un membre en fonction de son identifiant", description = "Supprime un membre en " + "fonction de son identifiant, ainsi que toutes les informations associées") @APIResponses(value = { @APIResponse(responseCode = "204", description = "Le membre a été supprimé avec succès"), @APIResponse(responseCode = "403", description = "Accès refusé"), @APIResponse(responseCode = "404", description = "Le membre n'existe pas"), @APIResponse(responseCode = "500", description = "Erreur interne du serveur") }) public Uni deleteAdminMembre( @Parameter(description = "Identifiant de membre") @PathParam("id") long id) { return membreService.delete(id); } }