我是Flink的新手,我正试图使用它来获取我的应用程序的实时视图。我要构建的动态视图中至少有一个是显示未满足SLA或已基本过期的条目,而这样做的条件将是简单的时间戳比较。因此,如果最近一次事件触及了 NOT ,我基本上希望在动态表中显示该条目。在开发环境中使用Flink 1.6(受AWS Kinesis限制),我没有看到Flink正在重新评估条件,除非事件触及该条目。
我已经将开发环境插入到Kinesis流中,该流从Web服务器发送实时访问日志事件。这不是我真正的用例,但是这是一个很容易开始测试的用例。我编写了一个简单的表查询,该查询提取一个请求路径,它的上次访问时间,并计算一个布尔标志以指示是否在最后一分钟没有访问它。我正在通过连接到PrintSinkFunction的撤回流对其进行调试,以便将所有更新/删除都打印到我的控制台上。
tEnv.registerDataStream("AccessLogs", accessLogs, "username, status, request, responseSize, referrer, userAgent, requestTime, ActionTime.rowtime");
Table paths = tEnv.sqlQuery("SELECT request AS path, MAX(requestTime) as lastTime, CASE WHEN MAX(requestTime) < CURRENT_TIMESTAMP - INTERVAL '1' MINUTE THEN 1 ELSE 0 END AS expired FROM AccessLogs GROUP BY request");
DataStream<Tuple2<Boolean, Row>> retractStream = tEnv.toRetractStream(paths, Row.class);
retractStream .addSink(new PrintSinkFunction<>());
我希望当我访问页面时,会将Add事件发送到此流。然后,如果我等待1分钟(不执行任何操作),则表中的CASE语句的计算结果将为1,因此我应该看到设置了该标志的Delete然后Add事件。
我实际上看到的是,直到我再次加载该页面,什么都没有发生。删除事件实际上已设置了标志,而紧随其后的添加事件又将其清除了(因为它不再“过期”,因此应该清除)。
// add/delete, path, lastAccess, expired
(true,/mypage,2019-05-20 20:02:48.0,0) // first page load, add event
(false,/mypage,2019-05-20 20:02:48.0,1) // second load > 2 mins later, remove event for the entry with expired flag set
(true,/mypage,2019-05-20 20:05:01.0,0) // second load, add event
编辑:我在搜索中遇到的最有用的提示是创建一个ProcessFunction。我认为这是我可以使用动态表进行处理的功能(在某些情况下,我最终会使用中间流来查看计算的日期),但希望不必这样做。
我已经使用了ProcessFunction方法,但是它比我最初认为的需要更多的修改:
答案 0 :(得分:0)
您的方法看起来很有希望,但是Flink的Table API / SQL(尚不支持)与移动的“现在”时间戳进行比较。
我分两步解决。
request
)对每个键(在您的情况下为requestTime
进行升级的表)。生成的动态表将保存每个请求的最新行。不幸的是,Flink都没有这两个功能(向上转换和与移动的“ now”时间戳进行比较)。不过,仍有一些工作正在进行表转换的升级。