package io.gmss.fiscad.service.worker;

import io.gmss.fiscad.entities.infocad.metier.Enquete;
import io.gmss.fiscad.entities.infocad.metier.Tpe;
import io.gmss.fiscad.entities.metadata.MobileDataCaracteristiqueBatiment;
import io.gmss.fiscad.entities.metadata.MobileDataCaracteristiqueUniteLogement;
import io.gmss.fiscad.entities.rfu.metier.CaracteristiqueBatiment;
import io.gmss.fiscad.entities.rfu.metier.CaracteristiqueUniteLogement;
import io.gmss.fiscad.entities.rfu.metier.EnqueteBatiment;
import io.gmss.fiscad.entities.rfu.metier.EnqueteUniteLogement;
import io.gmss.fiscad.entities.rfu.parametre.Caracteristique;
import io.gmss.fiscad.enums.TypeObjet;
import io.gmss.fiscad.paylaods.request.CaracteristiqueBatimentPaylod;
import io.gmss.fiscad.paylaods.request.CaracteristiqueUniteLogementPaylod;
import io.gmss.fiscad.repositories.infocad.metier.EnqueteRepository;
import io.gmss.fiscad.repositories.infocad.metier.TpeRepository;
import io.gmss.fiscad.repositories.metadata.MobileDataCaracteristiqueBatimentRepository;
import io.gmss.fiscad.repositories.metadata.MobileDataCaracteristiqueUniteLogementRepository;
import io.gmss.fiscad.repositories.rfu.metier.CaracteristiqueBatimentRepository;
import io.gmss.fiscad.repositories.rfu.metier.CaracteristiqueUniteLogementRepository;
import io.gmss.fiscad.repositories.rfu.metier.EnqueteBatimentRepository;
import io.gmss.fiscad.repositories.rfu.metier.EnqueteUniteLogementRepository;
import io.gmss.fiscad.repositories.rfu.parametre.CaracteristiqueRepository;
import io.gmss.fiscad.service.LogService;
import lombok.RequiredArgsConstructor;
import org.springframework.scheduling.annotation.Async;
import org.springframework.stereotype.Service;

import java.util.Optional;

@Service
@RequiredArgsConstructor
public class CaracteristiqueUniteLogementAsyncWorker {
    private final TpeRepository tpeRepository;
    private final MobileDataCaracteristiqueBatimentRepository mobileDataCaracteristiqueBatimentRepository;
    private final EnqueteRepository enqueteRepository;
    private final CaracteristiqueRepository caracteristiqueRepository;
    private final EnqueteUniteLogementRepository enqueteUniteLogementRepository;
    private final CaracteristiqueUniteLogementRepository caracteristiqueUniteLogementRepository;
    private final MobileDataCaracteristiqueUniteLogementRepository mobileDataCaracteristiqueUniteLogementRepository;
    private final LogService logService;
    //@Async("caracteristiqueUniteLogementExecutor")
    public void traitementAsyncCaracteristiqueUniteLogement(MobileDataCaracteristiqueUniteLogement mobileDataCaracteristiqueUniteLogement) {
        CaracteristiqueUniteLogementPaylod caracteristiqueUniteLogementPaylod = mobileDataCaracteristiqueUniteLogement.getCaracteristiqueUniteLogementPaylod();
        try {
            if (caracteristiqueUniteLogementPaylod.getTerminalId() == null) {
                logService.logTraiementAsync(TypeObjet.CARACTERISTIQUEUNITELOGEMENT, "Problème de terminal", "terminal non fourni : ", mobileDataCaracteristiqueUniteLogement.getId());
                return;
            } else {
                Optional<Tpe> optionalTpe = tpeRepository.findById(caracteristiqueUniteLogementPaylod.getTerminalId());
                if (optionalTpe.isEmpty()) {
                    logService.logTraiementAsync(TypeObjet.CARACTERISTIQUEUNITELOGEMENT, "Problème de terminal", "terminal inexistant : ", mobileDataCaracteristiqueUniteLogement.getId());
                    return;
                }
            }

            if (caracteristiqueUniteLogementPaylod.getEnqueteUniteLogementId() == null) {
                logService.logTraiementAsync(TypeObjet.CARACTERISTIQUEUNITELOGEMENT, "Problème de enquete unite logement", "enquete non fourni : ", mobileDataCaracteristiqueUniteLogement.getId());
                return;
            } else {
                Optional<EnqueteUniteLogement> optionalEnqueteUniteLogement = enqueteUniteLogementRepository.findFirstByExternalKeyAndTerminal_Id(caracteristiqueUniteLogementPaylod.getEnqueteUniteLogementId(), caracteristiqueUniteLogementPaylod.getTerminalId());
                if (optionalEnqueteUniteLogement.isEmpty()) {
                    logService.logTraiementAsync(TypeObjet.CARACTERISTIQUEUNITELOGEMENT, "Problème de enquete unite logement", "L'enquete précisée n'existe pas : ", mobileDataCaracteristiqueUniteLogement.getId());
                    return;
                }
            }
            CaracteristiqueUniteLogement caracteristiqueUniteLogement = new CaracteristiqueUniteLogement();
            caracteristiqueUniteLogement.setMobileDataId(mobileDataCaracteristiqueUniteLogement.getId());
            caracteristiqueUniteLogement = getCaracteristiqueUniteLogementFromCaracteristiqueUniteLogementPayLoad(caracteristiqueUniteLogement, caracteristiqueUniteLogementPaylod);
            caracteristiqueUniteLogementRepository.save(caracteristiqueUniteLogement);
            mobileDataCaracteristiqueUniteLogement.setTraiter(true);
            mobileDataCaracteristiqueUniteLogementRepository.save(mobileDataCaracteristiqueUniteLogement);
        } catch (Exception e) {
            logService.logTraiementAsync(TypeObjet.CARACTERISTIQUEUNITELOGEMENT, "Problème de inattendu", e.getMessage(), mobileDataCaracteristiqueUniteLogement.getId());
        }
    }

    private CaracteristiqueUniteLogement getCaracteristiqueUniteLogementFromCaracteristiqueUniteLogementPayLoad(CaracteristiqueUniteLogement caracteristiqueUniteLogement, CaracteristiqueUniteLogementPaylod caracteristiqueUniteLogementPaylod) {

        if (caracteristiqueUniteLogementPaylod.getEnqueteUniteLogementId() != null) {
            Optional<EnqueteUniteLogement> optionalEnqueteUniteLogement = enqueteUniteLogementRepository.findFirstByExternalKeyAndTerminal_Id(caracteristiqueUniteLogementPaylod.getEnqueteUniteLogementId(), caracteristiqueUniteLogementPaylod.getTerminalId());
            caracteristiqueUniteLogement.setEnqueteUniteLogement(optionalEnqueteUniteLogement.orElse(null));
        }

        if (caracteristiqueUniteLogementPaylod.getCaracteristiqueId() != null) {
            Optional<Caracteristique> optionalCaracteristique = caracteristiqueRepository.findById(caracteristiqueUniteLogementPaylod.getCaracteristiqueId());
            caracteristiqueUniteLogement.setCaracteristique(optionalCaracteristique.orElse(null));
        }

        if (caracteristiqueUniteLogementPaylod.getTerminalId() != null) {
            Optional<Tpe> optionalTpe = tpeRepository.findById(caracteristiqueUniteLogementPaylod.getTerminalId());
            caracteristiqueUniteLogement.setTerminal(optionalTpe.orElse(null));
        }
        if (caracteristiqueUniteLogementPaylod.getTerminalId() != null && caracteristiqueUniteLogementPaylod.getEnqueteId() != null) {
            Optional<Enquete> optionalEnquete = enqueteRepository.findFirstByExternalKeyAndTerminal_Id(caracteristiqueUniteLogementPaylod.getEnqueteId(), caracteristiqueUniteLogementPaylod.getTerminalId());
            if (optionalEnquete.isPresent()) {
                caracteristiqueUniteLogement.setEnqueteId(optionalEnquete.get().getId());
            }
        }
        caracteristiqueUniteLogement.setEnqueteExternalKey(caracteristiqueUniteLogementPaylod.getEnqueteId());
        caracteristiqueUniteLogement.setEnqueteUniteLogementExternalKey(caracteristiqueUniteLogementPaylod.getEnqueteUniteLogementId());
        caracteristiqueUniteLogement.setValeur(caracteristiqueUniteLogementPaylod.getValeur());
        caracteristiqueUniteLogement.setExternalKey(caracteristiqueUniteLogementPaylod.getExternalKey());
        return caracteristiqueUniteLogement;
    }
}
