I am developing a handler pipeline that follows a responsibility chain pattern.
The pipeline handler has the following interface:
public interface IPipelineHandler<TContext>
{
Func<TContext, Task> Next { get; set; }
Task HandleAsync(TContext context);
}
Each handler has a link to the next handler in the pipeline. The following class is used to build the pipeline:
public class PipelineBuilder<TContext>
{
private readonly List<IPipelineHandler<TContext>> handlers
= new List<IPipelineHandler<TContext>>();
public PipelineBuilder<TContext> Register(IPipelineHandler<TContext> handler)
{
handlers.Add(handler);
return this;
}
public Func<TContext, Task> Build()
{
IPipelineHandler<TContext> root = null;
IPipelineHandler<TContext> prev = null;
foreach (var handler in handlers)
{
if (root == null)
{
root = handler;
}
else
{
prev.Next = ctx => handler.HandleAsync(ctx);
}
prev = handler;
}
return root.HandleAsync;
}
}
The disadvantage of the current implementation is that each handler in the pipeline is designed in advance. I would like to build each handler on demand, so instead of passing the instance of the handler to the assembly, you pass Func<IPipelineHandler<TContext>>.
What modification needs to be done to Build()work with Func<IPipelineHandler<TContext>>so that each pipeline handler is created only when called?
- , , Build().