Prezi

Present Remotely

Send the link below via email or IM

Copy

Present to your audience

Start remote presentation

  • Invited audience members will follow you as you navigate and present
  • People invited to a presentation do not need a Prezi account
  • This link expires 10 minutes after you close the presentation
  • A maximum of 30 users can follow your presentation
  • Learn more about this feature in the manual

Do you really want to delete this prezi?

Neither you, nor the coeditors you shared it with will be able to recover it again.

DeleteCancel

Make your likes visible on Facebook?

Connect your Facebook account to Prezi and let your likes appear on your timeline.
You can change this under Settings & Account at any time.

No, thanks

Drools - Grasshoppa to Guru

Let's talk about what rules are, and more importantly, what they can (and can't!) do for you. We'll take a look at what makes Drools tick, brass tacks syntax, commonly used features and the modules of the Drools system.
by Jeremy Ary on 12 April 2013

Comments (0)

Please log in to add your comment.

Report abuse

Transcript of Drools - Grasshoppa to Guru

Techie answer: Benefits of a rules engine? Drools - Grasshoppa to Guru Separation of logic from data
we don't know how to make more coffee or clean a mug, only that we should; change procedure without altering logic Example Use Case - The Sammich Shop: Let's allow customers a discount of 10% on purchases over $15. Let's also give 15% off purchases over $25. Finally, we'll allow a combo deal discount of an additional 5% off purchases containing two or more sammiches and at least one drink. Load 'em up! Do something useful with our rules: @Test
public void testRules() {

StatefulKnowledgeSession session = null;

try {
KnowledgeBuilder builder = KnowledgeBuilderFactory.newKnowledgeBuilder();
builder.add(ResourceFactory.newClassPathResource("discountRules.drl"), ResourceType.DRL);
if (builder.hasErrors()) {
throw new RuntimeException(builder.getErrors().toString());
}

KnowledgeBase knowledgeBase = KnowledgeBaseFactory.newKnowledgeBase();
knowledgeBase.addKnowledgePackages(builder.getKnowledgePackages());

session = knowledgeBase.newStatefulKnowledgeSession();

// purchase > $15 and <= $25
Purchase firstPurchase = new Purchase(new BigDecimal("16"), 1, false);
FactHandle purchaseFact = session.insert(firstPurchase);
session.fireAllRules();

} catch(Throwable t) {
t.printStackTrace();
} finally {
if (session != null) {
session.dispose();
}
}
} Our rules in Drools Rule Language (DRL): rule "purchase over 15 and less than 25 dollars"
when
$p : Purchase ( total > 15, total <= 25 )
then
$p.setDiscount(0.10);
System.out.println("Level 1 discount: " + $p.getDiscount());
end Modules of Drools: jBPM (origins in Drools Flow):
Business Process Management, or BPM, is a means of describing some process that occurs within your organization as a series of steps involved, how those steps are connected, and who is involved in performing them. jBPM, which is based on the BPMN 2.0 specification (a standard for graphical representation), serves as a tool for describing such processes in a flowchart format Drools - Grasshoppa to Guru So what is Drools?


Github: http://github.com/jeremyary
LinkedIn: http://linkedin.com/in/jeremyary
Email: jeremy.ary@gmail.com
Twitter: @jeremyary Documentation: http://jboss.org/drools/documentation
IRC: #drools @ freenode Testing & Debugging Rules: Working Memory
whenever we insert, modify, or retract a fact, we're adding, changing, or removing the instance within the working memory. You can think of working memory as the knowledge container; a place where all our facts reside. Drools, part of the JBoss Enterprise BRMS product since federating in 2005, is a Business Rule Management System (BRMS) and rules engine written in Java which implements and extends the Rete pattern-matching algorithm within a rules engine capable of both forward and backward-chaining inference. Plain English: Drools is a collection of tools which allow us to separate and reason over logic and data found within business processes. Logic, or rules in our case, are pieces of knowledge often expressed as, "When some conditions occur, then do some tasks." Facts (data) are the objects that drive the decision process for us. When your mug is dirty, then go clean it.
When your mug is clean, then go check for coffee.
When the pot is full, then pour yourself a cup and return to your desk.
When the pot is empty, then mumble about coworkers and make more. Example: Useful when... Not so much when... problem too complex for traditional coding approaches
no fragile implementations ("big-if") required training of rule writers and developers kills budget or time allotment domain knowledge available, but non-technical
rules provide a nice documenting medium
DSL's, guided editors, etc. logic changes often over time problem not yet fully understood
allows for an iterative approach to the solution
helps when you need to "pull teeth" from end users small systems or one-off solutions that are likely to be discarded
beware the optimal, small solutions that tend to grow in complexity to meet needs! logic doesn't really change that often centralized business process knowledge source
explain a process, transfer responsibilities, and prevention of tribal knowledge Integration Other Dependency Mgmt. Add
Jars to
Project Maven
(central) Eclipse
Plugin <dependency>
<groupId>org.drools</groupId>
<artifactId>drools-compiler</artifactId>
<version>5.4.0.Final</version>
</dependency> [TRANSITIVELY PULLED]
<dependency>
<groupId>org.drools</groupId>
<artifactId>drools-core</artifactId>
<version>5.4.0.Final</version>
</dependency>

[TRANSITIVELY PULLED]
<dependency>
<groupId>org.drools</groupId>
<artifactId>knowledge-api</artifactId>
<version>5.4.0.Final</version>
</dependency> Drools Plugin: Auto-complete
syntax highlighting
debugging features Requires GEF:
http://download.eclipse.org/tools/gef/updates/releases/ Plugin:
http://jboss.org/drools/downloads.html
Look for "Eclipse Update Site" When Purchase > $15, then provide a 10% discount.
When Purchase > $25, then provide a 15% discount.
When Purchase has >= 2 sammiches and >= 1 drink, then provide an addition 5% discount. So what facts do we need to know about?
The Purchase - we need to know how much it costs, what it consisted of, and the discount total. public class Purchase {

private BigDecimal total;

private int sammichCount;

private boolean drinkIncluded;

private double discount; public Purchase(BigDecimal total, int sammichCount, boolean drinkIncluded) {
this.total = total;
this.sammichCount = sammichCount;
this.drinkIncluded = drinkIncluded;
this.discount = 0;
} public BigDecimal getTotal() {
return total;
}

public void setTotal(BigDecimal total) {
this.total = total;
}

public int getSammichCount() {
return sammichCount;
}

public void setSammichCount(int sammichCount) {
this.sammichCount = sammichCount;
}

public boolean isDrinkIncluded() {
return drinkIncluded;
}

public void setDrinkIncluded(boolean drinkIncluded) {
this.drinkIncluded = drinkIncluded;
}

public double getDiscount() {
return discount;
}

public void setDiscount(double discount) {
this.discount = discount;
}
} (Plain Old Java Object) POJO rule "purchase contains combo" salience -1
when
$p : Purchase ( drinkIncluded, sammichCount >= 2 )
then
$p.setDiscount($p.getDiscount() + 0.05);
System.out.println("Combo discount: " + $p.getDiscount());
end rule "purchase over 25 dollars"
when
$p : Purchase ( total > 25 )
then
$p.setDiscount(0.15);
System.out.println("Level 2 discount: " + $p.getDiscount());
end Highlighting:
Some keywords and operators to notice
Variables
when / then / end construct Some quick notes:
MVEL (MVFLEX Expression Language)
Condition vs. consequence
Patterns of a condition & property access
Java-esque code within consequences package org.tacoshop

import org.tacoshop.model.Purchase

global int comboCount

// hey here's a rule!
rule "example rule"
when
$p : Purchase ( sammichCount >= comboCount, ( sammichCount % 2 == 0 ) )
then
/* this consequence is pretty simple,
but let's give it a comment anyways */
$p.setDiscount(addDiscount($p, 0.15));
end

function double addDiscount(Purchase p, double discount) {
return (p.getDiscount + discount);
} package org.tacoshop

import org.tacoshop.model.Purchase

global int comboCount

// hey here's a rule!
rule "example rule"
when
$p : Purchase ( sammichCount >= comboCount, ( sammichCount % 2 == 0 ) )
then
/* this consequence is pretty simple,
but let's give it a comment anyways */
$p.setDiscount(addDiscount($p, 0.15));
end

function double addDiscount(Purchase p, double discount) {
return (p.getDiscount + discount);
} Sample Rule File: package declaration like Java functions imports like Java evaluative boolean statement single-, multi-line commenting global variable ... no, it's not a bad word What haven't we seen yet? rule attributes (not shown)
no-loop
salience
dialect Sample Rule File: && - both booleans must be true. Previously we've used && implicitly by including multiple property evaluations in a comma-separated series

|| - one of 2 booleans must be true. Note that when using && or || on a single property, the syntax can be shorted

( ) - we can form more complex patterns using parentheses

this - allows us to reference a fact within the condition of the pattern, which, among other uses, will disallow the same fact from satisfying multiple conditions

in - check if a value exists within a comma-separated list of values to potentially match (can be paired with not)

matches - match against a regular expression (can be paired with not)

memberOf - check if a field exists within a collection (can be paired with not)

contains - much like memberOf, but allows us to check the inverse - that a collection field contains a value (can be paired with not)

common operators that are likely familiar from Java
==, !=, >, >=,<, <= Operators for Constraints Conditional Elements for Patterns exists - at least one matching fact exists

not - no matching facts exist

from - allows access to nested collections

collect - allows evaluation of multiple facts within the system as a group:

accumulate - functions similarly to collect in that we're grouping facts, but also allows for manipulation on the collection prior to returning the result

eval - allows for execution of any block that returns a boolean value. Please note that evals are not kind on engine performance and thus should only be used when absolutely necessary

forall (single) - all facts of a given type match provided patterns

forall (multi) - all facts matching the first pattern must also match remaining patterns

and - both patterns must be true. Previously we've used and implicitly by including multiple conditions, but these can also be grouped with parentheses

or - one of 2 patterns must be true KnowledgeBuilder
compile rule resource
report errors KnowledgeBase
has compiled rules
issues sessions Session manipulation
add some facts
trigger rules firing ALWAYS DISPOSE OF SESSIONS! Manipulating Facts in Code: If we need to modify or remove that fact from the session later, then we'll need a reference to correlate our changes to the proper object:

Person person = new Person();
FactHandle personHandle = session.insert(new Person());

Update the object in session memory so that the two are in sync:

person.setGender("female");
session.update(personHandle, person);

Remove the Person object from the session's working memory:

session.retract(personHandle); Manipulating Facts in Rules: If we need to add a new Fact from within a rule consequence, we'll insert:

then
insert ( new Person() );
end

Update the object in session memory so that the two are in sync:

modify ( $person ) { setMood( "sleepy" ) };

Remove the Person object:

retract( $person ); Agenda
when a rule's conditions are met based on the provided data, a rule activation is added to the agenda. If something changes causing that rule's conditions to no longer be satisfied, then the activation is removed from the agenda. When we finally get to the point that we call fireAllRules(), we're simply asking the engine to go down the list of activations currently on the agenda and trigger their consequences. Event Listener
both the working memory and the agenda offer us the opportunity to take advantage of the observer pattern and attach special classes to our session that will be notified when certain events occur. These classes, called event listeners, offer us an excellent mechanism for passively debugging what's going on inside of our session. Custom Agenda Filter: class CustomAgendaFilter implements AgendaFilter {

private List<String> rulesToAllow;

public CustomAgendaFilter(String[] ruleNames) {
this.rulesToAllow = Arrays.asList(ruleNames);
}

public boolean accept(Activation activation) {
if (this.rulesToAllow.contains(activation.getRule().getName())) {
return true;
} else {
return false;
}
}
} @Test
public void testOnlyComboRuleFires() throws Exception {

session.insert(new Purchase(new BigDecimal("16"), 2, true));

String[] expectedRules = {"purchase contains combo"};
Assert.assertEquals(1, session.fireAllRules(new CustomAgendaFilter(expectedRules)));
} Drools Provides:
RuleNameEndsWithAgendaFilter
RuleNameEqualsAgendaFilter
RuleNameMatchesAgendaFilter
RuleNameStartsWithAgendaFilter Custom Agenda Event Listener: class CustomAgendaEventListener implements AgendaEventListener {

private List<String> rulesFired = new LinkedList<String>();

public List<String> getRulesFired() {
return this.rulesFired;
}

public void afterActivationFired(AfterActivationFiredEvent event) {
rulesFired.add(event.getActivation().getRule().getName());
}
} // NOTE: Interface carries several more methods @Test
public void testVerifyRulesViaListener() throws Exception {

CustomAgendaEventListener listener = new CustomAgendaEventListener();
session.addEventListener(listener);

// should trigger our first and last rule
session.insert(new Purchase(new BigDecimal("16"), 2, true));

Assert.assertEquals(2, session.fireAllRules(50));
Assert.assertEquals(listener.getRulesFired().get(0), "purchase over 15 and less than 25 dollars");
Assert.assertEquals(listener.getRulesFired().get(1), "purchase contains combo");
} WorkingMemoryEventListener:
objectInserted
objectUpdated
objectRetracted Drools Expert:
core engine of the system. We tell the engine about our logic and facts, and then we ask it to reason over what we've told it about and make some decisions for us. All other modules extend or rely upon the functionality of the core module, Expert. Drools Fusion:
Fusion gives the rules engine the ability to perform event processing, often referred to as complex event processing, or CEP. What's that, you say? Best to start with asking "What is an event?" When something occurs in a point of time, that's an event. It may be instantaneous, or it may have a duration. What's important is that it has some temporal association. Using that definition of events, we can define CEP as the ability to take in masses of events, determine which are likely to be important, and figure out relationships and patterns between them. Drools Guvnor:
Guvnor offers a collection of graphical editors with which we can view and edit our rules, and when combined with authentication, provides an excellent avenue for non-techie types to access and work with rules in a guided and controlled way. Drools Planner:
Planner helps us (the name's a hint!) carry out automated planning for NP-complete problems. As an example, in order to optimize how we distribute and utilize resources in an organization, sometimes we need to consider multiple possible solutions and choose which works best for us. http://www.packtpub.com/getting-started-with-drools/book
See the full transcript