先写一个hello world级别的例子
需求描述:
根据订单金额,决定订单的积分
金额 | 积分 |
---|---|
<100 | 无积分 |
>=100 && < 500 | 100 |
>=500 && < 1000 | 500 |
>=1000 | 1000 |
>=2000 | 仅打印文字 |
>=3000 | 仅打印文字 |
无条件 | 仅打印文字 |
代码实现
1. pom文件引入jar
<dependencies>
<dependency>
<groupId>org.drools</groupId>
<artifactId>drools-compiler</artifactId>
<version>7.73.0.Final</version>
</dependency>
<dependency>
<groupId>org.drools</groupId>
<artifactId>drools-mvel</artifactId>
<version>7.73.0.Final</version>
</dependency>
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>4.13.2</version>
<scope>test</scope>
</dependency>
</dependencies>
2. 定义kmoudle.xml
该文件必须放到 resources/META-INF目录下
```xml
<?xml version="1.0" encoding="UTF-8"?>
<kmodule xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns="http://www.drools.org/xsd/kmodule">
<kbase name="kbase1" default="true" packages="rules">
<ksession name="ksession1" default="true"/>
</kbase>
</kmodule>```
3. 定义Fact对象 Order
package com.dcy.drools.entity;
/**
* @author dcy
* @description
* @date 2022/10/11
**/
public class Order {
/**
* 消费金额
*/
private int amount;
/**
* 积分
*/
private int score;
public int getAmount() {
return amount;
}
public void setAmount(int amount) {
this.amount = amount;
}
public int getScore() {
return score;
}
public void setScore(int score) {
this.score = score;
}
}
4. 定义规则drl文件
order.drl,默认放到resources目录或子目录下即可。
package rules;
import com.dcy.drools.entity.Order
import com.dcy.drools.entity.Customer
rule "rule-c-4-11"
when
$customer:Customer(username == "李四")
then
System.out.println("触发规则: 姓名等于 李四" + $customer.getUsername());
end
rule "rule1"
salience 10
when
$order:Order(amount < 100)
then
$order.setScore(0);
System.out.println("触发规则:小于100无积分。");
end
rule "rule2"
when
$amount:Order(amount >= 100, amount < 500)
then
$amount.setScore(100);
System.out.println("触发规则:大于100小于500,积分100。");
end
rule "rule3"
when
// 年龄限制:
$amount:Order(amount >= 500, amount < 1000);
$customer:Customer(username == "张三")
then
$amount.setScore(500);
System.out.println("触发规则:大于500小于1000,积分500。");
System.out.println("触发张三和积分500.。");
end
rule "rule4"
// 年龄限制:
when
$amount:Order(amount >= 1000)
then
$amount.setScore(1000);
System.out.println("触发规则:大于1000,积分1000。");
end
rule "rule-true"
when
then
System.out.println("触发无条件为真。。。");
end
// 最后这行,是为了说明 rule、when、then、end关键字是定义规则的,而不需要换行和缩进,以上换行缩进,是为了便于阅读
rule "rule-one-line" when Order(amount >= 2000) then System.out.println("触发规则大于2000了。。"); end rule "rule-one-line-2" when Order(amount>=3000) then System.out.println("触发规则大于3000了。。"); end
5. 写测试代码
@Test
public void testOrderRules() {
// 获取services
KieServices kieServices = KieServices.Factory.get();
// 获取container
KieContainer container = kieServices.getKieClasspathContainer();
// 获取session
KieSession kieSession = container.newKieSession();
Order order = new Order();
order.setAmount(3123);
// 注入事实
kieSession.insert(order);
// 触发规则
System.out.println("规则执行前 order.score=" + order.getScore());
kieSession.fireAllRules();
System.out.println("规则执行后 order.score=" + order.getScore());
// 关闭session
kieSession.dispose();
}
6. 输出结果
规则执行前 order.score=0
触发规则:大于1000,积分1000。
触发无条件为真。。。
触发规则大于2000了。。
触发规则大于3000了。。
规则执行后 order.score=1000
drools执行过程
以上图片对应的是以上测试代码的执行过程。