package com.ruoyi.credit.service.impl;

import java.util.Date;
import java.util.List;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.atomic.AtomicInteger;
import java.util.concurrent.atomic.AtomicLong;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import com.ruoyi.common.utils.DateUtils;
import com.ruoyi.credit.domain.ValidationStatistics;
import com.ruoyi.credit.mapper.LoanConsistencyMapper;
import com.ruoyi.credit.mapper.ValidationStatisticsMapper;
import com.ruoyi.credit.service.IValidationStatisticsService;

/**
 * 验证统计信息Service业务层处理
 * 
 * @author ruoyi
 * @date 2025-01-12
 */
@Service
public class ValidationStatisticsServiceImpl implements IValidationStatisticsService 
{
    private static final Logger log = LoggerFactory.getLogger(ValidationStatisticsServiceImpl.class);

    @Autowired
    private ValidationStatisticsMapper validationStatisticsMapper;

    @Autowired
    private LoanConsistencyMapper loanConsistencyMapper;

    // 内存中的统计计数器，用于实时统计
    private final Map<String, AtomicInteger> dailyCounters = new ConcurrentHashMap<>();
    private final Map<String, AtomicLong> dailyTimings = new ConcurrentHashMap<>();

    /**
     * 查询验证统计信息
     * 
     * @param statisticsId 验证统计信息主键
     * @return 验证统计信息
     */
    @Override
    public ValidationStatistics selectValidationStatisticsById(Long statisticsId)
    {
        return validationStatisticsMapper.selectValidationStatisticsById(statisticsId);
    }

    /**
     * 根据日期查询验证统计信息
     * 
     * @param statisticsDate 统计日期
     * @return 验证统计信息
     */
    @Override
    public ValidationStatistics selectValidationStatisticsByDate(Date statisticsDate)
    {
        return validationStatisticsMapper.selectValidationStatisticsByDate(statisticsDate);
    }

    /**
     * 查询验证统计信息列表
     * 
     * @param validationStatistics 验证统计信息
     * @return 验证统计信息
     */
    @Override
    public List<ValidationStatistics> selectValidationStatisticsList(ValidationStatistics validationStatistics)
    {
        return validationStatisticsMapper.selectValidationStatisticsList(validationStatistics);
    }

    /**
     * 根据日期范围查询验证统计信息列表
     * 
     * @param startDate 开始日期
     * @param endDate 结束日期
     * @return 验证统计信息集合
     */
    @Override
    public List<ValidationStatistics> selectValidationStatisticsByDateRange(Date startDate, Date endDate)
    {
        return validationStatisticsMapper.selectValidationStatisticsByDateRange(startDate, endDate);
    }

    /**
     * 新增验证统计信息
     * 
     * @param validationStatistics 验证统计信息
     * @return 结果
     */
    @Override
    public int insertValidationStatistics(ValidationStatistics validationStatistics)
    {
        validationStatistics.setCreateTime(DateUtils.getNowDate());
        validationStatistics.setUpdateTime(DateUtils.getNowDate());
        validationStatistics.calculatePassRate();
        return validationStatisticsMapper.insertValidationStatistics(validationStatistics);
    }

    /**
     * 修改验证统计信息
     * 
     * @param validationStatistics 验证统计信息
     * @return 结果
     */
    @Override
    public int updateValidationStatistics(ValidationStatistics validationStatistics)
    {
        validationStatistics.setUpdateTime(DateUtils.getNowDate());
        validationStatistics.calculatePassRate();
        return validationStatisticsMapper.updateValidationStatistics(validationStatistics);
    }

    /**
     * 批量删除验证统计信息
     * 
     * @param statisticsIds 需要删除的验证统计信息主键
     * @return 结果
     */
    @Override
    public int deleteValidationStatisticsByIds(Long[] statisticsIds)
    {
        return validationStatisticsMapper.deleteValidationStatisticsByIds(statisticsIds);
    }

    /**
     * 删除验证统计信息信息
     * 
     * @param statisticsId 验证统计信息主键
     * @return 结果
     */
    @Override
    public int deleteValidationStatisticsById(Long statisticsId)
    {
        return validationStatisticsMapper.deleteValidationStatisticsById(statisticsId);
    }

    /**
     * 保存或更新验证统计信息（根据日期）
     * 
     * @param validationStatistics 验证统计信息
     * @return 结果
     */
    @Override
    @Transactional
    public int saveOrUpdateValidationStatistics(ValidationStatistics validationStatistics)
    {
        if (validationStatistics.getStatisticsDate() == null) {
            validationStatistics.setStatisticsDate(DateUtils.getNowDate());
        }
        
        validationStatistics.calculatePassRate();
        
        try {
            return validationStatisticsMapper.insertOrUpdateValidationStatistics(validationStatistics);
        } catch (Exception e) {
            log.error("保存或更新验证统计信息失败", e);
            throw e;
        }
    }

    /**
     * 记录验证结果并更新统计信息
     * 
     * @param date 验证日期
     * @param passed 是否通过验证
     * @param validationTime 验证耗时（毫秒）
     * @param cacheHit 是否命中缓存
     * @param failureReason 失败原因（如果验证失败）
     */
    @Override
    @Transactional
    public void recordValidationResult(Date date, boolean passed, long validationTime, boolean cacheHit, String failureReason)
    {
        try {
            String dateKey = DateUtils.parseDateToStr(DateUtils.YYYY_MM_DD, date);
            
            // 更新内存计数器
            updateMemoryCounters(dateKey, passed, validationTime, cacheHit);
            
            // 获取或创建当日统计记录
            ValidationStatistics statistics = selectValidationStatisticsByDate(date);
            if (statistics == null) {
                statistics = new ValidationStatistics();
                statistics.setStatisticsDate(date);
                statistics.setTotalValidations(0);
                statistics.setPassedValidations(0);
                statistics.setFailedValidations(0);
                statistics.setErrorValidations(0);
                statistics.setTimeoutValidations(0);
                statistics.setCacheHitRate(0);
                statistics.setMinValidationTime(Long.MAX_VALUE);
                statistics.setMaxValidationTime(0L);
            }
            
            // 更新统计数据
            statistics.setTotalValidations(statistics.getTotalValidations() + 1);
            
            if (passed) {
                statistics.setPassedValidations(statistics.getPassedValidations() + 1);
            } else {
                statistics.setFailedValidations(statistics.getFailedValidations() + 1);
                if (failureReason != null && !failureReason.trim().isEmpty()) {
                    statistics.setTopFailureReason(failureReason);
                }
            }
            
            // 更新时间统计
            updateTimingStatistics(statistics, validationTime);
            
            // 更新缓存命中率
            updateCacheHitRate(statistics, cacheHit);
            
            // 保存到数据库
            saveOrUpdateValidationStatistics(statistics);
            
            log.debug("记录验证结果完成，日期: {}, 通过: {}, 耗时: {}ms", dateKey, passed, validationTime);
            
        } catch (Exception e) {
            log.error("记录验证结果失败", e);
        }
    }

    /**
     * 获取今日验证统计信息
     * 
     * @return 今日验证统计信息
     */
    @Override
    public ValidationStatistics getTodayStatistics()
    {
        Date today = DateUtils.getNowDate();
        ValidationStatistics statistics = selectValidationStatisticsByDate(today);
        
        if (statistics == null) {
            // 如果没有今日统计，创建一个空的统计对象
            statistics = new ValidationStatistics();
            statistics.setStatisticsDate(today);
            statistics.setTotalValidations(0);
            statistics.setPassedValidations(0);
            statistics.setFailedValidations(0);
            statistics.setPassRate(0.0);
        }
        
        return statistics;
    }

    /**
     * 获取最新的统计记录
     * 
     * @param limit 限制数量
     * @return 验证统计信息集合
     */
    @Override
    public List<ValidationStatistics> getLatestStatistics(int limit)
    {
        return validationStatisticsMapper.selectLatestValidationStatistics(limit);
    }

    /**
     * 计算并更新统计信息
     * 
     * @param date 统计日期
     * @return 更新后的统计信息
     */
    @Override
    @Transactional
    public ValidationStatistics calculateAndUpdateStatistics(Date date)
    {
        try {
            // 从数据库重新计算统计信息
            ValidationStatistics statistics = calculateStatisticsFromDatabase(date);
            
            if (statistics != null) {
                saveOrUpdateValidationStatistics(statistics);
                log.info("重新计算并更新统计信息完成，日期: {}", DateUtils.parseDateToStr(DateUtils.YYYY_MM_DD, date));
            }
            
            return statistics;
            
        } catch (Exception e) {
            log.error("计算并更新统计信息失败，日期: {}", DateUtils.parseDateToStr(DateUtils.YYYY_MM_DD, date), e);
            return null;
        }
    }

    /**
     * 更新内存计数器
     */
    private void updateMemoryCounters(String dateKey, boolean passed, long validationTime, boolean cacheHit)
    {
        dailyCounters.computeIfAbsent(dateKey + "_total", k -> new AtomicInteger(0)).incrementAndGet();
        
        if (passed) {
            dailyCounters.computeIfAbsent(dateKey + "_passed", k -> new AtomicInteger(0)).incrementAndGet();
        } else {
            dailyCounters.computeIfAbsent(dateKey + "_failed", k -> new AtomicInteger(0)).incrementAndGet();
        }
        
        if (cacheHit) {
            dailyCounters.computeIfAbsent(dateKey + "_cache_hit", k -> new AtomicInteger(0)).incrementAndGet();
        }
        
        dailyTimings.computeIfAbsent(dateKey + "_total_time", k -> new AtomicLong(0)).addAndGet(validationTime);
    }

    /**
     * 更新时间统计
     */
    private void updateTimingStatistics(ValidationStatistics statistics, long validationTime)
    {
        // 更新最小时间
        if (statistics.getMinValidationTime() == null || validationTime < statistics.getMinValidationTime()) {
            statistics.setMinValidationTime(validationTime);
        }
        
        // 更新最大时间
        if (statistics.getMaxValidationTime() == null || validationTime > statistics.getMaxValidationTime()) {
            statistics.setMaxValidationTime(validationTime);
        }
        
        // 计算平均时间
        if (statistics.getAvgValidationTime() == null) {
            statistics.setAvgValidationTime(validationTime);
        } else {
            long totalTime = statistics.getAvgValidationTime() * (statistics.getTotalValidations() - 1) + validationTime;
            statistics.setAvgValidationTime(totalTime / statistics.getTotalValidations());
        }
    }

    /**
     * 更新缓存命中率
     */
    private void updateCacheHitRate(ValidationStatistics statistics, boolean cacheHit)
    {
        // 这里简化处理，实际应该维护缓存命中次数
        // 可以考虑在 ValidationStatistics 中添加 cacheHitCount 字段
        if (statistics.getCacheHitRate() == null) {
            statistics.setCacheHitRate(cacheHit ? 100 : 0);
        }
        // 实际实现中应该根据累计的缓存命中次数来计算准确的命中率
    }

    /**
     * 从数据库重新计算统计信息
     */
    private ValidationStatistics calculateStatisticsFromDatabase(Date date)
    {
        try {
            // 这里需要根据实际的 LoanConsistencyValidation 表结构来查询
            // 示例实现，需要根据实际情况调整
            
            ValidationStatistics statistics = new ValidationStatistics();
            statistics.setStatisticsDate(date);
            
            // 从 LoanConsistencyMapper 获取统计数据
            // 注意：这里需要在 LoanConsistencyMapper 中添加相应的统计查询方法
            
            statistics.setTotalValidations(0);
            statistics.setPassedValidations(0);
            statistics.setFailedValidations(0);
            statistics.setErrorValidations(0);
            statistics.setTimeoutValidations(0);
            
            return statistics;
            
        } catch (Exception e) {
            log.error("从数据库计算统计信息失败", e);
            return null;
        }
    }
}