Rule Engine

Rule Execution Logic with OpenRulesEngine

 

   
OpenRulesEngine

Execution Logic
    -
Relationships between Rules Inside Decision Tables
    -
Processing Multi-Hit and Single-Hit Decision Tables
Automatic Rules Updates
OpenRules Implementation of JSR-94

Rule Engine in Multi-Threaded Environments
Engine Performance and Scalability

OpenRules® include a rule engine known as "OpenRulesEngine" that is used to execute different rule sets and methods specified in Excel files using application-specific business objects.  OpenRulesEngine can be invoked from any Java application using a simple Java OpenRules® API or the standard JSR-94 interface.

Rules Execution Logic 

When OpenRulesEngine is created it downloads the main xls-file and all other files using the "include" properties in the Environment tables.  The engine executes the rules starting with the main method defined for this particular engine run.

Relationships between Rules Inside Decision Tables

The OpenRules® execution logic inside decision tables is very intuitive. OpenRules does not assume any implicit ("magic") execution logic and executes rules in the order specified by a rule designer.  All rules are executed one-by-one in the order they are placed in the rules table. There is a simple rule that governs rules execution inside a rules table:

The preceding rules are evaluated and executed first!

For standard vertical decision tables, all rules (rows) are executed in top-to-bottom order. For horizontal decision tables, all rules (columns) are executed in left-to-right order.

The execution logic of one rule (one row in the decision table) is as follows:

            IF ALL conditions are satisfied THEN execute ALL actions.

If at least one condition is violated (the proper code evaluation produces false), all other conditions in the same rule (row) are ignored and are not evaluated. 

The absence of a parameter in a condition cell means the condition is always true.  Actions are executed only if ALL conditions in the same row evaluated to be true.  Action cells with no parameters are ignored.

Processing Multi-Hit and Single-Hit Decision Tables

Let's consider how OpenRulesEngine executes very simple rules that defines a salutation "Mr.", "Mrs.", or "Ms." based on a customer's gender and marital status:

Rules void defineSalutation(Customer customer, Response response)
Gender Marital Status Set Salutation
Male   Mr.
Female Married Mrs.
Female Single Ms.

If a customer is Married Female the conditions of the second rules are satisfied and the salutation "Mrs." will be selected.  This is only a business view of the rules table.  The complete view including the hidden implementation details ("Java snippets") are presented below:

Rules void defineSalutation(Customer customer, Response response)
C1 C2 A1
customer.gender.equals(gender) customer.maritalStatus.equals(status) response.map.put("salutation",salutation); 
String gender String status String salutation
Gender Marital Status Set Salutation
Male   Mr.
Female Married Mrs.
Female Single Ms.

OpenRulesEngine will execute rules (all 3 "white" rows) one after another. For each row if conditions C1 and C2 are satisfied then the action A1 will be executed with the selected "salutation".

Please note that for this table conditions for all 3 rules will be examined before executing any actions. This is an example of so-called "multi-hit" rules table that executes all rules it may "hit". We may add one more rules at the very end of this table:

Rules void defineSalutation(Customer customer, Response response)
Gender Marital Status Set Salutation
Male   Mr.
Female Married Mrs.
Female Single Ms.
    ???

In this case, after executing the second rule OpenRulesEngine will also execute the new 4th rule and will override a salutation "Mrs." with "???".  It is obviously not good.  However, sometimes it may have a positive effect to avoid undefined values in cases when our previous rules did not cover all possible situations. What if our customer is a Divorced Female?!

How to avoid this multi-hit effect? We want to produce "???" only when no other rules were satisfied.  To achieve this you may use so-called "single-hit" tables that are specified by putting any return type except of "void" after the keyword "Rules".  The following is an example of a single-hit rules table that will do exactly what we need:

Rules String defineSalutation(Customer customer, Response response)
Gender Marital Status Set Salutation
Male   Mr.
Female Married Mrs.
Female Single Ms.
    ???

Another positive effect of such "single-hitness" may be felt for large tables with say 1000 rows: if OpenRulesEngine hits a rule #10 it would not bother to check the validity of the remaining 990 rules.

Having rules tables with a return value may also simplify your interface. For example, we do not really need a special object Response in which we used to write the defined salutation. Our simplified rules table may look like follows:

Rules String defineSalutation(Customer customer)
C1 C2 A1
customer.gender.equals(gender) customer.maritalStatus.equals(status) return salutation; 
String gender String status String salutation
Gender Marital Status Set Salutation
Male   Mr.
Female Married Mrs.
Female Single Ms.
    ???

Here is an example of Java code that creates an OpenRulesEngine and executes the latest rules table "defineSalutation":


public static void main(String[] args) {
    String fileName = "file:rules/main/HelloCustomer.xls";
    OpenRulesEngine engine = new OpenRulesEngine(fileName);
    Customer customer = new Customer();
    customer.setName("Robinson");
    customer.setGender("Female");
    customer.setMaritalStatus("Married");
    String salutation = (String) engine.run("defineSalutation", customer);
    System.out.println(salutation);
}
 

You can learn more about OpenRulesEngine API from the User's Guide.  The standard OpenRules's installation contains many examples that demonstrate how to invoke OpenRulesEngine from regular Java applications (see projects HelloJava, HelloJsr94, HelloXMLCustomer) as long as from web-based applications (see projects HelloJsp, HelloForms, and HelloWS). 

Relationships Between Rule Tables

In most practical cases business rules are not located in one file or in a single rule set, but rather are represented as a hierarchy of inter-related rules tables located in different files and directories - see Business Rules Repository. When you run OpenRulesEngine, you are executing a method from its main xls-file.  Frequently, this method defines an execution logic that uses the conditions and sequences of rules presented in other rules tables and methods.  In trivial cases, the rule engine can execute a rule table directly from a Java program. Typically, the main method executes a launcher that is a simple method specifying the execution sequence for different rules tables.

Because OpenRules interprets rules tables as regular methods, designers of rules frequently create special "processing flow" decision tables to specify the conditions under which different rules should be executed.  See examples of processing flow rules in such sample projects as Loan2 and LoanDynamics.  One way or another, a rule designer needs to explicitly specify the execution logic for different rule sets.

Dynamic Rules Updates

If a business rule is changed, OpenRulesEngine automatically reloads the rule when necessary.  Before any engine's run, OpenRulesEngine checks to determine if the main Excel file associated with this instance of the engine has been changed.  Actually, OpenRulesEngine looks at the latest modification dates of the file xlsMainFileName.  If it has been modified, OpenRulesEngine re-initializes itself and reloads all related Excel files.

OpenRules Implementation of JSR-94

OpenRules provides a reference implementation of the JSR94 standard known as Java Rule Engine API (see http://www.jcp.org/en/jsr/detail?id=94).  The standard OpenRules installation includes the following projects:

JSR-94 Project  Description
lib.jsr94 This project contains the standard jsr94-1.0 library
com.openrules.jsr94 This is an OpenRules's reference implementation for the JSR94 standard and includes the source code. It uses OpenRulesEngine to implement RuleExecutionSet
HelloJsr94 This is an example of using JSR94 for simple rules that generate customized greetings
HelloJspJsr94 HHelloJspJsr94 is similar to HelloJsp but uses the OpenRules JSR-94 Interface to create and run OpenRulesEngine for a web application.

Rule Engine in Multi-Threaded Environments

OpenRulesEngine is thread-safe and works very efficiently in multi-threaded environments supporting real parallelism. Contrary to many other rule engines, OpenRules' rule engine is stateless. It allows a user to create only one instance of the class OpenRulesEngine, and then share this instance between different threads - there are no needs to create a pool of rule engines. A user may also initialize the engine with application data common for all threads, and attach this data directly to the engine using the methods setAttachment(Object attachment). Different threads will receive this instance of the rule engine as a parameter, and will safely run various rules in parallel using the same engine.

OpenRules® installation includes an example "HelloFromThreads" that demonstrates how to organize a parallel execution of the same OpenRulesEngine's instance in different threads and how to measure their performance.

Engine Performance and Scalability

OpenRules® as a component of complex real-world applications has a proven record of high performance and scalability.  These days most Rule Engines demonstrate a high level of performance, but OpenRules® is frequently chosen over major commercial BR products because of the following differentiators:

  • High performance
  • High scalability for multi-user environments
  • Efficient use of memory.

Consider the results cited in a a report OpenRules® received from a major international bank.  The bank created a series of performance and scalability tests before selecting OpenRules® as the BR product of choice.  They demonstrated that OpenRules® scales to more than 300 concurrent users on a hyper-threaded Xeon box.  Each concurrent user executed its rules 10,000 times with the following results:

Note that initially OpenRulesEngine takes more time to download all rules into the memory. However, there is no need to create a pool of concurrent rule engines: being stateless, the same instance of OpenRulesEngine can handle different concurrent requests.

 

 

 

Welcome
Welcome
Business Rules Repository Decisions Top-Down Semantics In Concert Business Analyst Decisioning
Welcome
themed object
Business Rules - Time to Excel
Bookmark and Share