[rules-users] Drools and Clojure

André Thieme address.good.until.2009.dec.14 at justmail.de
Thu Aug 13 19:20:05 EDT 2009


Mark Proctor schrieb:
> Map( this['c'] == 206 )
> 
> That should work, we do support MVEL syntax for maps and arrays - we 
> just don't suppor method calls, yet.

Hello Mark. I just tested it and it indeed works for me.
Although as I understand it, this will be compiled into an expression
using eval (or it will even be only interpreted).
So, if that is true it can't bring any performance advantage.

The syntax is nothing I worry about. In Clojure, which is a Lisp, I have
macros and can remove any obstacles in the syntax I like. It is trivial
to develop new domain specific languages for rules. So, my rule syntax
for Clojure will look very lispy, and each user is free to change and
extend it. I will also allow the RHS to be written in Clojure code, no
Java needed.


But back to your example: I noticed something very interesting:
when I use the MVEL dialect for the Map lookup, then I get no NPE
anymore when I check in a Map which does *not* have the key I test
for.
So, now I have two versions of my rule:

package droolsandclojure;
import java.util.Map;

rule "Clojure test 1"
   when
    m:Map()
    eval((Integer)m.get("c") == 206)
   then
    System.out.println("Match: " + m);
end

and

package droolsandclojure;
import java.util.Map;

rule "Clojure MVEL test 2"
  dialect "mvel"
   when
    m:Map( this["c"] == 206 )
   then
    System.out.println("Match: " + m);
end


Only one of these two rules is used, not both at the same time.
When I use rule 1 then I can not insert Maps into my session which do
not have a key "c". If I try it and run my code I get a NPE.

When I use rule 2, the MVEL version, this is different. Now I can
insert any Maps and will not get an exception. The rule will simply
just not execute the RHS.

How can rule 1 be changed so that it will not put a constraint on the
objects which are allowed to go into the session without throwing a NPE?


And another interesting thing I noticed:
to both rules I added the line
global String s;
and in the LHS's of both rules I removed the "c" and put s at its place.
Then the first thing I did after creating a session was to
(.setGlobal session "s" "c")

The rule 1 accepted this change. I can use s instead of "c". But there
is still the limitation that I can only insert Maps into the session
which do have the String "c" as key. Otherwise: NPE.
The rule 2 (mvel) however does not accept s as a placeholder. I get:
Exception executing predicate this[s] == 206
[Thrown class org.drools.RuntimeDroolsException]

Any ideas how to get rid of the NPE?
-- 
Lisp is not dead. It’s just the URL that has changed:
http://clojure.org/



More information about the rules-users mailing list