| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188 |
- package com.zksy.manhole.utils;
- import static com.zksy.common.utils.CollectionSideEffects.*;
- import com.alibaba.fastjson.JSONObject;
- import com.zksy.api.utils.AlarmLevelUtil;
- import com.zksy.api.utils.SmsUtil;
- import com.zksy.api.domain.AlarmData;
- import com.zksy.api.service.AlarmDataService;
- import com.zksy.api.service.DeviceContactService;
- import org.slf4j.Logger;
- import org.slf4j.LoggerFactory;
- import org.springframework.beans.factory.annotation.Autowired;
- import org.springframework.beans.factory.annotation.Value;
- import org.springframework.http.HttpEntity;
- import org.springframework.http.HttpHeaders;
- import org.springframework.http.MediaType;
- import org.springframework.stereotype.Component;
- import org.springframework.web.client.RestTemplate;
- import java.math.BigDecimal;
- import java.time.LocalDateTime;
- import java.util.HashMap;
- import java.util.List;
- import java.util.Map;
- @Component
- public class AlarmUtil {
- private static final Logger log = LoggerFactory.getLogger(AlarmUtil.class);
- @Autowired
- private RestTemplate restTemplate;
- @Autowired
- private SmsUtil smsUtil;
- @Autowired
- private DeviceContactService devicePhoneFetchUtil;
- @Autowired
- private AlarmDataService alarmDataService;
- @Value("${device.status.api.url:http://zk-api-service/equipmentStatus/updateAlarmStatus}")
- private String deviceStatusApiUrl;
- public void checkAndSaveAlarm(String deviceCode,
- String warningType, String warningCode, Double minValue, Double maxValue,
- BigDecimal actualValue, String remark) {
- if (actualValue == null) {
- return;
- }
- boolean shouldAlarm = false;
- if (minValue != null && actualValue.doubleValue() <= minValue) {
- shouldAlarm = true;
- }
- if (maxValue != null && actualValue.doubleValue() >= maxValue) {
- shouldAlarm = true;
- }
- if (shouldAlarm) {
- saveAlarm(deviceCode, warningType, warningCode,
- minValue != null ? BigDecimal.valueOf(minValue) : null,
- maxValue != null ? BigDecimal.valueOf(maxValue) : null,
- actualValue, remark);
- }
- }
- public int saveAlarm(String deviceCode,
- String warningType, String warningCode, BigDecimal minValue, BigDecimal maxValue,
- BigDecimal actualValue, String remark) {
- int alarmLevel = 4;
- try {
- AlarmData alarmData = new AlarmData();
- alarmData.setDeviceCode(deviceCode);
-
- alarmData.setWarningCode(warningCode);
- alarmData.setMinValue(minValue);
- alarmData.setMaxValue(maxValue);
- alarmData.setActualValue(actualValue);
- alarmLevel = AlarmLevelUtil.calculateLevel(actualValue, minValue, maxValue);
- BigDecimal deviationRatio = AlarmLevelUtil.calculateDeviationRatio(actualValue, minValue, maxValue);
- alarmData.setAlarmLevel(alarmLevel);
- alarmData.setDeviationRatio(deviationRatio);
- alarmData.setAlarmStatus(0);
- alarmData.setCreateTime(LocalDateTime.now());
- boolean saved = run(deviceCode, warningCode + ":报警入库", () ->
- requireSaved(alarmDataService.saveAlarmData(alarmData)));
- if (alarmLevel == 1) {
- log.warn("【1级紧急告警】deviceCode={}, warningCode={}, deviationRatio={}%",
- deviceCode, warningCode, deviationRatio);
- sendAlarmSms(deviceCode, warningType, actualValue, minValue, maxValue);
- }
- if (saved) log.info("告警数据入库成功: deviceCode={}, warningCode={}, level={}级", deviceCode, warningCode, alarmLevel);
- } catch (Exception e) {
- log.error("保存告警数据失败: deviceCode={}, warningCode={}", deviceCode, warningCode, e);
- }
- return alarmLevel;
- }
- /**
- * 保存告警数据(指定告警等级,适用于状态型告警)
- * @param deviceCode 设备编码
- * @param warningType 告警类型
- * @param warningCode 告警编码
- * @param actualValue 实际值(可为null)
- * @param alarmLevel 告警等级(1-4)
- * @param remark 备注
- * @return 告警等级
- */
- public int saveAlarmWithLevel(String deviceCode,
- String warningType, String warningCode,
- BigDecimal actualValue, int alarmLevel, String remark) {
- try {
- AlarmData alarmData = new AlarmData();
- alarmData.setDeviceCode(deviceCode);
-
- alarmData.setWarningCode(warningCode);
- alarmData.setActualValue(actualValue);
- alarmData.setAlarmLevel(alarmLevel);
- alarmData.setDeviationRatio(BigDecimal.ZERO);
- alarmData.setAlarmStatus(0);
- alarmData.setCreateTime(LocalDateTime.now());
- boolean saved = run(deviceCode, warningCode + ":报警入库", () ->
- requireSaved(alarmDataService.saveAlarmData(alarmData)));
- if (alarmLevel == 1) {
- log.warn("【1级紧急告警】deviceCode={}, warningCode={}", deviceCode, warningCode);
- sendAlarmSms(deviceCode, warningType, actualValue, null, null);
- }
- if (saved) log.info("告警数据入库成功: deviceCode={}, warningCode={}, level={}级", deviceCode, warningCode, alarmLevel);
- } catch (Exception e) {
- log.error("保存告警数据异常: {}", e.getMessage());
- }
- return alarmLevel;
- }
- private void sendAlarmSms(String deviceCode, String warningType, BigDecimal actualValue,
- BigDecimal minValue, BigDecimal maxValue) {
- try {
- List<String> phoneList = devicePhoneFetchUtil.getPhoneListByDeviceCode(deviceCode);
- if (phoneList == null || phoneList.isEmpty()) {
- log.warn("报警短信发送失败:未找到设备{}的联系人手机号", deviceCode);
- return;
- }
- JSONObject params = new JSONObject();
- params.put("deviceNo", deviceCode);
- params.put("alarmType", warningType);
- params.put("location", "当前值:" + actualValue + ",正常范围:" + minValue + "~" + maxValue);
- Map<String, Boolean> result = smsUtil.sendBatchSms(phoneList, params.toJSONString());
- long successCount = result.values().stream().filter(Boolean::booleanValue).count();
- log.info("1级告警短信发送完成,成功{}条,失败{}条", successCount, phoneList.size() - successCount);
- } catch (Exception e) {
- log.error("发送报警短信异常: {}", e.getMessage());
- }
- }
- /**
- * 更新设备报警状态
- * @param deviceCode 设备编码
- * @param alarmStatus 报警状态:0-正常,1-报警
- */
- public void updateDeviceAlarmStatus(String deviceCode, int alarmStatus) {
- try {
- Map<String, Object> params = new HashMap<>();
- params.put("deviceCode", deviceCode);
- params.put("alarmStatus", alarmStatus);
- HttpHeaders headers = new HttpHeaders();
- headers.setContentType(MediaType.APPLICATION_JSON);
- HttpEntity<Map<String, Object>> request = new HttpEntity<>(params, headers);
- Map<?, ?> response = restTemplate.postForObject(deviceStatusApiUrl, request, Map.class);
- if (response == null || !Boolean.TRUE.equals(response.get("success"))) {
- log.warn("设备报警状态更新未成功: deviceCode={}, alarmStatus={}, response={}", deviceCode, alarmStatus, response);
- return;
- }
- log.info("设备报警状态更新成功: deviceCode={}, alarmStatus={}", deviceCode, alarmStatus);
- } catch (Exception e) {
- log.error("更新设备报警状态失败: deviceCode={}, alarmStatus={}", deviceCode, alarmStatus, e);
- }
- }
- }
|