24

I recently started upgrading my application JDK version from jdk1.7.0_121_x64 to jdk1.8.0_202_x64. I have some legacy code using Drools 5.4.0.Final. This code is working with JDK version jdk1.7.0_121_x64 without any issue.

Maven dependencies are:

<dependency>
    <groupId>org.drools</groupId>
    <artifactId>drools-core</artifactId>
    <version>5.4.0.Final</version>
</dependency>
<dependency>
    <groupId>org.drools</groupId>
    <artifactId>drools-decisiontables</artifactId>
    <version>5.4.0.Final</version>
</dependency>

DRL files are loaded as:

final KnowledgeBase kbase = KnowledgeBaseFactory.newKnowledgeBase();
final KnowledgeBuilder kbuilder = KnowledgeBuilderFactory.newKnowledgeBuilder();
kbuilder.add(resource, ResourceType.DRL);
knowledgeBase.addKnowledgePackages(kbuilder.getKnowledgePackages());

I was aware that there are issues using Drools with JDK 8. I referrred to other SO thread to start with.


When I built my application and executed Junit tests using JDK 8, tests failed with error:

testRunRule(com.company.app.RuleTest)  Time elapsed: 0.073 sec  <<< ERROR!
java.lang.RuntimeException: java.lang.RuntimeException: wrong class format
    at org.eclipse.jdt.internal.compiler.classfmt.ClassFileReader.<init>(ClassFileReader.java:372)
    at org.drools.commons.jci.compilers.EclipseJavaCompiler$2.createNameEnvironmentAnswer(EclipseJavaCompiler.java:287)
    at org.drools.commons.jci.compilers.EclipseJavaCompiler$2.findType(EclipseJavaCompiler.java:258)

As mentioned in SO thread, I found reference to this bugfix ticket DROOLS-329.


Based on approaches mentioned in this bugfix ticket, I tried to use JANINO compiler:

Added following maven dependency:

<dependency>
    <groupId>org.codehaus.janino</groupId>
    <artifactId>janino</artifactId>
    <version>2.5.16</version>
</dependency>

I added following VM argument (I was running tests from eclipse, so in eclipse launch configuration in JRE VM argument added the argument):

-Ddrools.dialect.java.compiler=JANINO

I could still see the wrong class format error. So I modified my code to load DRL files as:

final KnowledgeBase kbase = KnowledgeBaseFactory.newKnowledgeBase();
final Properties props = new Properties();
props.setProperty("drools.dialect.java.compiler", "JANINO");
final KnowledgeBuilderConfiguration config = KnowledgeBuilderFactory.newKnowledgeBuilderConfiguration(props, null);
final KnowledgeBuilder kbuilder = KnowledgeBuilderFactory.newKnowledgeBuilder(config);
kbuilder.add(resource, ResourceType.DRL);
knowledgeBase.addKnowledgePackages(kbuilder.getKnowledgePackages());

It didn't help. I could still see the wrong class format error.


I followed another apprroach mentioned in this external link. I updated added/updated maven dependencies as:

<dependency>
    <groupId>org.drools</groupId>
    <artifactId>drools-core</artifactId>
    <version>5.4.0.Final</version>
    <exclusions>
      <exclusion>
          <groupId>org.mvel</groupId>
          <artifactId>mvel2</artifactId>
      </exclusion>
   </exclusions>
</dependency>
<dependency>
    <groupId>org.drools</groupId>
    <artifactId>drools-decisiontables</artifactId>
    <version>5.4.0.Final</version>
    <exclusions>
      <exclusion>
          <groupId>org.eclipse.jdt.core.compiler</groupId>
          <artifactId>ecj</artifactId>
      </exclusion>
      <exclusion>
          <groupId>org.mvel</groupId>
          <artifactId>mvel2</artifactId>
      </exclusion>
   </exclusions>
</dependency>
<dependency>
    <groupId>org.mvel</groupId>
    <artifactId>mvel2</artifactId>
    <version>2.1.9.Final</version>
</dependency>
<dependency>
   <groupId>org.eclipse.jdt.core.compiler</groupId>
   <artifactId>ecj</artifactId>
   <version>4.6.1</version>
</dependency>

mvel2 patch is built using: https://github.com/mkornipati/mvel/tree/2.1.9.Final.Patch

With this wrong class format error is gone. But my tests are now failing with following error:

testRunRule(com.company.app.RuleTest))  Time elapsed: 4.684 sec  <<< ERROR!
java.lang.RuntimeException: org.drools.rule.InvalidRulePackage: Rule Compilation error : [Rule name='ruleCheck']
    org/drools/template/parser/Rule_ruleCheck_8eb4621227714a36b7b84c8b764527e4.java (2:80) : Only a type can be imported. java.util.Map resolves to a package
    org/drools/template/parser/Rule_ruleCheck_8eb4621227714a36b7b84c8b764527e4.java (2:101) : Only a type can be imported. java.util.HashMap resolves to a package
    org/drools/template/parser/Rule_ruleCheck_8eb4621227714a36b7b84c8b764527e4.java (6:299) : org.drools.spi.KnowledgeHelper cannot be resolved to a type
    org/drools/template/parser/Rule_ruleCheck_8eb4621227714a36b7b84c8b764527e4.java (6:339) : org.drools.template.parser.Row cannot be resolved to a type
    org/drools/template/parser/Rule_ruleCheck_8eb4621227714a36b7b84c8b764527e4.java (6:373) : org.drools.FactHandle cannot be resolved to a type
    org/drools/template/parser/Rule_ruleCheck_8eb4621227714a36b7b84c8b764527e4.java (6:411) : org.drools.template.parser.DefaultGenerator cannot be resolved to a type
    org/drools/template/parser/Rule_ruleCheck_8eb4621227714a36b7b84c8b764527e4.java (6:487) : org.drools.runtime.rule.RuleContext cannot be resolved to a type
    at org.drools.rule.Package.checkValidity(Package.java:445)

I don't know how to proceed further. Please let me know if you are able to make Drools 5.4 work with JDK 8.

user613114
  • 2,459
  • 10
  • 40
  • 68
  • 3
    1+ for the effort, I wish I would have an answer though. – Eugene Jan 12 '20 at 20:37
  • Have you considered a Drools upgrade? – Boris Jan 13 '20 at 12:01
  • @Boris: Right now I am trying with 5.6.0.Final version. From 6.x onwards, I know that KnowledgeBase is deprecated and I need to use KieBase. But it's an old code, and we do not wish to touch it. I learnt that people are able to run Drools 5.x using JDK 8 (e.g. URL mentioned in my post). So we are just trying to make existing version work with JDK 8. With JDK 1.7, code is running without any issue. – user613114 Jan 13 '20 at 13:18
  • @Boris: Tried with Drools version 5.6.0.Final. Output is same as version 5.4.0.Final. – user613114 Jan 13 '20 at 13:53
  • I see. Regards the old code, but you are touching it since you are upgrading Java. A professional software engineer's reply would be if you're upgrading one part of the software which requires further upgrades you have to do all of them, or none. If current version of Drupal doesn't support Java 8 I would never consider such an upgrade. What do you think? – Boris Jan 13 '20 at 14:54
  • 1
    @Boris: I would do it only if it's really necessary: 1) We do not have any documentation about this code. Person who wrote this code is not with us anymore. 2) Additional efforts are needed to migrate/test this code. Drools APIs themselves are changed. 3) There are references where people are able to run Drools 5.x with JDK 8 very minor modification (e.g. the URL mentioned in my post). So I would really give a try to make it run using easier approach first. – user613114 Jan 13 '20 at 15:02
  • How about providing an [MCVE](https://stackoverflow.com/help/mcve) on GitHub? This is too complex and has too many variables to exactly guess your setup. I cannot copy and compile + run your snippets. – kriegaex Jan 18 '20 at 05:53
  • @kriegaex: Let me try to create MCVE. – user613114 Jan 19 '20 at 22:20
  • This is possible; I did it with a Drools 5.0 app for my last company. Unfortunately I don't remember what I did (there's two properties to set on the knowledge builder). I'll see if I can't whip up an example app and figure it out. – Roddy of the Frozen Peas Feb 22 '20 at 21:04
  • It's going to be something specific to your implementation. I just created a Drools 5.0.1 project and ran it on Java 8 and it worked using your original KnowledgeBuilder code. Also tried 5.4.0 and it worked. Can you share the content of this "ruleCheck" rule that it dislikes? – Roddy of the Frozen Peas Feb 22 '20 at 21:33
  • OK. My example in 5.x works out of the box if you use the mvel dialect, but fails with the compiler errors for Java dialect. But without seeing what your rules look like, I can't help you further. – Roddy of the Frozen Peas Feb 22 '20 at 21:54
  • Where's that `RuleTest` class? – hfontanez Feb 08 '21 at 21:26

1 Answers1

1

I used Drools 7.7.0 with Java 8 and worked great for me. I am not sure what is the oldest Drools version that is compatible with Java 8. That said, Drools 5.4.0 was released in 2011. Java 8 was released in 2014, so you can assume it won't be compatible. Java 7 was released in July 2011. Depending on when 5.4.0 was released it might or might not be. Based on that, I expect Drools 5.4.0 to be compatible with Java 6 or earlier. If you want to use Java 8 with Drools, I don't see how you can without upgrading. I think the earliest compatible version is 6.1.0 download.jboss.org/drools/release.

In summary: Either downgrade your project to Java 6 to use Drools 5.4.0 or Upgrade Drools to use 6.1.0. Better yet, upgrade to latest Drools and then figure out what is the latest Java version it supports.

hfontanez
  • 2,640
  • 2
  • 21
  • 29