Stack Exchange
Read Drools variable to Java code
I'm new to drools and what I'm trying to do is to get a value from the rules
I used the code from the project sample of drools which is:
Reading the DRL file:
KnowledgeBuilder kbuilder = KnowledgeBuilderFactory.newKnowledgeBuilder();
kbuilder.add( ResourceFactory.newClassPathResource( "path.drl", getClass() ), ResourceType.DRL );
KnowledgeBuilderErrors errors = kbuilder.getErrors();

if( errors.size() > 0 )
{
     for( KnowledgeBuilderError error : errors )
     {
          System.err.println( error );
     }
     throw new IllegalArgumentException( "Could not parse knowledge." );
}

KnowledgeBase kbase = KnowledgeBaseFactory.newKnowledgeBase();
kbase.addKnowledgePackages( kbuilder.getKnowledgePackages() );
return kbase;

Inserting object and firing the rules
Bean bean = new Bean();
StatefulKnowledgeSession ksession = aKnowledgeBase.newStatefulKnowledgeSession();
// planning to insert a double
ksession.insert( bean );
ksession.fireAllRules();

What I want to do is to get a value from the rules, What I tried so far is using query which is I'm not sure if it is the proper way of doing it:
global String $test;

rule "Excellent"

    when
        // I'm planning to replace the bean with just a double is that possible?
        $m: bean ( listeningScore > 85 ) 
        $p: bean ( listeningScore < 101 )
    then
        $test = "Excellent";
        System.out.println( $test );

end

query "Knowledge" 
     $result : $test
end

Also this produce an error which I really don't know how to fix. Here is the stacktrace:
SLF4J: Failed to load class "org.slf4j.impl.StaticLoggerBinder".
SLF4J: Defaulting to no-operation (NOP) logger implementation
SLF4J: See http://www.slf4j.org/codes.html#StaticLoggerBinder for further details.
[24,0]: [ERR 102] Line 24:0 mismatched input 'end' in query
[0,0]: Parser returned a null Package
java.lang.IllegalArgumentException: Could not parse knowledge.
    at com.neu.als.thesis.units.InferenceEngine.readKnowledgeBase(InferenceEngine.java:61)
    at com.neu.als.thesis.units.EvaluationUnit.evaluateConceptKnowledgeLevel(EvaluationUnit.java:187)
    at com.neu.als.thesis.web.controllers.FLTController.evaluateFLT(FLTController.java:108)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source)
    at java.lang.reflect.Method.invoke(Unknown Source)
    at org.springframework.web.bind.annotation.support.HandlerMethodInvoker.invokeHandlerMethod(HandlerMethodInvoker.java:176)
    at org.springframework.web.servlet.mvc.annotation.AnnotationMethodHandlerAdapter.invokeHandlerMethod(AnnotationMethodHandlerAdapter.java:444)
    at org.springframework.web.servlet.mvc.annotation.AnnotationMethodHandlerAdapter.handle(AnnotationMethodHandlerAdapter.java:432)
    at org.springframework.web.servlet.DispatcherServlet.doDispatch(DispatcherServlet.java:925)
    at org.springframework.web.servlet.DispatcherServlet.doService(DispatcherServlet.java:856)
    at org.springframework.web.servlet.FrameworkServlet.processRequest(FrameworkServlet.java:946)
    at org.springframework.web.servlet.FrameworkServlet.doPost(FrameworkServlet.java:848)
    at javax.servlet.http.HttpServlet.service(HttpServlet.java:647)
    at org.springframework.web.servlet.FrameworkServlet.service(FrameworkServlet.java:822)
    at javax.servlet.http.HttpServlet.service(HttpServlet.java:728)
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:305)
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:210)
    at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:222)
    at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:123)
    at org.apache.catalina.authenticator.AuthenticatorBase.invoke(AuthenticatorBase.java:502)
    at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:171)
    at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:99)
    at org.apache.catalina.valves.AccessLogValve.invoke(AccessLogValve.java:953)
    at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:118)
    at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:408)
    at org.apache.coyote.http11.AbstractHttp11Processor.process(AbstractHttp11Processor.java:1023)
    at org.apache.coyote.AbstractProtocol$AbstractConnectionHandler.process(AbstractProtocol.java:589)
    at org.apache.tomcat.util.net.JIoEndpoint$SocketProcessor.run(JIoEndpoint.java:312)
    at java.util.concurrent.ThreadPoolExecutor.runWorker(Unknown Source)
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(Unknown Source)
    at java.lang.Thread.run(Unknown Source)


Firstly, that exception means that the DRL code won't compile. I suspect this is because your query is referencing a bound variable from another rule, but it could be something else. Check out the docs on syntax for queries.
However, I tend to use one of two mechanisms for getting rule responses into the Java code.

In a stateless session have rules modify the inserted fact(s). After rules execution, just look at the fact that you inserted.
In a stateful session you can additionally use session.getObjects() or session.getObjects(ObjectFilter) to get references to the facts that are in the working memory after rules execution.

Here's an example of the first pattern, modifying the inserted fact:
rule "Reject a request"
when
    $req: PaymentValidationRequest()
then
    $req.setValid(false);
    update($req);
end

PaymentValidationRequest request = new PaymentValidationRequest(payment);
request.setPayment(payment);
List<Object> facts = new ArrayList<Object>();
facts.add(request);     
ksession.execute(facts);
...
boolean isValid = request.isValid()
List<ValidationAnnotation> annotations = request.getAnnotations();

Here's an example of the second pattern, when your rules have inserted or modified facts:
    ObjectFilter filter = new ObjectFilter() {
        @Override
        public boolean accept(Object object) {
            return object.getClass().getSimpleName().equals("MyFact");
        }
    };

    for (FactHandle handle : session.getFactHandles(filter)) {
        Object fact = session.getObject(handle);
        // Do something with the fact you just found in working memory.
        // ...
    }


I only made one rule. And only 1 file. Can you give a snippets of what your trying to say?
