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.apache.maven.api; 20 21 import java.nio.file.Path; 22 import java.util.List; 23 import java.util.Optional; 24 25 import org.apache.maven.api.annotations.Experimental; 26 import org.apache.maven.api.annotations.Nonnull; 27 import org.apache.maven.api.model.Build; 28 import org.apache.maven.api.model.Model; 29 import org.apache.maven.api.model.Profile; 30 31 /** 32 * Interface representing a Maven project which can be created using the 33 * {@link org.apache.maven.api.services.ProjectBuilder ProjectBuilder} service. 34 * Such objects are immutable and plugin that wish to modify such objects 35 * need to do so using the {@link org.apache.maven.api.services.ProjectManager 36 * ProjectManager} service. 37 * <p> 38 * Projects are created using the {@code ProjectBuilder} from a POM file 39 * (usually named {@code pom.xml}) on the file system. 40 * The {@link #getPomPath()} will point to the POM file and the 41 * {@link #getBasedir()} to the directory parent containing the 42 * POM file. 43 * </p> 44 * 45 * @since 4.0.0 46 * @see org.apache.maven.api.services.ProjectManager 47 * @see org.apache.maven.api.services.ProjectBuilder 48 */ 49 @Experimental 50 public interface Project { 51 52 /** 53 * {@return the project groupId}. 54 */ 55 @Nonnull 56 String getGroupId(); 57 58 /** 59 * {@return the project artifactId}. 60 */ 61 @Nonnull 62 String getArtifactId(); 63 64 /** 65 * {@return the project version}. 66 */ 67 @Nonnull 68 String getVersion(); 69 70 /** 71 * {@return the project packaging}. 72 * <p> 73 * Note: unlike in legacy code, logical checks against string representing packaging (returned by this method) 74 * are NOT recommended (code like {@code "pom".equals(project.getPackaging)} must be avoided). Use method 75 * {@link #getArtifacts()} to gain access to POM or build artifact. 76 * 77 * @see #getArtifacts() 78 */ 79 @Nonnull 80 Packaging getPackaging(); 81 82 /** 83 * {@return the project language}. It is by default determined by {@link #getPackaging()}. 84 * 85 * @see #getPackaging() 86 */ 87 @Nonnull 88 default Language getLanguage() { 89 return getPackaging().language(); 90 } 91 92 /** 93 * {@return the project POM artifact}, which is the artifact of the POM of this project. Every project have a POM 94 * artifact, even if the existence of backing POM file is NOT a requirement (i.e. for some transient projects). 95 * 96 * @see org.apache.maven.api.services.ArtifactManager#getPath(Artifact) 97 */ 98 @Nonnull 99 default ProducedArtifact getPomArtifact() { 100 return getArtifacts().get(0); 101 } 102 103 /** 104 * {@return the project main artifact}, which is the artifact produced by this project build, if applicable. 105 * This artifact MAY be absent if the project is actually not producing any main artifact (i.e. "pom" packaging). 106 * 107 * @see #getPackaging() 108 * @see org.apache.maven.api.services.ArtifactManager#getPath(Artifact) 109 */ 110 @Nonnull 111 default Optional<ProducedArtifact> getMainArtifact() { 112 List<ProducedArtifact> artifacts = getArtifacts(); 113 return artifacts.size() == 2 ? Optional.of(artifacts.get(1)) : Optional.empty(); 114 } 115 116 /** 117 * {@return the project artifacts as immutable list}. Elements are the project POM artifact and the artifact 118 * produced by this project build, if applicable. Hence, the returned list may have one or two elements 119 * (never less than 1, never more than 2), depending on project packaging. 120 * <p> 121 * The list's first element is ALWAYS the project POM artifact. Presence of second element in the list depends 122 * solely on the project packaging. 123 * 124 * @see #getPackaging() 125 * @see #getPomArtifact() 126 * @see #getMainArtifact() 127 * @see org.apache.maven.api.services.ArtifactManager#getPath(Artifact) 128 */ 129 @Nonnull 130 List<ProducedArtifact> getArtifacts(); 131 132 /** 133 * {@return the project model}. 134 */ 135 @Nonnull 136 Model getModel(); 137 138 /** 139 * Shorthand method. 140 * 141 * @return the build element of the project model 142 */ 143 @Nonnull 144 default Build getBuild() { 145 Build build = getModel().getBuild(); 146 return build != null ? build : Build.newInstance(); 147 } 148 149 /** 150 * Returns the path to the pom file for this project. 151 * A project is usually read from a file named {@code pom.xml}, 152 * which contains the {@linkplain #getModel() model} in an XML form. 153 * When a custom {@code org.apache.maven.api.spi.ModelParser} is used, 154 * the path may point to a non XML file. 155 * <p> 156 * The POM path is also used to define the {@linkplain #getBasedir() base directory} 157 * of the project. 158 * 159 * @return the path of the pom 160 * @see #getBasedir() 161 */ 162 @Nonnull 163 Path getPomPath(); 164 165 /** 166 * Returns the project base directory, i.e. the directory containing the project. 167 * A project is usually read from the file system and this will point to 168 * the directory containing the POM file. 169 * 170 * @return the path of the directory containing the project 171 */ 172 @Nonnull 173 Path getBasedir(); 174 175 /** 176 * {@return the project direct dependencies (directly specified or inherited)}. 177 */ 178 @Nonnull 179 List<DependencyCoordinates> getDependencies(); 180 181 /** 182 * {@return the project managed dependencies (directly specified or inherited)}. 183 */ 184 @Nonnull 185 List<DependencyCoordinates> getManagedDependencies(); 186 187 /** 188 * {@return the project ID, usable as key}. 189 */ 190 @Nonnull 191 default String getId() { 192 return getModel().getId(); 193 } 194 195 /** 196 * Returns a boolean indicating if the project is the top level project for 197 * this reactor build. The top level project may be different from the 198 * {@code rootDirectory}, especially if a subtree of the project is being 199 * built, either because Maven has been launched in a subdirectory or using 200 * a {@code -f} option. 201 * 202 * @return {@code true} if the project is the top level project for this build 203 */ 204 boolean isTopProject(); 205 206 /** 207 * Returns a boolean indicating if the project is a root project, 208 * meaning that the {@link #getRootDirectory()} and {@link #getBasedir()} 209 * points to the same directory, and that either {@link Model#isRoot()} 210 * is {@code true} or that {@code basedir} contains a {@code .mvn} child 211 * directory. 212 * 213 * @return {@code true} if the project is the root project 214 * @see Model#isRoot() 215 */ 216 boolean isRootProject(); 217 218 /** 219 * Gets the root directory of the project, which is the parent directory 220 * containing the {@code .mvn} directory or flagged with {@code root="true"}. 221 * 222 * @return the root directory of the project 223 * @throws IllegalStateException if the root directory could not be found 224 * @see Session#getRootDirectory() 225 */ 226 @Nonnull 227 Path getRootDirectory(); 228 229 /** 230 * Returns project parent project, if any. 231 * <p> 232 * Note that the model may have a parent defined, but an empty parent 233 * project may be returned if the parent comes from a remote repository, 234 * as a {@code Project} must refer to a buildable project. 235 * 236 * @return an optional containing the parent project 237 * @see Model#getParent() 238 */ 239 @Nonnull 240 Optional<Project> getParent(); 241 242 /** 243 * Returns all profiles defined in this project. 244 * <p> 245 * This method returns only the profiles defined directly in the current project's POM 246 * and does not include profiles from parent projects. 247 * 248 * @return a non-null, possibly empty list of profiles defined in this project 249 * @see Profile 250 * @see #getEffectiveProfiles() 251 */ 252 @Nonnull 253 List<Profile> getDeclaredProfiles(); 254 255 /** 256 * Returns all profiles defined in this project and all of its parent projects. 257 * <p> 258 * This method traverses the parent hierarchy and includes profiles defined in parent POMs. 259 * The returned list contains profiles from the current project and all of its ancestors in 260 * the project inheritance chain. 261 * 262 * @return a non-null, possibly empty list of all profiles from this project and its parents 263 * @see Profile 264 * @see #getDeclaredProfiles() 265 */ 266 @Nonnull 267 List<Profile> getEffectiveProfiles(); 268 269 /** 270 * Returns all active profiles for the current project build. 271 * <p> 272 * Active profiles are those that have been explicitly activated through one of the following means: 273 * <ul> 274 * <li>Command line activation using the -P flag</li> 275 * <li>Maven settings activation in settings.xml via <activeProfiles></li> 276 * <li>Automatic activation via <activation> conditions</li> 277 * <li>The default active profile (marked with <activeByDefault>true</activeByDefault>)</li> 278 * </ul> 279 * <p> 280 * The active profiles control various aspects of the build configuration including but not 281 * limited to dependencies, plugins, properties, and build resources. 282 * 283 * @return a non-null, possibly empty list of active profiles for this project 284 * @see Profile 285 * @see #getEffectiveActiveProfiles() 286 */ 287 @Nonnull 288 List<Profile> getDeclaredActiveProfiles(); 289 290 /** 291 * Returns all active profiles for this project and all of its parent projects. 292 * <p> 293 * This method traverses the parent hierarchy and collects all active profiles from 294 * the current project and its ancestors. Active profiles are those that meet the 295 * activation criteria through explicit activation or automatic conditions. 296 * <p> 297 * The combined set of active profiles from the entire project hierarchy affects 298 * the effective build configuration. 299 * 300 * @return a non-null, possibly empty list of all active profiles from this project and its parents 301 * @see Profile 302 * @see #getDeclaredActiveProfiles() 303 */ 304 @Nonnull 305 List<Profile> getEffectiveActiveProfiles(); 306 }