一个轻量的规则引擎


Easy Rules是一个简单而强大的Java规则引擎,提供以下功能:

  1. 轻量级框架和易于学习的API
  2. 基于POJO的开发与注解的编程模型
  3. 定义抽象的业务规则并轻松应用它们
  4. 支持从简单规则创建组合规则的能力
  5. 支持使用表达式语言(如MVEL和SpEL)定义规则的能力
  6. 在一篇非常有趣的规则引擎的文章中,Martin Fowler说:

Git地址:https://github.com/j-easy/easy-rules

使用wiki:https://github.com/j-easy/easy-rules/wiki

在一篇非常有趣的规则引擎的文章中https://martinfowler.com/bliki/RulesEngine.html,Martin Fowler说:

您可以自己构建一个简单的规则引擎。您只需要创建一组具有条件和操作的对象,将它们存储在一个集合中,并运行它们来评估conditions和执行actions。

这正是Easy Rules所做的,它提供了抽象Rule来创建带有conditions和actions的规则,RulesEngine API运行一系列规则来评估conditions和执行actions。。

使用场景

在编写代码过程中,我们对于if...else...语句是相当的熟悉了。但是如果条件分支比较多,比如有十几个、几十个、上百个,甚至更多时,如果我们还坚持在业务逻辑代码中使用if...else...语句,那么这个文件中的代码显得十分不协调,并且如果我们以后想再增加或减少规则时,还要来到这块业务逻辑代码中去修改if...else...语句,这给将来的维护带来了一定的不便。

针对这种情况,我们可以考虑使用规则引擎来解决。规则引擎不只一种,本文介绍的是easy rule规则引擎的使用。对于上面的场景,easy rule会把if...else...中的逻辑从业务逻辑代码中提取出来,并把这些逻辑存放在其他文件中。这样做以后,业务逻辑代码看上去就清爽了很多。同时如果将来我们想要修改这些规则时,直接去找这些存放规则的文件就行了。在easy rule中,存放规则有两种方式,一种是使用 .java 文件,另外一种是使用 .yml 文件,下面我们分别介绍。

Example

  1. First, define your rule.. Either in a declarative way using annotations:
@Rule(name = "weather rule", description = "if it rains then take an umbrella")
public class WeatherRule {

    @Condition
    public boolean itRains(@Fact("rain") boolean rain) {
        return rain;
    }
    
    @Action
    public void takeAnUmbrella() {
        System.out.println("It rains, take an umbrella!");
    }
}

Or in a programmatic way with a fluent API:

Rule weatherRule = new RuleBuilder()
        .name("weather rule")
        .description("if it rains then take an umbrella")
        .when(facts -> facts.get("rain").equals(true))
        .then(facts -> System.out.println("It rains, take an umbrella!"))
        .build();
Or using an Expression Language:
Rule weatherRule = new MVELRule()
        .name("weather rule")
        .description("if it rains then take an umbrella")
        .when("rain == true")
        .then("System.out.println(\"It rains, take an umbrella!\");");
Or using a rule descriptor:
Like in the following weather-rule.yml example file:

name: "weather rule"
description: "if it rains then take an umbrella"
condition: "rain == true"
actions:
  - "System.out.println(\"It rains, take an umbrella!\");"
MVELRuleFactory ruleFactory = new MVELRuleFactory(new YamlRuleDefinitionReader());
Rule weatherRule = ruleFactory.createRule(new FileReader("weather-rule.yml"));
  1. Then, fire it!
public class Test {
    public static void main(String[] args) {
        // define facts
        Facts facts = new Facts();
        facts.put("rain", true);

        // define rules
        Rule weatherRule = ...
        Rules rules = new Rules();
        rules.register(weatherRule);

        // fire rules on known facts
        RulesEngine rulesEngine = new DefaultRulesEngine();
        rulesEngine.fire(rules, facts);
    }
}

评论

Your browser is out-of-date!

Update your browser to view this website correctly. Update my browser now

×