Wait

文档中心 › 组件索引 › Wait

Wait Processor

类型全限定名:cn.org.acal.lynxus.processors.standard.Wait

所属 Bundle:cn.org.acal.lynxus:lynxus-standard-nar:2.11.8

描述

将传入的 FlowFile 路由到 'wait' 关系,直到匹配的释放信号存储在分布式缓存中。

标签

mapcachewaitholddistributedsignalrelease

属性

下表中,加粗的属性为必填项;其余为可选项。表格同时标注默认值、是否支持表达式语言,以及是否为敏感属性(值会被加密)。

名称默认值可选值描述
Release Signal Identifier指定特定释放信号缓存的键的值。为了决定由 Wait 处理器处理的 FlowFile 应发送到 'success' 还是 'wait' 关系,处理器会检查此键指定的缓存中的信号。
支持表达式语言:是(使用 FlowFile 属性与环境/系统变量求值)
Target Signal Count1缓存中(由释放信号标识符指定)需要存在的信号数量,以便 Wait 处理器处理的 FlowFile 被发送到 'success' 关系。如果缓存中的信号数已达到此数量,FlowFile 将被路由到 'success' 关系,并且缓存中的信号数将减少此值。如果指定了信号计数器名称,此处理器检查特定计数器,否则检查缓存中的信号总数。
支持表达式语言:是(使用 FlowFile 属性与环境/系统变量求值)
Signal Counter Name在缓存内(由释放信号标识符指定),信号可能属于不同的计数器。如果指定了此属性,处理器检查缓存中属于此特定计数器的信号数。如果未指定,处理器检查缓存中的信号总数。
支持表达式语言:是(使用 FlowFile 属性与环境/系统变量求值)
等待缓冲计数1指定可以缓冲以检查是否可以继续前进的最大传入 FlowFile 数量。更多的缓冲可以提供更好的性能,因为它通过按信号标识符分组 FlowFile 来减少与缓存服务的交互次数。每次处理器执行只能处理一个信号标识符。
Releasable FlowFile Count1值或属性表达式语言语句的结果,将对 FlowFile 进行求值以确定可释放的 FlowFile 数量。这指定当目标计数达到目标信号数量时可以释放多少个 FlowFile。零 (0) 具有特殊含义,只要信号计数与目标匹配,就可以释放任意数量的 FlowFile。
支持表达式语言:是(使用 FlowFile 属性与环境/系统变量求值)
Expiration Duration10 min指示等待的 FlowFiles 将被路由到“过期”关系的持续时间
Distributed Cache Service控制器服务 API:
AtomicDistributedMapCacheClient
cn.org.acal.lynxus-lynxus-standard-services-api-nar-2.11.8
用于检查来自相应通知处理器的释放信号的Controller Service
Attribute Copy Modekeeporiginal
  • 替换已有属性 — 当缓存的属性被复制到发布的 FlowFile 时,它们会替换任何匹配的属性。
  • 保留原始属性 — 发布的 FlowFile 上的属性不会被复制的缓存属性覆盖。
指定如何处理从进入通知处理器的 FlowFiles 复制的属性
Wait Modewait
  • 转移到 wait 关系 — 当 FlowFile 的释放信号尚未通知时,将其转移到 'wait' 关系。此模式允许通过将 FlowFile 移入 wait 关系来让其他传入的 FlowFile 入队。建议在 'wait' 关系上设置优先级排序器(例如先进先出)。
  • 保留在上游连接中 — 当 FlowFile 的释放信号尚未通知时,将其转移到来源的上游连接。此模式有助于保持上游连接满载,以便在背压激活时上游源处理器不会被调度,并限制传入的 FlowFile。
指定如何处理等待通知信号的 FlowFile
Wait Penalty Duration如果配置,当信号标识符被处理但未满足释放条件时,该信号标识符将被惩罚,并且具有该信号标识符的 FlowFile 在指定时间段内不会被再次处理,这样该信号标识符不会阻塞其他信号标识符的处理。这对于以下用例很有用:Wait 处理器需要处理多个信号标识符,每个信号标识符有多个 FlowFile,并且在同一信号标识符内释放 FlowFile 的顺序很重要。FlowFile 顺序可以通过优先级排序器配置。重要提示:可处理的排队信号数量有限,Wait 处理器可能无法检查所有排队的信号 ID。请参阅附加详情了解最佳实践。

关系 (Relationships)

名称描述自动终止
expired超过配置的过期时间的 FlowFile 将被路由到此关系否
failure当无法到达缓存时,或者释放信号标识符评估为 null 或空时,FlowFiles 将被路由到此关系否
success缓存中具有匹​​配释放信号的 FlowFile 将被路由到此关系否
wait缓存中没有匹配释放信号的 FlowFile 将被路由到此关系否

写入的 FlowFile 属性

名称描述
wait.start.timestamp所有 FlowFile 将具有 'wait.start.timestamp' 属性,该属性设置文件首次进入此处理器时的初始纪元时间戳。这用于确定 FlowFile 的过期时间。当 FlowFile 传输到 failure、过期或 success 时不写入此属性
wait.counter.<counterName>每个计数器的名称,自上次缓存被清空以来至少有一个信号出现在缓存中,被复制到当前 FlowFile 作为属性。

状态管理

该组件不存储状态。

受限 (Restricted)

该组件不受限。

输入要求

该组件要求有传入连接。

详细说明

Wait

在 Wait Processor 中处理多个 signal id 的最佳实践

当 Wait Processor 需要处理多个 signal id(通过在 'Release Signal Identifier' 中配置 FlowFile Attribute 的表达式语言实现)时,为了获得预期结果,有几件事需要考虑。Processor 的 配置会因需求而异。同时,你还需要对 Wait Processor 的工作原理有总体了解:

  • Wait Processor 一次只处理一个 signal id
  • Wait Processor 的运行频率由 'Run Schedule' 定义
  • 处理哪个 FlowFile 由 Prioritizer 决定
  • 不仅限于 Wait Processor,对所有 Processor 而言,如果没有设置 Prioritizer, Connection 中排队 FlowFile 的顺序是不确定的

常见模式参见以下小节:

信号一经通知即释放对应 FlowFile

这是最常见的用例。FlowFile 之间相互独立,可以按任意顺序释放。

重要配置:

  • 在 'wait' Relationship 上使用 FirstInFirstOutPrioritizer(FIFO) (如果 'Wait Mode' 为 'Keep in the upstream connection',则在上游 Connection 上使用)

下表演示了每个 Wait 运行周期中:已通知的 signal id、排队中的 FlowFile 以及会发生什么。

# of Wait run Notified Signals Queue Index (FIFO) FlowFile UUID Signal ID
1 B 1 a A 该 FlowFile 被处理。但其信号未找到,会被重新排到队列末尾。
2 b B
3 c C
2 B 1 b B 该 FlowFile 被处理,由于其信号已被通知,它会被释放到 'success'。
2 c C
3 a A
3 1 c C 该 FlowFile 将在下一次运行时被处理。
2 a A

在每个 signal id 内优先释放高优先级 FlowFile

多个 FlowFile 共享同一个 signal id,且释放顺序很重要。

重要配置:

  • 在 'wait' Relationship 上使用 FIFO 之外的、符合你需求的一个(或一组)Prioritizer (如果 'Wait Mode' 为 'Keep in the upstream connection',则在上游 Connection 上使用), 例如 PriorityPrioritizer
  • 指定合适的 'Wait Penalty Duration',例如 "3 sec"
  • 'Wait Penalty Duration' 应大于 'Run Schedule',例如 "3 sec" > "1 sec"
  • 增大 'Run Duration',以避免 signal id 数量的限制(参见下文说明)

下表演示了每个 Wait 运行周期中:已通知的 signal id、排队中的 FlowFile 以及会发生什么。 示例使用 PriorityPrioritizer 来控制同一 signal id 内 FlowFile 的处理顺序。如果配置了 'Wait Penalty Duration',Wait Processor 会跟踪未释放的 signal id 及其惩罚(表示何时再次检查)。

# of Wait run Notified Signals Signal Penalties Queue Index (via 'priority' attribute) FlowFile UUID Signal ID 'priority' attr
1 (00:01) B 1 a-1 A 1 该 FlowFile 被处理。但其信号未找到,被施加惩罚。
2 b-1 B 1 由于 a-1 和 b-1 的优先级 '1' 相同,b-1 可能先于 a-1 被处理。可以再加一个 Prioritizer 来定义更具体的顺序。
3 b-2 B 2
2 (00:02) B A (00:04) 1 a-1 A 1 按配置的 Prioritizer 该 FlowFile 排第一,但其 signal id 处于惩罚期。因此本次执行中该 FlowFile 被跳过。
2 b-1 B 1 该 FlowFile 被处理。
3 b-2 B 2
3 (00:03) A (00:04) 1 a-1 A 1 该 FlowFile 排第一,但仍在惩罚期。
2 b-2 B 2 该 FlowFile 被处理,但其信号尚未被通知,因此被施加惩罚。
4 (00:04) B (00:06) 1 a-1 A 1 该 FlowFile 不再处于惩罚期并被处理。但其信号仍未被通知,因此再次被施加惩罚。
2 b-2 B 2

使用 'Wait Penalty Duration' 时 'Run Duration' 的重要性

基于 'Run Schedule' 与 'Wait Penalize Duration' 的组合,可检查的信号数量存在上限。一旦触及该 限制,即使某些 FlowFile 的 signal id 已被通知,它们也可能不被处理而一直留在 'wait' Relationship 中。假设 Wait 的配置为:

  • Run Schedule = 1 sec
  • Wait Penalize Duration = 3 sec
  • Release Signal Identifier = ${uuid}

并且 'wait' Relationship 中有 5 个 FlowFile:F1、F2 ... F5。此时 F5 的信号被通知。Wait 的 工作方式如下:

  • 00:00 时,Wait 检查 F1 的信号,未找到,对 F1 施加惩罚(至 00:03)
  • 00:01 时,Wait 检查 F2 的信号,未找到,对 F2 施加惩罚(至 00:04)
  • 00:02 时,Wait 检查 F3 的信号,未找到,对 F3 施加惩罚(至 00:05)
  • 00:03 时,Wait 检查 F4 的信号,未找到,对 F4 施加惩罚(至 00:06)
  • 00:04 时,Wait 再次检查 F1 的信号,因为它已不再处于惩罚期

上述循环反复进行,因此在 F1 ... F4 中某个被释放之前,F5 不会被释放。

为缓解这一限制,建议增大 'Run Duration'。增大 'Run Duration' 后,Wait Processor 可以在该时长内 持续被调度。例如,'Run Duration' 设为 500 ms 时,Wait 应当能在单次运行中遍历全部 5 个排队的 FlowFile。

使用计数器(counter)

计数器本质上是一个标签,用于区分缓存内的不同信号(这里的"缓存"是指包含具有相同 signal identifier 的信号的一个"容器")。

假设缓存中有如下信号(注意,这些不是 Wait Processor 传入(或 wait)Connection 上的 FlowFile,而是存储在缓存中的释放信号):

Signal ID Signal Counter Name
A counter_1
A counter_1
A counter_2

在此状态下,以下 FlowFile 被 Wait Processor 处理(该 FlowFile 带有 signal_counter_name Attribute,且 Wait Processor 被配置为使用该 Attribute 的值作为 Signal Counter Name 属性的值):

FlowFile UUID Signal ID signal_counter_name
a-1 A counter_3

尽管 Signal ID "A" 对应的缓存中有信号,上面的 FlowFile 仍会被发送到 'wait' Relationship, 因为缓存中没有属于名为 "counter_3" 的计数器的信号。

假设缓存状态与上面相同,以下 FlowFile 被 Wait Processor 处理:

FlowFile UUID Signal ID signal_counter_name
a-2 A counter_1

该 FlowFile 会被传输到 'success' Relationship,因为缓存 "A" 中有信号,且存在属于 "counter_1" 的信号。输出的 FlowFile 会被追加以下 Attribute 及其值:

  • wait.counter.counter_1 : 2
  • wait.counter.counter_2 : 1
  • wait.counter.total : 3

这里的关键点是:计数器可用于区分缓存内的不同信号。如果使用了计数器,经过 Wait Processor 的 每个计数器都会为 FlowFile 追加一个新 Attribute。如果一个缓存中使用了大量计数器,经过 Wait Processor 的 FlowFile 会被追加大量 Attribute。为避免这种情况,建议使用多个缓存、每个 缓存只含少量计数器,而不是一个缓存含很多计数器。

例如:

  • Release Signal ID "A" 对应的缓存包含计数器:"counter_1" 和 "counter_2"
  • Release Signal ID "B" 对应的缓存包含计数器:"counter_3" 和 "counter_4"
  • Release Signal ID "C" 对应的缓存包含计数器:"counter_5" 和 "counter_6"

(计数器名不需要在缓存之间唯一,缓存 "A" 使用的计数器名也可以在缓存 "B" 和 "C" 中复用。)