private object ParseValue(Type type, string stringData)
        {
            // null is only valid for bool variables
            // empty string is never valid
            if ((stringData != null || type == typeof(bool)) && (stringData == null || stringData.Length > 0))
            {
                try {
                    if (type == typeof(string))
                    {
                        return(stringData);
                    }
                    else if (type == typeof(bool))
                    {
                        if (stringData == null || stringData == "+")
                        {
                            return(true);
                        }
                        else if (stringData == "-")
                        {
                            return(false);
                        }
                    }
                    else if (IsNameValueCollectionType(type))
                    {
                        Match match = Regex.Match(stringData, @"(\w+[^=]*)=(\w*.*)");
                        if (match.Success)
                        {
                            string name  = match.Groups[1].Value;
                            string value = match.Groups[2].Value;

                            if (Unique && _valuePairs.Get(name) != null)
                            {
                                // we always assume we're dealing with properties
                                // here to make the message more clear
                                throw new CommandLineArgumentException(string.Format(CultureInfo.InvariantCulture,
                                                                                     ResourceUtils.GetString("NA1174"),
                                                                                     name, LongName));
                            }
                            _valuePairs.Add(name, value);
                            return(_valuePairs);
                        }
                        else
                        {
                            throw new CommandLineArgumentException(string.Format(CultureInfo.InvariantCulture,
                                                                                 ResourceUtils.GetString("NA1170"),
                                                                                 stringData, LongName), new ArgumentException(
                                                                       "Expected name/value pair (<name>=<value>)."));
                        }
                    }
                    else
                    {
                        if (type.IsEnum)
                        {
                            try {
                                return(Enum.Parse(type, stringData, true));
                            } catch (ArgumentException ex) {
                                string message = "Invalid value {0} for command-line argument '-{1}'. Valid values are: ";
                                foreach (object value in Enum.GetValues(type))
                                {
                                    message += value.ToString() + ", ";
                                }
                                // strip last ,
                                message = message.Substring(0, message.Length - 2) + ".";
                                throw new CommandLineArgumentException(string.Format(CultureInfo.InvariantCulture,
                                                                                     message, stringData, LongName), ex);
                            }
                        }
                        else
                        {
                            // Make a guess that the there's a public static Parse method on the type of the property
                            // that will take an argument of type string to convert the string to the type
                            // required by the property.
                            System.Reflection.MethodInfo parseMethod = type.GetMethod(
                                "Parse", BindingFlags.Public | BindingFlags.Static,
                                null, CallingConventions.Standard, new Type[] { typeof(string) },
                                null);

                            if (parseMethod != null)
                            {
                                // Call the Parse method
                                return(parseMethod.Invoke(null, BindingFlags.Default,
                                                          null, new object[] { stringData }, CultureInfo.InvariantCulture));
                            }
                            else if (type.IsClass)
                            {
                                // Search for a constructor that takes a string argument
                                ConstructorInfo stringArgumentConstructor =
                                    type.GetConstructor(new Type[] { typeof(string) });

                                if (stringArgumentConstructor != null)
                                {
                                    return(stringArgumentConstructor.Invoke(
                                               BindingFlags.Default, null, new object[] { stringData },
                                               CultureInfo.InvariantCulture));
                                }
                            }
                        }
                    }
                } catch (CommandLineArgumentException) {
                    throw;
                } catch (Exception ex) {
                    throw new CommandLineArgumentException(string.Format(CultureInfo.InvariantCulture,
                                                                         ResourceUtils.GetString("NA1170"),
                                                                         stringData, LongName), ex);
                }
            }

            throw new CommandLineArgumentException(string.Format(CultureInfo.InvariantCulture,
                                                                 ResourceUtils.GetString("NA1170"), stringData,
                                                                 LongName));
        }
Exemple #2
0
        /// <summary>
        /// Parse the argument list using the
        /// </summary>
        /// <param name="args"></param>
        private void ParseArgumentList(string[] args)
        {
            if (args != null)
            {
                foreach (string argument in args)
                {
                    if (argument.Length > 0)
                    {
                        switch (argument[0])
                        {
                        case '-':
                        case '/':
                            int    endIndex = argument.IndexOfAny(new char[] { ':', '+', '-' }, 1);
                            string option   = argument.Substring(1, endIndex == -1 ? argument.Length - 1 : endIndex - 1);
                            string optionArgument;

                            if (option.Length + 1 == argument.Length)
                            {
                                optionArgument = null;
                            }
                            else if (argument.Length > 1 + option.Length && argument[1 + option.Length] == ':')
                            {
                                optionArgument = argument.Substring(option.Length + 2);
                            }
                            else
                            {
                                optionArgument = argument.Substring(option.Length + 1);
                            }

                            CommandLineArgument arg = _argumentCollection[option];
                            if (arg == null)
                            {
                                throw new CommandLineArgumentException(string.Format(CultureInfo.InvariantCulture,
                                                                                     "Unknown argument '{0}'", argument));
                            }
                            else
                            {
                                // check if argument is obsolete
                                Attribute[] attribs = (Attribute[])arg.Property.GetCustomAttributes(
                                    typeof(ObsoleteAttribute), false);
                                if (attribs.Length > 0)
                                {
                                    ObsoleteAttribute obsoleteAttrib = (ObsoleteAttribute)attribs[0];
                                    string            message        = string.Format(CultureInfo.InvariantCulture,
                                                                                     ResourceUtils.GetString("NA1177"), option,
                                                                                     obsoleteAttrib.Message);
                                    if (obsoleteAttrib.IsError)
                                    {
                                        throw new CommandLineArgumentException(message);
                                    }
                                    else
                                    {
                                        Console.WriteLine(string.Empty);
                                        Console.WriteLine("Warning: " + message);
                                        Console.WriteLine(string.Empty);
                                    }
                                }

                                if (arg.IsExclusive && args.Length > 1)
                                {
                                    throw new CommandLineArgumentException(string.Format(CultureInfo.InvariantCulture,
                                                                                         "Commandline argument '-{0}' cannot be combined with other arguments.",
                                                                                         arg.LongName));
                                }
                                else
                                {
                                    arg.SetValue(optionArgument);
                                }
                            }
                            break;

                        case '@':
                            if (_supportsResponseFile)
                            {
                                string responseFile = argument.Substring(1, argument.Length - 1);
                                if (!File.Exists(responseFile))
                                {
                                    throw new CommandLineArgumentException(string.Format(CultureInfo.InvariantCulture,
                                                                                         "unable to open response file \"{0}\"", responseFile));
                                }
                                // load file and parse it.
                                ProcessResponseFile(responseFile);
                                break;
                            }
                            continue;

                        default:
                            if (_defaultArgument != null)
                            {
                                _defaultArgument.SetValue(argument);
                            }
                            else
                            {
                                throw new CommandLineArgumentException(string.Format(CultureInfo.InvariantCulture,
                                                                                     "Unknown argument '{0}'", argument));
                            }
                            break;
                        }
                    }
                }
            }
        }
        public void Finish(object destination)
        {
            if (IsRequired && !SeenValue)
            {
                throw new CommandLineArgumentException(string.Format(CultureInfo.InvariantCulture, "Missing required argument '-{0}'.", LongName));
            }

            if (IsArray)
            {
                _propertyInfo.SetValue(destination, _collectionValues.ToArray(_elementType), BindingFlags.Default, null, null, CultureInfo.InvariantCulture);
            }
            else if (IsCollection)
            {
                // If value of property is null, create new instance of collection
                if (_propertyInfo.GetValue(destination, BindingFlags.Default, null, null, CultureInfo.InvariantCulture) == null)
                {
                    if (!_propertyInfo.CanWrite)
                    {
                        throw new NotSupportedException(string.Format(CultureInfo.InvariantCulture,
                                                                      ResourceUtils.GetString("NA1171")
                                                                      + " but is not initialized and does not allow the"
                                                                      + "collection to be initialized.", LongName));
                    }
                    object instance = Activator.CreateInstance(_propertyInfo.PropertyType, BindingFlags.Public | BindingFlags.Instance, null, null, CultureInfo.InvariantCulture);
                    _propertyInfo.SetValue(destination, instance, BindingFlags.Default, null, null, CultureInfo.InvariantCulture);
                }

                object value = _propertyInfo.GetValue(destination,
                                                      BindingFlags.Default, null, null, CultureInfo.InvariantCulture);

                MethodInfo addMethod = null;

                // Locate Add method with 1 parameter
                foreach (MethodInfo method in value.GetType().GetMethods(BindingFlags.Public | BindingFlags.Instance))
                {
                    if (method.Name == "Add" && method.GetParameters().Length == 1)
                    {
                        ParameterInfo parameter = method.GetParameters()[0];
                        if (parameter.ParameterType != typeof(object))
                        {
                            addMethod = method;
                            break;
                        }
                    }
                }

                if (addMethod == null)
                {
                    throw new NotSupportedException(string.Format(CultureInfo.InvariantCulture, ResourceUtils.GetString("NA1169"), LongName));
                }
                else
                {
                    try {
                        foreach (object item in _collectionValues)
                        {
                            addMethod.Invoke(value, BindingFlags.Default, null, new object[] { item }, CultureInfo.InvariantCulture);
                        }
                    } catch (Exception ex) {
                        throw new NotSupportedException(string.Format(CultureInfo.InvariantCulture,
                                                                      ResourceUtils.GetString("NA1173"),
                                                                      LongName), ex);
                    }
                }
            }
            else if (IsNameValueCollection)
            {
                // If value of property is null, create new instance of collection
                if (_propertyInfo.GetValue(destination, BindingFlags.Default, null, null, CultureInfo.InvariantCulture) == null)
                {
                    if (!_propertyInfo.CanWrite)
                    {
                        throw new NotSupportedException(string.Format(CultureInfo.InvariantCulture,
                                                                      ResourceUtils.GetString("NA1171")
                                                                      + " but is not initialized and does not allow the"
                                                                      + "collection to be initialized.", LongName));
                    }
                    object instance = Activator.CreateInstance(_propertyInfo.PropertyType, BindingFlags.Public | BindingFlags.Instance, null, null, CultureInfo.InvariantCulture);
                    _propertyInfo.SetValue(destination, instance, BindingFlags.Default, null, null, CultureInfo.InvariantCulture);
                }

                object value = _propertyInfo.GetValue(destination,
                                                      BindingFlags.Default, null, null, CultureInfo.InvariantCulture);

                MethodInfo addMethod = null;

                // Locate Add method with 2 string parameters
                foreach (MethodInfo method in value.GetType().GetMethods(BindingFlags.Public | BindingFlags.Instance))
                {
                    if (method.Name == "Add" && method.GetParameters().Length == 2)
                    {
                        if (method.GetParameters()[0].ParameterType == typeof(string) &&
                            method.GetParameters()[1].ParameterType == typeof(string))
                        {
                            addMethod = method;
                            break;
                        }
                    }
                }

                if (addMethod == null)
                {
                    throw new NotSupportedException(string.Format(CultureInfo.InvariantCulture,
                                                                  ResourceUtils.GetString("NA1169"), LongName));
                }
                else
                {
                    try {
                        foreach (string key in _valuePairs)
                        {
                            addMethod.Invoke(value, BindingFlags.Default, null,
                                             new object[] { key, _valuePairs.Get(key) },
                                             CultureInfo.InvariantCulture);
                        }
                    } catch (Exception ex) {
                        throw new NotSupportedException(string.Format(CultureInfo.InvariantCulture,
                                                                      ResourceUtils.GetString("NA1173"),
                                                                      LongName), ex);
                    }
                }
            }
            else
            {
                // this fails on mono if the _argumentValue is null
                if (_argumentValue != null)
                {
                    _propertyInfo.SetValue(destination, _argumentValue, BindingFlags.Default, null, null, CultureInfo.InvariantCulture);
                }
            }
        }