3

I have created an eclipse PDE project and have added log4j as a dependency using the slf4j-api and slf4j.log4j12 bundles. In a class I have created the logger:

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

public class MyTest {

  private static final Logger logger = LoggerFactory.getLogger(MyTest.class
      .getName());

  public void tt() {
    logger.info("log-test");

  }

}

but when I run the PDE project using an OSGI launch configuration I get the warnings:

log4j:WARN No appenders could be found for logger (loggin_test.MyTest).
log4j:WARN Please initialize the log4j system properly.

based on this info:

http://jaikiran.wordpress.com/2006/07/05/i-get-log4jwarn-no-appenders-could-be-found-for-logger-message-2/

I need to put the log4j.properties in the PDE classpath. I have tried to put it in the root of the PDE project and add:

source.. = src/
output.. = bin/
bin.includes = META-INF/,\
               .,\
               log4j.properties

to the build.properties pane. But I still get the same warning. Where do I put the log4j.properties file in a PDE project?

EDIT: I have also tried adding it to the /src folder but it does not help.

mdahlman
  • 9,204
  • 4
  • 44
  • 72
u123
  • 15,603
  • 58
  • 186
  • 303
  • Is loggin_test the package name for class MyTest in your code? – JoseK Aug 26 '10 at 10:30
  • Yes. I have changed the package to loggin.test but it does not help. I have also tried : http://sites.google.com/site/springosgi/ch02.html but was not able to make it work. Any suggestions are more than welcome! – u123 Aug 26 '10 at 11:10
  • The error message says *loggin_test.MyTest* which is not the same as *loggin.test.MyTest* – JoseK Aug 26 '10 at 11:16
  • I know but that was before I changed to loggin.test.MyTest. After the change I get the error: log4j:WARN No appenders could be found for logger (loggin.test.MyTest). log4j:WARN Please initialize the log4j system properly. – u123 Aug 26 '10 at 11:23
  • Paste the manifests from your plug-ins and the log4j bundle into your question. – SteveD Aug 27 '10 at 08:15

5 Answers5

3

You've hit your first resource visibility problem with OSGi. Remember that in OSGi bundles must explicitly define their dependencies. Your problem is that your bundle defines a log4j property file, but it's the log4j bundle that must read it. But the log4j bundle doesn't know anything about your bundle (and nor should it).

Here's 2 solutions to the problem:

  1. Use Eclipse's buddy mechanism
  2. Put the log4j property file in an OSGi fragment and host it on the log4j bundle

Option 2 is a better solution, but if you find option 1 easier then go with that.

SteveD
  • 5,396
  • 24
  • 33
  • I have done the following: 1) Created a plugin where I add org.apache.log4j as a dependency. 2) Created a fragment with the previous plugin as a host and added the log4j.properties file to the root. 3) created a new plugin which depends on the plugin from 1). But I cannot use instantiate the logger with : Logger logger = Logger.getLogger("com.foo"); How do I make log4j visible in the final plugin which depends on the "wrapped" log4j plugin? – u123 Aug 26 '10 at 11:59
  • When you say you cannot use Logger.getLogger, you mean you get a compile-time or runtime problem? Is the plugin from 1) just a wrapped version of log4j? How did you create it? Did you use a tool such as Bundlor or Bnd? I don't recommend wrapping well-known libraries yourself - you can find bundles of common open source libraries at: http://www.springsource.com/repository/app/ – SteveD Aug 26 '10 at 13:31
  • Compile time error. Makes sense since the log4j types will only be visible in the plugin directly depending on log4j. I have tried another approach: I create a fragment (with the .properties file) and specify the org.apache.log4j as host (where I have downloaded org.apache.log4j from the website and manually added it to the running target platform ). But since I cannot depend on a fragment in my other plugin and the log4j in the target platform is not aware that it has been "extended" with the fragment I have the same problem. – u123 Aug 26 '10 at 14:00
  • Eclipse already has the log4j bundle, so you shouldn't add the JAR to your plug-in, but do a Require-Bundle on log4j in your plug-in. – SteveD Aug 26 '10 at 15:09
  • No log4j is not part of the default platform. Further the problem is not adding the log4j bundle but making sure it can find the log4j.properties file when its started. – u123 Aug 26 '10 at 17:47
0

I've just had the same situation when I tried to shift from using slf4j-simple to slf4j-log4j12 (while adding the log4j jar). After doing some debugging, it is just as SteveD mentions, the issue is a result of resource visibility. In my situation, I had a plugin which held my logging libraries; however, I did not want to specify my logging properties in a shared plugin.

My approach, which may work for your situation, was to have a logging configuration for each plugin that you wish to have logging capabilities. For a plugin that would required logging, I would add something like the following to the plugin's activator:

Bundle bundle = bundleContext.getBundle();
URL entry = bundle.getEntry("log4j.properties");

try(InputStream inputStream = entry.openStream())
{
    PropertyConfigurator.configure(inputStream);
}
catch(IOException e) {}

Even though it is unfortunate that code is required to be added to the activator; I was able to configure different logging capabilities per plugin, I did not have to deal with new plugins / Eclipse buddy registrations and also did not have to deal with managing log4j.properties files in any manifest or build.properties file.

Other Notes

  • When the failed-to-initialize message appears ("Please initialize the log4j system properly"), it will only appear once. This gave me some confusion at first when I didn't detect that two (2) plugins were configured incorrectly but only one (1) error message showed up.
jdknight
  • 1,801
  • 32
  • 52
0

AFAIK, you still need the Log4j JAR, since SLF4J is just a wrapper around it. Download the JAR from the Apache web site, add it to your build path and it should work just fine.

zvikico
  • 9,765
  • 4
  • 38
  • 49
  • He must already have the JAR, otherwise it's difficult for log4j to warn him that it can't find any appenders... – SteveD Aug 26 '10 at 11:31
  • Jep I already have added org.apache.log4j version 1.2.13 to the manifest file. – u123 Aug 26 '10 at 11:41
0

I got the same problem. Adding the folder containing log4j.xml to Project Build Path is not enough (why not?). Anyway, besides the reason for that (maybe eclipse gurus can answer that for us) I solved my problem adding the folder containing log4j.xml to the eclipse "Run configuration".

After you try to run your Standalone App for the first time and get the annoying "No appenders could be found for logger" message, follow the steps bellow:

  1. Go to Menu "Run" > "Run Configurations"
  2. Your main class should appear somewhere in the left tree. Probably under "Java Application". So select it
  3. Select "Classpath" tab, select "User Entries" and click "Advanced" button.
  4. On "Advanced Options" pop-up window, select "Add Folders", click "OK" button.
  5. On "Folder Selection" pop-up, navigate to your folder where log4j.xml is located and click "OK"btn.
  6. Click "Run" button... and... Finally!
L. Holanda
  • 4,432
  • 1
  • 36
  • 44
  • 1
    This really isn't the proper way to do it, see hbunny's solution. A PDE/RCP project should be able to run without changing any Run/VM/classpath settngs. In other words, what makes an Eclipse application's behavior is solely its installed plugins. – Hendy Irawan Dec 09 '10 at 18:20
0

Why not use the platform logging facility?

I've recently added logging to my Eclipse plugin. I used the logging facility that is built into the PDE. I'll post this just in case that option was somehow overlooked. I didn't realize that I didn't need to add log4j at first, perhaps others don't realize that either.

Nathan Tuggy
  • 2,237
  • 27
  • 30
  • 38