package org.jeecg.modules.system.app.service.impl;

import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import org.apache.commons.lang3.StringUtils;
import org.jeecg.modules.app.dto.evaluate.FindEvaluateDTO;
import org.jeecg.modules.app.dto.evaluate.FindEvaluatePage;
import org.jeecg.modules.system.app.dto.evaluate.FindEvaluateRequestDTO;
import org.jeecg.modules.system.app.dto.evaluate.FindEvaluateResponseDTO;
import org.jeecg.modules.system.app.entity.Evaluate;
import org.jeecg.modules.system.app.mapper.AppCoursesMapper;
import org.jeecg.modules.system.app.mapper.EvaluateMapper;
import org.jeecg.modules.system.app.service.IEvaluateService;
import org.jeecg.modules.system.app.utils.StringMasker;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.math.BigDecimal;
import java.math.RoundingMode;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

/**
 * @Description: 评价管理
 * @Author: jeecg-boot
 * @Date:   2025-07-07
 * @Version: V1.0
 */
@Service
public class EvaluateServiceImpl extends ServiceImpl<EvaluateMapper, Evaluate> implements IEvaluateService {

    @Autowired
    EvaluateMapper evaluateMapper;
    @Autowired
    private AppCoursesMapper appCoursesMapper;


    @Override
    public IPage<FindEvaluateResponseDTO> findPage(Integer pageNo, Integer pageSize, FindEvaluateRequestDTO findEvaluateRequestDTO) {
        Page<FindEvaluateResponseDTO> page = new Page<FindEvaluateResponseDTO>(pageNo, pageSize);
        IPage<FindEvaluateResponseDTO> findEvaluateResponseDTOIPage= evaluateMapper.findPage(page, findEvaluateRequestDTO);
        if (findEvaluateResponseDTOIPage!=null&&findEvaluateResponseDTOIPage.getRecords()!=null){
            for (FindEvaluateResponseDTO record : findEvaluateResponseDTOIPage.getRecords()) {
                List<String> strings = new ArrayList<>();
                if (StringUtils.isNotEmpty(record.getImages())) {
                    if (record.getImages().indexOf(",")>0){
                        strings = Arrays.asList(record.getImages().split(","));
                    }else {
                        strings.add(record.getImages());
                    }
                }
                if (record.getIsAnonymous()!=null&&record.getIsAnonymous()==0){
                    String username = record.getUsername();
                    String mask = StringMasker.mask(username);
                    record.setUsername(mask);
                }
                record.setImageList(strings);
            }
        }
        return findEvaluateResponseDTOIPage;
    }

    @Override
    public FindEvaluatePage<FindEvaluateResponseDTO> findByOrderPage(FindEvaluateDTO findEvaluateDTO) {
        Page<FindEvaluateResponseDTO> page = new Page<FindEvaluateResponseDTO>(findEvaluateDTO.getPageNo(), findEvaluateDTO.getPageSize());
        IPage<FindEvaluateResponseDTO> findEvaluateResponseDTOIPage=page;
        List<String> coursesIds = new ArrayList<>();
        BigDecimal averageScore =BigDecimal.valueOf(0).setScale(1 , RoundingMode.DOWN);
        Long scoreNum =0L;//评论数
        Long scoreSum =0L;//总评分
        Long goodScoreNum =0L;//好评数
        long applauseRate = 0L;
        if (StringUtils.isNotEmpty(findEvaluateDTO.getSiteId())){
            findEvaluateResponseDTOIPage = evaluateMapper.findBySiteId(page,findEvaluateDTO.getSiteId());
            scoreSum = evaluateMapper.findByAverageScore(findEvaluateDTO.getSiteId());//评论总评分
            scoreNum =  evaluateMapper.findByScoreNum(findEvaluateDTO.getSiteId());//评论总数
            goodScoreNum = evaluateMapper.findByGoodScoreNum(findEvaluateDTO.getSiteId());//好评数
            averageScore=calculateAverage(scoreSum,scoreNum);//评价平均评分
            applauseRate = goodScoreNumRate(goodScoreNum, scoreNum);//评价好评率
        } else if (StringUtils.isNotEmpty(findEvaluateDTO.getInstructorId())) {
            coursesIds = appCoursesMapper.findByInstructorId(findEvaluateDTO.getInstructorId());
        } else if (StringUtils.isNotEmpty(findEvaluateDTO.getCoursesId())) {
            coursesIds.add(findEvaluateDTO.getCoursesId());
        }
        if (coursesIds!=null&&!coursesIds.isEmpty()){
            findEvaluateResponseDTOIPage = evaluateMapper.findByCoursesId(page,coursesIds);
            scoreSum = evaluateMapper.findByAverageScoreByCoursesId(coursesIds);
            scoreNum =  evaluateMapper.findByScoreNumByCoursesId(coursesIds);
            goodScoreNum = evaluateMapper.findByGoodScoreNumByCoursesId(coursesIds);
            averageScore=calculateAverage(scoreSum,scoreNum);
            applauseRate = goodScoreNumRate(goodScoreNum, scoreNum);
        }
        if (findEvaluateResponseDTOIPage!=null &&findEvaluateResponseDTOIPage.getRecords()!=null){
            for (FindEvaluateResponseDTO record : findEvaluateResponseDTOIPage.getRecords()) {
                if (record.getIsAnonymous()!=null&&record.getIsAnonymous()==0){
                    String username = record.getUsername();
                    String mask = StringMasker.mask(username);
                    record.setUsername(mask);
                }
            }
        }

        return  FindEvaluatePage.build(findEvaluateResponseDTOIPage, averageScore, scoreNum,applauseRate);
    }

    @Override
    public Evaluate findByOrder(String orderId) {
        return evaluateMapper.findByOrderId(orderId);
    }

    @Override
    public Map<String, Long> batchGetGoodRateByInstructorIds(List<String> instructorIds) {
        Map<String, Long> resultMap = new HashMap<>();
        if (instructorIds == null || instructorIds.isEmpty()) {
            return resultMap;
        }
        List<Map<String, Object>> results = evaluateMapper.batchFindGoodRateByInstructorIds(instructorIds);
        if (results != null) {
            for (Map<String, Object> result : results) {
                String instructorId = (String) result.get("instructorId");
                Object goodRateObj = result.get("goodRate");
                Long goodRate = 0L;
                if (goodRateObj != null) {
                    if (goodRateObj instanceof Number) {
                        goodRate = ((Number) goodRateObj).longValue();
                    }
                }
                resultMap.put(instructorId, goodRate);
            }
        }
        return resultMap;
    }

    public static BigDecimal calculateAverage(Long scoreSum, Long scoreNum) {
        if (scoreNum == 0L) {
          return  BigDecimal.valueOf(0).setScale(1 , RoundingMode.DOWN);
        }

        // 将分子和分母都转换为BigDecimal
        BigDecimal sum = new BigDecimal(scoreSum);
        BigDecimal num = new BigDecimal(scoreNum);

        // 计算平均数，保留1位小数并四舍五入
        return sum.divide(num, 1, RoundingMode.HALF_UP);
    }


    public static long goodScoreNumRate(Long goodScoreNum, Long scoreNum) {
        // 计算平均数
        return scoreNum == 0 ? 0 : (long) (goodScoreNum * 100.00 / scoreNum);
    }
}
