Skip to content

Commit

Permalink
Non daemon option, fixes apache#43
Browse files Browse the repository at this point in the history
  • Loading branch information
gnodet committed Nov 10, 2020
1 parent 3fc5069 commit 00befb9
Show file tree
Hide file tree
Showing 7 changed files with 294 additions and 211 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -27,8 +27,10 @@
import java.util.List;
import java.util.Map;
import java.util.Optional;
import java.util.Properties;
import java.util.UUID;
import java.util.concurrent.TimeUnit;
import java.util.concurrent.atomic.AtomicReference;
import java.util.stream.Collectors;
import org.jboss.fuse.mvnd.common.BuildProperties;
import org.jboss.fuse.mvnd.common.DaemonCompatibilitySpec;
Expand Down Expand Up @@ -84,6 +86,10 @@ public DaemonClientConnection maybeConnect(DaemonInfo daemon) {
}

public DaemonClientConnection connect(ClientOutput output) {
if (parameters.noDaemon()) {
return connectNoDaemon();
}

final DaemonCompatibilitySpec constraint = new DaemonCompatibilitySpec(
parameters.javaHome(), parameters.getDaemonOpts());
output.accept(Message.buildStatus("Looking up daemon..."));
Expand All @@ -110,6 +116,49 @@ public DaemonClientConnection connect(ClientOutput output) {
return startDaemon();
}

private DaemonClientConnection connectNoDaemon() {
if (Environment.isNative()) {
throw new UnsupportedOperationException(
"The " + Environment.MVND_NO_DAEMON.getProperty() + " property is not supported in native mode.");
}
String daemon = ProcessHandle.current().pid() + "-" + System.currentTimeMillis();
Properties properties = new Properties();
properties.put(Environment.JAVA_HOME.getProperty(), parameters.javaHome().toString());
properties.put(Environment.USER_DIR.getProperty(), parameters.userDir().toString());
properties.put(Environment.USER_HOME.getProperty(), parameters.userHome().toString());
properties.put(Environment.MVND_HOME.getProperty(), parameters.mvndHome().toString());
properties.put(Environment.DAEMON_UID.getProperty(), daemon);
properties.put(Environment.MVND_DAEMON_STORAGE.getProperty(), parameters.daemonStorage().toString());
properties.put(Environment.DAEMON_REGISTRY.getProperty(), parameters.registry().toString());
properties.putAll(parameters.getDaemonOptsMap());
Environment.setProperties(properties);
AtomicReference<Throwable> throwable = new AtomicReference<>();
Thread serverThread = new Thread(() -> {
try {
Class<?> clazz = getClass().getClassLoader().loadClass("org.jboss.fuse.mvnd.daemon.Server");
try (AutoCloseable server = (AutoCloseable) clazz.getConstructor().newInstance()) {
((Runnable) server).run();
}
} catch (Throwable t) {
throwable.set(t);
}
});
serverThread.start();
long start = System.currentTimeMillis();
do {
DaemonClientConnection daemonConnection = connectToDaemonWithId(daemon, true);
if (daemonConnection != null) {
return daemonConnection;
}
try {
sleep(50L);
} catch (InterruptedException e) {
throw new DaemonException.InterruptedException(e);
}
} while (serverThread.isAlive() && System.currentTimeMillis() - start < DEFAULT_CONNECT_TIMEOUT);
throw new RuntimeException("Unable to connect to internal daemon", throwable.get());
}

private String handleStopEvents(Collection<DaemonInfo> idleDaemons, Collection<DaemonInfo> busyDaemons) {
final List<DaemonStopEvent> stopEvents = registry.getStopEvents();

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -73,6 +73,13 @@ public List<String> getDaemonOpts() {
.collect(Collectors.toList());
}

public Map<String, String> getDaemonOptsMap() {
return Arrays.stream(Environment.values())
.filter(Environment::isDiscriminating)
.collect(Collectors.toMap(Environment::getProperty,
v -> property(v).orFail().asString()));
}

public List<String> getDaemonCommandLineProperties() {
return Arrays.stream(Environment.values())
.filter(Environment::isDiscriminating)
Expand Down Expand Up @@ -239,6 +246,17 @@ public Path mavenRepoLocal() {
return property(Environment.MAVEN_REPO_LOCAL).asPath();
}

/**
* @return <code>true</code> if maven should be executed within this process instead of spawning a daemon.
*/
public boolean noDaemon() {
return value(Environment.MVND_NO_DAEMON)
.orSystemProperty()
.orEnvironmentVariable()
.orDefault()
.asBoolean();
}

/**
* @param newUserDir where to change the current directory to
* @return a new {@link DaemonParameters} with {@code userDir} set to the given {@code newUserDir}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -51,6 +51,7 @@ public String asCommandLineProperty(String value) {
* The path to the daemon registry
*/
DAEMON_REGISTRY("daemon.registry", null, null, false),
MVND_NO_DAEMON("mvnd.noDaemon", "MVND_NO_DAEMON", "false", true),
DAEMON_DEBUG("daemon.debug", null, false, true),
DAEMON_IDLE_TIMEOUT_MS("daemon.idleTimeoutMs", null, TimeUnit.HOURS.toMillis(3), true),
DAEMON_KEEP_ALIVE_MS("daemon.keepAliveMs", null, TimeUnit.SECONDS.toMillis(1), true),
Expand Down
26 changes: 19 additions & 7 deletions daemon/src/main/java/org/jboss/fuse/mvnd/daemon/Server.java
Original file line number Diff line number Diff line change
Expand Up @@ -74,6 +74,7 @@ public class Server implements AutoCloseable, Runnable {
public static final int CANCEL_TIMEOUT = 10 * 1000;

private final String uid;
private final boolean noDaemon;
private final ServerSocketChannel socket;
private final DaemonMavenCli cli;
private volatile DaemonInfo info;
Expand All @@ -88,6 +89,7 @@ public class Server implements AutoCloseable, Runnable {

public Server() throws IOException {
this.uid = Environment.DAEMON_UID.asString();
this.noDaemon = Environment.MVND_NO_DAEMON.asBoolean();
try {
cli = new DaemonMavenCli();
registry = new DaemonRegistry(Environment.DAEMON_REGISTRY.asPath());
Expand Down Expand Up @@ -138,8 +140,10 @@ public void close() {
try {
socket.close();
} finally {
clearCache("sun.net.www.protocol.jar.JarFileFactory", "urlCache");
clearCache("sun.net.www.protocol.jar.JarFileFactory", "fileCache");
if (!noDaemon) {
clearCache("sun.net.www.protocol.jar.JarFileFactory", "urlCache");
clearCache("sun.net.www.protocol.jar.JarFileFactory", "fileCache");
}
}
}
}
Expand Down Expand Up @@ -167,8 +171,14 @@ public void run() {
executor.scheduleAtFixedRate(this::expirationCheck,
expirationCheckDelayMs, expirationCheckDelayMs, TimeUnit.MILLISECONDS);
LOGGER.info("Daemon started");
new DaemonThread(this::accept).start();
awaitStop();
if (noDaemon) {
try (SocketChannel socket = this.socket.accept()) {
client(socket);
}
} else {
new DaemonThread(this::accept).start();
awaitStop();
}
} catch (Throwable t) {
LOGGER.error("Error running daemon loop", t);
} finally {
Expand Down Expand Up @@ -518,9 +528,11 @@ public <T extends Message> T request(Message request, Class<T> responseType, Pre
} catch (Throwable t) {
LOGGER.error("Error while building project", t);
} finally {
LOGGER.info("Daemon back to idle");
updateState(DaemonState.Idle);
System.gc();
if (!noDaemon) {
LOGGER.info("Daemon back to idle");
updateState(DaemonState.Idle);
System.gc();
}
}
}

Expand Down
206 changes: 206 additions & 0 deletions dist/src/main/distro/bin/mvnd.cmd
Original file line number Diff line number Diff line change
@@ -0,0 +1,206 @@
@REM Licensed to the Apache Software Foundation (ASF) under one
@REM or more contributor license agreements. See the NOTICE file
@REM distributed with this work for additional information
@REM regarding copyright ownership. The ASF licenses this file
@REM to you under the Apache License, Version 2.0 (the
@REM "License"); you may not use this file except in compliance
@REM with the License. You may obtain a copy of the License at
@REM
@REM http://www.apache.org/licenses/LICENSE-2.0
@REM
@REM Unless required by applicable law or agreed to in writing,
@REM software distributed under the License is distributed on an
@REM "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
@REM KIND, either express or implied. See the License for the
@REM specific language governing permissions and limitations
@REM under the License.

@REM -----------------------------------------------------------------------------
@REM Apache Maven Startup Script
@REM
@REM Environment Variable Prerequisites
@REM
@REM JAVA_HOME Must point at your Java Development Kit installation.
@REM MAVEN_BATCH_ECHO (Optional) Set to 'on' to enable the echoing of the batch commands.
@REM MAVEN_BATCH_PAUSE (Optional) set to 'on' to wait for a key stroke before ending.
@REM MAVEN_OPTS (Optional) Java runtime options used when Maven is executed.
@REM MAVEN_SKIP_RC (Optional) Flag to disable loading of mavenrc files.
@REM -----------------------------------------------------------------------------

@REM Begin all REM lines with '@' in case MAVEN_BATCH_ECHO is 'on'
@echo off
@REM enable echoing my setting MAVEN_BATCH_ECHO to 'on'
@if "%MAVEN_BATCH_ECHO%"=="on" echo %MAVEN_BATCH_ECHO%

@REM Execute a user defined script before this one
if not "%MAVEN_SKIP_RC%"=="" goto skipRcPre
@REM check for pre script, once with legacy .bat ending and once with .cmd ending
if exist "%USERPROFILE%\mavenrc_pre.bat" call "%USERPROFILE%\mavenrc_pre.bat"
if exist "%USERPROFILE%\mavenrc_pre.cmd" call "%USERPROFILE%\mavenrc_pre.cmd"
:skipRcPre

@setlocal

set ERROR_CODE=0

@REM ==== START VALIDATION ====
if not "%JAVA_HOME%"=="" goto OkJHome
for %%i in (java.exe) do set "JAVACMD=%%~$PATH:i"
goto checkJCmd

:OkJHome
set "JAVACMD=%JAVA_HOME%\bin\java.exe"

:checkJCmd
if exist "%JAVACMD%" goto chkMHome

echo The JAVA_HOME environment variable is not defined correctly >&2
echo This environment variable is needed to run this program >&2
echo NB: JAVA_HOME should point to a JDK not a JRE >&2
goto error

:chkMHome
set "MVND_HOME=%~dp0.."
if not "%MVND_HOME%"=="" goto stripMHome
goto error

:stripMHome
if not "_%MVND_HOME:~-1%"=="_\" goto checkMCmd
set "MVND_HOME=%MVND_HOME:~0,-1%"
goto stripMHome

:checkMCmd
if exist "%MVND_HOME%\bin\mvnd.cmd" goto init
goto error
@REM ==== END VALIDATION ====

:init

set MAVEN_CMD_LINE_ARGS=%*

@REM Find the project basedir, i.e., the directory that contains the folder ".mvn".
@REM Fallback to current working directory if not found.

set "MAVEN_PROJECTBASEDIR=%MAVEN_BASEDIR%"
if not "%MAVEN_PROJECTBASEDIR%"=="" goto endDetectBaseDir

set "EXEC_DIR=%CD%"
set "WDIR=%EXEC_DIR%"

@REM Look for the --file switch and start the search for the .mvn directory from the specified
@REM POM location, if supplied.

set FILE_ARG=
:arg_loop
if "%~1" == "-f" (
set "FILE_ARG=%~2"
shift
goto process_file_arg
)
if "%~1" == "--file" (
set "FILE_ARG=%~2"
shift
goto process_file_arg
)
@REM If none of the above, skip the argument
shift
if not "%~1" == "" (
goto arg_loop
) else (
goto findBaseDir
)

:process_file_arg
if "%FILE_ARG%" == "" (
goto findBaseDir
)
if not exist "%FILE_ARG%" (
echo POM file "%FILE_ARG%" specified the -f/--file command-line argument does not exist >&2
goto error
)
if exist "%FILE_ARG%\*" (
set "POM_DIR=%FILE_ARG%"
) else (
call :get_directory_from_file "%FILE_ARG%"
)
if not exist "%POM_DIR%" (
echo Directory "%POM_DIR%" extracted from the -f/--file command-line argument "%FILE_ARG%" does not exist >&2
goto error
)
set "WDIR=%POM_DIR%"
goto findBaseDir

:get_directory_from_file
set "POM_DIR=%~dp1"
:stripPomDir
if not "_%POM_DIR:~-1%"=="_\" goto pomDirStripped
set "POM_DIR=%POM_DIR:~0,-1%"
goto stripPomDir
:pomDirStripped
exit /b

:findBaseDir
cd /d "%WDIR%"
:findBaseDirLoop
if exist "%WDIR%\.mvn" goto baseDirFound
cd ..
IF "%WDIR%"=="%CD%" goto baseDirNotFound
set "WDIR=%CD%"
goto findBaseDirLoop

:baseDirFound
set "MAVEN_PROJECTBASEDIR=%WDIR%"
cd /d "%EXEC_DIR%"
goto endDetectBaseDir

:baseDirNotFound
if "_%EXEC_DIR:~-1%"=="_\" set "EXEC_DIR=%EXEC_DIR:~0,-1%"
set "MAVEN_PROJECTBASEDIR=%EXEC_DIR%"
cd "%EXEC_DIR%"

:endDetectBaseDir

set "jvmConfig=\.mvn\jvm.config"
if not exist "%MAVEN_PROJECTBASEDIR%%jvmConfig%" goto endReadAdditionalConfig

@setlocal EnableExtensions EnableDelayedExpansion
for /F "usebackq delims=" %%a in ("%MAVEN_PROJECTBASEDIR%\.mvn\jvm.config") do set JVM_CONFIG_MAVEN_PROPS=!JVM_CONFIG_MAVEN_PROPS! %%a
@endlocal & set JVM_CONFIG_MAVEN_PROPS=%JVM_CONFIG_MAVEN_PROPS%

:endReadAdditionalConfig

for %%i in ("%MVND_HOME%"\boot\*.jar "%MVND_HOME%"\lib\ext\*.jar "%MVND_HOME%"\lib\*.jar) do set DAEMON_JAR="%%i"
set DAEMON_LAUNCHER=org.jboss.fuse.mvnd.client.DefaultClient

"%JAVACMD%" ^
%JVM_CONFIG_MAVEN_PROPS% ^
%MAVEN_OPTS% ^
%MAVEN_DEBUG_OPTS% ^
-classpath %DAEMON_JAR% ^
"-Dlogback.configurationFile=%MVND_HOME%\conf\logging\logback.xml" ^
"-Dmvnd.home=%MAVEN_HOME%" ^
"-Dmaven.home=%MAVEN_HOME%" ^
"-Dlibrary.jansi.path=%MAVEN_HOME%\lib\jansi-native" ^
"-Dmaven.multiModuleProjectDirectory=%MAVEN_PROJECTBASEDIR%" ^
%DAEMON_LAUNCHER% %MAVEN_CMD_LINE_ARGS%
if ERRORLEVEL 1 goto error
goto end

:error
set ERROR_CODE=1

:end
@endlocal & set ERROR_CODE=%ERROR_CODE%

if not "%MAVEN_SKIP_RC%"=="" goto skipRcPost
@REM check for post script, once with legacy .bat ending and once with .cmd ending
if exist "%USERPROFILE%\mavenrc_post.bat" call "%USERPROFILE%\mavenrc_post.bat"
if exist "%USERPROFILE%\mavenrc_post.cmd" call "%USERPROFILE%\mavenrc_post.cmd"
:skipRcPost

@REM pause the script if MAVEN_BATCH_PAUSE is set to 'on'
if "%MAVEN_BATCH_PAUSE%"=="on" pause

if "%MAVEN_TERMINATE_CMD%"=="on" exit %ERROR_CODE%

cmd /C exit /B %ERROR_CODE%
2 changes: 1 addition & 1 deletion dist/src/main/distro/bin/mvnd.sh
Original file line number Diff line number Diff line change
Expand Up @@ -102,7 +102,7 @@ if [ ! -x "$JAVACMD" ] ; then
exit 1
fi

DAEMON_JAR=`echo "${MVND_HOME}"/mvn/lib/ext/*.jar "${MVND_HOME}"/mvn/lib/*.jar`
DAEMON_JAR=`echo "${MVND_HOME}"/mvn/boot/*.jar "${MVND_HOME}"/mvn/lib/ext/*.jar "${MVND_HOME}"/mvn/lib/*.jar`
DAEMON_JAR=$(echo $DAEMON_JAR | sed -e 's/ /:/g')
DAEMON_LAUNCHER=org.jboss.fuse.mvnd.client.DefaultClient

Expand Down

0 comments on commit 00befb9

Please sign in to comment.