Skip to content

Commit 6af564a

Browse files
Add tests for new property AutoDeleteOnIdle
1 parent 19b48ed commit 6af564a

11 files changed

+355
-0
lines changed
Lines changed: 69 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,69 @@
1+
namespace NServiceBus.Transport.AzureServiceBus.AcceptanceTests
2+
{
3+
using System;
4+
using System.Threading.Tasks;
5+
using AcceptanceTesting;
6+
using Azure.Messaging.ServiceBus;
7+
using Azure.Messaging.ServiceBus.Administration;
8+
using NServiceBus.AcceptanceTests;
9+
using NServiceBus.AcceptanceTests.EndpointTemplates;
10+
using NUnit.Framework;
11+
12+
public class When_using_auto_delete_on_idle : NServiceBusAcceptanceTest
13+
{
14+
const string ResultingEndpointInstanceName = "usingautodeleteonidle.endpointwithautodeleteonidle-12345";
15+
[SetUp]
16+
public async Task Setup()
17+
{
18+
var adminClient =
19+
new ServiceBusAdministrationClient(
20+
Environment.GetEnvironmentVariable("AzureServiceBus_ConnectionString"));
21+
try
22+
{
23+
// makes sure during local development the topic gets cleared before each test run
24+
await adminClient.DeleteQueueAsync(ResultingEndpointInstanceName);
25+
}
26+
catch (ServiceBusException ex) when (ex.Reason == ServiceBusFailureReason.MessagingEntityNotFound)
27+
{
28+
}
29+
}
30+
31+
[Test]
32+
public async Task Should_configure_queue_with_auto_delete_on_idle()
33+
{
34+
var instanceId = "12345";
35+
var context = await Scenario.Define<Context>()
36+
.WithEndpoint<EndpointWithAutoDeleteOnIdle>(b =>
37+
{
38+
b.CustomConfig(c =>
39+
{
40+
var transport = c.ConfigureTransport<AzureServiceBusTransport>();
41+
transport.AutoDeleteOnIdle = TimeSpan.FromMinutes(10);
42+
c.MakeInstanceUniquelyAddressable(instanceId);
43+
});
44+
})
45+
.Done(c => c.EndpointsStarted)
46+
.Run();
47+
48+
// Verify that the queue was created with the correct AutoDeleteOnIdle setting
49+
var adminClient = new ServiceBusAdministrationClient(
50+
Environment.GetEnvironmentVariable("AzureServiceBus_ConnectionString"));
51+
52+
var queueProperties = await adminClient.GetQueueAsync(ResultingEndpointInstanceName);
53+
54+
Assert.That(queueProperties.Value.AutoDeleteOnIdle, Is.EqualTo(TimeSpan.FromMinutes(10)));
55+
}
56+
57+
public class Context : ScenarioContext
58+
{
59+
}
60+
61+
public class EndpointWithAutoDeleteOnIdle : EndpointConfigurationBuilder
62+
{
63+
public EndpointWithAutoDeleteOnIdle()
64+
{
65+
EndpointSetup<DefaultServer>();
66+
}
67+
}
68+
}
69+
}
Lines changed: 103 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,103 @@
1+
namespace NServiceBus.Transport.AzureServiceBus.Tests.Administration;
2+
3+
using System;
4+
using System.Threading.Tasks;
5+
using NUnit.Framework;
6+
using Particular.Approvals;
7+
8+
[TestFixture]
9+
public class QueueCreatorTests
10+
{
11+
[Test]
12+
public async Task Should_set_AutoDeleteOnIdle_when_configured()
13+
{
14+
var transport = new AzureServiceBusTransport("connectionString", TopicTopology.Default)
15+
{
16+
AutoDeleteOnIdle = TimeSpan.FromMinutes(10)
17+
};
18+
19+
var recordingClient = new RecordingServiceBusAdministrationClient();
20+
var creator = new QueueCreator(transport);
21+
22+
await creator.Create(recordingClient, ["test-queue"], "test-queue");
23+
24+
var output = recordingClient.ToString();
25+
26+
Approver.Verify(output);
27+
}
28+
29+
[Test]
30+
public async Task Should_not_set_AutoDeleteOnIdle_when_null()
31+
{
32+
var transport = new AzureServiceBusTransport("connectionString", TopicTopology.Default)
33+
{
34+
AutoDeleteOnIdle = null
35+
};
36+
37+
var recordingClient = new RecordingServiceBusAdministrationClient();
38+
var creator = new QueueCreator(transport);
39+
40+
await creator.Create(recordingClient, ["test-queue"], "test-queue");
41+
42+
var output = recordingClient.ToString(); // AutoDeleteOnIdle should be default - TimeSpan.MaxValue
43+
44+
Approver.Verify(output);
45+
}
46+
47+
[Test]
48+
public async Task Should_only_set_AutoDeleteOnIdle_on_instance_specific_queue()
49+
{
50+
var transport = new AzureServiceBusTransport("connectionString", TopicTopology.Default)
51+
{
52+
AutoDeleteOnIdle = TimeSpan.FromMinutes(10)
53+
};
54+
55+
var recordingClient = new RecordingServiceBusAdministrationClient();
56+
var creator = new QueueCreator(transport);
57+
58+
await creator.Create(recordingClient, ["instance-queue", "error"], "instance-queue");
59+
60+
// AutoDeleteOnIdle should be default for shared queues - TimeSpan.MaxValue
61+
var output = recordingClient.ToString();
62+
63+
Approver.Verify(output);
64+
}
65+
66+
[Test]
67+
public async Task Should_not_set_AutoDeleteOnIdle_when_instance_name_is_null()
68+
{
69+
var transport = new AzureServiceBusTransport("connectionString", TopicTopology.Default)
70+
{
71+
AutoDeleteOnIdle = TimeSpan.FromMinutes(10)
72+
};
73+
74+
var recordingClient = new RecordingServiceBusAdministrationClient();
75+
var creator = new QueueCreator(transport);
76+
77+
// Create queue without specifying an instance name
78+
await creator.Create(recordingClient, ["some-queue"], null);
79+
80+
var output = recordingClient.ToString();
81+
82+
Approver.Verify(output);
83+
}
84+
85+
[Test]
86+
public async Task Should_not_set_AutoDeleteOnIdle_when_queue_name_does_not_match_instance_name()
87+
{
88+
var transport = new AzureServiceBusTransport("connectionString", TopicTopology.Default)
89+
{
90+
AutoDeleteOnIdle = TimeSpan.FromMinutes(10)
91+
};
92+
93+
var recordingClient = new RecordingServiceBusAdministrationClient();
94+
var creator = new QueueCreator(transport);
95+
96+
// Create queue with different instance name
97+
await creator.Create(recordingClient, ["some-queue"], "different-instance");
98+
99+
var output = recordingClient.ToString();
100+
101+
Approver.Verify(output);
102+
}
103+
}

src/Tests/ApprovalFiles/APIApprovals.Approve.approved.txt

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@ namespace NServiceBus
77
{
88
public AzureServiceBusTransport(string connectionString, NServiceBus.TopicTopology topology) { }
99
public AzureServiceBusTransport(string fullyQualifiedNamespace, Azure.Core.TokenCredential tokenCredential, NServiceBus.TopicTopology topology) { }
10+
public System.TimeSpan? AutoDeleteOnIdle { get; set; }
1011
public bool EnablePartitioning { get; set; }
1112
public int EntityMaximumSize { get; set; }
1213
public System.TimeSpan? MaxAutoLockRenewalDuration { get; set; }
Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
CreateQueueOptions: {
2+
"Name": "some-queue",
3+
"LockDuration": "00:05:00",
4+
"MaxSizeInMegabytes": 5120,
5+
"RequiresDuplicateDetection": false,
6+
"RequiresSession": false,
7+
"DefaultMessageTimeToLive": "10675199.02:48:05.4775807",
8+
"AutoDeleteOnIdle": "10675199.02:48:05.4775807",
9+
"DeadLetteringOnMessageExpiration": false,
10+
"DuplicateDetectionHistoryTimeWindow": "00:01:00",
11+
"MaxDeliveryCount": 2147483647,
12+
"EnableBatchedOperations": true,
13+
"AuthorizationRules": [],
14+
"Status": {},
15+
"ForwardTo": null,
16+
"ForwardDeadLetteredMessagesTo": null,
17+
"EnablePartitioning": false,
18+
"UserMetadata": null,
19+
"MaxMessageSizeInKilobytes": null
20+
}
Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
CreateQueueOptions: {
2+
"Name": "test-queue",
3+
"LockDuration": "00:05:00",
4+
"MaxSizeInMegabytes": 5120,
5+
"RequiresDuplicateDetection": false,
6+
"RequiresSession": false,
7+
"DefaultMessageTimeToLive": "10675199.02:48:05.4775807",
8+
"AutoDeleteOnIdle": "10675199.02:48:05.4775807",
9+
"DeadLetteringOnMessageExpiration": false,
10+
"DuplicateDetectionHistoryTimeWindow": "00:01:00",
11+
"MaxDeliveryCount": 2147483647,
12+
"EnableBatchedOperations": true,
13+
"AuthorizationRules": [],
14+
"Status": {},
15+
"ForwardTo": null,
16+
"ForwardDeadLetteredMessagesTo": null,
17+
"EnablePartitioning": false,
18+
"UserMetadata": null,
19+
"MaxMessageSizeInKilobytes": null
20+
}
Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
CreateQueueOptions: {
2+
"Name": "some-queue",
3+
"LockDuration": "00:05:00",
4+
"MaxSizeInMegabytes": 5120,
5+
"RequiresDuplicateDetection": false,
6+
"RequiresSession": false,
7+
"DefaultMessageTimeToLive": "10675199.02:48:05.4775807",
8+
"AutoDeleteOnIdle": "10675199.02:48:05.4775807",
9+
"DeadLetteringOnMessageExpiration": false,
10+
"DuplicateDetectionHistoryTimeWindow": "00:01:00",
11+
"MaxDeliveryCount": 2147483647,
12+
"EnableBatchedOperations": true,
13+
"AuthorizationRules": [],
14+
"Status": {},
15+
"ForwardTo": null,
16+
"ForwardDeadLetteredMessagesTo": null,
17+
"EnablePartitioning": false,
18+
"UserMetadata": null,
19+
"MaxMessageSizeInKilobytes": null
20+
}
Lines changed: 40 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,40 @@
1+
CreateQueueOptions: {
2+
"Name": "instance-queue",
3+
"LockDuration": "00:05:00",
4+
"MaxSizeInMegabytes": 5120,
5+
"RequiresDuplicateDetection": false,
6+
"RequiresSession": false,
7+
"DefaultMessageTimeToLive": "10675199.02:48:05.4775807",
8+
"AutoDeleteOnIdle": "00:10:00",
9+
"DeadLetteringOnMessageExpiration": false,
10+
"DuplicateDetectionHistoryTimeWindow": "00:01:00",
11+
"MaxDeliveryCount": 2147483647,
12+
"EnableBatchedOperations": true,
13+
"AuthorizationRules": [],
14+
"Status": {},
15+
"ForwardTo": null,
16+
"ForwardDeadLetteredMessagesTo": null,
17+
"EnablePartitioning": false,
18+
"UserMetadata": null,
19+
"MaxMessageSizeInKilobytes": null
20+
}
21+
CreateQueueOptions: {
22+
"Name": "error",
23+
"LockDuration": "00:05:00",
24+
"MaxSizeInMegabytes": 5120,
25+
"RequiresDuplicateDetection": false,
26+
"RequiresSession": false,
27+
"DefaultMessageTimeToLive": "10675199.02:48:05.4775807",
28+
"AutoDeleteOnIdle": "10675199.02:48:05.4775807",
29+
"DeadLetteringOnMessageExpiration": false,
30+
"DuplicateDetectionHistoryTimeWindow": "00:01:00",
31+
"MaxDeliveryCount": 2147483647,
32+
"EnableBatchedOperations": true,
33+
"AuthorizationRules": [],
34+
"Status": {},
35+
"ForwardTo": null,
36+
"ForwardDeadLetteredMessagesTo": null,
37+
"EnablePartitioning": false,
38+
"UserMetadata": null,
39+
"MaxMessageSizeInKilobytes": null
40+
}
Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
CreateQueueOptions: {
2+
"Name": "test-queue",
3+
"LockDuration": "00:05:00",
4+
"MaxSizeInMegabytes": 5120,
5+
"RequiresDuplicateDetection": false,
6+
"RequiresSession": false,
7+
"DefaultMessageTimeToLive": "10675199.02:48:05.4775807",
8+
"AutoDeleteOnIdle": "00:10:00",
9+
"DeadLetteringOnMessageExpiration": false,
10+
"DuplicateDetectionHistoryTimeWindow": "00:01:00",
11+
"MaxDeliveryCount": 2147483647,
12+
"EnableBatchedOperations": true,
13+
"AuthorizationRules": [],
14+
"Status": {},
15+
"ForwardTo": null,
16+
"ForwardDeadLetteredMessagesTo": null,
17+
"EnablePartitioning": false,
18+
"UserMetadata": null,
19+
"MaxMessageSizeInKilobytes": null
20+
}
Lines changed: 50 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,50 @@
1+
namespace NServiceBus.Transport.AzureServiceBus.Tests.Configuration;
2+
3+
using System;
4+
using NUnit.Framework;
5+
6+
[TestFixture]
7+
public class Validate_AutoDeleteOnIdle_Prop
8+
{
9+
[Test]
10+
public void AutoDeleteOnIdle_Should_accept_valid_timespan()
11+
{
12+
var transport = new AzureServiceBusTransport("connectionString", TopicTopology.Default);
13+
14+
var validTimeSpan = TimeSpan.FromMinutes(10);
15+
16+
Assert.DoesNotThrow(() => transport.AutoDeleteOnIdle = validTimeSpan);
17+
Assert.That(transport.AutoDeleteOnIdle, Is.EqualTo(validTimeSpan));
18+
}
19+
20+
[Test]
21+
public void AutoDeleteOnIdle_Should_accept_null()
22+
{
23+
var transport = new AzureServiceBusTransport("connectionString", TopicTopology.Default);
24+
25+
Assert.DoesNotThrow(() => transport.AutoDeleteOnIdle = null);
26+
Assert.That(transport.AutoDeleteOnIdle, Is.Null);
27+
}
28+
29+
[Test]
30+
public void AutoDeleteOnIdle_Should_throw_when_less_than_minimum()
31+
{
32+
var transport = new AzureServiceBusTransport("connectionString", TopicTopology.Default);
33+
34+
var invalidTimeSpan = TimeSpan.FromMinutes(4);
35+
36+
var exception = Assert.Throws<ArgumentOutOfRangeException>(() => transport.AutoDeleteOnIdle = invalidTimeSpan);
37+
Assert.That(exception.ParamName, Is.EqualTo("AutoDeleteOnIdle"));
38+
}
39+
40+
[Test]
41+
public void AutoDeleteOnIdle_Should_accept_minimum_value()
42+
{
43+
var transport = new AzureServiceBusTransport("connectionString", TopicTopology.Default);
44+
45+
var minimumTimeSpan = TimeSpan.FromMinutes(5);
46+
47+
Assert.DoesNotThrow(() => transport.AutoDeleteOnIdle = minimumTimeSpan);
48+
Assert.That(transport.AutoDeleteOnIdle, Is.EqualTo(minimumTimeSpan));
49+
}
50+
}

src/Tests/RecordingServiceBusAdministrationClient.cs

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -32,5 +32,11 @@ public override Task<Response<RuleProperties>> CreateRuleAsync(string topicName,
3232
return Task.FromResult<Response<RuleProperties>>(null);
3333
}
3434

35+
public override Task<Response<QueueProperties>> CreateQueueAsync(CreateQueueOptions options, CancellationToken cancellationToken = default)
36+
{
37+
builder.AppendLine($"CreateQueueOptions: {JsonSerializer.Serialize(options, SkdJsonSerializerContext.PolymorphicOptions)}");
38+
return Task.FromResult<Response<QueueProperties>>(null);
39+
}
40+
3541
public override string ToString() => builder.ToString();
3642
}

0 commit comments

Comments
 (0)