Merge remote-tracking branch 'origin/jetty-9.4.x' into jetty-10.0.x
Signed-off-by: Greg Wilkins <gregw@webtide.com>
This commit is contained in:
commit
1c3b816031
|
@ -1,19 +1,19 @@
|
||||||
//
|
//
|
||||||
// ========================================================================
|
// ========================================================================
|
||||||
// Copyright (c) 1995-2020 Mort Bay Consulting Pty Ltd and others.
|
// Copyright (c) 1995-2020 Mort Bay Consulting Pty Ltd and others.
|
||||||
|
// ========================================================================
|
||||||
|
// All rights reserved. This program and the accompanying materials
|
||||||
|
// are made available under the terms of the Eclipse Public License v1.0
|
||||||
|
// and Apache License v2.0 which accompanies this distribution.
|
||||||
//
|
//
|
||||||
// This program and the accompanying materials are made available under
|
// The Eclipse Public License is available at
|
||||||
// the terms of the Eclipse Public License 2.0 which is available at
|
// http://www.eclipse.org/legal/epl-v10.html
|
||||||
// https://www.eclipse.org/legal/epl-2.0
|
|
||||||
//
|
//
|
||||||
// This Source Code may also be made available under the following
|
// The Apache License v2.0 is available at
|
||||||
// Secondary Licenses when the conditions for such availability set
|
// http://www.opensource.org/licenses/apache2.0.php
|
||||||
// forth in the Eclipse Public License, v. 2.0 are satisfied:
|
|
||||||
// the Apache License v2.0 which is available at
|
|
||||||
// https://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
//
|
//
|
||||||
// SPDX-License-Identifier: EPL-2.0 OR Apache-2.0
|
// You may elect to redistribute this code under either of these licenses.
|
||||||
// ========================================================================
|
// ========================================================================
|
||||||
//
|
//
|
||||||
|
|
||||||
[[start-jar]]
|
[[start-jar]]
|
||||||
|
@ -65,7 +65,7 @@ When executed `start.jar` performs the following actions:
|
||||||
3. Uses default behavior of `java.io.File` (Relative to `System.getProperty` ("user.dir") and then as absolute file system path).
|
3. Uses default behavior of `java.io.File` (Relative to `System.getProperty` ("user.dir") and then as absolute file system path).
|
||||||
* Loads any dependent modules (merges XXNK, library, and properties results with active command line).
|
* Loads any dependent modules (merges XXNK, library, and properties results with active command line).
|
||||||
* Builds out server classpath.
|
* Builds out server classpath.
|
||||||
* Determines run mode:
|
* Determines run mode as one of:
|
||||||
** Shows informational command line options and exit.
|
** Shows informational command line options and exit.
|
||||||
** Executes Jetty normally, waits for Jetty to stop.
|
** Executes Jetty normally, waits for Jetty to stop.
|
||||||
** Executes a forked JVM to run Jetty in, waits for forked JVM to exit.
|
** Executes a forked JVM to run Jetty in, waits for forked JVM to exit.
|
||||||
|
@ -89,9 +89,36 @@ Lists the resolved configuration that will start Jetty.
|
||||||
* Server classpath
|
* Server classpath
|
||||||
* Server XML configuration files
|
* Server XML configuration files
|
||||||
--dry-run::
|
--dry-run::
|
||||||
Prints the resolved command line that `start.jar` should use to start a forked instance of Jetty.
|
Print the command line that the start.jar generates, then exit. This may be used to generate command lines when the start.ini includes -X or -D arguments:
|
||||||
|
....
|
||||||
|
$ java -jar start.jar --dry-run > jetty.sh
|
||||||
|
$ . jetty.sh
|
||||||
|
....
|
||||||
|
--dry-run=<parts>::
|
||||||
|
Print specific parts of the command line. The parts are a comma separated list of:
|
||||||
|
|
||||||
|
* "java" - the JVM to run
|
||||||
|
* "opts" - the JVM options (eg -D and -X flags)
|
||||||
|
* "path" - the JVM class path or JPMS modules options
|
||||||
|
* "main" - the main class to run
|
||||||
|
* "args" - the arguments passed to the main class
|
||||||
|
|
||||||
|
It is possible to decompose the start command:
|
||||||
|
....
|
||||||
|
$ OPTS=$(java -jar start.jar --dry-run=opts,path)
|
||||||
|
$ MAIN=$(java -jar start.jar --dry-run=main)
|
||||||
|
$ ARGS=$(java -jar start.jar --dry-run=args)
|
||||||
|
$ java $OPTS -Dextra=opt $MAIN $ARGS extra=arg
|
||||||
|
....
|
||||||
|
Alternatively to create an args file for java:
|
||||||
|
....
|
||||||
|
$ java -jar start.jar --dry-run=opts,path,main,args > /tmp/args
|
||||||
|
$ java @/tmp/args
|
||||||
|
....
|
||||||
--exec::
|
--exec::
|
||||||
Starts a forked instance of Jetty.
|
Forces the start to use a forked instance of java to run Jetty.
|
||||||
|
Some modules include `--exec` in order to set java command line options.
|
||||||
|
Some start options, such as `--jpms` also imply `--exec`
|
||||||
--exec-properties=<filename>::
|
--exec-properties=<filename>::
|
||||||
Assign a fixed name to the file used to transfer properties to the sub process.
|
Assign a fixed name to the file used to transfer properties to the sub process.
|
||||||
This allows the generated properties file to be saved and reused.
|
This allows the generated properties file to be saved and reused.
|
||||||
|
@ -99,7 +126,7 @@ Without this option, a temporary file is used.
|
||||||
--commands=<filename>::
|
--commands=<filename>::
|
||||||
Instructs `start.jar` to use each line of the specified file as arguments on the command line.
|
Instructs `start.jar` to use each line of the specified file as arguments on the command line.
|
||||||
|
|
||||||
===== Debugg and Start Logging
|
===== Debug and Start Logging
|
||||||
|
|
||||||
--debug::
|
--debug::
|
||||||
Enables debugging output of the startup procedure.
|
Enables debugging output of the startup procedure.
|
||||||
|
@ -275,3 +302,25 @@ If you have a need for a shaded version of `start.jar` (such as for Gradle), you
|
||||||
<classifier>shaded</classifier>
|
<classifier>shaded</classifier>
|
||||||
</dependency>
|
</dependency>
|
||||||
....
|
....
|
||||||
|
|
||||||
|
==== Start.jar without exec or forking.
|
||||||
|
|
||||||
|
Some Jetty modules include the `--exec` option so that java command line options can be set.
|
||||||
|
Also some `start.jar` options (eg. `--jpms`) include an implicit `--exec`.
|
||||||
|
To start jetty without forking a new JVM instance from the start JVM, the `--dry-run` option can be used to generate a command line:
|
||||||
|
....
|
||||||
|
$ CMD=$(java -jar start.jar --dry-run)
|
||||||
|
$ $CMD
|
||||||
|
....
|
||||||
|
It is possible to decompose the start command so that it can be modified:
|
||||||
|
....
|
||||||
|
$ OPTS=$(java -jar start.jar --dry-run=opts,path)
|
||||||
|
$ MAIN=$(java -jar start.jar --dry-run=main)
|
||||||
|
$ ARGS=$(java -jar start.jar --dry-run=args)
|
||||||
|
$ java $OPTS -Dextra=opt $MAIN $ARGS extra=arg
|
||||||
|
....
|
||||||
|
Alternatively to create an args file for java:
|
||||||
|
....
|
||||||
|
$ java -jar start.jar --dry-run=opts,path,main,args > /tmp/args
|
||||||
|
$ java @/tmp/args
|
||||||
|
....
|
|
@ -206,7 +206,7 @@ public class Main
|
||||||
|
|
||||||
StartLog.debug("%s - %s", invokedClass, invokedClass.getPackage().getImplementationVersion());
|
StartLog.debug("%s - %s", invokedClass, invokedClass.getPackage().getImplementationVersion());
|
||||||
|
|
||||||
CommandLineBuilder cmd = args.getMainArgs(false);
|
CommandLineBuilder cmd = args.getMainArgs(StartArgs.ARG_PARTS);
|
||||||
String[] argArray = cmd.getArgs().toArray(new String[0]);
|
String[] argArray = cmd.getArgs().toArray(new String[0]);
|
||||||
StartLog.debug("Command Line Args: %s", cmd.toString());
|
StartLog.debug("Command Line Args: %s", cmd.toString());
|
||||||
|
|
||||||
|
@ -407,7 +407,7 @@ public class Main
|
||||||
// Show Command Line to execute Jetty
|
// Show Command Line to execute Jetty
|
||||||
if (args.isDryRun())
|
if (args.isDryRun())
|
||||||
{
|
{
|
||||||
CommandLineBuilder cmd = args.getMainArgs(true);
|
CommandLineBuilder cmd = args.getMainArgs(args.getDryRunParts());
|
||||||
System.out.println(cmd.toString(StartLog.isDebugEnabled() ? " \\\n" : " "));
|
System.out.println(cmd.toString(StartLog.isDebugEnabled() ? " \\\n" : " "));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -446,7 +446,7 @@ public class Main
|
||||||
// execute Jetty in another JVM
|
// execute Jetty in another JVM
|
||||||
if (args.isExec())
|
if (args.isExec())
|
||||||
{
|
{
|
||||||
CommandLineBuilder cmd = args.getMainArgs(true);
|
CommandLineBuilder cmd = args.getMainArgs(StartArgs.ALL_PARTS);
|
||||||
cmd.debug();
|
cmd.debug();
|
||||||
ProcessBuilder pbuilder = new ProcessBuilder(cmd.getArgs());
|
ProcessBuilder pbuilder = new ProcessBuilder(cmd.getArgs());
|
||||||
StartLog.endStartLog();
|
StartLog.endStartLog();
|
||||||
|
|
|
@ -57,6 +57,14 @@ import org.eclipse.jetty.util.ManifestUtils;
|
||||||
public class StartArgs
|
public class StartArgs
|
||||||
{
|
{
|
||||||
public static final String VERSION;
|
public static final String VERSION;
|
||||||
|
public static final Set<String> ALL_PARTS = Collections.unmodifiableSet(new HashSet<>(Arrays.asList(
|
||||||
|
"java",
|
||||||
|
"opts",
|
||||||
|
"path",
|
||||||
|
"main",
|
||||||
|
"args")));
|
||||||
|
public static final Set<String> ARG_PARTS = Collections.unmodifiableSet(new HashSet<>(Arrays.asList(
|
||||||
|
"args")));
|
||||||
|
|
||||||
static
|
static
|
||||||
{
|
{
|
||||||
|
@ -219,6 +227,7 @@ public class StartArgs
|
||||||
private boolean listConfig = false;
|
private boolean listConfig = false;
|
||||||
private boolean version = false;
|
private boolean version = false;
|
||||||
private boolean dryRun = false;
|
private boolean dryRun = false;
|
||||||
|
private final Set<String> dryRunParts = new HashSet<>();
|
||||||
private boolean jpms = false;
|
private boolean jpms = false;
|
||||||
private boolean createStartd = false;
|
private boolean createStartd = false;
|
||||||
private boolean updateIni = false;
|
private boolean updateIni = false;
|
||||||
|
@ -676,8 +685,11 @@ public class StartArgs
|
||||||
return jvmArgs;
|
return jvmArgs;
|
||||||
}
|
}
|
||||||
|
|
||||||
public CommandLineBuilder getMainArgs(boolean addJavaInit) throws IOException
|
public CommandLineBuilder getMainArgs(Set<String> parts) throws IOException
|
||||||
{
|
{
|
||||||
|
if (parts.isEmpty())
|
||||||
|
parts = ALL_PARTS;
|
||||||
|
|
||||||
CommandLineBuilder cmd = new CommandLineBuilder();
|
CommandLineBuilder cmd = new CommandLineBuilder();
|
||||||
|
|
||||||
// Special Stop/Shutdown properties
|
// Special Stop/Shutdown properties
|
||||||
|
@ -685,10 +697,11 @@ public class StartArgs
|
||||||
ensureSystemPropertySet("STOP.KEY");
|
ensureSystemPropertySet("STOP.KEY");
|
||||||
ensureSystemPropertySet("STOP.WAIT");
|
ensureSystemPropertySet("STOP.WAIT");
|
||||||
|
|
||||||
if (addJavaInit)
|
if (parts.contains("java"))
|
||||||
{
|
|
||||||
cmd.addRawArg(CommandLineBuilder.findJavaBin());
|
cmd.addRawArg(CommandLineBuilder.findJavaBin());
|
||||||
|
|
||||||
|
if (parts.contains("opts"))
|
||||||
|
{
|
||||||
cmd.addRawArg("-Djava.io.tmpdir=" + System.getProperty("java.io.tmpdir"));
|
cmd.addRawArg("-Djava.io.tmpdir=" + System.getProperty("java.io.tmpdir"));
|
||||||
cmd.addRawArg("-Djetty.home=" + baseHome.getHome());
|
cmd.addRawArg("-Djetty.home=" + baseHome.getHome());
|
||||||
cmd.addRawArg("-Djetty.base=" + baseHome.getBase());
|
cmd.addRawArg("-Djetty.base=" + baseHome.getBase());
|
||||||
|
@ -703,6 +716,7 @@ public class StartArgs
|
||||||
|
|
||||||
Prop p = processSystemProperty(key, value, null);
|
Prop p = processSystemProperty(key, value, null);
|
||||||
cmd.addRawArg("-D" + p.key + "=" + getProperties().expand(p.value));
|
cmd.addRawArg("-D" + p.key + "=" + getProperties().expand(p.value));
|
||||||
|
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
@ -716,7 +730,10 @@ public class StartArgs
|
||||||
String value = System.getProperty(propKey);
|
String value = System.getProperty(propKey);
|
||||||
cmd.addEqualsArg("-D" + propKey, value);
|
cmd.addEqualsArg("-D" + propKey, value);
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (parts.contains("path"))
|
||||||
|
{
|
||||||
if (isJPMS())
|
if (isJPMS())
|
||||||
{
|
{
|
||||||
Map<Boolean, List<File>> dirsAndFiles = StreamSupport.stream(classpath.spliterator(), false)
|
Map<Boolean, List<File>> dirsAndFiles = StreamSupport.stream(classpath.spliterator(), false)
|
||||||
|
@ -765,52 +782,58 @@ public class StartArgs
|
||||||
cmd.addRawArg("--add-reads");
|
cmd.addRawArg("--add-reads");
|
||||||
cmd.addRawArg(entry.getKey() + "=" + String.join(",", entry.getValue()));
|
cmd.addRawArg(entry.getKey() + "=" + String.join(",", entry.getValue()));
|
||||||
}
|
}
|
||||||
|
|
||||||
cmd.addRawArg("--module");
|
|
||||||
cmd.addRawArg(getMainClassname());
|
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
cmd.addRawArg("-cp");
|
cmd.addRawArg("-cp");
|
||||||
cmd.addRawArg(classpath.toString());
|
cmd.addRawArg(classpath.toString());
|
||||||
cmd.addRawArg(getMainClassname());
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (parts.contains("main"))
|
||||||
|
{
|
||||||
|
if (isJPMS())
|
||||||
|
cmd.addRawArg("--module");
|
||||||
|
cmd.addRawArg(getMainClassname());
|
||||||
|
}
|
||||||
|
|
||||||
// pass properties as args or as a file
|
// pass properties as args or as a file
|
||||||
if (dryRun && execProperties == null)
|
if (parts.contains("args"))
|
||||||
{
|
{
|
||||||
for (Prop p : properties)
|
if (dryRun && execProperties == null)
|
||||||
{
|
{
|
||||||
cmd.addRawArg(CommandLineBuilder.quote(p.key) + "=" + CommandLineBuilder.quote(p.value));
|
for (Prop p : properties)
|
||||||
|
{
|
||||||
|
cmd.addRawArg(CommandLineBuilder.quote(p.key) + "=" + CommandLineBuilder.quote(p.value));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
else if (properties.size() > 0)
|
||||||
else if (properties.size() > 0)
|
|
||||||
{
|
|
||||||
Path propPath;
|
|
||||||
if (execProperties == null)
|
|
||||||
{
|
{
|
||||||
propPath = Files.createTempFile("start_", ".properties");
|
Path propPath;
|
||||||
propPath.toFile().deleteOnExit();
|
if (execProperties == null)
|
||||||
}
|
{
|
||||||
else
|
propPath = Files.createTempFile("start_", ".properties");
|
||||||
propPath = new File(execProperties).toPath();
|
propPath.toFile().deleteOnExit();
|
||||||
|
}
|
||||||
|
else
|
||||||
|
propPath = new File(execProperties).toPath();
|
||||||
|
|
||||||
try (OutputStream out = Files.newOutputStream(propPath))
|
try (OutputStream out = Files.newOutputStream(propPath))
|
||||||
|
{
|
||||||
|
properties.store(out, "start.jar properties");
|
||||||
|
}
|
||||||
|
cmd.addRawArg(propPath.toAbsolutePath().toString());
|
||||||
|
}
|
||||||
|
|
||||||
|
for (Path xml : xmls)
|
||||||
{
|
{
|
||||||
properties.store(out, "start.jar properties");
|
cmd.addRawArg(xml.toAbsolutePath().toString());
|
||||||
}
|
}
|
||||||
cmd.addRawArg(propPath.toAbsolutePath().toString());
|
|
||||||
}
|
|
||||||
|
|
||||||
for (Path xml : xmls)
|
for (Path propertyFile : propertyFiles)
|
||||||
{
|
{
|
||||||
cmd.addRawArg(xml.toAbsolutePath().toString());
|
cmd.addRawArg(propertyFile.toAbsolutePath().toString());
|
||||||
}
|
}
|
||||||
|
|
||||||
for (Path propertyFile : propertyFiles)
|
|
||||||
{
|
|
||||||
cmd.addRawArg(propertyFile.toAbsolutePath().toString());
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return cmd;
|
return cmd;
|
||||||
|
@ -936,6 +959,11 @@ public class StartArgs
|
||||||
return dryRun;
|
return dryRun;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public Set<String> getDryRunParts()
|
||||||
|
{
|
||||||
|
return dryRunParts;
|
||||||
|
}
|
||||||
|
|
||||||
public boolean isExec()
|
public boolean isExec()
|
||||||
{
|
{
|
||||||
return exec;
|
return exec;
|
||||||
|
@ -1154,6 +1182,21 @@ public class StartArgs
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (arg.startsWith("--dry-run="))
|
||||||
|
{
|
||||||
|
int colon = arg.indexOf('=');
|
||||||
|
for (String part : arg.substring(colon + 1).split(","))
|
||||||
|
{
|
||||||
|
if (!ALL_PARTS.contains(part))
|
||||||
|
throw new UsageException(UsageException.ERR_BAD_ARG, "Unrecognized --dry-run=\"%s\" in %s", part, source);
|
||||||
|
|
||||||
|
dryRunParts.add(part);
|
||||||
|
}
|
||||||
|
dryRun = true;
|
||||||
|
run = false;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
// Enable forked execution of Jetty server
|
// Enable forked execution of Jetty server
|
||||||
if ("--exec".equals(arg))
|
if ("--exec".equals(arg))
|
||||||
{
|
{
|
||||||
|
|
|
@ -28,7 +28,30 @@ Command Line Options:
|
||||||
|
|
||||||
--dry-run Print the command line that the start.jar generates,
|
--dry-run Print the command line that the start.jar generates,
|
||||||
then exit. This may be used to generate command lines
|
then exit. This may be used to generate command lines
|
||||||
when the start.ini includes -X or -D arguments.
|
when the start.ini includes -X or -D arguments:
|
||||||
|
|
||||||
|
java -jar start.jar --dry-run > jetty.sh
|
||||||
|
. jetty.sh
|
||||||
|
|
||||||
|
--dry-run=parts Print specific parts of the command line. The parts
|
||||||
|
are a comma separated list of
|
||||||
|
o "java" - the JVM to run
|
||||||
|
o "opts" - the JVM options (eg -D and -X flags)
|
||||||
|
o "path" - the JVM class path or JPMS modules options
|
||||||
|
o "main" - the main class to run
|
||||||
|
o "args" - the arguments passed to the main class
|
||||||
|
|
||||||
|
It is possible to decompose the start command:
|
||||||
|
|
||||||
|
OPTS=$(java -jar start.jar --dry-run=opts,path)
|
||||||
|
MAIN=$(java -jar start.jar --dry-run=main)
|
||||||
|
ARGS=$(java -jar start.jar --dry-run=args)
|
||||||
|
java $OPTS -Dextra=opt $MAIN $ARGS extra=arg
|
||||||
|
|
||||||
|
Alternatively to create an args file for java:
|
||||||
|
|
||||||
|
java -jar start.jar --dry-run=opts,path,main,args > /tmp/args
|
||||||
|
java @/tmp/args
|
||||||
|
|
||||||
--exec Run the generated command line (see --dry-run) in
|
--exec Run the generated command line (see --dry-run) in
|
||||||
a sub process. This can be used when start.ini
|
a sub process. This can be used when start.ini
|
||||||
|
@ -59,7 +82,6 @@ Debug and Start Logging:
|
||||||
issues where the jetty specific logger has not yet kicked
|
issues where the jetty specific logger has not yet kicked
|
||||||
in due to startup configuration errors.
|
in due to startup configuration errors.
|
||||||
|
|
||||||
|
|
||||||
Module Management:
|
Module Management:
|
||||||
------------------
|
------------------
|
||||||
|
|
||||||
|
|
|
@ -193,7 +193,7 @@ public class MainTest
|
||||||
assertThat("jetty.home", baseHome.getHome(), is(homePath.toString()));
|
assertThat("jetty.home", baseHome.getHome(), is(homePath.toString()));
|
||||||
assertThat("jetty.base", baseHome.getBase(), is(homePath.toString()));
|
assertThat("jetty.base", baseHome.getBase(), is(homePath.toString()));
|
||||||
|
|
||||||
CommandLineBuilder commandLineBuilder = args.getMainArgs(true);
|
CommandLineBuilder commandLineBuilder = args.getMainArgs(StartArgs.ALL_PARTS);
|
||||||
String commandLine = commandLineBuilder.toString("\n");
|
String commandLine = commandLineBuilder.toString("\n");
|
||||||
String expectedExpansion = String.format("-Xloggc:%s/logs/gc-%s.log",
|
String expectedExpansion = String.format("-Xloggc:%s/logs/gc-%s.log",
|
||||||
baseHome.getBase(), System.getProperty("java.version")
|
baseHome.getBase(), System.getProperty("java.version")
|
||||||
|
|
Loading…
Reference in New Issue