在OSGi环境中使用ServiceLoader for log4j jcl brigde

在OSGi环境中使用ServiceLoader for log4j jcl brigde,osgi,log4j2,apache-commons-logging,Osgi,Log4j2,Apache Commons Logging,我试图在osgi模式下使用log4j jcl桥,发现应该使用java.util.ServiceLoader从桥jar获取LogFactoryImpl。我是OSGi新手,所以在参考了一些教程后尝试了它,但它似乎不起作用。捆绑包处于已解析状态 LoggingActivator.java import org.apache.commons.logging.Log; import org.apache.commons.logging.LogFactory; import org.osgi.framewo

我试图在osgi模式下使用log4j jcl桥,发现应该使用java.util.ServiceLoader从桥jar获取LogFactoryImpl。我是OSGi新手,所以在参考了一些教程后尝试了它,但它似乎不起作用。捆绑包处于已解析状态

LoggingActivator.java

import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.osgi.framework.BundleActivator;
import org.osgi.framework.BundleContext;
import java.util.ServiceLoader;

public class LoggingActivator  implements BundleActivator{

private static Log log;
ServiceLoader<LogFactory> serviceLoader = ServiceLoader.load(LogFactory.class);
LogFactory service = serviceLoader.iterator().next();

public LoggingActivator(){
    if (service != null){
        log = service.getLog(LoggingActivator.class);
    }
}

@Override
public void start(BundleContext bundleContext) throws Exception {
    log.info("Activated Logging");
}

@Override
public void stop(BundleContext bundleContext) throws Exception {
    log.info("Deactivated Logging");
}


}
import org.apache.commons.logging.Log;
导入org.apache.commons.logging.LogFactory;
导入org.osgi.framework.BundleActivator;
导入org.osgi.framework.BundleContext;
导入java.util.ServiceLoader;
公共类LoggingActivator实现BundleActivator{
私有静态日志;
ServiceLoader ServiceLoader=ServiceLoader.load(LogFactory.class);
LogFactory服务=serviceLoader.iterator().next();
公共日志激活器(){
if(服务!=null){
log=service.getLog(LoggingActivator.class);
}
}
@凌驾
public void start(BundleContext BundleContext)引发异常{
日志信息(“激活日志”);
}
@凌驾
公共无效停止(BundleContext BundleContext)引发异常{
日志信息(“停用日志”);
}
}
pom.xml

    <dependency>
        <groupId>commons-logging</groupId>
        <artifactId>commons-logging</artifactId>
    </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>

公用记录
公用记录
org.apache.logging.log4j
log4j型芯
2.8.2
org.apache.logging.log4j
log4jcl
2.8.2


org.apache.logging.log4j.*,
org.apache.commons.logging*
!org.apache.logging.log4j.*,
!org.apache.commons.logging.*,
*;分辨率:=可选

ServiceLoader在OSGi中无法正常工作。我提议试一试。稍后您将不需要它,但它已经正确配置了日志记录,因此与从一开始就自己设置相比,它更容易启动

在您的bundle中,只需像在OSGi之外一样初始化一个commons日志记录器

class MyClass {
private Log log = LogFactory.getLog(MyClass.class);
...
}
将maven bundle插件保留为默认值。结果是一个bundle,它导入了commons日志API包,这正是您所需要的

然后启动karaf并部署您的包。日志记录应该是开箱即用的。有关更多信息,请参阅


Karaf使用pax日志记录。如果您想自己设置,您需要捆绑包pax logging api和pax logging service、felix config admin和felix fileinstall。后端是log4j。您可以使用ConfigAdmin和名为etc/org.ops4j.pax.logging.cfg的配置来配置它。配置文件是一个标准的log4j配置文件。

如果您想使用ServiceLoader,那么您可能应该看看Service Loader Mediator规范(OSGi概要第133章)。apachearies上有一个名为SPI-Fly的实现


其思想是服务加载程序中介在运行时扩展包的类,确保它正确设置了线程上下文类加载程序,以便您使用
ServiceLoader
查找实现。Service Loader Mediator还为它找到的每个已注册的实现注册OSGi服务,因此如果您愿意,您可以通过使用OSGi服务注册表来避免完全使用
ServiceLoader

启动并运行另一台服务器以启用日志记录是一个好主意吗?我怀疑这会影响主服务器的启动时间。这不是我的意思。只需像我建议的那样创建一个简单的包来演示日志记录,并将其部署到karaf中进行测试。然后在实际设置中重新创建pax日志设置。经过这一步,你不再需要卡拉夫了。
class MyClass {
private Log log = LogFactory.getLog(MyClass.class);
...
}