private async Task <TResult> ExecuteCommandWithHandlers <TResult>(ICommand <TResult> command, ICommandDispatchContext dispatchContext, CancellationToken cancellationToken) { IReadOnlyCollection <IPrioritisedCommandHandler> handlers = _commandRegistry.GetPrioritisedCommandHandlers(command); if (handlers == null || handlers.Count == 0) { throw new MissingCommandHandlerRegistrationException(command.GetType(), "No command actors registered for execution of command"); } TResult result = default(TResult); int handlerIndex = 0; foreach (IPrioritisedCommandHandler handlerTemplate in handlers) { object baseHandler = null; try { baseHandler = _commandHandlerFactory.Create(handlerTemplate.CommandHandlerType); if (baseHandler is ICommandHandler handler) { result = await _commandHandlerExecuter.ExecuteAsync(handler, command, result, cancellationToken); } else { if (baseHandler is IPipelineAwareCommandHandler chainHandler) { PipelineAwareCommandHandlerResult <TResult> chainResult = await _pipelineAwareCommandHandlerExecuter.ExecuteAsync(chainHandler, command, result, cancellationToken); result = chainResult.Result; if (chainResult.ShouldStop) { break; } } else { throw new UnableToExecuteHandlerException("Unexpected result type"); } } } catch (Exception ex) { bool shouldContinue = await _commandExecutionExceptionHandler.HandleException(ex, baseHandler, handlerIndex, command, dispatchContext); if (!shouldContinue) { break; } } handlerIndex++; } return(result); }
public async Task ExecutesCancellableHandlerWithResult() { // Arrange PipelineAwareCommandHandlerExecuter testSubject = new PipelineAwareCommandHandlerExecuter(); CancellableSimpleCommandPipelineAwareHandler handler = new CancellableSimpleCommandPipelineAwareHandler(); SimpleCommand command = new SimpleCommand(); // Act PipelineAwareCommandHandlerResult <SimpleResult> result = await testSubject.ExecuteAsync(handler, command, null, CancellationToken.None); // Assert Assert.Single(result.Result.Handlers); Assert.Equal(typeof(CancellableSimpleCommandPipelineAwareHandler), result.Result.Handlers.Single()); }