
Ask HN: Rules Engines for enforcing business rules - adelevie
Have any of you had any experience using any Rules Engine libraries? I'm working on a game and I'm trying to separate rule logic from application logic to let me easily test variations of game rules.<p>The game is built in Rails, but I'd like to hear about experience with any language.<p>Things I'm interested in:
-How the rules logically fit into the rest of the application (especially with MVC apps)
-How the rules are stored (ie, in db table, yaml file, ruby file, etc)
-Schema
-Anything else!<p>Thanks!
======
tansey
I've used Drools: <http://www.jboss.org/drools/>

It's a deductive rules engine for Java, so you give it some objects with state
and apply a set of first-order(ish) logic rules to them, in an if-then kind of
form. You can give rules different precedence levels to create a sort of
cascading effect.

Rules are stored in plain text, but they're read in and compiled into memory
for efficient execution. Defining your own DSL spec is a breeze. Your rules
are executed in the rest of the application with a few simple method calls. It
integrates with Java in a really slick way, so you can work with POJOs and
your rules operate on them.

It's a pretty cool DSL creator, actually. I used it in a research project by
integrating it with the Eclipse JDT and creating a DSL for source code
manipulation. Then I hooked it up to a little inference algorithm we created,
and the result was a plug-in which could take a before and after piece of
code, analyze the difference between the two (specifically in the case of
adding annotations to legacy code), and generate a set of Drools rules that
could automatically migrate similar legacy classes. See page 5 of our paper
for an example of how our DSL rule base looked:
<http://people.cs.vt.edu/~tilevich/papers/rosemari-oopsla.pdf>

------
stcredzero
I was just involved in a port of a Rules Engine for a top US bank. The engine
was written in Smalltalk. To make a very long story short, most of the rule
components had a 1-to-1 translation to a Smalltalk code block (or collection
of blocks), which was then compiled and executed. This would be a great way to
implement a Rules engine in Ruby. Define a very simple language, all of whose
components have a 1-to-1 mapping to a small subset of Ruby. Generate the Ruby
code and compile it. If your subset is kept simple, you can easily use a
compiler-compiler or just hand code a top-down parser. With a strict subset of
Ruby, you could also make everything a method and get the s-expression for
each method instead of parsing it yourself, but this makes it less
straightforward to restrict your subset of Ruby to exactly what you want. (You
may want such restrictions if you have non-programmers maintaing the rules.)

The framework I was working with also had components where arbitrary Smalltalk
code could be used. In retrospect, this is a bad idea.

All of the rule components were stored as strings with bits of metadata using
an Object Relational framework.

Also note that the entire Rules repository only amounted to about 5MB of
compressed data. I suspect this isn't unusually small. Rules can be cached
locally with the system only checking for updates.

(EDIT: DO NOT naively think you can use a bunch of regexps instead of a parser
of some kind. You can make this work, but it's a hack. If you don't know
enough about automata and languages to know why this wouldn't work, you
probably don't know enough to be certain about the results of such a hack.)

------
adelevie
Hey thanks for all your answers to far! Here's what I've been working with
(sorry if this only makes sense to Rails folks--ask me about a certain
section, and I'll try to clarify to non-Rails people as best I can): -A ruby
gem called rools -sample rule:

    
    
      rule 'foo' do
        parameter SomeObject
        condition { some_object.attribute == 'something_else' }
        consequence { some_object.change_state! }
      end

-inside of the application_controller, I run a before_filter with this code:
    
    
      rules = Rools:RuleSet.new 'path/to/file/that/has/rules.rb'
      so = SomeObject.find(:first)
      rules.assert so

~~~
tansey
That's pretty much how Drools works as well. :)

I'm going to guess that the rools gem was inspired by Drools, since the Drools
project is much older.

~~~
adelevie
And the name: Drools - D = rools

------
caffeine
Use Prolog.

~~~
adelevie
I have to stick with Ruby for this one. Thanks though!

~~~
caffeine
Maybe <http://github.com/preston/ruby-prolog> then?

Edit: or <http://eigenclass.org/hiki.rb?tiny+prolog+in+ruby> (not sure if
they're the same..)

