1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18 package org.apache.logging.log4j.core.osgi;
19
20 import java.util.Hashtable;
21 import java.util.concurrent.atomic.AtomicReference;
22
23 import org.apache.logging.log4j.LogManager;
24 import org.apache.logging.log4j.Logger;
25 import org.apache.logging.log4j.core.config.plugins.util.PluginRegistry;
26 import org.apache.logging.log4j.core.impl.Log4jProvider;
27 import org.apache.logging.log4j.core.util.Constants;
28 import org.apache.logging.log4j.spi.Provider;
29 import org.apache.logging.log4j.status.StatusLogger;
30 import org.apache.logging.log4j.util.PropertiesUtil;
31 import org.osgi.framework.Bundle;
32 import org.osgi.framework.BundleActivator;
33 import org.osgi.framework.BundleContext;
34 import org.osgi.framework.BundleEvent;
35 import org.osgi.framework.ServiceRegistration;
36 import org.osgi.framework.SynchronousBundleListener;
37 import org.osgi.framework.wiring.BundleWiring;
38
39
40
41
42 public final class Activator implements BundleActivator, SynchronousBundleListener {
43
44 private static final Logger LOGGER = StatusLogger.getLogger();
45
46 private final AtomicReference<BundleContext> contextRef = new AtomicReference<>();
47
48 ServiceRegistration provideRegistration = null;
49
50 @Override
51 public void start(final BundleContext context) throws Exception {
52 final Provider provider = new Log4jProvider();
53 final Hashtable<String, String> props = new Hashtable<>();
54 props.put("APIVersion", "2.60");
55 provideRegistration = context.registerService(Provider.class.getName(), provider, props);
56
57 if (PropertiesUtil.getProperties().getStringProperty(Constants.LOG4J_CONTEXT_SELECTOR) == null) {
58 System.setProperty(Constants.LOG4J_CONTEXT_SELECTOR, BundleContextSelector.class.getName());
59 }
60 if (this.contextRef.compareAndSet(null, context)) {
61 context.addBundleListener(this);
62
63 scanInstalledBundlesForPlugins(context);
64 }
65 }
66
67 private static void scanInstalledBundlesForPlugins(final BundleContext context) {
68 final Bundle[] bundles = context.getBundles();
69 for (final Bundle bundle : bundles) {
70
71 scanBundleForPlugins(bundle);
72 }
73 }
74
75 private static void scanBundleForPlugins(final Bundle bundle) {
76 final long bundleId = bundle.getBundleId();
77
78 if (bundle.getState() == Bundle.ACTIVE && bundleId != 0) {
79 LOGGER.trace("Scanning bundle [{}, id=%d] for plugins.", bundle.getSymbolicName(), bundleId);
80 PluginRegistry.getInstance().loadFromBundle(bundleId,
81 bundle.adapt(BundleWiring.class).getClassLoader());
82 }
83 }
84
85 private static void stopBundlePlugins(final Bundle bundle) {
86 LOGGER.trace("Stopping bundle [{}] plugins.", bundle.getSymbolicName());
87
88 PluginRegistry.getInstance().clearBundlePlugins(bundle.getBundleId());
89 }
90
91 @Override
92 public void stop(final BundleContext context) throws Exception {
93 provideRegistration.unregister();
94 this.contextRef.compareAndSet(context, null);
95 LogManager.shutdown();
96 }
97
98 @Override
99 public void bundleChanged(final BundleEvent event) {
100 switch (event.getType()) {
101
102 case BundleEvent.STARTED:
103 scanBundleForPlugins(event.getBundle());
104 break;
105
106 case BundleEvent.STOPPING:
107 stopBundlePlugins(event.getBundle());
108 break;
109
110 default:
111 break;
112 }
113 }
114 }