
package com.yami.shop.service.impl;

import cn.hutool.core.util.ObjectUtil;
import com.alibaba.excel.EasyExcel;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.yami.shop.bean.dto.SetChannelPriceDto;
import com.yami.shop.bean.dto.UpdateShannerProdDTO;
import com.yami.shop.bean.model.*;
import com.yami.shop.bean.vo.ChannelProdImportVO;
import com.yami.shop.common.exception.GlobalException;
import com.yami.shop.dao.*;
import com.yami.shop.service.ChannelProdService;
import lombok.AllArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.web.multipart.MultipartFile;

import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.math.BigDecimal;
import java.net.URLEncoder;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;

/**
 * 渠道对应商品管理服务实现类
 *
 * @author lgh on 2024/01/01.
 */
@Slf4j
@Service
@AllArgsConstructor
public class ChannelProdServiceImpl extends ServiceImpl<ChannelProdMapper, ChannelProd> implements ChannelProdService {

    private final ChannelProdMapper channelProdMapper;
    private final ChannelMapper channelMapper;
    private final ShopDetailMapper shopDetailMapper;
    private final ChannelShopMapper channelShopMapper;
    private final SkuMapper skuMapper;

    @Override
    public List<ChannelProd> getChannelProdsBychannelId(Long channelId) {
        if (channelId == null) {
            throw new GlobalException("渠道ID不能为空");
        }
        return channelProdMapper.getChannelProdsBychannelId(channelId);
    }

    @Override
    public List<ChannelProd> getChannelProdsBySkuId(Long skuId) {
        if (skuId == null) {
            throw new GlobalException("SKU ID不能为空");
        }
        return channelProdMapper.getChannelProdsBySkuId(skuId);
    }

    @Override
    public ChannelProd getChannelProdBychannelIdAndSkuId(Long channelId, Long skuId) {
        if (channelId == null) {
            throw new GlobalException("渠道ID不能为空");
        }
        if (skuId == null) {
            throw new GlobalException("SKU ID不能为空");
        }
        return channelProdMapper.getChannelProdBychannelIdAndSkuId(channelId, skuId);
    }

//    @Override
//    public IPage<ChannelProd> getChannelProdPage(PageParam<ChannelProd> page, ChannelProd channelProd) {
//        return channelProdMapper.getChannelProdPage(page, channelProd);
//    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void saveChannelProd(ChannelProd channelProd) {
        if (channelProd == null) {
            throw new GlobalException("渠道商品信息不能为空");
        }
        if (channelProd.getChannelId() == null) {
            throw new GlobalException("渠道ID不能为空");
        }
        if (channelProd.getSkuId() == null) {
            throw new GlobalException("SKU ID不能为空");
        }
        if (channelProd.getPurchasePrice() == null) {
            throw new GlobalException("进货价不能为空");
        }
        if (channelProd.getDeliveryPrice() == null) {
            throw new GlobalException("出货价不能为空");
        }
        if (channelProd.getChannelProdPrice() == null) {
            throw new GlobalException("渠道商品售价不能为空");
        }

        // 检查是否已存在
        ChannelProd existing = getChannelProdBychannelIdAndSkuId(channelProd.getChannelId(), channelProd.getSkuId());
        if (existing != null) {
            throw new GlobalException("该渠道下已存在此商品");
        }

        channelProd.setIsDelete(0);
        channelProd.setRecTime(new Date());
        channelProd.setUpdateTime(new Date());
        channelProdMapper.insert(channelProd);
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void updateChannelProd(ChannelProd channelProd) {
        if (channelProd == null) {
            throw new GlobalException("渠道商品信息不能为空");
        }
        if (channelProd.getId() == null) {
            throw new GlobalException("渠道商品ID不能为空");
        }

        channelProd.setUpdateTime(new Date());
        channelProdMapper.updateById(channelProd);
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void deleteChannelProdById(Long id) {
        if (id == null) {
            throw new GlobalException("渠道商品ID不能为空");
        }
        channelProdMapper.deleteById(id);
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void deleteChannelProdsBychannelId(Long channelId) {
        if (channelId == null) {
            throw new GlobalException("渠道ID不能为空");
        }
        channelProdMapper.deleteBychannelId(channelId);
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void deleteChannelProdsBySkuId(Long skuId) {
        if (skuId == null) {
            throw new GlobalException("SKU ID不能为空");
        }
        channelProdMapper.deleteBySkuId(skuId);
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void updateBatchPrices(List<ChannelProd> channelProds) {
        if (channelProds == null || channelProds.isEmpty()) {
            throw new GlobalException("渠道商品列表不能为空");
        }
        channelProdMapper.updateBatchPrices(channelProds);
    }

    @Override
    public Integer countByChannelId(Long channelId) {
        if (channelId == null) {
            throw new GlobalException("渠道ID不能为空");
        }
        return channelProdMapper.countBychannelId(channelId);
    }

    @Override
    public Integer countBySkuId(Long skuId) {
        if (skuId == null) {
            throw new GlobalException("SKU ID不能为空");
        }
        return channelProdMapper.countBySkuId(skuId);
    }

    @Override
    public Boolean existsByChannelIdAndSkuId(Long channelId, Long skuId) {
        if (channelId == null) {
            throw new GlobalException("渠道ID不能为空");
        }
        if (skuId == null) {
            throw new GlobalException("SKU ID不能为空");
        }
        ChannelProd channelProd = getChannelProdBychannelIdAndSkuId(channelId, skuId);
        return channelProd != null;
    }


    @Override
    public void downloadTemplate(HttpServletResponse response) {
        // 设置响应头
        response.setContentType("application/vnd.openxmlformats-officedocument.spreadsheetml.sheet");
        response.setCharacterEncoding("utf-8");
        try {
            String fileName = URLEncoder.encode("渠道商品导入模板", "UTF-8").replaceAll("\\+", "%20");

            response.setHeader("Content-disposition", "attachment;filename*=utf-8''" + fileName + ".xlsx");
//
//        // 创建模板数据（示例数据）
            List<ChannelProdImportVO> templateData = new ArrayList<>();

            // 写入Excel
            EasyExcel.write(response.getOutputStream(), ChannelProdImportVO.class)
                    .sheet("商品渠道及价格导入模板")
                    .doWrite(templateData);
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

    @Override
    public String importChannelProds(MultipartFile file) {
        // 读取Excel数据
        List<ChannelProdImportVO> importData = null;
        try {
            importData = EasyExcel.read(file.getInputStream())
                    .head(ChannelProdImportVO.class)
                    .sheet()
                    .doReadSync();
        } catch (IOException e) {
            log.error("读取Excel数据异常");
            e.printStackTrace();
        }

        int successCount = 0;
        for (int i = 0; i < importData.size(); i++) {
            ChannelProdImportVO importVO = importData.get(i);
            try {
                // 数据校验
                if (importVO.getChannelName() == null) {
                    throw new RuntimeException("渠道不能为空");
                }
                if (importVO.getSkuId() == null && importVO.getSkuCode() == null) {
                    throw new RuntimeException("失败原因:海博商品ID和商品编码不能同时为空");
                }
                if (importVO.getShopName() == null) {
                    throw new RuntimeException("海博门店不能为空");
                }
                if (importVO.getChannelProdPrice() == null || importVO.getChannelProdPrice().compareTo(BigDecimal.ZERO) < 0) {
                    throw new RuntimeException("渠道售价不能为空且必须大于等于0");
                }

                // 转换为实体对象
                ChannelProd channelProd = new ChannelProd();
                Channel channel = channelMapper.selectByName(importVO.getChannelName());
                if (ObjectUtil.isEmpty(channel)) {
                    log.error("渠道:{},在系统中不存在", importVO.getChannelName());
                    throw new GlobalException(String.format("失败原因: 渠道=%s,在系统中不存在", importVO.getChannelName()));
                }
                channelProd.setChannelId(channel.getId());

                Sku sku = skuMapper.selectOne(new LambdaQueryWrapper<Sku>()
                        .eq(importVO.getSkuId()!=null,Sku::getHbSkuId, importVO.getSkuId())
                        .eq(importVO.getSkuCode()!=null,Sku::getSkuCode, importVO.getSkuCode())
                        .eq(Sku::getIsDelete, 0));
                if (ObjectUtil.isEmpty(sku)) {
                    if (importVO.getSkuId() != null && importVO.getSkuCode() != null){
                        log.error("商品ID:{} 商品编码：{}，在系统中不存在", importVO.getSkuId(), importVO.getSkuCode());
                        throw new GlobalException(String.format("失败原因: 商品ID=%s 商品编码=%s,在系统中不存在", importVO.getSkuId(), importVO.getSkuCode()));
                    }
                    if (importVO.getSkuId() != null){
                        log.error("商品ID:{},在系统中不存在", importVO.getSkuId());
                        throw new GlobalException(String.format("失败原因: 商品ID=%s,在系统中不存在", importVO.getSkuId()));
                    }
                    if (importVO.getSkuCode() != null){
                        log.error("商品编码:{},在系统中不存在", importVO.getSkuCode());
                        throw new GlobalException(String.format("失败原因: 商品编码=%s,在系统中不存在", importVO.getSkuCode()));
                    }
                }
                channelProd.setSkuId(sku.getSkuId());
                channelProd.setPurchasePrice(importVO.getPurchasePrice());
                channelProd.setDeliveryPrice(importVO.getDeliveryPrice());
                channelProd.setChannelProdPrice(importVO.getChannelProdPrice());
                channelProd.setRecTime(new Date());
                channelProd.setUpdateTime(new Date());

                //检查门店是否存在
                ShopDetail shopDetail = shopDetailMapper.selectOne(new LambdaQueryWrapper<ShopDetail>().eq(ShopDetail::getShopName, importVO.getShopName()));
                if (ObjectUtil.isEmpty(shopDetail)) {
                    log.error("门店：{}，在系统中不存在", importVO.getShopName());
                    throw new GlobalException(String.format("失败原因: 门店=%s,在系统中不存在", importVO.getShopName()));
                }
                channelProd.setShopId(shopDetail.getShopId());

                // 新增操作
                ChannelProd channelProdCount = channelProdMapper.selectOne(new LambdaQueryWrapper<ChannelProd>()
                        .eq(ChannelProd::getShopId, shopDetail.getShopId())
                        .eq(ChannelProd::getIsDelete, 0)
                        .eq(ChannelProd::getSkuId, channelProd.getSkuId())
                        .eq(ChannelProd::getChannelId, channelProd.getChannelId()));
                if (channelProdCount == null) {
                    channelProdMapper.insert(channelProd);
                    log.info("添加渠道门店商品数据成功");
                }else {
                    channelProd.setId(channelProdCount.getId());
                    channelProdMapper.updateById(channelProd);
                }
                //添加渠道门店关联数据
                //检查门店是否已存在
                int channelShopCount = channelShopMapper.selectCount(new LambdaQueryWrapper<ChannelShop>()
                        .eq(ChannelShop::getShopId, shopDetail.getShopId())
                        .eq(ChannelShop::getIsDelete, 0)
                        .eq(ChannelShop::getChannelId, channelProd.getChannelId()));
                if (channelShopCount == 0) {
                    ChannelShop channelShop = new ChannelShop();
                    channelShop.setIsDelete(0);
                    channelShop.setChannelId(channelProd.getChannelId());
                    channelShop.setShopId(shopDetail.getShopId());
                    channelShopMapper.insert(channelShop);
                    log.info("添加渠道门店关联数据成功");
                }
                successCount++;
            } catch (Exception e) {
                log.error("导入数据失败，行号：{}，错误：{}", i + 3, e.getMessage());
                throw new GlobalException(String.format("第%s行数据导入失败！ %s", i + 3,e.getMessage()));
            }
        }
        return String.format("导入完成，成功：%d条", successCount);
    }
    // ... existing code ...

// ... existing code ...

    @Override
    public void setUpChannels(UpdateShannerProdDTO updateShannerProdDTO) {
        //根据门店和商品ID删除
        channelProdMapper.deleteChannelProd(updateShannerProdDTO);
        List<SetChannelPriceDto> setChannelPriceDtoList = updateShannerProdDTO.getSetChannelPriceDtoList();
        if (setChannelPriceDtoList != null){
            for (SetChannelPriceDto setChannelPriceDto : setChannelPriceDtoList) {
                ChannelProd channelProd = new ChannelProd();
                channelProd.setChannelId(setChannelPriceDto.getChannelId());
                channelProd.setSkuId(updateShannerProdDTO.getSkuId());
                channelProd.setShopId(updateShannerProdDTO.getShopId());
                channelProd.setPurchasePrice(updateShannerProdDTO.getPurchasePrice());
                channelProd.setDeliveryPrice(updateShannerProdDTO.getDeliveryPrice());
                if (setChannelPriceDto.getChannelProdPrice() == null){
                    throw new GlobalException("渠道售价不能为空");
                }
                channelProd.setChannelProdPrice(setChannelPriceDto.getChannelProdPrice());
                channelProd.setRecTime(new Date());
                channelProd.setIsDelete(0);
                channelProd.setUpdateTime(new Date());
                channelProdMapper.insert(channelProd);

                //检查门店是否已存在
                int channelShopCount = channelShopMapper.selectCount(new LambdaQueryWrapper<ChannelShop>()
                        .eq(ChannelShop::getShopId, updateShannerProdDTO.getShopId())
                        .eq(ChannelShop::getIsDelete, 0)
                        .eq(ChannelShop::getChannelId, setChannelPriceDto.getChannelId()));
                if (channelShopCount == 0) {
                    ChannelShop channelShop = new ChannelShop();
                    channelShop.setIsDelete(0);
                    channelShop.setChannelId(setChannelPriceDto.getChannelId());
                    channelShop.setShopId(updateShannerProdDTO.getShopId());
                    channelProd.setUpdateTime(new Date());
                    channelShopMapper.insert(channelShop);
                    log.info("添加渠道门店关联数据成功");
                }
            }
        }

    }

}
