1 package org
.argeo
.slc
.osgiboot
;
4 import java
.io
.IOException
;
5 import java
.util
.ArrayList
;
6 import java
.util
.HashMap
;
9 import java
.util
.StringTokenizer
;
11 import org
.argeo
.slc
.osgiboot
.internal
.springutil
.AntPathMatcher
;
12 import org
.argeo
.slc
.osgiboot
.internal
.springutil
.PathMatcher
;
13 import org
.argeo
.slc
.osgiboot
.internal
.springutil
.SystemPropertyUtils
;
14 import org
.osgi
.framework
.Bundle
;
15 import org
.osgi
.framework
.BundleContext
;
16 import org
.osgi
.framework
.BundleException
;
18 public class OsgiBoot
{
19 public final static String PROP_SLC_OSGI_START
= "slc.osgi.start";
20 public final static String PROP_SLC_OSGI_BUNDLES
= "slc.osgi.bundles";
21 public final static String PROP_SLC_OSGI_LOCATIONS
= "slc.osgi.locations";
22 public final static String PROP_SLC_OSGI_BASE_URL
= "slc.osgi.baseUrl";
23 public final static String PROP_SLC_OSGIBOOT_DEBUG
= "slc.osgiboot.debug";
25 public final static String DEFAULT_BASE_URL
= "reference:file:";
26 public final static String EXCLUDES_SVN_PATTERN
= "**/.svn/**";
28 private Boolean debug
= Boolean
.parseBoolean(System
.getProperty(
29 PROP_SLC_OSGIBOOT_DEBUG
, "false"));
31 private boolean excludeSvn
= true;
33 private final BundleContext bundleContext
;
35 public OsgiBoot(BundleContext bundleContext
) {
36 this.bundleContext
= bundleContext
;
39 public void installUrls(List
<String
> urls
) {
40 Map
<String
, Bundle
> installedBundles
= getInstalledBundles();
41 for (String url
: urls
) {
43 if (installedBundles
.containsKey(url
)) {
44 Bundle bundle
= installedBundles
.get(url
);
47 debug("Bundle " + bundle
.getSymbolicName()
48 + " already installed from " + url
);
50 Bundle bundle
= bundleContext
.installBundle(url
);
52 debug("Installed bundle " + bundle
.getSymbolicName()
55 } catch (BundleException e
) {
56 warn("Could not install bundle from " + url
+ ": "
63 public void startBundles() throws Exception
{
64 String bundlesToStart
= getProperty(PROP_SLC_OSGI_START
);
65 startBundles(bundlesToStart
);
68 public void startBundles(String bundlesToStartStr
) throws Exception
{
69 if (bundlesToStartStr
== null)
72 StringTokenizer st
= new StringTokenizer(bundlesToStartStr
, ",");
73 List bundlesToStart
= new ArrayList();
74 while (st
.hasMoreTokens()) {
75 String name
= st
.nextToken().trim();
76 bundlesToStart
.add(name
);
78 startBundles(bundlesToStart
);
81 public void startBundles(List bundlesToStart
) throws Exception
{
82 if (bundlesToStart
.size() == 0)
85 Map
<String
, Bundle
> bundles
= getBundles();
86 for (int i
= 0; i
< bundlesToStart
.size(); i
++) {
87 String name
= bundlesToStart
.get(i
).toString();
88 Bundle bundle
= bundles
.get(name
);
92 } catch (Exception e
) {
93 warn("Bundle " + name
+ " cannot be started: "
97 warn("Bundle " + name
+ " not installed.");
102 /** Key is location */
103 public Map
<String
, Bundle
> getInstalledBundles() {
104 Map
<String
, Bundle
> installedBundles
= new HashMap
<String
, Bundle
>();
106 for (Bundle bundle
: bundleContext
.getBundles()) {
107 installedBundles
.put(bundle
.getLocation(), bundle
);
109 return installedBundles
;
112 /** Key is symbolic name */
113 public Map
<String
, Bundle
> getBundles() {
114 Map
<String
, Bundle
> installedBundles
= new HashMap
<String
, Bundle
>();
115 for (Bundle bundle
: bundleContext
.getBundles())
116 installedBundles
.put(bundle
.getSymbolicName(), bundle
);
117 return installedBundles
;
120 public List
<String
> getLocationsUrls() {
121 String baseUrl
= getProperty(PROP_SLC_OSGI_BASE_URL
, DEFAULT_BASE_URL
);
122 String bundleLocations
= getProperty(PROP_SLC_OSGI_LOCATIONS
);
123 return getLocationsUrls(baseUrl
, bundleLocations
);
126 public List
<String
> getLocationsUrls(String baseUrl
, String bundleLocations
) {
127 List
<String
> urls
= new ArrayList
<String
>();
129 if (bundleLocations
== null)
131 bundleLocations
= SystemPropertyUtils
132 .resolvePlaceholders(bundleLocations
);
134 debug(PROP_SLC_OSGI_LOCATIONS
+ "=" + bundleLocations
);
136 StringTokenizer st
= new StringTokenizer(bundleLocations
,
138 while (st
.hasMoreTokens()) {
139 urls
.add(baseUrl
+ st
.nextToken().trim());
144 public List
<String
> getBundlesUrls() {
145 String baseUrl
= getProperty(PROP_SLC_OSGI_BASE_URL
, DEFAULT_BASE_URL
);
146 String bundlePatterns
= getProperty(PROP_SLC_OSGI_BUNDLES
);
147 return getBundlesUrls(baseUrl
, bundlePatterns
);
150 public List
<String
> getBundlesUrls(String baseUrl
, String bundlePatterns
) {
151 List
<String
> urls
= new ArrayList
<String
>();
153 List
<BundlesSet
> bundlesSets
= new ArrayList
<BundlesSet
>();
154 if (bundlePatterns
== null)
156 bundlePatterns
= SystemPropertyUtils
157 .resolvePlaceholders(bundlePatterns
);
159 debug(PROP_SLC_OSGI_BUNDLES
+ "=" + bundlePatterns
160 + " (excludeSvn=" + excludeSvn
+ ")");
162 StringTokenizer st
= new StringTokenizer(bundlePatterns
, ",");
163 while (st
.hasMoreTokens()) {
164 bundlesSets
.add(new BundlesSet(st
.nextToken()));
167 List
<String
> included
= new ArrayList
<String
>();
168 PathMatcher matcher
= new AntPathMatcher();
169 for (BundlesSet bundlesSet
: bundlesSets
)
170 for (String pattern
: bundlesSet
.getIncludes())
171 match(matcher
, included
, bundlesSet
.getDir(), null, pattern
);
173 List
<String
> excluded
= new ArrayList
<String
>();
174 for (BundlesSet bundlesSet
: bundlesSets
)
175 for (String pattern
: bundlesSet
.getExcludes())
176 match(matcher
, excluded
, bundlesSet
.getDir(), null, pattern
);
178 for (String fullPath
: included
) {
179 if (!excluded
.contains(fullPath
))
180 urls
.add(baseUrl
+ fullPath
);
186 protected void match(PathMatcher matcher
, List
<String
> matched
,
187 String base
, String currentPath
, String pattern
) {
188 if (currentPath
== null) {
190 File baseDir
= new File(base
.replace('/', File
.separatorChar
));
191 File
[] files
= baseDir
.listFiles();
194 warn("Base dir " + baseDir
+ " has no children, exists="
195 + baseDir
.exists() + ", isDirectory="
196 + baseDir
.isDirectory());
200 for (File file
: files
)
201 match(matcher
, matched
, base
, file
.getName(), pattern
);
203 String fullPath
= base
+ '/' + currentPath
;
204 if (matched
.contains(fullPath
))
205 return;// don't try deeper if already matched
207 boolean ok
= matcher
.match(pattern
, currentPath
);
209 debug(currentPath
+ " " + (ok ?
"" : " not ")
210 + " matched with " + pattern
);
212 matched
.add(fullPath
);
215 String newFullPath
= (base
+ '/' + currentPath
).replace('/',
217 File
[] files
= new File(newFullPath
).listFiles();
219 for (File file
: files
)
220 if (file
.isDirectory()) {
221 String newCurrentPath
= currentPath
+ '/'
223 if (matcher
.matchStart(pattern
, newCurrentPath
)) {
224 // recurse only if start matches
225 match(matcher
, matched
, base
, newCurrentPath
,
230 + " does not start match with "
236 // warn("Not a directory: " + newFullPath);
242 protected void info(Object obj
) {
243 System
.out
.println("# INFO " + obj
);
246 protected void debug(Object obj
) {
248 System
.out
.println("# DBUG " + obj
);
251 protected void warn(Object obj
) {
252 System
.out
.println("# WARN " + obj
);
253 // Because of a weird bug under Windows when starting it in a forked VM
254 // if (System.getProperty("os.name").contains("Windows"))
255 // System.out.println("# WARN " + obj);
257 // System.err.println("# WARN " + obj);
260 protected String
getProperty(String name
, String defaultValue
) {
262 if (defaultValue
!= null)
263 value
= System
.getProperty(name
, defaultValue
);
265 value
= System
.getProperty(name
);
267 if (value
== null || value
.equals(""))
273 protected String
getProperty(String name
) {
274 return getProperty(name
, null);
277 public Boolean
getDebug() {
281 public void setDebug(Boolean debug
) {
285 public BundleContext
getBundleContext() {
286 return bundleContext
;
289 /** Whether to exclude Subversion directories (true by default) */
290 public boolean isExcludeSvn() {
294 public void setExcludeSvn(boolean excludeSvn
) {
295 this.excludeSvn
= excludeSvn
;
298 protected class BundlesSet
{
299 private String baseUrl
= "reference:file";// not used yet
300 private final String dir
;
301 private List
<String
> includes
= new ArrayList
<String
>();
302 private List
<String
> excludes
= new ArrayList
<String
>();
304 public BundlesSet(String def
) {
305 StringTokenizer st
= new StringTokenizer(def
, ";");
307 if (!st
.hasMoreTokens())
308 throw new RuntimeException("Base dir not defined.");
310 String dirPath
= st
.nextToken();
312 if (dirPath
.startsWith("file:"))
313 dirPath
= dirPath
.substring("file:".length());
315 dir
= new File(dirPath
.replace('/', File
.separatorChar
))
318 debug("Base dir: " + dir
);
319 } catch (IOException e
) {
320 throw new RuntimeException("Cannot convert to absolute path", e
);
323 while (st
.hasMoreTokens()) {
324 String tk
= st
.nextToken();
325 StringTokenizer stEq
= new StringTokenizer(tk
, "=");
326 String type
= stEq
.nextToken();
327 String pattern
= stEq
.nextToken();
328 if ("in".equals(type
) || "include".equals(type
)) {
329 includes
.add(pattern
);
330 } else if ("ex".equals(type
) || "exclude".equals(type
)) {
331 excludes
.add(pattern
);
332 } else if ("baseUrl".equals(type
)) {
335 System
.err
.println("Unkown bundles pattern type " + type
);
339 if (excludeSvn
&& !excludes
.contains(EXCLUDES_SVN_PATTERN
)) {
340 excludes
.add(EXCLUDES_SVN_PATTERN
);
344 public String
getDir() {
348 public List
<String
> getIncludes() {
352 public List
<String
> getExcludes() {
356 public String
getBaseUrl() {