package shop.alien.store.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
import com.baomidou.mybatisplus.core.toolkit.ObjectUtils;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.scheduling.annotation.Async;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.CollectionUtils;
import shop.alien.entity.result.R;
import shop.alien.entity.store.LifeUser;
import shop.alien.entity.store.StoreImg;
import shop.alien.entity.store.StoreOfficialAlbum;
import shop.alien.entity.store.StoreVideo;
import shop.alien.entity.store.vo.StoreImgTypeVo;
import shop.alien.mapper.LifeUserMapper;
import shop.alien.mapper.StoreImgMapper;
import shop.alien.mapper.StoreOfficialAlbumMapper;
import shop.alien.store.service.StoreImgService;
import shop.alien.store.service.StoreVideoService;
import shop.alien.store.util.ai.AiImageColorExtractUtil;
import shop.alien.util.common.Constants;

import java.util.Comparator;
import java.util.List;
import java.util.Objects;
import java.util.stream.Collectors;

/**
 * 二期-门店图片 服务实现类
 *
 * @author ssk
 * @since 2024-12-05
 */
@Slf4j
@Transactional
@Service
@RequiredArgsConstructor
public class StoreImgServiceImpl extends ServiceImpl<StoreImgMapper, StoreImg> implements StoreImgService {

    private final StoreImgMapper storeImgMapper;
    private final StoreOfficialAlbumMapper storeOfficialAlbumMapper;
    private final LifeUserMapper lifeUserMapper;
    private final AiImageColorExtractUtil aiImageColorExtractUtil;
    private final StoreVideoService storeVideoService;

    /**
     * 获取门店图片
     *
     * @param storeId 门店id
     * @param imgType 图片类型, 0:其他, 1:入口图, 2:相册, 3:菜品, 4:环境, 5:价目表, 6:推荐菜, 7:菜单, 8:用户评论, 9:商家申诉, 10:商家头像, 11:店铺轮播图
     * @return list
     */
    @Override
    public List<StoreImg> getStoreImg(Integer storeId, Integer imgType) {
        LambdaQueryWrapper<StoreImg> lambdaQueryWrapper = new LambdaQueryWrapper<>();
        lambdaQueryWrapper.eq(StoreImg::getStoreId, storeId).eq(StoreImg::getImgType, imgType).orderByAsc(StoreImg::getImgSort);
        return this.list(lambdaQueryWrapper);
    }

    /**
     * 获取所有图片类型和数量
     *
     * @param storeId 门店id
     * @return StoreImgTypeVo
     */
    @Override
    public List<StoreImgTypeVo> getStoreImgTypeCount(Integer storeId) {
        List<StoreImgTypeVo> storeImgTypeVoList = storeImgMapper.getStoreImgTypeCount(storeId);
        for (StoreImgTypeVo storeImgTypeVo : storeImgTypeVoList) {
            //图片类型, 0:其他, 1:入口图, 2:相册, 3:菜品, 4:环境, 5:价目表, 6:推荐菜, 7:菜单, 8:用户评论, 9:商家申诉, 10:商家头像, 11:店铺轮播图
            switch (storeImgTypeVo.getImgType()) {
                case 0:
                    storeImgTypeVo.setImgTypeStr("其他");
                    break;
                case 3:
                    storeImgTypeVo.setImgTypeStr("菜品");
                    break;
                case 4:
                    storeImgTypeVo.setImgTypeStr("环境");
                    break;
                case 5:
                    storeImgTypeVo.setImgTypeStr("价目表");
                    break;
            }
        }
        return storeImgTypeVoList.stream().sorted(Comparator.comparing(StoreImgTypeVo::getImgType)).collect(Collectors.toList());
    }

    /**
     * 获取轮播图
     *
     * @return List<StoreImg>
     */
    @Override
    public List<StoreImg> getCarouselImage() {
        return this.list(new LambdaQueryWrapper<StoreImg>().eq(StoreImg::getImgType, 11));
    }

    @Override
    public List<String> getUrl(String id, Integer imgType) {
        QueryWrapper qw = new QueryWrapper<StoreImg>();
        qw.eq(Objects.nonNull(id), "store_id", id).
                eq(Objects.nonNull(imgType), "img_type", imgType);
        List<StoreImg> resDb = storeImgMapper.selectList(qw);
        return resDb.stream().map(StoreImg::getImgUrl).collect(Collectors.toList());

    }

    /**
     * 获取用户打卡广场小人图片
     *
     * @param userId 用户ID，用于标识和获取特定用户的信息
     * @return
     */
    @Override
    public R<String> getUserClockImg(Integer userId) {
        // 查询用户信息
        LifeUser lifeUser = lifeUserMapper.selectById(userId);

        // 判断用户是否存在
        if (ObjectUtils.isNotEmpty(lifeUser)) {
            // 检查用户是否设置了自定义打卡图片
            if (ObjectUtils.isNotEmpty(lifeUser.getClockImgId())) {
                // 查询用户设置的自定义图片
                StoreImg storeImg = storeImgMapper.selectById(lifeUser.getClockImgId());
                // 返回自定义图片URL或提示素材缺失
                if (ObjectUtils.isNotEmpty(storeImg)) {
                    return R.data(storeImg.getImgUrl());
                } else {
                    return R.fail("素材缺失");
                }
            } else {
                /*// 查询默认打卡图片
                StoreImg storeImg = storeImgMapper.selectOne(new QueryWrapper<StoreImg>().eq("img_type", 17).orderByAsc("img_sort").last("limit 1"));
                // 设置默认图片给用户并返回图片URL或提示素材缺失
                if (ObjectUtils.isNotEmpty(storeImg)) {
                    lifeUser.setClockImgId(storeImg.getId());
                    lifeUserMapper.updateById(lifeUser);
                    return R.data(storeImg.getImgUrl());
                } else {
                    return R.fail("素材缺失");
                }*/
                return R.data("");
            }
        } else {
            // 提示用户不存在
            return R.fail("用户不存在");
        }
    }

    /**
     * 通过businessId获取图片
     *
     * @param storeId 门店id
     * @param imgType 图片类型, 0:其他, 1:入口图, 2:相册, 3:菜品, 4:环境, 5:价目表, 6:推荐菜, 7:菜单, 8:用户评论, 9:商家申诉, 10:商家头像, 11:店铺轮播图
     * @param businessId 业务ID
     * @return list
     */
    @Override
    public List<StoreImg> getByBusinessId(Integer storeId, Integer imgType, Integer businessId) {
        if (imgType==4){
            LambdaQueryWrapper<StoreOfficialAlbum> queryWrapper = new LambdaQueryWrapper<>();
            queryWrapper.eq(StoreOfficialAlbum::getStoreId, storeId)
                    .eq(StoreOfficialAlbum::getAlbumName, "环境");
            List<StoreOfficialAlbum> list = storeOfficialAlbumMapper.selectList(queryWrapper);
            if (!CollectionUtils.isEmpty(list)) {
                StoreOfficialAlbum officialAlbum = list.get(0);
                if (ObjectUtils.isNotEmpty(officialAlbum)) {
                    businessId = officialAlbum.getId();
                }
            }
        }
        LambdaQueryWrapper<StoreImg> lambdaQueryWrapper = new LambdaQueryWrapper<>();
        lambdaQueryWrapper.eq(StoreImg::getStoreId, storeId)
                .eq(StoreImg::getImgType, imgType)
                .eq(StoreImg::getBusinessId, businessId).orderByAsc(StoreImg::getImgSort);
        List<StoreImg> storeImgList = this.list(lambdaQueryWrapper);
        int imgCount = storeImgList.size();
        LambdaUpdateWrapper<StoreOfficialAlbum> updateWrapper = new LambdaUpdateWrapper<>();
        updateWrapper.eq(StoreOfficialAlbum::getId, businessId).set(StoreOfficialAlbum::getImgCount, imgCount);
        storeOfficialAlbumMapper.update(null, updateWrapper);
        List<StoreImg> resList = this.list(lambdaQueryWrapper);
        // 查询对应相册的视频列表，获取第一个视频的封面
        if (businessId != null && businessId > 0) {
            List<StoreVideo> videoList = storeVideoService.getByStoreIdAndBusinessId(storeId, businessId);
            if (!CollectionUtils.isEmpty(videoList)) {
                StoreVideo storeVideo = videoList.get(0);
                String imgUrl = storeVideo.getImgUrl();
                if (imgUrl != null && !imgUrl.trim().isEmpty()) {
                    try {
                        // 解析JSON对象格式的imgUrl: {"video": "...", "cover": "..."}
                        com.alibaba.fastjson.JSONObject jsonObject = com.alibaba.fastjson.JSON.parseObject(imgUrl);
                        if (jsonObject != null && jsonObject.containsKey("cover")) {
                            String coverUrl = jsonObject.getString("cover");
                            if (coverUrl != null && !coverUrl.trim().isEmpty()) {
                                // 创建StoreImg对象，设置封面URL（注意：这是临时对象，id为null是正常的）
                                // 如果需要避免id为null，可以考虑不添加此对象，或者从视频表查询对应的图片记录
                                StoreImg storeImg = new StoreImg();
                                storeImg.setImgUrl(coverUrl);
                                storeImg.setStoreId(storeId);
                                storeImg.setImgType(imgType);
                                storeImg.setBusinessId(businessId);
                                storeImg.setImgDescription("视频");
                                storeImg.setImgSort(resList.size() + 1);
                                // 设置一个临时ID标识，避免前端处理null值的问题
                                // 使用负数作为临时标识，表示这是从视频中提取的封面
                                int tempId = storeVideo.getId() != null ? -storeVideo.getId() : -(int)(System.currentTimeMillis() % Integer.MAX_VALUE);
                                storeImg.setId(tempId);
                                resList.add(storeImg);
                                log.info("从视频中提取封面成功，视频ID：{}，coverUrl: {}", storeVideo.getId(), coverUrl);
                            }
                        }
                    } catch (Exception e) {
                        log.warn("解析视频imgUrl失败，imgUrl: {}, error: {}", imgUrl, e.getMessage());
                    }
                }
            }
        }
        return resList;
    }

    @Override
    public int saveOrUpdateImg(Integer storeId, Integer imgType) {
        int result = 0;
        if(storeId !=null && storeId > 0 && imgType != null){
            result = storeImgMapper.delete(new LambdaQueryWrapper<StoreImg>().eq(StoreImg::getStoreId, storeId).eq(StoreImg::getImgType, imgType));
        }
        return result;
    }

    /**
     * 异步提取图片颜色（不阻塞主流程）
     * 该方法在后台异步执行，提取成功后更新数据库中的颜色码
     *
     * @param storeImgId 图片ID
     * @param imgUrl 图片URL
     */
    @Override
    @Async("taskExecutor")
    public void asyncExtractColorForImg(Integer storeImgId, String imgUrl) {
        try {
            log.info("开始异步提取图片颜色，storeImgId: {}, imgUrl: {}", storeImgId, imgUrl);
            String colorCode = aiImageColorExtractUtil.extractCoverColor(imgUrl);
            if (colorCode != null) {
                // 更新数据库中的颜色码
                StoreImg updateImg = new StoreImg();
                updateImg.setId(storeImgId);
                updateImg.setColorCode(colorCode);
                updateImg.setIsExtract(1); // 提取成功，设置为已提取
                this.updateById(updateImg);
                log.info("异步提取图片颜色成功，storeImgId: {}, colorCode: {}", storeImgId, colorCode);
            } else {
                log.warn("异步提取图片颜色失败，storeImgId: {}, imgUrl: {}", storeImgId, imgUrl);
            }
        } catch (Exception e) {
            log.error("异步提取图片颜色异常，storeImgId: {}, imgUrl: {}", storeImgId, imgUrl, e);
        }
    }

    @Override
    public List<StoreImg> getByCover(Integer storeId, Integer imgType) {

        log.info("StoreImgController.getByBusinessId?storeId={}&imgType={}", storeId, imgType);



        QueryWrapper<StoreImg> queryWrapper = new QueryWrapper<>();

        queryWrapper.lambda()
                .eq(StoreImg::getImgType, imgType) // 商品 图片
                .eq(StoreImg::getDeleteFlag, Constants.DeleteFlag.NOT_DELETED)
                .eq(StoreImg::getStoreId,storeId );
        List<StoreImg> imagesList= storeImgMapper.getByCover(queryWrapper);


        return imagesList;
    }
}
