@Test public void testMultiValueOptionWithMapWithoutAuxTypes() { CommandSpec spec = CommandSpec.create(); OptionSpec option = OptionSpec.builder("-c", "--count").arity("3").type(Map.class).build(); assertTrue(option.isMultiValue()); spec.addOption(option); CommandLine commandLine = new CommandLine(spec); commandLine.parse("-c", "1=1.0", "2=2.0", "3=3.0"); Map<String, String> expected = new LinkedHashMap<String, String>(); expected.put("1", "1.0"); expected.put("2", "2.0"); expected.put("3", "3.0"); assertEquals(expected, spec.optionsMap().get("-c").getValue()); }
@Test public void testMixinAnnotationInjectsOptionsAndParametersInDeclarationOrder() throws Exception { @Command(sortOptions = false) class Receiver { @Mixin InjectsOptionsAndParameters.MixMeIn mixMeIn; @Option(names = {"-b", "--beta"}, description = "Receiver option") private int beta; @Parameters(description = "parameters from receiver") File[] receiverFiles; } CommandLine commandLine = new CommandLine(new Receiver()); CommandSpec commandSpec = commandLine.getCommandSpec(); assertEquals(2, commandSpec.options().size()); assertArrayEquals(new String[]{"-a", "--alpha"}, commandSpec.options().get(0).names()); assertArrayEquals(new String[]{"-b", "--beta"}, commandSpec.options().get(1).names()); assertEquals(2, commandSpec.positionalParameters().size()); assertEquals("<files>", commandSpec.positionalParameters().get(0).paramLabel()); assertEquals("<receiverFiles>", commandSpec.positionalParameters().get(1).paramLabel()); String expects = String.format("" + "Usage: <main class> [-a=<alpha>] [-b=<beta>] [<files>...] [<receiverFiles>...]%n" + " [<files>...] parameters from mixin%n" + " [<receiverFiles>...] parameters from receiver%n" + " -a, --alpha=<alpha> option from mixin%n" + " -b, --beta=<beta> Receiver option%n"); assertEquals(expects, usageString(commandLine, Help.Ansi.OFF)); }
StringBuilder clusteredOptional = new StringBuilder("-"); for (OptionSpec option : options) { if (option.hidden()) { continue; } boolean isFlagOption = option.typeInfo().isBoolean(); if (isFlagOption && option.arity().max <= 0) { // #612 consider arity: boolean options may require a parameter String shortestName = option.shortestName(); if (shortestName.length() == 2 && shortestName.startsWith("-")) { booleanOptions.add(option); if (option.required()) { clusteredRequired.append(shortestName.substring(1)); } else { if (!option.hidden()) { Text name = colorScheme.optionText(option.shortestName()); Text param = parameterLabelRenderer().renderParameterLabel(option, colorScheme.ansi(), colorScheme.optionParamStyles); if (option.required()) { // e.g., -x=VAL optionText = optionText.concat(" ").concat(name).concat(param).concat(""); if (option.isMultiValue()) { // e.g., -x=VAL [-x=VAL]... optionText = optionText.concat(" [").concat(name).concat(param).concat("]..."); if (option.isMultiValue()) { // add ellipsis to show option is repeatable optionText = optionText.concat("...");
.isNotNull(); if (optionSpec.type().equals(Boolean.class)) { tomlResult.getBoolean(tomlKey); } else if (optionSpec.isMultiValue() || optionSpec.arity().max > 1) { tomlResult.getArray(tomlKey); } else if (Number.class.isAssignableFrom(optionSpec.type())) { tomlResult.getLong(tomlKey); } else {
/** Ensures all attributes of this {@code CommandSpec} have a valid value; throws an {@link InitializationException} if this cannot be achieved. */ void validate() { Collections.sort(positionalParameters, new PositionalParametersSorter()); validatePositionalParameters(positionalParameters); List<String> wrongUsageHelpAttr = new ArrayList<String>(); List<String> wrongVersionHelpAttr = new ArrayList<String>(); List<String> usageHelpAttr = new ArrayList<String>(); List<String> versionHelpAttr = new ArrayList<String>(); for (OptionSpec option : options()) { if (option.usageHelp()) { usageHelpAttr.add(option.longestName()); if (!isBoolean(option.type())) { wrongUsageHelpAttr.add(option.longestName()); } } if (option.versionHelp()) { versionHelpAttr.add(option.longestName()); if (!isBoolean(option.type())) { wrongVersionHelpAttr.add(option.longestName()); } } } String wrongType = "Non-boolean options like %s should not be marked as '%s=true'. Usually a command has one %s boolean flag that triggers display of the %s. Alternatively, consider using @Command(mixinStandardHelpOptions = true) on your command instead."; String multiple = "Multiple options %s are marked as '%s=true'. Usually a command has only one %s option that triggers display of the %s. Alternatively, consider using @Command(mixinStandardHelpOptions = true) on your command instead.%n"; if (!wrongUsageHelpAttr.isEmpty()) { throw new InitializationException(String.format(wrongType, wrongUsageHelpAttr, "usageHelp", "--help", "usage help message")); } if (!wrongVersionHelpAttr.isEmpty()) { throw new InitializationException(String.format(wrongType, wrongVersionHelpAttr, "versionHelp", "--version", "version information")); } if (usageHelpAttr.size() > 1) { new Tracer().warn(multiple, usageHelpAttr, "usageHelp", "--help", "usage help message"); } if (versionHelpAttr.size() > 1) { new Tracer().warn(multiple, versionHelpAttr, "versionHelp", "--version", "version information"); } }
@Test public void testMixinStandardHelpOptions_SettingToTrueAddsHelpOptions() { CommandSpec spec = CommandSpec.create(); assertTrue(spec.mixins().isEmpty()); assertTrue(spec.optionsMap().isEmpty()); assertTrue(spec.posixOptionsMap().isEmpty()); assertTrue(spec.options().isEmpty()); spec.mixinStandardHelpOptions(true); assertFalse(spec.mixins().isEmpty()); assertFalse(spec.optionsMap().isEmpty()); assertFalse(spec.posixOptionsMap().isEmpty()); assertFalse(spec.options().isEmpty()); assertTrue(spec.mixinStandardHelpOptions()); OptionSpec usageHelp = spec.posixOptionsMap().get('h'); assertSame(usageHelp, spec.optionsMap().get("--help")); assertTrue(usageHelp.usageHelp()); OptionSpec versionHelp = spec.posixOptionsMap().get('V'); assertSame(versionHelp, spec.optionsMap().get("--version")); assertTrue(versionHelp.versionHelp()); }
private String getConfigurationValue(final OptionSpec optionSpec) { final String optionKey = getConfigurationKey(optionSpec); final String defaultValue; // Convert values to the right string representation for default string value if (optionSpec.type().equals(Boolean.class)) { defaultValue = getBooleanEntryAsString(optionKey); } else if (optionSpec.isMultiValue()) { defaultValue = getListEntryAsString(optionKey); } else if (optionSpec.type().equals(Integer.class)) { defaultValue = getIntegerEntryAsString(optionKey); } else { // else will be treated as String defaultValue = getEntryAsString(optionKey); } return defaultValue; }
@Test public void testMultiValueOptionArityAloneIsInsufficient() { CommandSpec spec = CommandSpec.create(); OptionSpec option = OptionSpec.builder("-c", "--count").arity("3").type(int.class).build(); assertFalse(option.isMultiValue()); spec.addOption(option); CommandLine commandLine = new CommandLine(spec); try { commandLine.parse("-c", "1", "2", "3"); fail("Expected exception"); } catch (UnmatchedArgumentException ex) { assertEquals("Unmatched arguments: 2, 3", ex.getMessage()); } }
private String getConfigurationKey(final OptionSpec optionSpec) { // remove leading dashes on option name as we can have "--" or "-" options return optionSpec.longestName().replaceFirst("^-+", ""); }
@Test public void testMultiValueOptionWithMapWithoutAuxTypes() { CommandSpec spec = CommandSpec.create(); OptionSpec option = OptionSpec.builder("-c", "--count").arity("3").type(Map.class).build(); assertTrue(option.isMultiValue()); spec.addOption(option); CommandLine commandLine = new CommandLine(spec); commandLine.parse("-c", "1=1.0", "2=2.0", "3=3.0"); Map<String, String> expected = new LinkedHashMap<String, String>(); expected.put("1", "1.0"); expected.put("2", "2.0"); expected.put("3", "3.0"); assertEquals(expected, spec.optionsMap().get("-c").getValue()); }
@Test public void testOptionLongestName_multipleEqualLength_returnsFirst() { assertEquals("-x", OptionSpec.builder("-x", "-a").build().longestName()); }
@Test public void testOptionLongestName_oneName() { assertEquals("-x", OptionSpec.builder("-x").build().longestName()); }
@Test public void testMultiValueOptionWithMapAndAuxTypes() { CommandSpec spec = CommandSpec.create(); OptionSpec option = OptionSpec.builder("-c", "--count").arity("3").type(Map.class).auxiliaryTypes(Integer.class, Double.class).build(); assertTrue(option.isMultiValue()); spec.addOption(option); CommandLine commandLine = new CommandLine(spec); commandLine.parse("-c", "1=1.0", "2=2.0", "3=3.0"); Map<Integer, Double> expected = new LinkedHashMap<Integer, Double>(); expected.put(1, 1.0); expected.put(2, 2.0); expected.put(3, 3.0); assertEquals(expected, spec.optionsMap().get("-c").getValue()); }
public int compare(OptionSpec o1, OptionSpec o2) { Range arity1 = o1.arity(); Range arity2 = o2.arity(); int result = arity1.max - arity2.max; if (result == 0) { result = arity1.min - arity2.min; } if (result == 0) { // arity is same if (o1.isMultiValue() && !o2.isMultiValue()) { result = 1; } // f1 > f2 if (!o1.isMultiValue() && o2.isMultiValue()) { result = -1; } // f1 < f2 } return result == 0 ? super.compare(o1, o2) : result; } }
@Test public void testOptionAuxiliaryTypeOverridesDefaultType() { assertEquals(int.class, OptionSpec.builder("-x").auxiliaryTypes(int.class).build().type()); assertEquals(int.class, OptionSpec.builder("-x").arity("0").auxiliaryTypes(int.class).build().type()); assertEquals(int.class, OptionSpec.builder("-x").arity("1").auxiliaryTypes(int.class).build().type()); assertEquals(int.class, OptionSpec.builder("-x").arity("0..1").auxiliaryTypes(int.class).build().type()); assertEquals(int.class, OptionSpec.builder("-x").arity("2").auxiliaryTypes(int.class).build().type()); assertEquals(int.class, OptionSpec.builder("-x").arity("0..2").auxiliaryTypes(int.class).build().type()); assertEquals(int.class, OptionSpec.builder("-x").arity("*").auxiliaryTypes(int.class).build().type()); }
@Test public void testMultiValueOptionWithListAndAuxTypes() { CommandSpec spec = CommandSpec.create(); OptionSpec option = OptionSpec.builder("-c", "--count").arity("3").type(List.class).auxiliaryTypes(Integer.class).build(); assertTrue(option.isMultiValue()); spec.addOption(option); CommandLine commandLine = new CommandLine(spec); commandLine.parse("-c", "1", "2", "3"); assertEquals(Arrays.asList(1, 2, 3), spec.optionsMap().get("-c").getValue()); }
protected boolean internalShowDefaultValue(boolean usageMessageShowDefaults) { return super.internalShowDefaultValue(usageMessageShowDefaults) && !help() && !versionHelp() && !usageHelp(); }