0

I'm using ManyConsole as a command line command and options parser for a console app. All commands are defined as a command class that derives from ConsoleCommand, and then implement a specific task. I defined an intermediary base class, ParkPayConsoleCommand derived from that class:

abstract class ParkPayConsoleCommand: ConsoleCommand
{
    protected readonly ParkPayDbContext DbContext = new ParkPayDbContext();
}

Then all my command classes derive from my base class, and enjoy a built in DbContext, e.g:

class ReadStartsCommand : ParkPayConsoleCommand
{
    public ReadStartsCommand()
    {
        _commandTrace = new TraceSource(CommandName, SourceLevels.All);
        IsCommand("read-starts", "Processes imported vehicle entry movements to create new VehiclePresence records with start date-times based on those movements");
        HasRequiredOption("b|batchId:", "The Id of the VehicleMovementBatch used to create new vehicle presences.", b => _batchIdOption = b);
    }

    public override int Run(string[] remainingArguments)
    {
        // Do the business of the command.
        return (int)ExitCodes.Success;
    }
}

It's a ManyConsole convention for each command class to name and describe itself, and define its command line options in its constructor, as you see above. Normally when I run a command such as the ReadStartsCommand above, it just writes to console what command is running, and not what options I passed.

Yet when I make ParkPayConsoleCommand.DbContext public, not protected, it outputs the string

DbContext : ParkPay.Model.Context.ParkPayDbContext

to the console at the end of the running command's name and description. Why does it do this when DbContext is not anywhere defined as a command option itself. This may seem trivial, but essentially I'm asking quite an important 'meta-question', and that is: Does ManyConsole implicitly interpret all public properties of its command classes as command options, even if they are not explicitly declared as such?

Julian
  • 33,915
  • 22
  • 119
  • 174
ProfK
  • 49,207
  • 121
  • 399
  • 775

2 Answers2

0

I can't speak to the original intent, but as you've found out, yes, it appears to do that. A suggestion of why this might be useful:

Sometimes the commandline options do not map 1-to-1 on to Properties of your ConsoleCommand class. Consider

public class VerbosityCommand : ConsoleCommand
{ 
    public int VerbosityLevel {get;set;}

    public VerbosityCommand(){
         this.IsCommand("Verbosity","Control the level of verbosity");
         this.HasOption("v|verbose","Increase verbosity, cumulative",x => Verbosity++);
    }
}

Now the block printed by ManyConsole will (helpfully) have VerbosityLevel : 3 (for example) rather than (unhelpfully) have

Verbose : set
Verbose : set
Verbose : set

or something similar.

Another example would be preset-type flags, which configure a number of properties in to common configurations.

In your case, it might be useful to make _batchIdOption public and ParkPayDbContext protected or private.

Greg
  • 2,163
  • 1
  • 18
  • 40
0

Basically yes all public properties are printed as Greg said. This does not imply they are all treated as arguments (and they are not). Some additional points:

  • if you do any work overriding OverrideAfterHandlingArgumentsBeforeRun() and assign the result to public members, that result will show up when the command is printed to the console. This can be useful to document some intermediate result for the user

  • to format how the members are printed, you can override ToString on the public member's type

I hope using ManyConsole is smooth otherwise.

Frank Schwieterman
  • 24,142
  • 15
  • 92
  • 130