private async Task Dispatch <TBusEvent>(TBusEvent busEvent, NimbusMessage nimbusMessage, Type handlerType) where TBusEvent : IBusEvent { var subscriptionFilter = _filterConditionProvider.GetFilterConditionFor(handlerType); if (!nimbusMessage.MatchesFilter(subscriptionFilter)) { _logger.Debug("Message {MessageId} does not match the subscription filter for {HandlerType}. Dropping it immediately.", nimbusMessage.MessageId, handlerType); return; } using (var scope = _dependencyResolver.CreateChildScope()) { var handler = CreateHandlerFromScope(scope, busEvent, handlerType, nimbusMessage); var interceptors = _inboundInterceptorFactory.CreateInterceptors(scope, handler, busEvent, nimbusMessage); Exception exception; try { foreach (var interceptor in interceptors) { _logger.Debug("Executing OnEventHandlerExecuting on {0} for message [MessageType:{1}, MessageId:{2}, CorrelationId:{3}]", interceptor.GetType().FullName, nimbusMessage.SafelyGetBodyTypeNameOrDefault(), nimbusMessage.MessageId, nimbusMessage.CorrelationId); await interceptor.OnEventHandlerExecuting(busEvent, nimbusMessage); _logger.Debug("Executed OnEventHandlerExecuting on {0} for message [MessageType:{1}, MessageId:{2}, CorrelationId:{3}]", interceptor.GetType().FullName, nimbusMessage.SafelyGetBodyTypeNameOrDefault(), nimbusMessage.MessageId, nimbusMessage.CorrelationId); } await DispatchToHandleMethod(busEvent, handler); foreach (var interceptor in interceptors.Reverse()) { _logger.Debug("Executing OnEventHandlerSuccess on {0} for message [MessageType:{1}, MessageId:{2}, CorrelationId:{3}]", interceptor.GetType().FullName, nimbusMessage.SafelyGetBodyTypeNameOrDefault(), nimbusMessage.MessageId, nimbusMessage.CorrelationId); await interceptor.OnEventHandlerSuccess(busEvent, nimbusMessage); _logger.Debug("Executed OnEventHandlerSuccess on {0} for message [MessageType:{1}, MessageId:{2}, CorrelationId:{3}]", interceptor.GetType().FullName, nimbusMessage.SafelyGetBodyTypeNameOrDefault(), nimbusMessage.MessageId, nimbusMessage.CorrelationId); } return; } catch (Exception exc) { exception = exc; } foreach (var interceptor in interceptors.Reverse()) { _logger.Debug("Executing OnEventHandlerError on {0} for message [MessageType:{1}, MessageId:{2}, CorrelationId:{3}]", interceptor.GetType().FullName, nimbusMessage.SafelyGetBodyTypeNameOrDefault(), nimbusMessage.MessageId, nimbusMessage.CorrelationId); await interceptor.OnEventHandlerError(busEvent, nimbusMessage, exception); _logger.Debug("Executed OnEventHandlerError on {0} for message [MessageType:{1}, MessageId:{2}, CorrelationId:{3}]", interceptor.GetType().FullName, nimbusMessage.SafelyGetBodyTypeNameOrDefault(), nimbusMessage.MessageId, nimbusMessage.CorrelationId); } _logger.Debug("Failed to dispatch EventMessage for message [MessageType:{0}, MessageId:{1}, CorrelationId:{2}]", nimbusMessage.SafelyGetBodyTypeNameOrDefault(), nimbusMessage.MessageId, nimbusMessage.CorrelationId); throw new DispatchFailedException("Failed to dispatch EventMessage", exception); } }
// ReSharper disable UnusedMember.Local private async Task Dispatch <TBusRequest, TBusResponse>(TBusRequest busRequest, NimbusMessage nimbusMessage, Type handlerType) where TBusRequest : IBusMulticastRequest <TBusRequest, TBusResponse> where TBusResponse : IBusMulticastResponse { var subscriptionFilter = _filterConditionProvider.GetFilterConditionFor(handlerType); if (!nimbusMessage.MatchesFilter(subscriptionFilter)) { _logger.Debug("Message {MessageId} does not match the subscription filter for {HandlerType}. Dropping it immediately.", nimbusMessage.MessageId, handlerType); return; } var replyQueueName = nimbusMessage.From; var replyQueueClient = _transport.GetQueueSender(replyQueueName); Exception exception = null; using (var scope = _dependencyResolver.CreateChildScope()) { var handler = (IHandleMulticastRequest <TBusRequest, TBusResponse>)scope.Resolve(handlerType); _propertyInjector.Inject(handler, nimbusMessage); var inboundInterceptors = _inboundInterceptorFactory.CreateInterceptors(scope, handler, busRequest, nimbusMessage); foreach (var interceptor in inboundInterceptors) { _logger.Debug("Executing OnRequestHandlerExecuting on {0} for message [MessageType:{1}, MessageId:{2}, CorrelationId:{3}]", interceptor.GetType().FullName, nimbusMessage.SafelyGetBodyTypeNameOrDefault(), nimbusMessage.MessageId, nimbusMessage.CorrelationId); await interceptor.OnMulticastRequestHandlerExecuting(busRequest, nimbusMessage); _logger.Debug("Executed OnRequestHandlerExecuting on {0} for message [MessageType:{1}, MessageId:{2}, CorrelationId:{3}]", interceptor.GetType().FullName, nimbusMessage.SafelyGetBodyTypeNameOrDefault(), nimbusMessage.MessageId, nimbusMessage.CorrelationId); } try { var response = await handler.Handle(busRequest); if (response != null) { var responseMessage = await _nimbusMessageFactory.CreateSuccessfulResponse(replyQueueName, response, nimbusMessage); DispatchLoggingContext.NimbusMessage = responseMessage; var outboundInterceptors = _outboundInterceptorFactory.CreateInterceptors(scope, nimbusMessage); _logger.Debug("Sending successful response message {0} to {1} [MessageId:{2}, CorrelationId:{3}]", responseMessage.SafelyGetBodyTypeNameOrDefault(), replyQueueName, nimbusMessage.MessageId, nimbusMessage.CorrelationId); foreach (var interceptor in outboundInterceptors) { await interceptor.OnMulticastResponseSending(response, nimbusMessage); } await replyQueueClient.Send(responseMessage); foreach (var interceptor in outboundInterceptors.Reverse()) { await interceptor.OnMulticastResponseSent(response, nimbusMessage); } _logger.Debug("Sent successful response message {0} to {1} [MessageId:{2}, CorrelationId:{3}]", nimbusMessage.SafelyGetBodyTypeNameOrDefault(), replyQueueName, nimbusMessage.MessageId, nimbusMessage.CorrelationId); } else { _logger.Debug("Handler declined to reply. [MessageId: {0}, CorrelationId: {1}]", nimbusMessage.MessageId, nimbusMessage.CorrelationId); } } catch (Exception exc) { // Capture any exception so we can send a failed response outside the catch block exception = exc; } if (exception == null) { foreach (var interceptor in inboundInterceptors.Reverse()) { _logger.Debug("Executing OnRequestHandlerSuccess on {0} for message [MessageType:{1}, MessageId:{2}, CorrelationId:{3}]", interceptor.GetType().FullName, nimbusMessage.SafelyGetBodyTypeNameOrDefault(), nimbusMessage.MessageId, nimbusMessage.CorrelationId); await interceptor.OnMulticastRequestHandlerSuccess(busRequest, nimbusMessage); _logger.Debug("Executed OnRequestHandlerSuccess on {0} for message [MessageType:{1}, MessageId:{2}, CorrelationId:{3}]", interceptor.GetType().FullName, nimbusMessage.SafelyGetBodyTypeNameOrDefault(), nimbusMessage.MessageId, nimbusMessage.CorrelationId); } } else { foreach (var interceptor in inboundInterceptors.Reverse()) { _logger.Debug("Executing OnRequestHandlerError on {0} for message [MessageType:{1}, MessageId:{2}, CorrelationId:{3}]", interceptor.GetType().FullName, nimbusMessage.SafelyGetBodyTypeNameOrDefault(), nimbusMessage.MessageId, nimbusMessage.CorrelationId); await interceptor.OnMulticastRequestHandlerError(busRequest, nimbusMessage, exception); _logger.Debug("Executed OnRequestHandlerError on {0} for message [MessageType:{1}, MessageId:{2}, CorrelationId:{3}]", interceptor.GetType().FullName, nimbusMessage.SafelyGetBodyTypeNameOrDefault(), nimbusMessage.MessageId, nimbusMessage.CorrelationId); } var failedResponseMessage = await _nimbusMessageFactory.CreateFailedResponse(replyQueueName, nimbusMessage, exception); _logger.Warn("Sending failed response message to {0} [MessageId:{1}, CorrelationId:{2}]", replyQueueName, exception.Message, nimbusMessage.MessageId, nimbusMessage.CorrelationId); await replyQueueClient.Send(failedResponseMessage); _logger.Debug("Sent failed response message to {0} [MessageId:{1}, CorrelationId:{2}]", replyQueueName, nimbusMessage.MessageId, nimbusMessage.CorrelationId); } } }