/// <summary>
        /// Used to register Azure Service Bus as well as add a mapping for messages to topics or queues. This method will use the Service Bus connection is passed in for all sending.
        /// </summary>
        /// <param name="services"></param>
        /// <param name="serviceBusName"></param>
        /// <param name="connectionBuilder"></param>
        /// <param name="transportType"></param>
        /// <param name="retryPolicy"></param>
        public static void AddAzureServiceBusConnectionPool(this IServiceCollection services, ServiceBusConnection connection, Action <ServiceBusClientPoolBuilder> connectionBuilder)
        {
            services.AddSingleton <IServiceBusClientPool>(provider =>
            {
                var poolBuilder = new ServiceBusClientPoolBuilder(connection);

                connectionBuilder(poolBuilder);

                return(new ServiceBusClientPool(poolBuilder));
            });
        }
        public async Task EnsureTopicsWithJsonSerializedMessageCanBeMappedProperly()
        {
            var builder = new ServiceBusClientPoolBuilder(new ServiceBusConnection("test.servicebus.windows.net", TransportType.Amqp, RetryPolicy.Default));

            var topicMock = new Mock <ITopicClient>();

            topicMock.Setup(m => m.SendAsync(It.IsAny <Message>()))
            .Verifiable();

            builder.AddTopicClient <FooMessage>(topicMock.Object);

            var pool = new ServiceBusClientPool(builder);

            await pool.SendTopicMessageAsync(new JsonSerializedMessage <FooMessage>(new FooMessage()));
        }
        public async Task EnsureExceptionIsThrowIfMessageIsNotMapped()
        {
            var builder = new ServiceBusClientPoolBuilder(new ServiceBusConnection("test.servicebus.windows.net", TransportType.Amqp, RetryPolicy.Default));

            var topicMock = new Mock <ITopicClient>();

            builder.AddTopicClient <FooMessage>(topicMock.Object);

            var pool = new ServiceBusClientPool(builder);

            await Assert.ThrowsAsync <MessageNotMappedException>(() =>
            {
                return(pool.SendTopicMessageAsync(new BarMessage()));
            });
        }
        public void EnsureTopicClientCanBeFetched()
        {
            var builder = new ServiceBusClientPoolBuilder(new ServiceBusConnection(new ServiceBusConnectionStringBuilder("test.servicebus.windows.net", "test", "test", "test")));

            var topicMock = new Mock <ITopicClient>();

            topicMock.Setup(m => m.TopicName).Returns("Test");

            topicMock.Setup(m => m.SendAsync(It.IsAny <Message>()))
            .Verifiable();

            builder.AddTopicClient <FooMessage>(topicMock.Object);

            var pool = new ServiceBusClientPool(builder);

            var client = pool.GetTopicSubscriptionClient <FooMessage>("test");

            Assert.NotNull(client);
        }
        /// <summary>
        /// Used to register Azure Service Bus as well as add a mapping for messages to topics or queues. This method takes in a connection string builder to configure the Service Bus connection.
        /// </summary>
        /// <param name="services"></param>
        /// <param name="serviceBusName"></param>
        /// <param name="connectionBuilder"></param>
        /// <param name="transportType"></param>
        /// <param name="retryPolicy"></param>
        public static void AddAzureServiceBusConnectionPool(this IServiceCollection services, ServiceBusConnectionStringBuilder connectionStringBuilder, Action <ServiceBusClientPoolBuilder> connectionBuilder)
        {
            services.AddSingleton(provider =>
            {
                var serviceBusConnection = new ServiceBusConnection(connectionStringBuilder);

                return(serviceBusConnection);
            });

            services.AddSingleton <IServiceBusClientPool>(provider =>
            {
                var serviceBusConnection = provider.GetRequiredService <ServiceBusConnection>();

                var poolBuilder = new ServiceBusClientPoolBuilder(serviceBusConnection);

                connectionBuilder(poolBuilder);

                return(new ServiceBusClientPool(poolBuilder));
            });
        }
        /// <summary>
        /// Used to register Azure Service Bus as well as add a mapping for messages to topics or queues. This method will use managed identity and just take in a service bus name t configure the connection.
        /// </summary>
        /// <param name="services"></param>
        /// <param name="serviceBusName"></param>
        /// <param name="connectionBuilder"></param>
        /// <param name="transportType"></param>
        /// <param name="retryPolicy"></param>
        public static void AddAzureServiceBusConnectionPool(this IServiceCollection services, string serviceBusName, Action <ServiceBusClientPoolBuilder> connectionBuilder, TransportType transportType = TransportType.Amqp, RetryPolicy retryPolicy = null)
        {
            services.AddSingleton(provider =>
            {
                var serviceBusConnection = new ServiceBusConnection($"{serviceBusName}.servicebus.windows.net", transportType, retryPolicy)
                {
                    TokenProvider = TokenProvider.CreateManagedIdentityTokenProvider()
                };

                return(serviceBusConnection);
            });

            services.AddSingleton <IServiceBusClientPool>(provider =>
            {
                var serviceBusConnection = provider.GetRequiredService <ServiceBusConnection>();

                var poolBuilder = new ServiceBusClientPoolBuilder(serviceBusConnection);

                connectionBuilder(poolBuilder);

                return(new ServiceBusClientPool(poolBuilder));
            });
        }