| /******************************************************************************* |
| * Copyright (c) 2008, 2009 Code 9 and others. All rights reserved. This |
| * program and the accompanying materials are made available under the terms of |
| * the Eclipse Public License v1.0 which accompanies this distribution, and is |
| * available at http://www.eclipse.org/legal/epl-v10.html |
| * |
| * Contributors: |
| * Code 9 - initial API and implementation |
| * IBM - ongoing development |
| ******************************************************************************/ |
| package org.eclipse.equinox.p2.publisher.eclipse; |
| |
| import java.io.File; |
| import java.util.*; |
| import org.eclipse.core.runtime.*; |
| import org.eclipse.equinox.internal.p2.publisher.eclipse.ExecutablesDescriptor; |
| import org.eclipse.equinox.p2.metadata.*; |
| import org.eclipse.equinox.p2.metadata.MetadataFactory.InstallableUnitDescription; |
| import org.eclipse.equinox.p2.publisher.*; |
| import org.eclipse.equinox.p2.publisher.actions.VersionAdvice; |
| import org.eclipse.equinox.p2.query.QueryUtil; |
| |
| /** |
| * Create IUs and CUs that represent the entire launcher for an application. This includes |
| * the executable, the launcher fragments as well as the CUs required to install and configure |
| * these elements. |
| */ |
| public class ApplicationLauncherAction extends AbstractPublisherAction { |
| |
| private final String flavor; |
| private final String[] configSpecs; |
| private final File location; |
| private final String executableName; |
| private final Version version; |
| private final String id; |
| |
| /** |
| * Returns the id of the top level IU published by this action for the given id and flavor. |
| * @param id the id of the application being published |
| * @param flavor the flavor being published |
| * @return the if for ius published by this action |
| */ |
| public static String computeIUId(String id, String flavor) { |
| return flavor + id + ".application"; //$NON-NLS-1$ |
| } |
| |
| public ApplicationLauncherAction(String id, Version version, String flavor, String executableName, File location, String[] configSpecs) { |
| this.flavor = flavor; |
| this.configSpecs = configSpecs; |
| this.id = id; |
| this.version = version; |
| this.executableName = executableName; |
| this.location = location; |
| } |
| |
| @Override |
| public IStatus perform(IPublisherInfo publisherInfo, IPublisherResult results, IProgressMonitor monitor) { |
| // Create the basic actions and run them putting the IUs in a temporary result |
| Collection<IPublisherAction> actions = createActions(publisherInfo); |
| createAdvice(publisherInfo, results); |
| IPublisherResult innerResult = new PublisherResult(); |
| MultiStatus finalStatus = new MultiStatus(ApplicationLauncherAction.class.getName(), 0, "publishing result", null); //$NON-NLS-1$ |
| for (IPublisherAction action : actions) { |
| if (monitor.isCanceled()) |
| return Status.CANCEL_STATUS; |
| finalStatus.merge(action.perform(publisherInfo, innerResult, monitor)); |
| } |
| if (!finalStatus.isOK()) |
| return finalStatus; |
| // merge the IUs into the final result as non-roots and create a parent IU that captures them all |
| results.merge(innerResult, IPublisherResult.MERGE_ALL_NON_ROOT); |
| publishApplicationLauncherIU(innerResult.getIUs(null, IPublisherResult.ROOT), results); |
| return Status.OK_STATUS; |
| } |
| |
| /** |
| * Create advice needed by the actions related to and following this action |
| */ |
| private void createAdvice(IPublisherInfo publisherInfo, IPublisherResult results) { |
| createLauncherAdvice(publisherInfo, results); |
| } |
| |
| /** |
| * Create and register advice that will tell people what versions of the launcher bundle and |
| * fragments are in use in this particular result. |
| */ |
| private void createLauncherAdvice(IPublisherInfo publisherInfo, IPublisherResult results) { |
| Collection<IInstallableUnit> ius = getIUs(results.getIUs(null, null), EquinoxLauncherCUAction.ORG_ECLIPSE_EQUINOX_LAUNCHER); |
| VersionAdvice advice = new VersionAdvice(); |
| boolean found = false; |
| for (IInstallableUnit iu : ius) { |
| // skip over source bundles and fragments |
| // TODO should we use the source property here rather than magic name matching? |
| if (iu.getId().endsWith(".source") || QueryUtil.isFragment(iu)) //$NON-NLS-1$ |
| continue; |
| advice.setVersion(IInstallableUnit.NAMESPACE_IU_ID, iu.getId(), iu.getVersion()); |
| found = true; |
| } |
| if (found) |
| publisherInfo.addAdvice(advice); |
| } |
| |
| private Collection<IInstallableUnit> getIUs(Collection<IInstallableUnit> ius, String prefix) { |
| Set<IInstallableUnit> result = new HashSet<IInstallableUnit>(); |
| for (IInstallableUnit tmp : ius) { |
| if (tmp.getId().startsWith(prefix)) |
| result.add(tmp); |
| } |
| return result; |
| } |
| |
| private void publishApplicationLauncherIU(Collection<? extends IVersionedId> children, IPublisherResult result) { |
| InstallableUnitDescription descriptor = createParentIU(children, computeIUId(id, flavor), version); |
| descriptor.setSingleton(true); |
| IInstallableUnit rootIU = MetadataFactory.createInstallableUnit(descriptor); |
| if (rootIU == null) |
| return; |
| result.addIU(rootIU, IPublisherResult.ROOT); |
| } |
| |
| private Collection<IPublisherAction> createActions(IPublisherInfo publisherInfo) { |
| Collection<IPublisherAction> actions = new ArrayList<IPublisherAction>(); |
| actions.add(new EquinoxLauncherCUAction(flavor, configSpecs)); |
| actions.addAll(createExecutablesActions(configSpecs)); |
| return actions; |
| } |
| |
| protected Collection<IPublisherAction> createExecutablesActions(String[] configs) { |
| Collection<IPublisherAction> actions = new ArrayList<IPublisherAction>(configs.length); |
| for (int i = 0; i < configs.length; i++) { |
| ExecutablesDescriptor executables = computeExecutables(configs[i]); |
| IPublisherAction action = new EquinoxExecutableAction(executables, configs[i], id, version, flavor); |
| actions.add(action); |
| } |
| return actions; |
| } |
| |
| protected ExecutablesDescriptor computeExecutables(String configSpec) { |
| // See if we know about an executables feature then use it as the source |
| ExecutablesDescriptor result = ExecutablesDescriptor.createExecutablesFromFeature(location, configSpec); |
| if (result != null) |
| return result; |
| // otherwise, assume that we are running against an Eclipse install and do the default thing |
| String os = AbstractPublisherAction.parseConfigSpec(configSpec)[1]; |
| return ExecutablesDescriptor.createDescriptor(os, executableName, location); |
| } |
| } |