示例#1
0
        private IList <string> DetermineMissingRequiredCommands(IList <CommandArgument> dispatchedCommands)
        {
            IList <string> missing = new List <string>();

            //
            // figure out which arguments are required
            //
            var required =
                this.arguments.Where(a =>
                                     CommandArgumentFlags.FlagEnabled(a.Flags, CommandArgumentFlags.Required)).ToList();

            if (required.Count > 0)
            {
                //
                // if we actually have some required arguments, then some might
                // not have been dispatched, which means they're missing
                //
                foreach (var requiredCommand in required)
                {
                    if (!dispatchedCommands.Contains(requiredCommand))
                    {
                        missing.Add(requiredCommand.LongName);
                    }
                }
            }

            return(missing);
        }
示例#2
0
        private string GetUsageString(string appName)
        {
            var sb = new StringBuilder();

            //
            // usage start
            //
            sb.Append("Usage: ");
            sb.Append(appName);
            sb.Append(' ');

            //
            // required arguments
            //
            var required = this.arguments.Where(a =>
                                                CommandArgumentFlags.FlagEnabled(a.Flags, CommandArgumentFlags.Required) &&
                                                CommandArgumentFlags.FlagDisabled(a.Flags, CommandArgumentFlags.HideInUsage)).ToList();

            if (required.Count > 0)
            {
                AppendArgumentsToUsage(sb, required);
            }

            //
            // optional arguments
            //
            var optional = this.arguments.Where(a =>
                                                CommandArgumentFlags.FlagDisabled(a.Flags, CommandArgumentFlags.Required) &&
                                                CommandArgumentFlags.FlagDisabled(a.Flags, CommandArgumentFlags.HideInUsage)).ToList();

            if (optional.Count > 0)
            {
                sb.Append(" [");
                AppendArgumentsToUsage(sb, optional);
                sb.Append("]");
            }

            return(sb.ToString());
        }
示例#3
0
        private void AppendArgumentsToUsage(StringBuilder sb, IList <CommandArgument> arguments)
        {
            foreach (var opt in arguments)
            {
                sb.Append(GetCommandDisplayName(opt.Name));
                if (CommandArgumentFlags.FlagEnabled(opt.Flags, CommandArgumentFlags.TakesParameter))
                {
                    if (!String.IsNullOrEmpty(opt.ParameterName))
                    {
                        sb.Append(" <");
                        sb.Append(opt.ParameterName);
                        sb.Append(">");
                    }
                    else
                    {
                        sb.Append(" <arg>");
                    }
                }

                sb.Append(' ');
            }

            sb.Remove(sb.Length - 1, 1);
        }
示例#4
0
        /// <summary>
        /// Parse the indicated string table
        /// </summary>
        /// <param name="args"></param>
        public void Parse(string[] args)
        {
            //
            // This parser attempts to emulate, roughly, the behavior
            // of the POSIX getopt C runtime function for parsing
            // command line arguments.  This mechanism is fairly
            // easy to use as it is quite flexible in how it
            // lets you submit arguments for parsing.
            //
            // For example, all of these would be valid and equivalent
            // command line arguments if you had flags
            // p, q, and z where z takes an argument.
            //
            // -p -q -z7
            // -p -q -z 7
            // -pqz7
            // -p -qz7
            //
            // -p -qz "7"
            // -p -qz"7"
            //
            // The main difference between this parser and getopt, however,
            // is that with getopt you have to do command handling dispatch
            // yourself in a big switch statement.  This parser does
            // the dispatching automatically leveraging C#'s Action<> convention.
            //
            // This parser also provides a slightly more cumbersome syntax for
            // specifying arguments, but by paying this syntax tax, you get the
            // benefit of a help screen that can be generated automatically
            // for you based on the list of command arguments you supply to the
            // parser.  This reduces the common burden a writer of a command line
            // tool has.  It also ensures that the help screen for the application
            // is always up to date whenever new flags or arguments are added
            // to the tool.
            //

            //
            // reset the tracking collections for unknown and missing
            // required commands
            //
            ResetTrackingCollections();

            //
            // first, we merge the whole command line into a single string
            // since we're going to have to parse char by char
            //

            ///*******************************************************
            ///Update
            ///Update, by this way, we can use another args inputs
            ///var args = Environment.GetCommandLineArgs();


            //var joined = String.Join(" ", args.Skip(1).ToArray());

            //
            // we keep track of all commands dispatched to determine if
            // any commands that are required were not supplied
            //
            var dispatchedCommands = new List <CommandArgument>();

            //
            // these are the state variables that are used to track what's
            // going on in the command line as we walk character by character
            // through it.
            //
            bool            isLongArg      = false;
            CommandArgument currentCommand = null;

            //
            // now we walk through the characters of the array until
            // we determine if we've found a matching switch
            //
            foreach (String arg in args.Skip(1))
            {
                if (IsArgStart(arg))
                {
                    //
                    // we check if we're about to deal with a long argument
                    //
                    isLongArg = IsLongArg(arg);

                    String argName;

                    if (!isLongArg)
                    {
                        argName = arg.Substring(1, arg.Length - 1);
                    }
                    else
                    {
                        argName = arg.Substring(2, arg.Length - 2);
                    }
                    currentCommand = GetCommand(argName, isLongArg);

                    if (currentCommand != null)
                    {
                        //
                        // if the current command doesn't take a parameter,
                        // then we just dispatch it to it's handler
                        //
                        if (CommandArgumentFlags.FlagDisabled(currentCommand.Flags,
                                                              CommandArgumentFlags.TakesParameter))
                        {
                            dispatchedCommands.Add(currentCommand);
                            currentCommand = DispatchCommand(currentCommand, String.Empty);
                        }
                    }
                }
                else
                {
                    //
                    // if we've reached a new arg, but there is a current
                    // command, that means we've been gathering a parameter
                    // for it and it needs to be dispatched now.
                    //
                    if (currentCommand != null)
                    {
                        dispatchedCommands.Add(currentCommand);
                        currentCommand = DispatchCommand(currentCommand, arg);
                    }
                    else if ((currentCommand == null) && !String.IsNullOrEmpty(arg.Trim()))
                    {
                        this.unknownCommands.Add(arg);
                    }
                }
            }

            //
            // now that we're done with all the dispatching, we need to determine
            // if there were any required commands that didn't get supplied
            // and store that set for the caller to use
            //
            this.missingRequired = DetermineMissingRequiredCommands(dispatchedCommands);
        }