Class path contains multiple SLF4J bindings, exclusion not working, - java

I get the following error:
SLF4J: Class path contains multiple SLF4J bindings.
SLF4J: Found binding in [jar:file:/C:/Users/Vash/.m2/repository/ch/qos/logback/logback-classic/1.2.3/logback-classic-1.2.3.jar!/org/slf4j/impl/StaticLoggerBinder.class]
SLF4J: Found binding in [jar:file:/C:/Users/Vash/.m2/repository/org/slf4j/slf4j-jdk14/1.7.25/slf4j-jdk14-1.7.25.jar!/org/slf4j /impl/StaticLoggerBinder.class]
I've already checked https://www.slf4j.org/codes.html#multiple_bindings
and similar questions. I've found using mvn dependency:tree that 4 dependencies use SLF4J so I've added the exclusion to them like this:
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
<exclusions>
<exclusion>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-log4j12</artifactId>
</exclusion>
<exclusion>
<groupId>log4j</groupId>
<artifactId>log4j</artifactId>
</exclusion>
</exclusions>
This didn't change anything and I still get the same error. I've tried deleting the .jar files specified in the warning but then I get error about missing classes. Also I'm using IntelliJ so maybe somehow reloading the pom.xml file is the issue here?

I think this is a bug/feature in Maven. Let's assume you have this dependency tree:
A
+---B
+---C
| +---D
|
+---D
and you exclude D on B, it will still be there because C also pulls it in. From Maven's point of view this makes sense because it doesn't try to understand whether there is a relationship between B and C. We know that they're all from Spring but Maven can't be so sure.
Solution: You need to duplicate the exclusion on C in your POM.
Use mvn dependency:tree to find all places where D is being used and add one exclusion each.
And make sure you actually exclude D. In your example above, you exclude org.slf4j:slf4j-log4j12 instead of org.slf4j:slf4j-jdk14

Related

SLF4J: Class path contains multiple SLF4J bindings In iNTELIJI LENGUAGE JAVA [duplicate]

I'm getting the following error. It seems there are multiple logging frameworks bound to slf4j. Not sure how to resolve this. Any help is greatly appreciated.
SLF4J: Class path contains multiple SLF4J bindings.
SLF4J: Found binding in [jar:file:/C:/Users/admin/.m2/repository/org/slf4j/slf4j-log4j12/1.6.4/slf4j-log4j12-1.6.4.jar!/org/slf4j/impl/StaticLoggerBinder.class]
SLF4J: Found binding in [jar:file:/C:/Users/admin/.m2/repository/org/slf4j/slf4j-log4j12/1.6.1/slf4j-log4j12-1.6.1.jar!/org/slf4j/impl/StaticLoggerBinder.class]
SLF4J: See http://www.slf4j.org/codes.html#multiple_bindings for an explanation.
Resolved by adding the following exclusion in the dependencies (of pom.xml) that caused conflict.
<exclusions>
<exclusion>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-log4j12</artifactId>
</exclusion>
</exclusions>
Gradle version;
configurations.all {
exclude module: 'slf4j-log4j12'
}
The error probably gives more information like this (although your jar names could be different)
SLF4J: Found binding in
[jar:file:/D:/Java/repository/ch/qos/logback/logback-classic/1.2.3/logback-classic-1.2.3.jar!/org/slf4j/impl/StaticLoggerBinder.class]
SLF4J: Found binding in
[jar:file:/D:/Java/repository/org/apache/logging/log4j/log4j-slf4j-impl/2.8.2/log4j-slf4j-impl-2.8.2.jar!/org/slf4j/impl/StaticLoggerBinder.class]
Noticed that the conflict comes from two jars, named logback-classic-1.2.3 and log4j-slf4j-impl-2.8.2.jar.
Run mvn dependency:tree in this project pom.xml parent folder, giving:
Now choose the one you want to ignore (could consume a delicate endeavor I need more help on this)
I decided not to use the one imported from spring-boot-starter-data-jpa (the top dependency) through spring-boot-starter and through spring-boot-starter-logging, pom becomes:
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter</artifactId>
<exclusions>
<exclusion>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-logging</artifactId>
</exclusion>
</exclusions>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-jpa</artifactId>
</dependency>
in above pom spring-boot-starter-data-jpa would use the spring-boot-starter configured in the same file, which excludes logging (it contains logback)
Sbt version:
Append exclude("org.slf4j", "slf4j-log4j12") to the dependency that transitively includes slf4j-log4j12. For example, when using Spark with Log4j 2.6:
libraryDependencies ++= Seq(
// One SLF4J implementation (log4j-slf4j-impl) is here:
"org.apache.logging.log4j" % "log4j-api" % "2.6.1",
"org.apache.logging.log4j" % "log4j-core" % "2.6.1",
"org.apache.logging.log4j" % "log4j-slf4j-impl" % "2.6.1",
// The other implementation (slf4j-log4j12) would be transitively
// included by Spark. Prevent that with exclude().
"org.apache.spark" %% "spark-core" % "1.5.1" exclude("org.slf4j", "slf4j-log4j12")
)
1.Finding the conflicting jar
If it's not possible to identify the dependency from the warning, then you can use the following command to identify the conflicting jar
mvn dependency: tree
This will display the dependency tree for the project and dependencies who have pulled in another binding with the slf4j-log4j12 JAR.
Resolution
Now that we know the offending dependency, all that we need to do is exclude the slf4j-log4j12 JAR from that dependency.
Ex - if spring-security dependency has also pulled in another binding with the slf4j-log4j12 JAR, Then we need to exclude the slf4j-log4j12 JAR from the spring-security dependency.
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-security</artifactId>
<exclusions>
<exclusion>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-logging</artifactId>
</exclusion>
</exclusions>
</dependency>
Note - In some cases multiple dependencies have pulled in binding with the slf4j-log4j12 JAR and you don't need to add exclude for each and every dependency that has pulled in.
You just have to do that add exclude dependency with the dependency which has been placed at first.
Ex -
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
<exclusions>
<exclusion>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-logging</artifactId>
</exclusion>
</exclusions>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-security</artifactId>
</dependency>
</dependencies>
If you work with gradle then add following code to your build.gradle file to exclude SLF4J binding from all the modules
configurations.all {
exclude group: 'org.springframework.boot', module: 'spring-boot-starter-logging'
}
I just ignored/removed that jar file.
<!--<dependency>-->
<!--<groupId>org.springframework.boot</groupId>-->
<!--<artifactId>spring-boot-starter-log4j2</artifactId>-->
<!--</dependency>-->
I solved by delete this:spring-boot-starter-log4j2
Just use only required dependency, not all :))). For me, for normal work of logging process you need this dependency exclude others from pom.xml
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-api</artifactId>
<version>1.7.5</version>
</dependency>
<dependency>
<groupId>ch.qos.logback</groupId>
<artifactId>logback-classic</artifactId>
<version>1.1.8</version>
</dependency>
<dependency>
<groupId>ch.qos.logback</groupId>
<artifactId>logback-core</artifactId>
<version>1.1.8</version>
</dependency>
This is issue because of StaticLoggerBinder.class class belongs to two different jars. this class references from logback-classic-1.2.3.jar and same class also referenced from log4j-slf4j-impl-2.10.0.jar. both of jar in classpath. Hence there is conflict between them.
This is reason of log file is not generation even though log4j2.xml file in classpath [src/main/resource].
We have so select one of jar, I recommend use log4j-slf4j-impl-2.10.0.jar file and exclude logback-classic-1.2.3.jar file.
Solution: open pom file and view the dependency Hierarchy [eclipse] or run
mvn dependency:tree command to find out the dependency tree and source of dependency that download the dependency. find the conflicting dependency and exclude them. For Springboot application try this.
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
<exclusions>
<exclusion>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-logging</artifactId>
</exclusion>
</exclusions>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-actuator</artifactId>
<exclusions>
<exclusion>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-logging</artifactId>
</exclusion>
</exclusions>
</dependency>
This is working fine for me after struggling a lots.
...
org.codehaus.mojo
cobertura-maven-plugin
2.7
test
ch.qos.logback
logback-classic
tools
com.sun
...
## I fixed with this
...
org.codehaus.mojo
cobertura-maven-plugin
2.7
test
ch.qos.logback
logback-classic
tools
com.sun
...
For me, it turned out to be an Eclipse/Maven issue after switch from log4j to logback. Take a look into your .classpath file and search for the string "log4j".
In my case I had the following there:
<classpathentry kind="var" path="M2_REPO/org/slf4j/slf4j-log4j12/1.7.1/slf4j-log4j12-1.7.1.jar"/>
<classpathentry kind="var" path="M2_REPO/log4j/log4j/1.2.17/log4j-1.2.17.jar" />
Removing those entries from the file (or you could regenerate it) fixed the issue.
For me the answer was to force a Maven rebuild. In Eclipse:
Right click on project-> Maven -> Disable Maven nature
Right click on project-> Spring Tools > Update Maven Dependencies
Right click on project-> Configure > Convert Maven Project
I solved this by going to Project Structure from my Intellij project.
I deleted the file named: Maven: org.apache.logging.log4j:log4j-to-slf4j-impl:2.14.1
This file is not shown in this picture. You may see two libraries mentioned as log4j-to-slf4j. Delete one and you are good to go.
For all those looking for the solution for spring-boot-type dependencies, the magic incantation for Gradle is this:
configurations.all {
exclude group: 'ch.qos.logback', module: 'logback-classic'
}
in your build.gradle at the top level (not inside the dependencies block).
All other solutions found in the interwebs (including the one here suggesting to exclude the slf4j module) did not work for me.
This is what I have in my build.gradle (snippet):
// Removes the annoying warning about the multiple SLF4J implementations:
// SLF4J: Class path contains multiple SLF4J bindings.
configurations.all {
exclude group: 'ch.qos.logback', module: 'logback-classic'
}
dependencies {
annotationProcessor "org.springframework.boot:spring-boot-configuration-processor"
implementation ('org.springframework.boot:spring-boot-starter-actuator')
implementation ('org.springframework.boot:spring-boot-starter-data-mongodb-reactive')
implementation ('org.springframework.boot:spring-boot-starter-webflux')
annotationProcessor "org.projectlombok:lombok:${lombokVersion}"
compileOnly "org.projectlombok:lombok:${lombokVersion}"
// Removes the annoying warning:
// warning: unknown enum constant When.MAYBE
// reason: class file for javax.annotation.meta.When not found
// See: https://stackoverflow.com/questions/29805622/could-not-find-or-load-main-class-org-gradle-wrapper-gradlewrappermain/31622432
implementation group: 'com.google.code.findbugs', name: 'jsr305', version: '3.0.2'
// other stuff...
YMMV
I had the same problem. In my pom.xml i had both
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-simple</artifactId>
<version>1.7.28</version>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
<version>2.2.1.RELEASE</version>
</dependency>
When i deleted the spring-boot-starter-web dependency, problem was solved.
I got this issue in a non-maven project, two depended jar each contained a slf4j. I solved
by remove one depended jar, compile the project(which of course getting failure) then add the removed one back.
In case these logs are the result of this fix:
https://stackoverflow.com/a/9919375/2894819
When one of your libraries actually use it. And your application doesn't need SL4J just replace implementation to runtimeOnly.
// contains dependency to sl4j-api
implementation("com.github.doyaaaaaken:kotlin-csv-jvm:1.2.0")
// add this to remove both warnings
runtimeOnly("org.slf4j:slf4j-nop:1.7.36")
In that case when you run your app the actual dependency will be included once by the library and won't be included to the bundle of your application.jar itself.
In my case I had 2 sources of dependencies for log4 one in C:\Program Files\smcf.ear directory and the second from maven which caused the multiple binding for sl4j.
Deleting the smcf.ear directory solved the issue for me.
The combination of <scope>provided</scope> and <exclusions> didn't work for me.
I had to use this:
<dependency>
<groupId>ch.qos.logback</groupId>
<artifactId>logback-classic</artifactId>
<scope>system</scope>
<systemPath>${project.basedir}/empty.jar</systemPath>
</dependency>
Where empty.jar is a jar file with literally nothing in it.
Seems removing .m2 directory and :
mvn install -DskipTests -T 4 resolved this issue for me.

JAVA SLF4J: Class path contains multiple SLF4J bindings on debug

I'm building a Java API and this happens on my vsCode when I try to debug my main class :
SLF4J: Class path contains multiple SLF4J bindings.
SLF4J: Found binding in [jar:file:/C:/Users/CDINDELE/.m2/repository/org/slf4j/slf4j-log4j12/1.7.25/slf4j-log4j12-1.7.25.jar!/org/slf4j/impl/StaticLoggerBinder.class]
I know this is a exclusion issue, so I've excluded the slf4j from my dependencies like this:
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-jpa</artifactId>
<exclusions>
<exclusion>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-over-log4j12</artifactId>
</exclusion>
</exclusions>
</dependency>
It works well with mvn install, and my API is working great with
java -jar myWar
However when I'm trying to use the debug with vscode on my main class (using the java plugin) the issue is coming back so it's impossible for me to debug this app which is not very convenient.
Any ideas ? Thanks

SLF4J: Class path contains multiple SLF4J bindings; exclude slf4j

I am trying to load a Video using OpenIMAJ. It does Display the Video but always shows me this Error:
SLF4J: Class path contains multiple SLF4J bindings.
SLF4J: Found binding in [jar:file:/C:/Users/MaryLu/.m2/repository/ch/qos/logback/logback-classic/1.0.0/logback-classic-1.0.0.jar!/org/slf4j/impl/StaticLoggerBinder.class]
SLF4J: Found binding in [jar:file:/C:/Users/MaryLu/.m2/repository/org/slf4j/slf4j-log4j12/1.7.2/slf4j-log4j12-1.7.2.jar!/org/slf4j/impl/StaticLoggerBinder.class]
SLF4J: See http://www.slf4j.org/codes.html#multiple_bindings for an explanation.
SLF4J: Actual binding is of type [ch.qos.logback.classic.selector.DefaultContextSelector]
16/04/24 20:39:57 INFO xuggle.XuggleVideo: URL file:/F:/workspaceMaven/keyboardcat.flv could not be opened by ffmpeg. Trying to open a stream to the URL instead.
20:39:57.984 [main] DEBUG com.xuggle.xuggler - Could not open output url: file:/F:/workspaceMaven/keyboardcat.flv (../../../../../../../csrc/com/xuggle/xuggler/Container.cpp:436)
I already checked Similar Questions but I didn't manage to solve the problem. If i understood, i need to exclude slf4j somewhere in my POM.xml but i don't really know in which dependency.
Already the answer is given in your log file. Follow the tutorial.
http://www.slf4j.org/codes.html#multiple_bindings
As Wouter stated
Run mvn dependency:tree and search which dependency have the slf4j implementations you do not want, then exclude them with a dependency exclusion like:
<dependency>
<groupId>org.someexternallib</groupId>
<artifactId>someexternallibartifact</artifactId>
<version>...</version>
<exclusions>
<exclusion>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-log4j12</artifactId>
</exclusion>
<exclusion>
<groupId>log4j</groupId>
<artifactId>log4j</artifactId>
</exclusion>
</exclusions>
</dependency>
The slf4j messages is just telling you that your slf4j configuration is broken so it falls back to a default configuration.
The real problem is that your URL does not point to a local file as you apparently expect it to because it is broken, so the code trying to use it fails. A possible reason for the brokenness might be if you have the file open already somewhere, so Windows will not allow it to be overwritten.
<exclusion>
<artifactId>logback-classic</artifactId>
<groupId>ch.qos.logback</groupId>
</exclusion>
<exclusion>
<artifactId>slf4j-simple</artifactId>
<groupId>org.slf4j</groupId>
</exclusion>
In order to find the dependencies that use above artifact, find out by
"$ mvn dependency:tree"
once you find that out put the above exclusions on the corresponding dependencies. That should fix it, I would say pay attention on specific dependencies.

Exception in java project [java.lang.IllegalAccessError: tried to access field org.slf4j.impl.StaticLoggerBinder.SINGLETON]

Exception in thread "main" java.lang.IllegalAccessError: tried to access field org.slf4j.impl.StaticLoggerBinder.SINGLETON from class org.slf4j.LoggerFactory
at org.slf4j.LoggerFactory.<clinit>(LoggerFactory.java:60)
at org.hibernate.cfg.Configuration.<clinit>(Configuration.java:151)
at com.erp.utility.Hibernatesession.getSession(Hibernatesession.java:24)
at com.erp.dao.Country_Dao.getcountryByname(Country_Dao.java:88)
at com.erp.service.Country_Service.getcountryByname(Country_Service.java:36)
at com.erp.storedata.Store_Data.main(Store_Data.java:24)
Use a newer version of the slf4j-api.jar. There was a breaking change between version 1.5.5 and earlier and 1.5.6 and later. Use a version after 1.5.6, and that error should go away. For reference, see http://www.slf4j.org/faq.html#IllegalAccessError.
Please add following file on your project:
slf4j-log4j12.jar
remove the file slf4j-api.jar from your build path.
Finally resolved this problem in my SpringBoot application. If updating version is not helping this might help. Sometimes other libraries might bring different versions of this dependencies. These are the steps:
By error stack trace figure out which dependency is giving this issue
Get maven dependency plugin tree. Using this tree details find out if this library is coming as part of the some other dependency. In my case, the logback-classic and log4j-over-slf4j were giving this problem. They came together under spring-boot-starter-web
Use <exclusions><exclusion></exclusion></exclusions> in your pom.xml in that dependency for the libraries that giving this issue. In my case it looks like this:
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
<exclusions>
<exclusion>
<artifactId>logback-classic</artifactId>
<groupId>ch.qos.logback</groupId>
</exclusion>
<exclusion>
<artifactId>log4j-over-slf4j</artifactId>
<groupId>org.slf4j</groupId>
</exclusion>
</exclusions>
</dependency>
References:
http://www.slf4j.org/faq.html#IllegalAccessError
http://www.slf4j.org/codes.html#multiple_bindings

How to add exclude certain packages from an external maven dependency

My Application depends on an external jar
<dependency>
<groupId>org.objectweb.joram</groupId>
<artifactId>jftp</artifactId>
<version>1.52</version>
</dependency>
I am mainly interested in using the following package import net.sf.jftp.net.*
But looks like this jar also exposes certain classes in org.apache.log4j package, causing the following exception on deploying application war file to tomcat
java.lang.SecurityException: class "org.apache.log4j.PropertyConfigurator"'s signer information does not match signer information of other classes in the same package
Is there any way i can avoid error?
First you can use
mvn dependency:tree
to see exactly which dependencies are loaded by jftp. Then, exclude the ones you don't want like this:
<dependency>
<groupId>org.objectweb.joram</groupId>
<artifactId>jftp</artifactId>
<version>1.52</version>
<exclusions>
<exclusion> <!-- declare the exclusion here -->
<groupId>sample.ProjectB</groupId>
<artifactId>Project-B</artifactId>
</exclusion>
</exclusions>
</dependency>

Categories