Merge tag 'v2.3.28' into testing
[lgpl/argeo-commons.git] / org.argeo.init / src / org / argeo / init / a2 / ProvisioningManager.java
diff --git a/org.argeo.init/src/org/argeo/init/a2/ProvisioningManager.java b/org.argeo.init/src/org/argeo/init/a2/ProvisioningManager.java
deleted file mode 100644 (file)
index 289870a..0000000
+++ /dev/null
@@ -1,290 +0,0 @@
-package org.argeo.init.a2;
-
-import static org.argeo.init.a2.A2Source.SCHEME_A2;
-import static org.argeo.init.a2.A2Source.SCHEME_A2_REFERENCE;
-
-import java.io.File;
-import java.io.UnsupportedEncodingException;
-import java.net.URI;
-import java.net.URLDecoder;
-import java.nio.charset.StandardCharsets;
-import java.nio.file.Files;
-import java.nio.file.Path;
-import java.nio.file.Paths;
-import java.util.ArrayList;
-import java.util.Collection;
-import java.util.Collections;
-import java.util.HashMap;
-import java.util.HashSet;
-import java.util.LinkedHashMap;
-import java.util.LinkedList;
-import java.util.List;
-import java.util.Map;
-import java.util.Set;
-
-import org.argeo.init.osgi.OsgiBootUtils;
-import org.osgi.framework.Bundle;
-import org.osgi.framework.BundleContext;
-import org.osgi.framework.Constants;
-import org.osgi.framework.Version;
-import org.osgi.framework.wiring.FrameworkWiring;
-
-/** Loads provisioning sources into an OSGi context. */
-public class ProvisioningManager {
-       BundleContext bc;
-       OsgiContext osgiContext;
-       List<ProvisioningSource> sources = Collections.synchronizedList(new ArrayList<>());
-
-       public ProvisioningManager(BundleContext bc) {
-               this.bc = bc;
-               osgiContext = new OsgiContext(bc);
-               osgiContext.load();
-       }
-
-       protected void addSource(ProvisioningSource source) {
-               sources.add(source);
-       }
-
-       void installWholeSource(ProvisioningSource source) {
-               Set<Bundle> updatedBundles = new HashSet<>();
-               for (A2Contribution contribution : source.listContributions(null)) {
-                       for (A2Component component : contribution.components.values()) {
-                               A2Module module = component.last().last();
-                               Bundle bundle = installOrUpdate(module);
-                               if (bundle != null)
-                                       updatedBundles.add(bundle);
-                       }
-               }
-//             FrameworkWiring frameworkWiring = bc.getBundle(0).adapt(FrameworkWiring.class);
-//             frameworkWiring.refreshBundles(updatedBundles);
-       }
-
-       public void registerSource(String uri) {
-               try {
-                       URI u = new URI(uri);
-
-                       // XOR
-                       Map<String, List<String>> properties = queryToMap(u);
-                       Map<String, String> xOr = new HashMap<>();
-                       for (String key : properties.keySet()) {
-                               List<String> lst = properties.get(key);
-                               if (lst.size() != 1)
-                                       throw new IllegalArgumentException("Invalid XOR definitions in " + uri);
-                               xOr.put(key, lst.get(0));
-                       }
-
-                       if (SCHEME_A2.equals(u.getScheme()) || SCHEME_A2_REFERENCE.equals(u.getScheme())) {
-                               if (u.getHost() == null || "".equals(u.getHost())) {
-                                       String baseStr = u.getPath();
-                                       if (File.separatorChar == '\\') {// MS Windows
-                                               baseStr = baseStr.substring(1).replace('/', File.separatorChar);
-                                       }
-                                       Path base = Paths.get(baseStr);
-                                       if (Files.exists(base)) {
-                                               FsA2Source source = new FsA2Source(base, xOr, SCHEME_A2_REFERENCE.equals(u.getScheme()));
-                                               source.load();
-                                               addSource(source);
-                                               OsgiBootUtils.info("Registered " + uri + " as source");
-
-                                               // OS specific / native
-                                               String localRelPath = A2Contribution.localOsArchRelativePath();
-                                               Path localLibBase = base.resolve(A2Contribution.LIB).resolve(localRelPath);
-                                               if (Files.exists(localLibBase)) {
-                                                       FsA2Source libSource = new FsA2Source(localLibBase, xOr,
-                                                                       SCHEME_A2_REFERENCE.equals(u.getScheme()));
-                                                       libSource.load();
-                                                       addSource(libSource);
-                                                       OsgiBootUtils.info("Registered OS-specific " + uri + " as source (" + localRelPath + ")");
-                                               }
-                                       } else {
-                                               OsgiBootUtils.debug("Source " + base + " does not exist, ignoring.");
-                                       }
-                               } else {
-                                       throw new UnsupportedOperationException(
-                                                       "Remote installation is not yet supported, cannot add source " + u);
-                               }
-                       } else {
-                               throw new IllegalArgumentException("Unkown scheme: for source " + u);
-                       }
-               } catch (Exception e) {
-                       throw new A2Exception("Cannot add source " + uri, e);
-               }
-       }
-
-       public boolean registerDefaultSource() {
-               String frameworkLocation = bc.getProperty("osgi.framework");
-               try {
-                       URI frameworkLocationUri = new URI(frameworkLocation);
-                       if ("file".equals(frameworkLocationUri.getScheme())) {
-                               Path frameworkPath = Paths.get(frameworkLocationUri);
-                               if (frameworkPath.getParent().getFileName().toString().equals(A2Contribution.BOOT)) {
-                                       Path base = frameworkPath.getParent().getParent();
-                                       String baseStr = base.toString();
-                                       if (File.separatorChar == '\\')// MS Windows
-                                               baseStr = '/' + baseStr.replace(File.separatorChar, '/');
-                                       URI baseUri = new URI(A2Source.SCHEME_A2, null, null, 0, baseStr, null, null);
-                                       registerSource(baseUri.toString());
-                                       OsgiBootUtils.debug("Default source from framework location " + frameworkLocation);
-                                       return true;
-                               }
-                       }
-               } catch (Exception e) {
-                       OsgiBootUtils.error("Cannot register default source based on framework location " + frameworkLocation, e);
-               }
-               return false;
-       }
-
-       public void install(String spec) {
-               if (spec == null) {
-                       for (ProvisioningSource source : sources) {
-                               installWholeSource(source);
-                       }
-               }
-       }
-
-       /** @return the new/updated bundle, or null if nothing was done. */
-       protected Bundle installOrUpdate(A2Module module) {
-               try {
-                       ProvisioningSource moduleSource = module.getBranch().getComponent().getContribution().getSource();
-                       Version moduleVersion = module.getVersion();
-                       A2Branch osgiBranch = osgiContext.findBranch(module.getBranch().getComponent().getId(), moduleVersion);
-                       if (osgiBranch == null) {
-                               Bundle bundle = moduleSource.install(bc, module);
-                               // TODO make it more dynamic, based on OSGi APIs
-                               osgiContext.registerBundle(bundle);
-//                             if (OsgiBootUtils.isDebug())
-//                                     OsgiBootUtils.debug("Installed bundle " + bundle.getLocation() + " with version " + moduleVersion);
-                               return bundle;
-                       } else {
-                               A2Module lastOsgiModule = osgiBranch.last();
-                               int compare = moduleVersion.compareTo(lastOsgiModule.getVersion());
-                               if (compare >= 0) {// update (also if same version)
-                                       Bundle bundle = (Bundle) lastOsgiModule.getLocator();
-                                       if (bundle.getBundleId() == 0)// ignore framework bundle
-                                               return null;
-                                       moduleSource.update(bundle, module);
-                                       // TODO make it more dynamic, based on OSGi APIs
-                                       // TODO remove old module? Or keep update history?
-                                       osgiContext.registerBundle(bundle);
-                                       OsgiBootUtils.info("Updated bundle " + bundle.getLocation() + " to version " + moduleVersion);
-                                       return bundle;
-                               } else {
-                                       if (OsgiBootUtils.isDebug())
-                                               OsgiBootUtils.debug("Did not install as bundle module " + module
-                                                               + " since a module with higher version " + lastOsgiModule.getVersion()
-                                                               + " is already installed for branch " + osgiBranch);
-                               }
-                       }
-               } catch (Exception e) {
-                       OsgiBootUtils.error("Could not install module " + module + ": " + e.getMessage(), e);
-               }
-               return null;
-       }
-
-       public Collection<Bundle> update() {
-               boolean fragmentsUpdated = false;
-               Set<Bundle> updatedBundles = new HashSet<>();
-               bundles: for (Bundle bundle : bc.getBundles()) {
-                       for (ProvisioningSource source : sources) {
-                               String componentId = bundle.getSymbolicName();
-                               Version version = bundle.getVersion();
-                               A2Branch branch = source.findBranch(componentId, version);
-                               if (branch == null)
-                                       continue bundles;
-                               A2Module module = branch.last();
-                               Version moduleVersion = module.getVersion();
-                               int compare = moduleVersion.compareTo(version);
-                               if (compare > 0) {// update
-                                       try {
-                                               source.update(bundle, module);
-//                                             bundle.update(in);
-                                               String fragmentHost = bundle.getHeaders().get(Constants.FRAGMENT_HOST);
-                                               if (fragmentHost != null)
-                                                       fragmentsUpdated = true;
-                                               OsgiBootUtils.info("Updated bundle " + bundle.getLocation() + " to version " + moduleVersion);
-                                               updatedBundles.add(bundle);
-                                       } catch (Exception e) {
-                                               OsgiBootUtils.error("Cannot update with module " + module, e);
-                                       }
-                               }
-                       }
-               }
-               FrameworkWiring frameworkWiring = bc.getBundle(0).adapt(FrameworkWiring.class);
-               if (fragmentsUpdated)// refresh all
-                       frameworkWiring.refreshBundles(null);
-               else
-                       frameworkWiring.refreshBundles(updatedBundles);
-               return updatedBundles;
-       }
-
-       private static Map<String, List<String>> queryToMap(URI uri) {
-               return queryToMap(uri.getQuery());
-       }
-
-       private static Map<String, List<String>> queryToMap(String queryPart) {
-               try {
-                       final Map<String, List<String>> query_pairs = new LinkedHashMap<String, List<String>>();
-                       if (queryPart == null)
-                               return query_pairs;
-                       final String[] pairs = queryPart.split("&");
-                       for (String pair : pairs) {
-                               final int idx = pair.indexOf("=");
-                               final String key = idx > 0 ? URLDecoder.decode(pair.substring(0, idx), StandardCharsets.UTF_8.name())
-                                               : pair;
-                               if (!query_pairs.containsKey(key)) {
-                                       query_pairs.put(key, new LinkedList<String>());
-                               }
-                               final String value = idx > 0 && pair.length() > idx + 1
-                                               ? URLDecoder.decode(pair.substring(idx + 1), StandardCharsets.UTF_8.name())
-                                               : null;
-                               query_pairs.get(key).add(value);
-                       }
-                       return query_pairs;
-               } catch (UnsupportedEncodingException e) {
-                       throw new IllegalArgumentException("Cannot convert " + queryPart + " to map", e);
-               }
-       }
-
-//     public static void main(String[] args) {
-//             if (args.length == 0)
-//                     throw new IllegalArgumentException("Usage: <path to A2 base>");
-//             Map<String, String> configuration = new HashMap<>();
-//             configuration.put("osgi.console", "2323");
-//             configuration.put("org.osgi.framework.bootdelegation",
-//                             "com.sun.jndi.ldap,com.sun.jndi.ldap.sasl,com.sun.security.jgss,com.sun.jndi.dns,com.sun.nio.file,com.sun.nio.sctp,sun.nio.cs");
-//             Framework framework = OsgiBootUtils.launch(configuration);
-//             try {
-//                     ProvisioningManager pm = new ProvisioningManager(framework.getBundleContext());
-//                     Map<String, String> xOr = new HashMap<>();
-//                     xOr.put("osgi", "equinox");
-//                     xOr.put("swt", "rap");
-//                     FsA2Source context = new FsA2Source(Paths.get(args[0]), xOr);
-//                     context.load();
-//                     pm.addSource(context);
-//                     if (framework.getBundleContext().getBundles().length == 1) {// initial
-//                             pm.install(null);
-//                     } else {
-//                             pm.update();
-//                     }
-//
-//                     Thread.sleep(2000);
-//
-//                     Bundle[] bundles = framework.getBundleContext().getBundles();
-//                     Arrays.sort(bundles, (b1, b2) -> b1.getSymbolicName().compareTo(b2.getSymbolicName()));
-//                     for (Bundle b : bundles)
-//                             if (b.getState() == Bundle.RESOLVED || b.getState() == Bundle.STARTING || b.getState() == Bundle.ACTIVE)
-//                                     System.out.println(b.getSymbolicName() + " " + b.getVersion());
-//                             else
-//                                     System.err.println(b.getSymbolicName() + " " + b.getVersion() + " (" + b.getState() + ")");
-//             } catch (Exception e) {
-//                     e.printStackTrace();
-//             } finally {
-//                     try {
-//                             framework.stop();
-//                     } catch (Exception e) {
-//                             e.printStackTrace();
-//                     }
-//             }
-//     }
-
-}