Skip to content

System.InvalidOperationException: on parsing GUID command line option. #333

Description

@AlexeyEvlampiev

Describe the bug
System.InvalidOperationException: Could not automatically determine how to convert string values into System.Guid is thrown when registering Guid- command line options.

To Reproduce
Steps to reproduce the behavior:

  1. Using this version of the library '2.5.0'
  2. Run this code
namespace ConsoleApp1
{
    using System;
    using System.Diagnostics;
    using McMaster.Extensions.CommandLineUtils;

    class Program
    {
        static void Main(string[] args)
        {
            var cmd = new CommandLineApplication();
            var guidOption = cmd
                .Option<Guid>("-g", "A GUID-option", CommandOptionType.SingleValue)
                .IsRequired();

            var expected = Guid.NewGuid().ToString();
            cmd.OnExecute(() =>
            {
                var actual = guidOption.ParsedValue;
                Debug.Assert(expected == actual.ToString());
            });
            cmd.Execute(new []{"-g", expected });
        }
    }
}
  1. See error "Could not automatically determine how to convert string values into System.Guid"

Expected behavior
Specifying command options of the Guid type should work seamlessly.

Additional context
I would suggest introducing a generic value parser that would cover most of the CLR standard library types:

using System;
    using System.ComponentModel;
    using System.Globalization;
    using McMaster.Extensions.CommandLineUtils.Abstractions;

    public class GenericValueParser : IValueParser {
        private GenericValueParser(Type targetType, TypeConverter converter)
        {
            TargetType = targetType;
            Converter = converter;
        }

        public static GenericValueParser Get<T>()
        {
            var targetType = typeof(T); 
            var converter = TypeDescriptor.GetConverter(targetType);
            return converter.CanConvertFrom(typeof(string)) ? new GenericValueParser(targetType, converter) : null;
        }

        public Type TargetType { get; }
        public TypeConverter Converter { get; }

        public object Parse(string argName, string value, CultureInfo culture)
        {
            return Converter.ConvertFromString(null, culture, value);
        }

    }

The originally failing code would be fixed with e.g.

namespace ConsoleApp1
{
    using System;
    using System.Diagnostics;
    using McMaster.Extensions.CommandLineUtils;

    class Program
    {
        static void Main(string[] args)
        {
            var cmd = new CommandLineApplication();
            cmd.ValueParsers.Add(GenericValueParser.Get<Guid>());
            var guidOption = cmd
                .Option<Guid>("-g", "A GUID-option", CommandOptionType.SingleValue)
                .IsRequired();

            var expected = Guid.NewGuid().ToString();
            cmd.OnExecute(() =>
            {
                var actual = guidOption.ParsedValue;
                Debug.Assert(expected == actual.ToString());
            });
            cmd.Execute(new []{"-g", expected });
        }
    }
}

Metadata

Metadata

Labels

bughelp wantedWe would be willing to take a well-written PR to help fix this.

Projects

No projects

Milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions