package it.sw.pa.comune.artegna.service.impl;

import it.sw.pa.comune.artegna.domain.UtenteApp;
import it.sw.pa.comune.artegna.repository.UtenteAppRepository;
import it.sw.pa.comune.artegna.service.UserService;
import it.sw.pa.comune.artegna.service.UtenteAppService;
import it.sw.pa.comune.artegna.service.dto.UtenteAppDTO;
import it.sw.pa.comune.artegna.service.mapper.UserMapper;
import it.sw.pa.comune.artegna.service.mapper.UtenteAppMapper;
import java.util.LinkedList;
import java.util.List;
import java.util.Optional;
import java.util.stream.Collectors;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.Pageable;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

/**
 * Service Implementation for managing {@link it.sw.pa.comune.artegna.domain.UtenteApp}.
 */
@Service
@Transactional
public class UtenteAppServiceImpl implements UtenteAppService {

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

    private final UtenteAppRepository utenteAppRepository;

    private final UtenteAppMapper utenteAppMapper;

    private final UserService userService;

    private final UserMapper userMapper;

    public UtenteAppServiceImpl(
        UtenteAppRepository utenteAppRepository,
        UtenteAppMapper utenteAppMapper,
        UserService userService,
        UserMapper userMapper
    ) {
        this.utenteAppRepository = utenteAppRepository;
        this.utenteAppMapper = utenteAppMapper;
        this.userService = userService;
        this.userMapper = userMapper;
    }

    @Override
    public UtenteAppDTO save(UtenteAppDTO utenteAppDTO) {
        LOG.debug("Request to save UtenteApp : {}", utenteAppDTO);
        UtenteApp utenteApp = utenteAppMapper.toEntity(utenteAppDTO);
        utenteApp = utenteAppRepository.save(utenteApp);
        return utenteAppMapper.toDto(utenteApp);
    }

    @Override
    public UtenteAppDTO update(UtenteAppDTO utenteAppDTO) {
        LOG.debug("Request to update UtenteApp : {}", utenteAppDTO);
        UtenteApp utenteApp = utenteAppMapper.toEntity(utenteAppDTO);
        utenteApp = utenteAppRepository.save(utenteApp);
        return utenteAppMapper.toDto(utenteApp);
    }

    @Override
    public Optional<UtenteAppDTO> partialUpdate(UtenteAppDTO utenteAppDTO) {
        LOG.debug("Request to partially update UtenteApp : {}", utenteAppDTO);

        return utenteAppRepository
            .findById(utenteAppDTO.getId())
            .map(existingUtenteApp -> {
                utenteAppMapper.partialUpdate(existingUtenteApp, utenteAppDTO);

                return existingUtenteApp;
            })
            .map(utenteAppRepository::save)
            .map(utenteAppMapper::toDto);
    }

    @Override
    @Transactional(readOnly = true)
    public List<UtenteAppDTO> findAll() {
        LOG.debug("Request to get all UtenteApps");
        return utenteAppRepository.findAll().stream().map(utenteAppMapper::toDto).collect(Collectors.toCollection(LinkedList::new));
    }

    public Page<UtenteAppDTO> findAllWithEagerRelationships(Pageable pageable) {
        return utenteAppRepository.findAllWithEagerRelationships(pageable).map(utenteAppMapper::toDto);
    }

    @Override
    @Transactional(readOnly = true)
    public Optional<UtenteAppDTO> findOne(Long id) {
        LOG.debug("Request to get UtenteApp : {}", id);
        return utenteAppRepository.findOneWithEagerRelationships(id).map(utenteAppMapper::toDto);
    }

    @Override
    @Transactional(readOnly = true)
    public Optional<UtenteAppDTO> findByUsername(String username) {
        LOG.debug("Request to get UtenteApp by username : {}", username);
        return utenteAppRepository.findByUsername(username).map(utenteAppMapper::toDto);
    }

    @Override
    public void delete(Long id) {
        LOG.debug("Request to delete UtenteApp : {}", id);
        utenteAppRepository.deleteById(id);
    }

    @Override
    public UtenteAppDTO fetchUtenteAppFromUser() {
        String currentLogin = SecurityContextHolder.getContext().getAuthentication().getName();
        //User currentUser = userService.getUserWithAuthoritiesByLogin(currentLogin).orElseThrow();
        UtenteAppDTO utenteAppDTO = utenteAppRepository.findByUsername(currentLogin).map(utenteAppMapper::toDto).orElseThrow();
        return utenteAppDTO;
    }
}
