diff --git a/src/CommandLine/ErrorExtensions.cs b/src/CommandLine/ErrorExtensions.cs index 2ffe629d..edd03478 100644 --- a/src/CommandLine/ErrorExtensions.cs +++ b/src/CommandLine/ErrorExtensions.cs @@ -23,5 +23,6 @@ public static IEnumerable OnlyMeaningfulOnes(this IEnumerable erro .Where(e => !(e.Tag == ErrorType.UnknownOptionError && ((UnknownOptionError)e).Token.EqualsOrdinalIgnoreCase("help"))); } + } } diff --git a/src/CommandLine/HelpTextExtensions.cs b/src/CommandLine/HelpTextExtensions.cs new file mode 100644 index 00000000..d0106de8 --- /dev/null +++ b/src/CommandLine/HelpTextExtensions.cs @@ -0,0 +1,45 @@ +// Copyright 2005-2015 Giacomo Stelluti Scala & Contributors. All rights reserved. See License.md in the project root for license information. +using System; +using System.IO; +using System.Collections.Generic; +using System.Linq; + +namespace CommandLine +{ + public static class HelpTextExtensions + { + /// + /// return true when errors contain HelpXXXError + /// + public static bool IsHelp(this IEnumerable errs) + { + if (errs.Any(x => x.Tag == ErrorType.HelpRequestedError || + x.Tag == ErrorType.HelpVerbRequestedError)) + return true; + //when AutoHelp=false in parser, help is disabled and Parser raise UnknownOptionError + return errs.Any(x => (x is UnknownOptionError ee ? ee.Token : "") == "help"); + } + + /// + /// return true when errors contain VersionXXXError + /// + public static bool IsVersion(this IEnumerable errs) + { + if (errs.Any(x => x.Tag == ErrorType.VersionRequestedError)) + return true; + //when AutoVersion=false in parser, Version is disabled and Parser raise UnknownOptionError + return errs.Any(x => (x is UnknownOptionError ee ? ee.Token : "") == "version"); + } + /// + /// redirect errs to Console.Error, and to Console.Out for help/version error + /// + public static TextWriter Output(this IEnumerable errs) + { + if (errs.IsHelp() || errs.IsVersion()) + return Console.Out; + return Console.Error; + } + } +} + + diff --git a/src/CommandLine/Text/HelpText.cs b/src/CommandLine/Text/HelpText.cs index 575c6fbc..1306e969 100644 --- a/src/CommandLine/Text/HelpText.cs +++ b/src/CommandLine/Text/HelpText.cs @@ -269,11 +269,11 @@ public static HelpText AutoBuild( var errors = Enumerable.Empty(); + if (onError != null && parserResult.Tag == ParserResultType.NotParsed) { errors = ((NotParsed)parserResult).Errors; - - if (errors.OnlyMeaningfulOnes().Any()) + if (errors.IsHelp() || errors.OnlyMeaningfulOnes().Any()) auto = onError(auto); } diff --git a/tests/CommandLine.Tests/Unit/Text/HelpTextAutoBuildFix.cs b/tests/CommandLine.Tests/Unit/Text/HelpTextAutoBuildFix.cs new file mode 100644 index 00000000..4b78aa13 --- /dev/null +++ b/tests/CommandLine.Tests/Unit/Text/HelpTextAutoBuildFix.cs @@ -0,0 +1,93 @@ +using System; +using System.Linq; +using CommandLine.Tests.Fakes; +using CommandLine.Text; +using FluentAssertions; +using Xunit; + +namespace CommandLine.Tests.Unit.Text +{ + public class HelpTextAutoBuildFix + { + + [Fact] + public void HelpText_wit_AdditionalNewLineAfterOption_true_should_have_newline() + { + // Fixture setup + // Exercize system + var sut = new HelpText { AdditionalNewLineAfterOption = true } + .AddOptions(new NotParsed(TypeInfo.Create(typeof(Simple_Options)), + Enumerable.Empty())); + + // Verify outcome + + var lines = sut.ToString().ToLines(); + + lines[2].Should().BeEquivalentTo(" stringvalue Define a string value here."); + lines[3].Should().BeEquivalentTo(String.Empty); + lines[4].Should().BeEquivalentTo(" s, shortandlong Example with both short and long name."); + lines[5].Should().BeEquivalentTo(String.Empty); + lines[7].Should().BeEquivalentTo(String.Empty); + lines[9].Should().BeEquivalentTo(String.Empty); + lines[11].Should().BeEquivalentTo(String.Empty); + lines[13].Should().BeEquivalentTo(String.Empty); + lines[14].Should().BeEquivalentTo(" value pos. 0 Define a long value here."); + // Teardown + } + + [Fact] + public void HelpText_wit_AdditionalNewLineAfterOption_false_should_not_have_newline() + { + // Fixture setup + // Exercize system + var sut = new HelpText { AdditionalNewLineAfterOption = false } + .AddOptions(new NotParsed(TypeInfo.Create(typeof(Simple_Options)), + Enumerable.Empty())); + + // Verify outcome + + var lines = sut.ToString().ToLines(); + + lines[2].Should().BeEquivalentTo(" stringvalue Define a string value here."); + + lines[3].Should().BeEquivalentTo(" s, shortandlong Example with both short and long name."); + lines[8].Should().BeEquivalentTo(" value pos. 0 Define a long value here."); + // Teardown + } + [Fact] + public void HelpText_wit_by_default_should_include_help_version_option() + { + // Fixture setup + // Exercize system + var sut = new HelpText () + .AddOptions(new NotParsed(TypeInfo.Create(typeof(Simple_Options)), + Enumerable.Empty())); + + // Verify outcome + + var lines = sut.ToString().ToNotEmptyLines(); + lines.Should().HaveCount(c => c ==7); + lines.Should().Contain(" help Display more information on a specific command."); + lines.Should().Contain(" version Display version information."); + // Teardown + } + + [Fact] + public void HelpText_wit_AutoHelp_false_should_hide_help_option() + { + // Fixture setup + // Exercize system + var sut = new HelpText { AutoHelp = false,AutoVersion = false} + .AddOptions(new NotParsed(TypeInfo.Create(typeof(Simple_Options)), + Enumerable.Empty())); + + // Verify outcome + + var lines = sut.ToString().ToNotEmptyLines(); + lines.Should().HaveCount(c => c ==5); + lines.Should().NotContain(" help Display more information on a specific command."); + lines.Should().NotContain(" version Display version information."); + // Teardown + } + } +}