Reputation: 11
In Drools rules file (drt) ,I'm storing the productId and Customer name in session . I want to apply discount only if for that particular customer and product ,discount wasn't applied already
Format of the Template file (Excel)
ProductID Quatntity Discount
Item_1 10 15
Item_2 20 20
Below is the drt file
template header
ProductId
Quantity
Discount
package com.main.discount;
dialect "java"
import java.util.Random;
import java.time.LocalDateTime;
import java.time.Instant;
import java.time.ZoneId;
import java.time.ZoneOffset;
import java.time.temporal.ChronoUnit;
import com.main.discount.Customer;
declare Discount
lCurrentTime: long
lCustomerName: String
lProductId: String
lExist: boolean
@timestamp(currentTime)
end
function Discount addDiscount(String productId,String customerName) {
Discount newRecord = new Discount();
newRecord.setLCustomerName(customerName);
newRecord.setLProductId(productId);
newRecord.setLCurrentTime(LocalDateTime.now().toEpochSecond(ZoneOffset.UTC));
newRecord.setLExist(true);
return newRecord;
}
template "OperationalMeasurement"
rule "Apply_Discount_@{row.rowNumber}"
no-loop
lock-on-active
salience 400
when
$c: Customer(productId == "@{ProductId}" ,$productId: productId && quantity >= "@{Quantity}" , $quantity: quantity, $customer: CustomerName)
not (Discount(lProductId == $productId, lCustomerName == $customer))
then
$c.setDiscount("@{Discount}");
Discount addCondition = addDiscount($productId,$customer);
insert(addCondition);
retract($c);
end
end template
Below is the code to call Initiate the Drools Kie session
KnowledgeBuilder kbuilder = KnowledgeBuilderFactory.newKnowledgeBuilder();
KieSessionConfiguration sessionConfig = KnowledgeBaseFactory.newKnowledgeSessionConfiguration();
sessionConfig.setOption( ClockTypeOption.get( ClockType.PSEUDO_CLOCK.getId() ) );
try {
loadRuleTemplate(DATA_FILE, RULE_TEMPLATE_FILE, "Discount", 2, 1);
} catch (IOException errorMsg) {
log.error(errorMsg.getMessage()); }
InternalKnowledgeBase kbase = KnowledgeBaseFactory.newKnowledgeBase();
kbase.addPackages(kbuilder.getKnowledgePackages());
KieSession kieSession = kbase.newKieSession(sessionConfig, null);
sessionClock = ksession.getSessionClock();
ksession.insert(Customer);
ksession.fireAllRules();
But everytime, not condition is ignored, eventhough record exist for customer and product , it still applies discount, Looks like I'm not able to retrieve Discount object from session. I'm using Stateful session.
Upvotes: 0
Views: 370
Reputation: 6322
I guess the problem you are having is related to the use of the lock-on-active
attribute in your rule. The lock-on-active
is nice to avoid infinite loops, but it comes with a cost: no new activations of that rule can happen by insertion or modifications of facts during the call of fireAllRules()
.
You can get a better explanation of the lock-on-active
attibute (and some ways to avoid having to use it) in this blog post.
Hope it helps,
Upvotes: 1