package com.ruoyi.base.service.impl;

import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;
import com.ruoyi.common.utils.DateUtils;
import com.ruoyi.common.event.PlayPlanChangedEvent;
import com.ruoyi.common.event.PlayPlanDisabledEvent;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.ApplicationEventPublisher;
import org.springframework.stereotype.Service;
import com.ruoyi.common.utils.StringUtils;
import org.springframework.transaction.annotation.Transactional;
import com.ruoyi.base.domain.RobotOpsPlayPlanItem;
import com.ruoyi.base.mapper.RobotOpsPlayPlanMapper;
import com.ruoyi.base.domain.RobotOpsPlayPlan;
import com.ruoyi.base.service.IRobotOpsPlayPlanService;

/**
 * 播放方案Service业务层处理
 *
 * @author ruoyi
 * @date 2026-05-11
 */
@Service
public class RobotOpsPlayPlanServiceImpl implements IRobotOpsPlayPlanService
{
    @Autowired
    private RobotOpsPlayPlanMapper robotOpsPlayPlanMapper;

    /** 事件发布器 */
    @Autowired
    private ApplicationEventPublisher eventPublisher;

    private static final Logger log = LoggerFactory.getLogger(RobotOpsPlayPlanServiceImpl.class);

    /**
     * 查询播放方案
     *
     * @param id 播放方案主键
     * @return 播放方案
     */
    @Override
    public RobotOpsPlayPlan selectRobotOpsPlayPlanById(Long id)
    {
        return robotOpsPlayPlanMapper.selectRobotOpsPlayPlanById(id);
    }

    /**
     * 查询播放方案列表
     *
     * @param robotOpsPlayPlan 播放方案
     * @return 播放方案
     */
    @Override
    public List<RobotOpsPlayPlan> selectRobotOpsPlayPlanList(RobotOpsPlayPlan robotOpsPlayPlan)
    {
        return robotOpsPlayPlanMapper.selectRobotOpsPlayPlanList(robotOpsPlayPlan);
    }

    /**
     * 新增播放方案
     *
     * @param robotOpsPlayPlan 播放方案
     * @return 结果
     */
    @Transactional(rollbackFor = Exception.class)
    @Override
    public int insertRobotOpsPlayPlan(RobotOpsPlayPlan robotOpsPlayPlan)
    {
        robotOpsPlayPlan.setCreateTime(DateUtils.getNowDate());
        Long previousPlanId = null;
        if ("1".equals(robotOpsPlayPlan.getStatus()))
        {
            RobotOpsPlayPlan currentPlayingPlan = robotOpsPlayPlanMapper.selectCurrentPlayingPlan();
            if (currentPlayingPlan != null)
            {
                previousPlanId = currentPlayingPlan.getId();
                robotOpsPlayPlanMapper.updatePlayPlanStatus(currentPlayingPlan.getId(), "0");
            }
        }
        int rows = robotOpsPlayPlanMapper.insertRobotOpsPlayPlan(robotOpsPlayPlan);
        insertRobotOpsPlayPlanItem(robotOpsPlayPlan);

        // 如果是新方案启用为当前播放，发布播放方案变化事件
        if ("1".equals(robotOpsPlayPlan.getStatus()) && eventPublisher != null)
        {
            // 如果之前有播放中的方案被停用，先发布禁用事件
            if (previousPlanId != null && !previousPlanId.equals(robotOpsPlayPlan.getId()))
            {
                eventPublisher.publishEvent(new PlayPlanDisabledEvent(this, previousPlanId));
            }
            // 发布新方案变化事件
            publishPlayPlanChangedEvent();
        }
        return rows;
    }

    /**
     * 修改播放方案
     *
     * @param robotOpsPlayPlan 播放方案
     * @return 结果
     */
    @Transactional(rollbackFor = Exception.class)
    @Override
    public int updateRobotOpsPlayPlan(RobotOpsPlayPlan robotOpsPlayPlan)
    {
        robotOpsPlayPlan.setUpdateTime(DateUtils.getNowDate());

        Long previousPlanId = null;
        boolean wasEnabled = false;
        // 检查当前方案是否正在播放
        RobotOpsPlayPlan currentPlayingPlan = robotOpsPlayPlanMapper.selectCurrentPlayingPlan();
        boolean isCurrentPlayingPlan = currentPlayingPlan != null
            && currentPlayingPlan.getId().equals(robotOpsPlayPlan.getId());

        if ("1".equals(robotOpsPlayPlan.getStatus()))
        {
            if (currentPlayingPlan != null && !currentPlayingPlan.getId().equals(robotOpsPlayPlan.getId()))
            {
                previousPlanId = currentPlayingPlan.getId();
                robotOpsPlayPlanMapper.updatePlayPlanStatus(currentPlayingPlan.getId(), "0");
                wasEnabled = true;
            }
        }
        else if (isCurrentPlayingPlan && currentPlayingPlan != null && "1".equals(currentPlayingPlan.getStatus()))
        {
            // 当前正在播放的方案被停用
            wasEnabled = true;
        }

        robotOpsPlayPlanMapper.deleteRobotOpsPlayPlanItemByPlanId(robotOpsPlayPlan.getId());
        insertRobotOpsPlayPlanItem(robotOpsPlayPlan);
        int result = robotOpsPlayPlanMapper.updateRobotOpsPlayPlan(robotOpsPlayPlan);

        // 如果状态变为启用，发布播放方案变化事件
        if (eventPublisher != null)
        {
            if ("1".equals(robotOpsPlayPlan.getStatus()))
            {
                // 如果之前有播放中的方案被停用，先发布禁用事件
                if (previousPlanId != null)
                {
                    eventPublisher.publishEvent(new PlayPlanDisabledEvent(this, previousPlanId));
                }
                // 发布新方案变化事件
                publishPlayPlanChangedEvent();
            }
            else if (wasEnabled)
            {
                // 方案从启用变为停用，发布禁用事件
                eventPublisher.publishEvent(new PlayPlanDisabledEvent(this, robotOpsPlayPlan.getId()));
            }
        }
        return result;
    }


    /**
     * 批量删除播放方案
     *
     * @param ids 需要删除的播放方案主键
     * @return 结果
     */
    @Transactional(rollbackFor = Exception.class)
    @Override
    public int deleteRobotOpsPlayPlanByIds(Long[] ids)
    {
        if (ids == null || ids.length == 0) {
            return 0;
        }

        // 检查是否有正在播放的方案被删除
        if (eventPublisher != null) {
            RobotOpsPlayPlan currentPlan = robotOpsPlayPlanMapper.selectCurrentPlayingPlan();
            if (currentPlan != null) {
                for (Long id : ids) {
                    if (id.equals(currentPlan.getId())) {
                        // 当前播放中的方案被删除，发布禁用事件
                        eventPublisher.publishEvent(new PlayPlanDisabledEvent(this, id));
                        break;
                    }
                }
            }
        }

        robotOpsPlayPlanMapper.deleteRobotOpsPlayPlanItemByPlanIds(ids);
        return robotOpsPlayPlanMapper.deleteRobotOpsPlayPlanByIds(ids);
    }

    /**
     * 删除播放方案信息
     *
     * @param id 播放方案主键
     * @return 结果
     */
    @Transactional(rollbackFor = Exception.class)
    @Override
    public int deleteRobotOpsPlayPlanById(Long id)
    {
        // 检查被删除的方案是否是当前播放中的方案
        if (eventPublisher != null) {
            RobotOpsPlayPlan currentPlan = robotOpsPlayPlanMapper.selectCurrentPlayingPlan();
            if (currentPlan != null && id.equals(currentPlan.getId())) {
                // 当前播放中的方案被删除，发布禁用事件
                eventPublisher.publishEvent(new PlayPlanDisabledEvent(this, id));
            }
        }

        robotOpsPlayPlanMapper.deleteRobotOpsPlayPlanItemByPlanId(id);
        return robotOpsPlayPlanMapper.deleteRobotOpsPlayPlanById(id);
    }

    /**
     * 查询当前正在播放的方案（包含素材项）
     *
     * @return 播放方案
     */
    @Override
    public RobotOpsPlayPlan selectCurrentPlayingPlanWithItems()
    {
        RobotOpsPlayPlan plan = robotOpsPlayPlanMapper.selectCurrentPlayingPlan();
        if (plan != null) {
            List<RobotOpsPlayPlanItem> items = robotOpsPlayPlanMapper.selectRobotOpsPlayPlanItemListByPlanId(plan.getId());
            plan.setRobotOpsPlayPlanItemList(items);
        }
        return plan;
    }

    /**
     * 新增播放方案素材明细信息
     *
     * @param robotOpsPlayPlan 播放方案对象
     */
    public void insertRobotOpsPlayPlanItem(RobotOpsPlayPlan robotOpsPlayPlan)
    {
        List<RobotOpsPlayPlanItem> robotOpsPlayPlanItemList = robotOpsPlayPlan.getRobotOpsPlayPlanItemList();
        Long id = robotOpsPlayPlan.getId();
        if (StringUtils.isNotNull(robotOpsPlayPlanItemList))
        {
            List<RobotOpsPlayPlanItem> list = new ArrayList<RobotOpsPlayPlanItem>();
            for (RobotOpsPlayPlanItem robotOpsPlayPlanItem : robotOpsPlayPlanItemList)
            {
                robotOpsPlayPlanItem.setPlanId(id);
                list.add(robotOpsPlayPlanItem);
            }
            if (list.size() > 0)
            {
                robotOpsPlayPlanMapper.batchRobotOpsPlayPlanItem(list);
            }
        }
    }

    /**
     * 发布播放方案变化事件
     */
    private void publishPlayPlanChangedEvent()
    {
        if (eventPublisher == null)
        {
            return;
        }
        try
        {
            RobotOpsPlayPlan plan = selectCurrentPlayingPlanWithItems();
            if (plan == null)
            {
                return;
            }

            Map<String, Object> result = new HashMap<>();
            result.put("enabled", true);
            result.put("planId", plan.getId());
            result.put("planName", plan.getPlanName());
            result.put("playMode", plan.getLoopMode() != null ? plan.getLoopMode() : "loop");
            result.put("defaultFitMode", "cover");

            // 使用更新时间生成版本号
            String version = "";
            if (plan.getUpdateTime() != null)
            {
                SimpleDateFormat sdf = new SimpleDateFormat("yyyyMMddHHmmss");
                version = sdf.format(plan.getUpdateTime());
            }
            result.put("version", version);

            // 转换素材项
            List<RobotOpsPlayPlanItem> items = plan.getRobotOpsPlayPlanItemList();
            List<Map<String, Object>> convertedItems = new ArrayList<>();
            if (items != null && !items.isEmpty())
            {
                items.stream()
                        .sorted((a, b) -> {
                            Long orderA = a.getPlayOrder() != null ? a.getPlayOrder() : 999L;
                            Long orderB = b.getPlayOrder() != null ? b.getPlayOrder() : 999L;
                            return orderA.compareTo(orderB);
                        })
                        .forEach(item -> {
                            Map<String, Object> itemMap = new HashMap<>();
                            itemMap.put("id", item.getId() != null ? String.valueOf(item.getId()) : "");
                            itemMap.put("type", item.getAssetType() != null ? item.getAssetType() : "image");
                            itemMap.put("title", item.getAssetName() != null ? item.getAssetName() : "");
                            itemMap.put("subtitle", "");
                            itemMap.put("url", item.getFileUrl() != null ? item.getFileUrl() : "");
                            itemMap.put("duration", item.getStaySeconds() != null ? item.getStaySeconds() * 1000 : 8000);
                            itemMap.put("fitMode", "cover");
                            itemMap.put("showTitle", false);
                            convertedItems.add(itemMap);
                        });
            }
            result.put("items", convertedItems);

            eventPublisher.publishEvent(new PlayPlanChangedEvent(this, result));
            log.info("[PlayPlan] 发布播放方案变化事件: {}", plan.getPlanName());
        }
        catch (Exception e)
        {
            log.error("[PlayPlan] 发布播放方案变化事件失败: {}", e.getMessage(), e);
        }
    }
}
