I know I can exclude one of the binding which I did in maven so my springboot.jar only contains logback and logback-slf bindings but then there is this external jar that I am referring on spring-boot class path introduces slf4j-log4j binding at runtime and gets confused.
java -Dprofile=dev -Dloader.path=springboot.jar,/usr/local/hadoop/lib,/usr/local/hbase/lib -jar springboot.jar
SLF4J: Found binding in [jar:file:/runtime/external/classpath/slf4j-log4j12-1.7.5.jar!/org/slf4j/impl/StaticLoggerBinder.class]
SLF4J: Found binding in [jar:file:/build/jar/path/springboot.jar!/lib/logback-classic-1.1.2.jar!/org/slf4j/impl/StaticLoggerBinder.class]
How do I resolved this when binding conflict is with external dependencies?
Thanks
You have to somehow exclude those jars from your classpath. So you shouldn't add the hbase lib dir in general, but enumerate all jarfiles.
In case you are using bash to start your application you can leverage its pattern matching: /usr/local/hbase/lib/!(slf4j-log4j12-*)
p.s. this is not a spring-boot question....
Related
I'm in the process of migrating my tests to use Junit5 and I noticed that somehow my logs stopped working.
Before I was defining my logs with a simple simplelogger.properties inside by test/resources folder.
But this no longer working.
I was reading the gradle documentation and I see a lot of information about it and I can define some logs using the test logging container.
Anyway this somehow does not seem to allow me to do what I want.
I'm looking if there is anything I can add to my test definition that let's me define the log4j configuration folder/file
test {
useJUnitPlatform()
maxHeapSize = '2G'
reports {
junitXml.enabled = true
html.enabled = true
}
timeout = Duration.ofMinutes(30)
testLogging {
showStandardStreams true
exceptionFormat 'full'
events "PASSED", "SKIPPED", "FAILED", "STANDARD_OUT", "STANDARD_ERROR"
}
systemProperty 'bla', 'bla'
}
Is there a way I can define a log4.properties file or a simplelogger.properties file and tell the jvm where to find it but instead of using the JVM parameters I would use some gradle configuration?
Also I notice when my tests start that it finds multiple SLF4J bindings which I'm not sure how to work around.
SLF4J: Class path contains multiple SLF4J bindings.
SLF4J: Found binding in [jar:file:/.gradle/caches/7.4.2/generated-gradle-jars/gradle-api-7.4.2.jar!/org/slf4j/impl/StaticLoggerBinder.class]
SLF4J: Found binding in [jar:file:/.gradle/caches/modules-2/files-2.1/ch.qos.logback/logback-classic/1.2.11/4741689214e9d1e8408b206506cbe76d1c6a7d60/logback-classic-1.2.11.jar!/org/slf4j/impl/StaticLoggerBinder.class]
SLF4J: Found binding in [jar:file:/.gradle/caches/modules-2/files-2.1/org.slf4j/slf4j-log4j12/1.7.30/c21f55139d8141d2231214fb1feaf50a1edca95e/slf4j-log4j12-1.7.30.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 [org.gradle.internal.logging.slf4j.OutputEventListenerBackedLoggerContext]
Is there any good documentation for this? I seem to not find what I need in the official documentation or examples.
The source of the problem might be something like this (i'm using the gradle-groovy plugin also):
SLF4J: multiple SLF4J bindings with Gradle Plugin
if nothing else works I'm thinking of trying something like this (to override it on the jvm args):
How to pass args to JVM which runs tests with Gradle
log4j configuration via JVM argument(s)?
I'm using an Eclipse CDT distribution from 2019-09 (v4.13, build id: I20190916-1045), on a SLES 15 machine (don't ask...)
When I start Eclipse up, I get the following text on my console:
org.eclipse.m2e.logback.configuration: The org.eclipse.m2e.logback.configuration bundle was activated before the state location was initialized. Will retry after the state location is initialized.
org.eclipse.m2e.logback.configuration: Logback config file: /home/lh156516/workspace/.metadata/.plugins/org.eclipse.m2e.logback.configuration/logback.1.13.0.20190716-1624.xml
SLF4J: Class path contains multiple SLF4J bindings.
SLF4J: Found binding in [bundleresource://470.fwk441444733:1/org/slf4j/impl/StaticLoggerBinder.class]
SLF4J: Found binding in [bundleresource://470.fwk441444733:2/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.util.ContextSelectorStaticBinder]
My questions:
Why was The "logback configuration bundle activated before the state location was initialized"?
How can I get the "bundle" to be activated only when its supposed to?
Why does the Simple Logging Facade for Java's Class path contain multiple SLF4J bindings?
Can I, and should I change the class path so that it only contains a single "SLF4J binding"?
Note: I'm not much of a "Java guy" and am not familiar with the inner workings of the Eclipse platform; think of me as a lay Eclipse user.
It's a bug, known since 2016:
https://bugs.eclipse.org/bugs/show_bug.cgi?id=506676
I am trying to start HIVE 3.1.2 on Hadoop 3.3.0 on my windows 10 PC for training purpose (yes I know linux is better ;-) but someone has to do it anyway). I have the following error message
it looks related to how SLF4J works (I guess) but since I am not a java (or any other language) dev I have no clue how to fix it
For what it worth I do not have an IT background so be gentle and talk to me as if I was 10y/o
Could any one help (BTW it is running on java 8)
$ hive
SLF4J: Class path contains multiple SLF4J bindings.
SLF4J: Found binding in [jar:file:/C:/zztop/hadoop/hive/lib/log4j-slf4j-impl-2.14.0.jar!/org/slf4j/impl/StaticLoggerBinder.class]
SLF4J: Found binding in [jar:file:/C:/zztop/hadoop/hive/lib/slf4j-log4j12-1.7.25.jar!/org/slf4j/impl/StaticLoggerBinder.class]
SLF4J: Found binding in [jar:file:/C:/zztop/hadoop/share/hadoop/common/lib/slf4j-log4j12-1.7.25.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 [org.apache.logging.slf4j.Log4jLoggerFactory]
WARNING: sun.reflect.Reflection.getCallerClass is not supported. This will impact performance.
Exception in thread "main" java.lang.NoClassDefFoundError: Could not initialize class org.apache.logging.log4j.util.PropertiesUtil
at org.apache.logging.log4j.status.StatusLogger.<clinit>(StatusLogger.java:71)
at org.apache.logging.log4j.LogManager.<clinit>(LogManager.java:60)
at org.apache.logging.slf4j.Log4jLoggerFactory.getContext(Log4jLoggerFactory.java:45)
at org.apache.logging.log4j.spi.AbstractLoggerAdapter.getLogger(AbstractLoggerAdapter.java:46)
at org.apache.logging.slf4j.Log4jLoggerFactory.getLogger(Log4jLoggerFactory.java:30)
at org.slf4j.LoggerFactory.getLogger(LoggerFactory.java:281)
at org.slf4j.LoggerFactory.getLogger(LoggerFactory.java:301)
at org.apache.hadoop.util.RunJar.<clinit>(RunJar.java:55)
What you are seeing is a misconfiguration of the logging framework, which it detects and complains about, including a link to http://www.slf4j.org/codes.html#multiple_bindings which explains the following:
SLF4J API is designed to bind with one and only one underlying logging
framework at a time. If more than one binding is present on the class
path, SLF4J will emit a warning, listing the location of those
bindings.
When multiple bindings are available on the class path, select one and
only one binding you wish to use, and remove the other bindings. For
example, if you have both slf4j-simple-2.0.0-alpha0.jar and
slf4j-nop-2.0.0-alpha0.jar on the class path and you wish to use the
nop (no-operation) binding, then remove slf4j-simple-2.0.0-alpha0.jar
from the class path.
It is not uncommon to see this problem, when combining multiple things together that bring their own logging backend. The solution is to figure out why (the jars are listed) and only leave one binding.
I am trying to get SLF4J to bind to logback, but it is instead defaulting to Log4j.
I have all the default config files configured for logback, as well as the bindings.
My classpath has the following relevant jars:
logback-classic
commons-logging (99.0-does-not-exist) //empty jar to exclude commons-logging
logback-core
logback-ext-spring
Note: No log4j dependencies are present.
This is a spring mvc app.
On startup SLF4J has the following output:
SLF4J: Class path contains multiple SLF4J bindings.
SLF4J: Found binding in [jar:file:/C:/Users/masierp/Documents/springsource/vfabric-tc-server-developer-2.8.2.RELEASE/blablahbkla/wtpwebapps/ilm-engine/WEB-INF/lib/activemq-all-5.7.0.jar!/org/slf4j/impl/StaticLoggerBinder.class]
SLF4J: Found binding in [jar:file:/C:/Users/masierp/Documents/springsource/vfabric-tc-server-developer-2.8.2.RELEASE/blablahbkla/wtpwebapps/ilm-engine/WEB-INF/lib/logback-classic-1.1.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 [org.slf4j.impl.Log4jLoggerFactory]
Note that none of the found bindings are log4j bindings.
I have messed with spring-ext (trying to use it as the spring listener) but with or without this jar the problem persists.
Any help appreciated, thanks.
Probably one of your dependencies has a log4j dependency. You need to exclude it.
Try to look on the parent pom.
I have a simple Eclipse Plugin which gives me following error on activation:
SLF4J: Class path contains multiple SLF4J bindings.
SLF4J: Found binding in [bundleresource://103.fwk8918249:1/org/slf4j/impl/StaticLoggerBinder.class]
SLF4J: Found binding in [bundleresource://103.fwk8918249:4/org/slf4j/impl/StaticLoggerBinder.class]
SLF4J: See http://www.slf4j.org/codes.html#multiple_bindings for an explanation.
both URLs resolve to the exact same jar in the bundle
libs/slf4j-log4j12.jar!/org/slf4j/impl/StaticLoggerBinder.class
How can i solve the problem?
How come that the bundle loads the jar twice (":1" and ":4")?
This is a result of defining an SLF4J binding in both your project's classpath (JDT .classpath file) and your MANIFEST.MF file.
You should remove your SLF4J binding from your project's class path:
YourProject → Properties → Java Build Path → Libraries
Select the SLF4J Binding JAR and hit 'Remove'.
Once you do this, there should only be a single reference to your SLF4J binding in your class loader (and thus the error message should not appear).
For me the issue occurred due to an installed plugin. To find out which one it is.. look for the file SavedExternalPluginList.txt in the metadata of the debugging eclipse instance, e.g.
runtime-EclipseApplication\.metadata\.plugins\org.eclipse.pde.core\SavedExternalPluginList.txt
and search for slf4j. This way you get an idea which plugins might be responsible. I found following entries:
file:/D:/EclipseJava/App/Eclipse/plugins/ch.qos.logback.slf4j_1.0.7.v201505121915.jar
file:/D:/EclipseJava/App/Eclipse/plugins/org.eclipse.m2e.maven.runtime.slf4j.simple_1.7.0.20160603-1931/
file:/D:/EclipseJava/App/Eclipse/plugins/org.slf4j.api_1.7.2.v20121108-1250.jar
file:/D:/EclipseJava/App/Eclipse/plugins/org.slf4j.impl.log4j12_1.7.2.v20131105-2200.jar
Disabling the plugin ch.qos.logback.slf4j for my Target Platform did the trick:
If you manually change the plugin selection, please be careful and use the Validate Plug-ins feature to make sure you don't create other issues.
This seems to solve the problem:
SLF4J: Class path contains multiple SLF4J bindings
If not, do you have two different versions of SLF4J on that path?