package com.iailab.module.data.ind.collection.handler; import com.iailab.module.data.common.enums.CommonConstant; import com.iailab.module.data.common.enums.JsErrorCode; import com.iailab.module.data.common.utils.JavaScriptHandler; import com.iailab.module.data.ind.service.IndItemService; import com.iailab.module.data.ind.dto.IndItemDTO; import com.iailab.module.data.ind.dto.IndItemValueDTO; import lombok.extern.slf4j.Slf4j; import org.apache.commons.lang3.StringUtils; import javax.annotation.Resource; import org.springframework.stereotype.Component; import java.math.BigDecimal; import java.util.ArrayList; import java.util.HashMap; import java.util.List; import java.util.Map; /** * @author PanZhibao * @Description * @createTime 2024年05月25日 */ @Slf4j @Component public class CalItemHandle { @Resource private JavaScriptHandler javaScriptHandler; public static final String regex = "[+\\-\\*\\/\\(\\)\\&\\|\\>\\<]"; @Resource private IndItemService indItemService; @Resource private AtomItemHandle atomItemHandle; public List getItemCalValue(String itemNo) { List result = new ArrayList<>(); IndItemDTO indItemDTO = indItemService.getItemCal(itemNo); if (indItemDTO == null) { return result; } String expression = indItemDTO.getExpression(); if (StringUtils.isBlank(expression)) { return result; } String[] arr = expression.split(regex); int dataLength = 0; List> valueMix = new ArrayList<>(); for (int i = 0; i < arr.length; i++) { String s = arr[i]; if (StringUtils.isBlank(s)) { continue; } valueMix.add(atomItemHandle.getItemSourceValue(s)); } dataLength = valueMix.get(0).size(); for (int i = 0; i < dataLength; i++) { Map dataMap = new HashMap<>(); for (int j = 0; j < valueMix.size(); j++) { IndItemValueDTO valueDTO = valueMix.get(j).get(i); dataMap.put(valueDTO.getItemNo(), valueDTO); } IndItemValueDTO itemValue = this.singleCompute(indItemDTO, dataMap); result.add(itemValue); } return result; } public List getItemCalValue(String itemNo, String start, String end) { List result = new ArrayList<>(); IndItemDTO indItemDTO = indItemService.getItemCal(itemNo); if (indItemDTO == null) { return result; } String expression = indItemDTO.getExpression(); if (StringUtils.isBlank(expression)) { return result; } String[] arr = expression.split(regex); int dataLength = 0; List> valueMix = new ArrayList<>(); for (int i = 0; i < arr.length; i++) { String s = arr[i]; if (StringUtils.isBlank(s)) { continue; } valueMix.add(atomItemHandle.getItemSourceValue(s, start, end)); } dataLength = valueMix.get(0).size(); for (int i = 0; i < dataLength; i++) { Map dataMap = new HashMap<>(); for (int j = 0; j < valueMix.size(); j++) { IndItemValueDTO valueDTO = valueMix.get(j).get(i); dataMap.put(valueDTO.getItemNo(), valueDTO); } IndItemValueDTO itemValue = this.singleCompute(indItemDTO, dataMap); result.add(itemValue); } return result; } private IndItemValueDTO singleCompute(IndItemDTO dto, Map dataMap) { IndItemValueDTO resultDto = new IndItemValueDTO(); String dataTime = ""; BigDecimal dataValue = CommonConstant.ZERO_VALUE; String expression = dto.getExpression(); String[] arr = expression.split(regex); for (int i = 0; i < arr.length; i++) { String s = arr[i]; if (StringUtils.isNotBlank(s) && dataMap.containsKey(s)) { dataTime = dataMap.get(s).getDataTime(); if (dataMap.get(s) == null || dataMap.get(s).getDataValue() == null) { resultDto.setDataTime(dataTime); return resultDto; } expression = expression.replace(s, dataMap.get(s).getDataValue().toString()); } } expression = expression.replace("&", "&&"); expression = expression.replace("|", "||"); expression = expression.replace("False", "false"); expression = expression.replace("True", "true"); log.info("ItemNo=" + dto.getItemNo() + ";expression=" + expression); String result = javaScriptHandler.eval(expression); log.info("result=" + result); if (result == null) { return null; } else if (result.contains(JsErrorCode.Infinity.name()) || result.contains(JsErrorCode.NaN.name())) { log.info("计算异常,使用默认值"); } else { dataValue = new BigDecimal(result); } resultDto.setDataTime(dataTime); if (dto.getCoefficient() != null) { dataValue = dataValue.multiply(dto.getCoefficient()); } if (dto.getPrecision() != null) { dataValue = dataValue.setScale(dto.getPrecision(), BigDecimal.ROUND_HALF_UP); } resultDto.setDataValue(dataValue); return resultDto; } }