//异步处理报警逻辑(汉王数据接入使用) public async void AsyncHandleAlarmPolicies1(string deviceId, string air, string curValue, DateTime now) { RetDeviceInfo deviceInfo = new RetDeviceInfo(); RetDeviceItemInfo itemInfo = new RetDeviceItemInfo(); using (MonitoringEntities device = new MonitoringEntities()) { try { var searchDevice = device.D_Devices.Where(s => s.DeviceLabel == deviceId).FirstOrDefault(); if (searchDevice != null) { deviceInfo.ID = searchDevice.ID; deviceInfo.Name = searchDevice.Name; deviceInfo.DeviceLabel = searchDevice.DeviceLabel; var searchDeviceItem = device.D_DevicesItem.Where(s => s.DeviceID == searchDevice.ID && s.PropertyLabel == air).FirstOrDefault(); if (searchDeviceItem != null) { itemInfo.ID = searchDeviceItem.ID; itemInfo.Name = itemInfo.Name; itemInfo.PropertyLabel = itemInfo.PropertyLabel; } } } catch (Exception e) { log.ErrorFormat("内部错误:{0},{1}", e.Message, e.StackTrace); } var result = await HandleAlarmPolicies1(deviceInfo, itemInfo, curValue, now); } }
/// <summary> /// 处理报警逻辑(汉王数据接入使用) /// 1.是否命中报警策略 /// 2.记录流水 /// 3.发送消息 /// </summary> /// <param name="deviceInfo"></param> /// <param name="itemInfo"></param> /// <param name="curValue"></param> /// <param name="now"></param> /// <returns></returns> private Task <int> HandleAlarmPolicies1(RetDeviceInfo deviceInfo, RetDeviceItemInfo itemInfo, string curValue, DateTime now) { int result = -1; using (AlertPoliciesEntities alert = new AlertPoliciesEntities()) { var alertInfo = alert.A_AlarmStrategy.Where(s => (s.DeviceID == deviceInfo.ID) && (s.DeviceItemId == itemInfo.ID) && (s.Active == true)).FirstOrDefault(); if (null != alertInfo) { if (isHitPolicies(curValue, alertInfo.Compare, alertInfo.Threshold)) { log.InfoFormat("[MQTT]Hit Policies,topic:{0}/{1},curValue:{2},compare:{3},theshold:{4}.", deviceInfo.DeviceLabel, itemInfo.PropertyLabel, curValue, alertInfo.Compare, alertInfo.Threshold); HistoryAlertPoliciesBLL historyBLL = new HistoryAlertPoliciesBLL(); HistoryAlertPoliciesModel model = new HistoryAlertPoliciesModel() { DeviceID = deviceInfo.ID.ToString(), DeviceItemID = itemInfo.ID.ToString(), StrategyID = alertInfo.ID.ToString(), Value = curValue, AlarmTime = now, EndTime = now.AddSeconds(1), OrgID = alertInfo.OrgID.ToString(), }; historyBLL.AddHistoryAlertPolicies(model); // 发送消息通知 UserApi api = new UserApi(); GetMessageInfoParameter messageModel = new GetMessageInfoParameter() { Type = "2", // 报警预警 Tittle = "【设备报警通知】" + deviceInfo.Name + itemInfo.Name + "报警!", Text = "<p>您好:</p><p class='ql-indent-1'>" + deviceInfo.Name + "(设备)" + itemInfo.Name + "(属性)当前数值为" + curValue + ",已触发预设报警策略,请及时处理异常!</p><p><br></p><p class='ql-align-right'>设备在线监测平台</p>", OrgID = alertInfo.OrgID.ToString() }; var userApi = api.AddAlarmMessage(messageModel); if (userApi.Code != 0) { log.ErrorFormat(userApi.Data); } } } } return(new Task <int>(() => result)); }
/// <summary> /// 将实时数据记录到TSDB /// </summary> /// <param name="deviceInfo"></param> /// <param name="itemInfo"></param> private void RecordToTsdb(RetDeviceInfo deviceInfo, RetDeviceItemInfo itemInfo, string curValue, DateTime now) { decimal value; try { value = Convert.ToDecimal(curValue); // 如果不能转成数字,则不存储到TSDB中。 } catch (Exception e) { log.ErrorFormat("内部错误:{0},{1}", e.Message, e.StackTrace); return; } DeviceMonitoringApi deviceApi = new DeviceMonitoringApi(); IoTHubConfigurationModel parameter = new IoTHubConfigurationModel(); parameter.ID = long.Parse(deviceInfo.DataConnectID); var retDataConnect = deviceApi.GetDataConnect(parameter); if (retDataConnect.Code == -1) { log.Error("获取数据连接数据出错,ID:" + deviceInfo.DataConnectID); return; } RetDataConnectConfiguration dataConnect = retDataConnect.Data; Dictionary <string, string> tagMap = new Dictionary <string, string>(); foreach (var tag in deviceInfo.TagList) { tagMap.Add(tag.Key, tag.Value); } try { OpentsdbClient client = new OpentsdbClient("http://" + dataConnect.ServerAddress + ":" + dataConnect.ServerPort); client.putData(itemInfo.PropertyLabel, now, value, tagMap); } catch (Exception) { return; } }
/// <summary> /// 通用的监听方法 /// 工作内容: /// 1.根据Topic获取设备及属性实例。Topic规则:DeviceLabel/PropertyLabel /// 2.查询是否命中报警策略,如果有则记录报警信息 /// 3.将实时数据保存到默认的TSDB数据库中 /// </summary> /// <param name="sender"></param> /// <param name="e"></param> private void MqttService_OnMqttMessageNotify(object sender, MqttMessageNotifyEventArgs e) { log.InfoFormat("[MQTT]收到消息:客户端:{0},主题:{1},消息:{2},Qos:{3},保留:{4}", e.ClientId, e.MqttApplicationMessage.Topic, Encoding.UTF8.GetString(e.MqttApplicationMessage.Payload), e.MqttApplicationMessage.QualityOfServiceLevel, e.MqttApplicationMessage.Retain); string[] topicArry = e.MqttApplicationMessage.Topic.Split('/'); if (topicArry.Length == 2) { string deviceLabel = topicArry[0]; string propertyLabel = topicArry[1]; DateTime now = DateTime.Now; DeviceMonitoringApi deviceMonitoringApi = new DeviceMonitoringApi(); GetDeviceInfoParameter par = new GetDeviceInfoParameter(); RetDeviceInfo deviceInfo = null; RetDeviceItemInfo itemInfo = null; par.DeviceLabel = deviceLabel; var resDeviceInfo = deviceMonitoringApi.GetDeviceInfo(par); if (resDeviceInfo.Code != -1) { deviceInfo = resDeviceInfo.Data; itemInfo = deviceInfo.DeviceItems.Find(s => s.PropertyLabel == propertyLabel); if (null == itemInfo) { log.ErrorFormat("根据Topic获取设备属性信息出错,无法匹配报警策略,deviceLabel{0},propertyLabel{1}", deviceLabel, propertyLabel); return; } } else { log.Error("根据deviceLabel获取设备信息失败" + resDeviceInfo.Msg); return; } //异步处理报警逻辑 AsyncHandleAlarmPolicies(deviceInfo, itemInfo, Encoding.UTF8.GetString(e.MqttApplicationMessage.Payload), now); //保存到TSDB RecordToTsdb(deviceInfo, itemInfo, Encoding.UTF8.GetString(e.MqttApplicationMessage.Payload), now); } else { log.ErrorFormat("解析TOPIC:{0} 失败,不符合规则", e.MqttApplicationMessage.Topic); } }
/// <summary> /// 物接入(研华网关方式) /// </summary> /// <param name="sender"></param> /// <param name="e"></param> private void MqttService_OnYanhuaMessageNotify(object sender, MqttMessageNotifyEventArgs e) { try { log.InfoFormat("[MQTT]收到消息:客户端:{0},主题:{1},消息:{2},Qos:{3},保留:{4}", e.ClientId, e.MqttApplicationMessage.Topic, Encoding.UTF8.GetString(e.MqttApplicationMessage.Payload), e.MqttApplicationMessage.QualityOfServiceLevel, e.MqttApplicationMessage.Retain); string[] topicArry = e.MqttApplicationMessage.Topic.Split('/'); string orgId = topicArry[0]; //组织ID //报文转换为对象 YanHuaPayload yanhuaPayload; try { yanhuaPayload = JsonHelper.JsonToEntity <YanHuaPayload>(Encoding.UTF8.GetString(e.MqttApplicationMessage.Payload)); } catch (Exception ex) { // 转换对象失败,报文格式不对,直接放弃 log.ErrorFormat("[MQTT]解析报文格式失败:{0},{1}", ex.Message, ex.StackTrace); return; } foreach (var payVal in yanhuaPayload.values) { try { DateTime uploadtime = DateTime.ParseExact(payVal.time, "yyyyMMdd-HH:mm:ss", CultureInfo.InvariantCulture); DeviceMonitoringApi deviceMonitoringApi = new DeviceMonitoringApi(); GetDeviceInfoParameter par = new GetDeviceInfoParameter(); RetDeviceInfo deviceInfo = null; RetDeviceItemInfo itemInfo = null; par.OrgID = orgId; par.Phone = payVal.device_ip; var resDeviceInfo = deviceMonitoringApi.GetDeviceInfo(par); if (resDeviceInfo.Code != -1) { deviceInfo = resDeviceInfo.Data; itemInfo = deviceInfo.DeviceItems.Find(s => s.Name == payVal.operationValue); if (null == itemInfo) { log.ErrorFormat("根据Topic获取设备属性信息出错,device_ip{0},name{1}", payVal.device_ip, payVal.name); continue; } } else { log.Error("根据deviceLabel获取设备信息失败" + resDeviceInfo.Msg); continue; } //处理报警逻辑 AsyncHandleAlarmPolicies(deviceInfo, itemInfo, payVal.data, uploadtime); //保存到TSDB RecordToTsdb(deviceInfo, itemInfo, payVal.data, uploadtime); } catch (Exception ex) { log.ErrorFormat("内部错误:{0},{1}", ex.Message, ex.StackTrace); continue; } } } catch (Exception ex) { log.ErrorFormat("内部错误:{0},{1}", ex.Message, ex.StackTrace); return; } }
private async void AsyncHandleAlarmPolicies(RetDeviceInfo deviceInfo, RetDeviceItemInfo itemInfo, string curValue, DateTime now) { var result = await HandleAlarmPolicies(deviceInfo, itemInfo, curValue, now); }