View Javadoc
1   /*
2    * Licensed to the Apache Software Foundation (ASF) under one
3    * or more contributor license agreements.  See the NOTICE file
4    * distributed with this work for additional information
5    * regarding copyright ownership.  The ASF licenses this file
6    * to you under the Apache License, Version 2.0 (the
7    * "License"); you may not use this file except in compliance
8    * with the License.  You may obtain a copy of the License at
9    *
10   *   http://www.apache.org/licenses/LICENSE-2.0
11   *
12   * Unless required by applicable law or agreed to in writing,
13   * software distributed under the License is distributed on an
14   * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
15   * KIND, either express or implied.  See the License for the
16   * specific language governing permissions and limitations
17   * under the License.
18   */
19  package org.eclipse.aether.util.graph.visitor;
20  
21  import java.io.File;
22  import java.nio.file.Path;
23  import java.util.ArrayList;
24  import java.util.List;
25  import java.util.Objects;
26  import java.util.function.Consumer;
27  
28  import org.eclipse.aether.artifact.Artifact;
29  import org.eclipse.aether.graph.Dependency;
30  import org.eclipse.aether.graph.DependencyNode;
31  
32  import static java.util.stream.Collectors.joining;
33  import static java.util.stream.Collectors.toList;
34  
35  /**
36   * Node list generator usable with different traversing strategies. It is wrapped {@link List}{@code <DependencyNode>} but
37   * offers several transformations, that are handy.
38   *
39   * @since 2.0.0
40   *
41   * @see PreorderDependencyNodeConsumerVisitor
42   * @see PostorderDependencyNodeConsumerVisitor
43   * @see LevelOrderDependencyNodeConsumerVisitor
44   */
45  public final class NodeListGenerator implements Consumer<DependencyNode> {
46  
47      private final ArrayList<DependencyNode> nodes;
48  
49      public NodeListGenerator() {
50          nodes = new ArrayList<>(128);
51      }
52  
53      @Override
54      public void accept(DependencyNode dependencyNode) {
55          nodes.add(dependencyNode);
56      }
57  
58      /**
59       * Gets the list of dependency nodes that was generated during the graph traversal.
60       *
61       * @return The list of dependency nodes, never {@code null}.
62       */
63      public List<DependencyNode> getNodes() {
64          return nodes;
65      }
66  
67      /**
68       * Gets the list of dependency nodes that was generated during the graph traversal and have {@code non-null}
69       * {@link DependencyNode#getDependency()}.
70       *
71       * @return The list of dependency nodes having dependency, never {@code null}.
72       */
73      public List<DependencyNode> getNodesWithDependencies() {
74          return getNodesWithDependencies(getNodes());
75      }
76  
77      /**
78       * Gets the dependencies seen during the graph traversal.
79       *
80       * @param includeUnresolved Whether unresolved dependencies shall be included in the result or not.
81       * @return The list of dependencies, never {@code null}.
82       */
83      public List<Dependency> getDependencies(boolean includeUnresolved) {
84          return getDependencies(getNodes(), includeUnresolved);
85      }
86  
87      /**
88       * Gets the artifacts associated with the list of dependency nodes generated during the graph traversal.
89       *
90       * @param includeUnresolved Whether unresolved artifacts shall be included in the result or not.
91       * @return The list of artifacts, never {@code null}.
92       */
93      public List<Artifact> getArtifacts(boolean includeUnresolved) {
94          return getArtifacts(getNodes(), includeUnresolved);
95      }
96  
97      /**
98       * Gets the files of resolved artifacts seen during the graph traversal.
99       *
100      * @return The list of artifact files, never {@code null}.
101      * @deprecated Use {@link #getPaths()} instead.
102      */
103     @Deprecated
104     public List<File> getFiles() {
105         return getFiles(getNodes());
106     }
107 
108     /**
109      * Gets the files of resolved artifacts seen during the graph traversal.
110      *
111      * @return The list of artifact files, never {@code null}.
112      * @since 2.0.0
113      */
114     public List<Path> getPaths() {
115         return getPaths(getNodes());
116     }
117 
118     /**
119      * Gets a class path by concatenating the artifact files of the visited dependency nodes. Nodes with unresolved
120      * artifacts are automatically skipped.
121      *
122      * @return The class path, using the platform-specific path separator, never {@code null}.
123      */
124     public String getClassPath() {
125         return getClassPath(getNodes());
126     }
127 
128     static List<DependencyNode> getNodesWithDependencies(List<DependencyNode> nodes) {
129         return nodes.stream().filter(d -> d.getDependency() != null).collect(toList());
130     }
131 
132     static List<Dependency> getDependencies(List<DependencyNode> nodes, boolean includeUnresolved) {
133         return getNodesWithDependencies(nodes).stream()
134                 .map(DependencyNode::getDependency)
135                 .filter(d -> includeUnresolved || d.getArtifact().getPath() != null)
136                 .collect(toList());
137     }
138 
139     static List<Artifact> getArtifacts(List<DependencyNode> nodes, boolean includeUnresolved) {
140         return getNodesWithDependencies(nodes).stream()
141                 .map(d -> d.getDependency().getArtifact())
142                 .filter(artifact -> includeUnresolved || artifact.getPath() != null)
143                 .collect(toList());
144     }
145 
146     @Deprecated
147     static List<File> getFiles(List<DependencyNode> nodes) {
148         return getNodesWithDependencies(nodes).stream()
149                 .map(d -> d.getDependency().getArtifact().getFile())
150                 .filter(Objects::nonNull)
151                 .collect(toList());
152     }
153 
154     static List<Path> getPaths(List<DependencyNode> nodes) {
155         return getNodesWithDependencies(nodes).stream()
156                 .map(d -> d.getDependency().getArtifact().getPath())
157                 .filter(Objects::nonNull)
158                 .collect(toList());
159     }
160 
161     static String getClassPath(List<DependencyNode> nodes) {
162         return getPaths(nodes).stream()
163                 .map(Path::toAbsolutePath)
164                 .map(Path::toString)
165                 .collect(joining(File.pathSeparator));
166     }
167 }