最近看到edgex foundry在规则引擎上有很大的改动,之前的规则引擎主要是基于drools实现的,使用模板对每个设备生成单独的drl文件,这也导致不能充分使用drools的规则,要充分使用drools的规则就不能使用模板,所以规则引擎在edgex foundry项目中一直以参考实现的方式存在。
01
—
了解EdgeX Foundry
EdgeX Foundry 是由Linux Foundation托管的与供应商无关的开源项目,它为IoT边缘计算构建了通用的开放框架,同样领域的项目还有KubeEdge等,它以微服务平台的形式部署在厂商的一块或多块板子上,之前用过比如像高通的RB3、intel的x86板子和英伟达的tx2等等,如果有了解aws的其实aws台湾一直在做的greengrass也是一样的功能,就是在设备端到云端中间添加了一层边缘端,用来对局域网内的设备进行数据采集和管理控制,并将收集的数据上报给云端,其平台架构如下图所示,也是数据平面和控制平面分离:
其中分发层和规则引擎是我们针对edgexfoundry二次开发的重点关注组件,scheduling是次要关注组件,我们简单描绘下数据通路:
每个组件之间的通信都是使用zeromq,分发层负责将数据上报到云端,规则引擎则是负责过滤数据并通知command告警,之前除了core层其他都是处于非常不完善的阶段,有很大的不确定性和定制化,光到目前为止,社区就有用app-function-sdk取代分发层的计划,也有用emqx取代规则引擎的趋势。
02
—
规则引擎简述
规则引擎是大家比较熟悉的部分,很多都会用到,规则引擎有很多类型,一是类似于graalvm动态执行js,groovy等,表述能力等于选用语言的能力,但是有学习一门语言的成本,二是使用基于规则匹配算法的开源,比如使用基于Rete规则匹配算法的drools,还有json简单定义规则,直接匹配。
edgex之前的规则引擎就是使用drools,实现了简单的比如大于小于等于这种规则,我们修改一下模版,增加与或非的逻辑,增加多重规则,增加一种场景当一个设备达到规则后唤醒其他设备,增加一种场景一个设备可以定期调度,比如闪烁一段时间。
drl的规则形式例如 rule...when...then...,我们在then后添加对应的实现类。
但是更加复杂的逻辑就很难使用这种模版加drools的方式实现,比如有状态的操作,十分钟内温度持续大于80这种,需要规则引擎部分维护状态的就很难实现了,这种需求更加的偏向流式处理。
03
—
使用轻量级流式处理取代规则引擎
源 (Source)SQL (业务逻辑处理)目标 (Sink)
// 数据类型{ "Device": "demo", "Created": 000, … "readings": [ {"Name": "Temperature", value: "30", "Created":123 …}, {"Name": "Humidity", value: "20", "Created":456 …}]}// 规则使用的sql,大于50的数据将被发送到mqtt,其余数据将被丢弃curl -X POST \ http://$kuiper_server:9081/rules \ -H 'Content-Type: application/json' \ -d '{ "id": "rule1", "sql": "SELECT * FROM demo WHERE temperature > 50", "actions": [ { "mqtt": { "server": "tcp://broker.emqx.io:1883", "topic": "result", "clientId": "demo_001" } }, { "log":{} } ]}
在时间流场景中,对时态窗口中包含的数据执行操作是一种常见的模式。Kuiper有四种窗口可供使用: 滚动窗口, 跳跃窗口,[滑动窗口][Sliding window]和 会话窗口。可以在Kuiper查询的查询语法的GROUP BY子句中使用窗口函数。
滚动窗口
滚动窗口函数用于将数据流分割成不同的时间段,并对其执行函数,下面的sql展示了统计数据流十秒内的记录数。
SELECT count(*) FROM demo GROUP BY ID, TUMBLINGWINDOW(ss, 10);
跳跃窗口
跳跃窗口功能会在时间上向前跳一段固定的时间。将它们视为可能重叠的翻转窗口可能很容易,因此事件可以属于多个跳跃窗口结果集
SELECT count(*) FROM demo GROUP BY ID, HOPPINGWINDOW(ss, 10, 5);
滑动窗口
滑动窗口功能与翻转或跳动窗口不同,仅在事件发生时会产生输出。每个窗口至少会有一个事件,并且该窗口连续向前移动€(ε)
SELECT count(*) FROM demo GROUP BY ID, SLIDINGWINDOW(mm, 1);
会话窗口
会话窗口功能对在相似时间到达的事件进行分组,以过滤掉没有数据的时间段。它有两个主要参数:超时和最大持续时间。
SELECT count(*) FROM demo GROUP BY ID, SESSIONWINDOW(mm, 2, 1);
04
—
尾言
使用流式处理取代规则引擎相比传统规则引擎更加优雅 ,对于有这种需求的比如告警可以参考它的实现来做更加优雅的时间窗口和sql处理。