I have a fairly simple case where I want to check in my rule condition whether an attribute is not null.
rule "only do action if attribute is not null"
when
$fact : Fact(attribute!=null, $attribute : attribute)
then
rulesLogger.debug("Rule fires = " + $attribute);
end
I have tracked this through in debug. A Fact is being inserted with the attribute as null but the rule still fires. The console output is as follows.
Rule fires = null
If I change the condition to attribute==null
then the rule doesn't fire. So it seems to be doing the exact opposite to what I would expect.
We do have a workaround for this using a function but it's a bit ugly and I can't figure out why it doesn't work in the first place.
function Boolean attributeExists(Fact fact)
{
if(fact.getAttribute() == null)
{
return Boolean.FALSE;
}
else
{
return Boolean.TRUE;
}
}
rule "only do action if attribute is not null"
when
$fact : Fact($attribute : attribute)
Boolean(booleanValue == true) from attributeExists($fact)
then
rulesLogger.debug("Rule fires = " + $attribute);
end
EDIT 1
The drools version is 5.3.0.
The fact is loaded via another rule using from
and a service method call. I can't see that the fact is invalid because it prints as I would expect to the console and also the manual workaround with a function works as expected. It's a strange one.
EDIT 2
I've found a better workaround. If I access the attribute using the getter method then the rule behaves as expected. This looks much better than having to write an extra function but it would still be nice to know why this isn't working when using the property name.
rule "only do action if attribute is not null"
when
$fact : Fact(getAttribute()!=null, $attribute : attribute)
then
rulesLogger.debug("Rule fires = " + $attribute);
end
The Fact class is just a boring POJO. It has no superclass other than Object and implements no interfaces. It's not a JPA entity or anything where there might be a proxy or lazy loading.
Try some of these. I'm not sure whether D was possible with 5.3.
rule "only do action if attribute is not null"
when
Fact($att: attribute != null) /* A */
Fact($att: attribute, eval($att != null)) /* B */
Fact($att: attribute, attribute != null) /* C */
Fact($att: attribute, $att != null) /* D */
then
rulesLogger.debug("Rule fires = " + $attribute);
end
An upgrade is highly recommended. 5.5.0 might be an option where no code breaks but failures like this one are avoided.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With