package com.skr.mdm.observer.global;

import cn.hutool.core.collection.ListUtil;
import cn.hutool.json.JSONUtil;
import com.baomidou.mybatisplus.extension.conditions.query.LambdaQueryChainWrapper;
import com.skr.mdm.bean.so.content.ContentDocumentSO;
import com.skr.mdm.dao.ContentDocumentDao;
import com.skr.mdm.dao.ContentDocumentUserDao;
import com.skr.mdm.entity.ContentDocumentDO;
import com.skr.mdm.entity.ContentDocumentUserDO;
import com.skr.mdm.enums.IssuedTypeEnum;
import com.skr.mdm.enums.SendCmdConfigEnum;
import com.skr.mdm.enums.StrategyEquipmentStateEnum;
import com.skr.mdm.event.UserActiveEvent;
import com.skr.mdm.handle.IssuedUserHandler;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.collections4.CollectionUtils;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.ApplicationListener;
import org.springframework.stereotype.Component;

import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import java.util.stream.Collectors;

/**
 * 用户设备激活全局文档下发
 *
 * @author nfq
 * @date 2022/06/09 9:50
 */
@Component
@Slf4j
public class GlobalDocumentObserver implements ApplicationListener<UserActiveEvent> {

    @Autowired
    private ContentDocumentDao contentDocumentDao;
    @Autowired
    private ContentDocumentUserDao contentDocumentUserDao;
    @Autowired
    private IssuedUserHandler issuedUserHandler;

    @Override
    public void onApplicationEvent(UserActiveEvent event) {
        try {
            // 获取有效时间未过期的全局文档
            List<ContentDocumentDO> contentDocumentDOList = new LambdaQueryChainWrapper<>(contentDocumentDao)
                    .ne(ContentDocumentDO::getGlobalType, IssuedTypeEnum.DEVICE.getIssuedType())
                    .eq(ContentDocumentDO::getCompanyId, event.getCompanyId())
                    .and(wrapper -> wrapper.isNull(ContentDocumentDO::getValidTime)
                            .or()
                            .le(ContentDocumentDO::getValidTime, new Date()))
                    .list();
            if (CollectionUtils.isNotEmpty(contentDocumentDOList)) {
                // 筛选非当前设备所在部门的部门全局策略
                List<ContentDocumentDO> contentDocumentDOS = contentDocumentDOList.stream()
                        .filter(contentDocumentDO ->
                                IssuedTypeEnum.DEPT_GLOBAL.getIssuedType().equals(contentDocumentDO.getGlobalType()) &&
                                        !JSONUtil.toList(JSONUtil.parseArray(contentDocumentDO.getDepartmentIds()), Integer.class)
                                                .contains(event.getDepartmentId()))
                        .collect(Collectors.toList());
                // 排除筛选出的部门策略
                if (CollectionUtils.isNotEmpty(contentDocumentDOS)) {
                    contentDocumentDOList.removeAll(contentDocumentDOS);
                }
                if (CollectionUtils.isEmpty(contentDocumentDOList)) {
                    return;
                }
                // 查重
                List<Integer> existStrategyIdList = new LambdaQueryChainWrapper<>(contentDocumentUserDao)
                        .eq(ContentDocumentUserDO::getEquipmentId, event.getEquipmentId())
                        .list()
                        .stream().map(ContentDocumentUserDO::getFileId)
                        .collect(Collectors.toList());
                if (CollectionUtils.isNotEmpty(existStrategyIdList)) {
                    contentDocumentDOList = contentDocumentDOList.stream().filter(contentDocumentDO ->
                                    !existStrategyIdList.contains(contentDocumentDO.getId()))
                            .collect(Collectors.toList());
                    if (CollectionUtils.isEmpty(contentDocumentDOList)) {
                        return;
                    }
                }
                // 保存并下发
                List<ContentDocumentSO> contentDocumentSOList = new ArrayList<>(contentDocumentDOList.size());
                for (ContentDocumentDO contentDocumentDO : contentDocumentDOList) {
                    ContentDocumentUserDO contentDocumentUserDO = ContentDocumentUserDO.builder()
                            .equipmentId(event.getEquipmentId())
                            .fileId(contentDocumentDO.getId())
                            .state(StrategyEquipmentStateEnum.ISSUING.getState())
                            .issuedTime(new Date())
                            .build();
                    BeanUtils.copyProperties(contentDocumentDO, contentDocumentUserDO);
                    contentDocumentUserDO.setId(null);
                    contentDocumentUserDao.insert(contentDocumentUserDO);
                    // 未到推送时间不下发
                    if (contentDocumentDO.getSendPushTime() != null && contentDocumentDO.getSendPushTime().after(new Date())) {
                        continue;
                    }
                    // 下发数据
                    ContentDocumentSO contentDocumentSO = new ContentDocumentSO();
                    BeanUtils.copyProperties(contentDocumentDO, contentDocumentSO);
                    contentDocumentSO.setSendTime(new Date());
                    contentDocumentSO.setFileUrl(contentDocumentDO.getFileUrl());
                    contentDocumentSOList.add(contentDocumentSO);
                }
                if (CollectionUtils.isNotEmpty(contentDocumentSOList)) {
                    issuedUserHandler.issuedUser(ListUtil.toList(event.getEquipmentId()), event.getCompanyId(),
                            SendCmdConfigEnum.CONTENT_SILENT_INSTALLATION.getCmd(), JSONUtil.toJsonStr(contentDocumentSOList));
                }
            }
        } catch (Exception e) {
            log.error("设备激活全局文档下发异常：" + event.getEquipmentId(), e);
        }
    }

}