Пример #1
0
        public Task Dispatch(TransportOperations outgoingMessages, TransportTransaction transaction, ContextBag context)
        {
            var channel = channelProvider.GetPublishChannel();

            try
            {
                var unicastTransportOperations   = outgoingMessages.UnicastTransportOperations;
                var multicastTransportOperations = outgoingMessages.MulticastTransportOperations;

                var tasks = new List <Task>(unicastTransportOperations.Count + multicastTransportOperations.Count);

                foreach (var operation in unicastTransportOperations)
                {
                    context.TryGet(out RabbitMQMessagePriority priority);
                    tasks.Add(SendMessage(operation, channel, priority));
                }

                foreach (var operation in multicastTransportOperations)
                {
                    context.TryGet(out RabbitMQMessagePriority priority);
                    tasks.Add(PublishMessage(operation, channel, priority));
                }

                channelProvider.ReturnPublishChannel(channel);

                return(tasks.Count == 1 ? tasks[0] : Task.WhenAll(tasks));
            }
            catch
            {
                channel.Dispose();
                throw;
            }
        }
Пример #2
0
        async Task MovePoisonMessage(BasicDeliverEventArgs message, string queue, CancellationToken messageProcessingCancellationToken)
        {
            try
            {
                var channel = channelProvider.GetPublishChannel();

                try
                {
                    await channel.RawSendInCaseOfFailure(queue, message.Body, message.BasicProperties, messageProcessingCancellationToken).ConfigureAwait(false);
                }
                finally
                {
                    channelProvider.ReturnPublishChannel(channel);
                }
            }
            catch (Exception ex) when(!ex.IsCausedBy(messageProcessingCancellationToken))
            {
                Logger.Error($"Failed to move poison message to queue '{queue}'. Returning message to original queue...", ex);
                consumer.Model.BasicRejectAndRequeueIfOpen(message.DeliveryTag);

                return;
            }

            try
            {
                consumer.Model.BasicAckSingle(message.DeliveryTag);
            }
            catch (AlreadyClosedException ex)
            {
                Logger.Warn($"Failed to acknowledge poison message because the channel was closed. The message was sent to queue '{queue}' but also returned to the original queue.", ex);
            }
        }
        public Task Dispatch(TransportOperations outgoingMessages, TransportTransaction transaction, CancellationToken cancellationToken = default)
        {
            var channel = channelProvider.GetPublishChannel();

            try
            {
                var unicastTransportOperations   = outgoingMessages.UnicastTransportOperations;
                var multicastTransportOperations = outgoingMessages.MulticastTransportOperations;

                var tasks = new List <Task>(unicastTransportOperations.Count + multicastTransportOperations.Count);

                foreach (var operation in unicastTransportOperations)
                {
                    tasks.Add(SendMessage(operation, channel, cancellationToken));
                }

                foreach (var operation in multicastTransportOperations)
                {
                    tasks.Add(PublishMessage(operation, channel, cancellationToken));
                }

                channelProvider.ReturnPublishChannel(channel);

                return(tasks.Count == 1 ? tasks[0] : Task.WhenAll(tasks));
            }
#pragma warning disable PS0019 // When catching System.Exception, cancellation needs to be properly accounted for - justification:
            // the same action is appropriate when an operation was canceled
            catch
#pragma warning restore PS0019 // When catching System.Exception, cancellation needs to be properly accounted for
            {
                channel.Dispose();
                throw;
            }
        }