本文章是一个项目系列文章的第九篇,这个系列文章非常详细,真的可以说是手把手拉着你在现场做实际的项目一样。如果你还不了解前面的内容,请参考
这些文章,每一篇都有项目实施中的特殊技术点, 每一篇你都会有不同的收获,建议你按照顺序不要漏过。
前面的文章,我们完成所有的设备安装、连接、调试和软件数据接入工作,并且设计制作了监控画面。现在工作任务列表只剩下短信报警功能了。
1 自动化系统的报警特点
作为一个程序员,经常会碰到基于一些数据,根据一定的逻辑算法判断并产生报警信息。在很多IT软件系统中,简单粗暴的方式是:只要系统触发需要关注的异常,要么直接记录到日志中,或者通过消息通道发送到特定人员(如通过邮件等)。这些异常作为日常运维经常需要专人分析和处理。所以,一般的IT系统报警实现可以说很简单。
但对于自动控制系统(或物联网系统),日常用户不是我们程序员。他们不允许系统疯狂地给他推送消息。另外,一些特殊的异常报警,必须获得及时处理,否则后果会很严重——比如,UPS非市电On line报警,那必须迅速做出响应。而一些报警日常却可以忽略,只需要知道就行了。
因此,基于现场这些传感器或控制器产生的数据,要实现报警功能,需要仔细斟酌。一些硬件设备可能还存在一些内在的不完善,也可能影响到报警实现。此时我们就需要使用软件支持的能力来规避。本次项目,我就遇到了这样的坑。因为这个坑很典型,所以我也分享给你。
2 IOT-Tree Server对报警的支持
在介入报警实现细节前,必须对IOT-Tree这个软件的报警功能做个介绍,否则后面看着可能会让你晕乎。
IOT-Tree的报警分3个层级:
1,数据标签内定义报警源——数据标签在运行过程中,可以设定触发报警源数据,但如果没有后续处理,则不会起作用,你只能在管理界面中看到有报警源数据。
2,报警处理(Handler)——你可以定义1个或多个报警Handler,然后关联数据标签报警源,只有关联了Handler的报警源,才会起作用。
3,报警输出——对于每个报警Handler,你可以定义1个或多个报警输出(如短信输出或邮件输出等)。
通过这3个层级的报警管理,你可以非常灵活多变的实现自己的报警需要,同时又很直观明了。
3 本项目需要的报警内容
1 本项目首先需要对UPS状态变化做报警——正常是online状态,只要出现非online状态就触发报警,当恢复online时,报警解除。
2 对于漏水传感器,监测到漏水异常,则触发报警,恢复后报警解除。
3 机房空调远端温度报警,当温度高于一定的值产生报警
4 所有的报警都需要使用短信推送到指定的相关人员
那么接下来,我就以这些需求,一步一步带着你,通过IOT-Tree来实现它。
4 在IOT-Tree Server配置实现报警
4.0 短信平台如何对接
在进入报警设置前,我先介绍一下我使用的短信平台。国内的短信平台大部分给你提供服务的时候,都需要你注册,给你分配key,然后你可以方便的进行充值。同时,对于短信格式,你必须在管理界面中设置短信模板。然后在调用时,只需他提供模板id和对应的数据参数即可。如我的一个模板如下:
【机房】机房高温度报警@var(st),当前温度@var(temp)
你使用这个模板时,只需要基于Http URL,post一个json数据就行{"st":"触发","temp":29} 。当然你post数据时,还需要提供你的身份key,模板id等参数。
4.0.1 IOT-Tree内部提供$$http支持
IOT-Tree内部提供JS支持,并且还可以针对一些通用api提供相关的插件。其中$$http这个插件,就是支持针对Http URL提供get 或 post支持。如我们这次使用的短信发送,可以使用如下JS代码实现
- let st = $alert.triggered?"触发":"";
- if(!st)
- st =$alert.released?"解除":"";
- if(!st)
- return;
- let temp = $alert.str_val;
- var msg = {"st":st,"temp":temp } ;
-
- var u = $$http.createUrl("https://api.xxxx.com/sms/send");
- u.setRequestHeader("Content-Type","application/x-www-form-urlencoded");
- u.setPostParam("appid","11111");
- u.setPostParam("user_key","567567456745675467");
- u.setPostParam("to","13911111111");
- u.setPostParam("sms_tp","112234");
- u.setPostParam("sms_data",JSON.stringify(msg));
-
- u.doPost();
-
- $debug.println("out alert sms post ok");
这个代码首先生产msg这个json对象,然后通过url创建一个HttpURL对象,然后设置相关参数,最后调用doPost()进行提交。
代码很简单,对应我们搞技术的人来说,你可以很短时间就可以掌握JS的基本语法。而在IOT-Tree则尽可能让你少些代码,以上代码是因为短信平台实在特殊,才需要你写这么多。事实上,上面代码关键的也就5行。那么,你如何才能知道$$http支持哪些函数呢,并且返回的那个u,内部又有哪些函数呢?
4.0.2 IOT-Tree的JS帮助
在IOT-Tree编辑JS的输入框中,一般情况下,你只需要双击就可以打开JS编辑辅助对话框。左边就会列出你当前运行JS的所有成员。如下面就是展开$$http和HttpURL这两个成员的内容:
当前的报警输出,目前就支持JS实现, 我们接着往下先。
4.1 UPS报警实现
我们在之前实现接入配置中,对UPS数据标签定义了4种运行状态(bool)类型,如下图:
而我们报警只需要在非online时触发,因此我们只需要针对ups_st_online这个数据标签定义报警源。
4.1.1 定义报警源
鼠标双击ups_st_online这个数据标签,会弹出编辑对话框。在Alert输入右边,点击"+"按钮,就会弹出新增报警源的对话框, 填写如下信息:
Alert Type=On Off
Alarm Value=0
Prompt=UPS不在线
点击Ok,确定之后此标签就支持内部报警源的参数了,其中触发条件是 值==0 ,解除条件是 值!=0. 你会看到标签列表多了一个标记
4.1.2 定义报警处理Handler
在项目管理中间树的上方,点击“Alert Manager”图标,右边就会出现本项目的报警管理选项卡。你可以看到左中右分别是报警源-报警Handlers和Outputs。并且左边已经出现了我们刚才定义的数据标签和报警源。
很明显,我们可以在Alert Handlers右边点击 "+Add"按钮添加报警处理(Handler)。弹出的对话框如下:
点击Ok,就可以看到这个处理项在列表中了。
4.1.3 关联报警源和Handler
我们用鼠标选中这个"UPS报警处理",你会看到左边的数据源右边会出现一个勾选框,你勾选这个,就会发现他们之间就建立了关联。同样的,你如果想去除关联,只需要取消勾选就行。
请点击上方的“Save"按钮,这样才能保存关联结果。
4.1.4 定义报警输出
点击右上角Outputs右边的"+Add"按钮,弹出的对话框填写如下:
其中,输出JS脚本和上面讲述的脚本类似,只是模板和json数据格式有差异:
- let st = $alert.triggered?"触发":"";
- if(!st)
- st =$alert.released?"解除":"";
- if(!st)
- return;
- var msg = {"st":st} ;
-
- var u = $$http.createUrl("https://api.xxxx.com/sms/send");
- u.setRequestHeader("Content-Type","application/x-www-form-urlencoded");
- u.setPostParam("appid","1111");
- u.setPostParam("user_key","11111111222222233333");
-
- u.setPostParam("sms_tp","55555");
- u.setPostParam("sms_data",JSON.stringify(msg));
-
- u.setPostParam("to","13611112222");
- u.doPost();
-
- $debug.println("out UPS sms post ok");
这个短信模板如下:
【机房监控】UPS非市电Online-报警@var(st)
代码中,$$http 上面已经有说明,那么$alert这个对象又有哪些成员呢?你只需要鼠标双击JS代码框,就会弹出JS辅助窗口,左边语法树中,你可以找到$alert,展开就可以看到成员了。
本输出非常简单,根据运行产生的$alert 对象,判断是否是触发(triggered)或解除(released)。然后生成msg对象,然后建立HttpURL对象,设置参数进行短信doPost发送。
4.1.5 关联报警处理Handler和输出
报警输出设置完成之后,你会在Outputs列表中看到这个项。此时,你点击中间的Handler,右边的输出项也会出现关联勾选框,你只要进行勾选,就可以完成关联了。
还是一样,关联之后不要忘记点击"Save"按钮。很简单,很直观,我们就完成了UPS的报警功能。
此时,你可以启动项目,然后在现场手工调整UPS到by pass模式,这样数据源就能触发、被Handler处理,并输出到运行那段JS代码促使短信的发出。当你手工恢复UPS到online模式,也会收到报警解除短信。
4.2 温度报警实现
温度报警和上面实现很类似,只是报警源和短信JS代码的JSON格式有所不同。这里就讲报警源如何设定,其他就没必要展开了。
温度值是一个连续值,和上面的bool报警源有差别。我们找到温湿度传感器那个设备,双击temp这个标签,在Alert边上,点击"+"按钮,填写如下信息:
请注意:我们这次选择的Alert Type是"Value >" 。并且Reference Value(参考值)=29,然后很重要的Release Error=-1。这样的报警源触发条件是温度值达到29度就触发,进入触发状态之后,温度必须降低到29+(-1)=28这个值才能解除。
这里面有个很重要的概念——死区。我们传感器在监测现实物理世界的时候,数据是有波动的。比如,温度到了29度瞬间,前几秒测试有29,然后接着就可能出现28.9,然后接着可能29.1。这种波动是个客观存在。可以想象,你如果在进入报警状态,解除之前不做个死区,那么在这种临界值,报警-解除可能会疯狂的重复,按照我们的上面定义的报警机制,那么系统会疯狂的发送报警触发和解除短信。有了这个死区概念,一旦进入报警触发状态,那么微小的波动跳变是不会让你解除报警状态的。
温度报警其他就不需要讲了,看个最终配置好的样子
4.3 漏水报警的一个坑
漏水传感器自身也有一个是否产生报警的数据标签(bool),我这次项目中,本以为这个报警源定义和UPS的状态(bool)一样简单了。没想到配置好,拿了水往传感器倒水测试时发现,这东东代码实现没有考虑上面的死区。并且那个模拟量值跳动的厉害(很明显缺乏抗干扰滤波)——其实这在传感器内部单片机上加应该不到20行代码就可以解决。
但远水解不了近渴啊。所以,我们就自己在传感器的那个模拟量值上加了如下配置。
4.3.1 在漏水传感器模拟量值支持抗干扰
在leak1和leak2上的a_val数据标签双击,打开编辑,勾选Filter - Enable anti-interference.
这样,IOT-Tree就会对这个标签做一定数量的历史数据,然后最新数据使用平均值。这样此数据明显会稳定很多。
4.3.2 添加报警源
点击Alert右边的"+"按钮,填写如下内容:
请仔细看,Alert Type 为Value< (因为有水之后值会变小,干了之后又会变大),参考值500,解除误差(死区)=50。你应该自己能理解了。
其他报警配置都类似,就不展开重复了。最终报警配置结果如下:
你可能已经发现,一个Handler既可以支持多个报警源,也可以支持多个Output,反正很灵活。
5 总结
这个报警处理还是很有特色的吧。本来应该是比较复杂难搞的东东,没想到就这么简单。本文章还给你讲述了实际项目需要注意的很多坑,你如果第一次接触,必定收获满满。
这样,我们项目工作基本接近尾声了。下一篇我们就着重收尾了,比如把我们笔记本配置的项目部署到机房触摸屏机器上等工作。你肯定还会有更多收获的。
评论记录:
回复评论: