Cloudera CDH/CDP 및 Hadoop EcoSystem, Semantic IoT등의 개발/운영 기술을 정리합니다. gooper@gooper.com로 문의 주세요.
---결과 값 -------------
init session.getFactCount() = 0
speed: 602.92267
speed: 601.1532
speed: 607.839
speed: 600.9022
speed: 609.21796
speed: 602.91187
speed: 604.02515
speed: 608.272
speed: 607.80176
speed: 606.90405
AA001 average speed: 605.982958984375
AA001 average speed: 605.982958984375
AA001 average speed: 605.982958984375
AA001 average speed: 605.982958984375
AA001 average speed: 605.982958984375
AA001 average speed: 605.982958984375
AA001 average speed: 605.982958984375
AA001 average speed: 605.982958984375
AA001 average speed: 605.982958984375
AA001 average speed: 605.982958984375
matched count of Fact = 10
-------sliding_rules.drl--------------
package com.gooper.drool_test;
import com.gooper.drool_test.model.FlightStatus
import com.gooper.drool_test.model.FlightControl
import com.gooper.drool_test.model.EmergencySignal
declare FlightStatus
@role(event)
end
declare EmergencySignal
@role(event)
end
rule "First contact"
salience 100
when
$currentFlight : FlightStatus() from entry-point "flight-control"
not (exists (FlightStatus(this != $currentFlight, flight == $currentFlight.flight) from entry-point "flight-control"))
$control : FlightControl()
then
$control.addFlight($currentFlight);
System.out.println("First contact with Flight " + $currentFlight.getFlight());
end
rule "flight arrival"
when
$flight : FlightStatus() from entry-point "flight-arrival"
$control : FlightControl()
// Obtain resources to prepare the flight landing
then
System.out.println("Flight " + $flight.getFlight() + " arriving to " + $control.getAirport() + ". Sending instructions");
// Send instructions to arriving flight
end
rule "flight average speed"
when
$flight : FlightStatus() from entry-point "flight-control"
$averageSpeed : Number(floatValue > 0) from accumulate(FlightStatus(flight==$flight.flight, $speed:speed) over window:length(5)
from entry-point "flight-control",
average($speed))
then
System.out.println($flight.getFlight() + " average speed: " + $averageSpeed);
end
-------------------SlidingWindow.java-----------------------
package com.gooper.drool_test;
import java.util.concurrent.TimeUnit;
import org.drools.core.time.SessionPseudoClock;
import org.kie.api.KieBase;
import org.kie.api.KieBaseConfiguration;
import org.kie.api.conf.EventProcessingOption;
import org.kie.api.io.ResourceType;
import org.kie.api.runtime.KieSession;
import org.kie.api.runtime.KieSessionConfiguration;
import org.kie.api.runtime.conf.ClockTypeOption;
import org.kie.api.runtime.rule.EntryPoint;
import org.kie.internal.KnowledgeBaseFactory;
import org.kie.internal.builder.KnowledgeBuilder;
import org.kie.internal.builder.KnowledgeBuilderFactory;
import org.kie.internal.io.ResourceFactory;
import com.gooper.drool_test.custom.CustomAgendaEventListener;
import com.gooper.drool_test.custom.CustomWorkingMemoryEventListener;
import com.gooper.drool_test.helper.FlightSimulation;
import com.gooper.drool_test.model.FlightStatus;
import org.kie.internal.builder.KnowledgeBuilderError;
/*
* Sliding-window test
*/
public class SlidingWindow {
public static final void main(String[] args) {
try {
// 지식 빌더 생성
KnowledgeBuilder kbuilder = KnowledgeBuilderFactory.newKnowledgeBuilder();
// 지식 빌더에 룰정의파일 설정
kbuilder.add(ResourceFactory. newClassPathResource("sliding_rules.drl"), ResourceType. DRL );
if (kbuilder.hasErrors()) {
if(kbuilder.getErrors().size() > 0) {
for(KnowledgeBuilderError kerror : kbuilder.getErrors()) {
System.out.println("error :" + kerror);
}
}
}
// 설정정보를 변경하기위한 config접근 정보를 얻음
KieBaseConfiguration config = KnowledgeBaseFactory.newKnowledgeBaseConfiguration();
config.setOption(EventProcessingOption.STREAM);
KieSessionConfiguration conf = KnowledgeBaseFactory.newKnowledgeSessionConfiguration();
conf.setOption(ClockTypeOption.get("pseudo"));
// 새로운 지식 베이스 생성
KieBase kiebase = kbuilder.newKnowledgeBase();
// 새로운 지식 베이스 세션 생성
KieSession session = kiebase.newKieSession(conf,null);
// logger등록(팩트에 의해 생성된 엑티베이션(Activation)관련 이벤트만 로깅)
//session.addEventListener(new CustomAgendaEventListener());
// logger등록(팩트의 추가/수정/제거 이벤트에 대한 정보)
//session.addEventListener(new CustomWorkingMemoryEventListener());
System.out.println(" init session.getFactCount() = " + session.getFactCount());
// SessionClock의 레퍼런스를 얻는다
SessionPseudoClock clock = session.getSessionClock();
FlightSimulation flightAA001 = new FlightSimulation("AA001", "San Francisco", "Los Angeles", 270);
for(int i = 0; i < 10; i++) {
FlightStatus flightStatus = flightAA001.update();
EntryPoint flightArrivalEntryPoint = session.getEntryPoint("flight-control");
flightArrivalEntryPoint.insert(flightStatus);
clock.advanceTime(5, TimeUnit.MINUTES);
Thread.sleep(100);
}
int matchedCnt = session.fireAllRules();
System.out.println(" matched count of Fact = " + matchedCnt);
session.dispose();
} catch (Throwable t) {
t.printStackTrace();
}
}
}
----------------------FlightSimulation.java------------------------
package com.gooper.drool_test.helper;
import java.util.Random;
import com.gooper.drool_test.model.FlightStatus;
/**
*
* @author Lucas Amador
*
*/
public class FlightSimulation {
private static final int AIRPORT_AIR_SPACE = 50;
private Random rnd = new Random();
private final String flight;
private final String origin;
private final String destination;
private long distance;
private boolean landed;
public FlightSimulation(String flight, String origin, String destination, long distance) {
this.flight = flight;
this.origin = origin;
this.destination = destination;
this.distance = distance;
}
public FlightStatus update() {
FlightStatus flightStatus = new FlightStatus();
flightStatus.setFlight(flight);
flightStatus.setDestination(destination);
flightStatus.setOrigin(origin);
flightStatus.setDestination(destination);
this.distance = calculateDistance();
flightStatus.setDistance(this.distance);
flightStatus.setSpeed(currentSpeed());
System.out.println("speed: " + flightStatus.getSpeed());
return flightStatus;
}
private long calculateDistance() {
if ((distance - AIRPORT_AIR_SPACE) <= AIRPORT_AIR_SPACE) {
landed = true;
return 0;
}
return distance - AIRPORT_AIR_SPACE;
}
private float currentSpeed() {
return (rnd.nextFloat() * 10) + 600;
}
public boolean isLanded() {
return landed;
}
}