package com.sw.mes.yb.accessory.service.impl;


import com.sw.mes.base.system.entity.DictionaryItem;
import com.sw.mes.core.base.BaseServiceImpl;
import com.sw.mes.base.system.service.DictionaryItemService;
import com.sw.mes.core.utils.DateUtil;
import com.sw.mes.enumvalue.EnumValuesEap;
import com.sw.mes.base.factory.init.entity.Equipment;
import com.sw.mes.base.factory.init.service.EquipmentService;
import com.sw.mes.outside.dto.SendEapSignalDto;
import com.sw.mes.yb.accessory.dao.EquipmentDeviceStatusDao;
import com.sw.mes.yb.accessory.entity.AccessoryMaterial;
import com.sw.mes.yb.accessory.entity.EquipmentAccessory;
import com.sw.mes.yb.accessory.entity.EquipmentDeviceStatus;
import com.sw.mes.yb.accessory.service.EquipmentAccessoryService;
import com.sw.mes.yb.accessory.service.EquipmentDeviceStatusService;
import com.sw.mes.yb.accessory.vo.EapToMesDeviceStatusVo;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Propagation;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.transaction.interceptor.TransactionAspectSupport;

import java.text.DecimalFormat;
import java.util.Date;
import java.util.List;


/**
* @Author
* @Description：
* @Date: Create in
* @Modified By:
*/
@Service
@Transactional
@Slf4j
public class EquipmentDeviceStatusServiceImpl extends BaseServiceImpl<EquipmentDeviceStatus> implements EquipmentDeviceStatusService {
    EquipmentDeviceStatusDao dao;
	@Autowired
    public void setDao(EquipmentDeviceStatusDao dao) {
        super.setBaseDao(dao);
        this.dao=dao;
    }

    @Autowired
    private EquipmentService equipmentService;

	@Autowired
    private EquipmentAccessoryService equipmentAccessoryService;

	@Autowired
    private DictionaryItemService dictionaryItemService;

    @Override
    public void createDeviceStatus(EapToMesDeviceStatusVo dto) {
        Equipment equipment = equipmentService.findByCode(dto.getDeviceCode());
        if (equipment == null){
            throw new RuntimeException("该设备不存在");
        }
        EquipmentDeviceStatus status = findByDeviceNo(dto.getDeviceCode());
        Date date = null;
        if (dto.getStartTime() == null){
            date = new Date();
        }else {
            date = dto.getStartTime();
        }

        if ("VacuumPumping".equals(dto.getTaskCode())){  //toDo 抽真空=1
            if (status == null){
                status = new EquipmentDeviceStatus();
                status.setDeviceNo(dto.getDeviceCode()); //设备编号
                status.setEquipment(equipment);
                status.setStartTime(date); //开启时间
                status.setStatus(1);  //状态
                saveOrUpdate(status);
            }else {
                if (status.getStatus() == 1){  /**如果当前状态也为抽真空*/
                    //不做处理
                }else {
                    status.setStartTime(date); //开启时间
                    status.setStatus(1);  //状态
                    saveOrUpdate(status);
                }
            }

        }else if ("ShutdownFurnace".equals(dto.getTaskCode())){ //toDo 停炉=2
            if (status == null){
                status = new EquipmentDeviceStatus();
                status.setDeviceNo(dto.getDeviceCode()); //设备编号
                status.setEquipment(equipment);
                status.setEndTime(date); //结束时间
                status.setStatus(2);  //状态
                saveOrUpdate(status);
            }else {
                if (status.getStatus() == 2){  /**如果当前状态也为停炉*/
                    //不做处理
                }else {
                    status.setEndTime(date); //结束时间
                    status.setStatus(2);  //状态
                    saveOrUpdate(status);

                    calculateUseTime(status.getDeviceNo(), status); /**计算使用时间*/
                }
            }
        }else {
            throw new RuntimeException("设备修改信号不正确！");
        }

    }

    /**
     * 热场寿命记录
     * @param dto
     */
    @Override
    @Transactional(propagation = Propagation.REQUIRES_NEW)
    public void accessoryLifeRecord(SendEapSignalDto dto) {
        try{
            Equipment equipment = equipmentService.findByCode(dto.getEquipmentCode());
            if (equipment == null){
                throw new RuntimeException("该设备不存在");
            }
            EquipmentDeviceStatus status = findByDeviceNo(dto.getEquipmentCode());
            Date date = new Date();

            if (EnumValuesEap.EapSignalType.抽真空.getKey() == dto.getSignal()){
                if (status == null){
                    status = new EquipmentDeviceStatus();
                    status.setDeviceNo(dto.getEquipmentCode()); //设备编号
                    status.setEquipment(equipment);
                    status.setStartTime(date); //开启时间
                    status.setStatus(1);  //状态  //toDo 抽真空=1
                    saveOrUpdate(status);
                }else {
                    if (status.getStatus() == 1){  /**如果当前状态也为抽真空*/
                        //不做处理
                    }else {
                        status.setStartTime(date); //开启时间
                        status.setStatus(1);  //状态
                        saveOrUpdate(status);
                    }
                }

            }else if (EnumValuesEap.EapSignalType.停炉.getKey() == dto.getSignal()){
                if (status == null){
                    status = new EquipmentDeviceStatus();
                    status.setDeviceNo(dto.getEquipmentCode()); //设备编号
                    status.setEquipment(equipment);
                    status.setEndTime(date); //结束时间
                    status.setStatus(2);  //状态  //toDo 停炉=2
                    saveOrUpdate(status);
                }else {
                    if (status.getStatus() == 2){  /**如果当前状态也为停炉*/
                        //不做处理
                    }else {
                        status.setEndTime(date); //结束时间
                        status.setStatus(2);  //状态
                        saveOrUpdate(status);

                        calculateUseTime(status.getDeviceNo(), status); /**计算使用时间*/
                    }
                }
            }else {
                throw new RuntimeException("设备修改信号不正确！");
            }
        }catch (Exception e){
            TransactionAspectSupport.currentTransactionStatus().setRollbackOnly();
            e.printStackTrace();
            log.error("热场寿命记录", e);
        }
    }

    /**
     * 停炉后计算使用时间并累加上寿命监控已使用时间
     * @param deviceNo
     * @param status
     */
    private void calculateUseTime(String deviceNo, EquipmentDeviceStatus status){
        List<EquipmentAccessory> list = equipmentAccessoryService.findByDeviceCode(deviceNo);
        if (list != null && list.size() > 0 ){
            for (EquipmentAccessory accessory : list) {
                Double useTime = accessory.getUseTime();
                AccessoryMaterial material = accessory.getMaterial();
                Double coldDown = 0d;
                if (material != null){
                    String norms = material.getSpecification(); //获取规格
                    DictionaryItem item = dictionaryItemService.findByThemeValueAndValueAndEnable("SubMaterialSize", norms, true);
                    //停炉后需要冷却,从数据字典根据辅料规格获取相应冷却时间
                    if (item != null){
                        String extendValue = item.getExtendValue();
                        if (extendValue != null){
                            coldDown = Double.valueOf(extendValue);
                        }
                    }
                }
                Double second = DateUtil.secondsBetween(status.getStartTime(), status.getEndTime()); //相差的秒数
                Double hour = second/60d/60d;  //计算抽真空-停炉的小时数，保留两位小数 时间差
                DecimalFormat decimalFormat = new DecimalFormat("#.##");
                Double timeDiff = Double.valueOf(decimalFormat.format(hour));

                Double newUseTime = useTime + coldDown + timeDiff;
                accessory.setUseTime(newUseTime);
                equipmentAccessoryService.saveOrUpdate(accessory);
            }
        }
    }

    public EquipmentDeviceStatus findByDeviceNo(String deviceNo) {
        List<EquipmentDeviceStatus> list = dao.findByDeviceNo(deviceNo);
        if (list != null && list.size() > 0 ){
            return list.get(0);
        }
        return null;
    }
}
