Drools事件生命周期



我不得不创建成对的规则来收回我的事件。它们似乎不会过期。我想要一个,并做了一些活动。你可以在下面看到,他们使用默认的持续时间,零。

因此,例如,如果我排除撤回规则,然后先插入RemoveConnectionEvent,然后插入CreateConnectionEvent,那么RemoveConnection规则仍然会触发。(在我的单元测试中使用议程监听器)

我对事件的期望是RemoveConnectionEvent将被忽略,如果不立即满足其条件,它将不会执行任何操作。我没想到当NewConnection规则响应CreateConnectionEvent时,一旦满足规则条件,它就会挂起并触发RemoveConnection规则。

为了让我的规则按预期运行,我创建了RetractedCreation、RetractedRemoval和RetractedUpdate。这似乎是一次黑客攻击。我在想象一个宣布我的事件是错误的。

有什么想法吗?

ps这是一个非常好的问答;A但我不使用窗户。它可能会推断,也许我的破解是一个"明确的过期策略"。

Drools Fusion CEP中的测试事件到期测试事件到期

这是我的规则。

package com.xxx
import com.xxx.ConnectedDevice
import com.xxx.RemoveConnectionEvent
import com.xxx.CreateConnectionEvent
import com.xxx.UpdateConnectionEvent
declare CreateConnectionEvent @role( event ) end
declare UpdateConnectionEvent @role( event ) end
declare RemoveConnectionEvent @role( event ) end
rule NewConnection
    when
        $connection : CreateConnectionEvent($newChannel : streamId)
        not ConnectedDevice( streamId == $newChannel )
    then
        insert( new ConnectedDevice($newChannel) );
end
rule RetractedCreation
    when
        $creationEvent : CreateConnectionEvent($newChannel : streamId)
        exists ConnectedDevice(streamId == $newChannel)
    then
        retract($creationEvent)
end
rule RemoveConnection
    when
        $remove : RemoveConnectionEvent($newChannel : streamId)
        $connection : ConnectedDevice( streamId == $newChannel )
    then
        retract( $connection );
end
rule RetractedRemoval
    when
        $removalEvent : RemoveConnectionEvent($newChannel : streamId)
        not ConnectedDevice(streamId == $newChannel)
    then
        retract($removalEvent)
end
rule UpdateConnection
    when
        $connectionUpdate : UpdateConnectionEvent($newChannel : streamId) 
        $connection : ConnectedDevice( streamId == $newChannel )
    then
    $connection.setLastMessage();
end
rule RetractedUpdate
    when
        $removalEvent : UpdateConnectionEvent($newChannel : streamId)
        not ConnectedDevice(streamId == $newChannel)
    then
        retract($removalEvent)
end

此自动到期功能相当难以捉摸。它什么时候能起作用,以及需要做些什么才能起作用,目前还没有一个简明的定义。

在你明显简单的情况下,如果你不使用时态运算符,并期望事件在匹配一条规则后被撤回,我会采取以下策略,而不会在"推断到期"one_answers"管理生命周期"上浪费另一个想法。

也许您的事件有一个通用(抽象)基类;否则,创建一个标记接口并将其附加到所有事件。让我们把这种类型称为Event。然后,一个单一规则

rule "retract event"
salience -999999
when
    $e: Event()
then
    retract( $e );
end

将处理所有(创建、更新、删除)事件。

编辑您也可以使用事件过期的显式设置。

declare CreateConnectionEvent
    @role( event )
    @expires(0ms)
end

确保使用

KieBaseConfiguration config = ks.newKieBaseConfiguration();
config.setOption( EventProcessingOption.STREAM );
KieBase kieBase = kieContainer.newKieBase( config );

创建KieBase时。我还建议"让时间过去",即提前一个伪时钟,或者让线程在插入事实后运行一两个fireUntilHalt

最新更新