-->

Friday 24 October 2008

Rules engine for NGinn

Today I have added a first working version of a rules engine to NGinn. The source code is in 'NGinn.RippleBoo' folder. 

The RippleBoo engine implements algorighm called 'Ripple Down Rules' - basically it is a binary decision tree. Each rule has simple "if then " structure, where condition is a boolean expression and action is a block of instructions. Apart from that, rule defines what will be the next rule to evaluate by specifying successor rule in positive case and successor rule in negative case. 

When rule condition evals to true, its action is executed and next rule to evaluate will be the 'positive' successor rule. When condition evals to false, action will not be executed and next rule to evaluate will be the 'negative' successor. In effect, we get a binary decision tree, but we don't have to worry about its completeness because it is guaranteed that at least one rule will fire no matter what are the conditions (because the first rule is always true).

Rules were implemented in Boo language using the RhinoDSL library from the Rhino-tools package. Rhino DSL is a library for building DSLs (domain specific languages) in Boo. Here's a link to its author's blog: http://ayende.com/Blog/archive/2007/12/03/Implementing-a-DSL.aspx. The guy has done a great work and many interesting examples of DSLs can be found there.

Below is an example ruleset in my "rule definition language". BTW, it's also a valid Boo script:


Ruleset "MyRules"


rule "R1", "R2", null, V.Counter < 9:
log.Info("AAA");

rule "R2", "R3", null, V.Counter < 8:
log.Info ("R2")

rule "R3", "R4", null, V.Counter < 7:
log.Info ("R3")

rule "R4", null, "R5", V.Counter == 1:
log.Info ("R4")

rule "R5", "R6", null, 1 == 1:
log.Info ("R5: Counter is ${V.Counter}")

rule "R6", "X", null, 2 % 2 == 0:
log.Info ("Rule six: {0}", date.Now)

rule "X", null, null, date.Today > date.Parse('2008-10-11'):
log.Warn("The X Rule!!!")


Sorry for the formatting, I'll fix that in spare time. And a short explanation of what each 'rule' means.
'rule' keyword defines a new rule. It has 5 parameters:
  • rule Id
  • id of positive successor rule (null if there is no successor)
  • id of negative successor rule (null if there is no successor)
  • condition
  • and action (action starts in new line, after last colon - because Boo allows such syntax).

So this entry:

rule "R6", "X", null, 2 % 2 == 0:
log.Info ("Rule six: {0}", date.Now)

means 'define rule R6 that will fire if expression "2 % 2 == 0" evals to true. If it is true, execute action that writes current date to log file. Next rule to evaluate will be "X", or none if the rule doesn't fire'

Currently rules engine is a completely standalone project, but I plan to integrate it into NGinn process engine.It will be used in many places, certainly as a part of process logic, but also for message routing and preprocessing. 

The main problem is that Boo is not yet used in NGinn, except for the RippleBoo project. Currently Script.Net language is the main script environment for NGinn processes and I wouldn't like to mix these two languages. So probably only one is here to stay, and chances are it will be Boo. Script.Net is more elastic and easier to use, but Boo is more mature, better tested and documented. Main issue with Boo is that it's a compiled language, so it will require more effort to integrate it with NGinn engine which is very 'dynamic' in nature. 


3 comments:

gregjaw said...

Od jakiegoś czasu obserwuje jak projekt się rozwija i jestem pod wrażeniem, naprawdę dobra robota.
Tak sobie myślę apropo BOO skoro zacząłeś tego używać czy nie chciałbyś poopowiadać coś więcej o tym języku i całej koncpecji języków domenowych może np. na spotkaniu WG.NET. ??

RG said...

Witam, dzięki za wyrazy uznania. Martwi mnie tylko tempo - jeszcze sporo brakuje zanim pierwszy release NGinn ujrzy swiatło dzienne. Z Boo dopiero się zaprzyjaźniam - wcześniej wybrałem Script.Net jako środowisko skryptowe, ale rozwija się on zbyt powoli jak na moje potrzeby. Boo jest dojrzalszy i ma bardzo ciekawe możliwości, myślę że jeszcze trochę z nim popracuję i bedę w stanie coś ciekawego poopowiadać na WGNecie.
BTW kiedy są spotkania WG.Net?

gregjaw said...

Strona grupy wg.net http://ms-groups.pl/wg.net/default.aspx
warto zasubskrybować rss-a z kalendarza żeby niczego nie przegapić ;)