
org.eclipse.m2e.internal.discovery.MavenDiscoveryService Maven / Gradle / Ivy
The newest version!
/*******************************************************************************
* Copyright (c) 2011 Sonatype, Inc.
* 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:
* Sonatype, Inc. - initial API and implementation
*******************************************************************************/
package org.eclipse.m2e.internal.discovery;
import java.lang.reflect.InvocationTargetException;
import java.util.ArrayList;
import java.util.Collection;
import java.util.HashSet;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;
import java.util.Set;
import org.apache.maven.execution.MavenExecutionRequest;
import org.apache.maven.plugin.MojoExecution;
import org.apache.maven.project.MavenProject;
import org.eclipse.core.runtime.CoreException;
import org.eclipse.core.runtime.IProgressMonitor;
import org.eclipse.core.runtime.IStatus;
import org.eclipse.core.runtime.Status;
import org.eclipse.equinox.internal.p2.discovery.Catalog;
import org.eclipse.equinox.internal.p2.discovery.model.CatalogItem;
import org.eclipse.equinox.internal.p2.ui.discovery.wizards.Messages;
import org.eclipse.equinox.p2.core.IProvisioningAgent;
import org.eclipse.equinox.p2.engine.IProfile;
import org.eclipse.equinox.p2.engine.IProfileRegistry;
import org.eclipse.equinox.p2.metadata.IInstallableUnit;
import org.eclipse.equinox.p2.query.IQuery;
import org.eclipse.equinox.p2.query.IQueryResult;
import org.eclipse.equinox.p2.query.QueryUtil;
import org.eclipse.equinox.p2.ui.ProvisioningUI;
import org.eclipse.jface.operation.IRunnableContext;
import org.eclipse.jface.operation.IRunnableWithProgress;
import org.eclipse.jface.window.Window;
import org.eclipse.m2e.core.MavenPlugin;
import org.eclipse.m2e.core.embedder.IMaven;
import org.eclipse.m2e.core.internal.lifecyclemapping.LifecycleMappingFactory;
import org.eclipse.m2e.core.internal.lifecyclemapping.LifecycleMappingResult;
import org.eclipse.m2e.core.internal.lifecyclemapping.MappingMetadataSource;
import org.eclipse.m2e.core.internal.lifecyclemapping.discovery.ILifecycleMappingRequirement;
import org.eclipse.m2e.core.internal.lifecyclemapping.discovery.IMavenDiscovery;
import org.eclipse.m2e.core.internal.lifecyclemapping.discovery.IMavenDiscoveryProposal;
import org.eclipse.m2e.core.internal.lifecyclemapping.discovery.MojoExecutionMappingConfiguration;
import org.eclipse.m2e.core.internal.lifecyclemapping.discovery.PackagingTypeMappingConfiguration;
import org.eclipse.m2e.core.internal.lifecyclemapping.model.LifecycleMappingMetadata;
import org.eclipse.m2e.core.internal.lifecyclemapping.model.LifecycleMappingMetadataSource;
import org.eclipse.m2e.core.internal.lifecyclemapping.model.PluginExecutionMetadata;
import org.eclipse.m2e.core.lifecyclemapping.model.IPluginExecutionMetadata;
import org.eclipse.m2e.core.lifecyclemapping.model.PluginExecutionAction;
import org.eclipse.m2e.core.project.configurator.MojoExecutionKey;
import org.eclipse.m2e.core.ui.internal.wizards.IMavenDiscoveryUI;
import org.eclipse.m2e.internal.discovery.operation.MavenDiscoveryInstallOperation;
import org.eclipse.m2e.internal.discovery.wizards.MavenDiscoveryUi;
import org.eclipse.osgi.util.NLS;
import org.eclipse.ui.statushandlers.StatusManager;
import org.osgi.framework.Bundle;
import org.osgi.framework.ServiceFactory;
import org.osgi.framework.ServiceRegistration;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
@SuppressWarnings({"restriction", "rawtypes"})
public class MavenDiscoveryService implements IMavenDiscoveryUI, IMavenDiscovery, ServiceFactory {
private static final Logger log = LoggerFactory.getLogger(MavenDiscoveryService.class);
public static class CatalogItemCacheEntry {
private final CatalogItem item;
private final LifecycleMappingMetadataSource metadataSource;
private final List projectConfigurators;
private final List mappingStrategies;
public CatalogItemCacheEntry(CatalogItem item, LifecycleMappingMetadataSource metadataSource,
List projectConfigurators, List mappingStrategies) {
this.item = item;
this.metadataSource = metadataSource;
this.projectConfigurators = projectConfigurators;
this.mappingStrategies = mappingStrategies;
}
public CatalogItem getItem() {
return item;
}
public LifecycleMappingMetadataSource getMetadataSource() {
return metadataSource;
}
public List getProjectConfigurators() {
return projectConfigurators;
}
public List getMappingStrategies() {
return mappingStrategies;
}
}
private List items;
public MavenDiscoveryService() {
this(true);
}
public MavenDiscoveryService(boolean factory) {
}
public Map> discover(MavenProject mavenProject,
List mojoExecutions, List preselected, IProgressMonitor monitor)
throws CoreException {
Map> proposals = new LinkedHashMap>();
if(items == null) {
items = new ArrayList();
Catalog catalog = MavenDiscovery.getCatalog();
IStatus status = catalog.performDiscovery(monitor);
if(!status.isOK()) {
log.error(status.toString());
return proposals;
}
IProvisioningAgent p2agent = ProvisioningUI.getDefaultUI().getSession().getProvisioningAgent();
IProfileRegistry profRegistry = (IProfileRegistry) p2agent.getService(IProfileRegistry.SERVICE_NAME);
IProfile profile = profRegistry.getProfile(IProfileRegistry.SELF);
for(CatalogItem item : catalog.getItems()) {
LifecycleMappingMetadataSource metadataSource = MavenDiscovery.getLifecycleMappingMetadataSource(item);
List projectConfigurators = new ArrayList();
List mappingStrategies = new ArrayList();
MavenDiscovery.getProvidedProjectConfigurators(item, projectConfigurators, mappingStrategies);
if(metadataSource != null && !itemInstalled(profile, item, monitor)) {
addCatalogItem(item, metadataSource, projectConfigurators, mappingStrategies);
}
}
catalog.dispose();
}
IMaven maven = MavenPlugin.getMaven();
MavenExecutionRequest request = maven.createExecutionRequest(monitor); // TODO this ignores workspace dependencies
Collection selectedItems = toCatalogItems(preselected);
List selectedSources = toMetadataSources(preselected);
for(CatalogItemCacheEntry itemEntry : items) {
CatalogItem item = itemEntry.getItem();
LifecycleMappingMetadataSource src = itemEntry.getMetadataSource();
boolean preselectItem = false;
for(CatalogItem selectedItem : selectedItems) {
if(selectedItem.getSiteUrl().equals(item.getSiteUrl())
&& selectedItem.getInstallableUnits().equals(item.getInstallableUnits())) {
preselectItem = true;
break;
}
}
if(src != null) {
src.setSource(item);
LifecycleMappingResult mappingResult = new LifecycleMappingResult();
List sources = new ArrayList(selectedSources);
if(!preselectItem) {
sources.add(src);
}
List metadataSources = LifecycleMappingFactory.getProjectMetadataSources(request,
mavenProject, sources, false, monitor);
LifecycleMappingFactory.calculateEffectiveLifecycleMappingMetadata(mappingResult, request, metadataSources,
mavenProject, mojoExecutions, false);
LifecycleMappingMetadata lifecycleMappingMetadata = mappingResult.getLifecycleMappingMetadata();
if(lifecycleMappingMetadata != null) {
IMavenDiscoveryProposal proposal = getProposal(lifecycleMappingMetadata.getSource());
if(proposal != null) {
put(proposals,
new PackagingTypeMappingConfiguration.PackagingTypeMappingRequirement(mavenProject.getPackaging()),
proposal);
} else if(!LifecycleMappingFactory.getLifecycleMappingExtensions().containsKey(
lifecycleMappingMetadata.getLifecycleMappingId())) {
if(itemEntry.getMappingStrategies().contains(lifecycleMappingMetadata.getLifecycleMappingId())) {
put(proposals, new PackagingTypeMappingConfiguration.LifecycleStrategyMappingRequirement(
lifecycleMappingMetadata.getPackagingType(), lifecycleMappingMetadata.getLifecycleMappingId()),
new InstallCatalogItemMavenDiscoveryProposal(item));
}
}
}
for(Map.Entry> entry : mappingResult.getMojoExecutionMapping()
.entrySet()) {
if(entry.getValue() != null) {
for(IPluginExecutionMetadata executionMapping : entry.getValue()) {
IMavenDiscoveryProposal proposal = getProposal(((PluginExecutionMetadata)executionMapping).getSource());
if(proposal != null) {
// assumes installation of mapping proposal installs all required project configurators
put(proposals, new MojoExecutionMappingConfiguration.MojoExecutionMappingRequirement(entry.getKey()),
proposal);
} else if(executionMapping.getAction() == PluginExecutionAction.configurator) {
// we have mapping from pom.xml
String configuratorId = LifecycleMappingFactory.getProjectConfiguratorId(executionMapping);
if(!LifecycleMappingFactory.getProjectConfiguratorExtensions().containsKey(configuratorId)) {
// User Story.
// Project pom.xml explicitly specifies lifecycle mapping strategy implementation,
// but the implementation is not currently installed. As a user I expect m2e to search
// marketplace for the implementation and offer installation if available
if(itemEntry.getProjectConfigurators().contains(configuratorId)) {
put(proposals,
new MojoExecutionMappingConfiguration.ProjectConfiguratorMappingRequirement(entry.getKey(),
configuratorId), new InstallCatalogItemMavenDiscoveryProposal(item));
}
}
}
}
}
}
}
}
return proposals;
}
/**
* Returns true if all IUs specified in the catalog item are installed in the profile
*/
public boolean itemInstalled(IProfile profile, CatalogItem item, IProgressMonitor monitor) {
if(profile == null) {
return false;
}
List> queries = new ArrayList>();
for(String iuId : item.getInstallableUnits()) {
queries.add(QueryUtil.createIUQuery(iuId));
}
IQueryResult result = profile.query(QueryUtil.createCompoundQuery(queries, true), monitor);
return !result.isEmpty();
}
public void addCatalogItem(CatalogItem item, LifecycleMappingMetadataSource metadataSource,
List projectConfigurators, List mappingStrategies) {
if(items == null) {
// for tests
items = new ArrayList();
}
items.add(new CatalogItemCacheEntry(item, metadataSource, projectConfigurators, mappingStrategies));
}
private IMavenDiscoveryProposal getProposal(LifecycleMappingMetadataSource src) {
if(src == null) {
return null;
}
if(src.getSource() instanceof CatalogItem) {
return new InstallCatalogItemMavenDiscoveryProposal((CatalogItem) src.getSource());
}
return null;
}
private List toMetadataSources(List proposals) {
List sources = new ArrayList();
for(IMavenDiscoveryProposal proposal : proposals) {
if(proposal instanceof InstallCatalogItemMavenDiscoveryProposal) {
CatalogItem catalogItem = ((InstallCatalogItemMavenDiscoveryProposal) proposal).getCatalogItem();
LifecycleMappingMetadataSource source = MavenDiscovery.getLifecycleMappingMetadataSource(catalogItem);
source.setSource(catalogItem);
sources.add(source);
}
}
return sources;
}
private void put(Map> allproposals,
ILifecycleMappingRequirement requirement, IMavenDiscoveryProposal proposal) {
List proposals = allproposals.get(requirement);
if(proposals == null) {
proposals = new ArrayList();
allproposals.put(requirement, proposals);
}
if(!proposals.contains(proposal)) {
proposals.add(proposal);
}
}
public boolean implement(List proposals, IRunnableWithProgress postInstallHook,
IRunnableContext context, Collection projectsToConfigure) {
try {
MavenDiscoveryInstallOperation runner = new MavenDiscoveryInstallOperation(toCatalogItems(proposals),
postInstallHook, true, false, projectsToConfigure);
context.run(true, true, runner);
int openInstallWizard = MavenDiscoveryUi.openInstallWizard(runner.getOperation(), true);
return openInstallWizard == Window.OK;
} catch(InvocationTargetException e) {
IStatus status = new Status(IStatus.ERROR, DiscoveryActivator.PLUGIN_ID, NLS.bind(
Messages.ConnectorDiscoveryWizard_installProblems, new Object[] {e.getCause().getMessage()}), e.getCause());
StatusManager.getManager().handle(status, StatusManager.SHOW | StatusManager.BLOCK | StatusManager.LOG);
return false;
} catch(InterruptedException e) {
// canceled
return false;
}
}
private Collection toCatalogItems(List proposals) {
Set items = new HashSet();
for(IMavenDiscoveryProposal proposal : proposals) {
if(proposal instanceof InstallCatalogItemMavenDiscoveryProposal) {
items.add(((InstallCatalogItemMavenDiscoveryProposal) proposal).getCatalogItem());
}
}
return items;
}
public Object getService(Bundle bundle, ServiceRegistration registration) {
return new MavenDiscoveryService(false); // not a factory instance
}
public void ungetService(Bundle bundle, ServiceRegistration registration, Object service) {
}
}
© 2015 - 2025 Weber Informatics LLC | Privacy Policy