package com.fjhx.sale.service.commission.impl;

import cn.hutool.core.util.ObjectUtil;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.fjhx.sale.entity.commission.dto.CommissionDto;
import com.fjhx.sale.entity.commission.dto.CommissionSelectDto;
import com.fjhx.sale.entity.commission.po.Commission;
import com.fjhx.sale.entity.commission.po.CommissionRule;
import com.fjhx.sale.entity.commission.vo.CommissionVo;
import com.fjhx.sale.entity.contract.po.Contract;
import com.fjhx.sale.mapper.commission.CommissionMapper;
import com.fjhx.sale.service.commission.CommissionRuleService;
import com.fjhx.sale.service.commission.CommissionService;
import com.fjhx.sale.service.contract.ContractService;
import com.ruoyi.common.exception.ServiceException;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.math.BigDecimal;


/**
 * <p>
 * 业绩提成表 服务实现类
 * </p>
 *
 * @author
 * @since 2023-05-11
 */
@Service
public class CommissionServiceImpl extends ServiceImpl<CommissionMapper, Commission> implements CommissionService {
    @Autowired
    private ContractService contractService;

    @Autowired
    private CommissionRuleService commissionRuleService;


    @Override
    public Page<CommissionVo> getPage(CommissionSelectDto dto) {
        QueryWrapper<Object> query = Wrappers.query();
        query.eq(ObjectUtil.isNotEmpty(dto.getUserId()), "c.user_id", dto.getUserId());
        query.eq(ObjectUtil.isNotEmpty(dto.getTime()), "DATE_FORMAT(c.create_time,'%Y')", dto.getTime());
        query.like(ObjectUtil.isNotEmpty(dto.getKeyword()),"c.contract_code",dto.getKeyword());
        query.orderByDesc("c.create_time");
        Page<CommissionVo> page = this.baseMapper.getPage(dto.getPage(), query);
        return page;
    }


    /**
     * 结算功能(添加业务提成表与业务提成规则表,修改合同表的结算状态)
     */
    @Override
    public void settlement(CommissionDto commissionDto) {
        if (ObjectUtil.isEmpty(commissionDto.getSettlementStatus())){
            throw  new ServiceException("参数缺失：结算状态或业绩提成规则表不能为null");
        }

        //修改合同表的结算状态
        Contract contract = new Contract();
        contract.setId(commissionDto.getContractId());
        contract.setSettlementStatus(commissionDto.getSettlementStatus());
        contractService.updateById(contract);

        //查询业绩表的信息
        Commission commission = baseMapper.selectOne(Wrappers.<Commission>lambdaQuery()
                .eq(Commission::getContractId, commissionDto.getContractId()));


        //如果为未结算则删除业绩提成表与业绩提成规则表的信息
        if (commissionDto.getSettlementStatus() == 0){
            //如果是取消结算，业绩表肯定有值
            Commission cm = baseMapper.selectOne(Wrappers.<Commission>query().lambda().eq(Commission::getContractId,commission.getContractId()));
            if(ObjectUtil.isEmpty(cm)){
                throw new ServiceException("数据异常,当前没有业绩提成数据,不能取消结算");
            }
            baseMapper.deleteById(cm.getId());
            commissionRuleService.remove(Wrappers.<CommissionRule>lambdaQuery()
                    .eq(CommissionRule::getCommissionId,cm.getId())
            );
        }else if (commissionDto.getSettlementStatus() == 1){
            saveOrUpdate(commissionDto);
        }

    }

    /**
     * 新增或修改业绩提成表与业绩提成规则表的信息
     * @param commissionDto
     */
    private void saveOrUpdate(CommissionDto commissionDto){
        CommissionRule commissionRule = new CommissionRule();
        if (ObjectUtil.isNotEmpty(commissionDto.getCommissionRule())){
            commissionRule = commissionDto.getCommissionRule();
        }else {
            commissionRule.setAfterSalesRatio(new BigDecimal(4));
            commissionRule.setDepartmentalRatio(new BigDecimal(33));
            commissionRule.setPersonalRatio(new BigDecimal(17));
            commissionRule.setPublicRatio(new BigDecimal(6));
            commissionRule.setHaveOverallRatio(new BigDecimal(5));
        }


        //计算售后金额：到账金额 * 售后占比（保留两位小数向上取整）
        commissionDto.setAfterSalesAmount(commissionDto.getTotalIncome()
                .multiply(commissionRule.getAfterSalesRatio())
                .divide(new BigDecimal(100))
                .setScale(2,BigDecimal.ROUND_HALF_UP));

        //计算公共金额：到账金额 * 公共占比
        commissionDto.setPublicAmount(commissionDto.getTotalIncome()
                .multiply(commissionRule.getPublicRatio())
                .divide(new BigDecimal(100))
                .setScale(2,BigDecimal.ROUND_HALF_UP));

        //计算总办金额：到账金额 * 总办占比
        commissionDto.setHaveOverallAmount(commissionDto.getTotalIncome()
                .multiply(commissionRule.getHaveOverallRatio())
                .divide(new BigDecimal(100))
                .setScale(2,BigDecimal.ROUND_HALF_UP));

        //计算净收入（总收入 - 总支出 - 售后 - 公共 - 总办）
        BigDecimal netIncome = commissionDto.getTotalIncome()
                .subtract(commissionDto.getTotalExpenses())
                .subtract(commissionDto.getAfterSalesAmount())
                .subtract(commissionDto.getPublicAmount())
                .subtract(commissionDto.getHaveOverallAmount());
        //计算部门提成金额：（总收入 - 总支出 - 售后 - 公共 - 总办） * 部门占比
        commissionDto.setDepartmentalCommission(netIncome.
                multiply(commissionRule.getDepartmentalRatio())
                .divide(new BigDecimal(100))
                .setScale(2,BigDecimal.ROUND_HALF_UP));

        //计算个人提成金额：（总收入 - 总支出 - 售后 - 公共 - 总办） * 个人占比
        commissionDto.setPersonalCommission(netIncome.multiply(commissionRule
                .getPersonalRatio()
                .divide(new BigDecimal(100))
                .setScale(2,BigDecimal.ROUND_HALF_UP)

        ));
        //如果ID为null则添加 否则为修改
        if (ObjectUtil.isNotEmpty(commissionDto.getId())){
            baseMapper.updateById(commissionDto);
        }else {
            baseMapper.insert(commissionDto);
        }
        commissionRule.setCommissionId(commissionDto.getId());
        //添加或修改业绩规则表信息
        commissionRuleService.saveOrUpdate(commissionRule);
    }

}
