--- a/jdk/src/jdk.jlink/share/classes/jdk/tools/jlink/internal/TaskHelper.java Sun Nov 20 23:19:54 2016 -0800
+++ b/jdk/src/jdk.jlink/share/classes/jdk/tools/jlink/internal/TaskHelper.java Mon Nov 21 10:08:20 2016 -0400
@@ -46,8 +46,8 @@
import java.util.MissingResourceException;
import java.util.ResourceBundle;
import java.util.Set;
+import java.util.stream.Stream;
-import jdk.tools.jlink.internal.plugins.ExcludeFilesPlugin;
import jdk.tools.jlink.internal.plugins.ExcludeJmodSectionPlugin;
import jdk.tools.jlink.plugin.Plugin;
import jdk.tools.jlink.plugin.Plugin.Category;
@@ -90,8 +90,7 @@
public boolean showUsage;
}
- public static class Option<T> {
-
+ public static class Option<T> implements Comparable<T> {
public interface Processing<T> {
void process(T task, String opt, String arg) throws BadArgs;
@@ -100,17 +99,34 @@
final boolean hasArg;
final Processing<T> processing;
final boolean hidden;
- final String[] aliases;
+ final String name;
+ final String shortname;
- public Option(boolean hasArg, Processing<T> processing, boolean hidden, String... aliases) {
+ public Option(boolean hasArg, Processing<T> processing, boolean hidden, String name, String shortname) {
+ if (!name.startsWith("--")) {
+ throw new RuntimeException("option name missing --, " + name);
+ }
+ if (!shortname.isEmpty() && !shortname.startsWith("-")) {
+ throw new RuntimeException("short name missing -, " + shortname);
+ }
+
this.hasArg = hasArg;
this.processing = processing;
- this.aliases = aliases;
this.hidden = hidden;
+ this.name = name;
+ this.shortname = shortname;
}
- public Option(boolean hasArg, Processing<T> processing, String... aliases) {
- this(hasArg, processing, false, aliases);
+ public Option(boolean hasArg, Processing<T> processing, String name, String shortname) {
+ this(hasArg, processing, false, name, shortname);
+ }
+
+ public Option(boolean hasArg, Processing<T> processing, boolean hidden, String name) {
+ this(hasArg, processing, hidden, name, "");
+ }
+
+ public Option(boolean hasArg, Processing<T> processing, String name) {
+ this(hasArg, processing, false, name, "");
}
public boolean isHidden() {
@@ -118,16 +134,10 @@
}
public boolean matches(String opt) {
- for (String a : aliases) {
- if (a.equals(opt)) {
- return true;
- } else if (opt.startsWith("--")
- && (hasArg && opt.startsWith(a + "="))) {
- return true;
- }
- }
- return false;
- }
+ return opt.equals(name) ||
+ opt.equals(shortname) ||
+ hasArg && opt.startsWith("--") && opt.startsWith(name + "=");
+ }
public boolean ignoreRest() {
return false;
@@ -137,28 +147,54 @@
processing.process(task, opt, arg);
}
- public String[] aliases() {
- return aliases;
+ public String getName() {
+ return name;
+ }
+
+ public String resourceName() {
+ return resourcePrefix() + name.substring(2);
+ }
+
+ public String getShortname() {
+ return shortname;
+ }
+
+ public String resourcePrefix() {
+ return "main.opt.";
+ }
+
+ @Override
+ public int compareTo(Object object) {
+ if (!(object instanceof Option<?>)) {
+ throw new RuntimeException("comparing non-Option");
+ }
+
+ Option<?> option = (Option<?>)object;
+
+ return name.compareTo(option.name);
+ }
+
+ }
+
+ private static class PluginOption extends Option<PluginsHelper> {
+ public PluginOption(boolean hasArg,
+ Processing<PluginsHelper> processing, boolean hidden, String name, String shortname) {
+ super(hasArg, processing, hidden, name, shortname);
+ }
+
+ public PluginOption(boolean hasArg,
+ Processing<PluginsHelper> processing, boolean hidden, String name) {
+ super(hasArg, processing, hidden, name, "");
+ }
+
+ public String resourcePrefix() {
+ return "plugin.opt.";
}
}
- private static class PlugOption extends Option<PluginsOptions> {
-
- public PlugOption(boolean hasArg,
- Processing<PluginsOptions> processing, boolean hidden, String... aliases) {
- super(hasArg, processing, hidden, aliases);
- }
-
- public PlugOption(boolean hasArg,
- Processing<PluginsOptions> processing, String... aliases) {
- super(hasArg, processing, aliases);
- }
- }
-
- private final class PluginsOptions {
+ private final class PluginsHelper {
private static final String PLUGINS_PATH = "--plugin-module-path";
- private static final String POST_PROCESS = "--post-process-path";
private Layer pluginsLayer = Layer.boot();
private final List<Plugin> plugins;
@@ -170,10 +206,10 @@
// Each such occurrence results in a Map of arguments. So, there could be multiple
// args maps per plugin instance.
private final Map<Plugin, List<Map<String, String>>> pluginToMaps = new HashMap<>();
- private final List<PlugOption> pluginsOptions = new ArrayList<>();
- private final List<PlugOption> mainOptions = new ArrayList<>();
+ private final List<PluginOption> pluginsOptions = new ArrayList<>();
+ private final List<PluginOption> mainOptions = new ArrayList<>();
- private PluginsOptions(String pp) throws BadArgs {
+ private PluginsHelper(String pp) throws BadArgs {
if (pp != null) {
String[] dirs = pp.split(File.pathSeparator);
@@ -193,13 +229,13 @@
addOrderedPluginOptions(plugin, optionsSeen);
}
}
- mainOptions.add(new PlugOption(false,
+ mainOptions.add(new PluginOption(false,
(task, opt, arg) -> {
// This option is handled prior
// to have the options parsed.
},
- "--plugin-module-path"));
- mainOptions.add(new PlugOption(true, (task, opt, arg) -> {
+ false, "--plugin-module-path"));
+ mainOptions.add(new PluginOption(true, (task, opt, arg) -> {
for (Plugin plugin : plugins) {
if (plugin.getName().equals(arg)) {
pluginToMaps.remove(plugin);
@@ -208,24 +244,24 @@
}
throw newBadArgs("err.no.such.plugin", arg);
},
- "--disable-plugin"));
- mainOptions.add(new PlugOption(true, (task, opt, arg) -> {
+ false, "--disable-plugin"));
+ mainOptions.add(new PluginOption(true, (task, opt, arg) -> {
Path path = Paths.get(arg);
if (!Files.exists(path) || !Files.isDirectory(path)) {
throw newBadArgs("err.image.must.exist", path);
}
existingImage = path.toAbsolutePath();
- }, true, POST_PROCESS));
- mainOptions.add(new PlugOption(true,
+ }, true, "--post-process-path"));
+ mainOptions.add(new PluginOption(true,
(task, opt, arg) -> {
lastSorter = arg;
},
true, "--resources-last-sorter"));
- mainOptions.add(new PlugOption(false,
+ mainOptions.add(new PluginOption(false,
(task, opt, arg) -> {
listPlugins = true;
},
- "--list-plugins"));
+ false, "--list-plugins"));
}
private List<Map<String, String>> argListFor(Plugin plugin) {
@@ -261,8 +297,8 @@
}
optionsSeen.add(option);
- PlugOption plugOption
- = new PlugOption(plugin.hasArguments(),
+ PluginOption plugOption
+ = new PluginOption(plugin.hasArguments(),
(task, opt, arg) -> {
if (!Utils.isFunctional(plugin)) {
throw newBadArgs("err.provider.not.functional",
@@ -312,7 +348,7 @@
}
}
},
- "--" + option);
+ false, "--" + option);
pluginsOptions.add(plugOption);
if (Utils.isFunctional(plugin)) {
@@ -322,44 +358,44 @@
if (plugin instanceof DefaultCompressPlugin) {
plugOption
- = new PlugOption(false,
+ = new PluginOption(false,
(task, opt, arg) -> {
Map<String, String> m = addArgumentMap(plugin);
m.put(DefaultCompressPlugin.NAME, DefaultCompressPlugin.LEVEL_2);
- }, "-c");
+ }, false, "--compress", "-c");
mainOptions.add(plugOption);
} else if (plugin instanceof StripDebugPlugin) {
plugOption
- = new PlugOption(false,
+ = new PluginOption(false,
(task, opt, arg) -> {
addArgumentMap(plugin);
- }, "-G");
+ }, false, "--strip-debug", "-G");
mainOptions.add(plugOption);
} else if (plugin instanceof ExcludeJmodSectionPlugin) {
- plugOption = new PlugOption(false, (task, opt, arg) -> {
+ plugOption = new PluginOption(false, (task, opt, arg) -> {
Map<String, String> m = addArgumentMap(plugin);
m.put(ExcludeJmodSectionPlugin.NAME,
ExcludeJmodSectionPlugin.MAN_PAGES);
- }, "--no-man-pages");
+ }, false, "--no-man-pages");
mainOptions.add(plugOption);
- plugOption = new PlugOption(false, (task, opt, arg) -> {
+ plugOption = new PluginOption(false, (task, opt, arg) -> {
Map<String, String> m = addArgumentMap(plugin);
m.put(ExcludeJmodSectionPlugin.NAME,
ExcludeJmodSectionPlugin.INCLUDE_HEADER_FILES);
- }, "--no-header-files");
+ }, false, "--no-header-files");
mainOptions.add(plugOption);
}
}
}
- private PlugOption getOption(String name) throws BadArgs {
- for (PlugOption o : pluginsOptions) {
+ private PluginOption getOption(String name) throws BadArgs {
+ for (PluginOption o : pluginsOptions) {
if (o.matches(name)) {
return o;
}
}
- for (PlugOption o : mainOptions) {
+ for (PluginOption o : mainOptions) {
if (o.matches(name)) {
return o;
}
@@ -461,7 +497,7 @@
private String getPluginsPath(String[] args) throws BadArgs {
String pp = null;
for (int i = 0; i < args.length; i++) {
- if (args[i].equals(PluginsOptions.PLUGINS_PATH)) {
+ if (args[i].equals(PluginsHelper.PLUGINS_PATH)) {
if (i == args.length - 1) {
throw new BadArgs("err.no.plugins.path").showUsage(true);
} else {
@@ -498,13 +534,13 @@
// Must extract it prior to do any option analysis.
// Required to interpret custom plugin options.
// Unit tests can call Task multiple time in same JVM.
- pluginOptions = new PluginsOptions(getPluginsPath(args));
+ pluginOptions = new PluginsHelper(getPluginsPath(args));
// First extract plugins path if any
String pp = null;
List<String> filteredArgs = new ArrayList<>();
for (int i = 0; i < args.length; i++) {
- if (args[i].equals(PluginsOptions.PLUGINS_PATH)) {
+ if (args[i].equals(PluginsHelper.PLUGINS_PATH)) {
if (i == args.length - 1) {
throw new BadArgs("err.no.plugins.path").showUsage(true);
} else {
@@ -529,7 +565,7 @@
for (int i = 0; i < args.length; i++) {
if (args[i].charAt(0) == '-') {
String name = args[i];
- PlugOption pluginOption = null;
+ PluginOption pluginOption = null;
Option<T> option = getOption(name);
if (option == null) {
pluginOption = pluginOptions.getOption(name);
@@ -585,32 +621,13 @@
}
public void showHelp(String progName) {
- showHelp(progName, true);
- }
-
- private void showHelp(String progName, boolean showsImageBuilder) {
log.println(bundleHelper.getMessage("main.usage", progName));
- for (Option<?> o : options) {
- String name = o.aliases[0].substring(1); // there must always be at least one name
- name = name.charAt(0) == '-' ? name.substring(1) : name;
- if (o.isHidden() || name.equals("h")) {
- continue;
- }
- log.println(bundleHelper.getMessage("main.opt." + name));
- }
-
- for (Option<?> o : pluginOptions.mainOptions) {
- if (o.aliases[0].equals(PluginsOptions.POST_PROCESS)
- && !showsImageBuilder) {
- continue;
- }
- String name = o.aliases[0].substring(1); // there must always be at least one name
- name = name.charAt(0) == '-' ? name.substring(1) : name;
- if (o.isHidden()) {
- continue;
- }
- log.println(bundleHelper.getMessage("plugin.opt." + name));
- }
+ Stream.concat(options.stream(), pluginOptions.mainOptions.stream())
+ .filter(option -> !option.isHidden())
+ .sorted()
+ .forEach(option -> {
+ log.println(bundleHelper.getMessage(option.resourceName()));
+ });
log.println(bundleHelper.getMessage("main.command.files"));
}
@@ -619,6 +636,7 @@
log.println("\n" + bundleHelper.getMessage("main.extended.help"));
List<Plugin> pluginList = PluginRepository.
getPlugins(pluginOptions.pluginsLayer);
+
for (Plugin plugin : Utils.getSortedPlugins(pluginList)) {
showPlugin(plugin, log);
}
@@ -671,7 +689,7 @@
}
}
- private PluginsOptions pluginOptions;
+ private PluginsHelper pluginOptions;
private PrintWriter log;
private final ResourceBundleHelper bundleHelper;