Trouble upgrading to couchbase java-client 2.6.1 - java

After upgrading the couchbase java-client to 2.6.1, I get the following error on application startup:
exception is java.lang.NoClassDefFoundError: com/couchbase/client/encryption/CryptoManager
After a quick investigation it looks that a Support for Field-Level Encryption was added since 2.6.0.
The problem seems to be the following transitive dependency:
<dependency>
<groupId>com.couchbase.client</groupId>
<artifactId>encryption</artifactId>
<version>${encryptionextension.version}</version>
<optional>true</optional>
</dependency>
which is marked as optional, however, it is declared in DefaultCouchbaseEnvironment and therefore cannot be optional.
The quick fix for this problem is to add the "encryption" transitive dependency to the classpath explicitly. Nevertheless, it seems to be a bug which will force all the clients to encounter the same problem.
UPDATE
The easiest way to reproduce the issue is to invoke the following code:
DefaultCouchbaseEnvironment.class.getDeclaredMethods();
This code is invoked by spring when loading coucbase environment as a spring bean. I've managed to isolate the issue to the single line of code which causes the problem.

Related

Missing dependency on EmbeddedKafka on integration test with groovy and spock

I've been trying to create an integration test using the embeddedKafka, but I'm getting problem of missing dependency when trying to run it, this is the error:
Unable to load class org.springframework.kafka.test.EmbeddedKafkaBroker due to missing dependency org/I0Itec/zkclient/serialize/ZkSerializer
I saw some stuff saying that this is related to my dependencies, so here is my dependencies:
springBootVersion = '2.3.5.RELEASE'
compile("org.springframework.boot:spring-boot-starter-web:${springBootVersion}")
compile("org.springframework.kafka:spring-kafka:${springBootVersion}")
testCompile("org.springframework.boot:spring-boot-starter-test:${springBootVersion}",
'org.spockframework:spock-core:1.2-groovy-2.4',
'org.spockframework:spock-spring:1.2-groovy-2.4',
'com.microsoft.azure:spring-data-cosmosdb:2.3.0',
'com.nimbusds:oauth2-oidc-sdk:5.64.4',
)
testCompile("org.springframework.kafka:spring-kafka-test:${springBootVersion}")
So, my question is, am I missing something?
EDIT
After changed the versions as indicated, I got a different error:
Error creating bean with name 'embeddedKafka': Invocation of init
method failed; nested exception is java.lang.NoClassDefFoundError:
scala/math/Ordering$$anon$7
I've added the scala dependencies, but still having the same issue:
testImplementation("org.scala-lang:scala-library:2.12.11")
testImplementation("org.scala-lang:scala-reflect:2.12.11")
You somehow have a mismatched kafka Vs. kafka-clients jars on the classpath; they all must be the same version.
You generally should not specify a version on boot's dependencies and use its dependency management instead.
You are pulling in spring-kafka 2.3.5 whereas spring-boot 2.3.5 requires spring-kafka 2.5.7.
Spring-kafka 2.5.x uses the kafka-clients 2.5.1.
See here for how to override versions of kafka jars when using a different version to the version that Boot prescribes.
the Kafka Client libraries for a time were inlining a particular version of the Scala library. This caused problems for those of us wanting to use the kafka client library with a slightly different version of Scala than that inline version.
In this cases the version of Scala they were using inline is Scala 2.12.10
They removed this dependency in later versions and this was backported as fixes (the earliest being 2.8.0) https://archive.apache.org/dist/kafka/2.8.0/RELEASE_NOTES.html)

Resolving conflict between transitive dependencies

I have a pom.xml where i've got hadoop-core dependency as provided
<dependency>
<groupId>org.apache.hadoop</groupId>
<artifactId>hadoop-core</artifactId>
<version>${hadoop.version}</version>
<scope>provided</scope>
</dependency>
When I add cfg4j as compile time dependency
<dependency>
<groupId>org.cfg4j</groupId>
<artifactId>cfg4j-core</artifactId>
<version>4.4.0</version>
</dependency>
<dependency>
<groupId>org.cfg4j</groupId>
<artifactId>cfg4j-consul</artifactId>
<version>4.4.0</version>
</dependency>
I've got an exception "java.lang.NoSuchMethodError: javax.ws.rs.core.Response.someMethod". I've investigated the problem and find out that the problem is from hadoop and cfg4j-consul. Hadoop core depends to jersey-core and cfg4j depends on cxf. Both declared javax.ws.rs as dependecy so the problem is that jersey has version 1.1 and cxf has 2.0.2. Hadoop dependency is provided, cause it's needed by Flink (framework) and it's in the lib folder. I can't just upgrade it or remove it, nor add it as compile time and exclude the lib. Even I was able to do it, I have no guarantees that hadoop will work as expected. I guess shading doesn't fix the problem cause it's not with cfg4j but one of the dependency of his dependency.
Is there way to resolve the conflict? Does gradle has it's onw ways to fix such issue?
Two approaches:
Shading: A bit more difficult as you say because this a transitive dependency, but I would have a look a Maven shade plugin and it would still be possible to declare the dependency directly if necessary.
Don't use the dependency and try to find some other library or solution for your problem.
Try the following steps, here is the source: https://reflectoring.io/nosuchmethod/
Your issue has nothing to do with the choice between Mavern and Gradle, switching therefor will not help.
Fixing a NoSuchMethodError
There are a lot of different flavors of NoSuchMethodErrors, but they all boil down to the fact that the compile time classpath differs from the runtime classpath.
The following steps will help to pinpoint the problem:
Step 1: Find Out Where the Class Comes From
First, we need to find out where the class containing the method in question comes from. We find this information in the error message of the NoSuchMethodError:
Exception in thread "main" java.lang.NoSuchMethodError:
io.reflectoring.nosuchmethod.Service.sayHello(Ljava/lang/String;)Ljava/lang/String;
Now, we can search the web or within the IDE to find out which JAR file contains this class. In the case above, we can see that it’s the Service class from our own codebase and not a class from another library.
If we have trouble finding the JAR file of the class, we can add the Java option -verbose:class when running our application. This will cause Java to print out all classes and the JARs they have been loaded from:
[Loaded io.reflectoring.nosuchmethod.Service from file:
/C:/daten/workspaces/code-examples2/patterns/build/libs/java-1.0.jar]
Step 2: Find Out Who Calls the Class
Next, we want find out where the method is being called. This information is available in the first element of the stack trace:
Exception in thread "main" java.lang.NoSuchMethodError:
io.reflectoring.nosuchmethod.Service.sayHello(Ljava/lang/String;)Ljava/lang/String;
at io.reflectoring.nosuchmethod.ProvokeNoSuchMethodError.main(ProvokeNoSuchMethodError.java:7)
Here, the class ProvokeNoSuchMethodError tries to call a method that does not exist at runtime. We should now find out which library this file belongs to.
Step 3: Check the Versions
Now that we know where the NoSuchMethodError is provoked and what method is missing, we can act.
We should now list all of our project dependencies.
In Gradle, we can call:
./gradlew dependencies > dependencies.txt
If we’re using Maven, a similiar result can be achieved with:
mvn dependency:list > dependencies.txt`
In this file, we can search for the libraries that contain the class with the missing method and the class that tries to call this method.
Usually we’ll find an output like this somewhere:
\--- org.springframework.retry:spring-retry:1.2.2.RELEASE
| \--- org.springframework:spring-core:4.3.13.RELEASE -> 5.0.8.RELEASE
The above means that the spring-retry library depends on spring-core in version 4.3.13, but some other library also depends on spring-core in version 5.0.8 and overrules the dependency version.
We can now search our dependencies.txt file for 5.0.8.RELEASE to find out which library introduces the dependency to this version.
Finally, we need to decide which of the two versions we actually need to satisfy both dependencies. Usually, this is the newer version since most frameworks are backwards compatible to some point. However, it can be the other way around or we might even not be able to resolve the conflict at all.

NoClassDefFoundError for ValueExtractorManager when using DL4J with JDK 1.8.265

I receive
java.lang.NoClassDefFoundError: Could not initialize class org.hibernate.validator.internal.engine.valueextraction.ValueExtractorManager
when using JDK version 1.8.0_265 and having one or more DL4J dependencies (version 1.0.0-beta7) in my Maven dependencies in Spring Boot application. This error doesn't occur on JDK v1.8.0_272.
My application runs on Spring Boot 2.3.7.RELEASE. I checked DL4J dependencies and listed the ones that cause this exception below:
<dependency>
<groupId>org.deeplearning4j</groupId>
<artifactId>deeplearning4j-core</artifactId>
<version>1.0.0-beta7</version>
</dependency>
<dependency>
<groupId>org.deeplearning4j</groupId>
<artifactId>arbiter-deeplearning4j</artifactId>
<version>1.0.0-beta7</version>
</dependency>
<dependency>
<groupId>org.deeplearning4j</groupId>
<artifactId>deeplearning4j-ui-model</artifactId>
<version>1.0.0-beta7</version>
</dependency>
This happens on both Linux and Windows with JDK (AdoptOpenJDK) v.1.8.265 but it works fine with JDK v1.8.272.
It's a bit critical for us to stick to 265 version and it's impossible to stop using Hibernate in the application.
Can't share full stacktrace as it's related to the project code but one of the places where this exception is throw is while instantiating javax.validation.Validation:
Validation.buildDefaultValidatorFactory().getValidator(); // this line causes NoClassDefFoundError
I ran mvn dependencies:tree and there's no Hibernate dependencies shown for the whole project so I assume the the dependencies above use old version of Hibernate that causes error because it conflicts with Hibernate from Spring but that's just an assumption because it definitely has something to do with JDK.
Is there a way to identify what exactly causes a problem and fix it without moving to new JDK?

"NoClassDefFoundError: javax/inject/Provider" even with javax.inject dependency included

After upgrading some Glassfish/Grizzly dependencies (in order to be compatible with the latest version of Azure's SDK IOT device client), I started getting an error because com.google.common.EventBus no longer existed. Adding the dependency:
<dependency>
<groupId>com.google.guava</groupId>
<artifactId>guava</artifactId>
<version>15.0</version>
</dependency>
fixed that, and it was able to run locally in IntelliJ. However, when I deployed the .deb file that was compiled to a Raspberry Pi, it started producing the error:
java.lang.NoClassDefFoundError: javax/inject/Provider
at com.google.inject.internal.MoreTypes.canonicalizeForKey(MoreTypes.jav
a:81)
at com.google.inject.Key.(Key.java:119)
at com.google.inject.Key.get(Key.java:212)
at com.google.inject.spi.Elements$RecordingBinder.bind(Elements.java:262
)
at com.google.inject.internal.InjectorShell$RootModule.configure(InjectorShell.java:276)
at com.google.inject.spi.Elements$RecordingBinder.install(Elements.java:223)
at com.google.inject.spi.Elements.getElements(Elements.java:101)
at com.google.inject.internal.InjectorShell$Builder.build(InjectorShell.java:133)
at com.google.inject.internal.InternalInjectorCreator.build(InternalInjectorCreator.java:103)
at com.google.inject.Guice.createInjector(Guice.java:95)
at com.google.inject.Guice.createInjector(Guice.java:72)
at com.google.inject.Guice.createInjector(Guice.java:62)
at com.infusion.empm.Main.main(Main.java:32) Caused by: java.lang.ClassNotFoundException: javax.inject.Provider
at java.net.URLClassLoader$1.run(URLClassLoader.java:366)
I read in a number of places that adding the dependency
<dependency>
<groupId>javax.inject</groupId>
<artifactId>javax.inject</artifactId>
<version>1</version>
</dependency>
is supposed to fix that (I already had the guice & javax-servlet-api dependencies referenced here), but it had no effect. When I do so, the result is two javax.inject jars (the other one being generated would seem to explain why I didn't need to explicitly add version 1 to get it to run locally):
javax.inject-2.5.0-b42.jar
javax.inject-1.jar
Someone else here used exclusions when they had those two jars, but even when I change my hk2 dependency accordingly, both jars are still present. I've also heard that adding javax.ws.rs-api is supposed to help, but that was already there. The imports in the Java code refer directly to com.google.inject.Provider, so I don't think there's any need to call guicify to convert a JSR-330 provider to a Guice one. Replacing every "com.google.inject" import in the local code with "java.inject" results in the same exact behavior, so it must be a dependency referencing google's code, which is in turn failing to find javax.
It turned out the cause was a script on the Pi which hardcoded the jars in the classpath.

Upgrading gwt from 2.1.1 to 2.8.0: ServiceConfigurationError: org.apache.juli.logging.Log: Provider org.eclipse.jetty.apache.jsp.JuliLog not a subtype

After upgrading gwt from version 2.1.1 to 2.8.0, I got the error message
2017-04-20 12:59:19.551:WARN:oejuc.AbstractLifeCycle:main: FAILED c.g.g.d.s.j.WebAppContextWithReload#341fbaf1{/,file:/C:/Users/xxx/.IntelliJIdea2017.1/system/gwt/xxx.97baa614/xxx.fdf824a8/run/www/,STARTING}{C:\Users\xxx\.IntelliJIdea2017.1\system\gwt\xxx.97baa614\xx.fdf824a8\run\www}: java.util.ServiceConfigurationError: org.apache.juli.logging.Log: Provider org.eclipse.jetty.apache.jsp.JuliLog not a subtype
java.util.ServiceConfigurationError: org.apache.juli.logging.Log: Provider org.eclipse.jetty.apache.jsp.JuliLog not a subtype
I found some other posts with similar messages, like this or this, but the situation seems to be different:
I do not use Maven or Ant, just pure IntelliJ, I have no reference to any Tomcat library, and I am not aware of any JSP in our application.
I found through debugging that first the class loader com.google.gwt.dev.shell.jetty.Jettylauncher$WebAppContextWithReload$WebAppClassLoaderExtension loads class org.eclipse.jetty.apache.jsp.JuliLog including interface org.apache.juli.logging.Log.
Then, later interface org.apache.juli.logging.Log is loaded by sun.misc.Launcher$AppClassLoader triggered indirectly by
org.eclipse.jetty.webapp.WebAppContext.startContext()
which calls method initialize of an
org.eclipse.jetty.jsp.JettyJspServlet
instance.
I have no idea why a JspServlet needs to be initialized at all, as no JSPs are used in the application, as far as I see, just a few Servlets. And it seems all the classes involved in this conflict are contained in the single jar gwt-dev.jar, so I see no possibility to influence any class loading behavior via class path settings.
Any idea how I could resolve this?
I also got this error upgrading from gwt from version 2.4 to 2.8.2.
Jake W's answer helped me.
To solve this, I ran a maven dependency tree on my project to figure out what was referencing jetty's apache-jsp.
To run the dependency tree, in Eclipse I created a new run configuration -> maven build -> with the goals "dependency:tree -Doutput=/dependency/file.txt". Once it's run, the console output will show where it saves the output. It should be the same location that you referenced with the -Doutput option.
Look for something like this in the output file:
- org.eclipse.jetty:apache-jsp:jar:9.2.14.v20151106:compile
And then look up in the tree to see where it's being pulled in from. In my case it came from this:
+- com.google.gwt:gwt-dev:jar:2.8.2:compile
+- net.sourceforge.htmlunit:htmlunit:jar:2.19:compile
\- org.eclipse.jetty:apache-jsp:jar:9.2.14.v20151106:compile
Once you know where it's coming from, (assuming you're using maven) you can add an exclusion in your pom.xml file for it:
</dependencies>
<dependency>
<groupId>com.google.gwt</groupId>
<artifactId>gwt-dev</artifactId>
<version>${gwt.version}</version>
<exclusions>
<exclusion>
<groupId>org.eclipse.jetty</groupId>
<artifactId>apache-jsp</artifactId>
</exclusion>
</exclusions>
</dependency>
</dependencies>
This worked for me. Thanks :)
I saw this error when I recently upgraded to GWT 2.8.0. Please try to exclude jetty-apache-Jsp related dependencies from your project.
You may see other jetty related issues as well, so please also make sure you are using exactly the same jetty version as GWT 2.8.0 is using.
I'm on mobile at the moment, unable to add more details, but I hope that can be a useful direction to go. Please add your comments if you still see issues, I will then have a look and update the answer when I'm on my laptop.
I have just ran into this exception after adding gwt-test-utils:0.53 dependency (with GWT 2.8.1)
I am using ant and all information found regarding this error indicated there was 2 versions of Juli Logging in the classpath, but every search came up with only gwt-dev.jar. Production builds worked fine, but dev mode did not which needs gwt-dev.jar.
Part of the build process has the jars copied from a local lib directory to war/WEB-INF/lib to pack into the war. The ant script points to the local lib directory for debugging, not the ones meant for the war file. Despite the war location not being listed in the ant file as a class path, it was still loading it.
Ultimately, gwt-dev.jar was conflicting with the copied version of itself.

Categories

Resources