mirror of
https://gitflic.ru/project/openide/openide.git
synced 2026-09-21 12:14:37 +07:00
maven: use aether for maven3 dependencies resolving
Related issues: IDEA-99301 Maven import does not honor order of dependencies on classpath IDEA-120647 a JUnit case succeeds in `mvn test` and eclipse but fails in intellij IDEA-89979 Module dependency ordering doesn't reflect maven pom dependency ordering IDEA-73255 IntelliJ test classpath doesn't match Maven's IDEA-110060 order of classpath entitis of project shall be the same as in maven pom IDEA-98262 Maven scope "provided" is overriden by "test"
This commit is contained in:
+88
@@ -0,0 +1,88 @@
|
||||
/*
|
||||
* Copyright 2000-2014 JetBrains s.r.o.
|
||||
*
|
||||
* 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 org.jetbrains.idea.maven.server;
|
||||
|
||||
import gnu.trove.THashMap;
|
||||
import org.apache.maven.RepositoryUtils;
|
||||
import org.apache.maven.artifact.Artifact;
|
||||
import org.apache.maven.model.Model;
|
||||
import org.apache.maven.model.Parent;
|
||||
import org.jetbrains.idea.maven.model.*;
|
||||
import org.sonatype.aether.graph.DependencyNode;
|
||||
|
||||
import java.io.File;
|
||||
import java.rmi.RemoteException;
|
||||
import java.util.*;
|
||||
|
||||
/**
|
||||
* {@link AetherModelConverter} provides adapted methods of {@link MavenModelConverter} for aether models conversion
|
||||
*
|
||||
* @author Vladislav.Soroka
|
||||
* @since 9/24/2014
|
||||
*/
|
||||
public class AetherModelConverter extends MavenModelConverter {
|
||||
|
||||
public static MavenModel convertModelWithAetherDependencyTree(Model model,
|
||||
List<String> sources,
|
||||
List<String> testSources,
|
||||
Collection<Artifact> dependencies,
|
||||
Collection<DependencyNode> dependencyTree,
|
||||
Collection<Artifact> extensions,
|
||||
File localRepository) throws RemoteException {
|
||||
MavenModel result = new MavenModel();
|
||||
result.setMavenId(new MavenId(model.getGroupId(), model.getArtifactId(), model.getVersion()));
|
||||
|
||||
Parent parent = model.getParent();
|
||||
if (parent != null) {
|
||||
result.setParent(new MavenParent(new MavenId(parent.getGroupId(), parent.getArtifactId(), parent.getVersion()),
|
||||
parent.getRelativePath()));
|
||||
}
|
||||
result.setPackaging(model.getPackaging());
|
||||
result.setName(model.getName());
|
||||
result.setProperties(model.getProperties() == null ? new Properties() : model.getProperties());
|
||||
result.setPlugins(convertPlugins(model));
|
||||
|
||||
Map<Artifact, MavenArtifact> convertedArtifacts = new THashMap<Artifact, MavenArtifact>();
|
||||
result.setExtensions(convertArtifacts(extensions, convertedArtifacts, localRepository));
|
||||
result.setDependencies(convertArtifacts(dependencies, convertedArtifacts, localRepository));
|
||||
result.setDependencyTree(convertAetherDependencyNodes(null, dependencyTree, convertedArtifacts, localRepository));
|
||||
|
||||
result.setRemoteRepositories(convertRepositories(model.getRepositories()));
|
||||
result.setProfiles(convertProfiles(model.getProfiles()));
|
||||
result.setModules(model.getModules());
|
||||
|
||||
convertBuild(result.getBuild(), model.getBuild(), sources, testSources);
|
||||
return result;
|
||||
}
|
||||
|
||||
public static List<MavenArtifactNode> convertAetherDependencyNodes(MavenArtifactNode parent,
|
||||
Collection<DependencyNode> nodes,
|
||||
Map<Artifact, MavenArtifact> nativeToConvertedMap,
|
||||
File localRepository) {
|
||||
List<MavenArtifactNode> result = new ArrayList<MavenArtifactNode>(nodes.size());
|
||||
for (DependencyNode each : nodes) {
|
||||
Artifact a = RepositoryUtils.toArtifact(each.getDependency().getArtifact());
|
||||
MavenArtifact ma = convertArtifact(a, nativeToConvertedMap, localRepository);
|
||||
|
||||
MavenArtifactNode newNode = new MavenArtifactNode(
|
||||
parent, ma, MavenArtifactState.ADDED, null, each.getDependency().getScope(),
|
||||
each.getPremanagedVersion(), each.getPremanagedScope());
|
||||
newNode.setDependencies(convertAetherDependencyNodes(newNode, each.getChildren(), nativeToConvertedMap, localRepository));
|
||||
result.add(newNode);
|
||||
}
|
||||
return result;
|
||||
}
|
||||
}
|
||||
+103
-17
@@ -40,6 +40,7 @@ import org.apache.maven.plugin.LegacySupport;
|
||||
import org.apache.maven.plugin.internal.PluginDependenciesResolver;
|
||||
import org.apache.maven.profiles.activation.*;
|
||||
import org.apache.maven.project.*;
|
||||
import org.apache.maven.project.ProjectDependenciesResolver;
|
||||
import org.apache.maven.project.inheritance.DefaultModelInheritanceAssembler;
|
||||
import org.apache.maven.project.interpolation.AbstractStringBasedModelInterpolator;
|
||||
import org.apache.maven.project.interpolation.ModelInterpolationException;
|
||||
@@ -69,6 +70,8 @@ import org.jetbrains.idea.maven.model.*;
|
||||
import org.jetbrains.idea.maven.server.embedder.*;
|
||||
import org.jetbrains.idea.maven.server.embedder.MavenExecutionResult;
|
||||
import org.sonatype.aether.RepositorySystemSession;
|
||||
import org.sonatype.aether.graph.Dependency;
|
||||
import org.sonatype.aether.repository.LocalRepositoryManager;
|
||||
import org.sonatype.aether.util.DefaultRepositorySystemSession;
|
||||
import org.sonatype.aether.util.graph.PreorderNodeListGenerator;
|
||||
|
||||
@@ -97,6 +100,9 @@ import java.util.concurrent.atomic.AtomicReference;
|
||||
org.jetbrains.idea.maven.server.embedder.CustomMaven3ModelInterpolator2 <-> org.apache.maven.model.interpolation.StringSearchModelInterpolator
|
||||
*/
|
||||
public class Maven3ServerEmbedderImpl extends MavenRemoteObject implements MavenServerEmbedder {
|
||||
|
||||
private final static boolean USE_MVN2_COMPATIBLE_DEPENDENCY_RESOLVING = System.getProperty("maven3.use.compat.resolver") != null;
|
||||
|
||||
@NotNull private final DefaultPlexusContainer myContainer;
|
||||
@NotNull private final Settings myMavenSettings;
|
||||
|
||||
@@ -410,23 +416,41 @@ public class Maven3ServerEmbedderImpl extends MavenRemoteObject implements Maven
|
||||
project.setDependencyArtifacts(project.createArtifacts(getComponent(ArtifactFactory.class), null, null));
|
||||
//
|
||||
|
||||
ArtifactResolutionRequest resolutionRequest = new ArtifactResolutionRequest();
|
||||
resolutionRequest.setArtifactDependencies(project.getDependencyArtifacts());
|
||||
resolutionRequest.setArtifact(project.getArtifact());
|
||||
resolutionRequest.setManagedVersionMap(project.getManagedVersionMap());
|
||||
resolutionRequest.setLocalRepository(myLocalRepository);
|
||||
resolutionRequest.setRemoteRepositories(project.getRemoteArtifactRepositories());
|
||||
resolutionRequest.setListeners(listeners);
|
||||
if (USE_MVN2_COMPATIBLE_DEPENDENCY_RESOLVING) {
|
||||
ArtifactResolutionRequest resolutionRequest = new ArtifactResolutionRequest();
|
||||
resolutionRequest.setArtifactDependencies(project.getDependencyArtifacts());
|
||||
resolutionRequest.setArtifact(project.getArtifact());
|
||||
resolutionRequest.setManagedVersionMap(project.getManagedVersionMap());
|
||||
resolutionRequest.setLocalRepository(myLocalRepository);
|
||||
resolutionRequest.setRemoteRepositories(project.getRemoteArtifactRepositories());
|
||||
resolutionRequest.setListeners(listeners);
|
||||
|
||||
resolutionRequest.setResolveRoot(false);
|
||||
resolutionRequest.setResolveTransitively(true);
|
||||
resolutionRequest.setResolveRoot(false);
|
||||
resolutionRequest.setResolveTransitively(true);
|
||||
|
||||
ArtifactResolver resolver = getComponent(ArtifactResolver.class);
|
||||
ArtifactResolutionResult result = resolver.resolve(resolutionRequest);
|
||||
ArtifactResolver resolver = getComponent(ArtifactResolver.class);
|
||||
ArtifactResolutionResult result = resolver.resolve(resolutionRequest);
|
||||
|
||||
project.setArtifacts(result.getArtifacts());
|
||||
project.setArtifacts(result.getArtifacts());
|
||||
// end copied from DefaultMavenProjectBuilder.buildWithDependencies
|
||||
ref.set(new MavenExecutionResult(project, exceptions));
|
||||
ref.set(new MavenExecutionResult(project, exceptions));
|
||||
}
|
||||
else {
|
||||
final DependencyResolutionResult dependencyResolutionResult = resolveDependencies(project, repositorySession);
|
||||
final List<Dependency> dependencies = dependencyResolutionResult.getDependencies();
|
||||
|
||||
Set<Artifact> artifacts = new LinkedHashSet<Artifact>(dependencies.size());
|
||||
for (Dependency dependency : dependencies) {
|
||||
final Artifact artifact = RepositoryUtils.toArtifact(dependency.getArtifact());
|
||||
artifact.setScope(dependency.getScope());
|
||||
artifact.setOptional(dependency.isOptional());
|
||||
artifacts.add(artifact);
|
||||
resolveAsModule(artifact);
|
||||
}
|
||||
|
||||
project.setArtifacts(artifacts);
|
||||
ref.set(new MavenExecutionResult(project, dependencyResolutionResult, exceptions));
|
||||
}
|
||||
}
|
||||
catch (Exception e) {
|
||||
ref.set(handleException(e));
|
||||
@@ -437,6 +461,54 @@ public class Maven3ServerEmbedderImpl extends MavenRemoteObject implements Maven
|
||||
return ref.get();
|
||||
}
|
||||
|
||||
private boolean resolveAsModule(Artifact a) {
|
||||
MavenWorkspaceMap map = myWorkspaceMap;
|
||||
if (map == null) return false;
|
||||
|
||||
MavenWorkspaceMap.Data resolved = map.findFileAndOriginalId(MavenModelConverter.createMavenId(a));
|
||||
if (resolved == null) return false;
|
||||
|
||||
a.setResolved(true);
|
||||
a.setFile(resolved.getFile(a.getType()));
|
||||
a.selectVersion(resolved.originalId.getVersion());
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* copied from {@link org.apache.maven.project.DefaultProjectBuilder#resolveDependencies(org.apache.maven.project.MavenProject, org.sonatype.aether.RepositorySystemSession)}
|
||||
*/
|
||||
private DependencyResolutionResult resolveDependencies(MavenProject project, RepositorySystemSession session) {
|
||||
DependencyResolutionResult resolutionResult;
|
||||
|
||||
try {
|
||||
ProjectDependenciesResolver dependencyResolver = getComponent(ProjectDependenciesResolver.class);
|
||||
DefaultDependencyResolutionRequest resolution = new DefaultDependencyResolutionRequest(project, session);
|
||||
resolutionResult = dependencyResolver.resolve(resolution);
|
||||
}
|
||||
catch (DependencyResolutionException e) {
|
||||
resolutionResult = e.getResult();
|
||||
}
|
||||
|
||||
Set<Artifact> artifacts = new LinkedHashSet<Artifact>();
|
||||
if (resolutionResult.getDependencyGraph() != null) {
|
||||
RepositoryUtils.toArtifacts(artifacts, resolutionResult.getDependencyGraph().getChildren(),
|
||||
Collections.singletonList(project.getArtifact().getId()), null);
|
||||
|
||||
// Maven 2.x quirk: an artifact always points at the local repo, regardless whether resolved or not
|
||||
LocalRepositoryManager lrm = session.getLocalRepositoryManager();
|
||||
for (Artifact artifact : artifacts) {
|
||||
if (!artifact.isResolved()) {
|
||||
String path = lrm.getPathForLocalArtifact(RepositoryUtils.toArtifact(artifact));
|
||||
artifact.setFile(new File(lrm.getRepository().getBasedir(), path));
|
||||
}
|
||||
}
|
||||
}
|
||||
project.setResolvedArtifacts(artifacts);
|
||||
project.setArtifacts(artifacts);
|
||||
|
||||
return resolutionResult;
|
||||
}
|
||||
|
||||
/**
|
||||
* adapted from {@link org.apache.maven.DefaultMaven#doExecute(org.apache.maven.execution.MavenExecutionRequest)}
|
||||
*/
|
||||
@@ -570,10 +642,24 @@ public class Maven3ServerEmbedderImpl extends MavenRemoteObject implements Maven
|
||||
|
||||
MavenModel model = null;
|
||||
try {
|
||||
model = MavenModelConverter
|
||||
.convertModel(mavenProject.getModel(), mavenProject.getCompileSourceRoots(), mavenProject.getTestCompileSourceRoots(),
|
||||
mavenProject.getArtifacts(), (rootNode == null ? Collections.emptyList() : rootNode.getChildren()),
|
||||
mavenProject.getExtensionArtifacts(), getLocalRepositoryFile());
|
||||
if (USE_MVN2_COMPATIBLE_DEPENDENCY_RESOLVING) {
|
||||
//noinspection unchecked
|
||||
final List<DependencyNode> dependencyNodes = rootNode == null ? Collections.emptyList() : rootNode.getChildren();
|
||||
model = MavenModelConverter.convertModel(
|
||||
mavenProject.getModel(), mavenProject.getCompileSourceRoots(), mavenProject.getTestCompileSourceRoots(),
|
||||
mavenProject.getArtifacts(), dependencyNodes, mavenProject.getExtensionArtifacts(), getLocalRepositoryFile());
|
||||
}
|
||||
else {
|
||||
final DependencyResolutionResult dependencyResolutionResult = result.getDependencyResolutionResult();
|
||||
final org.sonatype.aether.graph.DependencyNode dependencyGraph =
|
||||
dependencyResolutionResult != null ? dependencyResolutionResult.getDependencyGraph() : null;
|
||||
|
||||
final List<org.sonatype.aether.graph.DependencyNode> dependencyNodes =
|
||||
dependencyGraph != null ? dependencyGraph.getChildren() : Collections.<org.sonatype.aether.graph.DependencyNode>emptyList();
|
||||
model = AetherModelConverter.convertModelWithAetherDependencyTree(
|
||||
mavenProject.getModel(), mavenProject.getCompileSourceRoots(), mavenProject.getTestCompileSourceRoots(),
|
||||
mavenProject.getArtifacts(), dependencyNodes, mavenProject.getExtensionArtifacts(), getLocalRepositoryFile());
|
||||
}
|
||||
}
|
||||
catch (Exception e) {
|
||||
validate(mavenProject.getFile(), Collections.singleton(e), problems, null);
|
||||
|
||||
+4
-4
@@ -83,7 +83,7 @@ public class MavenModelConverter {
|
||||
return result;
|
||||
}
|
||||
|
||||
private static void convertBuild(MavenBuild result, Build build, List<String> sources, List<String> testSources) {
|
||||
public static void convertBuild(MavenBuild result, Build build, List<String> sources, List<String> testSources) {
|
||||
convertBuildBase(result, build);
|
||||
result.setOutputDirectory(build.getOutputDirectory());
|
||||
result.setTestOutputDirectory(build.getTestOutputDirectory());
|
||||
@@ -122,7 +122,7 @@ public class MavenModelConverter {
|
||||
return patterns == null ? Collections.<String>emptyList() : patterns;
|
||||
}
|
||||
|
||||
private static List<MavenRemoteRepository> convertRepositories(List<Repository> repositories) {
|
||||
public static List<MavenRemoteRepository> convertRepositories(List<Repository> repositories) {
|
||||
if (repositories == null) return new ArrayList<MavenRemoteRepository>();
|
||||
|
||||
List<MavenRemoteRepository> result = new ArrayList<MavenRemoteRepository>(repositories.size());
|
||||
@@ -191,7 +191,7 @@ public class MavenModelConverter {
|
||||
return result;
|
||||
}
|
||||
|
||||
private static MavenArtifact convertArtifact(Artifact artifact, Map<Artifact, MavenArtifact> nativeToConvertedMap, File localRepository) {
|
||||
public static MavenArtifact convertArtifact(Artifact artifact, Map<Artifact, MavenArtifact> nativeToConvertedMap, File localRepository) {
|
||||
MavenArtifact result = nativeToConvertedMap.get(artifact);
|
||||
if (result == null) {
|
||||
result = convertArtifact(artifact, localRepository);
|
||||
@@ -228,7 +228,7 @@ public class MavenModelConverter {
|
||||
return result;
|
||||
}
|
||||
|
||||
private static List<MavenPlugin> convertPlugins(Model mavenModel) throws RemoteException {
|
||||
public static List<MavenPlugin> convertPlugins(Model mavenModel) throws RemoteException {
|
||||
List<MavenPlugin> result = new ArrayList<MavenPlugin>();
|
||||
Build build = mavenModel.getBuild();
|
||||
|
||||
|
||||
+21
-1
@@ -15,18 +15,32 @@
|
||||
*/
|
||||
package org.jetbrains.idea.maven.server.embedder;
|
||||
|
||||
import org.apache.maven.project.DependencyResolutionResult;
|
||||
import org.apache.maven.project.MavenProject;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
public class MavenExecutionResult {
|
||||
private final MavenProject myMavenProject;
|
||||
private final List<Exception> myExceptions;
|
||||
private final DependencyResolutionResult myDependencyResolutionResult;
|
||||
|
||||
public MavenExecutionResult(@Nullable MavenProject mavenProject, List<Exception> exceptions) {
|
||||
this(mavenProject, null, exceptions);
|
||||
}
|
||||
|
||||
public MavenExecutionResult(@Nullable MavenProject mavenProject,
|
||||
@Nullable DependencyResolutionResult dependencyResolutionResult,
|
||||
List<Exception> exceptions) {
|
||||
myMavenProject = mavenProject;
|
||||
myExceptions = exceptions;
|
||||
myExceptions = exceptions == null ? new ArrayList<Exception>() : exceptions;
|
||||
myDependencyResolutionResult = dependencyResolutionResult;
|
||||
if(myDependencyResolutionResult != null && myDependencyResolutionResult.getCollectionErrors() != null) {
|
||||
myExceptions.addAll(myDependencyResolutionResult.getCollectionErrors());
|
||||
}
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@@ -34,6 +48,12 @@ public class MavenExecutionResult {
|
||||
return myMavenProject;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
public DependencyResolutionResult getDependencyResolutionResult() {
|
||||
return myDependencyResolutionResult;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public List<Exception> getExceptions() {
|
||||
return myExceptions;
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user