public void Should_return_routing_key_with_delay_zero_seconds_for_negative_delay() { var result = DelayInfrastructure.CalculateRoutingKey(-123, "some-address", out var startingDelayLevel); Assert.That(result, Is.EqualTo("0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.some-address")); Assert.That(startingDelayLevel, Is.EqualTo(0)); }
public void Should_return_correct_routing_key_based_on_delay(int delayInSeconds, string address, string expectedRoutingKey, int expectedStartingDelayLevel) { var result = DelayInfrastructure.CalculateRoutingKey(delayInSeconds, address, out var startingDelayLevel); Assert.That(result, Is.EqualTo(expectedRoutingKey)); Assert.That(startingDelayLevel, Is.EqualTo(expectedStartingDelayLevel)); }
public void Should_allow_startup_if_DisableTimeoutManager_setting_is_set() { settings.Set(SettingsKeys.DisableTimeoutManager, true); var result = DelayInfrastructure.CheckForInvalidSettings(settings); Assert.True(result.Succeeded); }
public void Should_allow_startup_if_external_timeout_manager_address_is_configured() { settings.Set(coreExternalTimeoutManagerAddressKey, "endpoint"); var result = DelayInfrastructure.CheckForInvalidSettings(settings); Assert.True(result.Succeeded); }
public void Should_allow_startup_if_timeout_manager_feature_is_disabled() { settings.Set(typeof(TimeoutManager).FullName, FeatureState.Disabled); var result = DelayInfrastructure.CheckForInvalidSettings(settings); Assert.True(result.Succeeded); }
public void Should_prevent_startup_if_DisableTimeoutManager_setting_is_set() { settings.Set(SettingsKeys.DisableTimeoutManager, true); var result = DelayInfrastructure.CheckForInvalidSettings(settings); Assert.False(result.Succeeded); Assert.AreEqual("Cannot disable the timeout manager when the specified routing topology does not implement ISupportDelayedDelivery.", result.ErrorMessage); }
public static (string DestinationQueue, string NewRoutingKey, int NewDelayLevel) GetNewRoutingKey(int delayInSeconds, DateTimeOffset timeSent, string currentRoutingKey, DateTimeOffset utcNow) { var originalDeliveryDate = timeSent.AddSeconds(delayInSeconds); var newDelayInSeconds = Convert.ToInt32(originalDeliveryDate.Subtract(utcNow).TotalSeconds); var destinationQueue = currentRoutingKey.Substring(currentRoutingKey.LastIndexOf('.') + 1); var newRoutingKey = DelayInfrastructure.CalculateRoutingKey(newDelayInSeconds, destinationQueue, out int newDelayLevel); return(destinationQueue, newRoutingKey, newDelayLevel); }
public void Should_allow_startup_if_timeout_manager_feature_is_deactivated_by_send_only() { settings.Set(typeof(TimeoutManager).FullName, FeatureState.Deactivated); settings.Set(coreSendOnlyEndpointKey, true); var result = DelayInfrastructure.CheckForInvalidSettings(settings); Assert.True(result.Succeeded); }
public void Should_prevent_startup_if_external_timeout_manager_address_is_configured() { settings.Set(coreExternalTimeoutManagerAddressKey, "endpoint"); var result = DelayInfrastructure.CheckForInvalidSettings(settings); Assert.False(result.Succeeded); Assert.AreEqual("An external timeout manager address cannot be configured because the timeout manager is not being used for delayed delivery.", result.ErrorMessage); }
public void Should_allow_startup_if_EnableTimeoutManager_setting_is_set_and_timeout_manager_feature_is_active() { settings.Set(SettingsKeys.EnableTimeoutManager, true); settings.Set(typeof(TimeoutManager).FullName, FeatureState.Active); var result = DelayInfrastructure.CheckForInvalidSettings(settings); Assert.True(result.Succeeded); }
public void Should_prevent_startup_if_timeout_manager_feature_is_disabled_and_DisableTimeoutManager_setting_is_not_set() { settings.Set(typeof(TimeoutManager).FullName, FeatureState.Disabled); var result = DelayInfrastructure.CheckForInvalidSettings(settings); Assert.False(result.Succeeded); Assert.AreEqual("The timeout manager is not active, but the transport has not been properly configured for this. " + "Use 'EndpointConfiguration.UseTransport<RabbitMQTransport>().DelayedDelivery().DisableTimeoutManager()' to ensure delayed messages can be sent properly.", result.ErrorMessage); }
public void Should_prevent_startup_if_EnableTimeoutManager_setting_is_set_and_timeout_feature_is_deactivated() { settings.Set(SettingsKeys.EnableTimeoutManager, true); settings.Set(typeof(TimeoutManager).FullName, FeatureState.Deactivated); var result = DelayInfrastructure.CheckForInvalidSettings(settings); Assert.False(result.Succeeded); Assert.AreEqual("The transport has been configured to enable the timeout manager, but the timeout manager is not active." + "Ensure that the timeout manager is active or remove the call to 'EndpointConfiguration.UseTransport<RabbitMQTransport>().DelayedDelivery().EnableTimeoutManager()'.", result.ErrorMessage); }
public Task Run(CancellationToken cancellationToken = default) { console.WriteLine($"Creating delay infrastructure v2.."); using var connection = connectionFactory.CreateAdministrationConnection(); using var channel = connection.CreateModel(); DelayInfrastructure.Build(channel); console.WriteLine("Delay infrastructure v2 created successfully"); return(Task.CompletedTask); }
public static void Reset( this ConventionalRoutingTopology routingTopology, ConnectionFactory connectionFactory, IEnumerable <string> receivingAddresses, IEnumerable <string> sendingAddresses) { using (var connection = connectionFactory.CreateAdministrationConnection()) using (var channel = connection.CreateModel()) { foreach (var address in receivingAddresses.Concat(sendingAddresses)) { channel.QueueDelete(address, false, false); channel.ExchangeDelete(address, false); } DelayInfrastructure.TearDown(channel); DelayInfrastructure.Build(channel); routingTopology.Initialize(channel, receivingAddresses, sendingAddresses); } }
void MigrateQueue(IModel channel, int delayLevel, CancellationToken cancellationToken) { var currentDelayQueue = $"nsb.delay-level-{delayLevel:00}"; var messageCount = channel.MessageCount(currentDelayQueue); var declaredDestinationQueues = new HashSet <string>(); if (messageCount > 0) { if (!quietMode) { console.Write($"Processing {messageCount} messages at delay level {delayLevel:00}. "); } int skippedMessages = 0; int processedMessages = 0; for (int i = 0; i < messageCount && !cancellationToken.IsCancellationRequested; i++) { var message = channel.BasicGet(currentDelayQueue, false); if (message == null) { // Queue is empty break; } if (MessageIsInvalid(message)) { skippedMessages++; if (!poisonQueueCreated) { channel.QueueDeclare(poisonMessageQueue, true, false, false); poisonQueueCreated = true; } channel.BasicPublish(string.Empty, poisonMessageQueue, message.BasicProperties, message.Body); channel.WaitForConfirmsOrDie(); channel.BasicAck(message.DeliveryTag, false); continue; } var messageHeaders = message.BasicProperties.Headers; var delayInSeconds = (int)messageHeaders[DelayInfrastructure.DelayHeader]; var timeSent = GetTimeSent(message); var(destinationQueue, newRoutingKey, newDelayLevel) = GetNewRoutingKey(delayInSeconds, timeSent, message.RoutingKey, DateTimeOffset.UtcNow); // Make sure the destination queue is bound to the delivery exchange to ensure delivery if (!declaredDestinationQueues.Contains(destinationQueue)) { routingTopology.BindToDelayInfrastructure(channel, destinationQueue, DelayInfrastructure.DeliveryExchange, DelayInfrastructure.BindingKey(destinationQueue)); declaredDestinationQueues.Add(destinationQueue); } var publishExchange = DelayInfrastructure.LevelName(newDelayLevel); if (messageHeaders != null) { //These headers need to be removed so that they won't be copied to an outgoing message if this message gets forwarded messageHeaders.Remove(DelayInfrastructure.XDeathHeader); messageHeaders.Remove(DelayInfrastructure.XFirstDeathExchangeHeader); messageHeaders.Remove(DelayInfrastructure.XFirstDeathQueueHeader); messageHeaders.Remove(DelayInfrastructure.XFirstDeathReasonHeader); } channel.BasicPublish(publishExchange, newRoutingKey, message.BasicProperties, message.Body); channel.WaitForConfirmsOrDie(); channel.BasicAck(message.DeliveryTag, false); processedMessages++; } if (!quietMode) { console.WriteLine($"{processedMessages} successful, {skippedMessages} skipped."); } } else { if (!quietMode) { console.WriteLine($"No messages to process at delay level {delayLevel:00}."); } } }
public Task Run(string endpointName, string?errorQueue, string?auditQueue, IEnumerable <string> instanceDiscriminators, CancellationToken cancellationToken = default) { console.WriteLine("Connecting to broker"); using var connection = connectionFactory.CreateAdministrationConnection(); using var channel = connection.CreateModel(); console.WriteLine("Checking for delay infrastructure v2"); try { channel.ExchangeDeclarePassive(DelayInfrastructure.DeliveryExchange); } catch (OperationInterruptedException) { console.Error.Write("Fail: Delay infrastructure v2 not found.\n"); throw; } console.WriteLine($"Creating queues"); var receivingAddresses = new List <string>() { endpointName }; if (instanceDiscriminators.Any()) { receivingAddresses.AddRange(instanceDiscriminators.Select(discriminator => $"{endpointName}-{discriminator}")); } var sendingAddresses = new List <string>(); if (!string.IsNullOrWhiteSpace(errorQueue)) { sendingAddresses.Add(errorQueue); } if (!string.IsNullOrWhiteSpace(auditQueue)) { sendingAddresses.Add(auditQueue); } routingTopology.Initialize(channel, receivingAddresses, sendingAddresses); foreach (var receivingAddress in receivingAddresses) { routingTopology.BindToDelayInfrastructure(channel, receivingAddress, DelayInfrastructure.DeliveryExchange, DelayInfrastructure.BindingKey(receivingAddress)); } console.WriteLine($"Completed successfully"); return(Task.CompletedTask); }
public void Should_allow_startup_if_EnableTimeoutManager_setting_is_not_set() { var result = DelayInfrastructure.CheckForInvalidSettings(settings); Assert.True(result.Succeeded); }