package com.yami.shop.service.impl;

import com.alibaba.excel.EasyExcel;
import com.alibaba.excel.context.AnalysisContext;
import com.alibaba.excel.event.AnalysisEventListener;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.yami.shop.bean.dto.ShopCategoryExcelDTO;
import com.yami.shop.bean.model.*;
import com.yami.shop.common.exception.GlobalException;
import com.yami.shop.dao.FrontCategoryMapper;
import com.yami.shop.dao.LabelMapper;
import com.yami.shop.dao.ShopCategoryMapper;
import com.yami.shop.dao.ShopDetailMapper;
import com.yami.shop.service.IShopCategoryService;
import lombok.AllArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.ObjectUtils;
import org.springframework.beans.BeanUtils;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.web.multipart.MultipartFile;

import javax.servlet.http.HttpServletResponse;
import java.net.URLEncoder;
import java.util.ArrayList;
import java.util.List;
import java.util.stream.Collectors;

/**
 * 门店前台类目服务实现类
 *
 * @author YourName
 * @since 2025-09-XX
 */
@Slf4j
@Service
@AllArgsConstructor
public class ShopCategoryServiceImpl extends ServiceImpl<ShopCategoryMapper, ShopCategory> implements IShopCategoryService {

    private final ShopCategoryMapper shopCategoryMapper;

    private final FrontCategoryMapper frontCategoryMapper;

    private final ShopDetailMapper shopDetailMapper;
    private final LabelMapper labelMapper;


    @Override
    public List<ShopCategory> treeShopCategory(Long shopId, String name) {
        // 获取所有未删除的前台类目
        List<ShopCategory> shopCategories = shopCategoryMapper.selectList(new LambdaQueryWrapper<ShopCategory>()
                .like(name != null, ShopCategory::getName, name)
                .eq(ShopCategory::getIsDelete, 0)
                .eq(shopId != null, ShopCategory::getShopId, shopId));
        // 构建树形结构
        return shopCategories; // 假设根节点的parentCode为"0"
//        return buildCategoryTree(shopCategories, "0"); // 假设根节点的parentCode为"0"
    }

    /**
     * 构建类目树形结构
     *
     * @param categories 所有类目列表
     * @param parentCode 父级编码
     * @return 树形结构的类目列表
     */
    private List<ShopCategory> buildCategoryTree(List<ShopCategory> categories, String parentCode) {
        List<ShopCategory> tree = new ArrayList<>();
        for (ShopCategory category : categories) {
            // 查找指定parentCode的子类目
            if (parentCode.equals(category.getParentCode())) {
                // 递归设置子类目
                List<ShopCategory> children = buildCategoryTree(categories, category.getCode());
                category.setChildren(children);
                tree.add(category);
            }
        }

        return tree;
    }


    @Override
    public void exportTemplate(HttpServletResponse response) throws Exception {
        // 设置响应头
        response.setContentType("application/vnd.openxmlformats-officedocument.spreadsheetml.sheet");
        response.setCharacterEncoding("utf-8");
        String fileName = URLEncoder.encode("门店前台类目导入模板", "UTF-8").replaceAll("\\+", "%20");
        response.setHeader("Content-disposition", "attachment;filename*=utf-8''" + fileName + ".xlsx");
        // 创建示例数据
        List<ShopCategoryExcelDTO> templateData = new ArrayList<>();
        // 使用EasyExcel导出模板
        EasyExcel.write(response.getOutputStream(), ShopCategoryExcelDTO.class)
                .sheet("店内分类导入模板")
                .doWrite(templateData);
    }


    @Override
    @Transactional(rollbackFor = Exception.class)
    public void importCategory(MultipartFile file) {
        try {
            // 检查文件是否为空
            if (file == null || file.isEmpty()) {
                throw new GlobalException("上传文件不能为空");
            }
            // 检查文件格式
            String fileName = file.getOriginalFilename();
            if (fileName == null || (!fileName.endsWith(".xls") && !fileName.endsWith(".xlsx"))) {
                throw new GlobalException("文件格式不正确，请上传Excel文件(.xls或.xlsx)");
            }
            // 解析Excel文件
            List<ShopCategory> shopCategories = parseExcelFile(file);

            // 批量保存数据
            if (!shopCategories.isEmpty()) {

                for (int i = 0; i < shopCategories.size(); i++) {
                    ShopCategory category = shopCategories.get(i);
                    // 检查数据有效性
                    Long shopId = validateShopCategories(category, i);
                    ShopCategory shopCategory = shopCategoryMapper.selectOne(
                            new LambdaQueryWrapper<ShopCategory>()
                                    .eq(ShopCategory::getName, category.getName())
                                    .eq(ShopCategory::getShopId, shopId)
                                    .eq(ShopCategory::getIsDelete, 0).eq(ShopCategory::getPid, 0L));
                    if (ObjectUtils.isEmpty(shopCategory)) {
                        category.setShopId(shopId);
                        category.setPid(0L);
                        this.save(category);
                    } else {
                        category.setId(shopCategory.getId());
                    }

                    System.out.println(category);

                    //添加对应的二级和三级类目
                    FrontCategory frontCategoryByName = frontCategoryMapper.selectListName(category.getSubName());
                    frontCategoryByName.setParentCode(category.getCode());
                    frontCategoryByName.setParentName(category.getName());
                    addShopCategory(frontCategoryByName, category.getHbShopId(), shopId, category.getId());
                }
            }
        } catch (Exception e) {
            log.error("导入门店前台类目失败：", e);
            throw new GlobalException("导入失败：" + e.getMessage());
        }
    }

    @Override
    public IPage<Category> listByParentIdAndShopId(Long parentId, Long shopId, Integer current, Integer size) {
        IPage<ShopCategory> page = page(new Page<>(current, size), new LambdaQueryWrapper<ShopCategory>()
                .eq(ShopCategory::getShopId, shopId)
                .eq(ShopCategory::getPid, parentId)
                .eq(ShopCategory::getIsDelete, 0)
                .orderByAsc(ShopCategory::getNum));
        Page res = new Page();
        BeanUtils.copyProperties(page, res);
        List<Category> categories = page.getRecords().stream().map((sc) -> {
            Category category = new Category();
            category.setCategoryId(sc.getId());
            category.setShopId(sc.getShopId());
            category.setParentId(sc.getPid());
            category.setCategoryName(sc.getName());
            category.setIcon(sc.getIcon());
            category.setPic(sc.getPic());
            category.setSeq(sc.getNum());
            category.setGrade(sc.getLevel());
            if (ObjectUtils.isNotEmpty(sc.getLabel())) {
                Label label = labelMapper.selectOne(new LambdaQueryWrapper<Label>()
                        .eq(Label::getId, sc.getLabel())
                        .eq(Label::getIsDelete, 0)
                        .eq(Label::getType, 0));
                if (null != label && null != label.getName()) {
                    category.setLabel(label.getName());
                }
            }
            return category;
        }).collect(Collectors.toList());
        res.setRecords(categories);
        return res;
    }

    /**
     * 添加对应的二级和三级类目
     *
     * @param frontCategory 前台类目模板
     * @param hbShopId      海报
     * @param shopId        门店ID
     */
    private void addShopCategory(FrontCategory frontCategory, String hbShopId, Long shopId, Long id) {
        ShopCategory shopCategory = new ShopCategory();
        shopCategory.setPid(id);
        shopCategory.setName(frontCategory.getName());
        shopCategory.setCode(frontCategory.getCode());
        shopCategory.setParentCode(frontCategory.getParentCode());
        shopCategory.setParentName(frontCategory.getName());
        shopCategory.setLevel(frontCategory.getLevel());
        shopCategory.setNum(frontCategory.getNum());
        shopCategory.setIsDelete(0);
        shopCategory.setOperateUser("admin");
        shopCategory.setIsLeaves(1);
        shopCategory.setIcon("https://zswl-shop.oss-cn-chengdu.aliyuncs.com/2025/09/eae85a85269045f6ba484bd1edf5f975.jpg");

        shopCategory.setHbShopId(hbShopId);
        shopCategory.setShopId(shopId);
        log.info("添加门店前台类目：{}", shopCategory);
        this.save(shopCategory);
        List<FrontCategory> frontCategoryList = frontCategoryMapper.selectList(new LambdaQueryWrapper<FrontCategory>()
                .eq(FrontCategory::getParentCode, frontCategory.getCode()));
        for (FrontCategory frontCategory1 : frontCategoryList) {
            addShopCategory(frontCategory1, hbShopId, shopId, shopCategory.getId());
        }
    }

    /**
     * 解析Excel文件
     *
     * @param file Excel文件
     * @return 门店前台类目列表
     */
    private List<ShopCategory> parseExcelFile(MultipartFile file) throws Exception {
        List<ShopCategory> shopCategories = new ArrayList<>();

        // 使用EasyExcel或Apache POI解析Excel
        // 这里以EasyExcel为例
        EasyExcel.read(file.getInputStream(), ShopCategoryExcelDTO.class, new AnalysisEventListener<ShopCategoryExcelDTO>() {
            @Override
            public void invoke(ShopCategoryExcelDTO excelDTO, AnalysisContext context) {
                ShopCategory shopCategory = convertToShopCategory(excelDTO);
                if (shopCategory != null) {
                    shopCategories.add(shopCategory);
                }
            }

            @Override
            public void doAfterAllAnalysed(AnalysisContext context) {
                // 解析完成后的操作
            }
        }).sheet().doRead();

        return shopCategories;
    }

    /**
     * 将Excel数据转换为ShopCategory对象
     *
     * @param excelDTO Excel数据传输对象
     * @return ShopCategory对象
     */
    private ShopCategory convertToShopCategory(ShopCategoryExcelDTO excelDTO) {
        if (excelDTO == null) {
            return null;
        }

        ShopCategory shopCategory = new ShopCategory();
        shopCategory.setName(excelDTO.getName());
        shopCategory.setSubName(excelDTO.getSubName());
        shopCategory.setCode(generateUniqueCode());
        shopCategory.setHbShopId(excelDTO.getShopId());
        shopCategory.setIsDelete(0); // 默认未删除
        shopCategory.setParentCode("0"); // 默认未删除

        return shopCategory;
    }

    /**
     * 生成唯一编码
     *
     * @return 唯一编码
     */
    private synchronized String generateUniqueCode() {
        // 使用时间戳+随机数生成唯一编码
        long timestamp = System.currentTimeMillis();
        int randomNum = (int) (Math.random() * 9999);
        return "BM" + timestamp + String.format("%04d", randomNum);
    }

    /**
     * 验证门店前台类目数据有效性
     *
     * @param category 门店前台类目
     */
    private Long validateShopCategories(ShopCategory category, int i) {
        // 检查必填字段
        if (ObjectUtils.isEmpty(category.getName())) {
            throw new GlobalException("第" + (i + 1) + "行：类目名称不能为空");
        }
        if (ObjectUtils.isEmpty(category.getHbShopId())) {
            throw new GlobalException("第" + (i + 1) + "行：门店ID不能为空");
        }
        ShopDetail shopDetail = shopDetailMapper.selectByHbStationId(category.getHbShopId());
        if (ObjectUtils.isEmpty(shopDetail)) {
            throw new GlobalException("第" + (i + 1) + "行：门店不存在");
        }

        // 检查类目名称长度
        if (category.getName().length() > 255) {
            throw new GlobalException("第" + (i + 1) + "行：类目名称长度不能超过255个字符");
        }

        // 检查是否已存在相同记录（根据类目名称+门店ID）
        ShopCategory existingCategory = this.getOne(new LambdaQueryWrapper<ShopCategory>()
                .eq(ShopCategory::getName, category.getName())
                .eq(ShopCategory::getShopId, category.getShopId())
                .last("LIMIT 1"));

        if (existingCategory != null) {
            throw new GlobalException("第" + (i + 1) + "行：门店'" + category.getShopId() +
                    "'下已存在类目名称为'" + category.getName() + "'的记录");
        }

        //查看前台类目模板里面是否存在二级类目
        Integer integer = frontCategoryMapper.selectCount(new LambdaQueryWrapper<FrontCategory>()
                .eq(FrontCategory::getName, category.getSubName())
                .eq(FrontCategory::getIsDelete, 0));

        if (integer < 1) {
            throw new GlobalException("第" + (i + 1) + "行：二级类目" + category.getSubName() + "不存在");
        }

        if (integer > 1) {
            throw new GlobalException("第" + (i + 1) + "行：二级类目" + category.getSubName() + "存在多个");
        }
        return shopDetail.getShopId();
    }


}
