Search code examples
javadrools

Drools: simple rule executed twice in a stateless session


I have created a simple Drools project. Everything works ok, except for the fact I get my rule executed twice, instead of once.

Please check my rule:

package rules

rule "age and type match"
   when
       $droolsIntro : rules.DroolsInstruction( type == "Manager" ) && rules.DroolsInstruction( age >= 20 )
   then
       System.out.println("age and type match");
       System.out.println($droolsIntro.introduceYourself());
   end

Please check the code:

List<DroolsInstruction> facts = new ArrayList<DroolsInstruction>();
DroolsInstruction object3 = new DroolsInstruction("Manager", 25);
DroolsInstruction object4 = new DroolsInstruction("Policeman", 31);
facts.add(object3);
facts.add(object4);
DroolsDynamicJar drools = new DroolsDynamicJar();
StatelessKieSession kSession = drools.getStatelessSessionWithJar();
kSession.execute(facts);

And here is output, which shows that the rule was executed twice for the same object:

age and type match Manager, 25, false

age and type match Manager, 25, false

Why?


Solution

  • This pattern

    DroolsInstruction( type == "Manager" )
    DroolsInstruction( age >= 20 )
    

    matches an entity "Manager" and one of age >= 20, but doesn't make any constraints as to their relationship. Thus, a Manager of age 25 matches the first pattern and the second pattern: fire! But the same Manager matches the first pattern and an old policeman matches the second pattern: fire again!

    If you want to look for old managers, you better write

    DroolsInstruction( type == "Manager", age >= 20 )
    

    although the circumstantial (and not recommended)

    $di1: DroolsInstruction( type == "Manager" )                                            
    $di2: DroolsInstruction( this == $di1, age >= 20 )
    

    would also work.