package com.ycwl.basic.biz;

import com.ycwl.basic.mapper.SourceMapper;
import com.ycwl.basic.model.pc.face.entity.FaceEntity;
import com.ycwl.basic.model.pc.face.resp.FaceRespVO;
import com.ycwl.basic.model.pc.faceSample.entity.FaceSampleEntity;
import com.ycwl.basic.model.pc.faceSample.resp.FaceSampleRespVO;
import com.ycwl.basic.model.pc.source.entity.SourceEntity;
import com.ycwl.basic.model.pc.template.entity.TemplateConfigEntity;
import com.ycwl.basic.repository.FaceRepository;
import com.ycwl.basic.repository.SourceRepository;
import com.ycwl.basic.repository.TemplateRepository;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;

import java.util.ArrayList;
import java.util.Arrays;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Objects;
import java.util.concurrent.atomic.AtomicInteger;
import java.util.stream.Collectors;

@Slf4j
@Component
public class TemplateBiz {
    @Autowired
    private TemplateRepository templateRepository;
    @Autowired
    private FaceRepository faceRepository;
    @Autowired
    private SourceMapper sourceMapper;

    public boolean determineTemplateCanGenerate(Long templateId, Long faceId) {
        return determineTemplateCanGenerate(templateId, faceId, true);
    }

    public boolean determineTemplateCanGenerate(Long templateId, Long faceId, boolean scanSource) {
        List<String> placeholderList = templateRepository.getTemplatePlaceholder(templateId);
        TemplateConfigEntity templateConfig = templateRepository.getTemplateConfig(templateId);
        int minimalPlaceholderFill = 1;
        if (null != templateConfig) {
            if (null != templateConfig.getMinimalPlaceholderFill()) {
                minimalPlaceholderFill = templateConfig.getMinimalPlaceholderFill();
            }
        }
        if (minimalPlaceholderFill <= 0) {
            return true;
        }
        FaceEntity face = faceRepository.getFace(faceId);
        long count;
        if (scanSource) {
            List<SourceEntity> sourceEntities = sourceMapper.listVideoByScenicFaceRelation(face.getScenicId(), faceId);
            if (sourceEntities == null || sourceEntities.isEmpty()) {
                log.info("faceId:{} has no source", faceId);
                return false;
            }
            count = sourceEntities.stream()
                    .map(SourceEntity::getDeviceId)
                    .filter(Objects::nonNull) // 添加对 null 的检查
                    .distinct()
                    .filter(deviceId -> placeholderList.contains(deviceId.toString()))
                    .count();
        } else {
            List<FaceSampleEntity> faceSampleList = faceRepository.getFaceSampleList(faceId);
            if (faceSampleList == null || faceSampleList.isEmpty()) {
                log.info("faceId:{} has no faceSample", faceId);
                return false;
            }
            count = faceSampleList.stream()
                    .map(FaceSampleEntity::getDeviceId)
                    .filter(Objects::nonNull) // 添加对 null 的检查
                    .distinct()
                    .filter(deviceId -> placeholderList.contains(deviceId.toString()))
                    .count();
        }
        return count >= minimalPlaceholderFill;
    }

    public boolean determineTemplateCanAutoGenerate(Long templateId, Long faceId) {
        return determineTemplateCanAutoGenerate(templateId, faceId, true);
    }

    public boolean determineTemplateCanAutoGenerate(Long templateId, Long faceId, boolean scanSource) {
        List<String> placeholderList = templateRepository.getTemplatePlaceholder(templateId);
        TemplateConfigEntity templateConfig = templateRepository.getTemplateConfig(templateId);
        Integer minimalPlaceholderFill = null;
        if (null != templateConfig) {
            if (null != templateConfig.getAutomaticPlaceholderFill()) {
                minimalPlaceholderFill = templateConfig.getAutomaticPlaceholderFill();
            }
        }
        if (minimalPlaceholderFill == null) {
            // 未开启
            log.info("模板：{}，未配置最小自动生成功能，默认生成！", templateId);
            minimalPlaceholderFill = 1;
        }
        if (minimalPlaceholderFill <= 0) {
            return true;
        }
        FaceEntity face = faceRepository.getFace(faceId);
        List<FaceSampleEntity> faceSampleList = faceRepository.getFaceSampleList(faceId);
        if (faceSampleList.isEmpty()) {
            return false;
        }
        long count;
        if (scanSource) {
            List<SourceEntity> sourceEntities = sourceMapper.listVideoByScenicFaceRelation(face.getScenicId(), faceId);
            count = sourceEntities.stream()
                    .map(SourceEntity::getDeviceId)
                    .filter(Objects::nonNull) // 添加对 null 的检查
                    .distinct()
                    .filter(deviceId -> placeholderList.contains(deviceId.toString()))
                    .count();
        } else {
            count = faceSampleList.stream()
                    .map(FaceSampleEntity::getDeviceId)
                    .distinct()
                    .filter(deviceId -> placeholderList.contains(deviceId.toString()))
                    .count();
        }
        return count >= minimalPlaceholderFill;
    }

    public Map<String, List<SourceEntity>> filterTaskParams(Long templateId, Map<String, List<SourceEntity>> allTaskParams) {
        if (allTaskParams == null || allTaskParams.isEmpty()) {
            return Map.of();
        }

        List<String> templatePlaceholders = templateRepository.getTemplatePlaceholder(templateId);
        if (templatePlaceholders == null || templatePlaceholders.isEmpty()) {
            log.info("filterTaskParams: templateId:{} has no placeholders", templateId);
            return Map.of();
        }
        TemplateConfigEntity templateConfig = templateRepository.getTemplateConfig(templateId);

        // 统计每个 placeholder 在模板中出现的次数
        Map<String, Long> placeholderCounts = templatePlaceholders.stream()
                .collect(Collectors.groupingBy(
                        placeholder -> placeholder,
                        Collectors.counting()
                ));

        Map<String, List<SourceEntity>> filteredParams = new HashMap<>();

        // 判断是否允许片段重复
        boolean allowDuplicate = templateConfig != null && Integer.valueOf(1).equals(templateConfig.getDuplicateEnable());

        for (Map.Entry<String, Long> entry : placeholderCounts.entrySet()) {
            String placeholder = entry.getKey();
            Long requiredCount = entry.getValue();

            if (placeholder.startsWith("P")) {
                // 图片源：占位符格式为 "P{deviceId}"
                String imageKey = placeholder;
                if (allTaskParams.containsKey(imageKey)) {
                    List<SourceEntity> allSources = allTaskParams.get(imageKey);
                    List<SourceEntity> selectedSources = selectSources(allSources, requiredCount.intValue(), allowDuplicate);
                    if (!selectedSources.isEmpty()) {
                        filteredParams.put(imageKey, selectedSources);
                    }
                }
            } else {
                // 视频源：占位符直接对应设备ID
                String videoKey = placeholder;
                if (allTaskParams.containsKey(videoKey)) {
                    List<SourceEntity> allSources = allTaskParams.get(videoKey);
                    List<SourceEntity> selectedSources = selectSources(allSources, requiredCount.intValue(), allowDuplicate);
                    if (!selectedSources.isEmpty()) {
                        filteredParams.put(videoKey, selectedSources);
                    }
                }
            }
        }

        log.debug("filterTaskParams: templateId:{}, original keys:{}, filtered keys:{}, placeholder counts:{}, allowDuplicate:{}",
                templateId, allTaskParams.keySet().size(), filteredParams.keySet().size(), placeholderCounts, allowDuplicate);
        
        return filteredParams;
    }

    private List<SourceEntity> selectSources(List<SourceEntity> allSources, int requiredCount, boolean allowDuplicate) {
        if (allSources == null || allSources.isEmpty()) {
            return new ArrayList<>();
        }

        if (!allowDuplicate) {
            // 不允许重复，使用原有逻辑
            int actualCount = Math.min(requiredCount, allSources.size());
            return new ArrayList<>(allSources.subList(0, actualCount));
        }

        // 允许重复，循环填充到所需数量
        List<SourceEntity> selectedSources = new ArrayList<>();
        int sourceIndex = 0;
        
        for (int i = 0; i < requiredCount; i++) {
            selectedSources.add(allSources.get(sourceIndex));
            sourceIndex = (sourceIndex + 1) % allSources.size();
        }
        
        return selectedSources;
    }

    public Long findFirstAvailableTemplate(List<Long> templateIds, Long faceId, boolean scanSource) {
        if (templateIds == null || templateIds.isEmpty() || faceId == null) {
            return null;
        }
        
        for (Long templateId : templateIds) {
            if (determineTemplateCanGenerate(templateId, faceId, scanSource)) {
                return templateId;
            }
        }
        
        return null;
    }
}