using System.Text.Json; using Azure.Messaging.ServiceBus; using Azure.Messaging.ServiceBus.Administration; using Elsa.Extensions; using Microsoft.Extensions.DependencyInjection; using NSubstitute; namespace Elsa.AzureServiceBus.ComponentTests.Extensions; public static class AzureServiceBusServiceCollectionExtensions { public static IServiceCollection AddAzureServiceBusTestServices(this IServiceCollection services) { var serviceBusClient = Substitute.For(); var senders = new Dictionary(); var processors = new Dictionary(); serviceBusClient.CreateSender(Arg.Any()).Returns(createSenderCall => { var queueOrTopicName = createSenderCall.Arg(); return senders.GetOrAdd(queueOrTopicName, () => { var serviceBusSender = Substitute.For(); serviceBusSender.SendMessageAsync(Arg.Any(), Arg.Any()).Returns(sendMessageCall => { var message = sendMessageCall.Arg(); var args = CreateMessageArgs(message); var serviceBusProcessor = processors.Where(x => x.Key.StartsWith(queueOrTopicName, StringComparison.OrdinalIgnoreCase)).ToList(); foreach (var (_, processor) in serviceBusProcessor) processor.RaiseProcessMessageAsync(args); return Task.CompletedTask; }); return serviceBusSender; }); }); serviceBusClient.CreateProcessor(Arg.Any(), Arg.Any()).Returns(createProcessorCall => { var queueOrTopicName = createProcessorCall.Arg(); var key = queueOrTopicName; return processors.GetOrAdd(key, () => { return new MockServiceBusProcessor(() => { processors.Remove(key); }); }); }); serviceBusClient.CreateProcessor(Arg.Any(), Arg.Any(), Arg.Any()).Returns(createProcessorCall => { var queueOrTopicName = createProcessorCall.ArgAt(0); var subscription = createProcessorCall.ArgAt(1); var key = $"{queueOrTopicName}:{subscription}"; return processors.GetOrAdd(key, () => { return new MockServiceBusProcessor(() => { processors.Remove(key); }); }); }); services.AddSingleton(serviceBusClient); services.AddSingleton(Substitute.For()); return services; } private static ProcessMessageEventArgs CreateMessageArgs(ServiceBusMessage transportMessage, int deliveryCount = 1) { var payloadJson = JsonSerializer.Serialize(transportMessage); var props = new Dictionary(); var message = ServiceBusModelFactory.ServiceBusReceivedMessage( body: BinaryData.FromString(payloadJson), deliveryCount: deliveryCount, correlationId: transportMessage.CorrelationId, properties: props ); return new ProcessMessageEventArgs(message, null, new CancellationToken()); } }