-
Notifications
You must be signed in to change notification settings - Fork 13
Defining custom directives
To define a custom directive, just create a new class that implements the IDirective
or IPipelinedDirective
interface and annotate it with [Directive]
attribute:
[Directive(BuiltInDirectives.Debug, Description = "Starts a debugging mode. Application will wait for debugger to be attached before proceeding.")]
public sealed class DebugDirective : IPipelinedDirective
{
/// <inheritdoc/>
public ValueTask OnInitializedAsync(CancellationToken cancellationToken)
{
return default;
}
/// <inheritdoc/>
public async ValueTask HandleAsync(ICliContext context, CommandPipelineHandlerDelegate next, CancellationToken cancellationToken)
{
#if NET5_0
int processId = Environment.ProcessId;
#else
int processId = Process.GetCurrentProcess().Id;
#endif
IConsole console = context.Console;
console.Output.WithForegroundColor(ConsoleColor.Green, (output) => output.WriteLine($"Attach debugger to PID {processId} to continue."));
Debugger.Launch();
while (!Debugger.IsAttached)
await Task.Delay(100, cancellationToken);
await next();
}
}
To implement IDirective
, the class needs to define ContinueExecution
property and the HandleAsync
method what gets called when the user specifies the directive in a command.
To facilitate both asynchronous and synchronous execution, this method returns a ValueTask
. Since the simple command above executes synchronously, we can just put return default
at the end. In an asynchronous command, however, we would use the async
/await
keywords instead.
As a parameter, this method takes an instance of IConsole
, an abstraction around the system console. You should use this abstraction in places where you would normally use System.Console
, in order to make your command testable.
ContinueExecution
property is used to determine whether to stop execution of the command after exiting the directive handler. It can be a get only or a get/set property.
Similarly to commands, in every directive it is possible to define a description and a manual with [Directive]
attribute. [Directive]
attribute provides also an easy way for excluding a command from execution in normal mode through InteractiveModeOnly
property.
Getting started
Advanced features
- Reporting errors
- Exception handling
- Metadata and startup message
- Graceful cancellation
- Dependency injection
- Middleware pipeline
- Environment variables
Utilities
Tests
Misc