diff --git a/jetty-start/src/main/java/org/eclipse/jetty/start/Main.java b/jetty-start/src/main/java/org/eclipse/jetty/start/Main.java index 18d1187da31..11f65687b45 100644 --- a/jetty-start/src/main/java/org/eclipse/jetty/start/Main.java +++ b/jetty-start/src/main/java/org/eclipse/jetty/start/Main.java @@ -38,8 +38,11 @@ import java.net.SocketTimeoutException; import java.nio.file.Path; import java.util.List; import java.util.Locale; +import java.util.regex.Matcher; +import org.eclipse.jetty.start.Props.Prop; import org.eclipse.jetty.start.config.CommandLineConfigSource; +import org.eclipse.jetty.start.config.ConfigSource; /** * Main start class. @@ -399,6 +402,32 @@ public class Main doStop(args); } + if (args.isUpdateIni()) + { + for (ConfigSource config : baseHome.getConfigSources()) + { + System.out.printf("ConfigSource %s%n",config.getId()); + for (StartIni ini : config.getStartInis()) + { + for (String line : ini.getAllLines()) + { + Matcher m = Module.SET_PROPERTY.matcher(line); + if (m.matches() && m.groupCount()==3) + { + String name = m.group(2); + String value = m.group(3); + Prop p = args.getProperties().getProp(name); + if (p!=null && ("#".equals(m.group(1)) || !value.equals(p.value))) + { + ini.update(baseHome,args.getProperties()); + break; + } + } + } + } + } + } + // Check base directory BaseBuilder baseBuilder = new BaseBuilder(baseHome,args); if(baseBuilder.build()) diff --git a/jetty-start/src/main/java/org/eclipse/jetty/start/Module.java b/jetty-start/src/main/java/org/eclipse/jetty/start/Module.java index a68d9a1fe21..fee0498a4f3 100644 --- a/jetty-start/src/main/java/org/eclipse/jetty/start/Module.java +++ b/jetty-start/src/main/java/org/eclipse/jetty/start/Module.java @@ -61,9 +61,8 @@ import org.eclipse.jetty.start.config.CommandLineConfigSource; public class Module implements Comparable { private static final String VERSION_UNSPECIFIED = "9.2"; - private static Pattern MOD_NAME = Pattern.compile("^(.*)\\.mod",Pattern.CASE_INSENSITIVE); - private static Pattern SET_PROPERTY = Pattern.compile("^(#?)\\s*([^=\\s]+)=(.*)$"); - + static Pattern MOD_NAME = Pattern.compile("^(.*)\\.mod",Pattern.CASE_INSENSITIVE); + static Pattern SET_PROPERTY = Pattern.compile("^(#?)\\s*([^=\\s]+)=(.*)$"); /** The file of the module */ private final Path _path; diff --git a/jetty-start/src/main/java/org/eclipse/jetty/start/StartArgs.java b/jetty-start/src/main/java/org/eclipse/jetty/start/StartArgs.java index 619dc43a705..2224876612a 100644 --- a/jetty-start/src/main/java/org/eclipse/jetty/start/StartArgs.java +++ b/jetty-start/src/main/java/org/eclipse/jetty/start/StartArgs.java @@ -178,6 +178,8 @@ public class StartArgs private boolean version = false; private boolean dryRun = false; private boolean createStartd = false; + private boolean updateIni = false; + private boolean exec = false; private String exec_properties; @@ -786,6 +788,11 @@ public class StartArgs return createStartd; } + public boolean isUpdateIni() + { + return updateIni; + } + public void parse(ConfigSources sources) { ListIterator iter = sources.reverseListIterator(); @@ -899,6 +906,13 @@ public class StartArgs return; } + if (arg.equals("--update-ini") || arg.equals("--update-inis")) + { + run = false; + updateIni = true; + return; + } + if ("--list-classpath".equals(arg) || "--version".equals(arg) || "-v".equals(arg) || "--info".equals(arg)) { listClasspath = true; diff --git a/jetty-start/src/main/java/org/eclipse/jetty/start/StartIni.java b/jetty-start/src/main/java/org/eclipse/jetty/start/StartIni.java index ab4c0141209..f46a76a29d6 100644 --- a/jetty-start/src/main/java/org/eclipse/jetty/start/StartIni.java +++ b/jetty-start/src/main/java/org/eclipse/jetty/start/StartIni.java @@ -18,8 +18,16 @@ package org.eclipse.jetty.start; +import java.io.BufferedWriter; import java.io.IOException; +import java.io.PrintWriter; +import java.nio.charset.StandardCharsets; +import java.nio.file.Files; import java.nio.file.Path; +import java.nio.file.StandardOpenOption; +import java.util.regex.Matcher; + +import org.eclipse.jetty.start.Props.Prop; /** * Simple Start .INI handler @@ -78,4 +86,40 @@ public class StartIni extends TextFile { return basedir; } + + public void update(BaseHome baseHome,Props props) throws IOException + { + String update = getFile().getFileName().toString(); + update = update.substring(0,update.lastIndexOf(".")); + String source = baseHome.toShortForm(getFile()); + + try (PrintWriter writer = new PrintWriter(Files.newBufferedWriter(getFile(),StandardCharsets.UTF_8,StandardOpenOption.TRUNCATE_EXISTING,StandardOpenOption.CREATE))) + { + for (String line : getAllLines()) + { + Matcher m = Module.SET_PROPERTY.matcher(line); + if (m.matches() && m.groupCount()==3) + { + String name = m.group(2); + String value = m.group(3); + Prop p = props.getProp(name); + if (p!=null && ("#".equals(m.group(1)) || !value.equals(p.value))) + { + StartLog.info("%-15s property updated %s=%s",update,name,p.value); + writer.printf("%s=%s%n",name,p.value); + } + else + { + writer.println(line); + } + } + else + { + writer.println(line); + } + } + } + + StartLog.info("%-15s updated %s",update,source); + } } diff --git a/jetty-start/src/main/java/org/eclipse/jetty/start/TextFile.java b/jetty-start/src/main/java/org/eclipse/jetty/start/TextFile.java index 5944f998377..3332e51fe73 100644 --- a/jetty-start/src/main/java/org/eclipse/jetty/start/TextFile.java +++ b/jetty-start/src/main/java/org/eclipse/jetty/start/TextFile.java @@ -40,6 +40,7 @@ public class TextFile implements Iterable { private final Path file; private final List lines = new ArrayList<>(); + private final List allLines = new ArrayList<>(); public TextFile(Path file) throws FileNotFoundException, IOException { @@ -62,6 +63,8 @@ public class TextFile implements Iterable continue; } + allLines.add(line); + if (line.charAt(0) == '#') { continue; @@ -106,6 +109,11 @@ public class TextFile implements Iterable return lines; } + public List getAllLines() + { + return allLines; + } + public void init() { } @@ -130,4 +138,10 @@ public class TextFile implements Iterable { addUniqueLine(line); } + + @Override + public String toString() + { + return file.toString(); + } } diff --git a/jetty-start/src/main/java/org/eclipse/jetty/start/config/ConfigSource.java b/jetty-start/src/main/java/org/eclipse/jetty/start/config/ConfigSource.java index 5127e649215..3789993a9ca 100644 --- a/jetty-start/src/main/java/org/eclipse/jetty/start/config/ConfigSource.java +++ b/jetty-start/src/main/java/org/eclipse/jetty/start/config/ConfigSource.java @@ -18,8 +18,12 @@ package org.eclipse.jetty.start.config; +import java.util.Collections; +import java.util.Set; + import org.eclipse.jetty.start.Props; import org.eclipse.jetty.start.RawArgs; +import org.eclipse.jetty.start.StartIni; /** * A Configuration Source @@ -72,4 +76,9 @@ public interface ConfigSource * @return the value of the property, or null if not found */ public String getProperty(String key); + + public default Set getStartInis() + { + return Collections.emptySet(); + } } diff --git a/jetty-start/src/main/java/org/eclipse/jetty/start/config/DirConfigSource.java b/jetty-start/src/main/java/org/eclipse/jetty/start/config/DirConfigSource.java index b35085172a4..47eb1827725 100644 --- a/jetty-start/src/main/java/org/eclipse/jetty/start/config/DirConfigSource.java +++ b/jetty-start/src/main/java/org/eclipse/jetty/start/config/DirConfigSource.java @@ -28,7 +28,9 @@ import java.nio.file.Path; import java.nio.file.PathMatcher; import java.util.ArrayList; import java.util.Collections; +import java.util.HashSet; import java.util.List; +import java.util.Set; import org.eclipse.jetty.start.FS; import org.eclipse.jetty.start.NaturalSort; @@ -75,6 +77,7 @@ public class DirConfigSource implements ConfigSource private final int weight; private final RawArgs args; private final Props props; + private final Set startInis = new HashSet<>(); /** * Create DirConfigSource with specified identifier and directory. @@ -109,6 +112,7 @@ public class DirConfigSource implements ConfigSource if (FS.canReadFile(iniFile)) { StartIni ini = new StartIni(iniFile); + startInis.add(ini); args.addAll(ini.getLines(),iniFile); parseAllArgs(ini.getLines(),iniFile.toString()); } @@ -149,6 +153,7 @@ public class DirConfigSource implements ConfigSource { StartLog.debug("Reading %s/start.d/%s - %s",id,diniFile.getFileName(),diniFile); StartIni ini = new StartIni(diniFile); + startInis.add(ini); args.addAll(ini.getLines(),diniFile); parseAllArgs(ini.getLines(),diniFile.toString()); } @@ -156,6 +161,12 @@ public class DirConfigSource implements ConfigSource } } + @Override + public Set getStartInis() + { + return startInis; + } + private void parseAllArgs(List lines, String origin) { for (String line : lines) diff --git a/jetty-start/src/main/resources/org/eclipse/jetty/start/usage.txt b/jetty-start/src/main/resources/org/eclipse/jetty/start/usage.txt index 65e84a80de9..459efdc5023 100644 --- a/jetty-start/src/main/resources/org/eclipse/jetty/start/usage.txt +++ b/jetty-start/src/main/resources/org/eclipse/jetty/start/usage.txt @@ -114,6 +114,10 @@ Module Management: Note: not all modules have ini templates and thus may be transitively enabled and not explicitly enabled in a ini file. + + --update-ini Scan all start.ini and start.d/*.ini files and update + any properties with values specified on the command + line. e.g. --update-ini jetty.http.port=8888 --create-startd Ensure that a start.d directory exists for use by subsequent --add-to-start=*. If a start.ini file exists diff --git a/jetty-start/src/test/resources/usecases/parameterized.addToStart.assert.txt b/jetty-start/src/test/resources/usecases/parameterized.addToStart.assert.txt index eadc75d87bc..b31ef3c69c5 100644 --- a/jetty-start/src/test/resources/usecases/parameterized.addToStart.assert.txt +++ b/jetty-start/src/test/resources/usecases/parameterized.addToStart.assert.txt @@ -12,6 +12,8 @@ PROP|main.prop=value0 PROP|name=value PROP|name0=changed0 PROP|name1=changed1 +PROP|property=value +PROP|property0=value0 # Files / Directories to create EXISTS|start.d/parameterized.ini diff --git a/jetty-start/src/test/resources/usecases/parameterized.commands.assert.txt b/jetty-start/src/test/resources/usecases/parameterized.commands.assert.txt index eadc75d87bc..b31ef3c69c5 100644 --- a/jetty-start/src/test/resources/usecases/parameterized.commands.assert.txt +++ b/jetty-start/src/test/resources/usecases/parameterized.commands.assert.txt @@ -12,6 +12,8 @@ PROP|main.prop=value0 PROP|name=value PROP|name0=changed0 PROP|name1=changed1 +PROP|property=value +PROP|property0=value0 # Files / Directories to create EXISTS|start.d/parameterized.ini diff --git a/jetty-start/src/test/resources/usecases/parameterized.update.assert.txt b/jetty-start/src/test/resources/usecases/parameterized.update.assert.txt new file mode 100644 index 00000000000..4e4570e277d --- /dev/null +++ b/jetty-start/src/test/resources/usecases/parameterized.update.assert.txt @@ -0,0 +1,20 @@ +## The XMLs we expect (order is important) +XML|${jetty.home}/etc/base.xml +XML|${jetty.home}/etc/main.xml + +# The LIBs we expect (order is irrelevant) +LIB|${jetty.home}/lib/base.jar +LIB|${jetty.home}/lib/main.jar +LIB|${jetty.home}/lib/other.jar + +# The Properties we expect (order is irrelevant) +PROP|main.prop=value0 +PROP|name=value +PROP|name0=changed0 +PROP|name1=changed1 +PROP|property=value +PROP|property0=changed0 +PROP|property1=changed1 + +# Files / Directories to create +EXISTS|start.d/parameterized.ini diff --git a/jetty-start/src/test/resources/usecases/parameterized.update.prepare.txt b/jetty-start/src/test/resources/usecases/parameterized.update.prepare.txt new file mode 100644 index 00000000000..6ecc31c4e0d --- /dev/null +++ b/jetty-start/src/test/resources/usecases/parameterized.update.prepare.txt @@ -0,0 +1,10 @@ +--create-startd +other=value +name=changed +name0=changed0 +name1=changed1 +--add-to-start=parameterized + +--update-ini +property0=changed0 +property1=changed1 diff --git a/jetty-start/src/test/resources/usecases/parameterized/start.d/tobeupdated.ini b/jetty-start/src/test/resources/usecases/parameterized/start.d/tobeupdated.ini new file mode 100644 index 00000000000..b2f0d878754 --- /dev/null +++ b/jetty-start/src/test/resources/usecases/parameterized/start.d/tobeupdated.ini @@ -0,0 +1,7 @@ + +#p=v +property=value +#comment +property0=value0 +#comment +#property1=value1