Easily manage command-line arguments
Writing a console application is rather easy. However, there is always a tedious task: handling the arguments of the command line. And what about the --help
command which is supposed to display a comprehensive and understandable description of all the combinations accepted by the application (and be up to date):
Microsoft teams were faced with the same problem when developing .NET Core. So they developed a library: Microsoft.Extensions.CommandLineUtils.
At the moment there is not much documentation available except the test project. It is hoped that the documentation of this project (and .NET Core more generally) is improving rapidly. Here are some examples of use (not exhaustive but sufficient for the vast majority of applications).
The first step is to install the NuGet package:
Install-Package Microsoft.Extensions.CommandLineUtils
The second step is to declare the information of the application (name and description) as well as the basic options that we want to support (--help
and --version
):
static void Main(string[] args)
{
// Description of the application
var app = new CommandLineApplication()
{
Name = "SampleApp.exe",
FullName = "Sample App",
Description = "Description of the application"
};
// Handle help and version arguments
// You can declare alias using "|"
app.HelpOption("-?|-h|--help");
app.VersionOption("--version", "1.0.0");
// Code of the console application when there is no argument
app.OnExecute(() =>
{
Console.WriteLine("App executed");
return 0;
});
// Parse the command line and execute the right code
try
{
app.Execute(args);
}
catch (CommandParsingException ex)
{
Console.WriteLine(ex.Message);
app.ShowHelp();
}
}
With these few lines of configuration, the application already recognizes different options:
SampleApp.exe --help
SampleApp.exe -?
SampleApp.exe –-version
Let's go further and perform something useful! An application can perform different tasks. For example, dotnet core cli has several commands including restore
, build
, publish
and pack
. Each command requires different arguments (paths, urls, log level, etc.) and associated documentation. This is reflected in the code by commands:
var app = new CommandLineApplication();
app.HelpOption();
app.VersionOption("--version", "1.0.0");
// sampleapp.exe restore [root] --source <SOURCE>
app.Command("restore", command =>
{
command.Description = "Restore package";
command.HelpOption("-?|-h|--help"); // AppSample.exe restore --help
var rootArg = command.Argument("[root]", "A list of projects or project folders to restore");
var sourceOption = command.Option("-s|--source <SOURCE>", "Specifies a NuGet package source to use during the restore operation", CommandOptionType.SingleValue);
command.OnExecute(() =>
{
var root = rootArg.Value;
var source = sourceOption.Value();
Console.WriteLine($"Restore: Root:{root}; Source:{source}");
return 0;
});
});
// TODO add other commands
// Executed when no commands are specified
app.OnExecute(() =>
{
app.ShowHelp();
return 0;
});
And now, we just added the management of the restore command. The result is immediate:
As you can see, this library is very easy to use. It allows organizing the different commands managed by the application as well as their arguments/options. It also makes it easy to provide an option to display help that is readable and always up-to-date, based on the code.
In summary, I would say that this library reconciles me with the command line 😃
Do you have a question or a suggestion about this post? Contact me!