package dev.lions.unionflow.server.resource;

import dev.lions.unionflow.server.service.ExportService;
import jakarta.enterprise.context.ApplicationScoped;
import jakarta.inject.Inject;
import jakarta.annotation.security.RolesAllowed;
import jakarta.ws.rs.*;
import jakarta.ws.rs.core.MediaType;
import jakarta.ws.rs.core.Response;
import java.util.List;
import java.util.UUID;
import org.eclipse.microprofile.openapi.annotations.Operation;
import org.eclipse.microprofile.openapi.annotations.responses.APIResponse;
import org.eclipse.microprofile.openapi.annotations.tags.Tag;
import org.jboss.logging.Logger;

/** Resource REST pour l'export des données */
@Path("/api/export")
@ApplicationScoped
@Tag(name = "Export", description = "API d'export des données")
@RolesAllowed({"ADMIN", "ADMIN_ORGANISATION", "MEMBRE", "USER"})
public class ExportResource {

  private static final Logger LOG = Logger.getLogger(ExportResource.class);

  @Inject ExportService exportService;

  @GET
  @Path("/cotisations/csv")
  @Produces("text/csv")
  @Operation(summary = "Exporter les cotisations en CSV")
  @APIResponse(responseCode = "200", description = "Fichier CSV généré")
  public Response exporterCotisationsCSV(
      @QueryParam("statut") String statut,
      @QueryParam("type") String type,
      @QueryParam("associationId") UUID associationId) {
    LOG.info("Export CSV des cotisations");
    
    byte[] csv = exportService.exporterToutesCotisationsCSV(statut, type, associationId);
    
    return Response.ok(csv)
        .header("Content-Disposition", "attachment; filename=\"cotisations.csv\"")
        .header("Content-Type", "text/csv; charset=UTF-8")
        .build();
  }

  @POST
  @RolesAllowed({"ADMIN", "ADMIN_ORGANISATION", "MEMBRE"})
  @Path("/cotisations/csv")
  @Consumes(MediaType.APPLICATION_JSON)
  @Produces("text/csv")
  @Operation(summary = "Exporter des cotisations spécifiques en CSV")
  @APIResponse(responseCode = "200", description = "Fichier CSV généré")
  public Response exporterCotisationsSelectionneesCSV(List<UUID> cotisationIds) {
    LOG.infof("Export CSV de %d cotisations", cotisationIds.size());
    
    byte[] csv = exportService.exporterCotisationsCSV(cotisationIds);
    
    return Response.ok(csv)
        .header("Content-Disposition", "attachment; filename=\"cotisations.csv\"")
        .header("Content-Type", "text/csv; charset=UTF-8")
        .build();
  }

  @GET
  @Path("/cotisations/{cotisationId}/recu")
  @Produces("text/plain")
  @Operation(summary = "Générer un reçu de paiement")
  @APIResponse(responseCode = "200", description = "Reçu généré")
  public Response genererRecu(@PathParam("cotisationId") UUID cotisationId) {
    LOG.infof("Génération reçu pour: %s", cotisationId);
    
    byte[] recu = exportService.genererRecuPaiement(cotisationId);
    
    return Response.ok(recu)
        .header("Content-Disposition", "attachment; filename=\"recu-" + cotisationId + ".txt\"")
        .header("Content-Type", "text/plain; charset=UTF-8")
        .build();
  }

  @POST
  @RolesAllowed({"ADMIN", "ADMIN_ORGANISATION", "MEMBRE"})
  @Path("/cotisations/recus")
  @Consumes(MediaType.APPLICATION_JSON)
  @Produces("text/plain")
  @Operation(summary = "Générer des reçus groupés")
  @APIResponse(responseCode = "200", description = "Reçus générés")
  public Response genererRecusGroupes(List<UUID> cotisationIds) {
    LOG.infof("Génération de %d reçus", cotisationIds.size());
    
    byte[] recus = exportService.genererRecusGroupes(cotisationIds);
    
    return Response.ok(recus)
        .header("Content-Disposition", "attachment; filename=\"recus-groupes.txt\"")
        .header("Content-Type", "text/plain; charset=UTF-8")
        .build();
  }

  @GET
  @Path("/rapport/mensuel")
  @Produces("text/plain")
  @Operation(summary = "Générer un rapport mensuel")
  @APIResponse(responseCode = "200", description = "Rapport généré")
  public Response genererRapportMensuel(
      @QueryParam("annee") int annee,
      @QueryParam("mois") int mois,
      @QueryParam("associationId") UUID associationId) {
    LOG.infof("Génération rapport mensuel: %d/%d", mois, annee);

    byte[] rapport = exportService.genererRapportMensuel(annee, mois, associationId);

    return Response.ok(rapport)
        .header("Content-Disposition",
            "attachment; filename=\"rapport-" + annee + "-" + String.format("%02d", mois) + ".txt\"")
        .header("Content-Type", "text/plain; charset=UTF-8")
        .build();
  }

  @GET
  @Path("/cotisations/{cotisationId}/recu/pdf")
  @Produces("application/pdf")
  @Operation(summary = "Générer un reçu de paiement en PDF")
  @APIResponse(responseCode = "200", description = "PDF généré")
  public Response genererRecuPDF(@PathParam("cotisationId") UUID cotisationId) {
    LOG.infof("Génération reçu PDF pour: %s", cotisationId);

    byte[] pdf = exportService.genererRecuPaiementPDF(cotisationId);
    return Response.ok(pdf)
        .header("Content-Disposition", "attachment; filename=\"recu-" + cotisationId + ".pdf\"")
        .header("Content-Type", "application/pdf")
        .build();
  }

  @GET
  @Path("/rapport/mensuel/pdf")
  @Produces("application/pdf")
  @Operation(summary = "Générer un rapport mensuel en PDF")
  @APIResponse(responseCode = "200", description = "PDF généré")
  public Response genererRapportMensuelPDF(
      @QueryParam("annee") int annee,
      @QueryParam("mois") int mois,
      @QueryParam("associationId") UUID associationId) {
    LOG.infof("Génération rapport mensuel PDF: %d/%d", mois, annee);

    byte[] pdf = exportService.genererRapportMensuelPDF(annee, mois, associationId);
    return Response.ok(pdf)
        .header("Content-Disposition",
            "attachment; filename=\"rapport-" + annee + "-" + String.format("%02d", mois) + ".pdf\"")
        .header("Content-Type", "application/pdf")
        .build();
  }
}

