1

I am using commons-logging which should bridge to Log4J2 in an OSGi environment and so have added the dependencies, export-package and import-package in the pom.xml as below but the logger does not get set to Log4J2 logger. No errors are shown but when debugged I found it being set to JDK14Logger.

    <dependency>
            <groupId>org.apache.logging.log4j</groupId>
            <artifactId>log4j-api</artifactId>
            <version>2.8.2</version>
        </dependency>
        <dependency>
            <groupId>org.apache.logging.log4j</groupId>
            <artifactId>log4j-core</artifactId>
            <version>2.8.2</version>
        </dependency>
        <dependency>
            <groupId>org.apache.logging.log4j</groupId>
            <artifactId>log4j-jcl</artifactId>
            <version>2.8.2</version>
        </dependency>
        <dependency>
            <groupId>commons-logging</groupId>
            <artifactId>commons-logging</artifactId>
            <version>2.8.2</version>
        </dependency>

        <Export-Package>
            org.apache.logging.log4j.*,
            org.apache.commons.logging.*
        </Export-Package>
        <Import-Package>
            !org.apache.logging.log4j.*,
            !org.apache.commons.logging.*,
            *;resolution:=optional
        </Import-Package>

[UPDATE]

From the log4j user mailing list I could figure out that due to the non-modular nature of ServiceLoader. I checked out a few usages of ServiceLoader in the OSGi environment to find implementations of interfaces but still couldn't get how this could be gotten to work.

I tried it using pax logging as well but the result is the same except for that the logger is now being set to JclLogger

Asma Zinneera Jabir
  • 801
  • 3
  • 13
  • 31

2 Answers2

1

As Christian said in the other answer, the best fit for logging in OSGI is the pax-logging bundle.

The Pax-logging is built over SLF4J and can be deployed with different possible implementations:

  • pax-logging-log4j2 (Log4J2)
  • pax-logging-logback (Logback)

Before we also used pax-logging-service which was using Log4J version 1 but it is not more recommended as the two other implementations works well.

I personally not tested Logback implementation in OSGI, but Log4j2 is working (with some limitations).

One of the good things with this solution is that you must not import any logging implementation on your bundles, the only things have to you do is:

  • declare slf4j-api as provided dependency (maven scope)
  • declare eventually the slf4j-simple as test scope in your maven

You don't need to tweak any of the maven-bundle-plugin options regarding logging of any of your bundles.

Here are the step how to do it in ServiceMix version 7.0.1; this release uses originally the pax-logging-services but the next step shows what need to be changed.

By installing the bundles in the startup.properties (immediately after boot time) you ensure that all libs are loaded in the beginning.

These two replace the older version of pax-logging-api and pax-logging-service replaced by pax-logging-log4j2:

mvn\:org.ops4j.pax.logging/pax-logging-api/1.11.13 = 8
mvn\:org.ops4j.pax.logging/pax-logging-log4j2/1.11.13 = 8

then in the file: org.ops4j.pax.logging.cfg you mentions just the line:

org.ops4j.pax.logging.log4j2.config.file=${karaf.etc}/log4j2.xml

and add your log4j2.xml file in the ${karaf.etc} folder (installation of servicemix/etc).

You have to copy the libs in the ${karaf.home}/system folder.

This is if you just need a standard log file.

Now come the limitations: if you need to generate your log as json document, I was only able to use the deprecated JSONLayout in the log4j2.xml.

For setting up JSONLayout you can follow my other answer.

In short:

Add the three Jackson dependencies in startup.properties:

mvn\:com.fasterxml.jackson.core/jackson-annotations/2.12.4 = 6
mvn\:com.fasterxml.jackson.core/jackson-core/2.12.4 = 6
mvn\:com.fasterxml.jackson.core/jackson-databind/2.12.4 = 6

and also the pax-logging-log4j2-extra (if you're using log4j2 implementation):

mvn\:org.ops4j.pax.logging/pax-logging-log4j2-extra/1.11.13 = 6

On my version I had to add the three following lines in overrides.properties:

mvn:com.fasterxml.jackson.core/jackson-core/2.12.4;range="[2,3)"
mvn:com.fasterxml.jackson.core/jackson-databind/2.12.4;range="[2,3)"
mvn:com.fasterxml.jackson.core/jackson-annotations/2.12.4;range="[2,3)"

I created a simple docker-compose with a servicemix 7.0.1 on github with the two ways of creating json logs (the new JsonTemplateLayout not working at the moment).

рüффп
  • 5,172
  • 34
  • 67
  • 113
0

If the above is in your user bundle then this is not correct. In your user bundle you should simply use the commons logging API and not change the settings of the maven bundle plugin.

It will then create Import-Package statements for the commons logging API but not for log4j which is what you want.

You then should install a suitable logging framework at runtime. I know that pax-logging can handle commons logging in a OSGi compatible way. Maybe plain log4j2 also works but I am not sure.

Christian Schneider
  • 19,420
  • 2
  • 39
  • 64
  • This was implemented the same way with Log4J with the relevant dependency, export and import package and commons-logging.properties. That worked. Now I am trying to change it to log4j2. – Asma Zinneera Jabir Jul 04 '17 at 08:01
  • That might work in some way but it is not correct and likely will cause problems. You should not embed the log4j runtime into your bundle. Among other things deploying log4j correctly (e.g. using pax-logging) allows to configure logging in one central place and also change it at runtime. – Christian Schneider Jul 04 '17 at 08:09
  • Updated the question with further findings. Please refer. – Asma Zinneera Jabir Jul 06 '17 at 11:19
  • Please try to leave the maven-bundle-plugin settings at defaults and use pax-logging at runtime. Many apache projects use this. – Christian Schneider Jul 06 '17 at 11:36
  • I tried using pax-logging but the log4j-jcl bridge is not available in pax-logging. Any alternative for this?? – Asma Zinneera Jabir Jul 11 '17 at 09:44
  • 1
    Pax logging has a built in adapter for commons logging. Simply use commons logging in your classes and pax logging will feed it into its log4j backend – Christian Schneider Jul 11 '17 at 09:51