package com.crm.manager.service.impl;

import com.crm.manager.dao.mapper.SalesPerformanceConfigMapper;
import com.crm.manager.dao.repository.SalesPerformanceConfigRepository;
import com.crm.manager.service.SalesPerformanceConfigService;
import com.crm.manager.service.UserInfoService;
import com.crm.rely.backend.core.constant.Constants;
import com.crm.rely.backend.core.dto.base.BaseResultWithPagerDto;
import com.crm.rely.backend.core.dto.base.PageDto;
import com.crm.rely.backend.core.dto.sales.SalesPerformanceConfigDto;
import com.crm.rely.backend.core.dto.sales.SalesPerformanceSalesDto;
import com.crm.rely.backend.core.entity.custom.info.InfoEntity;
import com.crm.rely.backend.core.entity.sales.SalesPerformanceConfigAddEntity;
import com.crm.rely.backend.core.entity.sales.SalesPerformanceConfigSearchEntity;
import com.crm.rely.backend.core.entity.sales.SalesPerformanceConfigUpdateEntity;
import com.crm.rely.backend.core.enums.SalesType;
import com.crm.rely.backend.core.pojo.table.SalesPerformanceConfigTable;
import com.crm.rely.backend.core.pojo.table.UserInfoTable;
import com.crm.rely.backend.exception.ServiceException;
import com.crm.rely.backend.util.FormatPage;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.compress.utils.Lists;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.List;

@Service
@Slf4j
public class SalesPerformanceConfigServiceImpl implements SalesPerformanceConfigService {

    @Autowired
    private SalesPerformanceConfigRepository salesPerformanceConfigRepository;
    @Autowired
    private SalesPerformanceConfigMapper salesPerformanceConfigMapper;
    @Autowired
    private UserInfoService userInfoService;

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void saveByEntity(SalesPerformanceConfigAddEntity entity, InfoEntity infoEntity) throws ServiceException {
        UserInfoTable userInfoTable = userInfoService.getDataById(entity.getSalesId());
        if (userInfoTable == null) throw ServiceException.exception(Constants.INFO_NOT_FOUND);

        if (!userInfoTable.getStamp().startsWith(infoEntity.getIbInfo().getStamp())
                || userInfoTable.getStamp().equals(infoEntity.getIbInfo().getStamp())) {
            throw ServiceException.exception(Constants.NOT_PERMIT);
        }

        if (salesPerformanceConfigRepository.existsBySalesId(entity.getSalesId())) {
            throw ServiceException.exception(Constants.RECORD_EXISTS);
        }

        SalesPerformanceConfigTable table = SalesPerformanceConfigTable.getInstance();
        BeanUtils.copyProperties(entity, table);
        table.setSalesNo(userInfoTable.getIbNo());
        table.setSalesName(userInfoTable.getName());
        table.setSalesType(userInfoTable.getSalesType());
        salesPerformanceConfigRepository.save(table);

    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void modifyByEntity(SalesPerformanceConfigUpdateEntity entity, InfoEntity infoEntity) throws ServiceException {
        UserInfoTable userInfoTable = userInfoService.getDataById(entity.getSalesId());
        if (userInfoTable == null) throw ServiceException.exception(Constants.INFO_NOT_FOUND);

        if (!userInfoTable.getStamp().startsWith(infoEntity.getIbInfo().getStamp())
                || userInfoTable.getStamp().equals(infoEntity.getIbInfo().getStamp())) {
            throw ServiceException.exception(Constants.NOT_PERMIT);
        }
        SalesPerformanceConfigTable table = salesPerformanceConfigRepository.getOne(entity.getId());
        if (table == null) throw ServiceException.exception(Constants.INFO_NOT_FOUND);

        BeanUtils.copyProperties(entity, table);
        table.setSalesNo(userInfoTable.getIbNo());
        table.setSalesName(userInfoTable.getName());
        table.setSalesType(userInfoTable.getSalesType());
        salesPerformanceConfigRepository.save(table);

    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void removeById(Long id, InfoEntity infoEntity) throws ServiceException {
        SalesPerformanceConfigTable table = salesPerformanceConfigRepository.getOne(id);
        if (table == null) throw ServiceException.exception(Constants.INFO_NOT_FOUND);

        UserInfoTable userInfoTable = userInfoService.getDataById(table.getSalesId());
        if (userInfoTable == null) throw ServiceException.exception(Constants.INFO_NOT_FOUND);

        if (!userInfoTable.getStamp().startsWith(infoEntity.getIbInfo().getStamp())
                || userInfoTable.getStamp().equals(infoEntity.getIbInfo().getStamp())) {
            throw ServiceException.exception(Constants.NOT_PERMIT);
        }

        salesPerformanceConfigRepository.deleteById(id);

    }

    @Override
    public SalesPerformanceConfigDto searchById(Long id, InfoEntity infoEntity) throws ServiceException {

        SalesPerformanceConfigTable table = salesPerformanceConfigRepository.findOne(id);
        if (table == null) throw ServiceException.exception(Constants.INFO_NOT_FOUND);

        UserInfoTable userInfoTable = userInfoService.getDataById(table.getSalesId());
        if (userInfoTable == null) throw ServiceException.exception(Constants.INFO_NOT_FOUND);

        if (!userInfoTable.getStamp().startsWith(infoEntity.getIbInfo().getStamp())) {
            throw ServiceException.exception(Constants.NOT_PERMIT);
        }

        return convertTableToDto(table);
    }

    @Override
    public BaseResultWithPagerDto<List<SalesPerformanceConfigDto>>
    searchList(SalesPerformanceConfigSearchEntity entity) throws ServiceException {
        Integer count = salesPerformanceConfigMapper.countSearch(entity);
        PageDto pageDto = FormatPage.format(entity.getPage(), count);
        if (count == null || count == 0) {
            return new BaseResultWithPagerDto(Constants.SUCCESS_CODE, Constants.SEARCH_SUCCESS, pageDto);
        }

        List<SalesPerformanceConfigTable> tables = salesPerformanceConfigMapper.listSearch(entity);
        List<SalesPerformanceConfigDto> dtos = convertTablesToDtos(tables);

        return new BaseResultWithPagerDto(Constants.SUCCESS_CODE, Constants.SEARCH_SUCCESS, pageDto, dtos);
    }

    @Override
    public List<SalesPerformanceSalesDto> getSalesDropdown(InfoEntity infoEntity) throws ServiceException {

        List<UserInfoTable> userInfoTables = userInfoService.getAllByStamp(infoEntity.getIbInfo().getStamp());
        List<SalesPerformanceSalesDto> dtos = Lists.newArrayList();
        for (UserInfoTable userInfoTable : userInfoTables) {
            SalesPerformanceSalesDto dto = new SalesPerformanceSalesDto();
            dto.setSalesId(userInfoTable.getId());
            dto.setSalesName(userInfoTable.getName());
            dto.setSalesType(userInfoTable.getSalesType());
            dto.setSaleNo(userInfoTable.getIbNo());
            dtos.add(dto);
        }

        return dtos;
    }


    private List<SalesPerformanceConfigDto> convertTablesToDtos(List<SalesPerformanceConfigTable> tables) {
        List<SalesPerformanceConfigDto> dtos = Lists.newArrayList();
        for (SalesPerformanceConfigTable table : tables) {
            dtos.add(convertTableToDto(table));
        }
        return dtos;
    }

    private SalesPerformanceConfigDto convertTableToDto(SalesPerformanceConfigTable table) {
        SalesPerformanceConfigDto dto = SalesPerformanceConfigDto.getInstance();
        BeanUtils.copyProperties(table, dto);
        dto.setSalesTypeName(SalesType.matchCode(dto.getSalesType()).getDesc());
        return dto;
    }

}
