dotnet / command-line-api

Command line parsing, invocation, and rendering of terminal output.
https://github.com/dotnet/command-line-api/wiki
MIT License
3.34k stars 375 forks source link

Pipeline execution order #2410

Open KathleenDollard opened 2 months ago

KathleenDollard commented 2 months ago

We have taken or considered many approaches to pipeline ordering. What we have observed:

The groupings are these:

Relavent design decisions

Proposal

Create pipeline groups with great names for:

Hey, are those great names?

New subsystems would be placed in a group:

public void Add(CliSubsystem subsystem, PipelineGroup pipelineGroup, bool runFirst = false);

We think it will rarely matter whether something runs first or last within its group. It would only matter when the new subsystem alters the behavior of another subsystem. To allow further customization within the group, we can commit to retaining the order things were added at eitehr the first or last position in the group. There will be only obtuse (*) ability to change the order of standard subsystems.

(*) We can't keep someone from removing it at its normal position and placing it elsewhere. That seems pathological.

Other approaches considered

KathleenDollard commented 2 months ago

Alternate names and including an API:

public enum CliPipelinePhases
{
   // I am actually not sure we need this, as ValueSubsystem needs to act like it is executing to get its data
   NonExecuting = 0,

   /// <summary>Operations that do not require data prep and that generally supersede invocation.</summary>
   EarlyTermination, // NonData?

   /// <summary>Operations that work with data prior to invocation, such as validation. These can terminate on error.</summary>  
   DataPreparation, // ValuePreperation?, BeforeInvocation?

   /// <summary>Invoking operations</summary
   Invocation,

   /// <summary>Error reporting, ExitCode transposition, possibly exception handling, cleanup</summary
   Finishing
}

public class Pipeline
{
   //...
   public void AddSubsystem(CliSubSystem subsystem, CliPipelinePhase phase, bool atStart = false) {...}
   //...
}

The pipeline would also continue to have properties for the expected subsystems, such as Help that could be used to replace the default, so this would not be the common case.