4.3 属性lock-on-active

默认值:false。

类型:Boolean。

属性说明:lock-on-active是指“锁定活跃”。既然它是规则体的属性,那一定是锁定规则的,而且是锁定活跃的规则。简单地说,当规则体设置该属性为true时,则当前只会被触发一次。当ruleflow-group或agenda-group再次被激活时,即使在规则体中设置了lock-on-active为true,该规则体也不能再次被激活,即无论如何更新规则事实对象,当前规则也只能被触发一次。这是no-loop的升级版,一个更强大的解决死循环的属性。下面通过例子结合no-loop说明中遇到的死循环问题提出解决方案。

创建规则文件isLockNoActive.drl,目录为rules/isLockNoActive,其内容为:

package rules.isLockNoActive
import com.pojo.Person;

rule "testLockNoActive1"
    lock-on-active true
    when
        $p:Person(name=="张三");
    then
       $p.setAge(30);
       update($p);
       System.out.println("testLockNoActive1 设置 no-loop时的效果");
end

rule "testLockNoActive2"
    lock-on-active true
    when
        $p:Person(age==30);
    then
       $p.setName("张三");
       update($p);
       System.out.println("testLockNoActive2 设置 no-loop时的效果");
end

修改kmodule.xml配置文件,并添加如下配置:

<kbase name="isLockNoActive" packages="rules.isLockNoActive">
    <ksession name="isLockNoActive"/>
</kbase>

创建RulesLockOnActive.java文件,目录为com.rulesAttributes,其内容为:

package com.rulesAttributes;

import com.pojo.Person;
import org.junit.Test;
import org.kie.api.KieServices;
import org.kie.api.runtime.KieContainer;
import org.kie.api.runtime.KieSession;

public class RulesLockOnActive {
    @Test
    public void testLockOnActive() {
        KieServices kss = KieServices.Factory.get();
        KieContainer kc = kss.getKieClasspathContainer();
        KieSession ks = kc.newKieSession("isLockNoActive");
        Person person = new Person();
        person.setName("张三");
        person.setAge(30);
        person.setClassName("一班");
        ks.insert(person);
        int count = ks.fireAllRules();
        System.out.println("总执行了" + count + "条规则");
        ks.dispose();
    }
}

执行testLockOnActive()方法,结果如图4-7所示。

075-1

图4-7 lock-on-active属性的使用