Tuesday, May 27, 2008

Rule Engine Tricks

While working with Oracle Business Rules I found some tricks:

1) Enable Logging

Provide following properties in decisionservice.desc file in your bpel process:

<properties>
<property name="watchRules">true</property>
<property name="watchActivations">true</property>
<property name="watchFacts">true</property>
<property name="watchCompilations">true</property>
</properties>
You have to provide this right in <ruleEngineProvider> and right after the <repository> tag. If you have worked with Rule Engine SDK, then you may realize that it is not really providing all debugging information which you can see via ruleSession.executeFunction("watchFacts"). Well, be happy with what it provides, it is good enough. If you want to look at more information then look at my article on Custom Decision Service.

2) Additional Libraries

If your BPEL process is having decision service and your Rule is calling external Java program, then you will need to include those Jar files in to your path. The directory would be: decisionservices\DecisionService\war\WEB-INF\lib under your BPEL root directory.

3) RuleSet invoking other RuleSets

Hmm, this was cool one. If you have ruleSet and inside that ruleSet you are calling another ruleSet via pushRuleSet functioin, it just works fine in RuleAuthor, but decision service interface doesn't let you execute it. It throws exception something like "Rule Set xyz is undefined". Well, again if you are familiar with how Rule SDK works, then you can guess why this is the case. Developer of decision service probably loading only one rule set and that is what causing the issue.

Resolution: Rule function is quite different, if you execute rule function and if rule function calls multiple RuleSet that just works fine. When I created my custom decision service, I did the same for both RuleSet and Rule Functions. Therefore, for out-of-the box rule decision service, we have to create function interface in order to interact with multiple rule-sets.

4) Deploying to home container

As shown in below diagram, if you specify oc4j_soa while deploying decision service, it just works fine. If you specify home during creating Jdeveloper connection while deploying Decision service it throws following exception. Therefore, we have to use oc4j_soa while making Jdeveloper AS/Integration server connection.

[deployDecisionServices]
[deployDecisionServices] 08/05/14 18:20:26 Notification ==>application : rules_default_TestBPEL1_1_0_DecisionService is in failed state

[deployDecisionServices]

[deployDecisionServices] Exception in thread "ConfigurableThreadImpl::" java.lang.NoClassDefFoundError: oracle/classloader/util/LocalizedText
[deployDecisionServices] at com.evermind.server.rmi.RMICall.EXCEPTION_ORIGINATES_FROM_THE_REMOTE_SERVER(RMICall.java:109)
[deployDecisionServices] at com.evermind.server.rmi.RMICall.throwRecordedException(RMICall.java:125)
[deployDecisionServices] at com.evermind.server.rmi.RMIClientConnection.obtainRemoteMethodResponse(RMIClientConnection.java:517)
[deployDecisionServices] at com.evermind.server.rmi.RMIClientConnection.invokeMethod(RMIClientConnection.java:461)
[deployDecisionServices] at com.evermind.server.rmi.RemoteInvocationHandler.invoke(RemoteInvocationHandler.java:63)
[deployDecisionServices] at com.evermind.server.rmi.RecoverableRemoteInvocationHandler.invoke(RecoverableRemoteInvocationHandler.java:28)
[deployDecisionServices] at com.evermind.server.ejb.StatefulSessionRemoteInvocationHandler.invoke(StatefulSessionRemoteInvocationHandler.java:31)
[deployDecisionServices] at __Proxy2.getEvents(Unknown Source)
[deployDecisionServices] at oracle.oc4j.admin.jmx.client.MBeanServerEjbRemoteSynchronizer.getEvents(MBeanServerEjbRemoteSynchronizer.java:530)
[deployDecisionServices] at oracle.oc4j.admin.jmx.client.CoreRemoteMBeanServer.getEvents(CoreRemoteMBeanServer.java:319)
[deployDecisionServices] at oracle.oc4j.admin.jmx.client.EventManager.run(EventManager.java:217)
[deployDecisionServices] at oracle.oc4j.admin.jmx.client.ThreadPool$ConfigurableThreadImpl.run(ThreadPool.java:303)

5 comments:

Unknown said...

Really very helpful tips. I was also getting error Exception in thread "ConfigurableThreadImpl::" java.lang.NoClassDefFoundError and it got resoved by setting oc4j instance name as "oc4j_soa" in application server connection

cheers !
deb

Unknown said...

This article saved the day! Thank you. For complex rules (hundreds or thousands of combinations), how do you use it? Say, the decision is based on one of many countries and one of hundreds of products?

Chintan Shah said...

Glad to know. Rule engine and Rete algorithm is designed for that. What is your specific question?

Anonymous said...

I think to enable logging you also need to add the same text to each decision service's xml config file in
BPEL_Process/decisionservices/DecisionService/war/WEB-INF/classes/decisionservices.xml

I don't think editing the toplevel decisionservices.decs file does this.

Nikhilesh Chitnis said...

thanks , this was very helpful!!!