mskeel Posted September 14, 2006 Posted September 14, 2006 I've parsed the command line on a console app a couple of different ways but I'm curious if there is a pattern or "best" way to do it. Physically parsing is easy. I've got a C# implementation of the GetOpt library. It's applying the arguments to the business logic -- setting up the application to run. That is the part I wonder about. Here is what I generally do: Public Class CommandLineApp //define these up top so it's easier to change them later Private Class DefinedParameters Public Const firstArgLong As String = "arg1" //... End Class Public Sub New() End Sub Public CommandLinePattern() //1. Get the command line parameters -- either passed in or Environment.GetCommandLineArgs() //2. Check initial error Conditions for early trouble //3. Set up GetOpt Try //4. Parse command line using GetOpt //5. Check for early termination scenarios -- user asks for help or version number, improper use of arguments, etc. //6. Set up boolean flags or variables for all the parameters that are left that could be good (such as hide banner or output file or configuration type) //7. Run the business/meaty part of the app with the flags/variables Catch e As ArgumentException Console.WriteLine(e.Message) ShowHelp() End Try End Function Here's an example in code to perhaps make things a little more clear. You can ignore this if you want, I'm just including it as an example to supplement some of my statements above. Public Class CommandLineApp ''define these up top so it's easier to change them later Private Class DefinedParameters Public Const loud As String = "loud" Public Const loud2 As String = "l" Public Const hidebanner As String = "hidebanner" Public Const hidebanner2 As String = "b" Public Const version As String = "version" Public Const version2 As String = "v" Public Const help As String = "help" Public Const help2 As String = "h" Public Const help3 As String = "?" End Class ' Public Sub New() ' End Sub ' 'Usage: Appy filename [-l|--loud] [-b|--hidebanner] | [-v|--version] | [--help|-h|-?] ''This is called from the static Main() function but could easily BE the Main() Public Function Run(ByVal commandLineArgs As String()) As Boolean If commandLineArgs.Length = 1 Then ''you have to either a filename, -v, or -h or the user needs more help ShowHelp() Return True End If ''Setting up GetOpt Dim commandLineParser As New Heyes.GetOpt(commandLineArgs) Dim expectedArgs() As String = {DefinedParameters.loud, DefinedParameters.loud2, _ DefinedParameters.hidebanner, DefinedParameters.hidebanner2, _ DefinedParameters.version, DefinedParameters.version2, _ DefinedParameters.help, DefinedParameters.help2, DefinedParameters.help3} Try commandLineParser.SetOpts(expectedArgs) commandLineParser.Parse() ''If there is a request for the version, always honor it If commandLineParser.IsDefined(DefinedParameters.version) OrElse commandLineParser.IsDefined(DefinedParameters.version2) Then ShowBanner() Return True End If ''if more than one file is attempted, send the user some help If commandLineParser.Args.Count > 2 Then ''1 or 0 files is alright. Remember, the exe is the first arg Console.WriteLine("Only one file may be specified at a time.") ShowHelp() Return True 'ditch out, becuase you failed End If ''no matter what, if the user wants help, give it to them, unless they want the version which I took care of above and ditched out If commandLineParser.IsDefined(DefinedParameters.help) OrElse _ commandLineParser.IsDefined(DefinedParameters.help2) OrElse _ commandLineParser.IsDefined(DefinedParameters.help3) Then ShowHelp() Return True ''ditch out, we gave them their help. End If If commandLineParser.IsDefined(DefinedParameters.loud) AndAlso commandLineParser.IsDefined(DefinedParameters.loud2) Then Console.WriteLine("Options cannot be specified more than once") Console.WriteLine("Paramater name: " + DefinedParameters.loud + ", " + DefinedParameters.loud2) ShowHelp() Return True End If If commandLineParser.IsDefined(DefinedParameters.hidebanner) AndAlso commandLineParser.IsDefined(DefinedParameters.hidebanner2) Then Console.WriteLine("Options cannot be specified more than once") Console.WriteLine("Paramater name: " + DefinedParameters.hidebanner + ", " + DefinedParameters.hidebanner2) ShowHelp() Return True End If ''define the arguments we have that aren't a help or version Dim hideBanner As Boolean = False If commandLineParser.IsDefined(DefinedParameters.loud) OrElse commandLineParser.IsDefined(DefinedParameters.loud2) Then Me._loud = True End If If commandLineParser.IsDefined(DefinedParameters.hidebanner) OrElse commandLineParser.IsDefined(DefinedParameters.hidebanner2) Then hideBanner = True End If ''Now down to business Execute(commandLineParser.Args(1), hideBanner) Return True Catch e As ArgumentException Console.WriteLine(e.Message) ShowHelp() Return True End Try End Function What do you do? Is there a good pattern to use or any general concepts that work particularly well? As I've said, what I do works, it just feels kind of clunky. I'm just curious what other developers are doing with regards to command line interfaces. Quote
Recommended Posts
Join the conversation
You can post now and register later. If you have an account, sign in now to post with your account.