/******************************************************************************* * Copyright 2013 Geoscience Australia * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. ******************************************************************************/ package au.gov.ga.earthsci.ant; import java.io.File; import java.util.ArrayList; import java.util.HashMap; import java.util.HashSet; import java.util.List; import java.util.Map; import java.util.Map.Entry; import java.util.Set; import org.apache.tools.ant.BuildException; import org.apache.tools.ant.DirectoryScanner; import org.apache.tools.ant.Task; import org.apache.tools.ant.types.FileSet; /** * Ant task that generates the <code>osgi.bundles</code> property for a FileSet * of JAR files. Uses the {@link BundleProperties} class to determine the * os/arch of each JAR file. * * @author Michael de Hoog (michael.dehoog@ga.gov.au) */ public class OsgiBundles extends Task { private String property; private String defaultStartLevel = "4"; private boolean defaultAutoStart = false; private List<FileSet> filesets = new ArrayList<FileSet>(); private Map<String, StartLevel> startLevels = new HashMap<String, StartLevel>(); public void setProperty(String property) { this.property = property; } public void setDefaultStartLevel(String startLevel) { this.defaultStartLevel = startLevel; } public void setDefaultAutoStart(boolean autoStart) { this.defaultAutoStart = autoStart; } public void addFileset(FileSet fileset) { filesets.add(fileset); } public void addConfiguredStartLevel(StartLevel startLevel) { startLevels.put(startLevel.getBundle(), startLevel); } @Override public void execute() throws BuildException { MultiMap<String, BundleProperties> resources = new MultiMap<String, BundleProperties>(); Set<String> uniqueOsArchs = new HashSet<String>(); for (FileSet fileset : filesets) { DirectoryScanner directoryScanner = fileset.getDirectoryScanner(getProject()); String[] includedFiles = directoryScanner.getIncludedFiles(); for (String filename : includedFiles) { filename = filename.replace('\\', '/'); File base = directoryScanner.getBasedir(); File file = new File(base, filename); BundleProperties bundleProperties = new BundleProperties(file); String[] osArchs = bundleProperties.getOsArchs(); for (String osArch : osArchs) { resources.putSingle(osArch, bundleProperties); uniqueOsArchs.add(osArch); } } } MultiMap<String, String> topLevelOsArchs = new MultiMap<String, String>(); for (String osArch : uniqueOsArchs) { boolean lowestLevel = true; for (String test : uniqueOsArchs) { //skip itself if (test == osArch) continue; if (test.contains(osArch)) { lowestLevel = false; break; } } if (lowestLevel) { for (String test : uniqueOsArchs) { if (osArch.contains(test)) { topLevelOsArchs.putSingle(osArch, test); } } } } StringBuilder sb = new StringBuilder(); for (Entry<String, List<String>> topLevelOsArch : topLevelOsArchs.entrySet()) { sb.append("\t<resources"); sb.append(topLevelOsArch.getKey()); sb.append(">\n"); sb.append("\t\t<property name=\"osgi.bundles\" value=\""); for (String osArch : topLevelOsArch.getValue()) { List<BundleProperties> bundles = resources.get(osArch); if (bundles != null) { for (BundleProperties bundle : bundles) { String name = bundle.getSymbolicName(); sb.append(name).append("@"); String startLevel = getStartLevel(name); boolean autoStart = isAutoStart(name); if (startLevel != null) { sb.append(startLevel); } if (startLevel != null && autoStart) { sb.append("\\"); } if (autoStart) { sb.append(":start"); } sb.append(','); } } } sb.deleteCharAt(sb.length() - 1); sb.append("\" />\n"); sb.append("\t</resources>\n"); } getProject().setNewProperty(property, sb.toString()); } private boolean isAutoStart(String bundle) { if (startLevels.containsKey(bundle)) { return startLevels.get(bundle).isAutoStart(); } return defaultAutoStart; } private String getStartLevel(String bundle) { if (startLevels.containsKey(bundle)) { return startLevels.get(bundle).getLevel(); } return defaultStartLevel; } }