Set argument if no option has found (dotnet/extensions#2822)

\n\nCommit migrated from 1513ad0854
This commit is contained in:
Kahbazi 2020-01-10 03:07:56 +03:30 committed by Andrew Stanton-Nurse
parent 639de3f5f4
commit 7d27ed93f7
2 changed files with 98 additions and 2 deletions

View File

@ -26,10 +26,13 @@ namespace Microsoft.Extensions.CommandLineUtils
// options.
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;
_continueAfterUnexpectedArg = continueAfterUnexpectedArg;
_treatUnmatchedOptionsAsArguments = treatUnmatchedOptionsAsArguments;
Options = new List<CommandOption>();
Arguments = new List<CommandArgument>();
Commands = new List<CommandLineApplication>();
@ -136,6 +139,7 @@ namespace Microsoft.Extensions.CommandLineUtils
CommandLineApplication command = this;
CommandOption option = null;
IEnumerator<CommandArgument> arguments = null;
var argumentsAssigned = false;
for (var index = 0; index < args.Length; index++)
{
@ -161,6 +165,25 @@ namespace Microsoft.Extensions.CommandLineUtils
var longOptionName = longOption[0];
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)
{
var ignoreContinueAfterUnexpectedArg = false;
@ -221,6 +244,25 @@ namespace Microsoft.Extensions.CommandLineUtils
processed = true;
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 (option == null)
{
@ -278,7 +320,7 @@ namespace Microsoft.Extensions.CommandLineUtils
option = null;
}
if (!processed && arguments == null)
if (!processed && !argumentsAssigned)
{
var currentCommand = command;
foreach (var subcommand in command.Commands)

View File

@ -1166,5 +1166,59 @@ Examples:
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);
}
}
}