View Javadoc
1   package org.apache.maven.shared.dependency.graph.internal;
2   
3   /*
4    * Licensed to the Apache Software Foundation (ASF) under one
5    * or more contributor license agreements.  See the NOTICE file
6    * distributed with this work for additional information
7    * regarding copyright ownership.  The ASF licenses this file
8    * to you under the Apache License, Version 2.0 (the
9    * "License"); you may not use this file except in compliance
10   * with the License.  You may obtain a copy of the License at
11   *
12   *  http://www.apache.org/licenses/LICENSE-2.0
13   *
14   * Unless required by applicable law or agreed to in writing,
15   * software distributed under the License is distributed on an
16   * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
17   * KIND, either express or implied.  See the License for the
18   * specific language governing permissions and limitations
19   * under the License.
20   */
21  
22  import org.apache.maven.artifact.resolver.filter.ArtifactFilter;
23  import org.apache.maven.project.MavenProject;
24  import org.apache.maven.shared.dependency.graph.DependencyGraphBuilder;
25  import org.apache.maven.shared.dependency.graph.DependencyGraphBuilderException;
26  import org.apache.maven.shared.dependency.graph.DependencyNode;
27  import org.codehaus.plexus.PlexusConstants;
28  import org.codehaus.plexus.PlexusContainer;
29  import org.codehaus.plexus.component.annotations.Component;
30  import org.codehaus.plexus.component.repository.exception.ComponentLookupException;
31  import org.codehaus.plexus.context.Context;
32  import org.codehaus.plexus.context.ContextException;
33  import org.codehaus.plexus.logging.AbstractLogEnabled;
34  import org.codehaus.plexus.personality.plexus.lifecycle.phase.Contextualizable;
35  
36  import java.util.Collection;
37  import java.util.Collections;
38  
39  /**
40   * Default dependency graph builder that detects current Maven version to delegate to either Maven 2 or Maven 3 specific
41   * code.
42   *
43   * @see Maven2DependencyGraphBuilder
44   * @see Maven3DependencyGraphBuilder
45   * @author Hervé Boutemy
46   * @since 2.0
47   */
48  @Component( role = DependencyGraphBuilder.class )
49  public class DefaultDependencyGraphBuilder
50      extends AbstractLogEnabled
51      implements DependencyGraphBuilder, Contextualizable
52  {
53      protected PlexusContainer container;
54  
55      /**
56       * Builds a dependency graph.
57       *
58       * @param project the project
59       * @param filter artifact filter (can be <code>null</code>)
60       * @return DependencyNode containing the dependency graph.
61       * @throws DependencyGraphBuilderException if some of the dependencies could not be resolved.
62       */
63      public DependencyNode buildDependencyGraph( MavenProject project, ArtifactFilter filter )
64          throws DependencyGraphBuilderException
65      {
66          return buildDependencyGraph( project, filter, null );
67      }
68  
69      /**
70       * Builds a dependency graph.
71       *
72       * @param project the project
73       * @param filter artifact filter (can be <code>null</code>)
74       * @param reactorProjects Collection of those projects contained in the reactor (can be <code>null</code>)
75       * @return DependencyNode containing the dependency graph.
76       * @throws DependencyGraphBuilderException if some of the dependencies could not be resolved.
77       */
78      public DependencyNode buildDependencyGraph( MavenProject project, ArtifactFilter filter,
79                                                  Collection<MavenProject> reactorProjects )
80          throws DependencyGraphBuilderException
81      {
82          try
83          {
84              String hint = isMaven31() ? "maven31" : isMaven2x() ? "maven2" : "maven3";
85  
86              DependencyGraphBuilder effectiveGraphBuilder =
87                  (DependencyGraphBuilder) container.lookup( DependencyGraphBuilder.class.getCanonicalName(), hint );
88              getLogger().debug( "building " + hint + " dependency graph for " + project.getId() + " with "
89                                     + effectiveGraphBuilder.getClass().getSimpleName() );
90  
91              return effectiveGraphBuilder.buildDependencyGraph( project, filter, reactorProjects );
92          }
93          catch ( ComponentLookupException e )
94          {
95              throw new DependencyGraphBuilderException( e.getMessage(), e );
96          }
97      }
98  
99      /**
100      * @return true if the current Maven is Maven 2.x.
101      */
102     protected static boolean isMaven2x()
103     {
104         return !canFindCoreClass( "org.apache.maven.project.DependencyResolutionRequest" ); // Maven 3 specific
105     }
106 
107     /**
108      * @return true if the current Maven version is Maven 3.1.
109      */
110     protected static boolean isMaven31()
111     {
112         return canFindCoreClass( "org.eclipse.aether.artifact.Artifact" ); // Maven 3.1 specific
113     }
114 
115     private static boolean canFindCoreClass( String className )
116     {
117         try
118         {
119             Thread.currentThread().getContextClassLoader().loadClass( className );
120 
121             return true;
122         }
123         catch ( ClassNotFoundException e )
124         {
125             return false;
126         }
127     }
128 
129     /**
130      * Injects the Plexus content.
131      *
132      * @param context   Plexus context to inject.
133      * @throws ContextException if the PlexusContainer could not be located.
134      */
135     public void contextualize( Context context )
136         throws ContextException
137     {
138         container = (PlexusContainer) context.get( PlexusConstants.PLEXUS_KEY );
139     }
140 }