![JAR search and dependency download from the Maven repository](/logo.png)
org.apache.maven.cling.invoker.LookupInvoker Maven / Gradle / Ivy
Show all versions of maven-cli Show documentation
/*
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements. See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership. The ASF licenses this file
* to you 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.apache.maven.cling.invoker;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.io.PrintWriter;
import java.nio.file.Files;
import java.nio.file.Path;
import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;
import java.util.Locale;
import java.util.Map;
import java.util.Properties;
import java.util.function.Consumer;
import java.util.function.Function;
import org.apache.maven.api.Constants;
import org.apache.maven.api.ProtoSession;
import org.apache.maven.api.cli.Invoker;
import org.apache.maven.api.cli.InvokerException;
import org.apache.maven.api.cli.InvokerRequest;
import org.apache.maven.api.cli.Logger;
import org.apache.maven.api.cli.Options;
import org.apache.maven.api.services.BuilderProblem;
import org.apache.maven.api.services.Interpolator;
import org.apache.maven.api.services.Lookup;
import org.apache.maven.api.services.MavenException;
import org.apache.maven.api.services.MessageBuilder;
import org.apache.maven.api.services.SettingsBuilder;
import org.apache.maven.api.services.SettingsBuilderRequest;
import org.apache.maven.api.services.SettingsBuilderResult;
import org.apache.maven.api.services.Source;
import org.apache.maven.api.settings.Mirror;
import org.apache.maven.api.settings.Profile;
import org.apache.maven.api.settings.Proxy;
import org.apache.maven.api.settings.Repository;
import org.apache.maven.api.settings.Server;
import org.apache.maven.api.settings.Settings;
import org.apache.maven.api.spi.PropertyContributor;
import org.apache.maven.artifact.InvalidRepositoryException;
import org.apache.maven.artifact.repository.ArtifactRepository;
import org.apache.maven.artifact.repository.ArtifactRepositoryPolicy;
import org.apache.maven.artifact.repository.MavenArtifactRepository;
import org.apache.maven.artifact.repository.layout.DefaultRepositoryLayout;
import org.apache.maven.bridge.MavenRepositorySystem;
import org.apache.maven.cling.invoker.spi.PropertyContributorsHolder;
import org.apache.maven.cling.logging.Slf4jConfiguration;
import org.apache.maven.cling.logging.Slf4jConfigurationFactory;
import org.apache.maven.cling.utils.CLIReportingUtils;
import org.apache.maven.execution.MavenExecutionRequest;
import org.apache.maven.internal.impl.SettingsUtilsV4;
import org.apache.maven.jline.FastTerminal;
import org.apache.maven.jline.MessageUtils;
import org.apache.maven.logging.BuildEventListener;
import org.apache.maven.logging.LoggingOutputStream;
import org.apache.maven.logging.ProjectBuildLogAppender;
import org.apache.maven.logging.SimpleBuildEventListener;
import org.apache.maven.logging.api.LogLevelRecorder;
import org.apache.maven.slf4j.MavenSimpleLogger;
import org.jline.terminal.Terminal;
import org.jline.terminal.TerminalBuilder;
import org.jline.terminal.impl.AbstractPosixTerminal;
import org.jline.terminal.spi.TerminalExt;
import org.slf4j.LoggerFactory;
import org.slf4j.spi.LocationAwareLogger;
import static java.util.Objects.requireNonNull;
import static org.apache.maven.cling.invoker.Utils.toMavenExecutionRequestLoggingLevel;
import static org.apache.maven.cling.invoker.Utils.toProperties;
/**
* Lookup invoker implementation, that boots up DI container.
*
* @param The context type.
*/
public abstract class LookupInvoker implements Invoker {
protected final ProtoLookup protoLookup;
public LookupInvoker(ProtoLookup protoLookup) {
this.protoLookup = requireNonNull(protoLookup);
}
@Override
public int invoke(InvokerRequest invokerRequest) throws InvokerException {
requireNonNull(invokerRequest);
Properties oldProps = (Properties) System.getProperties().clone();
ClassLoader oldCL = Thread.currentThread().getContextClassLoader();
try (C context = createContext(invokerRequest)) {
try {
if (context.containerCapsule != null
&& context.containerCapsule.currentThreadClassLoader().isPresent()) {
Thread.currentThread()
.setContextClassLoader(context.containerCapsule
.currentThreadClassLoader()
.get());
}
return doInvoke(context);
} catch (InvokerException.ExitException e) {
return e.getExitCode();
} catch (Exception e) {
throw handleException(context, e);
}
} finally {
Thread.currentThread().setContextClassLoader(oldCL);
System.setProperties(oldProps);
}
}
protected int doInvoke(C context) throws Exception {
pushCoreProperties(context);
pushUserProperties(context);
validate(context);
prepare(context);
configureLogging(context);
createTerminal(context);
activateLogging(context);
helpOrVersionAndMayExit(context);
preCommands(context);
container(context);
postContainer(context);
pushUserProperties(context); // after PropertyContributor SPI
lookup(context);
init(context);
postCommands(context);
settings(context);
return execute(context);
}
protected InvokerException handleException(C context, Exception e) throws InvokerException {
boolean showStackTrace = context.invokerRequest.options().showErrors().orElse(false);
if (showStackTrace) {
context.logger.error(
"Error executing " + context.invokerRequest.parserRequest().commandName() + ".", e);
} else {
context.logger.error(
"Error executing " + context.invokerRequest.parserRequest().commandName() + ".");
context.logger.error(e.getMessage());
for (Throwable cause = e.getCause(); cause != null && cause != cause.getCause(); cause = cause.getCause()) {
context.logger.error("Caused by: " + cause.getMessage());
}
}
return new InvokerException(e.getMessage(), e);
}
protected abstract C createContext(InvokerRequest invokerRequest) throws InvokerException;
protected void pushCoreProperties(C context) throws Exception {
System.setProperty(
Constants.MAVEN_HOME,
context.invokerRequest.installationDirectory().toString());
}
/**
* Note: this method is called twice from {@link #doInvoke(LookupContext)} and modifies context. First invocation
* when {@link LookupContext#pushedUserProperties} is null will push user properties IF key does not already
* exist among Java System Properties, and collects all they key it pushes. Second invocation happens AFTER
* {@link PropertyContributor} SPI invocation, and "refreshes" already pushed user properties by re-writing them
* as SPI may have modified them.
*/
protected void pushUserProperties(C context) throws Exception {
ProtoSession protoSession = context.protoSession;
HashSet sys = new HashSet<>(protoSession.getSystemProperties().keySet());
if (context.pushedUserProperties == null) {
context.pushedUserProperties = new HashSet<>();
protoSession.getUserProperties().entrySet().stream()
.filter(k -> !sys.contains(k.getKey()))
.peek(k -> context.pushedUserProperties.add(k.getKey()))
.forEach(k -> System.setProperty(k.getKey(), k.getValue()));
} else {
protoSession.getUserProperties().entrySet().stream()
.filter(k -> context.pushedUserProperties.contains(k.getKey()) || !sys.contains(k.getKey()))
.forEach(k -> System.setProperty(k.getKey(), k.getValue()));
}
}
protected void validate(C context) throws Exception {}
protected void prepare(C context) throws Exception {}
protected void configureLogging(C context) throws Exception {
// LOG COLOR
Options mavenOptions = context.invokerRequest.options();
Map userProperties = context.protoSession.getUserProperties();
String styleColor = mavenOptions
.color()
.orElse(userProperties.getOrDefault(
Constants.MAVEN_STYLE_COLOR_PROPERTY, userProperties.getOrDefault("style.color", "auto")));
if ("always".equals(styleColor) || "yes".equals(styleColor) || "force".equals(styleColor)) {
context.coloredOutput = true;
} else if ("never".equals(styleColor) || "no".equals(styleColor) || "none".equals(styleColor)) {
context.coloredOutput = false;
} else if (!"auto".equals(styleColor) && !"tty".equals(styleColor) && !"if-tty".equals(styleColor)) {
throw new IllegalArgumentException(
"Invalid color configuration value '" + styleColor + "'. Supported are 'auto', 'always', 'never'.");
} else {
boolean isBatchMode = !mavenOptions.forceInteractive().orElse(false)
&& mavenOptions.nonInteractive().orElse(false);
if (isBatchMode || mavenOptions.logFile().isPresent()) {
context.coloredOutput = false;
}
}
context.loggerFactory = LoggerFactory.getILoggerFactory();
context.slf4jConfiguration = Slf4jConfigurationFactory.getConfiguration(context.loggerFactory);
context.loggerLevel = Slf4jConfiguration.Level.INFO;
if (mavenOptions.verbose().orElse(false)) {
context.loggerLevel = Slf4jConfiguration.Level.DEBUG;
} else if (mavenOptions.quiet().orElse(false)) {
context.loggerLevel = Slf4jConfiguration.Level.ERROR;
}
context.slf4jConfiguration.setRootLoggerLevel(context.loggerLevel);
// else fall back to default log level specified in conf
// see https://issues.apache.org/jira/browse/MNG-2570
// Create the build log appender; also sets MavenSimpleLogger sink
ProjectBuildLogAppender projectBuildLogAppender =
new ProjectBuildLogAppender(determineBuildEventListener(context));
context.closeables.add(projectBuildLogAppender);
}
protected BuildEventListener determineBuildEventListener(C context) {
if (context.buildEventListener == null) {
context.buildEventListener = doDetermineBuildEventListener(context);
}
return context.buildEventListener;
}
protected BuildEventListener doDetermineBuildEventListener(C context) {
Consumer writer = determineWriter(context);
return new SimpleBuildEventListener(writer);
}
protected void createTerminal(C context) {
MessageUtils.systemInstall(
builder -> {
builder.streams(
context.invokerRequest.in().orElse(null),
context.invokerRequest.out().orElse(null));
builder.systemOutput(TerminalBuilder.SystemOutput.ForcedSysOut);
// The exec builder suffers from https://github.com/jline/jline3/issues/1098
// We could re-enable it when fixed to provide support for non-standard architectures,
// for which JLine does not provide any native library.
builder.exec(false);
if (context.coloredOutput != null) {
builder.color(context.coloredOutput);
}
},
terminal -> doConfigureWithTerminal(context, terminal));
context.terminal = MessageUtils.getTerminal();
// JLine is quite slow to start due to the native library unpacking and loading
// so boot it asynchronously
context.closeables.add(MessageUtils::systemUninstall);
MessageUtils.registerShutdownHook(); // safety belt
if (context.coloredOutput != null) {
MessageUtils.setColorEnabled(context.coloredOutput);
}
}
protected void doConfigureWithTerminal(C context, Terminal terminal) {
Options options = context.invokerRequest.options();
if (options.rawStreams().isEmpty() || !options.rawStreams().get()) {
MavenSimpleLogger stdout = (MavenSimpleLogger) context.loggerFactory.getLogger("stdout");
MavenSimpleLogger stderr = (MavenSimpleLogger) context.loggerFactory.getLogger("stderr");
stdout.setLogLevel(LocationAwareLogger.INFO_INT);
stderr.setLogLevel(LocationAwareLogger.INFO_INT);
System.setOut(new LoggingOutputStream(s -> stdout.info("[stdout] " + s)).printStream());
System.setErr(new LoggingOutputStream(s -> stderr.warn("[stderr] " + s)).printStream());
// no need to set them back, this is already handled by MessageUtils.systemUninstall() above
}
}
protected Consumer determineWriter(C context) {
if (context.writer == null) {
context.writer = doDetermineWriter(context);
}
return context.writer;
}
protected Consumer doDetermineWriter(C context) {
Options options = context.invokerRequest.options();
if (options.logFile().isPresent()) {
Path logFile = context.cwdResolver.apply(options.logFile().get());
try {
PrintWriter printWriter = new PrintWriter(Files.newBufferedWriter(logFile), true);
context.closeables.add(printWriter);
return printWriter::println;
} catch (IOException e) {
throw new MavenException("Unable to redirect logging to " + logFile, e);
}
} else {
// Given the terminal creation has been offloaded to a different thread,
// do not pass directly the terminal writer
return msg -> {
PrintWriter pw = context.terminal.writer();
pw.println(msg);
pw.flush();
};
}
}
protected void activateLogging(C context) throws Exception {
InvokerRequest invokerRequest = context.invokerRequest;
Options mavenOptions = invokerRequest.options();
context.slf4jConfiguration.activate();
org.slf4j.Logger l = context.loggerFactory.getLogger(this.getClass().getName());
context.logger = (level, message, error) -> l.atLevel(org.slf4j.event.Level.valueOf(level.name()))
.setCause(error)
.log(message);
if (mavenOptions.failOnSeverity().isPresent()) {
String logLevelThreshold = mavenOptions.failOnSeverity().get();
if (context.loggerFactory instanceof LogLevelRecorder recorder) {
LogLevelRecorder.Level level =
switch (logLevelThreshold.toLowerCase(Locale.ENGLISH)) {
case "warn", "warning" -> LogLevelRecorder.Level.WARN;
case "error" -> LogLevelRecorder.Level.ERROR;
default -> throw new IllegalArgumentException(
logLevelThreshold
+ " is not a valid log severity threshold. Valid severities are WARN/WARNING and ERROR.");
};
recorder.setMaxLevelAllowed(level);
context.logger.info("Enabled to break the build on log level " + logLevelThreshold + ".");
} else {
context.logger.warn("Expected LoggerFactory to be of type '" + LogLevelRecorder.class.getName()
+ "', but found '"
+ context.loggerFactory.getClass().getName() + "' instead. "
+ "The --fail-on-severity flag will not take effect.");
}
}
}
protected void helpOrVersionAndMayExit(C context) throws Exception {
InvokerRequest invokerRequest = context.invokerRequest;
if (invokerRequest.options().help().isPresent()) {
Consumer writer = determineWriter(context);
invokerRequest.options().displayHelp(context.invokerRequest.parserRequest(), writer);
throw new InvokerException.ExitException(0);
}
if (invokerRequest.options().showVersionAndExit().isPresent()) {
showVersion(context);
throw new InvokerException.ExitException(0);
}
}
protected void showVersion(C context) {
Consumer writer = determineWriter(context);
InvokerRequest invokerRequest = context.invokerRequest;
if (invokerRequest.options().quiet().orElse(false)) {
writer.accept(CLIReportingUtils.showVersionMinimal());
} else if (invokerRequest.options().verbose().orElse(false)) {
writer.accept(CLIReportingUtils.showVersion(
ProcessHandle.current().info().commandLine().orElse(null), describe(context.terminal)));
} else {
writer.accept(CLIReportingUtils.showVersion());
}
}
protected String describe(Terminal terminal) {
if (terminal == null) {
return null;
}
if (terminal instanceof FastTerminal ft) {
terminal = ft.getTerminal();
}
List subs = new ArrayList<>();
subs.add("type=" + terminal.getType());
if (terminal instanceof TerminalExt te) {
subs.add("provider=" + te.getProvider().name());
}
if (terminal instanceof AbstractPosixTerminal pt) {
subs.add("pty=" + pt.getPty().getClass().getName());
}
return terminal.getClass().getSimpleName() + " (" + String.join(", ", subs) + ")";
}
protected void preCommands(C context) throws Exception {
Options mavenOptions = context.invokerRequest.options();
boolean verbose = mavenOptions.verbose().orElse(false);
boolean version = mavenOptions.showVersion().orElse(false);
if (verbose || version) {
showVersion(context);
}
}
protected void container(C context) throws Exception {
context.containerCapsule = createContainerCapsuleFactory().createContainerCapsule(this, context);
context.closeables.add(context::closeContainer);
context.lookup = context.containerCapsule.getLookup();
// refresh logger in case container got customized by spy
org.slf4j.Logger l = context.loggerFactory.getLogger(this.getClass().getName());
context.logger = (level, message, error) -> l.atLevel(org.slf4j.event.Level.valueOf(level.name()))
.setCause(error)
.log(message);
}
protected ContainerCapsuleFactory createContainerCapsuleFactory() {
return new PlexusContainerCapsuleFactory<>();
}
protected void postContainer(C context) throws Exception {
ProtoSession protoSession = context.protoSession;
for (PropertyContributor propertyContributor : context.lookup
.lookup(PropertyContributorsHolder.class)
.getPropertyContributors()
.values()) {
protoSession = protoSession.toBuilder()
.withUserProperties(propertyContributor.contribute(protoSession))
.build();
}
context.protoSession = protoSession;
}
protected void lookup(C context) throws Exception {}
protected void init(C context) throws Exception {}
protected void postCommands(C context) throws Exception {
InvokerRequest invokerRequest = context.invokerRequest;
Logger logger = context.logger;
if (invokerRequest.options().showErrors().orElse(false)) {
logger.info("Error stacktraces are turned on.");
}
if (context.invokerRequest.options().verbose().orElse(false)) {
logger.debug("Message scheme: " + (MessageUtils.isColorEnabled() ? "color" : "plain"));
if (MessageUtils.isColorEnabled()) {
MessageBuilder buff = MessageUtils.builder();
buff.a("Message styles: ");
buff.trace("trace").a(' ');
buff.debug("debug").a(' ');
buff.info("info").a(' ');
buff.warning("warning").a(' ');
buff.error("error").a(' ');
buff.success("success").a(' ');
buff.failure("failure").a(' ');
buff.strong("strong").a(' ');
buff.mojo("mojo").a(' ');
buff.project("project");
logger.debug(buff.toString());
}
}
}
protected void settings(C context) throws Exception {
settings(context, true, context.lookup.lookup(SettingsBuilder.class));
}
/**
* This method is invoked twice during "normal" LookupInvoker level startup: once when (if present) extensions
* are loaded up during Plexus DI creation, and once afterward as "normal" boot procedure.
*
* If there are Maven3 passwords presents in settings, this results in doubled warnings emitted. So Plexus DI
* creation call keeps "emitSettingsWarnings" false. If there are fatal issues, it will anyway "die" at that
* spot before warnings would be emitted.
*/
protected void settings(C context, boolean emitSettingsWarnings, SettingsBuilder settingsBuilder) throws Exception {
Options mavenOptions = context.invokerRequest.options();
Path userSettingsFile = null;
if (mavenOptions.altUserSettings().isPresent()) {
userSettingsFile =
context.cwdResolver.apply(mavenOptions.altUserSettings().get());
if (!Files.isRegularFile(userSettingsFile)) {
throw new FileNotFoundException("The specified user settings file does not exist: " + userSettingsFile);
}
} else {
String userSettingsFileStr =
context.protoSession.getUserProperties().get(Constants.MAVEN_USER_SETTINGS);
if (userSettingsFileStr != null) {
userSettingsFile = context.userResolver.apply(userSettingsFileStr);
}
}
Path projectSettingsFile = null;
if (mavenOptions.altProjectSettings().isPresent()) {
projectSettingsFile =
context.cwdResolver.apply(mavenOptions.altProjectSettings().get());
if (!Files.isRegularFile(projectSettingsFile)) {
throw new FileNotFoundException(
"The specified project settings file does not exist: " + projectSettingsFile);
}
} else {
String projectSettingsFileStr =
context.protoSession.getUserProperties().get(Constants.MAVEN_PROJECT_SETTINGS);
if (projectSettingsFileStr != null) {
projectSettingsFile = context.cwdResolver.apply(projectSettingsFileStr);
}
}
Path installationSettingsFile = null;
if (mavenOptions.altInstallationSettings().isPresent()) {
installationSettingsFile = context.cwdResolver.apply(
mavenOptions.altInstallationSettings().get());
if (!Files.isRegularFile(installationSettingsFile)) {
throw new FileNotFoundException(
"The specified installation settings file does not exist: " + installationSettingsFile);
}
} else {
String installationSettingsFileStr =
context.protoSession.getUserProperties().get(Constants.MAVEN_INSTALLATION_SETTINGS);
if (installationSettingsFileStr != null) {
installationSettingsFile = context.installationResolver.apply(installationSettingsFileStr);
}
}
context.installationSettingsPath = installationSettingsFile;
context.projectSettingsPath = projectSettingsFile;
context.userSettingsPath = userSettingsFile;
Function interpolationSource = Interpolator.chain(
context.protoSession.getUserProperties()::get, context.protoSession.getSystemProperties()::get);
SettingsBuilderRequest settingsRequest = SettingsBuilderRequest.builder()
.session(context.protoSession)
.installationSettingsSource(
installationSettingsFile != null && Files.exists(installationSettingsFile)
? Source.fromPath(installationSettingsFile)
: null)
.projectSettingsSource(
projectSettingsFile != null && Files.exists(projectSettingsFile)
? Source.fromPath(projectSettingsFile)
: null)
.userSettingsSource(
userSettingsFile != null && Files.exists(userSettingsFile)
? Source.fromPath(userSettingsFile)
: null)
.interpolationSource(interpolationSource)
.build();
customizeSettingsRequest(context, settingsRequest);
context.logger.debug("Reading installation settings from '" + installationSettingsFile + "'");
context.logger.debug("Reading project settings from '" + projectSettingsFile + "'");
context.logger.debug("Reading user settings from '" + userSettingsFile + "'");
SettingsBuilderResult settingsResult = settingsBuilder.build(settingsRequest);
customizeSettingsResult(context, settingsResult);
context.effectiveSettings = settingsResult.getEffectiveSettings();
context.interactive = mayDisableInteractiveMode(context, context.effectiveSettings.isInteractiveMode());
context.localRepositoryPath = localRepositoryPath(context);
if (emitSettingsWarnings && !settingsResult.getProblems().isEmpty()) {
context.logger.info("");
context.logger.info(
"Some problems were encountered while building the effective settings (use -X to see details)");
if (context.invokerRequest.options().verbose().orElse(false)) {
for (BuilderProblem problem : settingsResult.getProblems()) {
context.logger.warn(problem.getMessage() + " @ " + problem.getLocation());
}
}
context.logger.info("");
}
}
protected void customizeSettingsRequest(C context, SettingsBuilderRequest settingsBuilderRequest)
throws Exception {}
protected void customizeSettingsResult(C context, SettingsBuilderResult settingsBuilderResult) throws Exception {}
protected boolean mayDisableInteractiveMode(C context, boolean proposedInteractive) {
if (!context.invokerRequest.options().forceInteractive().orElse(false)) {
if (context.invokerRequest.options().nonInteractive().orElse(false)) {
return false;
} else {
boolean runningOnCI = isRunningOnCI(context);
if (runningOnCI) {
context.logger.info(
"Making this build non-interactive, because the environment variable CI equals \"true\"."
+ " Disable this detection by removing that variable or adding --force-interactive.");
return false;
}
}
}
return proposedInteractive;
}
protected Path localRepositoryPath(C context) {
// user override
String userDefinedLocalRepo = context.protoSession.getUserProperties().get(Constants.MAVEN_REPO_LOCAL);
if (userDefinedLocalRepo == null) {
userDefinedLocalRepo = context.protoSession.getUserProperties().get(Constants.MAVEN_REPO_LOCAL);
if (userDefinedLocalRepo != null) {
context.logger.warn("The property '" + Constants.MAVEN_REPO_LOCAL
+ "' has been set using a JVM system property which is deprecated. "
+ "The property can be passed as a Maven argument or in the Maven project configuration file,"
+ "usually located at ${session.rootDirectory}/.mvn/maven.properties.");
}
}
if (userDefinedLocalRepo != null) {
return context.cwdResolver.apply(userDefinedLocalRepo);
}
// settings
userDefinedLocalRepo = context.effectiveSettings.getLocalRepository();
if (userDefinedLocalRepo != null && !userDefinedLocalRepo.isEmpty()) {
return context.userResolver.apply(userDefinedLocalRepo);
}
// defaults
return context.userResolver
.apply(context.protoSession.getUserProperties().get(Constants.MAVEN_USER_CONF))
.resolve("repository");
}
protected void populateRequest(C context, Lookup lookup, MavenExecutionRequest request) throws Exception {
populateRequestFromSettings(request, context.effectiveSettings);
Options options = context.invokerRequest.options();
request.setLoggingLevel(toMavenExecutionRequestLoggingLevel(context.loggerLevel));
request.setLocalRepositoryPath(context.localRepositoryPath.toFile());
request.setLocalRepository(createLocalArtifactRepository(context.localRepositoryPath));
request.setInteractiveMode(context.interactive);
request.setShowErrors(options.showErrors().orElse(false));
request.setBaseDirectory(context.invokerRequest.topDirectory().toFile());
request.setSystemProperties(toProperties(context.protoSession.getSystemProperties()));
request.setUserProperties(toProperties(context.protoSession.getUserProperties()));
request.setInstallationSettingsFile(
context.installationSettingsPath != null ? context.installationSettingsPath.toFile() : null);
request.setProjectSettingsFile(
context.projectSettingsPath != null ? context.projectSettingsPath.toFile() : null);
request.setUserSettingsFile(context.userSettingsPath != null ? context.userSettingsPath.toFile() : null);
request.setTopDirectory(context.invokerRequest.topDirectory());
if (context.invokerRequest.rootDirectory().isPresent()) {
request.setMultiModuleProjectDirectory(
context.invokerRequest.rootDirectory().get().toFile());
request.setRootDirectory(context.invokerRequest.rootDirectory().get());
}
request.addPluginGroup("org.apache.maven.plugins");
request.addPluginGroup("org.codehaus.mojo");
}
/**
* TODO: get rid of this!!!
*/
@Deprecated
private ArtifactRepository createLocalArtifactRepository(Path baseDirectory) {
DefaultRepositoryLayout layout = new DefaultRepositoryLayout();
ArtifactRepositoryPolicy blah = new ArtifactRepositoryPolicy(
true, ArtifactRepositoryPolicy.UPDATE_POLICY_ALWAYS, ArtifactRepositoryPolicy.CHECKSUM_POLICY_IGNORE);
return new MavenArtifactRepository(
"local", "file://" + baseDirectory.toUri().getRawPath(), layout, blah, blah);
}
protected void populateRequestFromSettings(MavenExecutionRequest request, Settings settings) throws Exception {
if (settings == null) {
return;
}
request.setOffline(settings.isOffline());
request.setInteractiveMode(settings.isInteractiveMode());
request.setPluginGroups(settings.getPluginGroups());
request.setLocalRepositoryPath(settings.getLocalRepository());
for (Server server : settings.getServers()) {
request.addServer(new org.apache.maven.settings.Server(server));
}
//
//
// true
// http
// proxy.somewhere.com
// 8080
// proxyuser
// somepassword
// www.google.com|*.somewhere.com
//
//
for (Proxy proxy : settings.getProxies()) {
if (!proxy.isActive()) {
continue;
}
request.addProxy(new org.apache.maven.settings.Proxy(proxy));
}
//
//
// nexus
// *
// http://repository.sonatype.org/content/groups/public
//
//
for (Mirror mirror : settings.getMirrors()) {
request.addMirror(new org.apache.maven.settings.Mirror(mirror));
}
for (Repository remoteRepository : settings.getRepositories()) {
try {
request.addRemoteRepository(MavenRepositorySystem.buildArtifactRepository(
new org.apache.maven.settings.Repository(remoteRepository)));
} catch (InvalidRepositoryException e) {
// do nothing for now
}
}
for (Repository pluginRepository : settings.getPluginRepositories()) {
try {
request.addPluginArtifactRepository(MavenRepositorySystem.buildArtifactRepository(
new org.apache.maven.settings.Repository(pluginRepository)));
} catch (InvalidRepositoryException e) {
// do nothing for now
}
}
request.setActiveProfiles(settings.getActiveProfiles());
for (Profile rawProfile : settings.getProfiles()) {
request.addProfile(
new org.apache.maven.model.Profile(SettingsUtilsV4.convertFromSettingsProfile(rawProfile)));
if (settings.getActiveProfiles().contains(rawProfile.getId())) {
List remoteRepositories = rawProfile.getRepositories();
for (Repository remoteRepository : remoteRepositories) {
try {
request.addRemoteRepository(MavenRepositorySystem.buildArtifactRepository(
new org.apache.maven.settings.Repository(remoteRepository)));
} catch (InvalidRepositoryException e) {
// do nothing for now
}
}
List pluginRepositories = rawProfile.getPluginRepositories();
for (Repository pluginRepository : pluginRepositories) {
try {
request.addPluginArtifactRepository(MavenRepositorySystem.buildArtifactRepository(
new org.apache.maven.settings.Repository(pluginRepository)));
} catch (InvalidRepositoryException e) {
// do nothing for now
}
}
}
}
}
protected int calculateDegreeOfConcurrency(String threadConfiguration) {
try {
if (threadConfiguration.endsWith("C")) {
String str = threadConfiguration.substring(0, threadConfiguration.length() - 1);
float coreMultiplier = Float.parseFloat(str);
if (coreMultiplier <= 0.0f) {
throw new IllegalArgumentException("Invalid threads core multiplier value: '" + threadConfiguration
+ "'. Value must be positive.");
}
int procs = Runtime.getRuntime().availableProcessors();
int threads = (int) (coreMultiplier * procs);
return threads == 0 ? 1 : threads;
} else {
int threads = Integer.parseInt(threadConfiguration);
if (threads <= 0) {
throw new IllegalArgumentException(
"Invalid threads value: '" + threadConfiguration + "'. Value must be positive.");
}
return threads;
}
} catch (NumberFormatException e) {
throw new IllegalArgumentException("Invalid threads value: '" + threadConfiguration
+ "'. Supported are int and float values ending with C.");
}
}
protected boolean isRunningOnCI(C context) {
String ciEnv = context.protoSession.getSystemProperties().get("env.CI");
return ciEnv != null && !"false".equals(ciEnv);
}
protected abstract int execute(C context) throws Exception;
}