자바 규칙 엔진 Easy Rules 사용 안내

쉬 운 규칙 개술


Easy Rules 는 자바 규칙 엔진 으로 영감 은'Should I use a Rules Engine?'라 는 글 에서 나 왔 다.
규칙 엔진 은 선택 할 수 있 는 계산 모델 을 제공 하 는 것 이다.일반적인 명령 식 모델(조건 과 순환 이 있 는 명령 으로 순서대로 구성)과 달리 규칙 엔진 은 생산 규칙 시스템 을 바탕 으로 한다.이것 은 하나의 생산 규칙 으로 모든 규칙 에 하나의 조건(condition)과 하나의 동작(action)―쉽게 말 하면 이 를 if-then 문장 으로 볼 수 있다.
정교 한 점 은 규칙 이 어떤 순서 로 든 작 성 될 수 있다 는 점 이다.엔진 은 순서 에 의미 가 있 는 어떤 방식 으로 든 계산 할 지 결정 한다.그것 을 고려 하 는 좋 은 방법 은 시스템 이 모든 규칙 을 실행 하고 조건 이 성립 된 규칙 을 선택 한 다음 에 해당 하 는 조작 을 하 는 것 이다.이렇게 하 는 장점 은 많은 문제 들 이 이 모델 에 자 연 스 럽 게 부합된다 는 것 이다.
if car.owner.hasCellPhone then premium += 100;
if car.model.theftRating > 4 then premium += 200;
if car.owner.livesInDodgyArea && car.model.theftRating > 2 then premium += 300;
규칙 엔진 은 이러한 계산 모델 의 프로 그래 밍 을 더욱 쉽게 만 드 는 도구 이다.그것 은 완전한 개발 환경 이나 전통 적 인 플랫폼 에서 일 할 수 있 는 구조 일 수 있다.생산 규칙 계산 모델 은 일부 계산 문제 만 해결 하 는 데 가장 적합 하기 때문에 규칙 엔진 은 비교적 큰 시스템 에 더욱 잘 끼 워 넣 을 수 있다.
너 는 스스로 간단 한 규칙 엔진 을 구축 할 수 있다.조건 과 동작 을 가 진 대상 을 만 들 고 집합 에 저장 한 다음 조건 을 평가 하고 이 동작 을 수행 하 는 것 이 필요 합 니 다.
Easy Rules 는 조건 과 동작 을 가 진 규칙 을 만 들 고 RuleEngine API 를 제공 합 니 다.이 API 는 하나의 규칙 을 통 해 실행 되 어 조건 을 평가 하고 동작 을 수행 합 니 다.
Easy Rules 는 간단 하고 사용 하기 쉬 우 며 두 단계 만 있 으 면 됩 니 다.
우선 규칙 을 정의 하 는 방식 은 여러 가지 가 있다.
주석

@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!");
  }
}
방식 2:체인 프로 그래 밍

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();
표현 식

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!\");");
방식 4:yml 프로필
weather-rule.yml

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"));
다음 규칙 적용

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);
  }
}
입문 사례:Hello Easy Rules

<dependency>
  <groupId>org.jeasy</groupId>
  <artifactId>easy-rules-core</artifactId>
  <version>4.0.0</version>
</dependency>
뼈 대 를 통 해 maven 프로젝트 만 들 기:

mvn archetype:generate \
  -DarchetypeGroupId=org.jeasy \
  -DarchetypeArtifactId=easy-rules-archetype \
  -DarchetypeVersion=4.0.0
기본적으로 Hello World Rule 규칙 을 만 들 었 습 니 다.다음 과 같 습 니 다.

package com.cjs.example.rules;

import org.jeasy.rules.annotation.Action;
import org.jeasy.rules.annotation.Condition;
import org.jeasy.rules.annotation.Rule;

@Rule(name = "Hello World rule", description = "Always say hello world")
public class HelloWorldRule {

  @Condition
  public boolean when() {
    return true;
  }

  @Action
  public void then() throws Exception {
    System.out.println("hello world");
  }

}

2.규칙 정의
2.1.정의 규칙
대부분의 업무 규칙 은 다음 과 같은 정의 로 표시 할 수 있다.
  • Name:네 임 스페이스 의 유일한 규칙 이름
  • 설명:규칙 의 간략 한 설명Priority:다른 규칙 에 비해 우선 순위Facts:사실,즉시 처리 할 수 있 는 데이터Conditions:규칙 을 적용 하기 위해 반드시 만족 해 야 하 는 조건
  • Actions:조건 이 만족 할 때 실행 하 는 동작
  • Easy Rules 는 모든 관건 점 에 업무 규칙 을 정의 하 는 추상 적 인 것 을 제공 했다.
    Easy Rules 에서 Rule 인터페이스 대표 규칙
    
    public interface Rule {
    
      /**
      * This method encapsulates the rule's conditions.
      * @return true if the rule should be applied given the provided facts, false otherwise
      */
      boolean evaluate(Facts facts);
    
      /**
      * This method encapsulates the rule's actions.
      * @throws Exception if an error occurs during actions performing
      */
      void execute(Facts facts) throws Exception;
    
      //Getters and setters for rule name, description and priority omitted.
    
    }
    evaluate 방법 은 결 과 를 TRUE 로 계산 해 야 규칙 을 실행 할 수 있 는 조건 을 패키지 합 니 다.execute 방법 은 규칙 조건 을 만족 시 킬 때 실행 해 야 할 동작 을 패키지 합 니 다.조건 과 조작 은 Condition 과 Action 인터페이스 에서 표시 합 니 다.
    정의 규칙 은 두 가지 방식 이 있 습 니 다.
    4
  • POJO 류 에 주 해 를 추가 합 니 다
  • RuleBuilder API 프로 그래 밍 을 통 해POJO 클래스 에@Rule 주 해 를 추가 할 수 있 습 니 다.예 를 들 어:
    
    @Rule(name = "my rule", description = "my rule description", priority = 1)
    public class MyRule {
    
      @Condition
      public boolean when(@Fact("fact") fact) {
        //my rule conditions
        return true;
      }
    
      @Action(order = 1)
      public void then(Facts facts) throws Exception {
        //my actions
      }
    
      @Action(order = 2)
      public void finally() throws Exception {
        //my final actions
      }
    }
    @Condition 주석 지정 규칙 조건
    @Fact 주석 지정 매개 변수
    @Action 지정 한 규칙 이 실 행 된 동작 설명
    RuleBuilder 는 체인 스타일 정의 규칙 을 지원 합 니 다.예 를 들 어:
    
    Rule rule = new RuleBuilder()
            .name("myRule")
            .description("myRuleDescription")
            .priority(3)
            .when(condition)
            .then(action1)
            .then(action2)
            .build();
    조합 규칙
    Composite Rule 은 하나의 규칙 으로 구성 되 어 있다.이것 은 전형 적 인 조합 디자인 모델 의 실현 이다.
    조합 규칙 은 서로 다른 방식 으로 조합 규칙 을 촉발 할 수 있 기 때문에 추상 적 인 개념 이다.
    Easy Rules 자체 3 가지 Composite Rule 실현:
  • UnitRule Group:모든 규칙 을 적용 하거나 그 어떠한 규칙(AND 논리)도 적용 하지 않 습 니 다
  • ActivationRule Group:첫 번 째 적용 규칙 을 실행 하고 그룹의 다른 규칙(XOR 논리)을 무시 합 니 다
  • conditional Rule Group:최고 우선 순위 의 규칙 계산 결과 가 true 이면 나머지 규칙 을 촉발 합 니 다복합 규칙 은 기본 규칙 에서 일반적인 규칙 으로 만 들 고 등록 할 수 있 습 니 다.
    
    //Create a composite rule from two primitive rules
    UnitRuleGroup myUnitRuleGroup = new UnitRuleGroup("myUnitRuleGroup", "unit of myRule1 and myRule2");
    myUnitRuleGroup.addRule(myRule1);
    myUnitRuleGroup.addRule(myRule2);
    
    //Register the composite rule as a regular rule
    Rules rules = new Rules();
    rules.register(myUnitRuleGroup);
    
    RulesEngine rulesEngine = new DefaultRulesEngine();
    rulesEngine.fire(rules, someFacts);
    모든 규칙 에는 우선 순위 가 있다.그것 은 등록 규칙 을 실행 하 는 기본 순 서 를 대표 합 니 다.기본 적 인 상황 에서 낮은 값 은 비교적 높 은 우선 순 위 를 나타 낸다.사용자 정의 우선 순위 정책 을 제공 하기 위해 compare To 방법 을 다시 쓸 수 있 습 니 다.
    2.2.사실 정의
    Easy Rules 에서 Fact API 는 사실 을 대표 합 니 다.
    
    public class Fact<T> {
       private final String name;
       private final T value;
    }

    밤 을 들다
    
    Fact<String> fact = new Fact("foo", "bar");
    Facts facts = new Facts();
    facts.add(fact);
    혹은 이런 약자 로 도 쓸 수 있다.
    
    Facts facts = new Facts();
    facts.put("foo", "bar");
    @Fact 주석 으로 Facts 를 condition 과 action 방법 에 주입 할 수 있 습 니 다.
    
    @Rule
    class WeatherRule {
    
      @Condition
      public boolean itRains(@Fact("rain") boolean rain) {
        return rain;
      }
    
      @Action
      public void takeAnUmbrella(Facts facts) {
        System.out.println("It rains, take an umbrella!");
        // can add/remove/modify facts
      }
    
    }
    2.3.정의 규칙 엔진
    Easy Rules 는 두 가지 RulesEngine 인 터 페 이 스 를 제공 합 니 다.
    Default RulesEngine:규칙 의 자연 순서에 따라 규칙 을 적용 합 니 다
  • Inference RulesEngine:이미 알 고 있 는 사실 에 대한 규칙 을 지속 적 으로 적용 하고 그 어떠한 규칙 도 적용 되 지 않 을 때 까지
  • 규칙 엔진 생 성:
    
    RulesEngine rulesEngine = new DefaultRulesEngine();
    
    // or
    
    RulesEngine rulesEngine = new InferenceRulesEngine();
    그리고 등록 규칙
    
    rulesEngine.fire(rules, facts);
    규칙 엔진 은 다음 그림 과 같이 설정 할 수 있 는 인자 가 있 습 니 다.

    밤 을 들다
    
    RulesEngineParameters parameters = new RulesEngineParameters()
      .rulePriorityThreshold(10)
      .skipOnFirstAppliedRule(true)
      .skipOnFirstFailedRule(true)
      .skipOnFirstNonTriggeredRule(true);
    
    RulesEngine rulesEngine = new DefaultRulesEngine(parameters);
    2.4.정의 규칙 모니터
    RuleListener 인터페이스 구현
    
    public interface RuleListener {
    
      /**
       * Triggered before the evaluation of a rule.
       *
       * @param rule being evaluated
       * @param facts known before evaluating the rule
       * @return true if the rule should be evaluated, false otherwise
       */
      default boolean beforeEvaluate(Rule rule, Facts facts) {
        return true;
      }
    
      /**
       * Triggered after the evaluation of a rule.
       *
       * @param rule that has been evaluated
       * @param facts known after evaluating the rule
       * @param evaluationResult true if the rule evaluated to true, false otherwise
       */
      default void afterEvaluate(Rule rule, Facts facts, boolean evaluationResult) { }
    
      /**
       * Triggered on condition evaluation error due to any runtime exception.
       *
       * @param rule that has been evaluated
       * @param facts known while evaluating the rule
       * @param exception that happened while attempting to evaluate the condition.
       */
      default void onEvaluationError(Rule rule, Facts facts, Exception exception) { }
    
      /**
       * Triggered before the execution of a rule.
       *
       * @param rule the current rule
       * @param facts known facts before executing the rule
       */
      default void beforeExecute(Rule rule, Facts facts) { }
    
      /**
       * Triggered after a rule has been executed successfully.
       *
       * @param rule the current rule
       * @param facts known facts after executing the rule
       */
      default void onSuccess(Rule rule, Facts facts) { }
    
      /**
       * Triggered after a rule has failed.
       *
       * @param rule the current rule
       * @param facts known facts after executing the rule
       * @param exception the exception thrown when attempting to execute the rule
       */
      default void onFailure(Rule rule, Facts facts, Exception exception) { }
    
    }
    3.예시
    
    <project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
     xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
      <modelVersion>4.0.0</modelVersion>
      <groupId>com.cjs.example</groupId>
      <artifactId>easy-rules-quickstart</artifactId>
      <version>1.0.0-SNAPSHOT</version>
      <packaging>jar</packaging>
      <dependencies>
        <dependency>
          <groupId>org.jeasy</groupId>
          <artifactId>easy-rules-core</artifactId>
          <version>4.0.0</version>
        </dependency>
        <dependency>
          <groupId>org.jeasy</groupId>
          <artifactId>easy-rules-support</artifactId>
          <version>4.0.0</version>
        </dependency>
        <dependency>
          <groupId>org.jeasy</groupId>
          <artifactId>easy-rules-mvel</artifactId>
          <version>4.0.0</version>
        </dependency>
        <dependency>
          <groupId>org.slf4j</groupId>
          <artifactId>slf4j-simple</artifactId>
          <version>1.7.30</version>
        </dependency>
      </dependencies>
    </project>

    4.확장
    규칙 은 본질 적 으로 하나의 함수 이다.예 를 들 어 y=f(x1,x2,..,xn)
    규칙 엔진 은 업무 코드 와 업무 규칙 의 분 리 를 해결 하기 위 한 엔진 으로 응용 프로그램 에 포 함 된 구성 요소 로 업무 결정 을 응용 프로그램 코드 에서 분리 하 는 것 을 실현 합 니 다.
    또 하나의 흔 한 방식 은 자바+Groovy 가 실현 하고 자바 에 Groovy 스 크 립 트 엔진 을 삽입 하여 업무 규칙 을 박리 하 는 것 이다.
    https://github.com/j-easy/easy-rules/wiki
    자바 규칙 엔진 Easy Rules 사용 에 관 한 소개 글 은 여기까지 입 니 다.더 많은 자바 규칙 엔진 Easy Rules 내용 은 우리 의 이전 글 을 검색 하거나 아래 의 관련 글 을 계속 찾 아 보 세 요.앞으로 많은 응원 부 탁 드 리 겠 습 니 다!

    좋은 웹페이지 즐겨찾기