diff --git a/ReadMe.md b/ReadMe.md index 604309b..fe010c0 100644 --- a/ReadMe.md +++ b/ReadMe.md @@ -77,7 +77,7 @@ internal static partial class ConsoleApp catch (Exception ex) { Environment.ExitCode = 1; - if (ex is ValidationException) + if (ex is ValidationException or ArgumentParseFailedException) { LogError(ex.Message); } diff --git a/sandbox/GeneratorSandbox/Program.cs b/sandbox/GeneratorSandbox/Program.cs index 40802d9..defda72 100644 --- a/sandbox/GeneratorSandbox/Program.cs +++ b/sandbox/GeneratorSandbox/Program.cs @@ -4,7 +4,7 @@ -args = ["show", "--aaa", "a", "--value", "10.2"]; +args = ["show", "--aaa", "a", "value", "10.2"]; var app = ConsoleApp.Create(); app.Add(); @@ -13,4 +13,5 @@ public class Test { public void Show(string aaa, [Range(0, 1)] double value) => ConsoleApp.Log($"{value}"); -} \ No newline at end of file +} + diff --git a/src/ConsoleAppFramework.Abstractions/ConsoleApp.Abstractions.cs b/src/ConsoleAppFramework.Abstractions/ConsoleApp.Abstractions.cs index 5cf5008..be56be9 100644 --- a/src/ConsoleAppFramework.Abstractions/ConsoleApp.Abstractions.cs +++ b/src/ConsoleAppFramework.Abstractions/ConsoleApp.Abstractions.cs @@ -18,4 +18,8 @@ public abstract class ConsoleAppFilter(ConsoleAppFilter next) public sealed class ConsoleAppFilterAttribute : Attribute where T : ConsoleAppFilter { +} + +public sealed class ArgumentParseFailedException(string message) : Exception(message) +{ } \ No newline at end of file diff --git a/src/ConsoleAppFramework/ConsoleAppGenerator.cs b/src/ConsoleAppFramework/ConsoleAppGenerator.cs index 6eeadff..d84f923 100644 --- a/src/ConsoleAppFramework/ConsoleAppGenerator.cs +++ b/src/ConsoleAppFramework/ConsoleAppGenerator.cs @@ -110,6 +110,10 @@ internal sealed class ConsoleAppFilterAttribute : Attribute { } +internal sealed class ArgumentParseFailedException(string message) : Exception(message) +{ +} + #endif [AttributeUsage(AttributeTargets.Parameter, AllowMultiple = false, Inherited = false)] @@ -179,17 +183,17 @@ public static Task RunAsync(string[] args) static void ThrowArgumentParseFailed(string argumentName, string value) { - throw new ArgumentException($"Argument '{argumentName}' failed to parse, provided value: {value}"); + throw new ArgumentParseFailedException($"Argument '{argumentName}' failed to parse, provided value: {value}"); } static void ThrowRequiredArgumentNotParsed(string name) { - throw new ArgumentException($"Required argument '{name}' was not specified."); + throw new ArgumentParseFailedException($"Required argument '{name}' was not specified."); } static void ThrowArgumentNameNotFound(string argumentName) { - throw new ArgumentException($"Argument '{argumentName}' is not recognized."); + throw new ArgumentParseFailedException($"Argument '{argumentName}' is not recognized."); } [MethodImpl(MethodImplOptions.AggressiveInlining)] @@ -364,7 +368,7 @@ static async Task RunWithFilterAsync(string commandName, string[] args, ConsoleA } Environment.ExitCode = 1; - if (ex is ValidationException) + if (ex is ValidationException or ArgumentParseFailedException) { LogError(ex.Message); } diff --git a/src/ConsoleAppFramework/Emitter.cs b/src/ConsoleAppFramework/Emitter.cs index d017769..0ac3e8e 100644 --- a/src/ConsoleAppFramework/Emitter.cs +++ b/src/ConsoleAppFramework/Emitter.cs @@ -313,7 +313,7 @@ public void EmitRun(SourceBuilder sb, CommandWithId commandWithId, bool isRunAsy sb.AppendLine("Environment.ExitCode = 1;"); - using (sb.BeginBlock("if (ex is ValidationException)")) + using (sb.BeginBlock("if (ex is ValidationException or ArgumentParseFailedException)")) { sb.AppendLine("LogError(ex.Message);"); } diff --git a/tests/ConsoleAppFramework.GeneratorTests/RunTest.cs b/tests/ConsoleAppFramework.GeneratorTests/RunTest.cs index 2c9ff67..98b181e 100644 --- a/tests/ConsoleAppFramework.GeneratorTests/RunTest.cs +++ b/tests/ConsoleAppFramework.GeneratorTests/RunTest.cs @@ -26,6 +26,15 @@ public void SyncRunShouldFailed() verifier.Error("ConsoleApp.Run(args, (int x) => { Console.Write((x)); });", "--x").Should().Contain("Argument 'x' failed to parse"); } + [Fact] + public void MissingArgument() + { + verifier.Error("ConsoleApp.Run(args, (int x, int y) => { Console.Write((x + y)); });", "--x 10 y 20").Should().Contain("Argument 'y' is not recognized."); + + Environment.ExitCode.Should().Be(1); + Environment.ExitCode = 0; + } + [Fact] public void ValidateOne() {