'Kie uses substring to extract its module name. But calls it wrongly?
So I am doing a project that involves a Java implementation of Drools client running up against a KIE service with Drools-WorkBench.
I've started building the final project, though I'm running into some troubles, as the URL of the KIE jar path, seems to have some issues.
So in the meat of the ServiceDiscoveryImpl the application tries to get its module name.
This it does with the following commands:
private static String getModuleName(URL url) {
String s = url.toString();
int moduleStart = s.indexOf("META-INF/kie") + "META-INF/kie".length() + 1;
return s.substring(moduleStart, s.length() - ("kie.conf".length() + 1));
}
Now in my case the value of s is jar:file:/C:/SLP/Drools/target/war.jar!/META-INF/kie.conf.
resulting in the value of moduleStart to be 53
and thus we make a call to String.substring with the value (53, 48). Causing the exception
java.lang.StringIndexOutOfBoundsException: begin 53, end 48, length 57
Stacktrace:
java.lang.StringIndexOutOfBoundsException: begin 53, end 48, length 57
java.base/java.lang.String.checkBoundsBeginEnd(String.java:3319)
java.base/java.lang.String.substring(String.java:1874)
org.kie.api.internal.utils.ServiceDiscoveryImpl.getModuleName(ServiceDiscoveryImpl.java:346)
java.base/java.util.stream.ReferencePipeline$3$1.accept(ReferencePipeline.java:195)
java.base/java.util.ArrayList$ArrayListSpliterator.forEachRemaining(ArrayList.java:1655)
java.base/java.util.stream.AbstractPipeline.copyInto(AbstractPipeline.java:484)
java.base/java.util.stream.AbstractPipeline.wrapAndCopyInto(AbstractPipeline.java:474)
java.base/java.util.stream.ReduceOps$ReduceOp.evaluateSequential(ReduceOps.java:913)
java.base/java.util.stream.AbstractPipeline.evaluate(AbstractPipeline.java:234)
java.base/java.util.stream.ReferencePipeline.collect(ReferencePipeline.java:578)
org.kie.api.internal.utils.ServiceDiscoveryImpl.findKieConfUrls(ServiceDiscoveryImpl.java:290)
org.kie.api.internal.utils.ServiceDiscoveryImpl.loadKieConfs(ServiceDiscoveryImpl.java:212)
java.base/java.util.stream.ReferencePipeline$3$1.accept(ReferencePipeline.java:195)
java.base/java.util.Spliterators$ArraySpliterator.tryAdvance(Spliterators.java:958)
java.base/java.util.stream.ReferencePipeline.forEachWithCancel(ReferencePipeline.java:127)
java.base/java.util.stream.AbstractPipeline.copyIntoWithCancel(AbstractPipeline.java:502)
java.base/java.util.stream.AbstractPipeline.copyInto(AbstractPipeline.java:488)
java.base/java.util.stream.AbstractPipeline.wrapAndCopyInto(AbstractPipeline.java:474)
java.base/java.util.stream.FindOps$FindOp.evaluateSequential(FindOps.java:150)
java.base/java.util.stream.AbstractPipeline.evaluate(AbstractPipeline.java:234)
java.base/java.util.stream.ReferencePipeline.findFirst(ReferencePipeline.java:543)
org.kie.api.internal.utils.ServiceDiscoveryImpl.getKieConfs(ServiceDiscoveryImpl.java:204)
org.kie.api.internal.utils.ServiceDiscoveryImpl.getServices(ServiceDiscoveryImpl.java:103)
org.kie.api.internal.utils.ServiceRegistry$Impl.<init>(ServiceRegistry.java:62)
org.drools.dynamic.DynamicServiceRegistrySupplier$LazyHolder.<clinit>(DynamicServiceRegistrySupplier.java:27)
org.drools.dynamic.DynamicServiceRegistrySupplier.get(DynamicServiceRegistrySupplier.java:32)
org.drools.dynamic.DynamicServiceRegistrySupplier.get(DynamicServiceRegistrySupplier.java:23)
org.kie.api.internal.utils.ServiceRegistry$Impl.getServiceRegistry(ServiceRegistry.java:90)
org.kie.api.internal.utils.ServiceRegistry$ServiceRegistryHolder.<clinit>(ServiceRegistry.java:49)
org.kie.api.internal.utils.ServiceRegistry.getInstance(ServiceRegistry.java:41)
org.kie.api.internal.utils.ServiceRegistry.getService(ServiceRegistry.java:37)
org.kie.api.KieServices$Factory$LazyHolder.<clinit>(KieServices.java:358)
org.kie.api.KieServices$Factory.get(KieServices.java:365)
utils.KieServerAccessor.validate(KieServerAccessor.java:73) // I call it here
module.RabbitMQConsumer.handleDrools(RabbitMQConsumer.java:112)
module.RabbitMQConsumer.access$000(RabbitMQConsumer.java:18)
module.RabbitMQConsumer$1.lambda$handleDelivery$0(RabbitMQConsumer.java:79)
java.base/java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:515)
java.base/java.util.concurrent.FutureTask.run$$$capture(FutureTask.java:264)
java.base/java.util.concurrent.FutureTask.run(FutureTask.java)
java.base/java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1128)
java.base/java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:628)
java.base/java.lang.Thread.run(Thread.java:829)
This seems like an oversight from the KIE team, and I would submit it as an issue, if not for the fact that this exception only occurs when running the .jar file, after building.
I have no ide as to how IDEA compiles / runs a java application, but whenever I use that feature, this exception does not occur. So I'm a bit confused whether this is actually a bug in the KIE java client, or just me who did something wrong with my building.
I hope some of you might be able to help explain why KIE does what they do, and how it is me building the jar wrongly that causes the exception.
My pom.xml file is atrocious, but here it is;
<?xml version="1.0" encoding="UTF-8"?>
<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/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>dk.slp</groupId>
<artifactId>DroolsWrapper</artifactId>
<version>1.0.0-SNAPSHOT</version>
<packaging>jar</packaging>
<name>Drools :: Wrapper</name>
<description>
The Wrapper Program which handel validations on received objects from RabbitMQ, and send the result to the output queue.
</description>
<dependencyManagement>
<dependencies>
<dependency>
<groupId>org.junit</groupId>
<artifactId>junit-bom</artifactId>
<version>5.8.2</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
<properties>
<runtime.version>7.59.0.Final</runtime.version>
<java.version>8</java.version>
<maven.compiler.source>${java.version}</maven.compiler.source>
<maven.compiler.target>${java.version}</maven.compiler.target>
</properties>
<build>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<version>3.8.0</version>
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-surefire-plugin</artifactId>
<version>2.22.2</version>
<configuration>
<skipTests>true</skipTests>
</configuration>
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-assembly-plugin</artifactId>
<executions>
<execution>
<phase>package</phase>
<goals>
<goal>single</goal>
</goals>
<configuration>
<finalName>war</finalName>
<archive>
<manifest>
<mainClass>
SLPDrools
</mainClass>
</manifest>
</archive>
<descriptorRefs>
<descriptorRef>jar-with-dependencies</descriptorRef>
</descriptorRefs>
<appendAssemblyId>false</appendAssemblyId>
</configuration>
</execution>
</executions>
</plugin>
</plugins>
</build>
<repositories>
<repository>
<id>jboss-public-repository-group</id>
<name>JBoss Public Repository Group</name>
<url>http://repository.jboss.org/nexus/content/groups/public/</url>
<releases>
<enabled>true</enabled>
<updatePolicy>never</updatePolicy>
</releases>
<snapshots>
<enabled>true</enabled>
<updatePolicy>daily</updatePolicy>
</snapshots>
</repository>
</repositories>
<dependencies>
<dependency>
<groupId>org.drools</groupId>
<artifactId>drools-core</artifactId>
<version>${runtime.version}</version>
</dependency>
<dependency>
<groupId>org.drools</groupId>
<artifactId>drools-decisiontables</artifactId>
<version>${runtime.version}</version>
</dependency>
<dependency>
<groupId>org.jbpm</groupId>
<artifactId>jbpm-test</artifactId>
<version>${runtime.version}</version>
</dependency>
<dependency>
<groupId>org.kie.server</groupId>
<artifactId>kie-server-client</artifactId>
<version>${runtime.version}</version>
<scope>compile</scope>
</dependency>
<dependency>
<groupId>ch.qos.logback</groupId>
<artifactId>logback-classic</artifactId>
<version>1.2.10</version>
</dependency>
<dependency>
<groupId>com.rabbitmq</groupId>
<artifactId>amqp-client</artifactId>
<version>5.13.1</version>
</dependency>
<dependency>
<groupId>org.mockito</groupId>
<artifactId>mockito-all</artifactId>
<version>1.10.19</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.droolsassert</groupId>
<artifactId>droolsassert</artifactId>
<version>3.0.8</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.junit.jupiter</groupId>
<artifactId>junit-jupiter</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>com.google.guava</groupId>
<artifactId>failureaccess</artifactId>
<version>1.0.1</version>
</dependency>
</dependencies>
</project>
EDIT:
So I narrowed down the problem a bit further, by trying to build with gradle instead using this process
jar {
manifest {
attributes "Main-Class": "$mainClassName"
}
from {
configurations.runtimeClasspath.collect { it.isDirectory() ? it : zipTree(it) }
}
}
and it displays this error message;
Caused by: org.gradle.api.GradleException: Could not expand ZIP 'C:\Users\asger.weirsoe\.m2\repository\org\kie\kie-ci\7.59.0.Final\kie-ci-7.59.0.Final.jar'.
Now I'm no expert, and getting a bit frustrated in the JAVA building mechanism. But I think this might be my issue, that some library that I need, which is fetched in the background is not baked into the .jar file. Resulting in my issues.
I googled this and found this in the documentation for KIE. But tbh it just made me more confused than gave me answers.
Sources
This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.
Source: Stack Overflow
| Solution | Source |
|---|
