1
votes

Using Drools 7.6.0 (although I can upgrade to a newer version).

I have a system composed of a core library that is used by an application. The core library defines some common rules, types, and globals in a common.drl file, and then the application defines some additional rules, types, and globals in another app.drl file. The rules in app.drl file may use types and globals defined in common.drl.

I'm trying to follow examples like this, but I get tons of errors like:

Unable to resolve ObjectType 'myType' : [Rule name='My Rule']

Where My Rule is from app.drl and myType is from common.drl.

Is this pattern not supported, or are there some additional steps I need to take to make it work?

Here is a simplified version demonstrating the problem:

common.drl:

package mypackage

declare MyType
    myField : String
end

app.drl:

package mypackage

rule "My Rule"
    when
        $element : MyType()
    then
        System.out.println("worked");
end

java:

package mypackage;

import java.io.FileInputStream;
import java.io.FileNotFoundException;

import org.kie.api.KieBase;
import org.kie.api.KieServices;
import org.kie.api.builder.KieBuilder;
import org.kie.api.builder.KieFileSystem;
import org.kie.api.builder.Message;
import org.kie.api.builder.Results;
import org.kie.api.runtime.KieContainer;
import org.kie.api.runtime.KieSession;

public class MultiLoadTest {

    public static void main(String[] args) throws FileNotFoundException {

        KieServices kieServices = KieServices.Factory.get();
        KieFileSystem kfs = kieServices.newKieFileSystem();
        // repeat
        FileInputStream fisCommon = new FileInputStream( "src/main/resources/rules/common.drl" );
        kfs.write( "src/main/resources/simple.drl",
                        kieServices.getResources().newInputStreamResource( fisCommon ) );

        FileInputStream fisApp = new FileInputStream( "src/main/resources/rules/app.drl" );
        kfs.write( "src/main/resources/simple.drl",
                        kieServices.getResources().newInputStreamResource( fisApp ) );
        // end
        KieBuilder kieBuilder = kieServices.newKieBuilder( kfs ).buildAll();

        Results results = kieBuilder.getResults();
        if( results.hasMessages( Message.Level.ERROR ) ){
            System.out.println( results.getMessages() );
            throw new IllegalStateException( "### errors ###" );
        }
        KieContainer kieContainer =
              kieServices.newKieContainer( kieServices.getRepository().getDefaultReleaseId() );
        KieBase kieBase = kieContainer.getKieBase();
        KieSession kieSession = kieContainer.newKieSession();


    }

}

Output:

2018-04-23 13:53:00,872 [main] ERROR Unable to build KieBaseModel:defaultKieBase
Unable to resolve ObjectType 'MyType' : [Rule name='My Rule']


Exception in thread "main" [Message [id=1, kieBase=defaultKieBase, level=ERROR, path=simple.drl, line=5, column=0
   text=Unable to resolve ObjectType 'MyType']]
java.lang.IllegalStateException: ### errors ###
    at mypackage.MultiLoadTest.main(MultiLoadTest.java:35)
1

1 Answers

2
votes

For me your example worked as expected. So I assume that the issue is in configuration/dependencies or part that you didn't provide.

Instead of going through all this details I can provide working example ( spring+maven+junit5) that shows how to insert and retrieve drools declared types from session.

Please follow GitHub link.

Particular test link.