On 19/07/2011 06:07, Marc Heinz wrote:
Hello everyone,
I need some enlightening about Drools "dynamic facts" (a term used in the
documentation, for facts that could be updated from outside the rule
engine).
The current documentation always list the "insert" method of a
StatefulKnowledgeSession being able to take an additional boolean
argument, stating that the corresponding fact supports the
PropertyChangeSupport related methods.
However, it seems that this method do not exists anymore for already some
time now...
After googling for a while it appears that some possible workaround were
modifyInsert (apparently removed from the API as well) and the
@propertyChangeSupport meta-data annotation, but I didn't manage to make
it work (actually I wasn't able to find any reference from it in the API,
so I guess that it is also not available anymore).
@propertyChangeSupport is the correct way to use property change
listeners. It is used on type declarations. The boolean approach is
deprecated.
Personally I don't like the feature and I consider it an
anti-pattern. the reason being is every time you change a field it's
going to notify the engine causing it to evaluate that change. you
change 3 fields you end up with triple the amount of work, then if
you changed the fields and then did a single update. Inside of the
engine the consequence's modify block does exactly that. It allows
you to block together 1..n setters and notify the engine on
completion.
Lookingat docs, it's in the New and Noteworthy. Seems it wasn't
copied into the main documentation though, we'll get that done:
http://docs.jboss.org/drools/release/5.2.0.Final/droolsjbpm-introduction-docs/html_single/index.html
Facts that implement support for property changes
as defined in the Javabean(tm) spec, now can be annotated so
that the engine register itself to listen for changes on fact
properties. The boolean parameter that was used in the insert()
method in the Drools 4 API is deprecated and does not exist in
the drools-api module.
Mark
So, this left us with the "session.update" method. Which seems to works
great, except that it will invalidate the whole fact into the working
memory, even if only some of the fields were changed.
Is this some current limitation of Drools? Does it have something to do
with those "Shadows Fact"? (that would be somehow immutable?)
When you notify the engine of a change, the entire fact and all it's
fields are evaluated.
If we effectively can't fire update targeted to some specific fields, this
has probably some big implications on performances (even for simple fact
with only a few fields). It would also means that one should always aim at
the finest granularity for better performances, by somehow "flattening"
the object structure into the knowledge base (which in turn could make
complicated to reuse those same Pojo in other frameworks, such as
hibernate).
This is the behaviour of most rule engines. Jess recently added a
feature for this use case called "slot specific". We've discussed
designs for this in Drools and hope to add it some time in the
future.
http://blog.athico.com/2010/07/slot-specific-and-refraction.html
Mark