Set argument if no option has found (dotnet/extensions#2822)
\n\nCommit migrated from 1513ad0854
This commit is contained in:
parent
639de3f5f4
commit
7d27ed93f7
|
|
@ -26,10 +26,13 @@ namespace Microsoft.Extensions.CommandLineUtils
|
||||||
// options.
|
// options.
|
||||||
private readonly bool _continueAfterUnexpectedArg;
|
private readonly bool _continueAfterUnexpectedArg;
|
||||||
|
|
||||||
public CommandLineApplication(bool throwOnUnexpectedArg = true, bool continueAfterUnexpectedArg = false)
|
private readonly bool _treatUnmatchedOptionsAsArguments;
|
||||||
|
|
||||||
|
public CommandLineApplication(bool throwOnUnexpectedArg = true, bool continueAfterUnexpectedArg = false, bool treatUnmatchedOptionsAsArguments = false)
|
||||||
{
|
{
|
||||||
_throwOnUnexpectedArg = throwOnUnexpectedArg;
|
_throwOnUnexpectedArg = throwOnUnexpectedArg;
|
||||||
_continueAfterUnexpectedArg = continueAfterUnexpectedArg;
|
_continueAfterUnexpectedArg = continueAfterUnexpectedArg;
|
||||||
|
_treatUnmatchedOptionsAsArguments = treatUnmatchedOptionsAsArguments;
|
||||||
Options = new List<CommandOption>();
|
Options = new List<CommandOption>();
|
||||||
Arguments = new List<CommandArgument>();
|
Arguments = new List<CommandArgument>();
|
||||||
Commands = new List<CommandLineApplication>();
|
Commands = new List<CommandLineApplication>();
|
||||||
|
|
@ -136,6 +139,7 @@ namespace Microsoft.Extensions.CommandLineUtils
|
||||||
CommandLineApplication command = this;
|
CommandLineApplication command = this;
|
||||||
CommandOption option = null;
|
CommandOption option = null;
|
||||||
IEnumerator<CommandArgument> arguments = null;
|
IEnumerator<CommandArgument> arguments = null;
|
||||||
|
var argumentsAssigned = false;
|
||||||
|
|
||||||
for (var index = 0; index < args.Length; index++)
|
for (var index = 0; index < args.Length; index++)
|
||||||
{
|
{
|
||||||
|
|
@ -161,6 +165,25 @@ namespace Microsoft.Extensions.CommandLineUtils
|
||||||
var longOptionName = longOption[0];
|
var longOptionName = longOption[0];
|
||||||
option = command.GetOptions().SingleOrDefault(opt => string.Equals(opt.LongName, longOptionName, StringComparison.Ordinal));
|
option = command.GetOptions().SingleOrDefault(opt => string.Equals(opt.LongName, longOptionName, StringComparison.Ordinal));
|
||||||
|
|
||||||
|
if (option == null && _treatUnmatchedOptionsAsArguments)
|
||||||
|
{
|
||||||
|
if (arguments == null)
|
||||||
|
{
|
||||||
|
arguments = new CommandArgumentEnumerator(command.Arguments.GetEnumerator());
|
||||||
|
}
|
||||||
|
if (arguments.MoveNext())
|
||||||
|
{
|
||||||
|
processed = true;
|
||||||
|
arguments.Current.Values.Add(arg);
|
||||||
|
argumentsAssigned = true;
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
//else
|
||||||
|
//{
|
||||||
|
// argumentsAssigned = false;
|
||||||
|
//}
|
||||||
|
}
|
||||||
|
|
||||||
if (option == null)
|
if (option == null)
|
||||||
{
|
{
|
||||||
var ignoreContinueAfterUnexpectedArg = false;
|
var ignoreContinueAfterUnexpectedArg = false;
|
||||||
|
|
@ -221,6 +244,25 @@ namespace Microsoft.Extensions.CommandLineUtils
|
||||||
processed = true;
|
processed = true;
|
||||||
option = command.GetOptions().SingleOrDefault(opt => string.Equals(opt.ShortName, shortOption[0], StringComparison.Ordinal));
|
option = command.GetOptions().SingleOrDefault(opt => string.Equals(opt.ShortName, shortOption[0], StringComparison.Ordinal));
|
||||||
|
|
||||||
|
if (option == null && _treatUnmatchedOptionsAsArguments)
|
||||||
|
{
|
||||||
|
if (arguments == null)
|
||||||
|
{
|
||||||
|
arguments = new CommandArgumentEnumerator(command.Arguments.GetEnumerator());
|
||||||
|
}
|
||||||
|
if (arguments.MoveNext())
|
||||||
|
{
|
||||||
|
processed = true;
|
||||||
|
arguments.Current.Values.Add(arg);
|
||||||
|
argumentsAssigned = true;
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
//else
|
||||||
|
//{
|
||||||
|
// argumentsAssigned = false;
|
||||||
|
//}
|
||||||
|
}
|
||||||
|
|
||||||
// If not a short option, try symbol option
|
// If not a short option, try symbol option
|
||||||
if (option == null)
|
if (option == null)
|
||||||
{
|
{
|
||||||
|
|
@ -278,7 +320,7 @@ namespace Microsoft.Extensions.CommandLineUtils
|
||||||
option = null;
|
option = null;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!processed && arguments == null)
|
if (!processed && !argumentsAssigned)
|
||||||
{
|
{
|
||||||
var currentCommand = command;
|
var currentCommand = command;
|
||||||
foreach (var subcommand in command.Commands)
|
foreach (var subcommand in command.Commands)
|
||||||
|
|
|
||||||
|
|
@ -1166,5 +1166,59 @@ Examples:
|
||||||
|
|
||||||
Assert.Equal($"Unrecognized option '{inputOption}'", exception.Message);
|
Assert.Equal($"Unrecognized option '{inputOption}'", exception.Message);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public void TreatUnmatchedOptionsAsArguments()
|
||||||
|
{
|
||||||
|
CommandArgument first = null;
|
||||||
|
CommandArgument second = null;
|
||||||
|
|
||||||
|
CommandOption firstOption = null;
|
||||||
|
CommandOption secondOption = null;
|
||||||
|
|
||||||
|
var firstUnmatchedOption = "-firstUnmatchedOption";
|
||||||
|
var firstActualOption = "-firstActualOption";
|
||||||
|
var seconUnmatchedOption = "--secondUnmatchedOption";
|
||||||
|
var secondActualOption = "--secondActualOption";
|
||||||
|
|
||||||
|
var app = new CommandLineApplication(treatUnmatchedOptionsAsArguments: true);
|
||||||
|
|
||||||
|
app.Command("test", c =>
|
||||||
|
{
|
||||||
|
firstOption = c.Option("-firstActualOption", "first option", CommandOptionType.NoValue);
|
||||||
|
secondOption = c.Option("--secondActualOption", "second option", CommandOptionType.NoValue);
|
||||||
|
|
||||||
|
first = c.Argument("first", "First argument");
|
||||||
|
second = c.Argument("second", "Second argument");
|
||||||
|
c.OnExecute(() => 0);
|
||||||
|
});
|
||||||
|
|
||||||
|
app.Execute("test", firstUnmatchedOption, firstActualOption, seconUnmatchedOption, secondActualOption);
|
||||||
|
|
||||||
|
Assert.Equal(firstUnmatchedOption, first.Value);
|
||||||
|
Assert.Equal(seconUnmatchedOption, second.Value);
|
||||||
|
|
||||||
|
Assert.Equal(firstActualOption, firstOption.Template);
|
||||||
|
Assert.Equal(secondActualOption, secondOption.Template);
|
||||||
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public void ThrowExceptionWhenUnmatchedOptionAndTreatUnmatchedOptionsAsArgumentsIsFalse()
|
||||||
|
{
|
||||||
|
CommandArgument first = null;
|
||||||
|
|
||||||
|
var firstOption = "-firstUnmatchedOption";
|
||||||
|
|
||||||
|
var app = new CommandLineApplication(treatUnmatchedOptionsAsArguments: false);
|
||||||
|
app.Command("test", c =>
|
||||||
|
{
|
||||||
|
first = c.Argument("first", "First argument");
|
||||||
|
c.OnExecute(() => 0);
|
||||||
|
});
|
||||||
|
|
||||||
|
var exception = Assert.Throws<CommandParsingException>(() => app.Execute("test", firstOption));
|
||||||
|
|
||||||
|
Assert.Equal($"Unrecognized option '{firstOption}'", exception.Message);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue