9

We try to switch to Drools 6 with the all new KIE workbench (formerly known as Guvnor) and the new maven-based artifacts.

Now I'd like to use the the system described in this blog post in the second image ("Deployment"): Loading the rules via HTTP from the workbench repository (the dotted arrow, going from HTTP on the left directly into the application).

The problem is, that I have no idea how to load the artifact into my KieServices/KieModule object. I basically do not want to use maven, I also cannot provide the path to maven's settings.xml globally as a Java parameter, so this option is out.

I think that a similar issue is this one. As mentioned there, I also tried to load an URL resource but the problem seems to be that the system cannot determine, what kind of ResourceType the given URL (http://localhost:8080/kie-drools/maven2/.../-1.0.0.jar) is. And yes, I can access the .jar from the repository directly from the browser, without authentication.

Any ideas or tutorials how to do this?

My testing code:

public static void main(String[] args) {
    KieServices ks = KieServices.Factory.get();
    KieRepository repo = ks.getRepository();

    String url = "http://localhost:8080/kie-drools/maven2/de/test/test/1.0.0/test-1.0.0.jar";

    Resource urlResource = ks.getResources().newUrlResource(url);
    KieModule kModule = repo.addKieModule(urlResource); // this already fails
}

The error:

Exception in thread "main" java.lang.RuntimeException: Unable to fetch module from resource :[UrlResource path='http://localhost:8080/kie-drools/maven2/de/itm/Herma400/1.0.1/Herma400-1.0.1.jar']
    at org.drools.compiler.kie.builder.impl.KieRepositoryImpl.getKieModule(KieRepositoryImpl.java:205)
    at org.drools.compiler.kie.builder.impl.KieRepositoryImpl.addKieModule(KieRepositoryImpl.java:161)
    at kieTest.MainKieTest.main(MainKieTest.java:24)
Caused by: java.lang.NullPointerException
    at org.drools.compiler.kie.builder.impl.ClasspathKieProject.getPomProperties(ClasspathKieProject.java:197)
    at org.drools.compiler.kie.builder.impl.ClasspathKieProject.fetchKModule(ClasspathKieProject.java:148)
    at org.drools.compiler.kie.builder.impl.ClasspathKieProject.fetchKModule(ClasspathKieProject.java:109)
    at org.drools.compiler.kie.builder.impl.KieRepositoryImpl.getKieModule(KieRepositoryImpl.java:190)
    ... 2 more

Thanks in advance!

Community
  • 1
  • 1
Dominik Sandjaja
  • 6,326
  • 6
  • 52
  • 77

3 Answers3

13

I finally managed to get this solved. Below is a working example which loads the Drools artifact from the KIE-repository via HTTP and executes the rules:

package kieTest;

import java.util.Scanner;

import org.drools.compiler.kproject.ReleaseIdImpl;
import org.kie.api.KieServices;
import org.kie.api.builder.KieScanner;
import org.kie.api.runtime.KieContainer;
import org.kie.api.runtime.StatelessKieSession;

public class MainKieTest {

    public static void main(String[] args) {

        // works even without -SNAPSHOT versions
        String url = "http://localhost:8080/kie-drools/maven2/de/test/Test/1.2.3/Test-1.2.3.jar";

        // make sure you use "LATEST" here!
        ReleaseIdImpl releaseId = new ReleaseIdImpl("de.test", "Test", "LATEST");

        KieServices ks = KieServices.Factory.get();

        ks.getResources().newUrlResource(url);

        KieContainer kieContainer = ks.newKieContainer(releaseId);

        // check every 5 seconds if there is a new version at the URL
        KieScanner kieScanner = ks.newKieScanner(kieContainer);
        kieScanner.start(5000L);
        // alternatively:
        // kieScanner.scanNow();

        Scanner scanner = new Scanner(System.in);
        while (true) {
            runRule(kieContainer);
            System.out.println("Press enter in order to run the test again....");
            scanner.nextLine();
        }
    }

    private static void runRule(KieContainer kieKontainer) {
        StatelessKieSession kSession = kieKontainer.newStatelessKieSession("testSession");
        kSession.setGlobal("out", System.out);
        kSession.execute("testRuleAgain");
    }
}

When searching for the solution, I found the following link helpful:

I hope someone finds this useful when getting SO as first search result ;-)

Dominik Sandjaja
  • 6,326
  • 6
  • 52
  • 77
  • Thank you very much ! I still do not understand why Drools 6 does not provide Agent anymore. Using a Maven Scanner for the application using Drools implies 44 megs of dependencies that are 1) unuseful for the client (e.g. ant !) 2) adds risks of conflicting (e.g. Guava) I think your proposition must be included into a KnowledgeAgent-like behaviour / à la Drools 5.5. – skay Mar 18 '14 at 10:07
  • Do You know if it's possible to have a `EventProcessingMode` set to `STREAM` in a Drools project/artifact with Your solution? I've asked [the question on SO](https://stackoverflow.com/questions/50724360/set-event-processing-to-stream-with-rules-from-a-maven-project-kiescanner), but I need the answer asap. Thanks! – Aleksandar Jun 07 '18 at 11:14
10

The code above uses maven and kie-ci. The URLResource you create is not used.

Here's a working sample :

    String url = "http://localhost:8080/kie-drools-wb/maven2/groupId/artifactId/1.0/artifactId-1.0.jar";

    KieServices ks = KieServices.Factory.get();
    KieRepository kr = ks.getRepository();
    UrlResource urlResource = (UrlResource) ks.getResources()
            .newUrlResource(url);
    urlResource.setUsername("admin");
    urlResource.setPassword("password");
    urlResource.setBasicAuthentication("enabled");
    InputStream is = urlResource.getInputStream();
    KieModule kModule = kr.addKieModule(ks.getResources()
            .newInputStreamResource(is));

    KieContainer kContainer = ks.newKieContainer(kModule.getReleaseId());

    kContainer.newStatelessKieSession();

Note that you still need to tweak a bit to allow this to work with the KieScanner.

jps
  • 164
  • 2
  • 8
  • How to import the UrlResource? I can't find this class. – Yiqun Hu Aug 02 '15 at 13:10
  • @jps Will KieScanner work with above mentioned approach ? – rishi Oct 20 '16 at 16:31
  • Do You know if it's possible to have a `EventProcessingMode` set to `STREAM` in a Drools project/artifact with Your solution? I've asked [the question on SO](https://stackoverflow.com/questions/50724360/set-event-processing-to-stream-with-rules-from-a-maven-project-kiescanner), but I need the answer asap. Thanks! – Aleksandar Jun 07 '18 at 11:15
2

Here are the steps, All the steps are mandatory

  • Add kie-clie dependency in your pom

    <dependency>
        <groupId>org.kie</groupId>
        <artifactId>kie-ci</artifactId>
        <version>6.2.0.Final</version>
    </dependency>
    
  • Add your KIE workbench maven repo to your pom.xml

    <repository>
        <id>guvnor-m2-repo</id>
        <name>Guvnor M2 Repo</name>
        <url>http://localhost:8080/drools/maven2wb/</url>
    </repository>
    
  • Add the dependency to your pom.xml

    <dependency>
        <groupId>groupId</groupId>
        <artifactId>artifactId</artifactId>
        <version>LATEST</version>
    </dependency>
    
  • Provide your repo credentials into settings.xml

    <server>
        <id>guvnor-m2-repo</id>
        <username>admin</username>
        <password>@dmin</password>
    </server>
    
  • Java code

    KieServices ks = KieServices.Factory.get();
    ReleaseId releaseId = ks.newReleaseId("groupID", "artifactID", "LATEST");
    KieContainer kieContainer = ks.newKieContainer(releaseId);
    KieSession kieSession = kieContainer.newKieSession();
    kieSession.insert(object);
    kieSession.fireAllRules();
    
Hasan Can Saral
  • 2,950
  • 5
  • 43
  • 78
craftsmannadeem
  • 2,665
  • 26
  • 22