]> git.argeo.org Git - gpl/argeo-slc.git/blob - runtime/org.argeo.slc.support.equinox/src/main/java/org/argeo/slc/osgi/BundlesManager.java
445fdf98cdcd3eac6bc7ef7113b057eca22d1113
[gpl/argeo-slc.git] / runtime / org.argeo.slc.support.equinox / src / main / java / org / argeo / slc / osgi / BundlesManager.java
1 package org.argeo.slc.osgi;
2
3 import java.util.ArrayList;
4 import java.util.List;
5
6 import org.apache.commons.logging.Log;
7 import org.apache.commons.logging.LogFactory;
8 import org.argeo.slc.SlcException;
9 import org.osgi.framework.Bundle;
10 import org.osgi.framework.BundleContext;
11 import org.osgi.framework.BundleException;
12 import org.osgi.framework.FrameworkEvent;
13 import org.osgi.framework.FrameworkListener;
14 import org.osgi.framework.InvalidSyntaxException;
15 import org.osgi.framework.ServiceReference;
16 import org.osgi.service.packageadmin.PackageAdmin;
17 import org.springframework.beans.factory.InitializingBean;
18 import org.springframework.context.ApplicationContext;
19 import org.springframework.osgi.context.BundleContextAware;
20
21 /** Wraps access to a {@link BundleContext} */
22 public class BundlesManager implements BundleContextAware, FrameworkListener,
23 InitializingBean {
24 private final static Log log = LogFactory.getLog(BundlesManager.class);
25
26 private BundleContext bundleContext;
27
28 private Long defaultTimeout = 10000l;
29 private final Object refreshedPackageSem = new Object();
30
31 /** Updates bundle synchronously. */
32 public void updateSynchronous(Bundle bundle) throws BundleException {
33 // int originalState = bundle.getState();
34 bundle.update();
35 boolean waiting = true;
36
37 long begin = System.currentTimeMillis();
38 do {
39 int state = bundle.getState();
40 if (state == Bundle.INSTALLED || state == Bundle.ACTIVE
41 || state == Bundle.RESOLVED)
42 waiting = false;
43
44 sleep(100);
45 if (System.currentTimeMillis() - begin > defaultTimeout)
46 throw new SlcException("Update of bundle "
47 + bundle.getSymbolicName()
48 + " timed out. Bundle state = " + bundle.getState());
49 } while (waiting);
50
51 if (log.isTraceEnabled())
52 log.debug("Bundle " + bundle.getSymbolicName() + " updated.");
53 }
54
55 /** Starts bundle synchronously. Does nothing if already started. */
56 public void startSynchronous(Bundle bundle) throws BundleException {
57 int originalState = bundle.getState();
58 if (originalState == Bundle.ACTIVE)
59 return;
60
61 bundle.start();
62 boolean waiting = true;
63
64 long begin = System.currentTimeMillis();
65 do {
66 if (bundle.getState() == Bundle.ACTIVE)
67 waiting = false;
68
69 sleep(100);
70 if (System.currentTimeMillis() - begin > defaultTimeout)
71 throw new SlcException("Start of bundle "
72 + bundle.getSymbolicName()
73 + " timed out. Bundle state = " + bundle.getState());
74 } while (waiting);
75
76 if (log.isTraceEnabled())
77 log.debug("Bundle " + bundle.getSymbolicName() + " started.");
78 }
79
80 /** Stops bundle synchronously. Does nothing if already started. */
81 public void stopSynchronous(Bundle bundle) throws BundleException {
82 int originalState = bundle.getState();
83 if (originalState != Bundle.ACTIVE)
84 return;
85
86 bundle.stop();
87 boolean waiting = true;
88
89 long begin = System.currentTimeMillis();
90 do {
91 if (bundle.getState() != Bundle.ACTIVE
92 && bundle.getState() != Bundle.STOPPING)
93 waiting = false;
94
95 sleep(100);
96 if (System.currentTimeMillis() - begin > defaultTimeout)
97 throw new SlcException("Stop of bundle "
98 + bundle.getSymbolicName()
99 + " timed out. Bundle state = " + bundle.getState());
100 } while (waiting);
101
102 if (log.isTraceEnabled())
103 log.debug("Bundle " + bundle.getSymbolicName() + " stopped.");
104 }
105
106 /** Refresh bundle synchronously. Does nothing if already started. */
107 public void refreshSynchronous(Bundle bundle) throws BundleException {
108 ServiceReference packageAdminRef = bundleContext
109 .getServiceReference(PackageAdmin.class.getName());
110 PackageAdmin packageAdmin = (PackageAdmin) bundleContext
111 .getService(packageAdminRef);
112 Bundle[] bundles = { bundle };
113 packageAdmin.refreshPackages(bundles);
114
115 synchronized (refreshedPackageSem) {
116 try {
117 refreshedPackageSem.wait(defaultTimeout);
118 } catch (InterruptedException e) {
119 // silent
120 }
121 }
122
123 if (log.isTraceEnabled())
124 log.debug("Bundle " + bundle.getSymbolicName() + " refreshed.");
125 }
126
127 public void frameworkEvent(FrameworkEvent event) {
128 if (event.getType() == FrameworkEvent.PACKAGES_REFRESHED) {
129 synchronized (refreshedPackageSem) {
130 refreshedPackageSem.notifyAll();
131 }
132 }
133 }
134
135 public List<ApplicationContext> listPublishedApplicationContexts(
136 String filter) {
137 try {
138 List<ApplicationContext> lst = new ArrayList<ApplicationContext>();
139 ServiceReference[] sfs = bundleContext.getServiceReferences(
140 ApplicationContext.class.getName(), filter);
141 for (int i = 0; i < sfs.length; i++) {
142 ApplicationContext applicationContext = (ApplicationContext) bundleContext
143 .getService(sfs[i]);
144 lst.add(applicationContext);
145 }
146 return lst;
147 } catch (InvalidSyntaxException e) {
148 throw new SlcException(
149 "Cannot list published application contexts", e);
150 }
151 }
152
153 public ServiceReference[] getServiceRefSynchronous(String clss,
154 String filter) throws InvalidSyntaxException {
155 if (log.isTraceEnabled())
156 log.debug("Filter: '" + filter + "'");
157 ServiceReference[] sfs = null;
158 boolean waiting = true;
159 long begin = System.currentTimeMillis();
160 do {
161 sfs = bundleContext.getServiceReferences(clss, filter);
162
163 if (sfs != null)
164 waiting = false;
165
166 sleep(100);
167 if (System.currentTimeMillis() - begin > defaultTimeout)
168 throw new SlcException("Search of services " + clss
169 + " with filter " + filter + " timed out.");
170 } while (waiting);
171
172 return sfs;
173 }
174
175 protected void sleep(long ms) {
176 try {
177 Thread.sleep(ms);
178 } catch (InterruptedException e) {
179 // silent
180 }
181 }
182
183 public void setBundleContext(BundleContext bundleContext) {
184 this.bundleContext = bundleContext;
185 }
186
187 public void afterPropertiesSet() throws Exception {
188 bundleContext.addFrameworkListener(this);
189 }
190
191 }