package org.mte.numecoeval.expositiondonneesentrees.infrastructure.jdbc;

import lombok.extern.slf4j.Slf4j;
import org.mte.numecoeval.expositiondonneesentrees.domain.exception.RestException;
import org.mte.numecoeval.expositiondonneesentrees.domain.model.Volume;
import org.mte.numecoeval.expositiondonneesentrees.generated.api.model.StatutTraitement;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import javax.sql.DataSource;
import java.sql.Array;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.SQLException;

@Slf4j
@Service
public class VolumeJdbc {

    @Autowired
    private DataSource dataSource;

    private static final String SQL_QUERY_VOLUME = """
            SELECT count(*) as count from %s
            WHERE nom_lot = ? AND nom_organisation = ? AND statut_traitement = ANY (?)
            """;

    /**
     * @param nomLot          nom lot
     * @param nomOrganisation nom organisation
     * @param table           entree table
     * @return le volume enCours, traite
     */
    public Volume getVolumeBy(String nomLot, String nomOrganisation, String table) {
        long countTermine = 0;
        long countEnCours = 0;

        try (Connection conn = dataSource.getConnection()) {

            try (PreparedStatement statement = conn.prepareStatement(String.format(SQL_QUERY_VOLUME, table))) {

                Array statuts = conn.createArrayOf("varchar", new String[]{
                        StatutTraitement.A_INGERER.getValue(),
                        StatutTraitement.EN_ATTENTE.getValue(),
                        StatutTraitement.INGERE.getValue()
                });

                statement.setString(1, nomLot);
                statement.setString(2, nomOrganisation);
                statement.setArray(3, statuts);

                var resultSet = statement.executeQuery();
                while (resultSet.next()) {
                    countEnCours = resultSet.getLong("count");
                }

                statuts = conn.createArrayOf("varchar", new String[]{
                        StatutTraitement.TRAITE.getValue(),
                        StatutTraitement.EN_ERREUR.getValue()
                });

                statement.setArray(3, statuts);
                resultSet = statement.executeQuery();
                while (resultSet.next()) {
                    countTermine = resultSet.getLong("count");
                }
            }
        } catch (SQLException e) {
            log.error("Cannot get volume of table {}", table);
            throw new RestException(e);
        }

        return new Volume(countEnCours, countTermine);
    }
}
