Flink SQL中窗口和水印触发机制

下面是一个使用窗口的例子,按说明写入了2条数据,各个窗口的开始和结束时间规则,以及水印的使用,代码如下:

-- 第一条数据09:00:25,第二条数据09:01:10
CREATE TEMPORARY TABLE kafka_test_report (
  `my_id` VARCHAR(64),
  `event_time` VARCHAR(20),
  `my_num` BIGINT,
  `ts` AS TO_TIMESTAMP(event_time),
  WATERMARK FOR ts AS ts - INTERVAL '3' SECOND
) WITH (
  'connector' = 'kafka',
  ...
);

CREATE TEMPORARY TABLE print_sink (
  `window_start` TIMESTAMP(3),
  `window_end` TIMESTAMP(3),
  `my_id` VARCHAR(64),
  `my_value` BIGINT
) WITH (
  'connector' = 'print'
);


BEGIN STATEMENT SET;

-- 滚动窗口,09:00:00作为窗口开始时间
INSERT INTO print_sink
SELECT
  TUMBLE_START(ts, INTERVAL '1' MINUTE) as window_start,
  TUMBLE_END(ts, INTERVAL '1' MINUTE) as window_end,
  my_id,
  COUNT(1) AS my_num
FROM kafka_test_report
GROUP BY TUMBLE(ts, INTERVAL '1' MINUTE),my_id;

-- 滑动窗口,首个更新窗口08:51:00作为开始时间,09:01:00作为结束时间
INSERT INTO print_sink
SELECT
  HOP_START (ts, INTERVAL '60' SECOND, INTERVAL '10' MINUTE) AS window_start,
  HOP_END (ts, INTERVAL '60' SECOND, INTERVAL '10' MINUTE) AS window_end,
  my_id,
  SUM(my_num) AS my_num
FROM kafka_test_report
GROUP BY HOP(ts, INTERVAL '60' SECOND, INTERVAL '10' MINUTE),my_id;

-- 累计窗口,首个更新窗口09:00:00->09:00:40
INSERT INTO print_sink
SELECT
  window_start,
  window_end,
  '101' AS my_id,
  SUM(my_num) AS my_num
FROM TABLE(CUMULATE(
  TABLE kafka_test_report,
  DESCRIPTOR(ts), -- 时间戳
  INTERVAL '40' SECOND,
  INTERVAL '1' HOUR
))
GROUP BY window_start,window_end;

END;

数据源为Kafka,有2个分区(并发),有1个分区一直没有数据,会导致无法触发窗口结束,导致结果数据异常。解决办法为:

  • 根据数据乱序的程度设置合理的offset大小,并保证所有并发都有数据。
  • 如果某个源表并发或源表上游partition因没有数据导致窗口始终无法被触发,可在Flink配置中添加table.exec.source.idle-timeout: s来触发窗口结束。table.exec.source.idle-timeout表示某个并发来源如果在指定时间内没有数据进来则临时设为空闲,此时下游任务无需等待该空闲并发源去增长他们的watermark,默认为0表示空闲并发源是禁用的。

综上,Flink解决一个分区没有数据无法触发窗口结束的方式是设置一个过期时间告诉Flink系统这个Partition没数据了,那么计算Watermark的时候就不考虑他了,等他有数据再把他列入计算Watermark的范畴。但如果每个分区都没有数据,还是无法更新watermark,即无法触发下游。此时结束标识数据可使用Sink的RDS延迟输出参数的方式配置。

  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
Flink SQL的JOIN操作可以和窗口一起使用,实现窗口上的JOIN计算,这可以在实时流处理非常有用。 窗口是数据流处理的一种重要概念,它可以将数据流按照时间或者数量等维度进行切分,然后对每个窗口内的数据进行计算。Flink SQL支持多种类型的窗口,如滚动窗口、滑动窗口、会话窗口等。 在使用Flink SQL进行JOIN操作时,可以将JOIN条件和窗口条件进行结合,以获取更加精细的数据切分和计算结果。例如,可以将两个数据流按照时间窗口进行JOIN操作,计算出在指定时间窗口内符合条件的数据。 具体来说,Flink SQL的JOIN操作和窗口的结合有以下几个步骤: 1. 定义窗口:使用Flink SQL窗口函数,对数据流进行窗口切分,定义窗口大小和滑动步长等参数。 2. 分区数据:将数据流按照JOIN条件进行分区,将不同数据流符合条件的数据分配到同一个计算节点上。 3. 缓存数据:将分区后的数据缓存到内存或者磁盘,以供后续的JOIN计算使用。 4. JOIN计算:对缓存的数据按照JOIN条件进行JOIN计算,同时按照窗口条件进行分组计算,计算出符合条件的数据。 5. 输出结果:将JOIN计算的结果输出到指定的目标位置,以供后续的查询分析使用。 总的来说,Flink SQL的JOIN操作和窗口的结合可以实现更加精细的数据切分和计算,可以在实时流处理实现更加复杂的数据分析和处理。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值