说明:

  以下内容,可以参考Esper官方网站《Qucik start & Tutorial 》(顺序做了部分调整)。 PS:因为英语水平有限(大学期间刚过CET4的英语小盲童一枚),翻译很烂(自己都感觉不能直视),描述不清的,可以随时问。一有时间,将给予解释。

Tutorial (教程)部分

1、简介 (该部分在入门第一弹中有提起)

Esper 是一个事件流处理和事件关联的引擎(CEP,complex event processing 复合事件处理)。作为实时事件驱动框架,当事件流中有事件条件发生时,Esper能够触发自定义动作(POJO)。Esper也是为了大量事件关联而设计,当有数百万的事件进来时,不能用经典的数据库架构来存储所有事件。

定制的事件处理语言EPL,允许表达丰富的事件条件、关联性,也可跨越事件窗口,从而最大限度的减少为应对复杂情况而必须建立系统的开发难度。

Esper是轻量级的java内核实现,其可以完全嵌入到任何的java进程、javaEE应用服务器或者给予java的ESB(企业服务总线)。Esper可以很快完成传入的大量消息或者事件处理的应用程序。

【总结】Esper是一个事件处理和复杂事件关联处理的java内核的轻量级引擎。对于大量事件的处理,能够用最短的时间做出反应,触发相应的操作。另外,为Esper量身定制的事件处理语言——类SQL语言,对于表达事件的条件以及关联关系的处理等非常方便。

2、事件流和复杂事件

信息对于作出明智的选择是至关重要的。不仅现实生活中这是事实,而且在计算机处理中尤其是一些领域,比如金融、欺诈检测、商业智能或是战场操作等,也是很重要的。信息从不同的来源,以消息或者事件的形式流动,如股票价格在某一特定时间的状态需要给出一个提示。也就是说,看离散的数据大部分时间是没有意义的。交易者需要看到一段时间的股票走势,以便结合其他信息在合适的时间做出最好的交易。

一条一条的离散事件是没有意义的,事件流——一个无限的事件集合——可认为是一个滑动的窗口,进一步关联是非常有意义的,并用最小的延迟对事件做出反应,对有效行动和竞争优势是至关重要的。

【总结】事件流其实一个个离散的事件串接而成。现实中对于事件流的监控或者处理,比如股票信息等,需要实时性的计算其走势,以便能够及时的获取有价值数据。事件流在Esper中是一个滑动的窗口,对事件关联处理等至关重要。

3、Esper

关系型数据库或者基于消息的系统比如JMS,真的很难处理时间数据和实时查询。事实上,数据库需要一个明确的查询来返回有意义的数据,并且在数据放生变化时不适合推送数据。JMS系统是无状态的,需要开发人员自己实现这个时间和聚合的逻辑。相比之下,Esper提供了更高的抽象和智能,可以认为是数据库的倒置:不是存储数据,而是对存储的数据运行查询,Esper允许应用程序存储查询,并让数据运行通过。当满足查询的条件发生时,Esper会做出实时的响应。执行模块是持续的,而不是只有在查询提交的时候。这个概念是EDA(事件驱动架构)的关键基础,在过去的10年,甚至更久都一直在积极的研究。然而,现实中对该系统重要性的认知最近才开始出现。

在Esper中,定制的EPL允许在引擎中注册查询。监听类(POJO类)会在事件满足EPL条件的时候由引擎进行调用。EPL能够表达复杂的匹配条件,包括事件窗口、事件流关联、过滤、聚合以及排序等。Esper statement也可以通过“followed by ” 即“->”条件从多个简单的事件中获取复杂事件。事件可以被描述成JavaBean类、传统的java类、XML或者是Map,作为消息发布者,促进重用现有的系统。

【总结】在处理实时性的数据时,比如心跳监控、股票价格走势等,Esper相对于关系型数据库有天然的优势,Esper不需要对完成的数据的存储,便可以完成数据的实时查询处理,从这点看,更像是数据库的倒置——试想一下,数据库是先存储数据,通过编译解析SQL,完成已存储数据的查询,Esper则是先编译EPL语句,形成一个过滤(或处理)层(或者网),实时过来的数据,通过这个过滤层完成有效事件的筛选或形成有效事件。Esper的事件处理语言——EPL,是类SQL语言,其select 语句、from语句、where语句以及group by 、having等,甚至包括大部分的聚合函数等,都和标准的SQL语言一致。在EPL规则的编写上,对于有数据库开发经验的人来说,上手十分容易。

4、开发事件驱动应用

用Esper来开发事件驱动应用并不困难。大概有下面的几步:

1> 通过分析业务域和定义探测的情景或者需要报告的信息,定义应用程序应该完成的功能或任务。

2> 定义性能要求,特别是吞吐量和延迟。

3> 确定从什么地方获取事件。

4> 根据业务确定事件格式和事件内容。

5> 设计导致复杂事件的事件关系。

6> 事件源。

7>  设计事件表示类型:java类、map、或XML等

8> 定义EPL语句,用于匹配模式和流的处理。

9> 比如,用CSV适配器作为事件模拟工具,测试检测场景,或产生加载加载事件。

10> 在最终的环境上,测试吞吐量和延迟。

5、设计事件表示方式

在Esper当中,java类是一种简单、丰富且通用的事件表示方式。通过接口和超类,java类提供了继承性和多态性,通过一个对象graph,就可以表示一个复杂的业务域。Maps或XML也是事件表示的一种方式。

6、事件流分析

EPL语句从一个或者多个事件流中派生和聚合信息,加入或合并事件流,并将一个时间流的结果提供给后续的语句。EPL在select语句和where语句的使用上,和SQL很相似。不过EPL语句用事件流和views替换了数据库的表格。和SQL中表格相似,views定义了可用于查询和过滤的数据。Views可以表示为一个事件流上的一个窗口。Views也可以排序事件、从事件属性获取统计数据、进行事件分组或者处理唯一的事件属性值。

下面的EPL语句用于计算股票事件过去30s的平均价格:

select avg(price) from StockTickEvent.win:time(30 sec)

下面EPL返回的是前100条股票事件的平均值:

select symbol, avg(price) as averagePrice
from StockTickEvent.win:length(100)
group by symbol

下面的例子关联了两个事件流。第一个事件流由欺诈告警事件组成,用于保存过去30分钟的事件信息。第二个流则是withdrawal事件,用来保存过去30秒的事件。这两个流通过account number进行关联:

select fraud.accountNumber as accntNum, fraud.warning as warn, withdraw.amount as amount,
MAX(fraud.timestamp, withdraw.timestamp) as timestamp, 'withdrawlFraud' as desc
from FraudWarningEvent.win:time(30 min) as fraud,
WithdrawalEvent.win:time(30 sec) as withdraw
where fraud.accountNumber = withdraw.accountNumber

7、事件模式匹配

Event patterns match when an event or multiple events occur that match the pattern's definition.

一个或多个事件发生时,事件模式会匹配定义的模式(很别扭啊⊙﹏⊙b)。模式也可以是基于时间的。模式匹配时通过状态机实现的。

模式表达式可以由连接了模式操作符的过滤器表达式组成。通过在圆括号中的嵌入表达式,可以实现更深的模式表达式嵌套。

5类操作符:

·控制模式探测器的创建和终止:every

· 逻辑操作符:and、or、not

· 操作事件顺序的时间操作符:-> (紧跟着发生的,followed by)

· 过滤输出事件的where条件,引起模式探测器的终止:如,timer:within

· 和观察其他事件一样,观察者也观察时间事件,如 timer:interval,  timer:at

下面是一些EPL的例子:

//模式匹配的是在接下来60秒钟IBM股票值大于80的所有事件
every StockTickEvent(symbol="IBM", price>80) where timer:within(60 seconds)
//每小时的第5分钟给出提醒:
every timer:at(5, *, *, *, *)
//当A事件发生时,如果后面跟的是B事件或C事件,则给出提醒(输出A事件)
A -> ( B or C )
//匹配的是每一个EventX,如果后跟EventY事件,并且其objectID和EventX的objectID一样,则给出提醒(输出a事件):
every a=EventX -> every b=EventY(objectID=a.objectID)

8、模式匹配和事件流分析结合使用

当检测到事件序列(或没有事件发生)时,模式就会匹配。模式匹配的结果可以用于进一步的分析和处理。

下面的模式监测的是 Status事件发生后的10s没有相同ID的status事件发生的场景。整个EPL语句进一步计算了所有发生的每个ID的事件总数。

select a.id, count(*) from pattern [
every a=Status -> (timer:interval(10 sec) and not Status(id=a.id)
] group by id

9、命名窗口

命名窗口在引擎中是全局的数据窗口,其可以参与到很多的语句查询,并且可以被多个statement执行select、insert和delete操作。命名窗口和关系型数据库系统的表很相似。

通过下面的几步可以创建命名窗口:

create window AlertNamedWindow as (origin string, priority string, alarmNumber long)

当事件到达时,可以触发一个select、update或delete操作。下面是一个select应用,简单的统计数据窗口中的记录行总数:

on TriggerEvent select count(*) from AlertNamedWindow

10、匹配-识别模式匹配(Match-Recognize Pattern Matching)

匹配-识别模式是一个基于正则表达式的模式匹配语法,是建议列入SQL的标准语法。

下面的匹配-识别模式,探测的是可能出现在事件中的模式,这些事件通过命名窗口(如上声明)保存。这个模式查找的是两个紧跟的事件,即事件之间没有相同的origin。第一个事件必须有一个“high”优先级,第二个事件必须是“medium”优先级。

select * from AlertNamedWindow
match_recognize (
partition by origin
measures a1.origin as origin, a1.alarmNumber as alarmNumber1, a2.alarmNumber as alarmNumber2
pattern (a1 a2)
define
a1 as a1.priority = 'high',
a2 as a2.priority = 'medium'
)

11、变量(Variables)

变量是一个标量、对象或者事件值,可用于所有的statement,包括模式。变量可以用在EPL中任意位置的表达式中。

【总结】开发Esper应用时,事件类型建议采用Java类,对于事件信息的描述更为直观(参考<a href="http://esper.codehaus.org/tutorials/tutorial/quickstart.html">Quick Start</a>)。在具有复杂关系的事件设计中,不建议使用Map的方式(可参考<a href="http://esper.codehaus.org/esper-4.9.0/doc/reference/en-US/html/performance.html#perf-tips-22">Esper参考文档性能部分</a>)。在EPL设计时,根据业务需求,如果能通过标准的SQL语法完成的,尽量不要使用匹配模式,因为在运行时,需要对Pattern进行额外的解析,其规则较SQL复杂,性能上有少许损耗。

数据窗口的使用,能够使得Esper处理更为复杂的应用场景,比如与分布式缓存、静态数据的使用等。变量不难理解,不管是高级的开发语言如java、C/C++,还是脚本语言如ruby、JS等,都有变量的概念,其使用范围,仅限于当前的Esper引擎实例。

另外,本节所描述的信息,如EPL、数据窗口等概念会在后续的更新中详细描述。敬请期待!!

注:转载请注明出处! 谢谢!

复杂事件处理引擎—Esper入门(第二弹)的更多相关文章

  1. 复杂事件处理引擎—Esper入门

    说明: 以下内容,可以参考Esper官方网站<Qucik start & Tutorial >(顺序做了部分调整). PS:因为英语水平有限(大学期间刚过CET4的英语小盲童一枚) ...

  2. 复杂事件处理引擎—Esper参考(事件部分)

    声明:Esper官方未提供中文文档,以后更新的大部分内容,均来自官方文档.本人英语小白一枚,翻译内容仅供参考.有些翻译确实不忍直视,君可略过. (有人可能会说,翻译的不好不如不翻,可能会误人子弟:不过 ...

  3. 复杂事件处理引擎—Esper工作原理

    前面对Esper进行了概述,包括事件类型.事件流.事件窗口以及EPL相关内容.当然,上面的知识,对于简单的Esper开发,应该已经足够,能够根据自己业务需求,做出一个满足需要的Esper应用.但是,真 ...

  4. 复杂事件处理引擎—Esper 处理模型

    1.esper的处理模型是持续性的——根据statement中事件流(event stream).视图(views).过滤器(filters)等的选择,esper引擎一旦处理事件数据,就会变更stat ...

  5. 青瓷引擎之纯JavaScript打造HTML5游戏第二弹——《跳跃的方块》Part 10(排行榜界面&界面管理)

    继上一次介绍了<神奇的六边形>的完整游戏开发流程后(可点击这里查看),这次将为大家介绍另外一款魔性游戏<跳跃的方块>的完整开发流程. (点击图片可进入游戏体验) 因内容太多,为 ...

  6. 微软TTS语音引擎编程入门

    原文链接地址:http://www.jizhuomi.com/software/135.html   我们都使用过一些某某词霸的英语学习工具软件,它们大多都有朗读的功能,其实这就是利用的Windows ...

  7. 浅谈Hybrid技术的设计与实现第二弹

    前言 浅谈Hybrid技术的设计与实现 浅谈Hybrid技术的设计与实现第二弹 浅谈Hybrid技术的设计与实现第三弹——落地篇 接上文:浅谈Hybrid技术的设计与实现(阅读本文前,建议阅读这个先) ...

  8. ElasticSearch入门 第二篇:集群配置

    这是ElasticSearch 2.4 版本系列的第二篇: ElasticSearch入门 第一篇:Windows下安装ElasticSearch ElasticSearch入门 第二篇:集群配置 E ...

  9. 高并发第二弹:并发概念及内存模型(JMM)

    高并发第二弹:并发概念及内存模型(JMM) 感谢 : 深入Java内存模型 http://www.importnew.com/10589.html, cpu缓存一致性 https://www.cnbl ...

随机推荐

  1. Letter Combinations of a Phone Number——LeetCode

    Given a digit string, return all possible letter combinations that the number could represent. A map ...

  2. X86 I/O端口

    与外设的交互都是通过读写外设上的寄存器进行的,外设的寄存器也成为“I/O端口”,它有两种编制方式:统一编址和独立编址. 统一编址: 外设接口中的IO寄存器(即IO端口)与主存单元一样看待,每个端口占用 ...

  3. AES - Rijndael 算法(二)

    三:Rijndael算法实现(C++版本) /*-------------------- Rijndael round subkeys ---------------------*/u8 roundK ...

  4. yum puppet dashboard

    该Dashboard是一种运行在Rails上的Ruby应用程序,它还不是可以添加到系统版本中的程序包,但是我们可以从Puppet Labs以RPM或者DEB包的形式获得该软件.我们也可以选择从资源进行 ...

  5. Selenium webdriver 元素操作

    本来这些东西网上一搜一大堆,但是本着收集的精神,整理一份放着吧!哈!哈!哈! 1. 输入框(text field or textarea) WebElement element = driver.fi ...

  6. Jenkins 初见

    在网上貌似没有找到Jenkins的中文的太多的文档,有的都是关于Hudson的一些 零零散散的,所以自己边学习边实践总结了以下系列文章,希望有助于大家对于Jenkins的使用. 本系列文章是基于我3年 ...

  7. python network programming tutorial

    关于网络编程以及socket 等一些概念和函数介绍就不再重复了,这里示例性用python 编写客户端和服务器端. 一.最简单的客户端流程: 1. Create a socket 2. Connect ...

  8. 通过 Linux 容器进行虚拟化

    简单介绍 Linux 容器是一种轻量级"虚拟化"方法,用于在单个控制主机上同一时候执行多个虚拟装置(容器).还有一个可用来描写叙述 Linux 容器所执行的操作的术语是" ...

  9. Android TableLayout 常用的属性介绍及演示

    TableLayout经常用的属性是: 1.android:collapseColumns:以第0行为序,隐藏指定的列:把android:collapseColumns=0,2 意思是把第0和第2列隐 ...

  10. 第一篇!in和exists性能比较和使用

    首先,先看下in和exists的区别: in 是把外表和内表作hash 连接: exists是对外表作loop循环,每次loop循环再对内表进行查询. 普遍的观点是exists比in效率高的.但是这不 ...