Implementing Refraction with Drools
by magaram
I believe we can inject in Refraction capabilities into Drools Rule Engine
using a simple Agenda Filter. I have tested this with test cases against
JRules and Drools and get similar results. Without the Refraction Agenda
Filter it loops infinitely as expected.
Please try it out and tell me what you think. I believe refraction is a much
needed feature of a forward chaining rule engine for commercial purposes.
Any feedback is deeply appreciated.
Here is what the code looks like
---------Agenda Filter---------------------------
package test;
import java.util.ArrayList;
import java.util.List;
import org.drools.runtime.rule.Activation;
import org.drools.runtime.rule.AgendaFilter;
/**
* This custom agenda filter injects refraction behavior into the rule engine
* @author Mukundan Agaram
*
*/
public class RefractionAgendaFilter implements AgendaFilter {
private List encounteredActivations = new ArrayList();
@Override
public boolean accept(Activation act)
{
//Check for a Refraction
if (encounteredActivations.contains(act))
{
//Remove from encountered activations for future firing
encounteredActivations.remove(act);
//return false so the rule is not selected as part of the refraction
return false;
}
//Otherwise add the rule to check for potential refractions in the future
encounteredActivations.add(act);
//select the rule to be part of the agenda
return true;
}
}
-----------------DRL------------------------
//created on: Jan 15, 2013
package test
dialect "mvel"
rule testFooBar1
salience 100
when
$foo : Foo()
$bar : Bar(y > 0)
then
$foo.setX(($foo.getX() + $bar.getY()));
System.out.println("Fired "+drools.getRule().getName())
update($foo);
end
rule testFooBar2
salience 150
when
$foo : Foo(x >= 6)
then
System.out.println("Fired "+drools.getRule().getName())
end
rule testFooBar3
salience 50
when
$foo : Foo(x >= 7)
then
System.out.println("Fired "+drools.getRule().getName())
end
----------------Runtime execution code--------------------------
package test;
import org.drools.KnowledgeBase;
import org.drools.KnowledgeBaseFactory;
import org.drools.builder.KnowledgeBuilder;
import org.drools.builder.KnowledgeBuilderFactory;
import org.drools.builder.ResourceType;
import org.drools.io.ResourceFactory;
import org.drools.runtime.StatefulKnowledgeSession;
public class TestFooBarMain {
private static void test()
{
KnowledgeBuilder kbuilder = KnowledgeBuilderFactory.newKnowledgeBuilder();
kbuilder.add( ResourceFactory.newClassPathResource( "TestFooBar.drl",
TestFooBarMain.class ),
ResourceType.DRL );
if ( kbuilder.hasErrors() ) {
System.out.println( kbuilder.getErrors().toString() );
}
else
{
System.out.println("DRL parsing - success!");
}
KnowledgeBase kbase = KnowledgeBaseFactory.newKnowledgeBase();
kbase.addKnowledgePackages( kbuilder.getKnowledgePackages() );
StatefulKnowledgeSession ksession = kbase.newStatefulKnowledgeSession();
Foo foo1 = new Foo();
foo1.setX(6);
Bar bar1 = new Bar();
bar1.setY(3);
ksession.insert(foo1);
ksession.insert(bar1);
ksession.fireAllRules(new RefractionAgendaFilter());
}
/**
* @param args
*/
public static void main(String[] args) {
test();
}
}
----------------Facts-------------------------
package test;
public class Foo {
private int x;
private int y;
public int getX() {
return x;
}
public void setX(int x) {
this.x = x;
}
public int getY() {
return y;
}
public void setY(int y) {
this.y = y;
}
}
package test;
public class Bar {
public int getX() {
return x;
}
public void setX(int x) {
this.x = x;
}
public int getY() {
return y;
}
public void setY(int y) {
this.y = y;
}
private int x;
private int y;
}
Thanks,
Mukundan Agaram
--
View this message in context: http://drools.46999.n3.nabble.com/Implementing-Refraction-with-Drools-tp4...
Sent from the Drools: User forum mailing list archive at Nabble.com.
11 years, 8 months
Question about drools-spring in a multi-treaded container (like tomcat).
by Gurvinder Narula1
Hello all,
I've been reading up about drool-spring integration and have put together a simple project that wires together a KnowledgeBase and KnowledgeSession as follows :
<drools:resource id="GroupUnit" type="DRL"
source="file:/Users/drools/drools-spring-test/src/Rules/drls/GroupUnit.drl" />
<drools:resource id="GradeUnit" type="DRL"
source="file:/Users/drools/drools-spring-test/src/Rules/drls/GradeUnit.drl"" />
<drools:resource id="EvaluateUnit" type="DRL"
source="file:/Users/drools/drools-spring-test/src/Rules/drls/EvaluateUnit.drl"" />
<drools:grid-node id="node1" />
<drools:kbase id="kbase1" node="node1">
<drools:resources>
<drools:resource ref="GroupUnit" />
<drools:resource ref="GradeUnit" />
<drools:resource ref="EvaluateUnit" />
</drools:resources>
</drools:kbase>
<drools:ksession id="ksession" type="stateful" kbase="kbase1"
node="node1" />
Then in my Controller call, I 'AutoWire' in the StatefulKnowledgeSession as follows :
@Controller
@RequestMapping( value = "foo" )
final class FooController{
@Autowired
StatefulKnowledgeSession ksession;
@RequestMapping( method = RequestMethod.GET )
@ResponseBody
public String evaluateUnit() {
Unit unit = new Unit("030", "502", "C", "9484", "45", new String[] {},
null);
if (ksession != null) {
ksession.fireAllRules();
ksession.insert(unit);
ksession.fireAllRules();
return "<UnitCategory>" + unit.getUnitCategory() + "</UnitCategory>";
}
else
return "<message> stateful session is null</message>";
}
The main question that I have is that – is this solution thread-safe ? From what I understand of spring is that beans configured without any additional qualifiers are inherently singletons. And when deployed in a multi-theaded container like tomcat, Spring assumes that the beans being severed up a thread-safe. So from I have read is that KnowledeSessions are inherently not thread safe. So putting the 2 together, I leaning towards the assessment that this above solution is NOT thread safe and that if I do want it to be thread safe I should set the StatefulKnowledgeSession to 'prototype' and not leave it as a singleton.
Please let me know if I'm missing anything in my assessment here !
Thanks in advance,
Gurvinder
This message is intended only for the individual or entity to which it is addressed. It may contain privileged, confidential information which is exempt from disclosure under applicable laws. If you are not the intended recipient, please note that you are strictly prohibited from disseminating or distributing this information (other than to the intended recipient) or copying this information. If you have received this communication in error, please notify us immediately by e-mail or by telephone at the above number. Thank you.
11 years, 8 months
Compiled rules differ KnowledgeAgent vs ResourceChangeScanner
by lhorton
Version 5.2.0.Final. I have a DRL file that is loaded into my server using a
change set and Spring configuration. The file loads without error, and I am
able to read the compiled package and print the rule names to confirm they
did load; however, only one of the rules fires. Then I copy (hot-deploy)
the same DRL file to its server-side directory, and the Resource change
Scanner picks it up and reloads it. After reload, all the expected rules
execute.
My guess is that the Spring/KnowledgeAgent compilation is different than the
one done via the resource change scanner. Has anyone else seen this
behavior? Any suggestions for further trouble shooting?
I can attach the change set, spring config and drl file if needed.
--
View this message in context: http://drools.46999.n3.nabble.com/Compiled-rules-differ-KnowledgeAgent-vs...
Sent from the Drools: User forum mailing list archive at Nabble.com.
11 years, 9 months
Unmarshall large session fails
by Magnus Vojbacke
I'm trying to unmarshal a knowledge session that has been persisted to file, but I get the following exception:
Stack Trace:
com.google.protobuf.InvalidProtocolBufferException: Protocol message was too large. May be malicious. Use CodedInputStream.setSizeLimit() to increase the size limit.
at com.google.protobuf.InvalidProtocolBufferException.sizeLimitExceeded:89
at com.google.protobuf.CodedInputStream.refillBuffer:720
at com.google.protobuf.CodedInputStream.isAtEnd:666
at com.google.protobuf.CodedInputStream.readTag:99
at org.drools.marshalling.impl.ProtobufMessages$Header$Builder.mergeFrom:967
at org.drools.marshalling.impl.ProtobufMessages$Header$Builder.mergeFrom:773
at com.google.protobuf.AbstractMessageLite$Builder.mergeFrom:212
at com.google.protobuf.AbstractMessage$Builder.mergeFrom:746
at org.drools.marshalling.impl.ProtobufMessages$Header.parseFrom:724
at org.drools.marshalling.impl.PersisterHelper.readFromStreamWithHeader:234
at org.drools.marshalling.impl.ProtobufInputMarshaller.loadAndParseSession:217
at org.drools.marshalling.impl.ProtobufInputMarshaller.readSession:107
at org.drools.marshalling.impl.ProtobufMarshaller.unmarshall:143
The session consists of >1M facts, and the file is ~167 MB in size.
While Googling, I stumbled upon the recommendation to run CodedInputStream.resetSizeCounter() inbetween deserializing messages. Is this a fix that could be implemented in Drools?
Is there any way of configuring or parameterizing the unmarshalling size limit used by Drools?
11 years, 9 months
continuous integration of rule assets via jenkins to guvnor?
by Cedric Hurst
I'd like to get a quick sanity check on best practices...
I'm working on a project where, by policy, all assets (including drl's, bpmn
files, etc) must be built, tested and packaged by a Jenkins server. Rule
assets are structured within a project that also includes non-rule assets.
As is quite common, the primary system of record for these assets is an SCM
like svn or git, and that's what our Jenkins box talks to.
However, for the rule stuff specifically, we're also using Guvnor's
drools-repository to package the assets into a knowledge base, which is
referenced jBPM's process engine in the runtime. The plan is to have
several Guvnor environments running with parity to development, QA, UAT and
production setups. However, we're having a very hard time figuring out how
best to sync our rule assets to these various repositories as part of an
automated release.
To the best of my understanding, rule assets are deployed to a Guvnor
instance file-by-file via WebDAV. One can also upload JARs for POJOs, but
DRLs, BPMN, DSL files need to be synced individually. Is this the case?
And, if so, how do other groups handle continuous integration and deployment
of assets coming from external SCMs?
Btw, I came across aware of a Maven plugin which seems to do this sort of
piece-by-piece deployment:
https://github.com/awaterma/drools-guvnor-plugin
So we could certainly port this sort of functionality to our own build
toolchain, but it seems like a lot of work so I'm hoping for a better way.
--
View this message in context: http://drools.46999.n3.nabble.com/continuous-integration-of-rule-assets-v...
Sent from the Drools: User forum mailing list archive at Nabble.com.
11 years, 9 months
Drools Clips
by Grant Rettke
Hi,
Anyone using or have used Drools Clips before? If so, what is your
opinion of it? If not, why not?
I'm pretty curious about it and wanted to start here before pinging
the dev list on who is maintaining it (nor not).
Best wishes,
--
Grant Rettke | ACM, AMA, COG, IEEE
grettke(a)acm.org | http://www.wisdomandwonder.com/
Wisdom begins in wonder.
((λ (x) (x x)) (λ (x) (x x)))
11 years, 9 months
Is it posibble to keep two date formats in drools like 'dd-MMM-yyyy' and 'dd-MMM-yyyy HH:mm'
by richie
Hi,
The default date format in drools is 'dd-MMM-yyyy', but in the definition of
rule attribute date-effective, it says it contain a date and time
definition, so if I set date-effective to "30-Jan-2013 08:00", then the time
set in date-effective will be ignored, so I changed the date format to
'dd-MMM-yyyy HH:mm', now the effective date works correctly, but then we got
problem here, if user input a date like "30-Jan-2013" the drools will failed
to execute, so must force user to input a date like this "30-Jan-2013
00:00", this is not user friendly and the string "00:00" is meaningless.
What I want to know is, if it's possible to keep this two formats both?
Thanks.
--
View this message in context: http://drools.46999.n3.nabble.com/Is-it-posibble-to-keep-two-date-formats...
Sent from the Drools: User forum mailing list archive at Nabble.com.
11 years, 9 months
Non short circuit ANDing
by mp
Hi,
I need to use non-short circuit ANDing (&) for my rules.
However, for a rules like (conditionA & conditionB) I get the following
error:
"Predicate 'conditionA & conditionB' must be a Boolean expression"
(conditionA && conditionB) works fine. But it short circuits the conditions.
Any ideas as to what I could be doing wrong or how I can ensure that
condition2 is evaluated irrespective of whether condition1 is true or false?
Thanks.
--
View this message in context: http://drools.46999.n3.nabble.com/Non-short-circuit-ANDing-tp4021928.html
Sent from the Drools: User forum mailing list archive at Nabble.com.
11 years, 9 months