Exemple #1
0
        private async Task ValidateAgentsState(PersistentStreamProviderState expectedState)
        {
            var mgmt = GrainClient.GrainFactory.GetGrain <IManagementGrain>(0);

            var states = await mgmt.SendControlCommandToProvider(adapterType, adapterName, (int)PersistentStreamProviderCommand.GetAgentsState);

            Assert.AreEqual(2, states.Length);
            foreach (var state in states)
            {
                PersistentStreamProviderState providerState;
                Enum.TryParse(state.ToString(), out providerState);
                Assert.AreEqual(expectedState, providerState);
            }

            var numAgents = await mgmt.SendControlCommandToProvider(adapterType, adapterName, (int)PersistentStreamProviderCommand.GetNumberRunningAgents);

            Assert.AreEqual(2, numAgents.Length);
            int totalNumAgents = numAgents.Select(Convert.ToInt32).Sum();

            if (expectedState == PersistentStreamProviderState.AgentsStarted)
            {
                Assert.AreEqual(AzureQueueAdapterFactory.DEFAULT_NUM_QUEUES, totalNumAgents);
            }
            else
            {
                Assert.AreEqual(0, totalNumAgents);
            }
        }
        private async Task ValidateAgentsState(PersistentStreamProviderState expectedState)
        {
            var mgmt        = GrainClient.GrainFactory.GetGrain <IManagementGrain>(0);
            var adapterType = AZURE_QUEUE_STREAM_PROVIDER_TYPE;
            var adapterName = AZURE_QUEUE_STREAM_PROVIDER_NAME;

            var states = await mgmt.SendControlCommandToProvider(adapterType, adapterName, (int)PersistentStreamProviderCommand.GetAgentsState);

            Assert.AreEqual(2, states.Length);
            foreach (var state in states.Cast <PersistentStreamProviderState>())
            {
                Assert.AreEqual(expectedState, state);
            }

            var numAgents = await mgmt.SendControlCommandToProvider(adapterType, adapterName, (int)PersistentStreamProviderCommand.GetNumberRunningAgents);

            Assert.AreEqual(2, numAgents.Length);
            int totalNumAgents = numAgents.Cast <int>().Sum();

            if (expectedState == PersistentStreamProviderState.AgentsStarted)
            {
                Assert.AreEqual(AzureQueueAdapterFactory.DEFAULT_NUM_QUEUES, totalNumAgents);
            }
            else
            {
                Assert.AreEqual(0, totalNumAgents);
            }
        }
        private async Task ValidateAgentsState(PersistentStreamProviderState expectedState)
        {
            var mgmt = GrainClient.GrainFactory.GetGrain<IManagementGrain>(0);

            var states = await mgmt.SendControlCommandToProvider(adapterType, adapterName, (int)PersistentStreamProviderCommand.GetAgentsState);
            Assert.AreEqual(2, states.Length);
            foreach (var state in states)
            {
                PersistentStreamProviderState providerState;
                Enum.TryParse(state.ToString(), out providerState);
                Assert.AreEqual(expectedState, providerState);
            }

            var numAgents = await mgmt.SendControlCommandToProvider(adapterType, adapterName, (int)PersistentStreamProviderCommand.GetNumberRunningAgents);
            Assert.AreEqual(2, numAgents.Length);
            int totalNumAgents = numAgents.Select(Convert.ToInt32).Sum();
            if (expectedState == PersistentStreamProviderState.AgentsStarted)
            {
                Assert.AreEqual(AzureQueueAdapterFactory.DEFAULT_NUM_QUEUES, totalNumAgents);
            }
            else
            {
                Assert.AreEqual(0, totalNumAgents);
            }
        }
        public async Task Init(string name, IProviderRuntime providerUtilitiesManager, IProviderConfiguration config)
        {
            if (!stateManager.PresetState(ProviderState.Initialized))
            {
                return;
            }
            if (String.IsNullOrEmpty(name))
            {
                throw new ArgumentNullException("name");
            }
            if (providerUtilitiesManager == null)
            {
                throw new ArgumentNullException("providerUtilitiesManager");
            }
            if (config == null)
            {
                throw new ArgumentNullException("config");
            }

            Name            = name;
            providerRuntime = (IStreamProviderRuntime)providerUtilitiesManager;
            logger          = providerRuntime.GetLogger(this.GetType().Name);
            adapterFactory  = new TAdapterFactory();
            // Temporary change, but we need GrainFactory inside ServiceProvider for now,
            // so will change it back as soon as we have an action item to add GrainFactory to ServiceProvider.
            adapterFactory.Init(config, Name, logger, new GrainFactoryServiceProvider(providerRuntime));
            queueAdapter = await adapterFactory.CreateAdapter();

            myConfig                  = new PersistentStreamProviderConfig(config);
            this.providerConfig       = config;
            this.serializationManager = this.providerRuntime.ServiceProvider.GetRequiredService <SerializationManager>();
            this.runtimeClient        = this.providerRuntime.ServiceProvider.GetRequiredService <IRuntimeClient>();
            if (this.myConfig.PubSubType == StreamPubSubType.ExplicitGrainBasedAndImplicit ||
                this.myConfig.PubSubType == StreamPubSubType.ExplicitGrainBasedOnly)
            {
                this.streamSubscriptionManager = this.providerRuntime.ServiceProvider
                                                 .GetService <IStreamSubscriptionManagerAdmin>().GetStreamSubscriptionManager(StreamSubscriptionManagerType.ExplicitSubscribeOnly);
            }
            string startup;

            if (config.Properties.TryGetValue(StartupStatePropertyName, out startup))
            {
                if (!Enum.TryParse(startup, true, out startupState))
                {
                    throw new ArgumentException(
                              String.Format("Unsupported value '{0}' for configuration parameter {1} of stream provider {2}.", startup, StartupStatePropertyName, config.Name));
                }
            }
            else
            {
                startupState = StartupStateDefaultValue;
            }
            logger.Info("Initialized PersistentStreamProvider<{0}> with name {1}, Adapter {2} and config {3}, {4} = {5}.",
                        typeof(TAdapterFactory).Name,
                        Name,
                        queueAdapter.Name,
                        myConfig,
                        StartupStatePropertyName, startupState);
            stateManager.CommitState();
        }
        public async Task StartAgents()
        {
            managerState = PersistentStreamProviderState.AgentsStarted;
            List <QueueId> myQueues = queueBalancer.GetMyQueues().ToList();

            Log(ErrorCode.PersistentStreamPullingManager_Starting, "Starting agents for {0} queues: {1}", myQueues.Count, PrintQueues(myQueues));
            await AddNewQueues(myQueues, true);

            Log(ErrorCode.PersistentStreamPullingManager_Started, "Started agents.");
        }
        public async Task StopAgents()
        {
            managerState = PersistentStreamProviderState.AgentsStopped;
            List <QueueId> queuesToRemove = queuesToAgentsMap.Keys.ToList();

            Log(ErrorCode.PersistentStreamPullingManager_Stopping, "Stopping agents for {0} queues: {1}", queuesToRemove.Count, PrintQueues(queuesToRemove));
            await RemoveQueues(queuesToRemove);

            Log(ErrorCode.PersistentStreamPullingManager_Stopped, "Stopped agents.");
        }
Exemple #7
0
        public async Task Init(string name, IProviderRuntime providerUtilitiesManager, IProviderConfiguration config)
        {
            if (!stateManager.PresetState(ProviderState.Initialized))
            {
                return;
            }
            if (String.IsNullOrEmpty(name))
            {
                throw new ArgumentNullException("name");
            }
            if (providerUtilitiesManager == null)
            {
                throw new ArgumentNullException("providerUtilitiesManager");
            }
            if (config == null)
            {
                throw new ArgumentNullException("config");
            }

            Name            = name;
            providerRuntime = (IStreamProviderRuntime)providerUtilitiesManager;
            logger          = providerRuntime.GetLogger(this.GetType().Name);
            adapterFactory  = new TAdapterFactory();
            adapterFactory.Init(config, Name, logger, providerRuntime.ServiceProvider);
            queueAdapter = await adapterFactory.CreateAdapter();

            myConfig = new PersistentStreamProviderConfig(config);
            string startup;

            if (config.Properties.TryGetValue(StartupStatePropertyName, out startup))
            {
                if (!Enum.TryParse(startup, true, out startupState))
                {
                    throw new ArgumentException(
                              String.Format("Unsupported value '{0}' for configuration parameter {1} of stream provider {2}.", startup, StartupStatePropertyName, config.Name));
                }
            }
            else
            {
                startupState = StartupStateDefaultValue;
            }

            logger.Info("Initialized PersistentStreamProvider<{0}> with name {1}, Adapter {2} and config {3}, {4} = {5}.",
                        typeof(TAdapterFactory).Name,
                        Name,
                        queueAdapter.Name,
                        myConfig,
                        StartupStatePropertyName, startupState);
            stateManager.CommitState();
        }
Exemple #8
0
        /// <summary>
        /// Adds a stream provider of type <see cref="AzureQueueStreamProvider"/>.
        /// </summary>
        /// <param name="config">The cluster configuration object to add provider to.</param>
        /// <param name="providerName">The provider name</param>
        /// <param name="connectionString">The azure storage connection string. If none is provided, it will use the same as in the Globals configuration.</param>
        /// <param name="numberOfQueues">The number of queues to use as partitions.</param>
        /// <param name="deploymentId">The deployment ID used for partitioning. If none is specified, the provider will use the same DeploymentId as the Cluster.</param>
        /// <param name="cacheSize">The cache size.</param>
        /// <param name="startupState">The startup state of the persistent stream provider.</param>
        /// <param name="persistentStreamProviderConfig">Settings related to all persistent stream providers.</param>
        public static void AddAzureQueueStreamProvider(
            this ClientConfiguration config,
            string providerName,
            string connectionString = null,
            int numberOfQueues      = AzureQueueAdapterFactory.NumQueuesDefaultValue,
            string deploymentId     = null,
            int cacheSize           = AzureQueueAdapterFactory.CacheSizeDefaultValue,
            PersistentStreamProviderState startupState = AzureQueueStreamProvider.StartupStateDefaultValue,
            PersistentStreamProviderConfig persistentStreamProviderConfig = null)
        {
            connectionString = GetConnectionString(connectionString, config);
            deploymentId     = deploymentId ?? config.DeploymentId;
            var properties = GetAzureQueueStreamProviderProperties(providerName, connectionString, numberOfQueues, deploymentId, cacheSize, startupState, persistentStreamProviderConfig);

            config.RegisterStreamProvider <AzureQueueStreamProvider>(providerName, properties);
        }
Exemple #9
0
        /// <summary>
        /// Adds a stream provider of type <see cref="AzureQueueStreamProviderV2"/>.
        /// </summary>
        /// <param name="config">The cluster configuration object to add provider to.</param>
        /// <param name="providerName">The provider name</param>
        /// <param name="connectionString">The azure storage connection string. If none is provided, it will use the same as in the Globals configuration.</param>
        /// <param name="numberOfQueues">The number of queues to use as partitions.</param>
        /// <param name="clusterId">The ClusterId used for partitioning. If none is specified, the provider will use the same ClusterId as the Cluster.</param>
        /// <param name="cacheSize">The cache size.</param>
        /// <param name="startupState">The startup state of the persistent stream provider.</param>
        /// <param name="persistentStreamProviderConfig">Settings related to all persistent stream providers.</param>
        public static void AddAzureQueueStreamProviderV2(
            this ClusterConfiguration config,
            string providerName,
            string connectionString = null,
            int numberOfQueues      = AzureQueueAdapterConstants.NumQueuesDefaultValue,
            string clusterId        = null,
            int cacheSize           = AzureQueueAdapterConstants.CacheSizeDefaultValue,
#pragma warning disable 618
            PersistentStreamProviderState startupState = AzureQueueStreamProvider.StartupStateDefaultValue,
#pragma warning restore 618
            PersistentStreamProviderConfig persistentStreamProviderConfig = null)
        {
            connectionString = GetConnectionString(connectionString, config);
            clusterId        = clusterId ?? config.Globals.ClusterId;
            var properties = GetAzureQueueStreamProviderProperties(providerName, connectionString, numberOfQueues, clusterId, cacheSize, startupState, persistentStreamProviderConfig);

            config.Globals.RegisterStreamProvider <AzureQueueStreamProviderV2>(providerName, properties);
        }
        /// <summary>
        /// Adds a stream provider of type <see cref="AzureQueueStreamProvider"/>.
        /// </summary>
        /// <param name="config">The cluster configuration object to add provider to.</param>
        /// <param name="providerName">The provider name</param>
        /// <param name="connectionString">The azure storage connection string. If none is provided, it will use the same as in the Globals configuration.</param>
        /// <param name="numberOfQueues">The number of queues to use as partitions.</param>
        /// <param name="deploymentId">The deployment ID used for partitioning. If none is specified, the provider will use the same DeploymentId as the Cluster.</param>
        /// <param name="cacheSize">The cache size.</param>
        /// <param name="startupState">The startup state of the persistent stream provider.</param>
        /// <param name="persistentStreamProviderConfig">Settings related to all persistent stream providers.</param>
        public static void AddAzureQueueStreamProvider(
            this ClusterConfiguration config,
            string providerName,
            string connectionString = null,
            int numberOfQueues      = AzureQueueAdapterConstants.NumQueuesDefaultValue,
            string deploymentId     = null,
            int cacheSize           = AzureQueueAdapterConstants.CacheSizeDefaultValue,
#pragma warning disable CS0618 // Type or member is obsolete
            PersistentStreamProviderState startupState = AzureQueueStreamProvider.StartupStateDefaultValue,
#pragma warning restore CS0618 // Type or member is obsolete
            PersistentStreamProviderConfig persistentStreamProviderConfig = null)
        {
            connectionString = GetConnectionString(connectionString, config);
            deploymentId     = deploymentId ?? config.Globals.DeploymentId;
            var properties = GetAzureQueueStreamProviderProperties(providerName, connectionString, numberOfQueues, deploymentId, cacheSize, startupState, persistentStreamProviderConfig);

#pragma warning disable 618
            config.Globals.RegisterStreamProvider <AzureQueueStreamProvider>(providerName, properties);
#pragma warning restore 618
        }
        public async Task Initialize(Immutable <IQueueAdapter> qAdapter)
        {
            if (qAdapter.Value == null)
            {
                throw new ArgumentNullException("qAdapter", "Init: queueAdapter should not be null");
            }

            Log(ErrorCode.PersistentStreamPullingManager_02, "Init.");

            // Remove cast once we cleanup
            queueAdapter = qAdapter.Value;
            await this.queueBalancer.Initialize(this.streamProviderName, this.adapterFactory.GetStreamQueueMapper(), config.SiloMaturityPeriod, this.providerConfig);

            queueBalancer.SubscribeToQueueDistributionChangeEvents(this);

            List <QueueId> myQueues = queueBalancer.GetMyQueues().ToList();

            Log(ErrorCode.PersistentStreamPullingManager_03, String.Format("Initialize: I am now responsible for {0} queues: {1}.", myQueues.Count, PrintQueues(myQueues)));

            queuePrintTimer = this.RegisterTimer(AsyncTimerCallback, null, QUEUES_PRINT_PERIOD, QUEUES_PRINT_PERIOD);
            managerState    = PersistentStreamProviderState.Initialized;
        }
        public Task Initialize(Immutable <IQueueAdapter> qAdapter)
        {
            if (qAdapter.Value == null)
            {
                throw new ArgumentNullException("qAdapter", "Init: queueAdapter should not be null");
            }

            logger.Info((int)ErrorCode.PersistentStreamPullingManager_02, "Init.");

            // Remove cast once we cleanup
            queueAdapter = qAdapter.Value;

            var meAsQueueBalanceListener = this.AsReference <IStreamQueueBalanceListener>();

            queueBalancer.SubscribeToQueueDistributionChangeEvents(meAsQueueBalanceListener);

            List <QueueId> myQueues = queueBalancer.GetMyQueues().ToList();

            logger.Info((int)ErrorCode.PersistentStreamPullingManager_03, String.Format("I am now responsible for {0} queues: {1}.", myQueues.Count, PrintQueues(myQueues)));

            managerState = PersistentStreamProviderState.Initialized;
            return(TaskDone.Done);
        }
        public Task Initialize(Immutable <IQueueAdapter> qAdapter)
        {
            if (qAdapter.Value == null)
            {
                throw new ArgumentNullException("qAdapter", "Init: queueAdapter should not be null");
            }

            Log(ErrorCode.PersistentStreamPullingManager_02, "Init.");

            // Remove cast once we cleanup
            queueAdapter = qAdapter.Value;

            var meAsQueueBalanceListener = this.AsReference <IStreamQueueBalanceListener>();

            queueBalancer.SubscribeToQueueDistributionChangeEvents(meAsQueueBalanceListener);

            List <QueueId> myQueues = queueBalancer.GetMyQueues().ToList();

            Log(ErrorCode.PersistentStreamPullingManager_03, String.Format("Initialize: I am now responsible for {0} queues: {1}.", myQueues.Count, PrintQueues(myQueues)));

            queuePrintTimer = this.RegisterTimer(AsyncTimerCallback, null, QUEUES_PRINT_PERIOD, QUEUES_PRINT_PERIOD);
            managerState    = PersistentStreamProviderState.Initialized;
            return(Task.CompletedTask);
        }
 public async Task StopAgents()
 {
     managerState = PersistentStreamProviderState.AgentsStopped;
     List<QueueId> queuesToRemove = queuesToAgentsMap.Keys.ToList();
     Log(ErrorCode.PersistentStreamPullingManager_Stopping, "Stopping agents for {0} queues: {1}", queuesToRemove.Count, PrintQueues(queuesToRemove));
     await RemoveQueues(queuesToRemove);
     Log(ErrorCode.PersistentStreamPullingManager_Stopped, "Stopped agents.");
 }
        public async Task StartAgents()
        {
            managerState = PersistentStreamProviderState.AgentsStarted;
            List<QueueId> myQueues = queueBalancer.GetMyQueues().ToList();

            Log(ErrorCode.PersistentStreamPullingManager_Starting, "Starting agents for {0} queues: {1}", myQueues.Count, PrintQueues(myQueues));
            await AddNewQueues(myQueues, true);
            Log(ErrorCode.PersistentStreamPullingManager_Started, "Started agents.");
        }
        public Task Initialize(Immutable<IQueueAdapter> qAdapter)
        {
            if (qAdapter.Value == null) throw new ArgumentNullException("qAdapter", "Init: queueAdapter should not be null");

            Log(ErrorCode.PersistentStreamPullingManager_02, "Init.");

            // Remove cast once we cleanup
            queueAdapter = qAdapter.Value;

            var meAsQueueBalanceListener = this.AsReference<IStreamQueueBalanceListener>();
            queueBalancer.SubscribeToQueueDistributionChangeEvents(meAsQueueBalanceListener);

            List<QueueId> myQueues = queueBalancer.GetMyQueues().ToList();
            Log(ErrorCode.PersistentStreamPullingManager_03, String.Format("Initialize: I am now responsible for {0} queues: {1}.", myQueues.Count, PrintQueues(myQueues)));

            managerState = PersistentStreamProviderState.Initialized;
            return TaskDone.Done;
        }
        public async Task Init(string name, IProviderRuntime providerUtilitiesManager, IProviderConfiguration config)
        {
            if (String.IsNullOrEmpty(name))
            {
                throw new ArgumentNullException("name");
            }
            if (providerUtilitiesManager == null)
            {
                throw new ArgumentNullException("providerUtilitiesManager");
            }
            if (config == null)
            {
                throw new ArgumentNullException("config");
            }

            Name            = name;
            providerRuntime = (IStreamProviderRuntime)providerUtilitiesManager;
            logger          = providerRuntime.GetLogger(this.GetType().Name);
            adapterFactory  = new TAdapterFactory();
            adapterFactory.Init(config, Name, logger);
            queueAdapter = await adapterFactory.CreateAdapter();

            string timePeriod;

            if (!config.Properties.TryGetValue(GET_QUEUE_MESSAGES_TIMER_PERIOD, out timePeriod))
            {
                getQueueMsgsTimerPeriod = DEFAULT_GET_QUEUE_MESSAGES_TIMER_PERIOD;
            }
            else
            {
                getQueueMsgsTimerPeriod = ConfigUtilities.ParseTimeSpan(timePeriod,
                                                                        "Invalid time value for the " + GET_QUEUE_MESSAGES_TIMER_PERIOD + " property in the provider config values.");
            }

            string timeout;

            if (!config.Properties.TryGetValue(INIT_QUEUE_TIMEOUT, out timeout))
            {
                initQueueTimeout = DEFAULT_INIT_QUEUE_TIMEOUT;
            }
            else
            {
                initQueueTimeout = ConfigUtilities.ParseTimeSpan(timeout,
                                                                 "Invalid time value for the " + INIT_QUEUE_TIMEOUT + " property in the provider config values.");
            }

            string balanceTypeString;

            balancerType = !config.Properties.TryGetValue(QUEUE_BALANCER_TYPE, out balanceTypeString)
                ? DEFAULT_STREAM_QUEUE_BALANCER_TYPE
                : (StreamQueueBalancerType)Enum.Parse(typeof(StreamQueueBalancerType), balanceTypeString);

            if (!config.Properties.TryGetValue(MAX_EVENT_DELIVERY_TIME, out timeout))
            {
                maxEventDeliveryTime = DEFAULT_MAX_EVENT_DELIVERY_TIME;
            }
            else
            {
                maxEventDeliveryTime = ConfigUtilities.ParseTimeSpan(timeout,
                                                                     "Invalid time value for the " + MAX_EVENT_DELIVERY_TIME + " property in the provider config values.");
            }

            string pubSubTypeString;

            pubSubType = !config.Properties.TryGetValue(STREAM_PUBSUB_TYPE, out pubSubTypeString)
                ? DEFAULT_STREAM_PUBSUB_TYPE
                : (StreamPubSubType)Enum.Parse(typeof(StreamPubSubType), pubSubTypeString);

            string startup;

            if (config.Properties.TryGetValue(STARTUP_STATE, out startup))
            {
                if (!Enum.TryParse(startup, true, out startupState))
                {
                    throw new ArgumentException(
                              String.Format("Unsupported value '{0}' for configuration parameter {1} of stream provider {2}.", startup, STARTUP_STATE, config.Name));
                }
            }
            else
            {
                startupState = PersistentStreamProviderState.AgentsStarted;
            }

            logger.Info("Initialized PersistentStreamProvider<{0}> with name {1}, {2} = {3}, {4} = {5}, {6} = {7} and with Adapter {8}.",
                        typeof(TAdapterFactory).Name, Name,
                        GET_QUEUE_MESSAGES_TIMER_PERIOD, getQueueMsgsTimerPeriod,
                        INIT_QUEUE_TIMEOUT, initQueueTimeout,
                        STARTUP_STATE, startupState,
                        queueAdapter.Name);
        }
Exemple #18
0
        private static Dictionary <string, string> GetAzureQueueStreamProviderProperties(string providerName, string connectionString, int numberOfQueues, string deploymentId, int cacheSize, PersistentStreamProviderState startupState, PersistentStreamProviderConfig persistentStreamProviderConfig)
        {
            if (string.IsNullOrWhiteSpace(providerName))
            {
                throw new ArgumentNullException(nameof(providerName));
            }
            if (numberOfQueues < 1)
            {
                throw new ArgumentOutOfRangeException(nameof(numberOfQueues));
            }

            var properties = new Dictionary <string, string>
            {
                { AzureQueueAdapterFactory.DataConnectionStringPropertyName, connectionString },
                { AzureQueueAdapterFactory.NumQueuesPropertyName, numberOfQueues.ToString() },
                { AzureQueueAdapterFactory.DeploymentIdPropertyName, deploymentId },
                { SimpleQueueAdapterCache.CacheSizePropertyName, cacheSize.ToString() },
                { AzureQueueStreamProvider.StartupStatePropertyName, startupState.ToString() },
            };

            persistentStreamProviderConfig?.WriteProperties(properties);

            return(properties);
        }
        private async Task ValidateAgentsState(PersistentStreamProviderState expectedState)
        {
            var mgmt = GrainClient.GrainFactory.GetGrain<IManagementGrain>(0);
            var adapterType = AZURE_QUEUE_STREAM_PROVIDER_TYPE;
            var adapterName = AZURE_QUEUE_STREAM_PROVIDER_NAME;

            var states = await mgmt.SendControlCommandToProvider(adapterType, adapterName, (int)PersistentStreamProviderCommand.GetAgentsState);
            Assert.AreEqual(2, states.Length);
            foreach (var state in states.Cast<PersistentStreamProviderState>())
            {
                Assert.AreEqual(expectedState, state);
            }

            var numAgents = await mgmt.SendControlCommandToProvider(adapterType, adapterName, (int)PersistentStreamProviderCommand.GetNumberRunningAgents);
            Assert.AreEqual(2, numAgents.Length);
            int totalNumAgents = numAgents.Cast<int>().Sum();
            if (expectedState == PersistentStreamProviderState.AgentsStarted)
            {
                Assert.AreEqual(AzureQueueAdapterFactory.DEFAULT_NUM_QUEUES, totalNumAgents);
            }
            else
            {
                Assert.AreEqual(0, totalNumAgents);
            }
        }
        private static Dictionary<string, string> GetAzureQueueStreamProviderProperties(string providerName, string connectionString, int numberOfQueues, string deploymentId, int cacheSize, PersistentStreamProviderState startupState, PersistentStreamProviderConfig persistentStreamProviderConfig)
        {
            if (string.IsNullOrWhiteSpace(providerName)) throw new ArgumentNullException(nameof(providerName));
            if (numberOfQueues < 1) throw new ArgumentOutOfRangeException(nameof(numberOfQueues));

            var properties = new Dictionary<string, string>
            {
                { AzureQueueAdapterFactory.DataConnectionStringPropertyName, connectionString },
                { AzureQueueAdapterFactory.NumQueuesPropertyName, numberOfQueues.ToString() },
                { AzureQueueAdapterFactory.DeploymentIdPropertyName, deploymentId },
                { SimpleQueueAdapterCache.CacheSizePropertyName, cacheSize.ToString() },
                { AzureQueueStreamProvider.StartupStatePropertyName, startupState.ToString() },
            };

            persistentStreamProviderConfig?.WriteProperties(properties);

            return properties;
        }
 /// <summary>
 /// Adds a stream provider of type <see cref="AzureQueueStreamProvider"/>.
 /// </summary>
 /// <param name="config">The cluster configuration object to add provider to.</param>
 /// <param name="providerName">The provider name</param>
 /// <param name="connectionString">The azure storage connection string. If none is provided, it will use the same as in the Globals configuration.</param>
 /// <param name="numberOfQueues">The number of queues to use as partitions.</param>
 /// <param name="deploymentId">The deployment ID used for partitioning. If none is specified, the provider will use the same DeploymentId as the Cluster.</param>
 /// <param name="cacheSize">The cache size.</param>
 /// <param name="startupState">The startup state of the persistent stream provider.</param>
 /// <param name="persistentStreamProviderConfig">Settings related to all persistent stream providers.</param>
 public static void AddAzureQueueStreamProvider(
     this ClusterConfiguration config,
     string providerName,
     string connectionString = null,
     int numberOfQueues = AzureQueueAdapterFactory.NumQueuesDefaultValue,
     string deploymentId = null,
     int cacheSize = AzureQueueAdapterFactory.CacheSizeDefaultValue,
     PersistentStreamProviderState startupState = AzureQueueStreamProvider.StartupStateDefaultValue,
     PersistentStreamProviderConfig persistentStreamProviderConfig = null)
 {
     connectionString = GetConnectionString(connectionString, config);
     deploymentId = deploymentId ?? config.Globals.DeploymentId;
     var properties = GetAzureQueueStreamProviderProperties(providerName, connectionString, numberOfQueues, deploymentId, cacheSize, startupState, persistentStreamProviderConfig);
     config.Globals.RegisterStreamProvider<AzureQueueStreamProvider>(providerName, properties);
 }